/* Uproad Hub — design tokens.

   ==========================================================================
   THE CYCLORAMA
   ==========================================================================
   A cyclorama is a seamless backdrop with no corner and no seam, where the
   horizon exists only where the light stops. That is the whole system:

     · There are no borders. Separation is luminance. A region is not marked
       off by a line, it is lit more or less than what surrounds it.
     · Cobalt sits low and rises into the room; rose gathers above it; and
       white-day is reserved for the ONE thing you are doing and nothing else.
     · Radii are large enough that the eye reads a curve, not a corner.
     · Type is light and open, because a cyc is vast and a heavy face sits on
       it like a sticker.

   This replaced "The Lit Workbench" (near-black ground, copper accent, Libre
   Caslon display serif) in 2026-08. The old world's two-grounds idea was
   written down but never executed — chrome, stage and surfaces all lived
   inside a ten-value band, so nothing was figure and nothing was ground.

   FOUR THEMES, and they are four states of the same light:
     dark        night cyc — cobalt from the floor, rose above
     light       day cyc — white-hot above, cobalt settling at the base
     adhd-dark   the same night, quiet: no rose, no drift, the glow pulled in
     adhd-light  the same day, quiet
   The quiet pair is NEVER a different hue. It is the same wash with the
   decoration taken out, because coloured overlays as a reading aid have
   failed replication for forty years.
   ========================================================================== */

:root {
  color-scheme: dark;

  /* ---- the three lights ------------------------------------------------ */
  /* THE GRADE IS WARM-KEY. Copper is the light, slate is the shadow. That is
     the whole change from the cobalt build, and it is not a recolour: which
     end of the frame the light comes from is the single biggest decision in a
     grade. A cool key with a warm accent reads as software. A warm key with a
     cool shadow reads as cinema, which is the business Uproad is actually in.
     These are the brand book's own hexes: copper #B5651D and muted navy
     #2C3E52, lifted only as far as each ground requires. */
  --up-slate:  #2C3E52;   /* the shadow, and the floor it makes. Brand navy. */
  --up-key:    #C87428;   /* the key light, off frame right. Brand copper. */
  --up-day:    #FFFDF9;   /* reserved for the active thing. Nothing else. */

  /* ---- night ground (the default) --------------------------------------- */
  /* SOFTENED 2026-08-10. This was #0B0E12, three values off pure black, and a
     near-black ground is the hardest surface an interface can have: every
     hairline on it is a maximum-contrast event, every panel edge is a cut, and
     the eye never gets to rest. Lifted to a slate-leaning charcoal, which
     costs almost nothing measurable — paper still reads 16.2:1 on it — and
     buys the whole app a softer floor to sit on. --up-ink stays where it was:
     it is the TEXT that lands on copper, not a ground, and it must not drift. */
  --up-ground: #14171C;
  --up-ink:    #0B0E12;
  --up-paper:  #F4F2EE;   /* default text. Warm, because the room is. */
  --up-cream:  #EDEAE4;   /* the day-cyc ground; see the light block below */

  /* "You are here" is copper now, and it is the brand's emphasis variant
     rather than the raw #B5651D, which clears nothing at 4.5:1 (paper 3.69,
     ink 4.19, white 4.34 — it sits in a tonal dead zone). See decisions.md. */
  --up-accent: #E08F45;
  /* due and danger have to stay legible AS SIGNALS next to a copper accent, so
     they are pushed apart on lightness and hue: gold, not amber, or "deadline"
     and "you are here" become the same colour. */
  --up-due:    #F3CB63;   /* deadline pressure, and only that */
  --up-danger: #FF7F6D;   /* errors and overdue */
  /* Approved — the one genuinely positive state in the app. It had no token,
     so the two places that needed it each carried their own literal: #3d7d54
     on the review page (3.76:1 on the night stage) and #4B9E6A on the status
     chip (3.28:1 on the day stage). Both failed, in opposite themes, because
     a single green cannot clear on both washes — which is exactly why every
     other semantic colour here is declared twice. */
  --up-ok:     #6FE0A0;

  /* Aliases. 129 rules say --up-copper and 7 say --up-navy, and after the
     regrade BOTH NAMES ARE FINALLY HONEST: --up-copper really is a copper and
     --up-navy really is the brand navy. The cobalt build had them pointing at
     a rose and a cobalt, which is why they read as legacy cruft. New rules
     still use --up-accent and --up-slate. */
  --up-copper:      var(--up-accent);
  --up-accent-warm: var(--up-accent);
  --up-navy:        var(--up-slate);

  /* Neutral ramp, warmed to sit in a tungsten room. A cool grey on a warm
     ground is both a contrast failure and a grading error — measured at
     3.87:1 on the warm build before this was corrected. */
  --up-neutral-100: #F1EEE8;
  --up-neutral-200: #D5D0C6;
  --up-neutral-300: #ADA79B;
  --up-neutral-400: #837D72;
  --up-neutral-500: #55524B;
  --up-neutral-600: #2E2C28;

  /* ---- semantic ------------------------------------------------------- */
  --up-bg:     var(--up-ground);
  --up-fg:     var(--up-paper);
  --up-border: var(--up-line);
  --up-muted:  #A9A399;

  /* Surfaces are translucent, not tinted: a region on a cyc is a place where
     more light lands, so it lets the wash through rather than covering it. */
  --up-surface:   rgba(244, 242, 238, 0.07);
  --up-surface-2: rgba(244, 242, 238, 0.115);
  --up-line:      rgba(244, 242, 238, 0.07);

  --up-strong-bg: var(--up-accent);   /* also used as a border-color, so it
                                         stays a solid — the gradient lives in
                                         --up-strong-grad */
  /* The committing control's gradient must never END on raw brand copper
     #B5651D: dark text on it measures 4.42:1, which is the same dead-zone
     failure decisions.md already recorded. It ends on the emphasis variant. */
  --up-strong-fg: #150E04;
  /* Softened with the 2026-08-10 pass. The range was #E9A45E → #D07A2C, a
     29-value drop across a pill, which reads as a moulded plastic lozenge
     rather than as a warm fill. Halving the range keeps the Day Rule's
     gradient — the committing action is still the only thing wearing one —
     while letting it read as ONE colour with a light on it. Ink measures
     6.66:1 on the darker stop, so the Copper Rule still clears. */
  --up-strong-grad: linear-gradient(135deg, #E39C57, #D4863C);
  /* The lift under a committing control. NEUTRAL, and that is the whole point:
     until 2026-08-09 these carried rgba(255,143,180,…) — the ROSE from the
     retired cobalt build — so .btn, the deck's Done and the FAB were all
     casting a pink light in a copper world. DESIGN.md already said it: a
     coloured glow reads as a light source, and there is no light source any
     more. Declared per theme because one alpha cannot serve both grounds — a
     shadow that reads on ink is a smear on cream. */
  --up-strong-lift: rgba(0, 0, 0, 0.34);

  /* ---- the ground ------------------------------------------------------
     FLAT, as of 2026-08-08. This is the biggest single change since the
     redesign and it is worth stating plainly: the cyclorama WAS the wash, so
     removing the gradient removes the metaphor. What is left is the grade —
     copper key, slate shadow, warm neutrals — on one honest ground.

     Mark's call, and the measured argument is stronger than the aesthetic one.
     A gradient ground is a MOVING TARGET: every value in the app has to clear
     against its worst point, wherever a user happens to scroll. A flat ground
     is a fixed one. Flattening cleared three long-standing contrast failures
     outright (.stage-sep, .ps-seg.ps-phase, span.slug) and improved a fourth,
     without a single colour being retuned. Atmosphere was quietly costing
     legibility everywhere, which for an app built for people with ADHD is the
     wrong thing to be spending. */
  --cyc-wash: linear-gradient(var(--up-ground), var(--up-ground));
  --cyc-horizon: linear-gradient(rgba(0,0,0,0), rgba(0,0,0,0));
  /* A card is a surface with an edge now, not a pool of light with a fade.
     DESIGN.md used to call that fade "the one detail separating a lit region
     from a rectangle with a line drawn round it" — this world wants the
     rectangle, because a rectangle is legible at any scroll position. */
  --cyc-pool:  linear-gradient(rgba(244,242,238,0.075), rgba(244,242,238,0.075));
  /* THE SOFT PASS, 2026-08-10 (Mark's brief: "I love how soft Todoist looks").
     The Edge Rule stands — every surface still has an edge — but it was being
     stated twice, by a rim AND a two-part shadow, on every panel in the app.
     Say it once. A panel now separates mostly by FILL (surface lifted above),
     with the hairline as confirmation rather than as the argument, and the
     shadow reduced to a single contact shadow that says "this sits on top"
     without drawing a second outline underneath. */
  --cyc-spill: 0 1px 2px rgba(0,0,0,0.30);
  --cyc-rim:   rgba(244, 242, 238, 0.085);
  --cyc-scrim: rgba(20, 23, 28, 0.55);
  --cyc-ease:  cubic-bezier(.2, .9, .25, 1);
  --cyc-blur:  0px;   /* no frost: see the ground note above */

  /* ---- shape ----------------------------------------------------------- */
  /* Three steps, and every one is large: under about 20px the eye reads a
     rounded rectangle, which is a corner, which a cyclorama does not have.
     Controls go fully round because a pill has no corner at all. */
  --up-radius-sm: 999px;  /* controls — buttons, chips, inputs, nav items */
  --up-radius:    16px;   /* panels — cards, tables, wells */
  --up-radius-lg: 22px;   /* the deck card and dialogs */
  /* A FOURTH step, and the calendar is why it exists. The scale above assumes
     every element is either a single-line control (pill) or a full-width panel
     (26px+). A dense grid of small blocks is neither: an event chip in a 66px
     day column is 66px wide, so a 26px radius is nearly half its width and the
     corners round away into each other — and the company rule down its left
     edge bends into an arc. At 999px it was worse still: a literal ellipse.
     Use this ONLY for small repeated blocks in a dense grid. It is the one
     place the "no corner under 20px" rule is relaxed, because at this size the
     alternative is not a corner, it is a blob. */
  --up-radius-xs: 10px;

  /* THE CALENDAR'S HAIRLINE — the one documented exception to the no-border
     rule, alongside the quiet themes' nav edge. Mark's call, 2026-08-08.
     The justification is that a calendar's lines are INFORMATION, not
     decoration: they say which day and which row a thing is in, and that is a
     job luminance cannot do at seven columns wide. Everywhere else, an edge is
     still a rim of light or nothing. Scoped to .wk/.cal so it cannot spread. */
  --cal-rule: rgba(244, 242, 238, 0.11);

  --up-measure: 72ch;

  /* ---- type ------------------------------------------------------------ */
  /* One family. The display serif was retired with the workbench: a cyc has no
     serif in it, and the "one thing at a time" moment is now carried by SCALE
     and LIGHT rather than by a second voice. That also deleted a font file. */
  --up-font-display: "Work Sans", "Helvetica Neue", sans-serif;
  --up-font-title:   var(--up-font-body);
  --up-font-body:    "Work Sans", "Helvetica Neue", sans-serif;
  /* The DATA voice (quiet accents, 2026-08-10) — the one sanctioned second
     family. Micro-caps mono for instrument readouts that report machine truth:
     the tally light, the slate strip, film tags, data chips. 10–11px, never
     prose, never a heading, never a sentence. DESIGN.md § Typography has the
     law; the desk-decoration version of this idea was rejected the same day. */
  --up-font-mono: "SF Mono", ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;

  --up-text-headline: 42px;
  --up-text-subhead:  22px;
  --up-text-body:     16px;
  --up-text-caption:  11px;

  /* 300 is the display weight here, and it is deliberate: at 40-52px a light
     grotesque reads as space and air, which is what a cyc is. */
  --up-weight-light:    300;
  --up-weight-regular:  400;
  --up-weight-medium:   500;
  --up-weight-semibold: 600;
  --up-weight-bold:     700;

  /* ---- spacing --------------------------------------------------------- */
  --up-space-xs: 4px;
  --up-space-sm: 8px;
  --up-space-md: 16px;
  --up-space-lg: 24px;
  --up-space-xl: 40px;
  --up-space-2xl: 64px;
}

/* ==========================================================================
   DAY CYC — the same backdrop with the lights up. Warm white above, slate
   settling at the base, the copper key still raking in from frame right.

   This is the theme every CLIENT sees: the portal renders `data-theme="light"`
   unconditionally, because a client page is a daytime letter. So the day grade
   is not the secondary case here, it is the shop window.
   ========================================================================== */
body[data-theme$="light"] {
  color-scheme: light;

  /* THE PAPER CAME UP, 2026-08-10. The day ground was #EDEAE4 — the same value
     as --up-cream, a print-stock beige — and it was the single hardest thing
     about this theme. A dusty ground forces every panel to be a WHITE PLATE
     laid on top of it just to be seen, so a page of work read as a tray of
     slabs rather than as a page. Lifting the ground to a warm near-white
     inverts that: the ground is the paper, panels are barely-lifted regions of
     it, and the delta doing the work drops from ~20 values to ~7.
     --up-cream is deliberately left where it was: it is the STOCK colour used
     by the brand surfaces, not the app's floor, and the two stopped being the
     same thing here. */
  --up-ground: #F7F4EF;
  --up-ink:    #171310;
  --up-cream:  #EDEAE4;
  --up-paper:  #171310;

  --up-accent: #8F4E15;   /* brand copper deepened until it clears on paper —
                             measured 5.47:1 in decisions.md. The night value
                             (#D8853A) is far too light on this ground. */
  --up-due:    #6B4600;
  --up-danger: #A8301F;
  --up-ok:     #186B41;   /* 6.53:1 on the day plate; the night value is 1.63 */

  /* EVERY alias that :root defined as var(...) has to be re-declared here.
     A custom property whose value is `var(--x)` resolves against the value of
     --x AT THE ELEMENT THAT DECLARED IT, so --up-fg: var(--up-paper) declared
     on :root keeps the NIGHT paper even after --up-paper is re-pointed on
     body. Left out, the chrome renders near-white text on a daytime sidebar —
     measured at 1.07:1 — because .content re-declares --up-fg for itself and
     the sidebar, which lives outside .content, never gets the memo. */
  --up-bg:     var(--up-ground);
  --up-fg:     var(--up-paper);
  --up-border: var(--up-line);
  --up-copper:      var(--up-accent);
  --up-accent-warm: var(--up-accent);
  --up-strong-bg:   var(--up-accent);

  --cal-rule:  rgba(23, 19, 16, 0.10);
  /* #4A4139 measured 8.3:1 on the old ground — not a legibility problem, a
     WEIGHT problem: secondary prose that dark competes with the sentence it is
     subordinate to, and .up-caption is the most-used text class in the app.
     Eased to 5.4:1 on the new paper, which is still comfortably over the
     4.5 floor and finally reads as the quieter of two voices. */
  --up-muted:  #665D53;
  /* Near-opaque now, and that is the whole trade of the soft pass: the panel
     is described by its FILL sitting a few values above the paper, so the
     hairline around it can drop to a whisper instead of doing all the work. */
  --up-surface:   rgba(255, 253, 249, 0.88);
  --up-surface-2: rgba(255, 253, 249, 1);
  --up-line:      rgba(23, 19, 16, 0.065);

  --up-strong-fg: #FFFDF9;
  /* Range halved, same as night — see the note at :root. Day white measures
     4.92:1 on the lighter stop, so the Copper Rule still clears. */
  --up-strong-grad: linear-gradient(135deg, #A65C1C, #8C4A12);
  /* Warm ink at a fraction of the night alpha — see the note at :root. */
  --up-strong-lift: rgba(23, 19, 16, 0.13);

  --up-neutral-100: #2E2C28;
  --up-neutral-200: #55524B;
  --up-neutral-300: #6E675D;
  --up-neutral-400: #6E675D;
  --up-neutral-500: #443E37;
  --up-neutral-600: #171310;

  --cyc-wash: linear-gradient(var(--up-ground), var(--up-ground));
  --cyc-horizon: linear-gradient(rgba(0,0,0,0), rgba(0,0,0,0));
  /* #FFFDF9, the brand's own day white, not #FFFFFF. On a warm ground a pure
     white plate is the one cool object in the room and it reads as a hole. */
  --cyc-pool:  linear-gradient(#FFFDF9, #FFFDF9);
  --cyc-spill: 0 1px 2px rgba(23,19,16,0.045);
  --cyc-rim:   rgba(23, 19, 16, 0.075);
  --cyc-scrim: rgba(247, 244, 239, 0.55);
}

/* ==========================================================================
   QUIET — what the pair means now that the whole app is flat.

   Honesty about the change: the loud/quiet distinction used to be atmosphere
   (wash, drift, glow, frost) versus none. The clean pass removed the
   atmosphere everywhere, so most of that delta is simply gone, and the two
   pairs are now much closer than they were. What is LEFT is the part with an
   evidence base behind it rather than a look:

     · no shadow at all — separation by hairline only, so nothing on screen
       implies depth that isn't there
     · no transitions

   That is a smaller difference than before and it is deliberately not a hue
   change: coloured overlays as a reading aid have failed replication for
   forty years, and the supportable guidance (W3C COGA) is about visual noise.
   OPEN QUESTION for Mark: with the app now quiet by default, four theme slots
   may be two more than this needs. Collapsing to light/dark would remove a
   decision, which is this app's own tie-breaker.
   ========================================================================== */
body[data-theme^="adhd"] {
  --cyc-spill: none;
  --cyc-blur:  0px;
}
/* The quiet pair carries no shadow at all, so its hairline is the ONLY thing
   left saying where a panel ends — it stays a step firmer than the loud pair's
   after the soft pass, for the same reason it always was. */
body[data-theme="adhd-dark"] {
  --cyc-pool: linear-gradient(rgba(244,242,238,0.075), rgba(244,242,238,0.075));
  --cyc-rim:  rgba(244, 242, 238, 0.115);
}
body[data-theme="adhd-light"] {
  --cyc-pool: linear-gradient(#FFFDF9, #FFFDF9);
  --cyc-rim:  rgba(23, 19, 16, 0.10);
}
