mirror of
https://github.com/shaka-project/shaka-player.git
synced 2026-06-13 15:46:46 +03:00
fix: Fix suspend caption rendering when captions container is not visible (#9959)
There are platforms (some WebKit STBs) where IntersectionObserver doesn't work well with fullscreen. Managing multiple videos on screen. Detecting which one opens in PiP and Fullscreen.
This commit is contained in:
committed by
GitHub
parent
a090001426
commit
d689f69c45
@@ -79,6 +79,11 @@ shaka.text.UITextDisplayer = class {
|
||||
});
|
||||
this.configureCaptionsTimer_();
|
||||
|
||||
/** @private {shaka.util.Timer} */
|
||||
this.applyVisibilityTimer_ = new shaka.util.Timer(() => {
|
||||
this.applyVisibility_();
|
||||
});
|
||||
|
||||
/**
|
||||
* Maps cues to cue elements. Specifically points out the wrapper element of
|
||||
* the cue (e.g. the HTML element to put nested cues inside).
|
||||
@@ -165,7 +170,9 @@ shaka.text.UITextDisplayer = class {
|
||||
const entry = entries[entries.length - 1];
|
||||
this.isContainerActuallyVisible_ =
|
||||
entry.isIntersecting && entry.intersectionRatio > 0;
|
||||
this.applyVisibility_();
|
||||
const captionsUpdatePeriod =
|
||||
this.config_?.captionsUpdatePeriod || 0.25;
|
||||
this.applyVisibilityTimer_.tickAfter(captionsUpdatePeriod);
|
||||
}
|
||||
}, options);
|
||||
goog.asserts.assert(this.videoContainer_,
|
||||
@@ -174,7 +181,11 @@ shaka.text.UITextDisplayer = class {
|
||||
}
|
||||
|
||||
this.eventManager_.listen(document, 'visibilitychange', (e) => {
|
||||
this.applyVisibility_();
|
||||
this.applyVisibilityTimer_.tickNow();
|
||||
});
|
||||
|
||||
this.eventManager_.listen(document, 'fullscreenchange', () => {
|
||||
this.applyVisibilityTimer_.tickNow();
|
||||
});
|
||||
|
||||
this.eventManager_.listenMulti(
|
||||
@@ -183,18 +194,18 @@ shaka.text.UITextDisplayer = class {
|
||||
'enterpictureinpicture',
|
||||
'leavepictureinpicture',
|
||||
], () => {
|
||||
this.applyVisibility_();
|
||||
this.applyVisibilityTimer_.tickNow();
|
||||
});
|
||||
|
||||
if ('documentPictureInPicture' in window) {
|
||||
this.eventManager_.listen(window.documentPictureInPicture, 'enter',
|
||||
(e) => {
|
||||
this.applyVisibility_();
|
||||
this.applyVisibilityTimer_.tickNow();
|
||||
|
||||
const event = /** @type {DocumentPictureInPictureEvent} */(e);
|
||||
const pipWindow = event.window;
|
||||
this.eventManager_.listenOnce(pipWindow, 'pagehide', () => {
|
||||
this.applyVisibility_();
|
||||
this.applyVisibilityTimer_.tickNow();
|
||||
});
|
||||
});
|
||||
}
|
||||
@@ -202,7 +213,7 @@ shaka.text.UITextDisplayer = class {
|
||||
const video = /** @type {HTMLVideoElement} */(this.video_);
|
||||
if (video.webkitPresentationMode || video.webkitSupportsFullscreen) {
|
||||
this.eventManager_.listen(video, 'webkitpresentationmodechanged', () => {
|
||||
this.applyVisibility_();
|
||||
this.applyVisibilityTimer_.tickNow();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -267,28 +278,22 @@ shaka.text.UITextDisplayer = class {
|
||||
|
||||
this.isTextVisible_ = false;
|
||||
this.cues_ = [];
|
||||
if (this.captionsTimer_) {
|
||||
this.captionsTimer_.stop();
|
||||
this.captionsTimer_ = null;
|
||||
}
|
||||
this.captionsTimer_?.stop();
|
||||
this.captionsTimer_ = null;
|
||||
this.applyVisibilityTimer_?.stop();
|
||||
this.applyVisibilityTimer_ = null;
|
||||
|
||||
this.currentCuesMap_.clear();
|
||||
|
||||
// Tear-down the event manager to ensure messages stop moving around.
|
||||
if (this.eventManager_) {
|
||||
this.eventManager_.release();
|
||||
this.eventManager_ = null;
|
||||
}
|
||||
this.eventManager_?.release();
|
||||
this.eventManager_ = null;
|
||||
|
||||
if (this.resizeObserver_) {
|
||||
this.resizeObserver_.disconnect();
|
||||
this.resizeObserver_ = null;
|
||||
}
|
||||
this.resizeObserver_?.disconnect();
|
||||
this.resizeObserver_ = null;
|
||||
|
||||
if (this.visibilityObserver_) {
|
||||
this.visibilityObserver_.disconnect();
|
||||
this.visibilityObserver_ = null;
|
||||
}
|
||||
this.visibilityObserver_?.disconnect();
|
||||
this.visibilityObserver_ = null;
|
||||
|
||||
return Promise.resolve();
|
||||
}
|
||||
@@ -380,17 +385,37 @@ shaka.text.UITextDisplayer = class {
|
||||
* @private
|
||||
*/
|
||||
applyVisibility_() {
|
||||
const isPiPActive = !!((window.documentPictureInPicture &&
|
||||
window.documentPictureInPicture.window) ||
|
||||
document.pictureInPictureElement);
|
||||
const video = /** @type {HTMLVideoElement} */(this.video_);
|
||||
let isPiPActive = false;
|
||||
if (window.documentPictureInPicture &&
|
||||
window.documentPictureInPicture.window) {
|
||||
isPiPActive = true;
|
||||
} else if (document.pictureInPictureElement === video) {
|
||||
isPiPActive = true;
|
||||
}
|
||||
let isFullscreenActive = false;
|
||||
if (document.fullscreenEnabled &&
|
||||
document.fullscreenElement === this.videoContainer_) {
|
||||
isFullscreenActive = true;
|
||||
} else if (video.webkitSupportsFullscreen) {
|
||||
isFullscreenActive = video.webkitDisplayingFullscreen;
|
||||
}
|
||||
const pageVisible = document.visibilityState === 'visible';
|
||||
const actuallyVisible =
|
||||
isPiPActive || (pageVisible && this.isContainerActuallyVisible_);
|
||||
const actuallyVisible = isPiPActive || isFullscreenActive ||
|
||||
(pageVisible && this.isContainerActuallyVisible_);
|
||||
if (actuallyVisible) {
|
||||
if (this.renderSuspended_) {
|
||||
this.renderSuspended_ = false;
|
||||
this.configureCaptionsTimer_();
|
||||
this.updateCaptions_();
|
||||
requestAnimationFrame(() => {
|
||||
if (!this.textContainer_) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (this.textContainer_.parentElement && this.isTextVisible_) {
|
||||
this.updateCaptions_();
|
||||
}
|
||||
});
|
||||
}
|
||||
} else {
|
||||
if (!this.renderSuspended_) {
|
||||
|
||||
Reference in New Issue
Block a user