mirror of
https://github.com/screentinker/screentinker.git
synced 2026-05-15 07:32:23 -06:00
Fix player video cycling bug and connecting overlay during cached playback
Clear pending advance timers when switching content items to prevent stale image/widget duration timers from interrupting video playback. Also skip showing "Connecting..." overlay when cached playlist is already playing. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
d73abc809d
commit
ad3095cdf5
|
|
@ -109,6 +109,7 @@
|
||||||
let layout = null;
|
let layout = null;
|
||||||
let zones = {};
|
let zones = {};
|
||||||
let userHasInteracted = false;
|
let userHasInteracted = false;
|
||||||
|
let advanceTimer = null;
|
||||||
|
|
||||||
// Track user interaction for autoplay policy
|
// Track user interaction for autoplay policy
|
||||||
['click', 'touchstart', 'keydown'].forEach(evt => {
|
['click', 'touchstart', 'keydown'].forEach(evt => {
|
||||||
|
|
@ -191,7 +192,7 @@
|
||||||
tapOverlay.onclick = () => {
|
tapOverlay.onclick = () => {
|
||||||
unlockAudio();
|
unlockAudio();
|
||||||
tapOverlay.remove();
|
tapOverlay.remove();
|
||||||
showStatus('Connecting...');
|
if (!isPlaying) showStatus('Connecting...');
|
||||||
connect(config.serverUrl);
|
connect(config.serverUrl);
|
||||||
};
|
};
|
||||||
document.body.appendChild(tapOverlay);
|
document.body.appendChild(tapOverlay);
|
||||||
|
|
@ -200,7 +201,7 @@
|
||||||
setTimeout(() => {
|
setTimeout(() => {
|
||||||
if (tapOverlay.parentNode) {
|
if (tapOverlay.parentNode) {
|
||||||
tapOverlay.remove();
|
tapOverlay.remove();
|
||||||
showStatus('Connecting (audio muted)...');
|
if (!isPlaying) showStatus('Connecting (audio muted)...');
|
||||||
connect(config.serverUrl);
|
connect(config.serverUrl);
|
||||||
}
|
}
|
||||||
}, 5000);
|
}, 5000);
|
||||||
|
|
@ -700,6 +701,9 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
function renderContent(item) {
|
function renderContent(item) {
|
||||||
|
// Clear any pending advance timer from previous content (image/widget duration timers)
|
||||||
|
if (advanceTimer) { clearTimeout(advanceTimer); advanceTimer = null; }
|
||||||
|
|
||||||
const container = document.getElementById('playerContainer');
|
const container = document.getElementById('playerContainer');
|
||||||
container.style.display = 'block';
|
container.style.display = 'block';
|
||||||
container.innerHTML = '';
|
container.innerHTML = '';
|
||||||
|
|
@ -727,7 +731,7 @@
|
||||||
video.style.cssText = 'width:100%;height:100%;object-fit:contain;background:#000';
|
video.style.cssText = 'width:100%;height:100%;object-fit:contain;background:#000';
|
||||||
video.loop = (playlist.length === 1);
|
video.loop = (playlist.length === 1);
|
||||||
video.onended = () => { if (!video.loop) nextItem(); };
|
video.onended = () => { if (!video.loop) nextItem(); };
|
||||||
video.onerror = (e) => { console.error('Video error:', src, e); setTimeout(nextItem, 3000); };
|
video.onerror = (e) => { console.error('Video error:', src, e); advanceTimer = setTimeout(nextItem, 3000); };
|
||||||
video.onloadeddata = () => {
|
video.onloadeddata = () => {
|
||||||
console.log('Video loaded:', item.filename, 'muted:', video.muted);
|
console.log('Video loaded:', item.filename, 'muted:', video.muted);
|
||||||
};
|
};
|
||||||
|
|
@ -740,10 +744,10 @@
|
||||||
const img = document.createElement('img');
|
const img = document.createElement('img');
|
||||||
img.src = src;
|
img.src = src;
|
||||||
img.style.cssText = 'width:100%;height:100%;object-fit:contain';
|
img.style.cssText = 'width:100%;height:100%;object-fit:contain';
|
||||||
img.onerror = () => { console.error('Image error'); setTimeout(nextItem, 3000); };
|
img.onerror = () => { console.error('Image error'); advanceTimer = setTimeout(nextItem, 3000); };
|
||||||
container.appendChild(img);
|
container.appendChild(img);
|
||||||
// Auto advance for images
|
// Auto advance for images
|
||||||
setTimeout(nextItem, (item.duration_sec || 10) * 1000);
|
advanceTimer = setTimeout(nextItem, (item.duration_sec || 10) * 1000);
|
||||||
} else if (item.widget_id) {
|
} else if (item.widget_id) {
|
||||||
const iframe = document.createElement('iframe');
|
const iframe = document.createElement('iframe');
|
||||||
iframe.src = `${serverUrl}/api/widgets/${item.widget_id}/render`;
|
iframe.src = `${serverUrl}/api/widgets/${item.widget_id}/render`;
|
||||||
|
|
@ -751,7 +755,7 @@
|
||||||
iframe.allow = 'autoplay; fullscreen';
|
iframe.allow = 'autoplay; fullscreen';
|
||||||
container.appendChild(iframe);
|
container.appendChild(iframe);
|
||||||
// Auto advance for widgets
|
// Auto advance for widgets
|
||||||
setTimeout(nextItem, (item.duration_sec || 30) * 1000);
|
advanceTimer = setTimeout(nextItem, (item.duration_sec || 30) * 1000);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -793,7 +797,7 @@
|
||||||
img.src = src;
|
img.src = src;
|
||||||
img.style.cssText = `width:100%;height:100%;object-fit:${zone.fit_mode || 'cover'}`;
|
img.style.cssText = `width:100%;height:100%;object-fit:${zone.fit_mode || 'cover'}`;
|
||||||
div.appendChild(img);
|
div.appendChild(img);
|
||||||
if (playlist.length > 1) setTimeout(nextItem, (assignment.duration_sec || 10) * 1000);
|
if (playlist.length > 1) advanceTimer = setTimeout(nextItem, (assignment.duration_sec || 10) * 1000);
|
||||||
}
|
}
|
||||||
|
|
||||||
container.appendChild(div);
|
container.appendChild(div);
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue