/*
 * The console's stylesheet.
 *
 * A file in `public/` rather than an import, so that the whole of what this page loads is a short list
 * a person can read. It carries no font, no image and no reference of any kind to anywhere else — the
 * public page's rule, which applies with more force here: a console that fetched a stylesheet from a
 * third party would hand that party the fact that support looked at something, on a timetable.
 *
 * ## It began as the public page's look, and the palette is the app's file
 *
 * The three faces, the fluid steps, the hairline ruling and the tabular numerals below came from
 * `apps/site/src/styles.css`, and are this screen's own since the site's October 2026 redesign gave it
 * faces it serves itself. **The COLOURS are no longer a copy.** They
 * were, and this comment defended it as "the honest trade a second build makes rather than depending
 * on the site's for a colour" — which was the right instinct about the wrong two files. They come from
 * `@tenweeks/palette` now: a package with no dependencies of its own, under this console and the app
 * rather than beside one of them, so nothing here depends on another build either. (The public site
 * left it in its October 2026 redesign and declares its own colours.)
 *
 * **It is reached from `src/main.ts` and not from inside this file, and that asymmetry is deliberate.**
 * This file is served exactly as it is written; nothing rewrites it, so an imported stylesheet named
 * here would be a real request a browser makes — the one thing this surface refuses hardest, and
 * `test/design.test.ts` refuses it over these bytes in the three spellings a request takes. Those three
 * are deliberately not written out in this comment, for the reason the public page's stylesheet gives
 * about its own: a mention in prose reads to a substring check exactly like the real thing, and the fix
 * for that is never to relax the check. The other two surfaces put their stylesheets through a bundler
 * that resolves such a reference off disk at build time and inlines it, so they name the palette in
 * their CSS. Here the bundler is handed it directly and emits it beside the page — a file from this
 * origin, in the document's head, which the locked screen is painted from before anybody signs in.
 *
 * ## What did NOT cross, and ADR-0025 is why
 *
 * The site's identity is a lab notebook, and its furniture there includes a highlighter behind the
 * one door, a drawn ornament in the corner of the hero, a stamp with a shadow under it, an ambient
 * wash over the top band and a drawn dash above every heading. **None of it is here.** ADR-0025 says
 * this surface is deliberately austere and is an operator tool rather than a marketing surface, so
 * what crosses is the TYPE, the PALETTE and the SPACING — which is what makes two screens the same
 * product — and the ornament stays on the page that is selling something. Where the port and the
 * ADR disagreed, the ADR won and the ornament was dropped.
 *
 * One consequence is worth stating because it is what makes the checking below complete: there is
 * no gradient and no translucent layer anywhere in this file, so every ink is drawn on a flat token
 * and there is no composite for a check to miss.
 *
 * ## Nothing is dimmed
 *
 * There is no `opacity` in this file and there must not be, in its strongest form: a dimmed colour
 * is one nothing ever checked, and the way to make a label quieter here is a colour that has been.
 * Every pair is asserted at WCAG AA in both rooms by `packages/palette/test/contrast.test.ts`, which
 * reads the palette out of the package and this screen's own two levers out of these bytes — and
 * measures the other two surfaces in the same pass, because three suites asking one question of three
 * copies could agree and all be wrong.
 *
 * ## The three panel weights, and the correction to how they were drawn
 *
 * `destroy` is the set of levers that cannot be undone from this console, and an operator reaching
 * for one under pressure should be able to tell from across the desk which sort of thing they are
 * about to press. The three now differ in the THICKNESS of the margin rule as well as its colour,
 * which is the correction: the grant brown and the destroy red are 1.29:1 apart in the light palette
 * and 1.14:1 apart in the dark one, so to anybody who cannot tell those two hues apart the old rule
 * said exactly the same thing on both.
 */

:root {
  /* --- the two weights this screen adds to the palette ----------------------
   *
   * The palette itself is `@tenweeks/palette`, imported by `src/main.ts` — the paper, the slips, the
   * inks, the two weights of rule and the pencil, in both rooms, with the argument for each value
   * beside it there. What is left here is the two colours that are this surface's alone, for actions
   * that carry a cost. Rules only — neither is ever a text colour — and both clear 3:1 on the paper
   * and on a slip.
   *
   * They are 1.29:1 apart in light and 1.14:1 in dark, which is to say the same grey to anybody who
   * cannot separate those hues, so the weight and not the colour carries the signal. WCAG 1.4.1.
   *
   * **This file ships verbatim** — it is served from `public/`, so Vite copies it uncompressed and
   * un-stripped, and the locked screen loads it before anybody has signed in. `render.ts` refuses to
   * draw panels there precisely so the page is not a map of the surface; a comment that enumerates
   * what the levers DO would hand the same map to the same reader in prose. Design reasoning belongs
   * here. What each control is for does not.
   *
   * **The light room is the base here and the dark one is the query, which is the opposite way round
   * from the palette, and it costs nothing.** A token a query does not restate keeps the base value,
   * so the two orders describe the same two rooms — and these two tokens are in neither the palette's
   * base nor its query, so no declaration below is ever in a race with one of its.
   */
  --grant: #7a4b00;
  --destroy: #8a1420;

  /* --- type ---------------------------------------------------------------- */
  /*
   * Three faces, all of them the reader's own. Nothing is fetched, so the personality comes from
   * scale, weight, spacing and tabular numerals — the same discipline a notebook works under.
   */
  --font-display: ui-sans-serif, system-ui, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
  --font-body: system-ui, -apple-system, 'Segoe UI', Roboto, sans-serif;
  /* The recorded marginalia: labels, dates, counts, and everything an operator types. */
  --font-mono: ui-monospace, 'Cascadia Mono', 'Segoe UI Mono', Menlo, Consolas, monospace;

  /*
   * Four steps of the site's scale — the four this screen uses. Each runs from its small-screen size
   * at a 320px viewport to its large-screen size at 1600px and is flat outside that. Both ends are
   * `rem` and the middle term carries a `rem` component, so a reader who has raised their browser's
   * text size still gets bigger text.
   */
  --step--1: clamp(0.875rem, 0.859rem + 0.078vw, 0.9375rem);
  --step-0: clamp(1.0625rem, 1.047rem + 0.078vw, 1.125rem);
  --step-1: clamp(1.125rem, 1.094rem + 0.156vw, 1.25rem);
  --step-2: clamp(1.3125rem, 1.234rem + 0.39vw, 1.625rem);

  /* --- space and width ----------------------------------------------------- */
  --tap: 44px;
  /* Roughly sixty characters at the reading size, which is where prose stops being tiring. */
  --measure: 36rem;
  /*
   * The column, and it is deliberately not the site's `--page`. That number is 90rem because the
   * page it caps is a run of full-bleed bands; this screen is one stack of panels, and 46rem is the
   * width the console already had.
   */
  --page: 46rem;
  /*
   * Also not the site's, and for the same reason as `--page` above it — stated here because an
   * undocumented near-match is the one a later reader "corrects". The site opens to 3.5rem because
   * its bands are full-bleed and need air at the edge; a 46rem column of panels does not, and a
   * gutter that wide on a phone would take a third of the screen from a 64-character value.
   */
  --gutter: clamp(1rem, 0.5rem + 2.5vw, 2rem);
  --pad: clamp(1rem, 0.75rem + 1.25vw, 1.5rem);

  color-scheme: light dark;
}

/*
 * The dark room's two weights, and nothing else: the palette's dark values are in the package, where
 * a designed counterpart with hand-picked values is argued for rather than an inversion, because
 * "read on anything" includes a desk at 8am and one at 11pm.
 *
 * Both are lifted here for the same reason every ink is: a brown and a red chosen against paper are
 * unreadable on a near-black ground.
 */
@media (prefers-color-scheme: dark) {
  :root {
    --grant: #e0a95a;
    --destroy: #f08a95;
  }
}

* {
  box-sizing: border-box;
}

body {
  margin: 0;
  padding: env(safe-area-inset-top) env(safe-area-inset-right) env(safe-area-inset-bottom)
    env(safe-area-inset-left);
  background: var(--ground);
  color: var(--ink);
  font-family: var(--font-body);
  font-size: var(--step-0);
  line-height: 1.6;
  -webkit-text-size-adjust: 100%;
}

/*
 * A 64-character hash is one word, and one unbreakable word is the only thing on this screen that
 * can push a 375px layout sideways. Broken rather than allowed to overflow.
 */
h1,
h2,
h3,
p,
li {
  overflow-wrap: break-word;
}

p {
  margin: 0 0 0.6rem;
  max-width: var(--measure);
}

/*
 * The ring sets no `border-radius` of its own, and there is nothing on this screen for it to
 * restate: every shape below is square. Every current engine draws an outline following the
 * element's own radius anyway.
 */
:focus-visible {
  outline: 3px solid var(--focus);
  outline-offset: 3px;
}

#console {
  width: min(100%, var(--page));
  margin: 0 auto;
  padding: var(--gutter);
}

header {
  margin: 0 0 1.25rem;
}

h1 {
  margin: 0 0 0.35rem;
  font-family: var(--font-display);
  font-size: var(--step-2);
  font-weight: 800;
  line-height: 1.15;
  letter-spacing: -0.02em;
}

h2 {
  margin: 0 0 0.35rem;
  font-family: var(--font-display);
  font-size: var(--step-1);
  font-weight: 700;
  line-height: 1.25;
  letter-spacing: -0.015em;
}

h3 {
  margin: 0 0 0.25rem;
  font-family: var(--font-display);
  font-size: var(--step-0);
  font-weight: 700;
  line-height: 1.3;
}

.lead {
  color: var(--quiet);
}

/*
 * Marginalia: a note written beside a record rather than in it, and typed rather than set. The
 * colour is a checked token and not a dimming — see the file comment.
 */
.note,
.hint {
  font-family: var(--font-mono);
  font-size: var(--step--1);
  line-height: 1.5;
  color: var(--quiet);
}

/*
 * A slip: hairline ruled, on paper of its own, with a rule down the margin. Every top-level region
 * of both screens is one of these — the panels, the sign-in, the macros, the boundary — so the
 * screen reads as a stack of records rather than as a page of cards.
 */
section {
  margin: 0 0 1rem;
  padding: var(--pad);
  border: 1px solid var(--line);
  border-left: 3px solid var(--edge);
  background: var(--surface);
}

/*
 * The two weights that cost something. The colour says WHICH of the two it is; the thickness says
 * that it is one of them at all, and the thickness is what a reader who cannot tell the two hues
 * apart is left with.
 */
.panel-grant {
  border-left-color: var(--grant);
}

.panel-destroy {
  border-left-width: 6px;
  border-left-color: var(--destroy);
}

.macro {
  margin-top: 0.85rem;
}

.support-script {
  margin-top: 1rem;
  padding-top: 0.85rem;
  border-top: 1px solid var(--line);
}

.support-script ol {
  padding-left: 1.4rem;
}

.support-rule,
.support-reply,
.support-references,
.support-escalation {
  font-size: var(--step--1);
  line-height: 1.55;
}

.support-reply,
.support-escalation {
  padding-left: 0.85rem;
  border-left: 3px solid var(--cool);
}

.support-escalation {
  border-left-color: var(--destroy);
}

.field {
  margin: 0 0 0.85rem;
}

label {
  display: block;
  margin: 0 0 0.25rem;
  font-family: var(--font-mono);
  font-size: var(--step--1);
  font-weight: 600;
  line-height: 1.4;
}

/*
 * The box a record is typed into. Monospaced and tabular for the job rather than for the look: the
 * values here are long and opaque, and the task is comparing them a character at a time.
 */
input,
textarea {
  width: 100%;
  padding: 0.5rem 0.55rem;
  border: 1px solid var(--edge);
  background: var(--surface-2);
  color: var(--ink);
  font-family: var(--font-mono);
  font-size: var(--step-0);
  font-variant-numeric: tabular-nums;
  line-height: 1.5;
}

.hint {
  margin: 0.25rem 0 0;
}

/*
 * The one control shape, and its boundary is `currentColor` — so the outline of a thing you can
 * press cannot drift away from the ink inside it. It is at least a finger tall, it moves a tenth of
 * a rem under the press, and it moves instantly for anybody who has asked for less movement.
 */
button {
  min-height: var(--tap);
  padding: 0.55rem 1.1rem;
  border: 2px solid currentColor;
  background: transparent;
  color: var(--ink);
  font-family: var(--font-body);
  font-size: var(--step-0);
  font-weight: 600;
  line-height: 1.4;
  cursor: pointer;
  transition: transform 140ms ease;
}

/*
 * `:active` and NOT `:hover`, which is the correction a checker forced and the reason this rule
 * carries a comment at all.
 *
 * As written it moved on approach rather than on press — so an operator's pointer merely crossing a
 * destroy lever made it shift, a tap on a touch device left it displaced because `:hover` sticks
 * there, and a keyboard activation got nothing at all. The comment above claimed a press animation
 * this file did not contain, and the suite's own case was named for one it never asserted.
 *
 * ADR-0025 would not have bought motion for its own sake. What it buys here is confirmation on the
 * one surface where the levers cannot be undone: pressing a thing that spends or destroys should
 * feel like pressing it, and should feel like nothing at all when merely passed over.
 */
button:active {
  transform: translate(0.1rem, 0.1rem);
}

/*
 * A ruled entry, and it STACKS: what the value is called on one line and the value itself on the
 * next, because a value here can be a 64-character hash and a phone is 375px wide. It becomes a
 * ruled row at 48rem, where there is finally room for two columns of anything.
 */
.line {
  display: grid;
  gap: 0.1rem;
  padding: 0.45rem 0;
  border-bottom: 1px solid var(--line);
}

.label {
  font-family: var(--font-mono);
  font-size: var(--step--1);
  line-height: 1.5;
  color: var(--quiet);
}

/* A recorded figure, with its digits lined up: a column of figures whose digits do not line up is
   a table that has stopped being one. */
.value {
  font-family: var(--font-mono);
  font-size: var(--step-0);
  font-variant-numeric: tabular-nums;
  line-height: 1.5;
  /* The 64-character hash again, and `anywhere` rather than `break-word` because what pushes a
     layout sideways here is the cell's own minimum width rather than the line it is on. */
  overflow-wrap: anywhere;
  color: var(--cool);
}

.result {
  margin-top: 0.85rem;
}

.answer-lead {
  font-weight: 600;
}

.working {
  font-family: var(--font-mono);
  font-size: var(--step--1);
  color: var(--quiet);
}

/*
 * A refusal is a correction, and a correction in a notebook is written in the pencil and struck
 * against a rule in the margin rather than tidied away. `.held` is the one a second press of a panel
 * holding codes gets, and it is the same thing said in the same place.
 */
.refusal,
.held {
  margin: 0.5rem 0 0;
  padding-left: 0.85rem;
  border-left: 3px solid var(--accent-ink);
  font-weight: 600;
  color: var(--accent-ink);
}

/*
 * The same margin shape in graphite: something recorded rather than something refused. The two
 * written-down conversations and the boundary rule are quotable text, so they are typed.
 */
.notice,
.macro-body,
.rule {
  padding-left: 0.85rem;
  border-left: 3px solid var(--cool);
  font-family: var(--font-mono);
  font-size: var(--step--1);
  line-height: 1.55;
}

/*
 * A slip within a slip — its own paper, ruled, with a rule down its margin — because a warning and
 * the thing it warns about have to be read as one. A warning placed below is one read after the
 * panel has already been closed.
 */
/*
 * **Its margin rule is `--destroy` and its weight is the destroy weight**, restored after a checker
 * noticed the port had quietly turned this down — from a 2px `--destroy` boundary to a 1px `--edge`
 * one with a pencil margin. Both pass AA, so nothing failed; what was lost was salience, on the one
 * region in this console whose contents cannot be asked for again.
 *
 * Re-encoding how loud a warning is is not typography, palette or spacing, and the port did not have
 * licence for it. The rest of the slip-within-a-slip treatment is the port's and stays.
 */
.once {
  margin-top: 0.85rem;
  padding: 0.85rem;
  border: 1px solid var(--edge);
  border-left: 6px solid var(--destroy);
  background: var(--surface-2);
}

.once-warning {
  margin: 0 0 0.6rem;
  font-weight: 700;
  color: var(--accent-ink);
}

.codes {
  list-style: none;
  padding: 0;
  margin: 0 0 0.85rem;
}

.codes code {
  font-family: var(--font-mono);
  font-size: var(--step-1);
  font-variant-numeric: tabular-nums;
  line-height: 1.9;
  letter-spacing: 0.06em;
  user-select: all;
}

/* ---------------------------------------------------------------------------
   Tablet — 48rem. The one width on this screen with room for a label and its
   value on the same line, and the only layout here that has a second column.
   --------------------------------------------------------------------------- */

@media (min-width: 48rem) {
  .line {
    display: flex;
    justify-content: space-between;
    align-items: baseline;
    gap: 0 1.5rem;
  }

  .label,
  .value {
    min-width: 0;
  }

  .value {
    text-align: right;
  }
}

/* ---------------------------------------------------------------------------
   Motion, for anybody who has asked for less of it. There is one transition in
   this file — a control answering a press — and this is what switches it off.
   --------------------------------------------------------------------------- */

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