refactor(core): split the frozen-picture judgement so it stays under the complexity limit (#6870)

This commit is contained in:
Miguel Ángel
2026-10-31 02:13:23 +00:00
committed by GitHub
parent 2439b62acd
commit 2bd8cd95cb
+18 -10
View File
@@ -14,23 +14,31 @@ type Look = { film: number; time: number };
const looks = new WeakMap<HTMLVideoElement, Look>();
const stood = new WeakSet<HTMLVideoElement>();
function look(el: HTMLVideoElement, film: number): void {
looks.set(el, { film, time: el.currentTime });
}
function judge(clip: RuntimeMediaClip, el: HTMLVideoElement, last: Look, film: number): void {
const due = mediaSourceTimeAt(clip, film) - mediaSourceTimeAt(clip, last.film);
const moved = el.currentTime - last.time;
const standing = due >= FROZEN_PICTURE.minDueSeconds && moved < due * FROZEN_PICTURE.movedShare;
if (standing) stood.add(el);
else stood.delete(el);
}
/** Whether any video in the window shows nothing, or its clock stands still against its clip's own timing. */
export function hasFrozenPicture(clips: readonly RuntimeMediaClip[], filmTime: number): boolean {
let frozen = false;
for (const clip of clips) {
const el = clip.el;
if (!isVideoElement(el)) continue;
const look = looks.get(el);
if (!look || filmTime < look.film) {
looks.set(el, { film: filmTime, time: el.currentTime });
const last = looks.get(el);
if (!last || filmTime < last.film) {
look(el, filmTime);
stood.delete(el);
} else if (filmTime - look.film >= FROZEN_PICTURE.lookSeconds) {
const due = mediaSourceTimeAt(clip, filmTime) - mediaSourceTimeAt(clip, look.film);
if (due >= FROZEN_PICTURE.minDueSeconds) {
if (el.currentTime - look.time < due * FROZEN_PICTURE.movedShare) stood.add(el);
else stood.delete(el);
} else stood.delete(el);
looks.set(el, { film: filmTime, time: el.currentTime });
} else if (filmTime - last.film >= FROZEN_PICTURE.lookSeconds) {
judge(clip, el, last, filmTime);
look(el, filmTime);
}
if (el.readyState < HAVE_CURRENT_DATA || stood.has(el)) frozen = true;
}