@font-face {
  font-family: "Outfit"; font-style: normal; font-weight: 400; font-display: swap;
  src: url("/fonts/outfit-400.woff2") format("woff2");
}
@font-face {
  font-family: "Outfit"; font-style: normal; font-weight: 600; font-display: swap;
  src: url("/fonts/outfit-600.woff2") format("woff2");
}

/* Laugh Tale design tokens — "Canon, played straight", ported from
   home.flxtcg.com (lifehub), which ported it from psa.flxtcg.com. Same laws,
   Laugh Tale's parameters: DARK ONLY on a neutral graphite sheet (#131418 —
   never blue-gray, never black, never near-black-plus-violet), one warm amber
   accent (#e3a455, the straw hat), Outfit 400/600 self-hosted.

   THE CONTRACT: components consume these tokens and nothing else; no raw
   colours in app.css. One accent (--ac) plus one ambient partner (--ac2);
   every other accent shade is color-mix-derived HERE. Never hand-pick a shade
   downstream. Type is three rungs — 26/600 masthead, 17/600 data, 13/400 body —
   with tracking scaled to size and nothing tracking positive. Glass is chrome
   only: the sticky masthead and the filter capsules. Content sits bare on the
   sheet: hairline runs, no boxes, no tints, no shadows. Card ART is the only
   colour-rich thing on the page and the UI stays quiet around it.

   ONE DELIBERATE DIVERGENCE FROM THE PARENT, and it is forced by the accent:
   lifehub's Darkened Fill Rule puts WHITE on --ac-fill because steel blue is
   dark. Amber is not. White on #e3a455 measures 2.16:1; the sheet's own ink on
   it measures 8.5:1. So --on-fill is a warm near-black and the fill LIGHTENS on
   hover. The law is unchanged — "the label clears 4.5:1, and hover moves the
   fill further from the ground" — only the direction flips, because the ground
   and the accent swapped ends of the ramp. */

:root {
  color-scheme: dark;

  /* ---- the accent pair --------------------------------------------------
     --ac is painted raw on focus rings, data-bar fills and the one filled
     capsule. --ac2's only job is the ambient ground. Everything else derives. */
  --ac: #e3a455;
  --ac2: #d98b3a;
  /* label ink on --ac-fill — the ONLY ink that ever sits on the accent */
  --on-fill: #1a1206;

  /* accent as TEXT: links, the active nav label, share figures, qty badges.
     Lifted a touch off the raw accent so it separates from --ac-fill sitting
     next to it in the same view (9.0:1 on the sheet). */
  --ac-pale: color-mix(in srgb, var(--ac) 88%, #ffffff);
  /* its hover. FURTHER FROM THE GROUND, and the ground here is graphite, so
     further out is more white: 88% -> 62% (11.5:1). Never toward the accent —
     that is the FILL's move, and borrowing it walks the ink back toward the
     sheet, which is the bug lifehub's audit #12 spent a round on. */
  --ac-hot: color-mix(in srgb, var(--ac) 62%, #ffffff);
  /* the one filled surface: raw amber, 8.5:1 against both the sheet under it
     and the --on-fill label on it. Hover lightens (further from graphite);
     darkening would walk the capsule back toward its own ground. */
  --ac-fill: var(--ac);
  --ac-fill-hot: color-mix(in srgb, var(--ac) 78%, #ffffff);

  /* ---- the sheet and the ink ramp --------------------------------------- */
  --bg: #131418;               /* the sheet; lives on <html> so overscroll shows it */
  --surface: #1b1c21;          /* detached SOLID data panels: the card popover */
  --surface3: rgba(255,255,255,.07);  /* quiet fill: fields, revealed hit areas */
  --ph: rgba(255,255,255,.05); /* the missing-art tile */
  --hovrow: rgba(255,255,255,.06);    /* the only tint content ever receives */
  --txt: #efedea;              /* ink — warm-neutral, not white */
  --m1: #9a978f;               /* secondary text (6.3:1) */
  --tert: #8b8880;             /* non-text furniture: marks, key lines (5.0:1) */
  --hair: rgba(255,255,255,.12);
  --hairh: rgba(255,255,255,.3);
  --hair2: rgba(255,255,255,.08);
  --track: rgba(255,255,255,.13);     /* the unfilled part of a share bar */
  --barfill: var(--ac);        /* raw amber measures 6.2:1 against --track */
  --tagmix: 18%;               /* accent-wash strength for chips; graphite eats a
                                  low-alpha wash, hence 18 and not light's 12 */
  /* A data label that has to read over ARBITRARY card art. Not glass — glass is
     chrome, and this sits on content — a near-opaque plate so a qty stays legible
     over a white sail or a black coat alike. */
  --badge: rgba(9,10,12,.82);

  /* ---- Liquid Glass: chrome only ----------------------------------------
     Translucent ground plus a DUAL rim (specular catch on the top edge,
     falloff on the bottom). One rim is a frosted card; the pair is a lens. */
  --glass: rgba(28,29,34,.62);
  --glasssolid: #1e1f24;       /* reduced-transparency / no-backdrop-filter twin */
  --rim: rgba(255,255,255,.16);
  --rimb: rgba(0,0,0,.35);     /* heavier than a light sheet's: a low-alpha dark
                                  edge simply vanishes on graphite */
  --segtrack: rgba(255,255,255,.05);  /* faint track inside a segmented capsule */
  --segon: rgba(255,255,255,.1);      /* the nav lamp / the on filter capsule */
  --shc: rgba(0,0,0,.34);      /* Glass Lens cast */
  --shc2: rgba(0,0,0,.5);      /* popover cast */
  --shc3: rgba(0,0,0,.28);     /* whisper cast: chrome at rest, the lamp lift */
  --fhov: #ffffff;             /* an inactive nav label on hover */
  --scrim: rgba(0,0,0,.5);
  --scrim-solid: rgba(0,0,0,.6);

  /* ambient ground (body::before): two very wide, very soft radials pooled in
     the top corners, derived ONLY from --ac/--ac2 — the warm room air the glass
     masthead needs to lens. Graphite eats alpha, so 10/7 rather than a light
     sheet's 6/4. If you can name where it stops, it is too strong. */
  --amb: radial-gradient(112% 56% at 82% -20%, color-mix(in srgb, var(--ac2) 10%, transparent), transparent 56%),
         radial-gradient(90% 48% at -12% -6%, color-mix(in srgb, var(--ac) 7%, transparent), transparent 52%);

  /* ---- status voices -----------------------------------------------------
     Two, and they keep to their jobs: green is approved/confirmed, red is
     errors and the pending flag's alert. Amber is the accent, not a warning —
     there is no third voice, and a page that wants one wants a word instead. */
  --ok: #43c383;
  --err: #ff8a7a;

  /* ---- the card-colour vocabulary ---------------------------------------
     THE ONE PLACE THE One-Accent Rule DOES NOT REACH, and it is the game's
     vocabulary rather than the site's: a leader is Red or Blue the way a date
     is a Tuesday. Six hues cannot be five shades of amber and still mean six
     things. Kept honest by three constraints — they only ever paint 7px MARKS,
     never text, a surface or a fill; every mark carries the colour's NAME as a
     text or visually-hidden twin, so the reading survives without hue; and each
     is tuned to clear 3:1 against the sheet on its own (Black included, at
     3.7:1 — it is the darkest mark, which is the reading). Nothing else on the
     site may spend them. */
  --c-red: #e0655a;
  --c-green: #62b877;
  --c-blue: #5c9fe0;
  --c-purple: #a78ae0;
  --c-black: #6f7076;
  --c-yellow: #e0c257;

  /* ---- type: three rungs, plus a caption tier hanging off body -----------
     Every size in the sheet has a token here. A new size does not create a
     rung: it hangs off the caption tier or the numeral set, or it does not
     ship. Outfit has no 650, so the rungs run 600/600/400 and the masthead is
     separated from the data rung by SIZE and TRACKING, not extra weight. */
  --sans: 'Outfit', ui-rounded, 'SF Pro Rounded', -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
  --fs-title: 26px;   --tr-title: -0.021em;   /* the page's one display line */
  --fs-title-c: 22px; --tr-title-c: -0.017em; /* the same, under 640px */
  --fs-gate: 24px;    --tr-gate: -0.02em;     /* the centred gate title */
  --fs-data: 17px;    --tr-data: -0.012em;    /* section heads, brand, event names */
  --fs-ui: 15px;      /* fields and controls; 16px on touch (the iOS zoom guard) */
  --fs-b: 13px;       /* body — the default */
  --fs-s: 12px;       /* caption */
  --fs-xs: 11.5px;    /* micro: qty badges, card names, chips. The floor. */

  /* ---- corners: content squares off, controls are capsules --------------- */
  --r-xs: 4px;        /* the qty badge */
  --r-sm: 6px;        /* card art, thumbnails */
  --r-md: 8px;        /* revealed hit areas */
  --r-lg: 12px;       /* the presented leader card */
  --r-xl: 14px;       /* popovers, panels, the decklist field */
  --r-cap: 999px;     /* every single-line control */

  /* ---- motion -----------------------------------------------------------
     The whole budget: ONE entrance settle on the sections, ONE signature — the
     deck grid's card stagger — plus chrome (the nav lamp's glide, press-scale,
     the popover materialize). Nothing decorative, nothing that loops. */
  --ease-settle: cubic-bezier(.2,.7,.3,1);
  --ease-runout: cubic-bezier(.23,1,.32,1);   /* considered decelerations */
  --t-rise: 380ms;      /* the section settle's travel */
  --t-stagger: 40ms;    /* its step; section n waits (n - 1) of these */
  /* The deck grid's step. Deliberately smaller than --t-stagger and applied in
     BANDS rather than per tile: fifty cards at 40ms each would take two seconds
     to arrive, and an entrance that outlasts the chrome reads as lag, not
     arrival. Ten bands of five at 26ms lands the last one at 260ms — inside the
     section settle it rides on. */
  --t-card-stagger: 26ms;
  --t-card-rise: 300ms;
  --t-press: 140ms;     /* controls */
  --t-press-tile: 120ms;/* big tap targets: a card tile reads sluggish at 140 */
  --t-quiet: 150ms;
  --t-state: 180ms;
  --t-lift: 140ms;      /* the popover materialize */
  --t-lamp: 260ms;      /* the nav lamp's glide between entries */
}
