diff --git a/python/www/flask/static/webrtc.js b/python/www/flask/static/webrtc.js index 199244743..f8487952c 100644 --- a/python/www/flask/static/webrtc.js +++ b/python/www/flask/static/webrtc.js @@ -196,12 +196,38 @@ function playStream(url, videoElement) { function sendStream(url, deviceId) { console.log(`sending stream ${url} (deviceId=${deviceId})`); - connections[url] = {}; - - connections[url].type = 'outbound'; - connections[url].deviceId = deviceId; - connections[url].webrtcConfig = { 'iceServers': [{ 'urls': 'stun:stun.l.google.com:19302' }] }; + if( url in connections && connections[url].type == 'outbound' ) { + // replace the outbound stream in the existing connection + replaceStream(url, deviceId); + return false; + } + else { + // create a new outbound connection + connections[url] = {}; + + connections[url].type = 'outbound'; + connections[url].deviceId = deviceId; + connections[url].webrtcConfig = { 'iceServers': [{ 'urls': 'stun:stun.l.google.com:19302' }] }; + + connections[url].websocket = new WebSocket(url); + connections[url].websocket.addEventListener('message', onServerMessage); + + return true; + } +} - connections[url].websocket = new WebSocket(url); - connections[url].websocket.addEventListener('message', onServerMessage); +function replaceStream(url, deviceId) { + console.log(`replacing stream for outbound WebRTC connection to ${url}`); + console.log(`old device ID: ${connections[url].deviceId}`); + console.log(`new device ID: ${deviceId}`); + + var constraints = {'audio': false, 'video': { deviceId: deviceId }}; + + navigator.mediaDevices.getUserMedia(constraints).then((stream) => { + const [videoTrack] = stream.getVideoTracks(); + const sender = connections[url].webrtcPeer.getSenders().find((s) => s.track.kind === videoTrack.kind); + console.log('found sender:', sender); + sender.replaceTrack(videoTrack); + connections[url].deviceId = deviceId; + }).catch(reportError); } diff --git a/python/www/flask/templates/index.html b/python/www/flask/templates/index.html index bfce879f1..ef7ee7015 100644 --- a/python/www/flask/templates/index.html +++ b/python/www/flask/templates/index.html @@ -24,8 +24,8 @@ }; send = function() { - sendStream(getWebsocketURL('input'), document.getElementById('send-stream').value); - play(); // autoplay browser stream + if( sendStream(getWebsocketURL('input'), document.getElementById('send-stream').value) ) + play(); // autoplay browser stream } window.onload = function() { diff --git a/python/www/html/index.html b/python/www/html/index.html index 0fc45b5a8..aa7eab857 100644 --- a/python/www/html/index.html +++ b/python/www/html/index.html @@ -12,8 +12,8 @@ }; send = function() { - sendStream(getWebsocketURL('input'), document.getElementById('send-stream').value); - play(); // autoplay browser stream + if( sendStream(getWebsocketURL('input'), document.getElementById('send-stream').value) ) + play(); // autoplay browser stream } window.onload = function() { diff --git a/python/www/html/webrtc.js b/python/www/html/webrtc.js index eba1aef83..0d92876fc 100644 --- a/python/www/html/webrtc.js +++ b/python/www/html/webrtc.js @@ -133,12 +133,38 @@ function playStream(url, videoElement) { function sendStream(url, deviceId) { console.log(`sending stream ${url} (deviceId=${deviceId})`); - connections[url] = {}; - - connections[url].type = 'outbound'; - connections[url].deviceId = deviceId; - connections[url].webrtcConfig = { 'iceServers': [{ 'urls': 'stun:stun.l.google.com:19302' }] }; + if( url in connections && connections[url].type == 'outbound' ) { + // replace the outbound stream in the existing connection + replaceStream(url, deviceId); + return false; + } + else { + // create a new outbound connection + connections[url] = {}; + + connections[url].type = 'outbound'; + connections[url].deviceId = deviceId; + connections[url].webrtcConfig = { 'iceServers': [{ 'urls': 'stun:stun.l.google.com:19302' }] }; + + connections[url].websocket = new WebSocket(url); + connections[url].websocket.addEventListener('message', onServerMessage); + + return true; + } +} - connections[url].websocket = new WebSocket(url); - connections[url].websocket.addEventListener('message', onServerMessage); +function replaceStream(url, deviceId) { + console.log(`replacing stream for outbound WebRTC connection to ${url}`); + console.log(`old device ID: ${connections[url].deviceId}`); + console.log(`new device ID: ${deviceId}`); + + var constraints = {'audio': false, 'video': { deviceId: deviceId }}; + + navigator.mediaDevices.getUserMedia(constraints).then((stream) => { + const [videoTrack] = stream.getVideoTracks(); + const sender = connections[url].webrtcPeer.getSenders().find((s) => s.track.kind === videoTrack.kind); + console.log('found sender:', sender); + sender.replaceTrack(videoTrack); + connections[url].deviceId = deviceId; + }).catch(reportError); } diff --git a/python/www/recognizer/static/webrtc.js b/python/www/recognizer/static/webrtc.js index 199244743..f8487952c 100644 --- a/python/www/recognizer/static/webrtc.js +++ b/python/www/recognizer/static/webrtc.js @@ -196,12 +196,38 @@ function playStream(url, videoElement) { function sendStream(url, deviceId) { console.log(`sending stream ${url} (deviceId=${deviceId})`); - connections[url] = {}; - - connections[url].type = 'outbound'; - connections[url].deviceId = deviceId; - connections[url].webrtcConfig = { 'iceServers': [{ 'urls': 'stun:stun.l.google.com:19302' }] }; + if( url in connections && connections[url].type == 'outbound' ) { + // replace the outbound stream in the existing connection + replaceStream(url, deviceId); + return false; + } + else { + // create a new outbound connection + connections[url] = {}; + + connections[url].type = 'outbound'; + connections[url].deviceId = deviceId; + connections[url].webrtcConfig = { 'iceServers': [{ 'urls': 'stun:stun.l.google.com:19302' }] }; + + connections[url].websocket = new WebSocket(url); + connections[url].websocket.addEventListener('message', onServerMessage); + + return true; + } +} - connections[url].websocket = new WebSocket(url); - connections[url].websocket.addEventListener('message', onServerMessage); +function replaceStream(url, deviceId) { + console.log(`replacing stream for outbound WebRTC connection to ${url}`); + console.log(`old device ID: ${connections[url].deviceId}`); + console.log(`new device ID: ${deviceId}`); + + var constraints = {'audio': false, 'video': { deviceId: deviceId }}; + + navigator.mediaDevices.getUserMedia(constraints).then((stream) => { + const [videoTrack] = stream.getVideoTracks(); + const sender = connections[url].webrtcPeer.getSenders().find((s) => s.track.kind === videoTrack.kind); + console.log('found sender:', sender); + sender.replaceTrack(videoTrack); + connections[url].deviceId = deviceId; + }).catch(reportError); } diff --git a/python/www/recognizer/templates/index.html b/python/www/recognizer/templates/index.html index 4a19aaab9..1141bb216 100644 --- a/python/www/recognizer/templates/index.html +++ b/python/www/recognizer/templates/index.html @@ -13,20 +13,21 @@ - - - + + + +