From 9a408482ed47c96d91f3cdc359900a70e3beeb2e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=81lvaro=20Velad=20Galv=C3=A1n?= Date: Thu, 31 Oct 2024 08:32:00 +0100 Subject: [PATCH] perf(Ads): Reduce latency for interstitial to start playing (#7525) Previously we relied on an event triggered by the video itself which was launched 4 to 60 times per second, which meant that we had an update (in the worst case) of 250ms. Now we use a timer that is triggered every 25ms, which considerably reduces the delay. This is important so as not to show anything from the original ad's live. --- lib/ads/interstitial_ad_manager.js | 27 +++++++++++++++++++++++---- 1 file changed, 23 insertions(+), 4 deletions(-) diff --git a/lib/ads/interstitial_ad_manager.js b/lib/ads/interstitial_ad_manager.js index 7c3c28226b..cd6beddf88 100644 --- a/lib/ads/interstitial_ad_manager.js +++ b/lib/ads/interstitial_ad_manager.js @@ -93,10 +93,25 @@ shaka.ads.InterstitialAdManager = class { this.lastPlayedAd_ = null; this.eventManager_.listen(this.baseVideo_, 'timeupdate', () => { - if (this.playingAd_ || this.basePlayer_.isRemotePlayback()) { + if (this.playingAd_ || this.lastTime_ || + this.basePlayer_.isRemotePlayback()) { + return; + } + this.lastTime_ = this.baseVideo_.currentTime; + const currentInterstitial = this.getCurrentInterstitial_( + /* needPreRoll= */ true, /* numberToSkip= */ 0, this.lastPlayedAd_); + if (currentInterstitial) { + this.setupAd_(currentInterstitial, /* sequenceLength= */ 1, + /* adPosition= */ 1, /* initialTime= */ Date.now()); + } + }); + + /** @private {shaka.util.Timer} */ + this.timeUpdateTimer_ = new shaka.util.Timer(() => { + if (this.playingAd_ || !this.lastTime_ || + this.basePlayer_.isRemotePlayback()) { return; } - const needPreRoll = this.lastTime_ == null || this.lastTime_ == 0; this.lastTime_ = this.baseVideo_.currentTime; // Remove last played add when the new time is before to the ad time. if (this.lastPlayedAd_ && @@ -105,12 +120,12 @@ shaka.ads.InterstitialAdManager = class { this.lastPlayedAd_ = null; } const currentInterstitial = this.getCurrentInterstitial_( - needPreRoll, /* numberToSkip= */ 0, this.lastPlayedAd_); + /* needPreRoll= */ false, /* numberToSkip= */ 0, this.lastPlayedAd_); if (currentInterstitial) { this.setupAd_(currentInterstitial, /* sequenceLength= */ 1, /* adPosition= */ 1, /* initialTime= */ Date.now()); } - }); + }).tickEvery(/* seconds= */ 0.025); /** @private {shaka.util.Timer} */ this.pollTimer_ = new shaka.util.Timer(async () => { @@ -219,6 +234,10 @@ shaka.ads.InterstitialAdManager = class { if (this.adContainer_) { shaka.util.Dom.removeAllChildren(this.adContainer_); } + if (this.timeUpdateTimer_) { + this.timeUpdateTimer_.stop(); + this.timeUpdateTimer_ = null; + } if (this.pollTimer_) { this.pollTimer_.stop(); this.pollTimer_ = null;