// Zeichnet das Tray-Menü aus dem Zustand, den der Hauptprozess schickt. // Ohne Electron (Seite direkt im Browser geöffnet) greift ein Stub, damit sich die Optik prüfen lässt. (function () { const api = window.trayApi || { onState: () => {}, action: (id) => console.log('action', id), resize: () => {}, close: () => {} }; const menu = document.getElementById('menu'); let buttons = []; let activeIndex = -1; function setActive(index) { activeIndex = index; buttons.forEach((b, i) => b.classList.toggle('active', i === index)); } function render(state) { document.body.classList.toggle('light', state && state.dark === false); menu.textContent = ''; buttons = []; activeIndex = -1; for (const item of (state && state.items) || []) { if (item.type === 'separator') { const sep = document.createElement('div'); sep.className = 'sep'; menu.appendChild(sep); continue; } if (item.id === 'header' || item.id === 'status' || item.id === 'queue') { const line = document.createElement('div'); line.className = item.id === 'header' ? 'header' : 'status'; line.textContent = item.label; menu.appendChild(line); continue; } const button = document.createElement('button'); button.className = 'item'; button.disabled = item.enabled === false; button.setAttribute('role', item.type === 'checkbox' ? 'menuitemcheckbox' : 'menuitem'); if (item.type === 'checkbox') button.setAttribute('aria-checked', String(!!item.checked)); const check = document.createElement('span'); check.className = 'check'; check.textContent = item.type === 'checkbox' && item.checked ? '✓' : ''; const label = document.createElement('span'); label.textContent = item.label; button.append(check, label); button.addEventListener('click', () => api.action(item.id)); button.addEventListener('mouseenter', () => { if (!button.disabled) setActive(buttons.indexOf(button)); }); button.addEventListener('mouseleave', () => setActive(-1)); menu.appendChild(button); buttons.push(button); } api.resize(Math.ceil(document.body.scrollHeight)); } function move(step) { const enabled = buttons.map((b, i) => (b.disabled ? -1 : i)).filter((i) => i >= 0); if (enabled.length === 0) return; const pos = enabled.indexOf(activeIndex); const next = pos < 0 ? (step > 0 ? 0 : enabled.length - 1) : (pos + step + enabled.length) % enabled.length; setActive(enabled[next]); } document.addEventListener('keydown', (e) => { if (e.key === 'Escape') api.close(); else if (e.key === 'ArrowDown') { e.preventDefault(); move(1); } else if (e.key === 'ArrowUp') { e.preventDefault(); move(-1); } else if ((e.key === 'Enter' || e.key === ' ') && buttons[activeIndex]) { e.preventDefault(); buttons[activeIndex].click(); } }); window.__renderTray = render; api.onState(render); })();