diff --git a/src/app/channel/connectedUser.js b/src/app/channel/connectedUser.js index 54839ef..5347cb4 100644 --- a/src/app/channel/connectedUser.js +++ b/src/app/channel/connectedUser.js @@ -236,7 +236,7 @@ class connectedUser{ const chatBuffer = this.channel.chatBuffer.buffer; //Send off the metadata to our user's clients - this.emit("clientMetadata", {user: userObj, flairList, queueLock, chatBuffer, streamType: chanDB.settings.streamType, iceServers: config.iceServers}); + this.emit("clientMetadata", {user: userObj, flairList, queueLock, chatBuffer, streamType: chanDB.settings.streamType}); } /** diff --git a/src/app/channel/media/queue.js b/src/app/channel/media/queue.js index 8dbe0f6..5f9d4df 100644 --- a/src/app/channel/media/queue.js +++ b/src/app/channel/media/queue.js @@ -333,6 +333,7 @@ class queue{ let title = "Livestream"; let filename = '/'; let streamURL = '/'; + let rawLink = {combo: [['default', config.iceServers]]}; if(data != null && data.title != null){ //If the title is too long @@ -386,6 +387,7 @@ class queue{ //Kill schedule timers to prevent items from starting during the stream await this.stopScheduleTimers(); + //If we're streaming via HLS if(chanDB.settings.streamType == "livehls"){ //Syntatic sugar because I'm lazy :P streamURL = chanDB.settings.streamURL; @@ -406,6 +408,8 @@ class queue{ //Otherwise, hand over the filename filename = filename[1]; } + + rawLink = {combo:[['default',streamURL]]}; } //Create queued media object from stream URL and set it to nowPlaying @@ -416,7 +420,7 @@ class queue{ streamURL, chanDB.settings.streamType, 0, - streamURL, + rawLink, new Date().getTime() ); @@ -1266,7 +1270,7 @@ class queue{ } //If we're ending an HLS Livestream - if(wasPlaying.type == "livehls"){ + if(wasPlaying.type == "livehls" || wasPlaying.type == "webrtc"){ //Redirect to the endLivestream function return this.endLivestream(wasPlaying, chanDB) } @@ -1574,7 +1578,7 @@ class queue{ const stoppedMedia = this.nowPlaying; //Ignore early end for livestreams - if(this.nowPlaying.type != 'livehls'){ + if(this.nowPlaying.type != 'livehls' && this.nowPlaying.type != 'webrtc'){ //Get difference between current time and start time and set as early end stoppedMedia.earlyEnd = (new Date().getTime() - stoppedMedia.startTime) / 1000; } @@ -1811,7 +1815,7 @@ class queue{ const now = new Date().getTime(); //If something was playing - if(chanDB.media.nowPlaying != null && chanDB.media.nowPlaying.type != 'livehls'){ + if(chanDB.media.nowPlaying != null && (chanDB.media.nowPlaying.type != 'livehls' && chanDB.media.nowPlaying.type != 'webrtc')){ //Rehydrate the currently playing item int oa queued media object const wasPlaying = chanDB.media.nowPlaying.rehydrate(); diff --git a/www/js/channel/channel.js b/www/js/channel/channel.js index 96c85f0..840b939 100644 --- a/www/js/channel/channel.js +++ b/www/js/channel/channel.js @@ -153,9 +153,6 @@ class channel{ //Store streamType this.streamType = data.streamType; - - //Store URLs to known Internet Connectivitey Establishment servers. - this.iceServer = data.iceServers; } /** diff --git a/www/js/channel/mediaHandler.js b/www/js/channel/mediaHandler.js index 0923876..d98a792 100644 --- a/www/js/channel/mediaHandler.js +++ b/www/js/channel/mediaHandler.js @@ -926,4 +926,60 @@ class hlsLiveStreamHandler extends hlsBase{ } } } +} + +/** + * Wrapper handler for WebRTC Streams, calling back to webRTCHandler.js for heavy lifting + * @extends rawFileBase + */ +class WebRTCLivestreamHandler extends rawFileBase{ + /** + /** + * Instantiates a new WebRTCMediaHandler + * @param {channel} client - Parent Client Management Object + * @param {player} player - Parent Canopy Player Object + * @param {Object} media - De-hydrated media object from server + */ + constructor(client, player, media){ + //Call derived constructor + super(client, player, media, "webrtc"); + + /** + * Internet Connectivity Establishment configuration + */ + this.iceConfig = {iceServers: new Map(media.rawLink.combo).get('default')}; + + this.defineListeners(); + } + + defineListeners(){ + //Run derived method + super.defineListeners(); + + //Disable right clicking + this.video.addEventListener('contextmenu', (e)=>{e.preventDefault()}); + } + + start(){ + //call derived start function + super.start(); + + //Lock the player + this.setPlayerLock(true); + } + + setVideoTitle(title){ + //Add title as text content for security :P + this.player.title.innerText = `: ${utils.unescapeEntities(title)}`; + + //Create glow span + const glowSpan = document.createElement('span'); + //Fill glow span content + glowSpan.innerText = "🔴LIVE"; + //Set glowspan class + glowSpan.classList.add('critical-danger-text'); + + //Inject glowspan into title in a way that allows it to be easily replaced + this.player.title.prepend(glowSpan); + } } \ No newline at end of file diff --git a/www/js/channel/panels/queuePanel/queuePanel.js b/www/js/channel/panels/queuePanel/queuePanel.js index 023f1bd..6824d53 100644 --- a/www/js/channel/panels/queuePanel/queuePanel.js +++ b/www/js/channel/panels/queuePanel/queuePanel.js @@ -188,7 +188,7 @@ class queuePanel extends panelObj{ */ handleStart(data){ //If we're starting an HLS Livestream - if(data.media != null && data.media.type == 'livehls'){ + if(data.media != null && (data.media.type == 'livehls' || data.media.type == 'webrtc' )){ //Hide the 'goLive' controls this.goLiveDiv.style.display = 'none'; } @@ -282,7 +282,7 @@ class queuePanel extends panelObj{ client.socket.emit('getStreamType'); //If we're not livestreaming - if(client.player.mediaHandler.type != "livehls"){ + if(client.player.mediaHandler.type != "livehls" && client.player.mediaHandler.type != "webrtc"){ //If the div is hidden if(this.goLiveDiv.style.display == 'none'){ //Show the div @@ -1188,7 +1188,7 @@ class queuePanel extends panelObj{ const staleEntry = this.queueContainer.querySelector('.queue-entry.live'); //If we're not livestreaming - if(client.player.mediaHandler.type != "livehls"){ + if(client.player.mediaHandler.type != "livehls" && client.player.mediaHandler.type != "webrtc"){ //If we have a stale entry if(staleEntry != null){ //Remove stale entry since we're no longer streaming diff --git a/www/js/channel/player.js b/www/js/channel/player.js index 26413d6..a454e2e 100644 --- a/www/js/channel/player.js +++ b/www/js/channel/player.js @@ -188,6 +188,9 @@ class player{ }else if(data.media.type == "livehls"){ //Create a new HLS Livestream Handler for it this.mediaHandler = new hlsLiveStreamHandler(this.client, this, data.media); + }else if(data.media.type == "webrtc"){ + //Create a new HLS Livestream Handler for it + this.mediaHandler = new WebRTCLivestreamHandler(this.client, this, data.media); }else if(data.media.type == 'dm'){ this.mediaHandler = new hlsDailymotionHandler(this.client, this, data.media); //Otherwise, if we have a raw-file compatible source diff --git a/www/js/channelSettings.js b/www/js/channelSettings.js index 15fb613..a048b76 100644 --- a/www/js/channelSettings.js +++ b/www/js/channelSettings.js @@ -412,7 +412,7 @@ class livestreamPreferences{ handleTypeUpdate(data){ //If the stream type is HLS - if(data.streamType == "livehls"){ + if(data.streamType == "livehls" || data.streamType == "webrtc"){ //Ensure the hls button is checked this.hlsButton.checked = true; //Ensure the stream url input is enabled