From 4d72901ba7d32b0d495f8bd1cc79169f6f6874c7 Mon Sep 17 00:00:00 2001 From: Andrew S Date: Wed, 13 Mar 2024 12:29:44 -0500 Subject: [PATCH] Fix for DASH --- chrome/player/FastStreamClient.mjs | 39 +++++++++++++------- chrome/player/modules/dash.mjs | 45 ++++++++++++----------- chrome/player/players/dash/DashPlayer.mjs | 27 +++++++++----- 3 files changed, 67 insertions(+), 44 deletions(-) diff --git a/chrome/player/FastStreamClient.mjs b/chrome/player/FastStreamClient.mjs index 8af88289..81908f85 100644 --- a/chrome/player/FastStreamClient.mjs +++ b/chrome/player/FastStreamClient.mjs @@ -675,7 +675,9 @@ export class FastStreamClient extends EventEmitter { } hasDownloaded = true; - this.player.downloadFragment(nextDownload); + this.player.downloadFragment(nextDownload).catch((e) => { + + }); nextDownload = this.getNextToDownload(); if (index++ > 10000) { throw new Error('Infinite loop detected'); @@ -691,28 +693,37 @@ export class FastStreamClient extends EventEmitter { } predownloadReservedFragments() { - const fragments = this.getReservedFragments(this.fragments); - const audioFragments = this.getReservedFragments(this.audioFragments); - - if (audioFragments.length) { - let currentVideoIndex = 0; - audioFragments.forEach((fragment) => { - const videoFragment = fragments[currentVideoIndex]; - while (videoFragment && videoFragment.start < fragment.start) { - currentVideoIndex++; + const fragments = this.getWaitingReservedFragments(this.fragments); + const audioFragments = this.getWaitingReservedFragments(this.audioFragments); + + let hasDownloaded = false; + + if (audioFragments.length > 0 && ( + fragments.length === 0 || fragments[0].start > audioFragments[0].start + )) { + audioFragments.every((fragment) => { + if (!this.downloadManager.canGetFile(fragment.getContext())) { + return false; } + this.player.downloadFragment(fragment).catch((e) => { - fragments.splice(currentVideoIndex, 0, fragment); + }); + hasDownloaded = true; + return true; }); } - let hasDownloaded = false; + if (hasDownloaded) { + return true; + } fragments.every((fragment) => { if (!this.downloadManager.canGetFile(fragment.getContext())) { return false; } - this.player.downloadFragment(fragment); + this.player.downloadFragment(fragment).catch((e) => { + + }); hasDownloaded = true; return true; }); @@ -720,7 +731,7 @@ export class FastStreamClient extends EventEmitter { return hasDownloaded; } - getReservedFragments(fragments) { + getWaitingReservedFragments(fragments) { if (!fragments) return []; return fragments.filter((fragment) => { return fragment && fragment.status === DownloadStatus.WAITING && !fragment.canFree(); diff --git a/chrome/player/modules/dash.mjs b/chrome/player/modules/dash.mjs index 7ff7703f..9d676310 100644 --- a/chrome/player/modules/dash.mjs +++ b/chrome/player/modules/dash.mjs @@ -11865,7 +11865,7 @@ let dash; */ - function selectMediaInfo(newMediaInfo) { + function selectMediaInfo(newMediaInfo, customQuality = undefined) { if (newMediaInfo !== mediaInfo && (!newMediaInfo || !mediaInfo || newMediaInfo.type === mediaInfo.type)) { mediaInfo = newMediaInfo; } @@ -11880,20 +11880,24 @@ let dash; var quality, averageThroughput; var bitrate = null; - if ((realAdaptation === null || realAdaptation.id !== newRealAdaptation.id) && type !== Constants/* default.TEXT */.Z.TEXT) { - averageThroughput = abrController.getThroughputHistory().getAverageThroughput(type, isDynamic); - bitrate = averageThroughput || abrController.getInitialBitrateFor(type, streamInfo.id); - quality = abrController.getQualityForBitrate(mediaInfo, bitrate, streamInfo.id); + if (customQuality !== undefined) { + quality = customQuality; } else { - quality = abrController.getQualityFor(type, streamInfo.id); - } - - if (minIdx !== undefined && quality < minIdx) { - quality = minIdx; - } - - if (quality > maxQuality) { - quality = maxQuality; + if ((realAdaptation === null || realAdaptation.id !== newRealAdaptation.id) && type !== Constants/* default.TEXT */.Z.TEXT) { + averageThroughput = abrController.getThroughputHistory().getAverageThroughput(type, isDynamic); + bitrate = averageThroughput || abrController.getInitialBitrateFor(type, streamInfo.id); + quality = abrController.getQualityForBitrate(mediaInfo, bitrate, streamInfo.id); + } else { + quality = abrController.getQualityFor(type, streamInfo.id); + } + + if (minIdx !== undefined && quality < minIdx) { + quality = minIdx; + } + + if (quality > maxQuality) { + quality = maxQuality; + } } mediaInfo.representations = voRepresentations; @@ -17769,7 +17773,7 @@ let dash; manifestUpdater.refreshManifest(); } } else { - processor.selectMediaInfo(mediaInfo).then(function () { + processor.selectMediaInfo(mediaInfo, e.customQuality).then(function () { if (mediaInfo.type === Constants/* default.VIDEO */.Z.VIDEO || mediaInfo.type === Constants/* default.AUDIO */.Z.AUDIO) { abrController.updateTopQualityIndex(mediaInfo); } @@ -24015,8 +24019,7 @@ let dash; */ - function setTrack(track) { - var noSettingsSave = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false; + function setTrack(track, noSettingsSave = false, customQuality) { if (!track || !track.streamInfo) return; var type = track.type; var streamInfo = track.streamInfo; @@ -24029,6 +24032,7 @@ let dash; eventBus.trigger(Events/* default.CURRENT_TRACK_CHANGED */.Z.CURRENT_TRACK_CHANGED, { oldMediaInfo: current, newMediaInfo: track, + customQuality, switchMode: settings.get().streaming.trackSwitchMode[type] }, { streamId: id @@ -29651,7 +29655,7 @@ let dash; (0,SupervisorTools/* checkInteger */.SE)(newQuality); var topQualityIdx = getMaxAllowedIndexFor(type, streamId); - if (newQuality !== oldQuality && newQuality >= 0 && newQuality <= topQualityIdx) { + if ((reason?.forceReplace || newQuality !== oldQuality) && newQuality >= 0 && newQuality <= topQualityIdx) { _changeQuality(type, oldQuality, newQuality, topQualityIdx, reason, streamId); } } @@ -40958,14 +40962,13 @@ let dash; */ - function setCurrentTrack(track) { - var noSettingsSave = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : false; + function setCurrentTrack(track, noSettingsSave = false, customQuality) { if (!streamingInitialized) { throw STREAMING_NOT_INITIALIZED_ERROR; } - mediaController.setTrack(track, noSettingsSave); + mediaController.setTrack(track, noSettingsSave, customQuality); } /* --------------------------------------------------------------------------- diff --git a/chrome/player/players/dash/DashPlayer.mjs b/chrome/player/players/dash/DashPlayer.mjs index 2ceb8a5f..384497ef 100644 --- a/chrome/player/players/dash/DashPlayer.mjs +++ b/chrome/player/players/dash/DashPlayer.mjs @@ -49,7 +49,7 @@ export default class DashPlayer extends EventEmitter { }, }, // 'debug': { - // 'logLevel': DashJS.Debug.LOG_LEVEL_INFO, + // 'logLevel': DashJS.Debug.LOG_LEVEL_DEBUG, // }, }); @@ -86,13 +86,13 @@ export default class DashPlayer extends EventEmitter { }); this.dash.on('initFragmentNeeded', ()=>{ - if (this.desiredVideoLevel && this.currentLevel !== this.desiredVideoLevel) { - this.currentLevel = this.desiredVideoLevel; - } + // if (this.desiredVideoLevel && this.currentLevel !== this.desiredVideoLevel) { + // this.currentLevel = this.desiredVideoLevel; + // } - if (this.desiredAudioLevel && this.currentAudioLevel !== this.desiredAudioLevel) { - this.currentAudioLevel = this.desiredAudioLevel; - } + // if (this.desiredAudioLevel && this.currentAudioLevel !== this.desiredAudioLevel) { + // this.currentAudioLevel = this.desiredAudioLevel; + // } }); this.dash.on(DashJS.MediaPlayer.events.STREAM_INITIALIZED, (e) => { @@ -251,10 +251,18 @@ export default class DashPlayer extends EventEmitter { get levels() { const tracks = this.dash.getTracksFor('video'); - const currentLang = this.dash.getCurrentTrackFor('video')?.lang || navigator.language || 'en'; + const currentLang = this.getCurrentLang(); return TrackFilter.getLevelList(tracks, currentLang); } + getCurrentLang() { + try { + return this.dash.getCurrentTrackFor('video')?.lang || navigator.language || 'en'; + } catch (e) { + return navigator.language || 'en'; + } + } + get currentLevel() { const processor = this.dash.getStreamController()?.getActiveStream()?.getProcessors()?.find((o) => o.getType() === 'video'); if (!processor) { @@ -275,7 +283,8 @@ export default class DashPlayer extends EventEmitter { console.warn('Could not find video track', value); } this.desiredVideoLevel = value; - this.dash.setCurrentTrack(track); + + this.dash.setCurrentTrack(track, true, repIndex); this.dash.setQualityFor('video', repIndex, true); } catch (e) { console.warn(e);