import { useGlobal } from 'hooks/useGlobal'; // App-wide music player state (react-query-backed via useGlobal, so it's shared across the whole app and // survives route changes). The audio element itself lives in MusicPlayerHost (mounted once in the // persistent DashboardLayout); this hook is the control surface any component uses to drive it. export type PlayerTrack = { albumRel: string; // album path relative to the Music root (for stream + cover URLs) file: string; // track filename within the album folder title?: string; artist?: string; }; export type MusicPlayerState = { queue: PlayerTrack[]; index: number; playing: boolean; }; const INITIAL: MusicPlayerState = { queue: [], index: 0, playing: false }; export function useMusicPlayer() { const [state, setState] = useGlobal('MUSIC_PLAYER', INITIAL); const playQueue = (queue: PlayerTrack[], index = 0) => setState({ queue, index: Math.max(0, Math.min(index, Math.max(0, queue.length - 1))), playing: true }); // Like playQueue but paused — for restoring a saved "currently playing" on load without auto-playing // (browsers block autoplay on reload anyway; the user resumes with a click). const loadQueue = (queue: PlayerTrack[], index = 0) => setState({ queue, index: Math.max(0, Math.min(index, Math.max(0, queue.length - 1))), playing: false }); const toggle = () => setState((s) => ({ ...s, playing: !s.playing })); const setPlaying = (playing: boolean) => setState((s) => ({ ...s, playing })); // Mirror an engine-driven natural advance into the index WITHOUT restarting playback (the audio engine // has already transitioned to the next track gaplessly; this only updates the UI/highlight). const syncIndex = (index: number) => setState((s) => ({ ...s, index })); const jump = (index: number) => setState((s) => ({ ...s, index: Math.max(0, Math.min(index, s.queue.length - 1)), playing: true })); const next = () => setState((s) => s.index < s.queue.length - 1 ? { ...s, index: s.index + 1, playing: true } : { ...s, playing: false }, ); const prev = () => setState((s) => (s.index > 0 ? { ...s, index: s.index - 1, playing: true } : s)); const close = () => setState(INITIAL); const current = state.queue[state.index]; return { ...state, current, playQueue, loadQueue, toggle, setPlaying, syncIndex, jump, next, prev, close }; }