/* ============================================================
   TOKENS — two layers.
   Layer 1: raw ramps. Never referenced by components.
   Layer 2: semantic tokens. The only thing components may use.
   ============================================================ */

:root {
  /* Dark first: this list is in decreasing order of preference, so the first
     entry is what a UA that expresses no colour-scheme preference gets. Dark
     is the brand default, so it leads; light stays listed, so an explicit
     system light preference is still honoured. */
  color-scheme: dark light;

  /* ── Layer 1 — raw ramps ─────────────────────────────────── */
  /* Warm neutrals (R=G>B) carry the brand's warmth. */
  --warm-950: #080808;
  --warm-900: #111111;
  --warm-850: #181818;
  --warm-800: #242424;
  --warm-500: #6e6e66;
  --warm-100: #f0ede8;
  --warm-050: #faf8f5;

  /* True neutrals. Used where the absence of warmth is the signal. */
  --grey-700: #55554c;
  --grey-300: #cccccc;
  --ink-900:  #1a1a17;

  /* Warm sand accent. */
  --sand-600: #6b5a3c;
  --sand-500: #8a7550;
  --sand-300: #c8b99a;
  --sand-200: #d4c7ad;
  --sand-900: #3d3526;

  /* ── Layer 2 — semantic tokens ───────────────────────────── */
  /* Each defined ONCE via light-dark(). Dark is the brand default:
     see the fallback block below for engines without light-dark(). */
  --page:               light-dark(#faf8f5, #080808);
  --surface:            light-dark(#ffffff, #111111);
  /* Dark branch is #121212, not the #181818 this started at: body copy renders
     on this surface (.cs-method, .cs-disclaimer, .cs-key-takeaway, the CV photo
     placeholder), and at #181818 --text-secondary measured Lc 74.56 — under the
     Lc 75 body floor. The containers are defined by their borders rather than
     their fill, so darkening costs no legibility. Guarded by contrast.test.ts. */
  --surface-2:          light-dark(#f2efea, #121212);

  --text-primary:       light-dark(#1a1a17, #f0ede8);  /* warm */
  --text-secondary:     light-dark(#55554c, #cccccc);  /* neutral — the temperature difference is the hierarchy signal */

  --accent:             light-dark(#8a7550, #c8b99a);  /* decorative only */
  --accent-text:        light-dark(#6b5a3c, #d4c7ad);  /* interactive text, >=16px */

  --border-subtle:      light-dark(#e2ddd5, #242424);  /* decorative rules; no contrast requirement */
  --border-interactive: light-dark(#767065, #6e6e66);  /* control boundaries; >=3:1 both themes */

  /* Sticky-topbar scrim. Theme-aware translucent wash of --page; kept as its
     own token (not a literal repeated in cv.css/portfolio.css) so both
     sheets can only ever reference one value. */
  --topbar-scrim:       light-dark(rgb(250 248 245 / 0.92), rgb(8 8 8 / 0.92));

}

/* There is deliberately NO @supports fallback for light-dark(). The function
   shipped in Firefox 120, Chrome 123 and Safari 17.5 — all 2024 or earlier.
   The hand-maintained dark fallback that used to live here produced five
   separate defects in review (a toggle button that reported a state it could
   not deliver, a near-black print palette, native UI fighting the page, a
   stored preference the visitor could not clear), every one of them in a code
   path nothing renders in CI, because the test browser always supports the
   feature. Guards can pin such a path's shape but never execute it.

   An engine without the function now resolves these custom properties as
   invalid at computed-value time and falls back to UA defaults: system canvas
   and system text. Those honour `color-scheme: dark light` above, so such a
   visitor still gets a coherent light or dark page. The brand palette is lost
   there; legibility is not. */

/* An explicit choice overrides the system preference in both directions. */
:root[data-theme='light'] { color-scheme: only light; }
:root[data-theme='dark']  { color-scheme: only dark; }
