// ── PLAYER PiP ──────────────────────────────────────────────────────────────── let hlsInstance = null; function openPip(channelName, programTitle) { const url = getStreamUrl(channelName); const pip = document.getElementById('pip'); const video = document.getElementById('pipVideo'); const err = document.getElementById('pipError'); document.getElementById('pipChannel').textContent = channelName; document.getElementById('pipProgram').textContent = programTitle || ''; err.style.display = 'none'; pip.classList.add('visible'); // Tear down the previous HLS instance before opening another stream. if (hlsInstance) { hlsInstance.destroy(); hlsInstance = null; } video.src = ''; if (!url) { err.style.display = 'block'; err.textContent = '⚠ Aucun stream trouvé pour cette chaîne'; return; } if (Hls.isSupported()) { hlsInstance = new Hls({ enableWorker: false, debug: false }); hlsInstance.loadSource(url); hlsInstance.attachMedia(video); hlsInstance.on(Hls.Events.MANIFEST_PARSED, () => { console.log('[PiP] Manifest parsed, lecture...'); video.play().catch(e => console.warn('[PiP] play() refusé:', e)); }); hlsInstance.on(Hls.Events.ERROR, (e, data) => { console.error('[PiP] HLS error:', data.type, data.details, data.fatal, data.response); if (data.fatal) { const detail = data.response ? ` (HTTP ${data.response.code})` : ` (${data.details})`; err.style.display = 'block'; err.textContent = '⚠ Erreur de lecture du stream' + detail; } }); } else if (video.canPlayType('application/vnd.apple.mpegurl')) { // Safari can play HLS natively without hls.js. video.src = url; video.addEventListener('loadedmetadata', () => video.play().catch(() => {})); } else { err.style.display = 'block'; err.textContent = '⚠ HLS non supporté sur ce navigateur'; } } function closePip() { const pip = document.getElementById('pip'); const video = document.getElementById('pipVideo'); pip.classList.remove('visible'); if (hlsInstance) { hlsInstance.destroy(); hlsInstance = null; } video.pause(); video.src = ''; }