Limit YouTube start prompt to join sync
This commit is contained in:
+26
-8
@@ -52,6 +52,7 @@ let currentYoutubeVideoId = "";
|
||||
let applyingWatchStateUntil = 0;
|
||||
let pauseEnforcementUntil = 0;
|
||||
let syncedPlaybackRetryUntil = 0;
|
||||
let youtubeStartPromptAllowedUntil = 0;
|
||||
let desiredYoutubePlaying = false;
|
||||
let youtubeReadyResolvers = [];
|
||||
let watchApplySequence = 0;
|
||||
@@ -348,7 +349,12 @@ async function ensureYoutubePlayer(initialState = {}) {
|
||||
iframe?.setAttribute("allow", "autoplay; encrypted-media; fullscreen; picture-in-picture");
|
||||
youtubeReadyResolvers.splice(0).forEach((resolve) => resolve());
|
||||
if (shouldAutoplay) {
|
||||
requestYoutubePlayback(youtubePlayer, initialVideoId, initialPosition);
|
||||
requestYoutubePlayback(
|
||||
youtubePlayer,
|
||||
initialVideoId,
|
||||
initialPosition,
|
||||
Boolean(initialState.allowStartPrompt)
|
||||
);
|
||||
}
|
||||
},
|
||||
onStateChange: handleYoutubeStateChange
|
||||
@@ -382,7 +388,7 @@ function setYoutubeStartPromptVisible(visible) {
|
||||
youtubeStartButton.hidden = !visible;
|
||||
}
|
||||
|
||||
function requestYoutubePlayback(player, videoId, position) {
|
||||
function requestYoutubePlayback(player, videoId, position, allowStartPrompt = false) {
|
||||
const requestId = ++youtubePlaybackRequestId;
|
||||
const startedAt = Date.now();
|
||||
|
||||
@@ -420,6 +426,8 @@ function requestYoutubePlayback(player, videoId, position) {
|
||||
requestId === youtubePlaybackRequestId &&
|
||||
desiredYoutubePlaying &&
|
||||
currentYoutubeVideoId === videoId &&
|
||||
allowStartPrompt &&
|
||||
Date.now() < youtubeStartPromptAllowedUntil &&
|
||||
player.getPlayerState?.() !== YT.PlayerState.PLAYING
|
||||
) {
|
||||
setYoutubeStartPromptVisible(true);
|
||||
@@ -476,7 +484,12 @@ function handleYoutubeStateChange(event) {
|
||||
now < syncedPlaybackRetryUntil &&
|
||||
[YT.PlayerState.UNSTARTED, YT.PlayerState.CUED, YT.PlayerState.PAUSED].includes(event.data)
|
||||
) {
|
||||
requestYoutubePlayback(youtubePlayer, currentYoutubeVideoId, currentYoutubeSnapshot().position);
|
||||
requestYoutubePlayback(
|
||||
youtubePlayer,
|
||||
currentYoutubeVideoId,
|
||||
currentYoutubeSnapshot().position,
|
||||
Date.now() < youtubeStartPromptAllowedUntil
|
||||
);
|
||||
return;
|
||||
}
|
||||
if (event.data === YT.PlayerState.PLAYING) {
|
||||
@@ -500,6 +513,7 @@ function handleYoutubeStateChange(event) {
|
||||
desiredYoutubePlaying = action === "play";
|
||||
if (desiredYoutubePlaying) {
|
||||
syncedPlaybackRetryUntil = 0;
|
||||
youtubeStartPromptAllowedUntil = 0;
|
||||
setYoutubeStartPromptVisible(false);
|
||||
} else {
|
||||
setYoutubeStartPromptVisible(false);
|
||||
@@ -523,7 +537,7 @@ function handleYoutubeStateChange(event) {
|
||||
}
|
||||
}
|
||||
|
||||
async function applyWatchState(state, { suppressEvents = true } = {}) {
|
||||
async function applyWatchState(state, { suppressEvents = true, allowStartPrompt = false } = {}) {
|
||||
const applySequence = ++watchApplySequence;
|
||||
const shouldPlay = state?.action === "play" || (!state?.action && Boolean(state?.playing));
|
||||
watchPlaylist = normalizedPlaylist(state?.playlist);
|
||||
@@ -541,6 +555,7 @@ async function applyWatchState(state, { suppressEvents = true } = {}) {
|
||||
desiredYoutubePlaying = false;
|
||||
youtubePlaybackRequestId++;
|
||||
syncedPlaybackRetryUntil = 0;
|
||||
youtubeStartPromptAllowedUntil = 0;
|
||||
setYoutubeStartPromptVisible(false);
|
||||
youtubePlayer?.stopVideo?.();
|
||||
youtubeShell.classList.remove("is-active");
|
||||
@@ -560,7 +575,8 @@ async function applyWatchState(state, { suppressEvents = true } = {}) {
|
||||
const player = await ensureYoutubePlayer({
|
||||
videoId: currentYoutubeVideoId,
|
||||
position,
|
||||
autoplay: shouldPlay
|
||||
autoplay: shouldPlay,
|
||||
allowStartPrompt
|
||||
});
|
||||
await whenYoutubeReady();
|
||||
if (applySequence !== watchApplySequence) return;
|
||||
@@ -572,15 +588,17 @@ async function applyWatchState(state, { suppressEvents = true } = {}) {
|
||||
if (suppressEvents) {
|
||||
syncedPlaybackRetryUntil = Date.now() + 8000;
|
||||
}
|
||||
youtubeStartPromptAllowedUntil = allowStartPrompt ? Date.now() + 10000 : 0;
|
||||
} else {
|
||||
youtubePlaybackRequestId++;
|
||||
syncedPlaybackRetryUntil = 0;
|
||||
youtubeStartPromptAllowedUntil = 0;
|
||||
setYoutubeStartPromptVisible(false);
|
||||
pauseEnforcementUntil = Math.max(pauseEnforcementUntil, Date.now() + 3000);
|
||||
}
|
||||
|
||||
if (shouldPlay) {
|
||||
setYoutubeStartPromptVisible(true);
|
||||
setYoutubeStartPromptVisible(allowStartPrompt);
|
||||
const sameVideo = player.getVideoData?.().video_id === currentYoutubeVideoId;
|
||||
const playerState = player.getPlayerState?.();
|
||||
if (sameVideo && ![YT.PlayerState.UNSTARTED, YT.PlayerState.CUED].includes(playerState)) {
|
||||
@@ -591,7 +609,7 @@ async function applyWatchState(state, { suppressEvents = true } = {}) {
|
||||
if (playerState !== YT.PlayerState.PLAYING) {
|
||||
player.playVideo();
|
||||
}
|
||||
requestYoutubePlayback(player, currentYoutubeVideoId, position);
|
||||
requestYoutubePlayback(player, currentYoutubeVideoId, position, allowStartPrompt);
|
||||
} else {
|
||||
if (player.getVideoData?.().video_id !== currentYoutubeVideoId) {
|
||||
player.cueVideoById(currentYoutubeVideoId, position);
|
||||
@@ -871,7 +889,7 @@ async function handleSignal(message) {
|
||||
peerId = message.peerId;
|
||||
setStatus(`Joined the call as ${displayName}. ${message.peers.length} other participant(s).`);
|
||||
if (message.watchState) {
|
||||
await applyWatchState(message.watchState);
|
||||
await applyWatchState(message.watchState, { allowStartPrompt: true });
|
||||
}
|
||||
if (message.presentationState?.sharing) {
|
||||
setTimeout(() => {
|
||||
|
||||
Reference in New Issue
Block a user