/* ═══════════════════════════════════════════════════════════════
   cite0 · V3 design tokens — dashboard (bright mode)
   ───────────────────────────────────────────────────────────────
   The token source of truth for the V3 client + admin dashboard.

   SCHEME (locked 2026-07-09): black & white + green/red.
     • Grayscale        → neutral structure & content
     • Black (--ink)    → identity, primary, interactive, emphasis
     • Green / Red      → MEANING only (good / bad), with intensity
                          ramps expressing DEGREE (mild → strong)
     No accent hue. Brand marks (Fraunces, the cite0 wordmark) are
     kept; the app UI itself is monochrome + semantic color.

   HIGHLIGHTING RULE (see md/v3/design/foundation.md):
     • Neutral emphasis  → contrast, never color: inversion (--surface-
       invert + white text), weight, elevation. One dominant highlight
       per view (the inverted "special black" hero).
     • Meaningful emphasis → green/red + intensity, ONLY when it is a
       genuine good/bad judgment.

   Fonts are kept from the brand — load via /design/fonts.css
   (Fraunces / Inter / JetBrains Mono). This file defines no @font-face.
   ═══════════════════════════════════════════════════════════════ */

:root {
  /* ─── Neutral ramp — the base ──────────────────────────────── */
  --n-0:    #ffffff;   /* card / raised surface        */
  --n-25:   #fafafa;   /* row hover                    */
  --n-50:   #f5f5f6;   /* page background              */
  --n-100:  #ececef;   /* sunken / track fill          */
  --n-200:  #e2e2e6;   /* bar background               */
  --n-300:  #c9c9d0;   /* flat trend line, disabled    */
  --n-400:  #9a9aa2;   /* faint text, placeholder      */
  --n-500:  #6c6c73;
  --n-600:  #5c5c63;   /* muted text                   */
  --n-800:  #2a2a2e;
  --n-900:  #1c1c20;
  --n-950:  #141417;   /* ink — primary text & black   */

  /* ─── Green ramp — success, degree of good ─────────────────── */
  --green-50:  #f0fdf4;
  --green-100: #dcfce7;
  --green-300: #86efac;   /* light green = partial / mentioned */
  --green-500: #16a34a;   /* strong green = strong success     */
  --green-600: #15803d;   /* green text/ink                    */
  --green-700: #14652f;

  /* ─── Red ramp — concern, degree of bad ────────────────────── */
  --red-50:  #fef2f2;
  --red-100: #fee2e2;
  --red-300: #fca5a5;
  --red-500: #dc2626;
  --red-600: #c02626;     /* red text/ink */
  --red-700: #b91c1c;

  /* ═══ SEMANTIC — use these in components ═══════════════════════ */

  /* Surfaces */
  --surface-page:    var(--n-50);
  --surface:         var(--n-0);
  --surface-hover:   var(--n-25);
  --surface-sunken:  var(--n-100);
  --surface-invert:  var(--n-950);   /* the "special black" — hero moment */

  /* Text */
  --text:            var(--n-950);
  --text-muted:      var(--n-600);
  --text-subtle:     var(--n-500);
  --text-faint:      var(--n-400);
  --text-invert:     var(--n-0);
  --text-invert-muted: rgba(255,255,255,.62);

  /* Borders / hairlines */
  --border:          rgba(20,20,23,.09);
  --border-strong:   rgba(20,20,23,.16);
  --border-invert:   rgba(255,255,255,.12);

  /* Emphasis / identity / interactive = BLACK (no accent hue) */
  --emphasis:        var(--n-950);   /* primary buttons, active nav, "you", your-data */
  --emphasis-hover:  #000000;
  --on-emphasis:     var(--n-0);
  --focus-ring:      var(--n-950);

  /* Meaning — POSITIVE (green) */
  --positive:        var(--green-500);
  --positive-ink:    var(--green-600);
  --positive-soft:   var(--green-100);
  --positive-faint:  var(--green-50);

  /* Meaning — NEGATIVE (red). Destructive actions (delete) also use red. */
  --negative:        var(--red-500);
  --negative-ink:    var(--red-600);
  --negative-soft:   var(--red-100);
  --negative-faint:  var(--red-50);

  /* Directional (deltas, sparklines): up=green, down=red, flat=neutral */
  --trend-up:        var(--green-500);
  --trend-down:      var(--red-500);
  --trend-flat:      var(--n-300);

  /* ─── Categorical — the shopper-priority dimensions ──────────
     The ONE place hue is allowed to mean something other than
     good/bad: these categories carry no judgment, and telling them
     apart is the job (a donut of 11 slices). Bound to the DIMENSION,
     never to rank — so filtering or re-sorting never repaints a slice.
     Mirrors the fixed registry in engine/internal/prompt (DimensionDef).
     Never use these for status; green/red own that. */
  --dim-cost:        #2563eb;
  --dim-quality:     #7c3aed;
  --dim-assurance:   #0891b2;
  --dim-skill:       #e11d48;
  --dim-reputation:  #ea580c;
  --dim-comfort:     #d97706;
  --dim-speed:       #0d9488;
  --dim-suitability: #c026d3;
  --dim-access:      #4d7c0f;
  --dim-service:     #a16207;
  --dim-values:      #78716c;
  --dim-use-case:    #4f46e5;
  --dim-unknown:     var(--n-400);

  /* Categorical — KIND OF SOURCE (where AI read it). Same rule as --dim-*:
     hue is bound to the kind, never to rank, so re-sorting never repaints one.
     "Owned" is deliberately the ink: your own pages are identity, not a
     category (system.md §1). Mirrors radar.SourceType in the engine. */
  --src-review:      #7c3aed;
  --src-directory:   #0891b2;
  --src-gbp:         #ea580c;
  --src-publisher:   #4d7c0f;
  --src-reddit:      #e11d48;
  --src-youtube:     #d97706;
  --src-marketplace: #c026d3;
  --src-government:  #0d9488;
  --src-competitor:  #a16207;
  --src-owned:       var(--emphasis);
  --src-unknown:     var(--n-400);

  /* ─── Typography (fonts kept from brand) ───────────────────── */
  --font-display: 'Fraunces', 'Georgia', serif;
  --font-sans:    'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
  --font-mono:    'JetBrains Mono', ui-monospace, 'SF Mono', Menlo, monospace;

  --text-h1:       28px;   /* page title (display serif)   */
  --text-h2:       23px;   /* section / owner lede         */
  --text-h3:       15px;   /* card / panel heading         */
  --text-body-lg:  16px;
  --text-body:     14px;   /* default UI text              */
  --text-sm:       13px;   /* controls, secondary          */
  --text-caption:  12px;   /* labels, footnotes            */
  --text-micro:    11px;   /* uppercase eyebrows, counts   */
  --text-metric:   34px;   /* hero metric number (serif)   */

  --weight-regular:  400;
  --weight-medium:   500;
  --weight-semibold: 600;
  --weight-bold:     700;

  --tracking-tight:   -0.02em;  /* display headings */
  --tracking-snug:    -0.01em;
  --tracking-normal:  0;
  --tracking-eyebrow:  0.06em;  /* uppercase micro labels */

  --leading-tight:   1.15;
  --leading-snug:    1.3;
  --leading-normal:  1.5;

  /* ─── Spacing (4-px base) ──────────────────────────────────── */
  --space-1:  4px;
  --space-2:  8px;
  --space-3:  12px;
  --space-4:  16px;
  --space-5:  22px;
  --space-6:  30px;
  --space-7:  44px;
  --space-8:  64px;

  /* ─── Radii ────────────────────────────────────────────────── */
  --radius-sm:   7px;    /* small buttons, chips-square   */
  --radius:      10px;   /* buttons, inputs               */
  --radius-lg:   14px;   /* tiles, list containers        */
  --radius-xl:   16px;   /* panels, cards                 */
  --radius-pill: 999px;  /* chips, status pills, bars     */

  /* ─── Shadows — subtle by default ──────────────────────────── */
  --shadow-sm:      0 1px 2px rgba(20,20,23,.05);
  --shadow:         0 2px 8px rgba(20,20,23,.06);
  --shadow-md:      0 8px 22px rgba(20,20,23,.10);
  --shadow-lg:      0 12px 40px rgba(20,20,23,.14);
  /* the inverted hero tile + its glowing-white number */
  --shadow-invert:  0 12px 40px rgba(20,20,23,.28);
  --glow-invert:    0 0 26px rgba(255,255,255,.45);

  /* ─── Motion ───────────────────────────────────────────────── */
  --duration-fast: 120ms;
  --duration-base: 180ms;
  --duration-slow: 260ms;
  --ease-standard: cubic-bezier(0.2, 0, 0, 1);
  --ease-out:      cubic-bezier(0, 0, 0.2, 1);

  /* ─── Texture ──────────────────────────────────────────────── */
  /* Subtle film grain adds craft to flat monochrome. Apply as a
     fixed, pointer-events:none SVG feTurbulence overlay at this
     opacity (multiply on light surfaces). */
  --grain-opacity: 0.03;

  /* ─── Z-index ──────────────────────────────────────────────── */
  --z-raised:  10;
  --z-sticky:  100;
  --z-overlay: 900;
  --z-modal:   1000;
  --z-toast:   1100;

  /* Glow for a headline on a dark surface (noir landing). Off on light. */
  --text-glow: none;
}

/* ═══════════════════════════════════════════════════════════════
   THEME · noir  — the DARK landing (marketing surface)
   ───────────────────────────────────────────────────────────────
   Same foundation, inverted. The landing opts in with
   <html data-theme="noir"> (or on any wrapper); it only re-points the
   SEMANTIC tokens, so components read the same var(--surface|--text|
   --emphasis|--positive…) and re-skin to "glowing white on special
   black + grain". The light dashboard stays on :root and is untouched.
   Aesthetic reference: md/v3/design/noir-landing.html.
   ═══════════════════════════════════════════════════════════════ */
:root[data-theme="noir"],
[data-theme="noir"] {
  /* Surfaces — deep, layered black (Onyx → Carbon). Page also takes the
     noir bloom via the .v3-noir-page utility below. */
  --surface-page:   #0a0a0b;
  --surface:        #141416;   /* raised card / panel      */
  --surface-hover:  #17171a;
  --surface-sunken: #0e0e10;
  --surface-invert: #f6f6f7;   /* rare light block on dark */

  /* Text — near-white, never pure, with a white glow on headlines */
  --text:              #f6f6f7;
  --text-muted:        rgba(246,246,247,.66);
  --text-subtle:       rgba(246,246,247,.50);
  --text-faint:        rgba(246,246,247,.38);
  --text-invert:       #0a0a0b;
  --text-invert-muted: rgba(10,10,11,.62);
  --text-glow:         0 0 44px rgba(255,255,255,.22);

  /* Hairlines — luminous, low alpha */
  --border:        rgba(255,255,255,.10);
  --border-strong: rgba(255,255,255,.20);
  --border-invert: rgba(10,10,11,.14);

  /* Emphasis / primary / interactive = WHITE on dark (the glowing CTA) */
  --emphasis:       #f6f6f7;
  --emphasis-hover: #ffffff;
  --on-emphasis:    #0a0a0b;
  --focus-ring:     #ffffff;

  /* Meaning — lifted so green/red read on black */
  --positive:       #34d399;
  --positive-ink:   #6ee7b7;
  --positive-soft:  rgba(52,211,153,.14);
  --positive-faint: rgba(52,211,153,.08);
  --negative:       #fb7185;
  --negative-ink:   #fda4af;
  --negative-soft:  rgba(251,113,133,.14);
  --negative-faint: rgba(251,113,133,.08);
  --trend-up:       #34d399;
  --trend-down:     #fb7185;
  --trend-flat:     rgba(255,255,255,.25);

  /* Categorical — same hues, lifted to read on black */
  --dim-cost:        #60a5fa;
  --dim-quality:     #a78bfa;
  --dim-assurance:   #22d3ee;
  --dim-skill:       #fb7185;
  --dim-reputation:  #fb923c;
  --dim-comfort:     #fbbf24;
  --dim-speed:       #2dd4bf;
  --dim-suitability: #e879f9;
  --dim-access:      #a3e635;
  --dim-service:     #d4b106;
  --dim-values:      #a8a29e;
  --dim-use-case:    #818cf8;
  --dim-unknown:     rgba(255,255,255,.38);

  /* Source kinds — same hues, lifted to read on black. --src-owned follows
     --emphasis (white on noir), so "your own pages" stays the identity mark. */
  --src-review:      #a78bfa;
  --src-directory:   #22d3ee;
  --src-gbp:         #fb923c;
  --src-publisher:   #a3e635;
  --src-reddit:      #fb7185;
  --src-youtube:     #fbbf24;
  --src-marketplace: #e879f9;
  --src-government:  #2dd4bf;
  --src-competitor:  #d4b106;
  --src-owned:       var(--emphasis);
  --src-unknown:     rgba(255,255,255,.38);

  /* Shadows — deeper on dark */
  --shadow-sm:     0 1px 2px rgba(0,0,0,.40);
  --shadow:        0 2px 10px rgba(0,0,0,.45);
  --shadow-md:     0 8px 28px rgba(0,0,0,.50);
  --shadow-lg:     0 24px 64px rgba(0,0,0,.60);
  --shadow-invert: 0 24px 70px rgba(0,0,0,.55);
  --glow-invert:   0 0 40px rgba(255,255,255,.35);

  /* Grain a touch stronger; blend as overlay on dark (set by utility) */
  --grain-opacity: 0.05;

  /* ── Landing-only highlight materials (noir marketing surface) ──────
     Silver is the PRIMARY highlight — a lit metallic sheen used for
     headlines / key CTAs, brighter than flat white. Blue is a RARE cold
     spark: at most one moment per view (a live pulse, a single word).
     Neither exists on the light dashboard. */
  --silver-hi:    #ffffff;
  --silver-mid:   #d7dae0;
  --silver-low:   #9aa0ad;
  --silver-sheen: linear-gradient(155deg, #ffffff 0%, #dfe3ea 42%, #9aa0ad 100%);
  --silver-glow:  0 0 32px rgba(226,230,238,.45);

  --spark-blue:      #5b8bff;   /* rare cold accent */
  --spark-blue-soft: rgba(91,139,255,.16);
  --spark-blue-glow: rgba(91,139,255,.55);
}

/* ═══════════════════════════════════════════════════════════════
   Utility primitives — additive helpers new components can opt into.
   ═══════════════════════════════════════════════════════════════ */

/* The one dominant, neutral "look here" highlight per view. */
.v3-surface-invert {
  background: var(--surface-invert);
  color: var(--text-invert);
}
/* Glowing-white hero number on an inverted surface (data emphasis,
   not a brand color). Pair with the display serif. */
.v3-metric {
  font-family: var(--font-display);
  font-weight: var(--weight-semibold);
  font-size: var(--text-metric);
  line-height: 1;
}
.v3-surface-invert .v3-metric { text-shadow: var(--glow-invert); }

/* Directional value (delta / change). Add .up | .down | .flat. */
.v3-delta { font-weight: var(--weight-bold); font-variant-numeric: tabular-nums; }
.v3-delta.up   { color: var(--positive-ink); }
.v3-delta.down { color: var(--negative-ink); }
.v3-delta.flat { color: var(--text-faint); }

/* Headline that glows on the noir landing, plain on the light dashboard. */
.v3-headline { text-shadow: var(--text-glow); }

/* Glowing-silver text — the noir landing's primary highlight material.
   Metallic sheen + soft bloom; use for the hero headline word / wordmark. */
.v3-silver {
  background: var(--silver-sheen, #fff);
  -webkit-background-clip: text; background-clip: text; color: transparent;
  filter: drop-shadow(var(--silver-glow, 0 0 32px rgba(226,230,238,.45)));
}
/* Rare cold-blue spark — landing only, ≈one moment per view. */
.v3-spark { color: var(--spark-blue, #5b8bff); }
.v3-spark-dot {
  width: 8px; height: 8px; border-radius: 50%;
  background: var(--spark-blue, #5b8bff);
  box-shadow: 0 0 10px var(--spark-blue-glow, rgba(91,139,255,.55));
}

/* The noir landing page background: deep black + a soft white bloom. Use on
   the landing root under [data-theme="noir"]. On light it's a no-op fallback. */
.v3-noir-page {
  background:
    radial-gradient(1100px 620px at 72% -14%, rgba(255,255,255,.12), transparent 58%),
    linear-gradient(180deg, #0e0e10 0%, #0a0a0b 52%, #060607 100%);
  background-attachment: fixed;
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    transition-duration: 0.01ms !important;
  }
}
