mirror of
https://github.com/jakejarvis/jarv.is.git
synced 2026-06-29 19:05:58 -04:00
set the color-scheme CSS property to either light or dark onChange
https://developer.mozilla.org/en-US/docs/Web/CSS/color-scheme
This commit is contained in:
@@ -1,17 +1,13 @@
|
||||
/* eslint-disable no-var */
|
||||
|
||||
// A super tiny script to restore dark mode off the bat (to hopefully avoid blinding flashes of white).
|
||||
// NOTE: This is inlined by Hugo/esbuild (see layouts/partials/head/restore-theme.html) instead of Webpack.
|
||||
// ANOTHER NOTE: Whenever this code is changed, its (minified) CSP hash *MUST* be updated manually in vercel.json.
|
||||
|
||||
import { getDarkPref } from "./src/utils/theme.js";
|
||||
import { getDarkPref, updateDOM } from "./src/utils/theme.js";
|
||||
|
||||
try {
|
||||
var cl = document.documentElement.classList;
|
||||
var pref = getDarkPref();
|
||||
|
||||
// set `<html class="dark">` if either the user has explicitly toggled in the past or if their OS is in dark mode
|
||||
if (pref === "true" || (!pref && window.matchMedia("(prefers-color-scheme: dark)").matches)) {
|
||||
cl.remove("light");
|
||||
cl.add("dark");
|
||||
}
|
||||
} catch (error) {}
|
||||
// Set root class and color-scheme property to dark if either...
|
||||
// - the user has explicitly toggled it previously.
|
||||
// - the user's OS is in dark mode.
|
||||
const pref = getDarkPref();
|
||||
updateDOM(pref === "true" || (!pref && window.matchMedia("(prefers-color-scheme: dark)").matches));
|
||||
} catch (e) {}
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
import { h } from "preact";
|
||||
import { useState, useEffect, useCallback } from "preact/hooks";
|
||||
import { isDark, getDarkPref, setDarkPref } from "../utils/theme.js";
|
||||
import { isDark, getDarkPref, setDarkPref, updateDOM } from "../utils/theme.js";
|
||||
|
||||
// react components:
|
||||
import BulbOn from "../assets/bulb-on.svg";
|
||||
@@ -28,11 +28,8 @@ const ThemeToggle = () => {
|
||||
} catch (e) {}
|
||||
}, [saved, matchCallback]);
|
||||
|
||||
useEffect(() => {
|
||||
// sets appropriate `<html class="...">`
|
||||
document.documentElement.classList.remove("dark", "light");
|
||||
document.documentElement.classList.add(dark ? "dark" : "light");
|
||||
}, [dark]);
|
||||
// sets appropriate `<html class="...">` and `color-scheme` CSS property when mode changes
|
||||
useEffect(() => updateDOM(dark), [dark]);
|
||||
|
||||
const handleToggle = () => {
|
||||
// only update the local storage preference if the user explicitly presses the lightbulb
|
||||
|
||||
@@ -1,3 +1,7 @@
|
||||
// class names (`<html class="...">`) for each theme
|
||||
const lightClass = "light";
|
||||
const darkClass = "dark";
|
||||
|
||||
// store preference in local storage
|
||||
const storageKey = "dark_mode";
|
||||
export const getDarkPref = () => localStorage.getItem(storageKey);
|
||||
@@ -5,4 +9,17 @@ export const setDarkPref = (pref) => localStorage.setItem(storageKey, pref);
|
||||
|
||||
// use the `<html class="...">` as a hint to what the theme was set to outside of the button component
|
||||
// there's probably (definitely) a cleaner way to do this..?
|
||||
export const isDark = () => document.documentElement.classList.contains("dark");
|
||||
export const isDark = () => document.documentElement.classList.contains(darkClass);
|
||||
|
||||
// sets appropriate `<html class="...">` and `color-scheme` CSS property
|
||||
export const updateDOM = (dark) => {
|
||||
const root = document.documentElement;
|
||||
|
||||
// set `<html class="...">`
|
||||
root.classList.remove(darkClass, lightClass);
|
||||
root.classList.add(dark ? darkClass : lightClass);
|
||||
|
||||
// ...and the CSS `color-scheme` property:
|
||||
// https://developer.mozilla.org/en-US/docs/Web/CSS/color-scheme
|
||||
root.style.colorScheme = dark ? "dark" : "light";
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user