summaryrefslogtreecommitdiff
path: root/prepare-videochat.sh
diff options
context:
space:
mode:
Diffstat (limited to 'prepare-videochat.sh')
-rwxr-xr-xprepare-videochat.sh151
1 files changed, 122 insertions, 29 deletions
diff --git a/prepare-videochat.sh b/prepare-videochat.sh
index 341a8e9..38a36d2 100755
--- a/prepare-videochat.sh
+++ b/prepare-videochat.sh
@@ -92,6 +92,11 @@ else
FLIP_METHOD=none
fi
+GST_FLIP="! videoflip method=\"$FLIP_METHOD\" "
+if [ $FLIP_METHOD = 'none' ]; then
+ GST_FLIP=""
+fi
+
### CONFIGURATION
# If your "adb" is not in your $PATH, set the full path to it here.
@@ -113,8 +118,6 @@ WIFI_IP=192.168.2.140
# Port on which IP Webcam is listening
PORT=8080
-# GStreamer debug string (see gst-launch manpage)
-GST_DEBUG=souphttpsrc:0,videoflip:0,ffmpegcolorspace:0,v4l2sink:0,pulse:0
### FUNCTIONS
@@ -156,7 +159,7 @@ url_reachable() {
if ! can_run curl && can_run apt-get; then
# Some versions of Ubuntu do not have curl by default (Arch
# has it in its core, so we don't need to check that case)
- sudo apt-get install curl
+ sudo apt-get install -y curl
fi
curl -sI "$1" >/dev/null
}
@@ -174,13 +177,48 @@ start_iw_server() {
sleep 2s
}
+if can_run lsb_release; then
+ DIST=`lsb_release -i | awk -F: '{print $2}'`
+ RELEASE=`lsb_release -r | awk -F: '{print $2}'`
+elif [ -f /etc/debian_version ] ; then
+ DIST="Debian"
+ RELEASE=`perl -ne 'chomp; if(m:(jessie|testing|sid):){print "8.0"}elsif(m:[\d\.]+:){print}else{print "0.0"}' < /etc/debian_version`
+fi
+
+GST_VER="0.10"
+GST_CONVERTER="ffmpegcolorspace"
+GST_MIMETYPE="video/x-raw-yuv"
+GST_FORMAT="format=(fourcc)YV12"
+
+GST_0_10_MIMETYPE=$GST_MIMETYPE
+GST_0_10_FORMAT=$GST_FORMAT
+
+if [ $DIST = "Debian" -a `echo "$RELEASE >= 8.0" | bc` -eq 1 ] ||\
+ [ $DIST = "Ubuntu" -a `echo "$RELEASE >= 14.04" | bc` -eq 1 ]
+then
+ GST_VER="1.0"
+ GST_CONVERTER="videoconvert"
+ GST_MIMETYPE="video/x-raw"
+ GST_FORMAT="format=YV12"
+fi
+
+# GStreamer debug string (see gst-launch manpage)
+GST_DEBUG=souphttpsrc:0,videoflip:0,$GST_CONVERTER:0,v4l2sink:0,pulse:0
+
### MAIN BODY
# Check if the user has v4l2loopback
if ! has_kernel_module v4l2loopback; then
- info "The v4l2loopback kernel module is not installed or could not be loaded. I will try to install the kernel module using your distro's package manager. If that doesn't work, please install v4l2loopback manually from github.com/umlaeute/v4l2loopback."
- if can_run apt-get; then
- sudo apt-get install python-apport v4l2loopback-dkms
+ info "The v4l2loopback kernel module is not installed or could not be loaded. Attempting to install the kernel module using your distro's package manager."
+ if [ $DIST = "Debian" ] || [ $DIST = "Ubuntu" ]; then
+ V4L2LOOPBACK_PKGS="v4l2loopback-dkms"
+ if [ $DIST = "Ubuntu" ]; then
+ V4L2LOOPBACK_PKGS="${V4L2LOOPBACK_PKGS} python-apport"
+ fi
+ sudo apt-get -y install $V4L2LOOPBACK_PKGS
+ if [ $? != 0 ]; then
+ info "Installation failed. Please install v4l2loopback manually from github.com/umlaeute/v4l2loopback."
+ fi
elif can_run yaourt; then
yaourt -S v4l2loopback-git
fi
@@ -192,12 +230,21 @@ if ! has_kernel_module v4l2loopback; then
fi
fi
+# check if the user has the pulse gst plugin installed
+if [ ! -f /usr/lib/*/gstreamer-$GST_VER/libgstpulse.so ]; then
+ if [ $DIST = "Debian" ] || [ $DIST = "Ubuntu" ]; then
+ sudo apt-get install -y gstreamer${GST_VER}-pulseaudio
+ elif can_run yaourt; then
+ echo "we should figure out what package supplies this"
+ fi
+fi
+
# Use the first "v4l2 loopback" device as the webcam: this should help
# when loading v4l2loopback on a system that already has a regular
# webcam.
if ! can_run v4l2-ctl; then
if can_run apt-get; then
- sudo apt-get install v4l-utils
+ sudo apt-get install -y v4l-utils
elif can_run pacman; then
sudo pacman -S v4l-utils
fi
@@ -241,38 +288,67 @@ while ! iw_server_is_started; do
info "The IP Webcam video feed is not reachable at $VIDEO_URL. Please open IP Webcam in your phone and start the server."
done
+SINK_NAME="ipwebcam"
# Load null-sink if needed
-if !(pactl list sinks | grep -q module-null-sink); then
- pactl load-module module-null-sink
+if !(pactl list sinks | grep -q $SINK_NAME); then
+ pactl load-module module-null-sink sink_name="$SINK_NAME" sink_properties="device.description='IP\ Webcam'"
fi
-NULL_SINK=$(LC_ALL=C pactl list sinks | \
- sed -n -e '/Name:/h; /module-null-sink/{x; s/\s*Name:\s*//g; p; q}' )
+SINK_ID=$(pactl list sinks | sed -n -e "/Owner Module:/h; /$SINK_NAME.monitor/{x; s/\s*Owner Module:\s*//g; p; q}")
+
+#DUPLEX_SINK_NAME="ipwebcam_mic"
+#if !(pactl list sinks | grep -q $DUPLEX_SINK_NAME); then
+# pactl load-module module-null-sink sink_name="$DUPLEX_SINK_NAME" sink_properties="device.description='IP\ Webcam\ and\ Mic\ MUX',filter.want=echo-cancel"
+#fi
+#DUPLEX_SINK_ID=$(pactl list sinks | sed -n -e "/Owner Module:/h; /$DUPLEX_SINK_NAME.monitor/{x; s/\s*Owner Module:\s*//g; p; q}")
+
+
+#if !(pactl list modules | grep -q "source=${SINK_NAME}.monitor sink=${DUPLEX_SINK_NAME}"); then
+# pactl load-module module-loopback source="${SINK_NAME}.monitor" sink="$DUPLEX_SINK_NAME"
+#fi
+#SINKMON_LOOP_ID=$(pactl list modules | sed -n -e "/Module #/h; /source=${SINK_NAME}.monitor sink=${DUPLEX_SINK_NAME}/{x; s/\s*Module #\s*//g; p; q}")
+
+DEFAULT_SINK=$(pacmd dump | mawk '/set-default-sink/ {print $2}')
+DEFAULT_SOURCE=$(pacmd dump | mawk '/set-default-source/ {print $2}')
+
+#if !(pactl list modules | grep -q "source=${DEFAULT_SINK} sink=${DUPLEX_SINK_NAME}"); then
+#if !(pactl list modules | grep -q "source=${DUPLEX_SINK_NAME}.monitor sink=${DEFAULT_SINK}"); then
+if !(pactl list modules | grep -q "source=${SINK_NAME}.monitor sink=${DEFAULT_SINK}"); then
+# pactl load-module module-loopback source=${DEFAULT_SINK} sink="$DUPLEX_SINK_NAME"
+# pactl load-module module-loopback source=${DUPLEX_SINK_NAME}.monitor sink="$DEFAULT_SINK"
+ pactl load-module module-loopback source=${SINK_NAME}.monitor sink="$DEFAULT_SINK"
+fi
+#DEFAULT_LOOP_ID=$(pactl list modules | sed -n -e "/Module #/h; /source=${DEFAULT_SOURCE} sink=${DUPLEX_SINK_NAME}/{x; s/\s*Module #\s*//g; p; q}")
+#DEFAULT_LOOP_ID=$(pactl list modules | sed -n -e "/Module #/h; /source=${DUPLEX_SINK_NAME}.monitor sink=${DEFAULT_SINK}/{x; s/\s*Module #\s*//g; p; q}")
+DEFAULT_LOOP_ID=$(pactl list modules | sed -n -e "/Module #/h; /source=${SINK_NAME}.monitor sink=${DEFAULT_SINK}/{x; s/\s*Module #\s*//g; p; q}")
+
+pactl load-module module-echo-cancel \
+ source_name="ipwebcam_efilter" source_master="${SINK_NAME}.monitor" source_properties="device.description='IP\ Webcam\ and\ Mic\ echo\ filter\ source'" \
+ sink_name="default_efilter" sink_master="${DEFAULT_SINK}" sink_properties="device.description='IP\ Webcam\ and\ Mic\ echo\ filter\ sink'" \
+ aec_method="webrtc" save_aec=1 use_volume_sharing=1
# Install and open pavucontrol as needed
if ! can_run pavucontrol; then
info "You don't have pavucontrol. I'll try to install its Debian/Ubuntu package."
- sudo apt-get install pavucontrol
+ sudo apt-get install -y pavucontrol
fi
if ! pgrep pavucontrol; then
- info "We will open now pavucontrol. You should leave it open to change the recording device of your video chat program to 'Monitor Null Output'. NOTE: make sure that in 'Output Devices' *all* devices are listed, and in the Playback tab the $GSTLAUNCH program sends its audio to the 'Null Sink'."
+ info "We will open now pavucontrol. You should leave it open to change the recording device of your video chat program to 'Monitor IP Webcam'. NOTE: make sure that in 'Output Devices' *all* devices are listed, and in the Playback tab the $GSTLAUNCH program sends its audio to the 'IP Webcam'."
pavucontrol &
fi
# Check for gst-launch
-GSTLAUNCH=gst-launch
-if can_run apt-get; then
+GSTLAUNCH=gst-launch-${GST_VER}
+if [ $DIST = "Debian" ]; then
# Debian
- GSTLAUNCH=gst-launch
if ! can_run "$GSTLAUNCH"; then
info "You don't have gst-launch. I'll try to install its Debian/Ubuntu package."
- sudo apt-get install gstreamer-tools
+ sudo apt-get install -y gstreamer${GST_VER}-tools
fi
elif can_run pacman; then
# Arch
- GSTLAUNCH=gst-launch-0.10
if ! can_run "$GSTLAUNCH"; then
info "You don't have gst-launch. I'll try to install its Arch package."
- sudo pacman -S gstreamer0.10 gstreamer0.10-good-plugins
+ sudo pacman -S gstreamer${GST_VER} gstreamer${GST_VER}-good-plugins
fi
fi
if ! can_run "$GSTLAUNCH"; then
@@ -282,18 +358,35 @@ fi
# Start the GStreamer graph needed to grab the video and audio
set +e
-info "Using IP Webcam as webcam/microphone through v4l2loopback device $DEVICE and PulseAudio sink '$NULL_SINK'. You can now open your videochat app."
+info "Using IP Webcam as webcam/microphone through v4l2loopback device $DEVICE. Microphone is directed to $SINK_NAME and multiplexed with ${DEFAULT_SOURCE}. You can now open your videochat app."
+
+WIDTH=640
+HEIGHT=480
+GST_FPS=5
+DIMENSIONS="width=$WIDTH,height=$HEIGHT"
+
+GST_0_10_CAPS="$GST_0_10_MIMETYPE,$GST_0_10_FORMAT,$DIMENSIONS"
+CAPS="$GST_MIMETYPE,$GST_FORMAT,$DIMENSIONS,framerate=$GST_FPS/1" \
+#sudo v4l2loopback-ctl set-caps $GST_0_10_CAPS $DEVICE
+
"$GSTLAUNCH" -vt --gst-plugin-spew --gst-debug="$GST_DEBUG" \
- souphttpsrc location="http://$IP:$PORT/videofeed" do-timestamp=true is-live=true \
+ souphttpsrc location="$VIDEO_URL" do-timestamp=true is-live=true \
! multipartdemux \
! jpegdec \
- ! ffmpegcolorspace ! "video/x-raw-yuv, format=(fourcc)YV12" \
- ! videoflip method="$FLIP_METHOD" ! videorate ! "video/x-raw-yuv, framerate=25/1" \
- ! v4l2sink device="$DEVICE" \
- souphttpsrc location="http://$IP:$PORT/audio.wav" do-timestamp=true is-live=true \
- ! wavparse ! audioconvert \
- ! volume volume=3 ! rglimiter \
- ! pulsesink device="$NULL_SINK" sync=false \
- 2>&1 | tee feed.log
+ $GST_FLIP \
+ ! $GST_CONVERTER \
+ ! videoscale \
+ ! videorate \
+ ! $CAPS \
+ ! v4l2sink device="$DEVICE" sync=true \
+ souphttpsrc location="$AUDIO_URL" do-timestamp=true is-live=true \
+ ! wavparse \
+ ! audioconvert \
+ ! volume volume=3 \
+ ! rglimiter \
+ ! pulsesink device="$SINK_NAME" sync=true \
+ 2>&1 | tee feed.log
info "Disconnected from IP Webcam. Have a nice day!"
+
+pactl unload-module ${SINK_ID}