51 lines
1.4 KiB
TypeScript
51 lines
1.4 KiB
TypeScript
/**
|
|
* Shares the chosen theme with every component. `ThemeProvider` fills this
|
|
* context and `useTheme` reads it.
|
|
*
|
|
* @module
|
|
*/
|
|
|
|
import { createContext } from "react";
|
|
|
|
/**
|
|
* Lists every site style, which `ThemeProvider` checks a stored choice
|
|
* against. Each has a stylesheet under `src/themes/`, keyed on the root
|
|
* element's `data-style`, which is absent for "smooth".
|
|
*/
|
|
export const STYLE_NAMES = [
|
|
"smooth",
|
|
"brutalist",
|
|
"geocities",
|
|
"nyt",
|
|
"kanagawa",
|
|
"melange",
|
|
] as const;
|
|
/** Held by `ThemeProvider` for the style chosen in this browser. */
|
|
export type StyleName = typeof STYLE_NAMES[number];
|
|
|
|
/** Lists every color scheme. "auto" follows the system's. */
|
|
export const COLOR_SCHEMES = ["auto", "light", "dark"] as const;
|
|
/** Held by `ThemeProvider` for the color scheme chosen in this browser. */
|
|
export type ColorScheme = typeof COLOR_SCHEMES[number];
|
|
|
|
/**
|
|
* Provided by `ThemeProvider` to `useTheme`. A setter applies and stores the
|
|
* choice for this browser.
|
|
*/
|
|
export interface ThemeContextValue {
|
|
style: StyleName;
|
|
colorScheme: ColorScheme;
|
|
setStyle(s: StyleName): void;
|
|
setColorScheme(c: ColorScheme): void;
|
|
}
|
|
|
|
/** The theme's context. Its default is only seen outside `ThemeProvider`. */
|
|
export const ThemeContext: React.Context<ThemeContextValue> = createContext<
|
|
ThemeContextValue
|
|
>({
|
|
style: "smooth",
|
|
colorScheme: "auto",
|
|
setStyle: () => {},
|
|
setColorScheme: () => {},
|
|
});
|