/* ============================================================
   Termdeck — Control tokens (buttons and button-shaped things)

   The app had grown 56 distinct clickable controls across 18 heights,
   10 radii, 9 font sizes and 21 paddings, because every surface that
   needed a button wrote one. This file is the single scale they all
   read from; public/style.css's BUTTON SYSTEM section is the one
   recipe that consumes it.

   Two kinds of token live here and they do different jobs:

     --btn-h-* / --btn-px-* / --btn-radius-*   the SCALE. Fixed rungs.
                                               A component picks one.
     --btn-bg / --btn-fg / --btn-bd (+states)  the SLOTS. A variant
                                               re-declares these and
                                               the recipe repaints; no
                                               component re-states
                                               `background` itself.

   Adding a variant means setting slots, never writing geometry. That
   is the whole point — see DESIGN.md § Components › Buttons.
   ============================================================ */

:root {
  /* --- Scale: height ------------------------------------------
     Four rungs. Before adding a fifth, answer which of these it is
     not (the Five-Rungs Rule, applied to geometry). The old ladder
     ran 16/18/22/24/26/27/28/29/30/32/33/34/38/43 — fourteen steps
     inside 27 pixels, not one of them a difference a user can see. */
  --btn-h-xs: 24px;   /* a chip inside a dense row */
  --btn-h-sm: 28px;   /* dense chrome: tabstrip, toolbars, composer rail */
  --btn-h-md: 32px;   /* the default control */
  --btn-h-lg: 36px;   /* a prominent action, a dialog footer */
  --btn-h-touch: 44px; /* the coarse-pointer floor — WCAG 2.2 SC 2.5.8 */

  /* --- Scale: side padding -----------------------------------
     Paired with the height rung above it. */
  --btn-px-xs: 8px;
  --btn-px-sm: 10px;
  --btn-px-md: 12px;
  --btn-px-lg: 20px;  /* was 15 — the 20px rung, so a prominent action has room */
  --btn-gap: 6px;     /* icon → label */

  /* --- Scale: shape ------------------------------------------
     One family (the One-Family-Per-Surface Rule). 6px is the control
     radius, because it is the one Linear draws on a button and on an
     input. It was 4px, tightened on the argument that at 6px a 28px
     chip reads slightly upholstered; the reference disagrees, and on
     a shape swap the reference wins the same way it won the palette.
     Pill is still for things that are pills. */
  --btn-radius: var(--radius-sm);
  --btn-radius-xs: var(--radius-2xs);
  --btn-radius-pill: var(--radius-pill);

  /* --- Scale: type -------------------------------------------
     Geist, not Geist Mono. A button label is an instruction, not a
     value a developer verifies, so it is not on the mono spine;
     mono stays on the chips that show a host, a path or a count.
     Sans also sets ~8% narrower, which is what buys long labels
     ("Allow for this session") their room on a 390px screen. */
  --btn-family: var(--font-sans);
  --btn-font-sm: var(--ui-meta);      /* 12 — xs/sm rungs */
  --btn-font: var(--ui-control);      /* 13 — md/lg rungs */
  --btn-weight: var(--weight-medium); /* 500 */
  --btn-weight-strong: var(--weight-semibold); /* 600 — filled primary */
  --btn-leading: var(--leading-snug);
  --btn-tracking: var(--tracking-normal);
  --btn-icon: 15px;

  /* --- Motion + disabled -------------------------------------- */
  --btn-transition:
    background-color var(--duration-fast) var(--ease-standard),
    border-color var(--duration-fast) var(--ease-standard),
    color var(--duration-fast) var(--ease-standard);
  --btn-disabled-opacity: 0.45;

  /* --- Slots: the default (secondary) variant ------------------
     Every button paints from these seven. A variant swaps them and
     nothing else. Values resolve to the workspace palette, so a
     re-skin moves the buttons with it.

     A BUTTON IS IDENTIFIED BY ITS FILL, NOT BY AN OUTLINE. --btn-bd
     used to be --workspace-control-border, which put a 3.72:1 grey
     rectangle around every secondary and quiet control in the app —
     56 of them, and the app read as a grid of boxes. The border does
     not simply come off, though: for a fill alone to carry the 3:1 of
     WCAG 2.2 SC 1.4.11 against --workspace-bg it would have to be
     about #5d5d5d, a light-grey key on a near-black console. So the
     border's JOB moves rather than disappearing — onto the pairing
     DESIGN.md § Elevation already assigns to a resting control,
     Level 2: a lightness step plus light catching the top edge. The
     hairline stays underneath as the grouping edge it always was. */
  --btn-bg: var(--workspace-surface-raised);
  --btn-fg: var(--workspace-text);
  --btn-bd: var(--workspace-border);
  --btn-bg-hover: var(--workspace-surface-hover);
  --btn-fg-hover: var(--workspace-text);
  --btn-bd-hover: var(--workspace-border-strong);
  --btn-bg-active: var(--workspace-surface);

  /* --- Slot: the bezel ----------------------------------------
     The seventh slot, and the one that replaced the outline. It is
     --workspace-edge-highlight, the same inset top-light + bottom
     gather every resting card and the composer shell already wear,
     so a button reads as the same kind of object they do.

     Two things about the OFF value. It is `0 0 #0000` and not `none`
     because the focus rule composes the ring and the bezel in one
     box-shadow list, and `box-shadow: <ring>, none` is invalid — the
     whole declaration would drop and the control would lose its focus
     ring, which is the one failure mode this system must not have.
     And the off value is a token rather than a literal so a variant
     turns the bezel off by naming it, not by knowing the incantation.

     --btn-bezel-lit is the filled rung: a fill catches more light than
     a dark surface does, so primary and Stop take a 22% top edge where
     a secondary takes 10%. That value is not new — it is the bezel
     Send already wore by hand in the composer tray. */
  --btn-bezel: var(--workspace-edge-highlight);
  --btn-bezel-none: 0 0 #0000;
  --btn-bezel-lit: inset 0 1px 0 rgba(255, 255, 255, 0.22), inset 0 -6px 8px -6px rgba(0, 0, 0, 0.45);

  /* --- Selected/on state, shared by toggles and segmented sets --
     White at low alpha: "this one is chosen" is identity, and the
     palette reserves white for identity. Not a second fill colour —
     green stays the one "go". The tint is the whole signal: --btn-on-bd
     used to add a 32%-white outline on top of it, which said the same
     thing twice and said it in the shape the rest of the system just
     stopped using. */
  --btn-on-bg: rgba(var(--workspace-accent-rgb), 0.10);
  --btn-on-fg: var(--workspace-accent);
  --btn-on-bd: transparent;

  /* --- Badges -------------------------------------------------
     A badge is a button-shaped thing that is not clickable, which is
     why it lives here and reads from the same shape scale. The app
     grew twelve of them (.nav-badge, .ctx-badge, .host-badge,
     .status-badge, .perm-ask-badge, .term-queue-badge, …), each with
     its own geometry; these are the rungs they should collapse onto.

     Two grounds, borrowed from the filled/soft pair that reads well on
     a marketing surface and reads even better on a dark one:

       FILLED  solid semantic fill, near-black text. Loud. For a count
               or a state someone has to act on.
       SOFT    tinted ground + coloured text + a tinted hairline. Quiet.
               For a label that is information, not an alarm.

     Soft is the default. A filled badge is a claim on attention and
     the console spends those sparingly — same discipline as the one
     filled green action per view. */
  --badge-h: 18px;
  --badge-px: var(--space-2);        /* 8 */
  --badge-px-tight: var(--space-1);  /* 4 — inside a dense row */
  --badge-radius: var(--radius-xs);   /* 4 - linear's badge corner (was 2) */
  --badge-font: var(--ui-label);     /* 12 — moved with the ladder (was 11) */
  --badge-weight: var(--weight-medium);
  --badge-tracking: var(--tracking-wide);

  /* Info — the new semantic. Filled pairs #3d86f7 with near-black at
     5.6:1; soft puts the same blue on its own 14% tint. */
  --badge-info-bg: var(--workspace-info);
  --badge-info-fg: var(--workspace-info-fg);
  --badge-info-soft-bg: var(--workspace-info-soft);
  --badge-info-soft-fg: var(--workspace-info-text);
  --badge-info-soft-bd: var(--workspace-info-border);
}
