Changing the Theme

Getting Started

The whole site re-skins from a single file: src/content/settings/theme.json. Eight knobs, no hidden state.

The eight knobs

  • primaryColor — main brand color. Used by links, primary buttons, the info callout, focus rings.
  • accentColor — secondary accent. Used by the tip callout and small highlights.
  • backgroundLight — page background in light mode.
  • backgroundDark — page background in dark mode. The rest of the dark palette is derived from this via color-mix in tokens.css, so you only set one dark value.
  • fontFamilyBody — body font stack.
  • fontFamilyHeadings — heading font stack. Falls back to fontFamilyBody if omitted.
  • baseFontSize — root font size, e.g. 16px. Everything scales relative to this.
  • borderRadius — corner radius for cards, buttons, and most surfaces.

How a change reaches the browser

The values in theme.json become CSS custom properties at build time via src/styles/tokens.css. Components read those custom properties — never hardcoded values. Change a knob, run npm run build, redeploy. No component edits required.

Dark mode is automatic. The toggle in the top bar persists per device under the coursetemplate:v1:theme localStorage key and respects the system preference on first visit.