"use client"; import { createContext, useCallback, useContext, useEffect, useState, } from "react"; export type ThemeMode = "light" | "dark" | "system"; type ThemeContextValue = { theme: ThemeMode; resolvedTheme: "light" | "dark"; setTheme: (theme: ThemeMode) => void; }; const ThemeContext = createContext(null); const STORAGE_KEY = "nomadvip-theme"; function getSystemTheme(): "light" | "dark" { if (typeof window === "undefined") return "light"; return window.matchMedia("(prefers-color-scheme: dark)").matches ? "dark" : "light"; } function getStoredTheme(): ThemeMode { if (typeof window === "undefined") return "system"; return (localStorage.getItem(STORAGE_KEY) as ThemeMode) || "system"; } export function ThemeProvider({ children }: { children: React.ReactNode }) { const [theme, setThemeState] = useState("system"); const [resolvedTheme, setResolvedTheme] = useState<"light" | "dark">("light"); const applyTheme = useCallback((mode: "light" | "dark") => { const root = document.documentElement; root.classList.remove("light", "dark"); root.classList.add(mode); setResolvedTheme(mode); }, []); const setTheme = useCallback( (newTheme: ThemeMode) => { setThemeState(newTheme); localStorage.setItem(STORAGE_KEY, newTheme); const resolved = newTheme === "system" ? getSystemTheme() : newTheme; applyTheme(resolved); }, [applyTheme] ); useEffect(() => { const stored = getStoredTheme(); setThemeState(stored); const resolved = stored === "system" ? getSystemTheme() : stored; applyTheme(resolved); const media = window.matchMedia("(prefers-color-scheme: dark)"); const handler = () => { if (getStoredTheme() === "system") { applyTheme(media.matches ? "dark" : "light"); } }; media.addEventListener("change", handler); return () => media.removeEventListener("change", handler); }, [applyTheme]); return ( {children} ); } export function useTheme() { const ctx = useContext(ThemeContext); if (!ctx) throw new Error("useTheme must be used within ThemeProvider"); return ctx; }