gStreamer is pretty complicated to learn and understand if you never have worked with this before, but the benefit is great.
After fresh install of rasbian wheezy image, run raspi-config and set your language ect. Im also set overclock to medium.
Bellow is a step by step for installing gStreamer into RPI with rasbian image.
sudo apt-get install proftpd-basic
sudo apt-get install inadyn (Only needed if using TCP server)
sudo aptitude install libv4l-0 v4l-utils
echo "deb http://vontaene.de/raspbian-updates/ . main " >> /etc/apt/sources.list
sudo apt-get update
sudo apt-get install gstreamer1.0 ffmpeg
sudo modprobe ipv6
reboot
Be aware of section 7. "sudo modprobe ipv6" You will need to run this every time after reboot or add it to startup script.
Bellow is a working code snippet for RPI using Web-cam or GoPro.
You need to add Ip adress for you GCS or DynDns address.
#!/bin/bash
modprobe easycap 'bars=0'
#320x240
#360x288
#640x480
#704x576
WIDTH=640
HEIGHT=480
ip=
v4l2-ctl --set-fmt-video=width=$WIDTH,height=$HEIGHT,pixelformat=1
v4l2-ctl -i 1
gst-launch-1.0 -v \
rtpbin name=rtpbin v4l2src device=/dev/video0 \
! video/x-raw,width=$WIDTH,height=$HEIGHT,framerate=25/1 \
! queue \
! omxh264enc target-bitrate=900000 control-rate=3 \
! "video/x-h264,profile=high" \
! h264parse \
! queue max-size-bytes=10000000 \
! rtph264pay pt=96 config-interval=1 \
! rtpbin.send_rtp_sink_0 rtpbin.send_rtp_src_0 \
! udpsink port=5000 host=$ip ts-offset=0 name=vrtpsink rtpbin.send_rtcp_src_0 \
! udpsink port=5001 host=$ip sync=false async=false name=vrtcpsink udpsrc port=5005 name=vrtpsrc \
! rtpbin.recv_rtcp_sink_0
Ground Control Station
For receiving the gStreamer pipeline at your GCS, you can use VLC or Gstreamer running at windows or linux platform. I will post both methods.
VLC
Create a file with .sdp extension and insert below content. Open the file in vlc player.
This snippet will recive video at port 5000.
v=0
s=ESP H264+AAC STREAM
m=video 5000 RTP/AVP 96
a=rtpmap:96 H264/90000
a=fmtp:96 media=video; clock-rate=90000; encoding-name=H264; sprop-parameter-
sets=Z2QAKK2EBUViuKxUdCAqKxXFYqOhAVFYrisVHQgKisVxWKjoQFRWK4rFR0ICorFcVio6ECSFITk8nyfk/k/J8nm5s00IEkKQnJ5Pk/J/J+T5PNzZprQFoeyA,aO48sA==
a=control:trackID=1
If you want to Transcode the video to e.g Mission Planner HUD, then add the following line.
sout=#transcode{vcodec=MJPG,vb=1500,fps=15,scale=1,width=800,height=448,acodec=none}:duplicate{dst=http{mux=mpjpeg,dst=:8080/},dst=display} :sout-all :sout-keep
Right click in Mission Planner HUD and select source. 🙂
Gstreamer
If you want to use gStreamer which seems to be less latency than VLC then use below code.
Install gStreamer for windows. Open cmd line and go to gStreamer directory.
gst-launch-1.0 udpsrc caps="application/x-rtp, media=(string)video, clock-rate=(int)
90000, encoding-name=(string)H264, sampling=(string)YCbCr-4:4:4, depth=(string)8,
width=(string)320, height=(string)240, colorimetry=(string)SMPTE240M,
ssrc=(uint)1825678493, payload=(int)96, clock-base=(uint)4068866987,
seqnum-base=(uint)24582" port=5000 ! rtph264depay ! decodebin !queue! autovideosink
Gstreamer and Youtube Live
I was able to stream to Youtube-Live with this code snippet bellow using videotestsrc which just generating a test picture.
Make sure you have set up your Youtube-Live account correctly before testing. Remember to type in your correct live id in this script.
gst-launch-1.0 videotestsrc pattern=0 is-live=true ! timeoverlay
halignment=left valignment=bottom text="Stream time:" shaded-
background=true ! 'video/x-raw, format=(string)BGRA, pixel-aspect-
ratio=(fraction)1/1, interlace-mode=(string)progressive, width=320,
height=240, framerate=30/1' ! queue ! videoconvert ! x264enc
bitrate=4000 key-int-max=50 bframes=0 byte-stream=false aud=true
tune=zerolatency ! h264parse ! 'video/x-h264,level=
(string)'4.1',profile='main ! queue ! mux. audiotestsrc is-live=true !
'audio/x-raw, format=(string)S16LE, endianness=(int)1234, signed=
(boolean)true, width=(int)16, depth=(int)16, rate=(int)44100,
channels=(int)2' ! queue ! voaacenc bitrate=128000 ! aacparse !
audio/mpeg,mpegversion=4,stream-format=raw ! queue ! flvmux
streamable=true name=mux ! rtmpsink
location="rtmp://a.rtmp.youtube.com/live2/your_live_id_code
live=true flashver=FMLE/3.0(compatible;FMSc/1.0)"
If you want to use Video0 and and not Videotestsrc, you can use this code snippet.
gst-launch-1.0 rtpbin name=rtpbin v4l2src device=/dev/video0 !
video/x-raw, gop-size=15, pixel-aspect-ratio=1/1, width=320,
height=240, framerate=5/1, control-rate=1 ! videoconvert ! x264enc
bitrate=4000 key-int-max=12 bframes=0 byte-stream=false aud=true
tune=zerolatency ! h264parse ! queue max-size-bytes=10000000 !
'video/x-h264,level=(string)'4.1',profile='high ! queue ! mux.
audiotestsrc is-live=t ! 'audio/x-raw, format=(string)S16LE,
endianness=(int)1234, signed=(boolean)true, width=(int)16, depth=
(int)16, rate=(int)44100, channels=(int)2' ! queue ! voaacenc
bitrate=128000 ! aacparse ! audio/mpeg,mpegversion=4,stream-format=raw
! queue ! flvmux streamable=true name=mux ! rtmpsink
location=rtmp://a.rtmp.youtube.com/live2/x/your_live_id_code
?videoKeyframeFrequency=1&totalDatarate=128 app=live2 flashVer="FME/3.0%20(compatible;%20FMSc%201.0)"
swfUrl=rtmp://a.rtmp.youtube.com/live2
I also found this Script (for YouTube Live, UStream, Akamai and Twitch) , but not tested yet.
#!/bin/bash
if [ $# != 1 ] ; then
echo "Parameter error"
echo "Usage : $0 you | you1 | you2 | aka | akamai | ustream"
exit
fi
################### YouTube Settings ###################
# These data are available to you when you create a Live event in YouTube
# First Camera - INSERT YOUR OWN DATA
youtube_auth1='myname.a1b2-c3d4-e5f6-g7h8'
# Second Camera - Optional
youtube_auth2=''
youtube_app='live2'
serverurl='rtmp://INSERT_YOUTUBE_SERVER_HERE/'$youtube_app
################### UStream Settings ###################
# RTMP URL from your UStream Account : See www.ustream.tv -> Channel -> Remote
rtmpurl='INSERT_YOUR_USTREAM_RTMP_URL_HERE'
# This is your Stream Key : See www.ustream.tv -> Channel -> Remote
streamkey='INSERT_YOUR_STREAM_KEY_HERE'
################### Twitch Settings ###################
twitch_server=live.twitch.tv
twitch_streamkey='INSERT_YOUR_STREAM_KEY_HERE'
# twitch_streamkey=live_12345678_6asdk3khhewrkhqe4k32AswlH6hrwd
################### Akamai Settings ###################
akamai_server='INSERT_YOUR_AKAMAI_SERVER_NAME_HERE'
akamai_user='INSERT_YOUR_AKAMAI_USER_NAME_HERE'
akamai_pass='INSERT_YOUR_AKAMAI_PASSWORD_NAME_HERE'
########################################################
# You can change the settings below to suit your needs
###################### Settings ########################
width=1280
height=720
audiorate=44100
channels=2
framerate='30/1'
vbitrate=4000
abitrate=128000
GST_DEBUG="--gst-debug=flvmux:0,rtmpsink:0"
###################### Settings ########################
########################################################
# THe following settings should not be changed
h264_level=4.1
h264_profile=main
h264_bframes=0
keyint=`echo "2 * $framerate" |bc`
datarate=`echo "$vbitrate + $abitrate / 1000" |bc`
flashver='FME/3.0%20(compatible;%20FMSc%201.0)'
akamai_flashver="flashver=FMLE/3.0(compatible;FMSc/1.0) playpath=I4Ckpath_12@44448"
########################################################
# This will detect gstreamer-1.0 over gstreamer-0.10
gstlaunch=`which gst-launch-1.0`
if [ X$gstlaunch != X ] ; then
VIDEOCONVERT=videoconvert
VIDEO='video/x-raw, format=(string)BGRA, pixel-aspect-ratio=(fraction)1/1, interlace-mode=(string)progressive'
AUDIO=audio/x-raw
# VIDEO=video/x-raw-yuv
vfid=string
afid="format=(string)S16LE, "
else
gstlaunch=`which gst-launch-0.10`
if [ X$gstlaunch != X ] ; then
VIDEOCONVERT=ffmpegcolorspace
VIDEO='video/x-raw-rgb, bpp=(int)32, depth=(int)32, endianness=(int)4321, red_mask=(int)65280, green_mask=(int)16711680, blue_mask=(int)-16777216, pixel-aspect-ratio=(fraction)1/1, interlaced=(boolean)false'
AUDIO=audio/x-raw-int
vfid=fourcc
afid=""
else
echo "Could not find gst-launch-1.0 or gst-launch-0.10. Stopping"
exit
fi
fi
case $1 in
you|you1|you2|youtube|youtube1|youtube2)
if [ $1 = you2 -o $1 = youtube2 ] ; then
auth="$youtube_auth2"
else
auth="$youtube_auth1"
fi
if [ X$auth = X ] ; then
echo "auth was not set YouTube"
exit 1
fi
ENCAUDIOFORMAT='aacparse ! audio/mpeg,mpegversion=4,stream-format=raw'
videoencoder="x264enc bitrate=$vbitrate key-int-max=$keyint bframes=$h264_bframes byte-stream=false aud=true tune=zerolatency"
audioencoder="faac bitrate=$abitrate"
location=$serverurl'/x/'$auth'?videoKeyframeFrequency=1&totalDatarate='$datarate' app='$youtube_app' flashVer='$flashver' swfUrl='$serverurl
;;
ustream)
videoencoder="x264enc bitrate=$vbitrate bframes=0"
#ENCAUDIOFORMAT='audio/mpeg'
ENCAUDIOFORMAT=mpegaudioparse
abitrate=`echo "$abitrate / 1000" | bc`
audioencoder="lamemp3enc bitrate=$abitrate ! mpegaudioparse"
location="$rtmpurl/$streamkey live=1 flashver=$flashver"
;;
twitch)
if [ $vbitrate -gt 3000] ; then vbitrate=3000 ; fi
videoencoder="x264enc bitrate=$vbitrate bframes=0"
ENCAUDIOFORMAT=mpegaudioparse
abitrate=`echo "$abitrate / 1000" | bc`
audioencoder="lamemp3enc bitrate=$abitrate ! mpegaudioparse"
location="rtmp://$twitch_server/app/$twitch_streamkey live=1 flashver=$flashver"
;;
aka | akamai)
videoencoder="x264enc bitrate=$vbitrate bframes=0"
audioencoder="faac bitrate=$abitrate"
ENCAUDIOFORMAT='aacparse ! audio/mpeg,mpegversion=4,stream-format=raw'
stream_key="live=true pubUser=$akamai_user pubPasswd=$akamai_pass"
location="rtmp://$akamai_server/EntryPoint $stream_key $akamai_flashver"
;;
*) echo 'Use youtube, akamai or ustream'
exit
esac
ENCVIDEOFORMAT='h264parse ! video/x-h264,level=(string)'$h264_level',profile='$h264_profile
VIDEOFORMAT=$VIDEO', framerate='$framerate', width='$width', height='$height
AUDIOFORMAT=$AUDIO', '$afid' endianness=(int)1234, signed=(boolean)true, width=(int)16, depth=(int)16, rate=(int)'$audiorate', channels=(int)'$channels
TIMEOLPARMS='halignment=left valignment=bottom text="Stream time:" shaded-background=true'
VIDEOSRC="videotestsrc pattern=0 is-live=true ! timeoverlay $TIMEOLPARMS"
AUDIOSRC="audiotestsrc is-live=true"
$gstlaunch -v $GST_DEBUG \
$VIDEOSRC !\
$VIDEOFORMAT !\
queue !\
$VIDEOCONVERT !\
$videoencoder !\
$ENCVIDEOFORMAT !\
queue !\
mux. $AUDIOSRC !\
$AUDIOFORMAT !\
queue !\
$audioencoder !\
$ENCAUDIOFORMAT !\
queue !\
flvmux streamable=true name=mux !\
queue !\
rtmpsink location="$location"