// Cross-tab persistent chat-audio prefs (master volume / muted / unlocked).
//
// Why Zustand here (vs. AudioPlayer's plain module-level store): the chat
// audio system has more knobs (per-event toggles + volume + muted) and lives
// behind a React context where multiple chat providers might exist. We get the
// `subscribe()` + `useSyncExternalStore` plumbing for free, and the persist
// middleware handles cross-tab sync via the `storage` event.
//
// We DO NOT close the AudioContext (matches AudioPlayer's ADR-004) and we
// remain SSR-safe by gating window access in the bus, not here.

'use client';

import { create } from 'zustand';
import { persist, createJSONStorage } from 'zustand/middleware';

import type { ChatAudioEvent } from './types';

const STORAGE_KEY = 'djangocfg-chat-audio:prefs';

export interface ChatAudioPrefsState {
  /** 0..1 master volume. */
  volume: number;
  /** Master mute (overrides per-event toggles). */
  muted: boolean;
  /** Per-event opt-out — `false` silences a single trigger. */
  enabled: Partial<Record<ChatAudioEvent, boolean>>;

  setVolume: (v: number) => void;
  setMuted: (m: boolean) => void;
  setEventEnabled: (event: ChatAudioEvent, enabled: boolean) => void;
}

const clamp01 = (v: number): number => {
  if (!Number.isFinite(v)) return 1;
  return v < 0 ? 0 : v > 1 ? 1 : v;
};

export const useChatAudioPrefs = create<ChatAudioPrefsState>()(
  persist(
    (set) => ({
      volume: 1,
      muted: false,
      enabled: {},

      setVolume: (v) => set({ volume: clamp01(v) }),
      setMuted: (m) => set({ muted: !!m }),
      setEventEnabled: (event, enabled) =>
        set((s) => ({ enabled: { ...s.enabled, [event]: enabled } })),
    }),
    {
      name: STORAGE_KEY,
      storage: createJSONStorage(() => {
        // SSR-safe: zustand calls `getStorage()` lazily, but be defensive.
        if (typeof window === 'undefined') {
          return {
            getItem: () => null,
            setItem: () => undefined,
            removeItem: () => undefined,
          };
        }
        return window.localStorage;
      }),
      partialize: (s) => ({ volume: s.volume, muted: s.muted, enabled: s.enabled }),
      version: 1,
    },
  ),
);
