document.addEventListener("DOMContentLoaded", () => { const themeSwitch = document.getElementById("theme-switch"); const prefersDarkScheme = window.matchMedia("(prefers-color-scheme: dark)"); const applyTheme = (theme) => { document.documentElement.classList.toggle("dark", theme === "dark"); }; const getStoredTheme = () => localStorage.getItem("theme"); const setStoredTheme = (theme) => localStorage.setItem("theme", theme); // Initial load const savedTheme = getStoredTheme(); if (savedTheme) { applyTheme(savedTheme); } else { applyTheme(prefersDarkScheme.matches ? "dark" : "light"); } // system changes prefersDarkScheme.addEventListener("change", (e) => { const saved = getStoredTheme(); if (!saved) { applyTheme(e.matches ? "dark" : "light"); } }); // toggle handler themeSwitch.addEventListener("click", () => { const currentTheme = document.documentElement.classList.contains("dark") ? "dark" : "light"; const newTheme = currentTheme === "dark" ? "light" : "dark"; applyTheme(newTheme); setStoredTheme(newTheme); }); const updateBodyThemeAttr = () => { const current = document.documentElement.classList.contains("dark") ? "dark" : "light"; document.body.setAttribute("data-theme", current); }; updateBodyThemeAttr(); // update on change const observer = new MutationObserver(updateBodyThemeAttr); observer.observe(document.documentElement, { attributes: true, attributeFilter: ["class"] }); prefersDarkScheme.addEventListener("change", () => { updateBodyThemeAttr(); }); });