1 2const STREAM_URL = 'https://stream.zeno.fm/48898dd2ba9uv'; 3const MOUNT = '48898dd2ba9uv'; 4const META_URL = `https://api.zeno.fm/mounts/metadata/subscribe/${MOUNT}`; 5 6const audio = new Audio(STREAM_URL); 7audio.volume = 0.8; 8 9document.addEventListener('DOMContentLoaded', () => { 10 const btn = document.getElementById('play-pause-btn'); 11 const icon = document.getElementById('btn-icon'); 12 const status = document.getElementById('status-text'); 13 const track = document.getElementById('current-track'); 14 const muteBtn = document.getElementById('mute-toggle'); 15 const volIcon = document.getElementById('vol-icon'); 16 17 let playing = false; 18 let lastVolume = 0.8; 19 20 try { 21 const source = new EventSource(META_URL); 22 source.onmessage = e => { 23 try { 24 const data = JSON.parse(e.data); 25 if (data.streamTitle) track.textContent = data.streamTitle; 26 } catch {} 27 }; 28 } catch {} 29 30 audio.play().then(() => { 31 playing = true; 32 icon.className = 'fas fa-pause'; 33 status.textContent = 'EN VIVO'; 34 }).catch(() => { 35 status.textContent = 'PAUSADO'; 36 }); 37 38 btn.onclick = () => { 39 if (playing) { 40 audio.pause(); 41 icon.className = 'fas fa-play'; 42 status.textContent = 'PAUSADO'; 43 } else { 44 audio.play(); 45 icon.className = 'fas fa-pause'; 46 status.textContent = 'EN VIVO'; 47 } 48 playing = !playing; 49 }; 50 51 if (muteBtn) { 52 muteBtn.onclick = () => { 53 if (audio.volume > 0) { 54 lastVolume = audio.volume; 55 audio.volume = 0; 56 volIcon.className = 'fas fa-volume-mute'; 57 } else { 58 audio.volume = lastVolume; 59 volIcon.className = 'fas fa-volume-up'; 60 } 61 }; 62 } 63});
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.