/* ═══════════════════════════════════════════════════════════════════════════════════════════════
   nous.css — THE ONE STYLESHEET (2026-09-13, C1442 — Kamran: "go for 1 — own stylesheet, nous.css")

   WHY IT EXISTS. 06-registers/UI-AUDIT.md measured 23 lister pages live: 16 different page
   widths, 7 side margins, 6 body-text sizes, 26 distinct text sizes, 9 button shapes, 5 colour
   families — because every page carried its own private copy of the styles. This file is the
   copy. It holds the TOKENS (the numbers) and the BASE PIECES every page uses. A page that
   adopts it deletes its private copy and keeps only what is specific to that page.

   HOW IT IS LOADED. _page() in app-server.js injects <link rel="stylesheet" href="/nous.css?v=…">
   at the top of <head> on every non-bare page — BEFORE the page's own <style>, so where the two
   disagree the page still wins. Nothing here fires until a page opts in.

   HOW A PAGE OPTS IN. <body class="nous">. Every rule below is scoped to .nous — a page without
   the class is untouched, byte for byte. Add "wide" for table/log pages: <body class="nous wide">.
   The selectors are written :where(.nous) … so they carry the specificity of a bare element:
   a page's own .foo rule always beats them without !important.

   THE NUMBERS. From UI-AUDIT.md §2 — where pages already agreed, that value; elsewhere the most
   common one. Kamran's to change; change them HERE and every adopted page follows.

   CLASS NAMES are the ones the pages already use (.wrap .stats .stat .k .v .bar .chip .meta
   .empty button.ghost …), so migrating a page is deleting lines, not renaming things.
   ═══════════════════════════════════════════════════════════════════════════════════════════════ */

/* ── 1. TOKENS ─────────────────────────────────────────────────────────────────────────────── */
.nous{
  /* colour — the navy family exactly as 16 of 23 pages already had it */
  --bg:#0b1220;        /* page ground */
  --soft:#0e1626;      /* inputs, hover rows, quiet fills */
  --card:#111a2b;      /* cards, tiles, sticky table header */
  --line:#1e2a3f;      /* every border and divider */
  --ink:#e6edf7;       /* text */
  --mut:#8fa0b8;       /* secondary text, labels */
  --blue:#8fb3ff;      /* links, ghost buttons */
  --accent:#4f46e5;    /* the one action colour */
  --ok:#4ade80;  --warn:#fbbf24;  --miss:#f87171;  --bad:#f87171;
  --warn-bg:#1a1405; --warn-line:#7c5e12;
  --ok-bg:#0d1b12;   --ok-line:#1d3a2a;
  --bad-bg:#1c0f12;  --bad-line:#5a1f28;

  /* layout — one 8-px grid */
  --frame:1200px;      /* normal page frame; .wide switches to --frame-wide */
  --frame-wide:1800px; /* log / table pages */
  --gutter:20px;       /* side margin at every width */
  --gap:16px;          /* between siblings */
  --pad:16px;          /* inside a card */
  --r-card:12px;  --r-ctl:8px;  --r-chip:999px;

  /* type ladder — 7 rungs, nothing below 11 */
  --t-h1:22px;  --t-h2:16px;  --t-body:14px;  --t-cell:13px;  --t-meta:12px;  --t-label:11px;
  --font:-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,Helvetica,Arial,sans-serif;
  --mono:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;

  /* controls */
  --ctl-h:36px;  --ctl-h-primary:44px;
}

/* Light theme (C1466 — the studio pages that carry a 🌓 toggle set data-theme=light on <html>;
   the P&L rail is the first shared piece to live on one). Same names, light values — mirrors
   pnl.html's own light palette so the two halves of that page agree. */
:root[data-theme="light"] .nous{
  --bg:#ffffff; --soft:#f7f8fa; --card:#f7f8fa; --line:#e5e7eb; --ink:#191919; --mut:#6b7280;
  --blue:#2563eb; --accent:#4f46e5; --ok:#15803d; --warn:#b45309; --miss:#b91c1c; --bad:#b91c1c;
  --warn-bg:#fff7e6; --warn-line:#f2d28a; --ok-bg:#ecfdf3; --ok-line:#a7e3bf; --bad-bg:#fef2f2; --bad-line:#f5b5b5;
}

/* ── 2. GROUND + FRAME ─────────────────────────────────────────────────────────────────────── */
:where(.nous){margin:0;background:var(--bg);color:var(--ink);font-family:var(--font);font-size:var(--t-body);line-height:1.5;-webkit-font-smoothing:antialiased}
:where(.nous) *,:where(.nous) *::before,:where(.nous) *::after{box-sizing:border-box}
:where(.nous) .wrap{max-width:var(--frame);margin:0 auto;padding:20px var(--gutter) 60px}
:where(.nous.wide) .wrap{max-width:var(--frame-wide)}

/* ── 3. TYPE ───────────────────────────────────────────────────────────────────────────────── */
:where(.nous) h1{font-size:var(--t-h1);font-weight:700;line-height:1.2;margin:0 0 4px;letter-spacing:-.01em}
:where(.nous) h2{font-size:var(--t-h2);font-weight:700;line-height:1.3;margin:0 0 10px}
:where(.nous) h3{font-size:var(--t-body);font-weight:700;margin:0 0 8px}
:where(.nous) p{margin:0 0 10px}
:where(.nous) a{color:var(--blue)}
:where(.nous) .sum{color:var(--mut);font-size:var(--t-body);margin:0 0 var(--gap)}
:where(.nous) .sum b{color:var(--ink)}
:where(.nous) .meta{color:var(--mut);font-size:var(--t-meta);margin-top:2px}
:where(.nous) .hint{color:var(--mut);font-size:var(--t-meta)}
:where(.nous) .label,:where(.nous) .eyebrow{color:var(--mut);font-size:var(--t-label);text-transform:uppercase;letter-spacing:.06em;font-weight:700}
:where(.nous) .mono{font-family:var(--mono)}
:where(.nous) .num{font-variant-numeric:tabular-nums}

/* ── 4. CARDS + STAT TILES ─────────────────────────────────────────────────────────────────── */
:where(.nous) .card{background:var(--card);border:1px solid var(--line);border-radius:var(--r-card);padding:var(--pad)}
:where(.nous) .card + .card{margin-top:var(--gap)}
:where(.nous) .stats{display:flex;flex-wrap:wrap;gap:10px;margin:6px 0 var(--gap)}
:where(.nous) .stat{background:var(--card);border:1px solid var(--line);border-radius:var(--r-card);padding:9px 15px;min-width:120px}
:where(.nous) .stat .k{color:var(--mut);font-size:var(--t-label);text-transform:uppercase;letter-spacing:.05em;font-weight:700}
:where(.nous) .stat .v{color:var(--ink);font-size:19px;font-weight:800;margin-top:2px;line-height:1.1;font-variant-numeric:tabular-nums}
:where(.nous) .stat.sync .v{font-size:var(--t-cell);font-weight:600;color:var(--blue)}
:where(.nous) .stat.warn{border-color:var(--warn-line);background:var(--warn-bg)}
:where(.nous) .stat.bad{border-color:var(--bad-line);background:var(--bad-bg)}

/* ── 5. BAR (search / filter row) ──────────────────────────────────────────────────────────── */
:where(.nous) .bar{display:flex;flex-wrap:wrap;gap:8px;align-items:center;margin-bottom:14px}
:where(.nous) .bar > input,:where(.nous) .bar > select{height:var(--ctl-h)}
:where(.nous) .bar .grow{flex:1;min-width:220px}

/* ── 6. CONTROLS — one height, one corner, and they line up in a row. `.btn` is the same thing on
      an <a> (a link that looks like a button) — Scan/Captures uses both. ─────────────────────── */
:where(.nous) input,:where(.nous) select,:where(.nous) textarea{
  background:var(--soft);border:1px solid var(--line);color:var(--ink);border-radius:var(--r-ctl);
  padding:8px 11px;font-size:var(--t-body);font-family:var(--font);line-height:1.3;min-height:var(--ctl-h)}
:where(.nous) textarea{min-height:88px;resize:vertical}
:where(.nous) input:focus,:where(.nous) select:focus,:where(.nous) textarea:focus,:where(.nous) button:focus-visible{outline:2px solid var(--blue);outline-offset:1px}
:where(.nous) input:disabled,:where(.nous) select:disabled,:where(.nous) textarea:disabled{opacity:.55;cursor:not-allowed}
:where(.nous) input::placeholder{color:var(--mut);opacity:.8}
:where(.nous) button,:where(.nous) .btn{
  border:1px solid var(--accent);background:var(--accent);color:#fff;border-radius:var(--r-ctl);
  padding:0 14px;min-height:var(--ctl-h);font-size:var(--t-body);font-weight:600;font-family:var(--font);
  cursor:pointer;display:inline-flex;align-items:center;gap:6px;line-height:1;white-space:nowrap}
:where(.nous) button:hover,:where(.nous) .btn:hover{filter:brightness(1.08)}
:where(.nous) button:disabled,:where(.nous) .btn:disabled{opacity:.5;cursor:not-allowed;filter:none}
:where(.nous) button.ghost,:where(.nous) .btn.ghost{background:transparent;color:var(--blue);border-color:var(--line);font-weight:500}
:where(.nous) button.ghost:hover,:where(.nous) .btn.ghost:hover{border-color:var(--blue);filter:none}
:where(.nous) button.primary,:where(.nous) .btn.primary{min-height:var(--ctl-h-primary);padding:0 18px;font-size:15px}
:where(.nous) button.danger,:where(.nous) .btn.danger{background:transparent;color:var(--bad);border-color:var(--bad-line)}
:where(.nous) button.small,:where(.nous) .btn.small{min-height:28px;padding:0 10px;font-size:var(--t-meta)}
:where(.nous) a.btn{text-decoration:none}
:where(.nous) label{display:block;color:var(--mut);font-size:var(--t-meta);margin:0 0 4px}
:where(.nous) .field{display:grid;gap:4px;margin-bottom:12px}

/* ── 7. TABLE ──────────────────────────────────────────────────────────────────────────────── */
:where(.nous) table{width:100%;border-collapse:collapse}
:where(.nous) th{text-align:left;color:var(--mut);font-size:var(--t-label);text-transform:uppercase;letter-spacing:.05em;font-weight:700;
  padding:8px 10px;border-bottom:1px solid var(--line);position:sticky;top:0;background:var(--bg);z-index:1;white-space:nowrap}
:where(.nous) td{padding:10px;border-bottom:1px solid var(--line);vertical-align:top;font-size:var(--t-cell)}
:where(.nous) tr:hover td{background:var(--soft)}
:where(.nous) td.num,:where(.nous) th.num{text-align:right;font-variant-numeric:tabular-nums}
:where(.nous) .scroll{overflow-x:auto}

/* ── 8. CHIPS + STATUS ─────────────────────────────────────────────────────────────────────── */
:where(.nous) .chip{display:inline-block;background:var(--soft);border:1px solid var(--line);color:var(--mut);
  border-radius:var(--r-chip);padding:2px 9px;font-size:var(--t-meta);line-height:1.4;white-space:nowrap}
:where(.nous) .chip.ok{color:var(--ok);border-color:var(--ok-line);background:var(--ok-bg)}
:where(.nous) .chip.warn{color:var(--warn);border-color:var(--warn-line);background:var(--warn-bg)}
:where(.nous) .chip.bad,:where(.nous) .chip.miss{color:var(--bad);border-color:var(--bad-line);background:var(--bad-bg)}
:where(.nous) .chip.mono{font-family:var(--mono);letter-spacing:.03em}
:where(.nous) .ok{color:var(--ok)}  :where(.nous) .warn{color:var(--warn)}  :where(.nous) .bad,:where(.nous) .miss{color:var(--bad)}

/* ── 9. MESSAGES + EMPTY STATES ────────────────────────────────────────────────────────────── */
:where(.nous) .msg{border:1px solid var(--line);background:var(--card);border-radius:var(--r-ctl);padding:10px 12px;font-size:var(--t-cell);margin:8px 0}
:where(.nous) .msg.ok{border-color:var(--ok-line);background:var(--ok-bg);color:var(--ok)}
:where(.nous) .msg.warn{border-color:var(--warn-line);background:var(--warn-bg);color:var(--warn)}
:where(.nous) .msg.err,:where(.nous) .msg.bad{border-color:var(--bad-line);background:var(--bad-bg);color:var(--bad)}
:where(.nous) .empty{color:var(--mut);padding:24px 8px}
:where(.nous) .note{color:var(--mut);font-size:var(--t-meta);margin-top:14px;border-top:1px solid var(--line);padding-top:10px}
:where(.nous) .more{display:block;margin:var(--gap) auto 0}

/* ── 10. TOGGLE SWITCH (the eBay-style "Allow offers" switch on Revise) ────────────────────── */
:where(.nous) .switch{position:relative;display:inline-block;width:38px;height:22px;flex:none}
:where(.nous) .switch input{opacity:0;width:0;height:0;min-height:0;position:absolute}
:where(.nous) .switch .knob{position:absolute;inset:0;background:var(--line);border-radius:999px;transition:background .15s;cursor:pointer}
:where(.nous) .switch .knob::after{content:"";position:absolute;top:3px;left:3px;width:16px;height:16px;border-radius:50%;background:#fff;transition:transform .15s}
:where(.nous) .switch input:checked + .knob{background:var(--accent)}
:where(.nous) .switch input:checked + .knob::after{transform:translateX(16px)}
:where(.nous) .switch input:focus-visible + .knob{outline:2px solid var(--blue);outline-offset:2px}

/* ── 10b. FILTER RAIL (C1465/C1468 — the eBay-style left-hand filters; drawn by nous-rail.js) ──
   ONE FRAME (Kamran 2026-09-13: "filter frame is not aligned or bonded with the order frame"):
   .layout is a single card; the rail is its left column (280 px, divider on its right, sticky as
   the page scrolls) and .main its right column, so the two share one top edge, one border and
   one background. Section headings are <details>/<summary> so each folds like eBay's; the active
   filters sit at the top as chips, each one removable, with "Clear all" first. */
:where(.nous) .layout{display:flex;align-items:stretch;gap:0;background:var(--card);border:1px solid var(--line);border-radius:var(--r-card);overflow:clip}
:where(.nous) .layout > .main{flex:1 1 0;min-width:0;border-left:1px solid var(--line)}
:where(.nous) .layout .card{border:0;border-radius:0;background:transparent}   /* a card inside the frame would be a border inside a border */
:where(.nous) .nous-rail{flex:0 0 280px;width:280px;align-self:flex-start;position:sticky;top:0;max-height:100vh;overflow:auto;padding:10px 16px 16px;scrollbar-width:thin}
:where(.nous) .rail-sec{border-top:1px solid var(--line);padding:8px 0 10px}
:where(.nous) .rail-sec:first-of-type{border-top:0}
:where(.nous) .rail-sec > summary{cursor:pointer;list-style:none;font-weight:700;font-size:var(--t-cell);color:var(--ink);padding:6px 0;display:flex;justify-content:space-between;align-items:center;user-select:none}
:where(.nous) .rail-sec > summary::-webkit-details-marker{display:none}
:where(.nous) .rail-sec > summary::after{content:"⌃";color:var(--mut);font-size:12px;transform:translateY(2px)}
:where(.nous) .rail-sec:not([open]) > summary::after{content:"⌄";transform:translateY(-2px)}
:where(.nous) .rail-body{padding:2px 0 0}
:where(.nous) .rail-link{display:block;color:var(--blue);text-decoration:none;font-size:var(--t-cell);padding:3px 0;line-height:1.35;overflow-wrap:anywhere}
:where(.nous) .rail-link:hover{text-decoration:underline}
:where(.nous) .rail-link.on{color:var(--ink);font-weight:700}
:where(.nous) .rail-link.lvl1{padding-left:10px} :where(.nous) .rail-link.lvl2{padding-left:20px}
:where(.nous) .rail-link.lvl3{padding-left:30px} :where(.nous) .rail-link.lvl4{padding-left:40px}
:where(.nous) .nous-rail .count{color:var(--mut);font-size:var(--t-meta);font-weight:400;white-space:nowrap}
:where(.nous) .rail-check{display:flex;align-items:center;gap:8px;font-size:var(--t-cell);color:var(--ink);padding:4px 0;cursor:pointer;line-height:1.3}
:where(.nous) .rail-check input{width:16px;height:16px;min-height:0;margin:0;accent-color:var(--accent);flex:none}
:where(.nous) .rail-more{display:block;color:var(--blue);font-size:var(--t-meta);text-decoration:none;padding:4px 0}
:where(.nous) .rail-note{color:var(--mut);font-size:var(--t-meta);padding:4px 0}
:where(.nous) .rail-range{display:flex;gap:6px;align-items:center}
:where(.nous) .rail-range input{width:0;flex:1 1 0;min-width:0;min-height:30px;height:30px;padding:4px 8px;font-size:var(--t-meta)}
:where(.nous) .rail-range span{color:var(--mut);font-size:var(--t-meta)}
:where(.nous) .rail-range button{padding:0 10px;min-height:30px;height:30px}
:where(.nous) .rail-active{padding:4px 0 10px;display:flex;flex-wrap:wrap;gap:6px;align-items:center}
:where(.nous) .rail-active .rail-clear{color:var(--blue);font-size:var(--t-cell);font-weight:700;text-decoration:none;flex:1 1 100%}
:where(.nous) .rail-active .chip{cursor:pointer;color:var(--ink)}
:where(.nous) .rail-active .chip:hover{border-color:var(--bad);color:var(--bad)}
@media (max-width:900px){
  :where(.nous) .layout{display:block}
  :where(.nous) .layout > .main{border-left:0;border-top:1px solid var(--line)}
  :where(.nous) .nous-rail{width:auto;position:static;max-height:none;display:grid;grid-template-columns:1fr 1fr;gap:0 16px}
  :where(.nous) .rail-active{grid-column:1 / -1}
}

/* ── 11. SMALL SCREENS ─────────────────────────────────────────────────────────────────────── */
@media (max-width:640px){
  :where(.nous) .wrap{padding:14px 16px 48px}
  :where(.nous) .stats{gap:8px}
  :where(.nous) .stat{min-width:calc(50% - 4px)}
  :where(.nous) .bar > *{flex:1 1 100%}
}
@media (prefers-reduced-motion:reduce){
  :where(.nous) *{transition:none !important}
}
