all writing
Dec 18, 20251 min read

Theming with CSS variables (and nothing else)

How I theme components without runtime JS, context, or any framework lock-in.

I've been theming components with CSS variables — and nothing else — for about two years now. No context providers, no runtime style objects, no theme libraries.

The whole approach in 12 lines

:root {
  --bg: #fff;
  --fg: #111;
}
[data-theme='dark'] {
  --bg: #0d0d0d;
  --fg: #f0f0f0;
}

That's it. Toggle data-theme on the html element and every variable cascades. No re-render, no flash, no client/server mismatch.

Tokens vs. semantic names

Two-tier naming is the trick that scales: --gray-9 is a token, --fg is a semantic alias for it. Components only ever read the semantic names.