atmosphere explorer pds.ls
tool typescript atproto
at main 54 lines 1.8 kB view raw
1import { createSignal } from "solid-js"; 2 3export const themeEvent = () => { 4 if (localStorage.getItem("theme") !== null) return; 5 const isDark = window.matchMedia("(prefers-color-scheme: dark)").matches; 6 document.documentElement.classList.toggle("dark", isDark); 7}; 8 9export const ThemeSelection = () => { 10 const [theme, setTheme] = createSignal( 11 localStorage.getItem("theme") === null ? "auto" 12 : localStorage.theme === "dark" ? "dark" 13 : "light", 14 ); 15 16 const updateTheme = (newTheme: string) => { 17 setTheme(newTheme); 18 document.documentElement.classList.toggle( 19 "dark", 20 newTheme === "dark" || 21 (newTheme === "auto" && window.matchMedia("(prefers-color-scheme: dark)").matches), 22 ); 23 if (newTheme === "auto") localStorage.removeItem("theme"); 24 else localStorage.theme = newTheme; 25 }; 26 27 const ThemeOption = (props: { theme: string; label: string }) => { 28 return ( 29 <button 30 classList={{ 31 "flex items-center min-w-21 justify-center rounded-xl border px-3 py-2": true, 32 "bg-neutral-200/60 border-neutral-300 dark:border-neutral-500 dark:bg-neutral-700": 33 theme() === props.theme, 34 "border-neutral-200 dark:border-neutral-600 hover:bg-neutral-200/30 dark:hover:bg-neutral-800": 35 theme() !== props.theme, 36 }} 37 onclick={() => updateTheme(props.theme)} 38 > 39 {props.label} 40 </button> 41 ); 42 }; 43 44 return ( 45 <div class="flex flex-col gap-1"> 46 <label class="font-medium select-none">Theme</label> 47 <div class="flex gap-2"> 48 <ThemeOption theme="auto" label="Auto" /> 49 <ThemeOption theme="light" label="Light" /> 50 <ThemeOption theme="dark" label="Dark" /> 51 </div> 52 </div> 53 ); 54};