From 9e3da3cb35da71d339444158db359bfec63035a0 Mon Sep 17 00:00:00 2001 From: Matthias Date: Tue, 6 Feb 2024 13:06:19 +0100 Subject: [PATCH] Added liveUpdateTimeThreshold to control time syncing during live streams (#4382) * Added liveUpdateTimeThresholdInMilliseconds in order to control the frequency of time updates during live streams --- index.d.ts | 1 + src/core/Settings.js | 4 ++++ src/streaming/controllers/PlaybackController.js | 16 +++++++++++----- 3 files changed, 16 insertions(+), 5 deletions(-) diff --git a/index.d.ts b/index.d.ts index cdbe0a2367..3dbc1ea5f9 100644 --- a/index.d.ts +++ b/index.d.ts @@ -963,6 +963,7 @@ declare namespace dashjs { abandonLoadTimeout?: number, wallclockTimeUpdateInterval?: number, manifestUpdateRetryInterval?: number, + liveUpdateTimeThresholdInMilliseconds?: number, applyServiceDescription?: boolean, applyProducerReferenceTime?: boolean, applyContentSteering?: boolean, diff --git a/src/core/Settings.js b/src/core/Settings.js index 7e4f66d6a7..bbc8a87343 100644 --- a/src/core/Settings.js +++ b/src/core/Settings.js @@ -62,6 +62,7 @@ import Events from './events/Events'; * abandonLoadTimeout: 10000, * wallclockTimeUpdateInterval: 100, * manifestUpdateRetryInterval: 100, + * liveUpdateTimeThresholdInMilliseconds: 0, * cacheInitSegments: false, * applyServiceDescription: true, * applyProducerReferenceTime: true, @@ -744,6 +745,8 @@ import Events from './events/Events'; * How frequently the wallclockTimeUpdated internal event is triggered (in milliseconds). * @property {number} [manifestUpdateRetryInterval=100] * For live streams, set the interval-frequency in milliseconds at which dash.js will check if the current manifest is still processed before downloading the next manifest once the minimumUpdatePeriod time has. + * @property {number} [liveUpdateTimeThresholdInMilliseconds=0] + * For live streams, postpone syncing time updates until the threshold is passed. Increase if problems occurs during live streams on low end devices. * @property {boolean} [cacheInitSegments=false] * Enables the caching of init segments to avoid requesting the init segments before each representation switch. * @property {boolean} [applyServiceDescription=true] @@ -874,6 +877,7 @@ function Settings() { abandonLoadTimeout: 10000, wallclockTimeUpdateInterval: 100, manifestUpdateRetryInterval: 100, + liveUpdateTimeThresholdInMilliseconds: 0, cacheInitSegments: false, applyServiceDescription: true, applyProducerReferenceTime: true, diff --git a/src/streaming/controllers/PlaybackController.js b/src/streaming/controllers/PlaybackController.js index d0ce36d9c7..9f751adb75 100644 --- a/src/streaming/controllers/PlaybackController.js +++ b/src/streaming/controllers/PlaybackController.js @@ -58,6 +58,7 @@ function PlaybackController() { isDynamic, playOnceInitialized, lastLivePlaybackTime, + lastLiveUpdateTime, availabilityStartTime, availabilityTimeComplete, lowLatencyModeEnabled, @@ -88,6 +89,7 @@ function PlaybackController() { lowLatencyModeEnabled = false; initialCatchupModeActivated = false; seekTarget = NaN; + lastLiveUpdateTime = NaN; if (videoModel) { eventBus.off(Events.DATA_UPDATE_COMPLETED, _onDataUpdateCompleted, instance); @@ -723,11 +725,15 @@ function PlaybackController() { // Updates playback time for paused dynamic streams // (video element doesn't call timeupdate when the playback is paused) if (getIsDynamic()) { - streamController.addDVRMetric(); - if (isPaused()) { - _updateLivePlaybackTime(); - } else { - updateCurrentTime(); + const now = Date.now(); + if (isNaN(lastLiveUpdateTime) || now > lastLiveUpdateTime + settings.get().streaming.liveUpdateTimeThresholdInMilliseconds) { + streamController.addDVRMetric(); + if (isPaused()) { + _updateLivePlaybackTime(); + } else { + updateCurrentTime(); + } + lastLiveUpdateTime = now; } } }