Goal:
On Raspberry Pi, take input from connected camera and microphone, combine into single stream, play across network using VLC app.
More details:
I am trying to make what amounts to an IP camera using a Raspberry Pi Zero W, a USB microphone, and a camera connected over the Pi's camera port.
The idea is for the live audio and video to be viewable only on my local network from any device that can run VLC player.
Video is Working
I have decided to use Gstreamer's command line tools to build this application, as it reportedly has lower latency than using something like cvlc or ffmpeg.
I have constructed a working video-only pipeline, based on code from this link.
#!/bin/bash
dstAdr=${1:-192.168.0.255}
raspivid -n -w 640 -h 480 -fps 20 -b 2000000 -a 12 -t 0 -o - \
| gst-launch-1.0 -v fdsrc \
! video/x-h264, width=640, height=480, framerate=20/1 \
! h264parse config-interval=-1 \
! mpegtsmux \
! udpsink host=$dstAdr port=5004
This stream is viewable from my PC and smartphone by opening the network stream udp://@:5004 in VLC.
How to Include Audio?
I have a USB microphone that I wish to use to capture live audio and include it in the MPEG stream. I have confirmed that the microphone is operational by recording a short clip from it and playing back the file on my PC.
Based on the description of Gstreamer muxes at this answer, I have created the following pipeline in an attempt to include the audio in the stream:
raspivid -n -w 640 -h 480 -fps 20 -b 2000000 -a 12 -t 0 -o - \
| gst-launch-1.0 -e -v fdsrc \
! video/x-h264, width=640, height=480, framerate=20/1 \
! h264parse config-interval=-1 \
! mpegtsmux name=mux \
! rtpmp2tpay \
! udpsink host=$dstAdr port=5004 \
alsasrc device=hw:1,0 \
! audio/x-raw, channels=1, rate=44100 \
! queue \
! lamemp3enc \
! mux.
The microphone only has 1 channel, and the rate has been double-checked as well. The pipeline does not immediately throw an error message, but VLC on other devices are not able to play the stream. After some time, this error message is displayed:
ERROR: from element /GstPipeline:pipeline0/GstAlsaSrc:alsasrc0: Internal data stream error.
Additional debug info:
gstbasesrc.c(3055): gst_base_src_loop (): /GstPipeline:pipeline0/GstAlsaSrc:alsasrc0:
streaming stopped, reason not-negotiated (-4)
EOS on shutdown enabled -- waiting for EOS after Error
Waiting for EOS...
ERROR: from element /GstPipeline:pipeline0/GstQueue:queue0: Internal data stream error.
Additional debug info:
gstqueue.c(988): gst_queue_handle_sink_event (): /GstPipeline:pipeline0/GstQueue:queue0:
streaming stopped, reason not-negotiated (-4)
Questions
- Are there additional options that need to be explicitly included in with
alsasrc? - Is it even possible to mux two live feeds into a single stream using the Gstreamer command line tools?
- Is it possible to do this using the Gstreamer C API?