/* ==========================================================================
   DocBridge — design system
   Phase 1. Tokens, type, texture, spacing, motion. No page here.
   Palette and voices per BRIEF.md. Nothing inherited from the product UI
   or the previous docbridge.legal site.
   ========================================================================== */

/* ---- Typefaces (self-hosted, OFL) -------------------------------------- */
@font-face{font-family:"Instrument Serif";font-style:normal;font-weight:400;font-display:swap;
  src:url("../fonts/InstrumentSerif-Regular.woff2") format("woff2")}
@font-face{font-family:"Instrument Serif";font-style:italic;font-weight:400;font-display:swap;
  src:url("../fonts/InstrumentSerif-Italic.woff2") format("woff2")}
@font-face{font-family:"Schibsted Grotesk";font-style:normal;font-weight:400 900;font-display:swap;
  src:url("../fonts/SchibstedGrotesk-Variable.woff2") format("woff2")}
@font-face{font-family:"Fragment Mono";font-style:normal;font-weight:400;font-display:swap;
  src:url("../fonts/FragmentMono-Regular.woff2") format("woff2")}

/* ---- Tokens -------------------------------------------------------------- */
:root{
  /* Ink: near-black with a blue undertone */
  --ink-950:#06080D;
  --ink-900:#0B0F17;
  --ink-800:#121826;
  --ink-700:#1B2333;
  --ink-600:#2A3447;

  /* Bone: archival cream */
  --bone-50:#F7F2E8;
  --bone-100:#EFE8D9;
  --bone-200:#E3D9C4;
  --bone-300:#D2C5AA;
  --bone-400:#B9A98A;

  /* Brass / amber: paper, warmth, the human side */
  --brass-300:#E6BE72;
  --brass-400:#D2A24F;
  --brass-500:#B8863A;
  --brass-700:#7A5A22;   /* text-safe on bone */
  --brass-800:#5A4218;

  /* Signal: one cold luminous cyan-white. Live states only. */
  --signal:#B6F3FF;
  --signal-glow:rgba(182,243,255,.55);
  --signal-dim:rgba(182,243,255,.28);

  /* Text roles */
  --on-ink:var(--bone-100);
  --on-ink-2:rgba(239,232,217,.66);
  --on-ink-3:rgba(239,232,217,.54);
  --on-bone:var(--ink-900);
  --on-bone-2:rgba(11,15,23,.66);
  --on-bone-3:rgba(11,15,23,.50);

  /* Rules */
  --rule-ink:rgba(239,232,217,.12);
  --rule-bone:rgba(11,15,23,.14);

  /* Type */
  --serif:"Instrument Serif",Georgia,"Times New Roman",serif;
  --sans:"Schibsted Grotesk","Helvetica Neue",Arial,sans-serif;
  --mono:"Fragment Mono",ui-monospace,"SFMono-Regular",Menlo,monospace;

  --fs-display:clamp(3.25rem, 1.6rem + 7vw, 8.5rem);
  --fs-h2:clamp(2.375rem, 1.5rem + 3.6vw, 5rem);
  --fs-h3:clamp(1.625rem, 1.25rem + 1.4vw, 2.5rem);
  --fs-lead:clamp(1.125rem, 1rem + .4vw, 1.375rem);
  --fs-body:1.0625rem;
  --fs-small:.9375rem;
  --fs-mono:.8125rem;
  --fs-mono-xs:.6875rem;

  --lh-display:.92;
  --lh-h2:.98;
  --lh-body:1.55;
  --lh-mono:1.5;

  --ls-display:-.035em;
  --ls-h2:-.025em;
  --ls-mono:.02em;
  --ls-label:.14em;

  --measure:34ch;

  /* Space: 4px base, rhythm widens fast */
  --s-1:.25rem; --s-2:.5rem; --s-3:.75rem; --s-4:1rem; --s-5:1.5rem;
  --s-6:2rem;  --s-7:3rem;  --s-8:4rem;   --s-9:6rem; --s-10:8rem;
  --s-11:12rem; --s-12:16rem;
  --section-pad:clamp(6rem, 14vw, 13rem);
  --gutter:clamp(1.25rem, 5vw, 5rem);

  /* Motion: everything is slow except the settle */
  --dur-snap:180ms;      /* case-match settle. The only fast motion. */
  --dur-hold:500ms;      /* the uncertain beat holds this much longer */
  --dur-rise:700ms;      /* headlines rise 16px and fade in */
  --dur-travel:1600ms;   /* signal along a routing path */
  --dur-render:2000ms;   /* thermal line-by-line render */
  --dur-type:36ms;       /* per character, mono type-on */
  --stagger:90ms;

  --ease-rise:cubic-bezier(.16,1,.3,1);
  --ease-travel:cubic-bezier(.65,0,.35,1);
  --ease-snap:cubic-bezier(.2,.9,.25,1);
  --ease-linear:linear;

  /* Textures (SVG turbulence, no bitmaps) */
  /* grain: fine isotropic film grain, opaque so blending is predictable */
  --grain:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='256' height='256'><filter id='g'><feTurbulence type='fractalNoise' baseFrequency='.9' numOctaves='2' stitchTiles='stitch' seed='3'/><feColorMatrix type='saturate' values='0'/><feComponentTransfer><feFuncA type='linear' slope='0' intercept='1'/></feComponentTransfer></filter><rect width='256' height='256' filter='url(%23g)'/></svg>");
  /* mottle: soft pulp blotches for bone grounds */
  --mottle:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='480' height='480'><filter id='m'><feTurbulence type='fractalNoise' baseFrequency='.028' numOctaves='4' stitchTiles='stitch' seed='5'/><feColorMatrix type='saturate' values='0'/><feComponentTransfer><feFuncA type='linear' slope='0' intercept='1'/></feComponentTransfer></filter><rect width='480' height='480' filter='url(%23m)'/></svg>");
  /* fibre: faint horizontal streaks, the direction a thermal head prints */
  --fiber:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='420' height='420'><filter id='f'><feTurbulence type='fractalNoise' baseFrequency='.03 .7' numOctaves='3' stitchTiles='stitch' seed='11'/><feColorMatrix type='saturate' values='0'/><feComponentTransfer><feFuncA type='linear' slope='0' intercept='1'/></feComponentTransfer></filter><rect width='420' height='420' filter='url(%23f)'/></svg>");
  --thermal-lines:repeating-linear-gradient(to bottom, rgba(90,66,24,.07) 0 1px, transparent 1px 3px);
}

/* ---- Base ---------------------------------------------------------------- */
*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%;text-rendering:optimizeLegibility}
body{margin:0;font-family:var(--sans);font-size:var(--fs-body);line-height:var(--lh-body);
  font-feature-settings:"kern","liga";-webkit-font-smoothing:antialiased;background:var(--ink-900);color:var(--on-ink)}
h1,h2,h3,p{margin:0}
a{color:inherit}
:focus-visible{outline:2px solid var(--signal);outline-offset:4px}
.ground-bone :focus-visible{outline-color:var(--ink-900)}

/* ---- Grounds -------------------------------------------------------------- */
.ground-ink,.ground-bone{position:relative;isolation:isolate}
.ground-ink{background:var(--ink-900);color:var(--on-ink)}
.ground-bone{background:var(--bone-100);color:var(--on-bone)}

/* film grain + vignette over ink */
.ground-ink::before{content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;
  background-image:var(--grain);background-size:256px 256px;opacity:.11;mix-blend-mode:screen}
.ground-ink::after{content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;
  background:radial-gradient(120% 90% at 50% 35%, transparent 45%, rgba(4,6,10,.55) 100%)}

/* paper fibre + fine grain over bone */
.ground-bone::before{content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;
  background-image:var(--mottle),var(--grain);background-size:480px 480px,256px 256px;
  opacity:.5;mix-blend-mode:soft-light}
.ground-bone::after{content:"";position:absolute;inset:0;z-index:-1;pointer-events:none;
  background:radial-gradient(120% 90% at 50% 30%, transparent 55%, rgba(90,66,24,.16) 100%)}

/* ---- Voices ---------------------------------------------------------------- */
.v-display{font-family:var(--serif);font-weight:400;font-size:var(--fs-display);
  line-height:var(--lh-display);letter-spacing:var(--ls-display);text-wrap:balance}
.v-h2{font-family:var(--serif);font-weight:400;font-size:var(--fs-h2);
  line-height:var(--lh-h2);letter-spacing:var(--ls-h2);text-wrap:balance}
.v-h3{font-family:var(--serif);font-weight:400;font-size:var(--fs-h3);line-height:1.05;letter-spacing:-.015em}
.v-serif-i{font-family:var(--serif);font-style:italic}

.v-lead{font-family:var(--sans);font-size:var(--fs-lead);line-height:1.45;font-weight:400;max-width:var(--measure)}
.v-body{font-family:var(--sans);font-size:var(--fs-body);line-height:var(--lh-body);max-width:var(--measure)}
.v-small{font-family:var(--sans);font-size:var(--fs-small);line-height:1.5}

.v-mono{font-family:var(--mono);font-size:var(--fs-mono);line-height:var(--lh-mono);letter-spacing:var(--ls-mono);font-variant-numeric:tabular-nums}
.v-label{font-family:var(--mono);font-size:var(--fs-mono-xs);line-height:1.4;letter-spacing:var(--ls-label);text-transform:uppercase}

.muted{color:var(--on-ink-2)}     .ground-bone .muted{color:var(--on-bone-2)}
.faint{color:var(--on-ink-3)}     .ground-bone .faint{color:var(--on-bone-3)}
.brass{color:var(--brass-400)}    .ground-bone .brass{color:var(--brass-700)}
.signal{color:var(--signal);text-shadow:0 0 12px var(--signal-glow)}

/* ---- Objects ----------------------------------------------------------------- */
/* thermal paper: warm, slightly yellowed, print-head banding, fibre */
.paper{position:relative;background:
  linear-gradient(180deg, var(--bone-50) 0%, var(--bone-100) 60%, var(--bone-200) 100%);
  color:var(--ink-900);box-shadow:0 30px 60px -30px rgba(0,0,0,.8), 0 2px 0 rgba(255,255,255,.35) inset}
.paper::before{content:"";position:absolute;inset:0;pointer-events:none;
  background-image:var(--thermal-lines),var(--fiber),var(--mottle),var(--grain);
  background-size:auto,420px 420px,480px 480px,256px 256px;
  mix-blend-mode:multiply;opacity:.2}
/* raking light: driven by --lx/--ly (0..1) from the cursor */
.paper::after{content:"";position:absolute;inset:0;pointer-events:none;
  background:radial-gradient(90% 70% at calc(var(--lx,.3)*100%) calc(var(--ly,.2)*100%),
    rgba(255,250,235,.55), rgba(255,250,235,0) 60%);mix-blend-mode:soft-light}

/* routing path + signal */
.route{stroke:var(--rule-ink);stroke-width:1;fill:none}
.route-live{stroke:var(--signal);stroke-width:1.5;fill:none;
  filter:drop-shadow(0 0 6px var(--signal-glow));stroke-linecap:round}
.dot-live{fill:var(--signal);filter:drop-shadow(0 0 8px var(--signal-glow))}

.rule{height:1px;background:var(--rule-ink)}  .ground-bone .rule{background:var(--rule-bone)}

/* ---- Motion primitives ----------------------------------------------------- */
@keyframes rise{from{opacity:0;transform:translateY(16px)}to{opacity:1;transform:none}}
@keyframes travel{to{stroke-dashoffset:0}}
@keyframes pulse-once{0%{transform:scale(1);opacity:1}50%{transform:scale(1.6);opacity:.4}100%{transform:scale(1);opacity:1}}
@keyframes settle{0%{transform:translateY(-6px) scale(1.01);opacity:0}100%{transform:none;opacity:1}}

.rise{animation:rise var(--dur-rise) var(--ease-rise) both}
.rise>*{animation:rise var(--dur-rise) var(--ease-rise) both}
.rise>:nth-child(2){animation-delay:var(--stagger)}
.rise>:nth-child(3){animation-delay:calc(var(--stagger)*2)}
.rise>:nth-child(4){animation-delay:calc(var(--stagger)*3)}
.travel{stroke-dasharray:var(--len,600);stroke-dashoffset:var(--len,600);
  animation:travel var(--dur-travel) var(--ease-travel) forwards}
.settle{animation:settle var(--dur-snap) var(--ease-snap) both}
.pulse-once{animation:pulse-once 900ms var(--ease-travel) 1}

@media (prefers-reduced-motion: reduce){
  *,*::before,*::after{animation-duration:1ms !important;animation-delay:0ms !important;transition-duration:1ms !important;transition-delay:0ms !important}
  .travel{stroke-dashoffset:0}
}
