/* ============================================================
   THE 2028 DESIGN SYSTEM
   Three interchangeable flavors over one 42-token contract.

   USAGE — reskin any page by changing one word:

       <html data-flavor="instrument">   navy plate, brass hardware
       <html data-flavor="paper">        warm stock, two-plate letterpress
       <html data-flavor="phosphor">     unlit coating, one excited accent

   Omit the attribute entirely and you get instrument, the descendant
   of the TomorrowLytics "Instrument Panel" behind status.mediagato.com.
   Its 11 core values are byte-identical to that app's globals.css.

   Light/dark is a SEPARATE axis: each flavor declares both ramps and
   hooks html.light, the same mechanism the existing pages already use.
   Flavor and theme never interfere.
   ============================================================ */


/* ############ FLAVOR: INSTRUMENT ############ */
/* ============================================================
   2028 · FLAVOR: INSTRUMENT — "Unlit Faceplate"
   HOME THEME: dark. Declares all 42 contract tokens.
   color-scheme is the one non-custom property here, on purpose:
   native scrollbars and form controls must be re-lit with the
   ground, and in base it would not follow the flavor.
   ============================================================ */
:root,
:root[data-flavor="instrument"] {
  color-scheme: dark;

  /* ── Material · 6 ──────────────────────────────────────────
     Navy cast, never neutral. R=11 G=15 B=20 — the blue channel
     leads, because unlit rooms read blue. Grounds and hairlines
     lean blue together; --ink takes the complementary lean.
     --recess collapses onto --ground: a faceplate has no section
     bands, so an input is a well milled back down to plate level
     inside a panel. The ladder is MONOTONE — every step is a step
     further from the ground, in both themes.                     */
  --ground:      #0b0f14;
  --recess:      #0b0f14;
  --surface:     #10151b;
  --surface-hi:  #151b23;   /* hover + table header */
  --scrim:       rgba(11, 15, 20, 0.72);
  --scrim-dense: rgba(11, 15, 20, 0.92);

  /* ── Ink · 3 ───────────────────────────────────────────────
     Green lean, so the ink sits ON the plate rather than hovering
     in front of it. Measured on --ground:
       ink 16.9:1 · ink-dim 6.40:1 (6.10:1 on --surface) · faint 4.15:1
     --ink-faint is a 3:1-class token BY DESIGN — nothing that must
     be read uses it: placeholders, disabled, zero values, the — mark. */
  --ink:       #eef1f0;
  --ink-dim:   #8b96a3;
  --ink-faint: #6b7681;

  /* ── Line · 2 ──────────────────────────────────────────────
     The hairline picks up the same blue cast as its own ground.  */
  --line:    #1c232b;
  --line-hi: #2b343f;

  /* ── Brand · 6 · BRASS ─────────────────────────────────────
     A material, not a hue: a machined dial bezel under warm light.
     Two brass values with SEPARATE jobs, because one value cannot
     do both (see the light block for the proof):
       --accent    = fills, arcs, stripes, borders, graphics.
                     7.92:1 on ground; carries --accent-ink at 8.08:1.
       --accent-hi = brass AS TEXT and as a hover border.
                     9.89:1 on ground. Brighter on dark, darker on
                     light: the direction inverts, the rule does not.
     --accent-ink is a very dark BROWN, not #000 — ink printed on
     brass, not a hole punched through it. CONSTANT in both themes.
     --accent-rgb MUST stay a bare triple: the mote field string-
     interpolates it into rgba() every frame and dies silently otherwise.
     --grad-a == --grad-b == --accent, so every inherited gradient
     rule renders FLAT BRASS without editing one line of legacy CSS. */
  --accent:     #e0973b;
  --accent-hi:  #f0ad52;
  --accent-ink: #100b04;
  --accent-rgb: 224, 151, 59;
  --grad-a:     #e0973b;
  --grad-b:     #e0973b;

  /* ── Semantic severity · 5 ─────────────────────────────────
     Stepped DOWN from the framework defaults. Measured in HSL:
       good  S 33% vs #22c55e S 71%  (−38pp)
       warn  S 67% vs #f59e0b S 92%  (−25pp)
       bad   S 53% vs #ef4444 S 84%  (−31pp)
       info  S 39% vs #06b6d4 S 94%  (−55pp)
     On a board that is 95% green, saturated green buries the one
     red. --info absorbs the pilot's cyan role (notices, pending,
     Coming Soon) so the brand hue is never contested by a state.
     On --ground: good 5.84 · warn 8.51 · bad 4.59 · info 5.59.    */
  --good: #4f9d6e;
  --warn: #d9a441;
  --bad:  #c85a4a;
  --info: #5f8fb8;
  --tint: 14%;

  /* ── Type · 5 · theme-invariant ────────────────────────────
     ONE webfont in the whole flavor, at ONE weight. Asking for a
     second display weight invites a synthesized fake narrow and is
     a contract violation. Sans and mono are the machine's own faces
     — the interface should look like the hardware it runs on.
     Rule: prose is sans; anything the machine produced is mono.
     Never: display face on body copy; sans on a measured value.   */
  --font-display: 'Archivo Narrow', 'Arial Narrow', 'Helvetica Neue Condensed', 'Liberation Sans Narrow', 'Roboto Condensed', Impact, sans-serif;
  --font-sans:    ui-sans-serif, system-ui, -apple-system, 'Segoe UI', Roboto, 'Helvetica Neue', sans-serif;
  --font-mono:    ui-monospace, 'SFMono-Regular', 'SF Mono', 'Cascadia Mono', 'Segoe UI Mono', 'Liberation Mono', Menlo, Consolas, monospace;
  --display-weight: 700;
  --tracking-label: 0.14em;

  /* ── Geometry · 6 · theme-invariant ────────────────────────
     5 / 7 / 8 — machined, graded, never uniform. Nothing above 8px
     except a true pill. One radius everywhere reads as a template. */
  --r-chip:    5px;
  --r-control: 7px;
  --r-panel:   8px;
  --r-pill:    999px;
  --hair:      1px;
  --stripe:    3px;

  /* ── Motion · 3 · theme-invariant ──────────────────────────
     One duration in the system. One infinite loop, at resting heart
     rate — a claim that the reading is live, not decoration.       */
  --t-fast:    .15s;
  --ease:      ease;
  --pulse-dur: 2.4s;

  /* ── Layout · 3 ────────────────────────────────────────────
     1040 for marketing surfaces; a dashboard re-declares --wrap in
     site-local CSS after the flavor loads. --measure is applied to
     paragraphs independently of their container.                   */
  --wrap:    1040px;
  --gutter:  24px;
  --measure: 640px;

  /* ── Texture · 3 · read by the field renderer ──────────────
     Brass motes drifting ~3 px/sec over the plate. Density scales
     by device-pixel AREA, not by count.                            */
  --field-mode:    motes;
  --field-opacity: 0.55;
  --field-density: 320000;
}

/* ============================================================
   LIGHT — the panel with the cover off, under shop lights.
   A full re-pick, not an inversion. Exactly the 22 tokens that
   flip; the other 20 (type, geometry, motion, layout, accent-ink,
   tint, field-mode) inherit from :root untouched.
   Class-scoped ONLY — no prefers-color-scheme block anywhere, or
   the boot guard and the toggle stop agreeing with each other.
   ============================================================ */
html.light,
html.light[data-flavor="instrument"] {
  color-scheme: light;

  /* ── Material ──────────────────────────────────────────────
     Warm bone stock, green channel leading. Never #ffffff, and no
     token here has R==G==B.
     The ladder stays MONOTONE and keeps its meaning across the
     flip: each step moves further from the ground in the same
     direction, so an input well (--recess == --ground) still reads
     as cut BELOW its panel, and hover is still a step away from
     the plate rather than back toward it.
       ground 0.8815 → surface 0.9491 → surface-hi 0.9874 (rel. lum.) */
  --ground:      #f0f2ed;
  --recess:      #f0f2ed;
  --surface:     #f8faf5;
  --surface-hi:  #fdfefb;
  --scrim:       rgba(240, 242, 237, 0.78);
  --scrim-dense: rgba(240, 242, 237, 0.94);

  /* ── Ink ───────────────────────────────────────────────────
     Near-black with a blue cast, echoing the dark theme's ground.
     Measured on --ground: ink 15.8:1 · ink-dim 6.26:1 · faint 3.42:1
     (--ink-faint is 3:1-class by design, same rule as dark.)       */
  --ink:       #12181f;
  --ink-dim:   #4f5a64;
  --ink-faint: #79838d;

  /* ── Line ──────────────────────────────────────────────────
     Green-cast hairline, matched to its own warm stock — the same
     ground/hairline cast agreement the dark theme has in blue.     */
  --line:    #dde0da;
  --line-hi: #c3c8bd;

  /* ── Brand · BRASS, RE-LIT ─────────────────────────────────
     Not the same hex dimmed: brass darkens two stops to hold on bone.
     THE PROOF THAT TWO VALUES ARE REQUIRED — with a constant near-
     black --accent-ink (rel. lum. 0.0036), a single brass value B
     would have to satisfy both
        (0.9315)/(B+0.05) >= 4.5   ->  B <= 0.157
        (B+0.05)/(0.0536) >= 4.5   ->  B >= 0.191
     which is unsatisfiable; the best simultaneous ratio is 4.17:1.
     So the job is split rather than faked:
       --accent    #c17419  fills / arcs / stripes / borders.
                   3.22:1 on ground (>=3:1 graphic bar), and carries
                   --accent-ink at 5.39:1 for button labels.
       --accent-hi #8f4c0b  brass AS TEXT and hover borders.
                   5.81:1 on ground, 6.23:1 on surface — AA either way.
     A filled brass control does NOT swap to --accent-hi on hover
     (that would drop its label to 3.0:1). It mixes toward --ink,
     which darkens here and brightens on dark from one rule:
       color-mix(in srgb, var(--accent) 92%, var(--ink))
       -> label holds 4.78:1 light / 8.57:1 dark, and the fill moves
          FURTHER from the ground in both themes.                    */
  --accent:     #c17419;
  --accent-hi:  #8f4c0b;
  --accent-rgb: 193, 116, 25;
  --grad-a:     #c17419;
  --grad-b:     #c17419;

  /* ── Semantic severity, RE-DERIVED ─────────────────────────
     Dark-mode severities wash out on bone; these are picked, not
     carried across. Still desaturated vs the framework 700s:
       good  S 44% vs #15803d S 72%  (−28pp)
       warn  S 70% vs #b45309 S 90%  (−20pp)
       bad   S 56% vs #b91c1c S 74%  (−18pp)
       info  S 36% vs #0e7490 S 82%  (−46pp)
     On --ground: good 4.64 · warn 4.90 · bad 6.10 · info 5.16.
     --tint stays 14% — it is why alerts, pills and badges read as
     one set across both themes and across every flavor.            */
  --good: #2f7a4e;
  --warn: #8a6118;
  --bad:  #9c3a2c;
  --info: #3c6b80;

  /* ── Texture ───────────────────────────────────────────────
     A field tuned for dark is invisible on paper, and dark motes on
     light read heavier per mote — so opacity drops and density
     thins. The renderer re-reads --accent-rgb per frame, so the
     motes follow the theme for free; this fixes the original's
     hardcoded rgba(224,151,59) that ignored light mode entirely.   */
  --field-opacity: 0.34;
  --field-density: 340000;
}

/* ############ FLAVOR: PAPER ############ */

:root[data-flavor="paper"] {
  color-scheme: dark;

  /* ── MATERIAL — the ink plate. Dark is the press bed after the pull:
        the ground IS the black plate, and the paper is promoted to type.
        CAST (stated): every neutral in this system leans warm, R>G>B, in both
        themes — on a two-plate job every neutral is either the stock or a warm
        brown-black plate printed on it. The complementary cool lean is reserved
        for --info (indigo ink) and for --bad, which sits on the magenta side of
        red while the accent sits on the orange side. ── */
  --ground:      #17130E;   /* 23,19,14  — warm brown-black slab. Never #0a0a0a. */
  --recess:      #1C1711;   /* 28,23,17  — the milled well: inputs, code, mock canvas */
  --surface:     #221C15;   /* 34,28,21  — the plate: panel, card, nav, table wrap */
  --surface-hi:  #2C251C;   /* 44,37,28  — hover + table head: further from ground */
  --scrim:       rgba(23,19,14,.74);
  --scrim-dense: rgba(23,19,14,.94);

  /* ── INK — the paper, printed. Body copy is --ink-dim at 8.57:1, not a mumble. ── */
  --ink:         #F2ECDF;   /* 15.58:1 on ground */
  --ink-dim:     #BCB19C;   /*  8.57:1 on ground / 7.88:1 on surface — DEFAULT BODY */
  --ink-faint:   #948875;   /*  5.27:1 — placeholders, folios, figure numbers, the em-dash */

  /* ── LINE — two grades, and the grade is a decision, not a nudge.
        --line is a printed hairline (structure at rule weight, 2.04:1).
        --line-hi carries information and clears 3:1 — controls, table heads,
        the neatline. Any border a user must locate uses --line-hi. ── */
  --line:        #544737;   /* 2.04:1 */
  --line-hi:     #75654C;   /* 3.24:1 */

  /* ── BRAND — THE RED PLATE. Iron oxide, re-mixed hotter for the dark run.
        Six named jobs per viewport. Never small type. Never a gradient. ── */
  --accent:      #B54828;   /* 179,72,40 — 3.43:1 on ground (graphics + large text only) */
  --accent-hi:   #BD4E2A;   /* 3.74:1 — BRIGHTER on dark = further from ground */
  --accent-ink:  #FBF9F3;   /* bare stock knocked out of the plate. CONSTANT both themes.
                               5.09:1 on --accent, 4.65:1 on --accent-hi */
  --accent-rgb:  179, 72, 40;   /* BARE TRIPLE — canvas / rgba() contract */
  --grad-a:      #B54828;   /* two plates cannot blend: every gradient renders FLAT */
  --grad-b:      #B54828;

  /* ── SEVERITY — pigments, quarantined from brand in usage AND in hue.
        --bad sits at ~352° (magenta side); --accent sits at ~14° (orange side). ── */
  --good:        #7DA268;   /* sap green.    S 23.8% vs #22c55e 70.6% → −46.8pp | 6.32:1 */
  --warn:        #BE9E58;   /* raw sienna.   S 44.0% vs #f59e0b 92.1% → −48.1pp | 7.18:1 */
  --bad:         #CC7B86;   /* crimson lake. S 44.3% vs #ef4444 84.2% → −39.9pp | 5.84:1 */
  --info:        #7599A8;   /* indigo ink.   S 22.7% vs #06b6d4 94.5% → −71.8pp | 5.99:1 */
  --tint:        14%;

  /* ── TYPE — three faces, three fixed jobs. The display face ships ONE weight
        because 400 is the only cut Libre Caslon Display has: the rule is enforced
        by the face, not by discipline. ── */
  --font-display: 'Libre Caslon Display','Big Caslon','Hoefler Text',Georgia,'Times New Roman',serif;
  --font-sans:    'Source Serif 4',Charter,'Iowan Old Style',Cambria,Georgia,serif; /* contract name; a book body is a serif */
  --font-mono:    'IBM Plex Mono',ui-monospace,'SFMono-Regular',Consolas,'Liberation Mono',monospace;
  --display-weight: 400;
  --tracking-label: 0.18em;

  /* ── GEOMETRY — a trimmed sheet has a sharp corner. Squarest grade in the family. ── */
  --r-chip:      2px;
  --r-control:   3px;
  --r-panel:     5px;
  --r-pill:      999px;
  --hair:        1px;
  --stripe:      3px;

  /* ── MOTION ── */
  --t-fast:      .15s;
  --ease:        ease;
  --pulse-dur:   2.4s;

  /* ── LAYOUT — generous margins, book measure declared independently of container ── */
  --wrap:        1040px;
  --gutter:      28px;
  --measure:     36rem;

  /* ── TEXTURE — no field, in either theme. Paper does not shimmer. ── */
  --field-mode:    none;
  --field-opacity: 0;
  --field-density: 320000;
}

/* ═══ LIGHT IS HOME. Ink on warm laid stock.
       Re-picked, not inverted: the material stack REVERSES direction (a panel is a
       screened tint block, DARKER than the sheet; an input is a knockout, BRIGHTER
       than everything), the accent changes hex and hue-temperature, hover reverses
       direction, and every severity is re-derived because the dark values wash out
       on paper. Only --accent-ink survives the flip unchanged — the paper is the paper. ═══ */
html.light[data-flavor="paper"] {
  color-scheme: light;

  /* MATERIAL — a press adds ink, it cannot remove it: surfaces descend from the sheet */
  --ground:      #F4F0E6;   /* 244,240,230 — warm laid text stock. Never #fff. */
  --recess:      #FBF9F3;   /* 251,249,243 — KNOCKOUT to bare stock: inputs, code, mock canvas */
  --surface:     #ECE6D8;   /* 236,230,216 — a screened tint block printed on the sheet */
  --surface-hi:  #E2DAC8;   /* 226,218,200 — hover lays down more ink: DARKER = further from ground */
  --scrim:       rgba(244,240,230,.74);
  --scrim-dense: rgba(244,240,230,.94);

  /* INK — this is the whole ballgame on a light theme */
  --ink:         #1E1A15;   /* 30,26,21 — warm brown-black. Printed on the stock, not punched through it. 15.21:1 */
  --ink-dim:     #4A4238;   /* 74,66,56 — DEFAULT BODY COPY. 8.67:1 on ground, 7.93:1 on surface */
  --ink-faint:   #6F6355;   /* 111,99,85 — folios, figure numbers, placeholders, the em-dash. 5.14:1 */

  /* LINE — same two grades, re-picked */
  --line:        #B3A489;   /* 2.15:1 — a printed hairline rule */
  --line-hi:     #94856B;   /* 3.17:1 — controls, table heads, the neatline */

  /* BRAND — RED LEAD / MINIUM. The rubric plate, mixed for the stock it prints on. */
  --accent:      #A3301B;   /* 165,48,27 — 6.16:1 on ground, 5.64:1 on surface */
  --accent-hi:   #7B1F10;   /* 9.10:1 — DARKER on light = further from ground */
  --accent-rgb:  165, 48, 27;
  --grad-a:      #A3301B;
  --grad-b:      #A3301B;
  /* --accent-ink deliberately NOT redeclared: 6.66:1 on --accent, 9.84:1 on --accent-hi */

  /* SEVERITY — re-derived pigments; --bad pulled to ~349° and to a far darker value
     class (L 0.059 vs the accent's 0.100) so brand red and state red never rhyme */
  --good:        #3D6238;   /* sap green.    S 27.3% (−43.3pp) | 6.15:1 ground / 5.03:1 surface-hi */
  --warn:        #755A1C;   /* raw sienna.   S 61.4% (−30.7pp) | 5.74:1 / 4.69:1 */
  --bad:         #7E2434;   /* crimson lake. S 55.6% (−28.6pp) | 8.43:1 / 6.90:1 */
  --info:        #38566E;   /* indigo ink.   S 32.5% (−62.0pp) | 6.77:1 / 5.54:1 */
}

/* ############ FLAVOR: PHOSPHOR ############ */

:root[data-flavor="phosphor"] {
  color-scheme: dark;

  /* ── Material — the coating unlit, behind glass. G highest in every value. ── */
  --ground:        #080b09;   /* R8 G11 B9 — never #000, #0a0a0a, or a neutral */
  --recess:        #080b09;   /* collapsed onto ground: the well IS the unlit plate */
  --surface:       #0e1311;   /* one value-step up — the faceplate */
  --surface-hi:    #151b18;   /* hover + table head — further FROM ground = brighter here */
  --scrim:         rgba(8, 11, 9, 0.72);
  --scrim-dense:   rgba(8, 11, 9, 0.93);

  /* ── Ink — silkscreen printed ON the plate. Complementary WARM lean (R highest).
        Only the accent emits; ink sits on the ground rather than in front of it. ── */
  --ink:           #eceae6;   /* 16.46:1 on ground */
  --ink-dim:       #9a9793;   /*  6.80:1 — the default for body copy */
  --ink-faint:     #6a6864;   /*  3.56:1 — placeholders, zero values, the em-dash */

  /* ── Line — picks up the cast of its own ground ── */
  --line:          #1b211e;
  --line-hi:       #2c3430;

  /* ── Brand — ONE accent: the plate excited. hsl(79, 65%, 61%).
        NOT hsl(120,100%,50%) terminal green; hue 79, saturation 65. ── */
  --accent:        #b4dd5c;   /* 12.65:1 on ground */
  --accent-hi:     #c8ea78;   /* 14.59:1 — brighter on dark = further from ground */
  --accent-ink:    #0b1005;   /* CONSTANT both themes. A very dark OLIVE-black, not #000 —
                                 ink laid on a lit cell, not a hole punched through it.
                                 12.32:1 on accent, 14.21:1 on accent-hi. */
  --accent-rgb:    180, 221, 92;   /* BARE TRIPLE — canvas contract, do not wrap in a colour fn */
  --grad-a:        #b4dd5c;        /* a == b: every legacy gradient renders FLAT */
  --grad-b:        #b4dd5c;

  /* ── Severity — quarantined from brand, every one ≥30pp below its default ── */
  --good:          #4e9c86;   /* S33 vs #22c55e S71 (-38pp) · 6.05:1 · deliberately TEAL,
                                 hue 163, so it can never be confused with the accent */
  --warn:          #c1913c;   /* S53 vs #f59e0b S92 (-39pp) · 6.95:1 */
  --bad:           #c9584c;   /* S54 vs #ef4444 S84 (-30pp) · 4.69:1 */
  --info:          #7f8f9e;   /* S14 vs #06b6d4 S94 (-80pp) · 5.96:1 — informational, never brand */
  --tint:          14%;       /* the one fill strength, reused by pills, badges, alerts */

  /* ── Type — three faces, three jobs; display ships ONE instance ── */
  --font-display:   'Martian Mono', 'Roboto Mono', ui-monospace, 'Cascadia Mono', Consolas, monospace;
  --font-sans:      'IBM Plex Sans', ui-sans-serif, system-ui, -apple-system, 'Segoe UI', Roboto, sans-serif;
  --font-mono:      'IBM Plex Mono', ui-monospace, 'SF Mono', 'Cascadia Mono', Consolas, 'Liberation Mono', monospace;
  --display-weight: 600;
  --display-stretch: 75%;     /* selects the pinned wdth-75 instance; condensed so a 50px
                                 mono headline still fits the measure */
  --tracking-label: 0.2em;    /* wide — a tracked mono legend reads as a character grid */

  /* ── Geometry — the squarest grade in the family. A character cell is a rectangle. ── */
  --r-chip:        2px;
  --r-control:     3px;
  --r-panel:       4px;
  --r-pill:        999px;
  --hair:          1px;
  --stripe:        3px;

  /* ── Motion ── */
  --t-fast:        .15s;
  --ease:          cubic-bezier(.2, 0, 0, 1);   /* fast attack, long tail — phosphor persistence */
  --pulse-dur:     2.4s;

  /* ── Layout ── */
  --wrap:          1040px;
  --gutter:        24px;
  --measure:       640px;

  /* ── Texture — the entire budget is this one number ── */
  --bloom:         5%;        /* strength of the single static radial lift off the top edge */
  --field-mode:    none;      /* Phosphor is the flavor that turns the particle field OFF */
  --field-opacity: 0;
  --field-density: 0;
}

/* Light is a re-pick, not an inversion: the bench lamp is on and the plate is
   read by reflection instead of emission. The material order therefore INVERTS
   coherently — panels are milled BELOW the ground plane rather than raised
   above it — so in BOTH themes "further from the ground" means "more contrast",
   and an input stays the deepest thing in a panel either way. The green cast on
   grounds and hairlines and the warm cast on ink both survive. --bloom goes to
   zero because a plate only blooms in the dark. */
html.light[data-flavor="phosphor"] {
  color-scheme: light;

  --ground:        #e9ece5;   /* R233 G236 B229 — pale bench, green cast, never #fff */
  --recess:        #dadfd4;   /* the deepest well */
  --surface:       #e0e4db;   /* the plate, set into the bench */
  --surface-hi:    #d5dacf;   /* hover: further from ground = DARKER. Direction inverts. */
  --scrim:         rgba(233, 236, 229, 0.78);
  --scrim-dense:   rgba(233, 236, 229, 0.94);

  --ink:           #1a1814;   /* still leans warm · 14.85:1 */
  --ink-dim:       #56534d;   /*  6.42:1 */
  --ink-faint:     #807d76;   /*  3.44:1 — non-essential text only */

  --line:          #c9cfc1;   /* green cast, matched to its own paper */
  --line-hi:       #b2b9a8;

  /* Phosphor cannot emit in daylight, so it is re-derived as pigment: same hue
     family (78), driven down to an olive that holds against paper. Re-picked
     to satisfy every pair simultaneously — 3.35:1 on ground and 3.10:1 on panel
     (graphic/large-text thresholds), and 4.82:1 under --accent-ink so button
     and badge labels clear AA. It is never used for small text. */
  --accent:        #698a1b;
  --accent-hi:     #66851a;   /* DARKER = further from ground (3.57:1 vs 3.35:1); 4.53:1
                                 under --accent-ink, so hover never drops below AA */
  --accent-ink:    #0b1005;   /* unchanged by contract */
  --accent-rgb:    105, 138, 27;
  --grad-a:        #698a1b;
  --grad-b:        #698a1b;

  /* Re-derived, not carried across — the dark severities wash out on paper */
  --good:          #2f6f5c;   /* S41 vs S71 (-30pp) · 4.96:1 */
  --warn:          #7a601f;   /* S59 vs S92 (-33pp) · 5.00:1 */
  --bad:           #963a2f;   /* S52 vs S84 (-32pp) · 5.98:1 */
  --info:          #4c5a68;   /* S16 vs S94 (-78pp) · 5.92:1 */

  --bloom:         0%;        /* no bloom in a lit room: the backdrop paints nothing */
  --field-opacity: 0;
}

/* ============================================================
   COMPAT BRIDGE — the 24 legacy token names used by the existing
   stylesheets, mapped onto the 42-token contract.

   Every alias is a var() REFERENCE, not a literal, so it re-resolves
   automatically when the flavor or theme changes. This is why no
   light-mode duplicate of this block is ever needed.

   Verified against the pilot: style.css references 22 of these via
   ~125 var() calls, and script.js reads the remaining two —
   --particle-color (line 57, string-interpolated into rgba()) and
   --nav-bg-scroll (line 149).

   --particle-color MUST stay a bare "R, G, B" triple. A hex value or
   an rgb() wrapper kills the particle field silently, with no console
   error, because the canvas builds `rgba(${pc}, alpha)` by hand.
   ============================================================ */
:root {
  --bg-deep:        var(--ground);
  --bg-surface:     var(--recess);
  --bg-card:        var(--surface);
  --bg-card-hover:  var(--surface-hi);
  --text-primary:   var(--ink);
  --text-secondary: var(--ink-dim);
  --text-muted:     var(--ink-faint);
  --accent-1:       var(--accent);
  --accent-2:       var(--grad-b);
  --accent-3:       var(--info);
  --gradient-start: var(--grad-a);
  --gradient-end:   var(--grad-b);
  --border:         var(--line);
  --border-hover:   var(--line-hi);
  --nav-bg:         var(--scrim);
  --nav-bg-scroll:  var(--scrim-dense);
  --footer-bg:      var(--scrim-dense);
  --particle-color: var(--accent-rgb);
  --mock-canvas-bg: var(--recess);
  --radius:         var(--r-panel);
  --radius-sm:      var(--r-control);
  --radius-xs:      var(--r-chip);
  --font:           var(--font-sans);
  --mono:           var(--font-mono);
}
