/*
 * Reqce stylesheet (ADR-0002, ADR-0012, reference v0.5 §5-§10, §17).
 * One file, plain CSS with custom properties, no preprocessor, no
 * framework. Ordered layers keep specificity flat (reference §8.1):
 * later layers win regardless of selector specificity or source order.
 *
 * U1b re-skin (reference v0.5, decisions 12-16, ADR-0016's dated note):
 * a persistent left sidebar with grouped navigation, a top bar carrying
 * the breadcrumb and account identity, card sections everywhere, larger
 * radii and taller controls, filled primary buttons, a centred sign-in
 * card -- with the palette of §6.1 unchanged (the owner's own words: "use
 * the reqce palette"). Layout and components changed; every colour value
 * below is byte-for-byte the same as the pre-U1b file.
 */
@layer reset, tokens, base, layout, components, state, print;

/* ============================================================ reset === */
@layer reset {
  *, *::before, *::after { box-sizing: border-box; }
  html { color-scheme: light; -webkit-text-size-adjust: 100%; }
  body { margin: 0; }
  h1, h2, h3, h4, p, figure, blockquote, dl, dd { margin: 0; }
  ul, ol { margin: 0; padding: 0; }
  img, svg { display: block; max-width: 100%; }
  input, button, textarea, select { font: inherit; color: inherit; }
  button { background: none; border: 0; padding: 0; }
  table { border-collapse: collapse; }
}

/* =============================================================== tokens */
@layer tokens {
  :root {
    /* §6.1 palette -- unchanged by the re-skin (owner: "use the reqce palette") */
    --rq-paper:        #FFFFFF;
    --rq-ground:       #F3F5F7;
    --rq-surface-alt:  #FAFBFC;

    --rq-ink:          #15202B;
    --rq-ink-2:        #4A5763;
    --rq-ink-3:        #5F6B76;

    --rq-line:         #D9DFE5;
    --rq-line-strong:  #B9C2CB;

    --rq-accent:       #1B4D8F;
    --rq-accent-hover: #143A6B;
    --rq-accent-soft:  #E8EFF7;
    --rq-focus:        #0B63CE;
    --rq-accent-admin: #7A2E2E;

    --rq-ok:      #1E6B45;  --rq-ok-soft:     #E3F1E9;
    --rq-warn:    #8A5A00;  --rq-warn-soft:   #FBF0D5;
    --rq-danger:  #A32218;  --rq-danger-soft: #FBE8E5;

    --rq-ins-soft: #E3F1E9;
    --rq-del-soft: #FBE8E5;

    /* §6.4 the rest -- decision 14: 6px controls, 10px cards */
    --rq-radius:    6px;
    --rq-radius-lg: 10px;
    --rq-shadow:    0 1px 2px rgb(21 32 43 / .06);
    --rq-ring:      0 0 0 2px var(--rq-paper), 0 0 0 4px var(--rq-focus);
    --rq-motion:    120ms ease-out;

    /* §6.4 eight tag tints, one hue family each, all AA against --rq-ink */
    --rq-tag-blue:   #DCE8F7;
    --rq-tag-teal:   #D8EEEA;
    --rq-tag-green:  #DEEEDD;
    --rq-tag-olive:  #E9EED6;
    --rq-tag-amber:  #F5E9C9;
    --rq-tag-orange: #F6E1CE;
    --rq-tag-rose:   #F6DEE0;
    --rq-tag-purple: #E9E0F2;

    /* §7 typography */
    --rq-font-ui:   system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
    --rq-font-read: "Iowan Old Style", "Palatino Linotype", Palatino, "Book Antiqua", Georgia, serif;
    --rq-font-mono: ui-monospace, SFMono-Regular, Menlo, Consolas, "Liberation Mono", monospace;

    /* §7 the seven-token type scale -- every font-size in this file is one
       of these (or 1em for an inherited control), enforced by
       StylesheetGuardTest */
    --rq-text-meta:   0.8125rem;
    --rq-text-dense:  0.875rem;
    --rq-text-body:   0.9375rem;
    --rq-text-title:  1rem;
    --rq-text-page:   1.25rem;
    --rq-text-metric: 1.5rem;
    --rq-text-read:   1.0625rem;

    /* §5 spacing scale -- the only permitted values */
    --rq-space-1: 0.25rem;
    --rq-space-2: 0.5rem;
    --rq-space-3: 0.75rem;
    --rq-space-4: 1rem;
    --rq-space-5: 1.5rem;
    --rq-space-6: 2rem;
    --rq-space-7: 3rem;
    --rq-space-8: 4rem;

    /* §5 layout */
    --rq-reading-max:   38rem;
    --rq-sidebar-w:     16rem;
    --rq-topbar-h:      4rem;
    --rq-gutter:        2rem;

    /* §4.6/§5, decision 21, "Rhythm above the frame": the board frame's
       height is the viewport remainder below its own top, with a 16rem
       floor -- the offset is measured, not summed. On the board route
       with the scanner banner present the frame's top edge sits at 28rem
       at content widths below about 88rem, where the filter group's
       action row wraps beneath its fields (top bar 4, banner 2.4, main
       padding 1, page header 3.3 + 1, switcher 3.1 + 1, filter group
       with two rows 11, gap 1), plus 1rem for the main area's bottom
       padding so the frame ends at the padding edge; at wider widths the
       action row fits beside the fields and the frame ends about 3.5rem
       short, which is accepted; no script measures this. */
    --rq-board-offset: 29rem;
  }
}

/* ================================================================ base = */
@layer base {
  html { font-family: var(--rq-font-ui); }
  body {
    color: var(--rq-ink);
    background: var(--rq-ground);
    font-size: var(--rq-text-body);
    line-height: 1.5;
  }

  /* §7 type scale: page heading, block title (h2, .rq-block__heading),
     group title (h3, legend) -- headings never take the accent colour. */
  h1 { font-size: var(--rq-text-page); line-height: 1.3; font-weight: 600; }
  h2 { font-size: var(--rq-text-title); line-height: 1.35; font-weight: 600; }
  h3 { font-size: var(--rq-text-body); line-height: 1.4; font-weight: 600; }

  a { color: var(--rq-accent); }
  a:hover { color: var(--rq-accent-hover); }

  /* §13 focus-visible ring everywhere; outline:none with no replacement is a defect */
  :focus-visible {
    outline: none;
    box-shadow: var(--rq-ring);
    border-radius: var(--rq-radius);
  }

  code, kbd, samp, .rq-mono {
    font-family: var(--rq-font-mono);
  }

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

/* ============================================================== layout = */
@layer layout {
  /* the five permitted utilities (§8.2) -- resist adding a sixth */
  .rq-stack { display: flex; flex-direction: column; gap: var(--rq-space-3); }
  .rq-cluster { display: flex; flex-wrap: wrap; align-items: center; gap: var(--rq-space-3); list-style: none; margin: 0; padding: 0; }
  .rq-visually-hidden {
    position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px;
    overflow: hidden; clip: rect(0, 0, 0, 0); white-space: nowrap; border: 0;
  }
  .rq-truncate { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
  .rq-no-print { }

  .rq-skip-link {
    position: absolute;
    left: var(--rq-space-2);
    top: -3rem;
    z-index: 100;
    background: var(--rq-accent);
    color: var(--rq-paper);
    padding: var(--rq-space-2) var(--rq-space-4);
    border-radius: var(--rq-radius);
    transition: top var(--rq-motion);
  }
  .rq-skip-link:focus { top: var(--rq-space-2); }

  .rq-page {
    /* Decision 22: the page fills the content column between its gutters
       at every window width. width:100% (not the flexbox stretch default
       this would otherwise already get) stays as the backstop against
       flex-item sizing: .rq-main carries this class and is a flex item of
       .rq-shell__content's column flex, where a cross-axis auto margin
       would suppress stretch sizing in favour of sizing to content --
       exactly the failure mode that let .rq-board's full-bleed width
       calc() below grow this element, and so the whole page, past the
       content column into a page-level horizontal scrollbar. An explicit
       width re-establishes the 100%-of-container size. */
    width: 100%;
    padding-inline: var(--rq-gutter);
  }
  @media (max-width: 40rem) {
    .rq-page { padding-inline: 1rem; }
  }

  /* §4.2 decision 12: the persistent sidebar + top-bar shell. .rq-shell
     is a two-column flex row for the width the sidebar occupies (16rem,
     collapsing to a <details> disclosure below 52rem); .rq-shell__content
     is everything else, itself a column (top bar, banners, flash, main). */
  .rq-shell {
    display: flex;
    align-items: stretch;
    min-height: 100vh;
  }
  .rq-shell__content {
    flex: 1 1 auto;
    min-width: 0;
    display: flex;
    flex-direction: column;
  }

  .rq-sidebar {
    flex: 0 0 var(--rq-sidebar-w);
    width: var(--rq-sidebar-w);
    background: var(--rq-paper);
    border-right: 1px solid var(--rq-line);
  }
  .rq-sidebar__toggle {
    display: none;
    cursor: pointer;
    list-style: none;
    font-weight: 600;
    padding: var(--rq-space-3) var(--rq-space-4);
    border-bottom: 1px solid var(--rq-line);
  }
  .rq-sidebar__toggle::-webkit-details-marker { display: none; }
  .rq-sidebar__body {
    display: flex;
    flex-direction: column;
    height: 100%;
    padding: var(--rq-space-4);
    gap: var(--rq-space-5);
  }

  /* The one recorded exception to "no images in the chrome" (ADR-0016,
     dated note): the mark beside the text product name. */
  .rq-brand {
    display: flex;
    align-items: center;
    gap: var(--rq-space-2);
    text-decoration: none;
    color: var(--rq-ink);
    font-weight: 600;
  }
  .rq-brand__mark { height: 1.75rem; width: auto; }

  .rq-sidebar__group-label {
    font-size: var(--rq-text-meta);
    font-weight: 600;
    color: var(--rq-ink-3);
    margin-bottom: var(--rq-space-2);
  }
  .rq-sidebar__group ul { list-style: none; display: flex; flex-direction: column; gap: 2px; }
  .rq-sidebar__group a {
    display: flex;
    align-items: center;
    gap: var(--rq-space-2);
    padding: var(--rq-space-2) var(--rq-space-3);
    border-radius: var(--rq-radius);
    color: var(--rq-ink-2);
    text-decoration: none;
    font-size: var(--rq-text-dense);
  }
  /* §5 "Containers": emphasis is a line change, never a tint --
     --rq-surface-alt is reserved for table heads, board columns, code and
     disabled controls, so hover here is a colour change only. */
  .rq-sidebar__group a:hover { color: var(--rq-ink); }
  .rq-sidebar__group a[aria-current="page"] {
    background: var(--rq-accent-soft);
    color: var(--rq-accent);
    font-weight: 600;
  }
  .rq-sidebar__group a .rq-icon { color: var(--rq-ink-3); }
  .rq-sidebar__group a[aria-current="page"] .rq-icon { color: var(--rq-accent); }

  /* Admin shell (reference §4.8): the same layout, --rq-accent-admin
     instead of --rq-accent on the sidebar's current entry, and a visible
     Admin label -- never merged with tenant navigation. */
  .rq-shell[data-admin="true"] .rq-sidebar__group a[aria-current="page"] {
    background: color-mix(in srgb, var(--rq-accent-admin) 12%, var(--rq-paper));
    color: var(--rq-accent-admin);
  }
  .rq-shell[data-admin="true"] .rq-sidebar__group a[aria-current="page"] .rq-icon { color: var(--rq-accent-admin); }
  .rq-chip--admin { border-color: var(--rq-accent-admin); color: var(--rq-accent-admin); background: color-mix(in srgb, var(--rq-accent-admin) 10%, var(--rq-paper)); margin-left: var(--rq-space-2); }

  .rq-avatar {
    flex: none;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 2rem;
    height: 2rem;
    border-radius: 50%;
    background: var(--rq-accent);
    color: var(--rq-paper);
    font-size: var(--rq-text-meta);
    font-weight: 600;
  }

  @media (max-width: 52rem) {
    .rq-shell { flex-direction: column; }
    .rq-sidebar { width: 100%; flex-basis: auto; border-right: 0; border-bottom: 1px solid var(--rq-line); }
    .rq-sidebar__toggle { display: block; }
    .rq-sidebar:not([open]) .rq-sidebar__body { display: none; }
  }

  .rq-topbar {
    min-height: var(--rq-topbar-h);
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--rq-space-4);
    border-bottom: 1px solid var(--rq-line);
    background: var(--rq-paper);
    padding-inline: var(--rq-gutter);
    flex-wrap: wrap;
  }
  @media (max-width: 40rem) {
    .rq-topbar { padding-inline: 1rem; }
  }

  /* §4.2 decision 23: the account cluster is the top bar's only account
     surface -- bell and account control vertically centred as one row. */
  .rq-topbar__account { display: flex; align-items: center; gap: var(--rq-space-4); height: 100%; margin-inline-start: auto; }
  .rq-topbar__account-text { display: flex; flex-direction: column; text-align: left; line-height: 1.2; }
  .rq-topbar__account-text strong { font-size: var(--rq-text-body); font-weight: 600; }
  .rq-topbar__muted { color: var(--rq-ink-3); font-size: var(--rq-text-meta); }

  .rq-account-menu { position: relative; }
  .rq-account-menu > summary {
    cursor: pointer;
    list-style: none;
    display: inline-flex;
    align-items: center;
    gap: var(--rq-space-2);
    height: 2.75rem;
  }
  .rq-account-menu > summary::-webkit-details-marker { display: none; }
  .rq-account-menu__panel {
    position: absolute;
    right: 0;
    top: calc(100% + var(--rq-space-1));
    background: var(--rq-paper);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius);
    box-shadow: var(--rq-shadow);
    padding: var(--rq-space-2) 0;
    min-width: 12rem;
    z-index: 10;
  }
  .rq-account-menu__item {
    display: block;
    width: 100%;
    text-align: left;
    padding: var(--rq-space-2) var(--rq-space-4);
    font: inherit;
    color: var(--rq-ink);
    text-decoration: none;
    background: transparent;
    border: 0;
    cursor: pointer;
  }
  .rq-account-menu__item:hover { background: var(--rq-accent-soft); }

  .rq-breadcrumb-band { display: flex; align-items: center; min-width: 0; }

  /* min-width:0 + overflow-x:hidden: .rq-main is a flex item along
     .rq-shell__content's cross axis (column flex), and .rq-board's own
     full-bleed calc() below can otherwise report a larger intrinsic
     content width that stretch-sizing honours, growing .rq-main (and so
     the whole page) past the content column and opening a page-level
     horizontal scrollbar. This clamps .rq-main to the column's actual
     width and clips any residual bleed at that edge instead. */
  .rq-main { padding-block: var(--rq-space-6); min-width: 0; overflow-x: hidden; }
  @media (max-width: 40rem) {
    .rq-main { padding-block: var(--rq-space-4); }
  }

  /* §4.9 decision 15: the sign-in card and the workspace home's
     first-run screen -- ground edge to edge, one centred 28rem card. */
  .rq-minimal-main {
    min-height: 100vh;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: var(--rq-space-6) var(--rq-space-4);
  }
  .rq-signin {
    width: 100%;
    max-width: 28rem;
    background: var(--rq-paper);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius-lg);
    padding: var(--rq-space-6);
    text-align: center;
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: var(--rq-space-4);
  }
  .rq-signin__logo { margin-inline: auto; }
  .rq-signin h1 { margin: 0; }
  .rq-signin p { color: var(--rq-ink-2); }

  /* §4.5 item-page header: identifier slot, markers row, AC block and
     working notes visually separated within the reading content. The
     item page's own layout is the block grid now (.rq-bento, §5) -- the
     old two-column .rq-item-grid is gone; .rq-item-rail is a plain
     block (it carries .rq-block itself, reference §4.5), so nothing
     rail-specific is needed beyond its inner definition-list spacing. */
  .rq-item-header__identifier { display: flex; align-items: center; gap: var(--rq-space-2); margin: 0 0 var(--rq-space-1); }
  .rq-marker-row { display: flex; flex-wrap: wrap; align-items: center; gap: var(--rq-space-2); margin-top: var(--rq-space-2); }
  .rq-item-ac { margin-top: var(--rq-space-5); }
  .rq-working-notes {
    margin-top: var(--rq-space-6);
    padding-top: var(--rq-space-4);
    border-top: 1px solid var(--rq-line);
  }
  .rq-working-notes h3 { color: var(--rq-ink-2); }
  .rq-item-rail .rq-definition-list { row-gap: var(--rq-space-2); }
  .rq-comment-thread .rq-comment + .rq-comment { margin-top: var(--rq-space-4); }

  /* Definition list (reference §9 score summary, §4.5 item rail): term
     column fixed, description takes the rest. */
  .rq-definition-list {
    display: grid;
    grid-template-columns: auto 1fr;
    column-gap: var(--rq-space-3);
    row-gap: var(--rq-space-1);
    margin: 0;
  }
  .rq-definition-list dt { color: var(--rq-ink-2); font-weight: 400; }
  .rq-definition-list dd { margin: 0; }

  /* §4.6/§5, decision 21: the board sits inside the page clamp, at the
     filter group's own width -- no breakout. The frame is its own
     bordered box and its own horizontal scroll container for the
     columns; height is the viewport remainder below the frame's top
     (--rq-board-offset, tokens layer) with a 16rem floor, so the page
     itself never scrolls sideways or grows past one screen's height. */
  .rq-board {
    display: flex;
    gap: var(--rq-space-4);
    overflow-x: auto;
    padding: var(--rq-space-4);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius-lg);
    background: var(--rq-paper);
    height: max(16rem, calc(100vh - var(--rq-board-offset)));
    -webkit-overflow-scrolling: touch;
  }
  .rq-board > p { padding: var(--rq-space-2); color: var(--rq-ink-2); }
  /* §4.6 column: a framed unit, full frame height (the flex row's default
     align-items:stretch gives every column the frame's own height), its
     own three-part flex column so only the body (below) scrolls. */
  .rq-board__column {
    flex: 0 0 20rem;
    display: flex;
    flex-direction: column;
    overflow: hidden;
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius-lg);
    background: var(--rq-surface-alt);
  }
  .rq-board__column-body {
    flex: 1 1 auto;
    overflow-y: auto;
    min-height: 0;
    padding: var(--rq-space-2);
  }
  .rq-board__column-cards {
    list-style: none;
  }
  /* §4.6 "Collapsed outcome columns" (decision 30): 3rem, label vertical. */
  .rq-board__column[data-collapsed] { flex-basis: 3rem; }
  .rq-board__column[data-collapsed] > .rq-board__column-header {
    flex-direction: column;
    writing-mode: vertical-rl;
    height: 100%;
  }
  /* §5 "on a phone the board becomes one column at a time with a column
     selector" -- the selector itself is a template-rendered <form>/<select>
     (JS-free); this hides every column but the selected one below 40rem.
     The frame's own height rule still applies at this width. */
  @media (max-width: 40rem) {
    .rq-board { flex-direction: column; }
    .rq-board__column {
      flex: 1 1 auto;
      width: 100%;
    }
    .rq-board__column:not([data-phone-selected]) {
      display: none;
    }
  }

  /* §5 "Block grid": on a stream page a block follows the block before it
     with one gap of space; on a grid page the .rq-bento gap does that
     job instead (components layer overrides this to 0 inside .rq-bento). */
  .rq-block + .rq-block {
    margin-top: var(--rq-space-4);
  }
}

/* =========================================================== components */
@layer components {
  /* Page header: title, one-line purpose, primary action right */
  .rq-page-header {
    display: flex;
    flex-wrap: wrap;
    align-items: flex-start;
    justify-content: space-between;
    gap: var(--rq-space-4);
    margin-bottom: var(--rq-space-6);
  }
  /* §4.6 "Rhythm above the frame": the board route's own header sits
     1rem above the view switcher, not the usual 2rem, as part of the
     compact stack the frame needs to fit a 768px-tall window. */
  .rq-page-header.rq-page-header--compact { margin-bottom: var(--rq-space-4); }
  /* §4.6 "Rhythm above the frame": the four spec-home views' main area get 1rem
     of top padding, not the usual 2rem (§5 default, set on .rq-main in
     the base layer). layout.php owns <main class="rq-page rq-main"> for
     every route, so spec-home templates carry `rq-spec-home` on the page
     header and this :has() rule reaches up from it. `:has()` is supported in
     every evergreen browser (Chrome/Edge 105+, Firefox 121+, Safari
     16.4+), so no negative-margin fallback is used. This sits in the
     components layer, after base, so it wins over .rq-main's own
     padding-block without needing extra specificity. */
  .rq-main:has(> .rq-spec-home) { padding-block: var(--rq-space-4); }
  .rq-page-header__purpose { color: var(--rq-ink-2); margin-top: var(--rq-space-1); }
  .rq-page-header__actions,
  .rq-block__actions { display: flex; gap: var(--rq-space-2); flex-wrap: wrap; }

  /* Breadcrumb */
  .rq-breadcrumb ol {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: var(--rq-space-1);
    list-style: none;
    font-size: var(--rq-text-meta);
    color: var(--rq-ink-3);
  }
  .rq-breadcrumb a { color: var(--rq-ink-2); text-decoration: none; }
  .rq-breadcrumb a:hover { text-decoration: underline; }
  .rq-breadcrumb li:not(:last-child)::after {
    content: "/";
    margin-inline-start: var(--rq-space-1);
    color: var(--rq-line-strong);
  }
  .rq-breadcrumb li:last-child { color: var(--rq-ink); font-weight: 600; }

  /* Banner band */
  .rq-banner {
    padding: var(--rq-space-2) var(--rq-gutter);
    font-size: var(--rq-text-dense);
    border-bottom: 1px solid var(--rq-line);
  }
  .rq-banner--warn { background: var(--rq-warn-soft); color: var(--rq-warn); }
  .rq-banner--danger { background: var(--rq-danger-soft); color: var(--rq-danger); }
  .rq-banner--info { background: var(--rq-accent-soft); color: var(--rq-accent); }

  /* Flash / undo band */
  .rq-flash {
    padding: var(--rq-space-2) var(--rq-gutter);
    font-size: var(--rq-text-dense);
    display: flex;
    align-items: center;
    gap: var(--rq-space-3);
  }
  .rq-flash--success { background: var(--rq-ok-soft); color: var(--rq-ok); }
  .rq-flash--error { background: var(--rq-danger-soft); color: var(--rq-danger); }
  .rq-flash__undo { margin-inline-start: auto; }

  /* Block (reference §2 principle 7, §5 "Containers", §9, decision 17):
     paper, 1px line, 10px radius, no shadow, a title with a muted
     one-line subtitle beneath. The page's own content unit; flex column
     so an optional footer (rq-block__footer) can pin to the bottom edge
     with margin-top:auto, and so blocks sharing a bento row (align-items:
     stretch) still lay their own content out top-to-bottom. */
  .rq-block {
    display: flex;
    flex-direction: column;
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius-lg);
    background: var(--rq-paper);
    padding: var(--rq-space-5);
  }
  @media (max-width: 40rem) {
    .rq-block { padding: var(--rq-space-4); }
  }
  .rq-block__heading-row {
    display: flex;
    flex-wrap: wrap;
    align-items: flex-start;
    justify-content: space-between;
    gap: var(--rq-space-3);
    margin-bottom: var(--rq-space-3);
  }
  .rq-block > .rq-block__heading:first-child { margin-bottom: var(--rq-space-1); }
  .rq-block__subtitle { color: var(--rq-ink-2); font-size: var(--rq-text-meta); margin-bottom: var(--rq-space-3); }
  .rq-block__subtitle:last-child { margin-bottom: 0; }
  /* Metric block (reference §9): the one number in a metric block. */
  .rq-block__value {
    font-size: var(--rq-text-metric);
    line-height: 1.2;
    font-weight: 600;
    font-variant-numeric: tabular-nums;
  }
  /* A block's footer -- the drill-through line, a "Show all" link, an
     action row -- pins to the block's bottom edge (§5 "Block grid") so
     footers align across a bento row. */
  .rq-block__footer { margin-top: auto; }
  /* A linked block reads emphasis as a line change, never a lift or a
     tint (§5 "Containers"). */
  a.rq-block:hover { border-color: var(--rq-line-strong); }

  /* Group (reference §5 "Containers", §9): a bordered container inside a
     block, 6px radius, no fill; nesting stops here -- never a group in a
     group. An <h3> or a <legend> inside it is the group title, already
     body-size/600 from the base h3/legend rule. */
  .rq-group {
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius);
    background: var(--rq-paper);
    padding: var(--rq-space-4);
  }
  .rq-group + .rq-group { margin-top: var(--rq-space-3); }
  .rq-group:focus-within { border-color: var(--rq-line-strong); }

  /* Row (reference §5 "Containers", §9): children of ul/ol/dl/tbody get a
     1px divider between rows -- a border-top on every row but the first,
     so there is never one above the first or below the last -- no radius,
     list markers removed. */
  .rq-rows { list-style: none; margin: 0; padding: 0; }
  .rq-rows > li,
  .rq-rows > tr,
  .rq-rows > dt {
    padding-block: var(--rq-space-3);
    border-top: 1px solid var(--rq-line);
  }
  .rq-rows > li:first-child,
  .rq-rows > tr:first-child,
  .rq-rows > dt:first-of-type {
    border-top: none;
  }
  /* dl.rq-rows: each dt/dd pair on one row instead of stacked -- the
     divider (border-top above) stays on dt, so it falls between pairs,
     never between a pair's own dt and dd. */
  dl.rq-rows {
    display: grid;
    grid-template-columns: minmax(8rem, max-content) 1fr;
    column-gap: var(--rq-space-3);
  }
  dl.rq-rows > dt { color: var(--rq-ink-2); }
  dl.rq-rows > dd { margin: 0; padding-block: var(--rq-space-3); }

  /* Block grid (reference §5 "Block grid", §9): six equal columns above
     72rem, stepping down at the three breakpoints; a block declares its
     width with one bounded span modifier, defaulting to span 3. No
     `grid-auto-flow: dense` -- DOM order is reading order. */
  .rq-bento {
    display: grid;
    grid-template-columns: repeat(6, minmax(0, 1fr));
    gap: var(--rq-space-4);
    align-items: stretch;
  }
  /* Inside the grid the gap carries the space between blocks; the stream
     page's block+block margin (layout layer) would otherwise double it. */
  .rq-bento > .rq-block + .rq-block { margin-top: 0; }
  .rq-bento > .rq-block { grid-column: span 3; }
  .rq-bento > .rq-block--span-2 { grid-column: span 2; }
  .rq-bento > .rq-block--span-3 { grid-column: span 3; }
  .rq-bento > .rq-block--span-4 { grid-column: span 4; }
  .rq-bento > .rq-block--span-6 { grid-column: span 6; }
  .rq-block--tall { grid-row: span 2; }
  @media (max-width: 72rem) {
    .rq-bento { grid-template-columns: repeat(4, minmax(0, 1fr)); }
    .rq-bento > .rq-block,
    .rq-bento > .rq-block--span-3,
    .rq-bento > .rq-block--span-4,
    .rq-bento > .rq-block--span-6 { grid-column: span 4; }
    .rq-bento > .rq-block--span-2 { grid-column: span 2; }
  }
  @media (max-width: 52rem) {
    .rq-bento { grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .rq-bento > .rq-block,
    .rq-bento > .rq-block--span-3,
    .rq-bento > .rq-block--span-4,
    .rq-bento > .rq-block--span-6 { grid-column: span 2; }
    .rq-bento > .rq-block--span-2 { grid-column: span 1; }
  }
  @media (max-width: 40rem) {
    .rq-bento { grid-template-columns: 1fr; }
    .rq-bento > .rq-block,
    .rq-bento > .rq-block--span-2,
    .rq-bento > .rq-block--span-3,
    .rq-bento > .rq-block--span-4,
    .rq-bento > .rq-block--span-6 { grid-column: span 1; }
  }

  /* Data table */
  .rq-table { width: 100%; font-size: var(--rq-text-dense); line-height: 1.4; border-collapse: collapse; }
  .rq-table caption { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0, 0, 0, 0); }
  /* --rq-surface-alt is reserved for table header rows among other
     things (§5 "Containers") -- this is that reserved use. */
  .rq-table th { text-align: left; color: var(--rq-ink-2); font-weight: 600; background: var(--rq-surface-alt); border-bottom: 1px solid var(--rq-line-strong); padding: var(--rq-space-2) var(--rq-space-3); }
  .rq-table td { border-bottom: 1px solid var(--rq-line); padding: var(--rq-space-2) var(--rq-space-3); vertical-align: top; }
  .rq-table td.rq-mono { font-family: var(--rq-font-mono); }
  .rq-table__empty { font-family: var(--rq-font-ui); text-align: center; color: var(--rq-ink-2); padding: var(--rq-space-5) var(--rq-space-3); }
  .rq-table__empty .rq-empty { padding: 0; }
  .rq-table__empty-cell { color: var(--rq-ink-3); }
  .rq-table [aria-sort] a { color: inherit; text-decoration: none; display: inline-flex; align-items: center; gap: 0.25rem; }
  /* Sortable header arrow (§9 "sortable header"): a text glyph, not an
     image, so it reads through the translation guard's literal-text scan
     as punctuation and survives print/high-contrast without an icon. */
  .rq-table th[aria-sort] a::after { content: "\2195"; color: var(--rq-ink-3); font-weight: 400; }
  .rq-table th[aria-sort="ascending"] a::after { content: "\2191"; color: var(--rq-ink); }
  .rq-table th[aria-sort="descending"] a::after { content: "\2193"; color: var(--rq-ink); }
  @media (max-width: 40rem) {
    .rq-table thead { display: none; }
    .rq-table tr { display: block; border: 1px solid var(--rq-line); border-radius: var(--rq-radius); margin-bottom: var(--rq-space-2); }
    .rq-table td { display: block; border: none; border-bottom: 1px solid var(--rq-line); }
    .rq-table td::before { content: attr(data-label); font-weight: 600; display: block; color: var(--rq-ink-2); font-size: var(--rq-text-meta); }
  }

  /* Dashboard column-count panel (reference §4.10, §9 "Metric block"): a
     plain table inside the block -- the block is its own frame (§5
     "Containers"), so no outer border here; the tbody carries .rq-rows
     for its row dividers. */
  .rq-dashboard__columns { width: 100%; font-size: var(--rq-text-dense); line-height: 1.4; border-collapse: collapse; }
  .rq-dashboard__columns th { text-align: left; color: var(--rq-ink-2); font-weight: 600; padding-block: var(--rq-space-2); }
  .rq-dashboard__columns td { padding-block: var(--rq-space-2); }

  /* Pagination */
  .rq-pagination { display: flex; align-items: center; gap: var(--rq-space-3); font-size: var(--rq-text-meta); color: var(--rq-ink-3); margin-top: var(--rq-space-3); }

  /* Filter bar (reference §9, §4.6 "Filter group actions"): one flex row
     that wraps, the fields first and the action cluster last, both
     bottom-aligned so a checkbox field's baseline matches the buttons'.
     .rq-field--checkbox carries no bottom margin of its own -- its
     outer edge would otherwise sit lower than a button's and throw the
     flex-end alignment off. */
  .rq-filter-bar {
    display: flex;
    flex-wrap: wrap;
    align-items: flex-end;
    gap: var(--rq-space-3);
  }
  /* §4.6 "Rhythm above the frame": 8rem (was 11rem) so the board's four
     fields plus the action cluster fit on one row at the filter group's
     own width; a field carries no bottom margin here (unlike the default
     .rq-field below) since the row is bottom-aligned with no wrapped
     second line beneath it. Shared by every page using .rq-filter-bar
     (list, table, search, board), not board-specific. */
  .rq-filter-bar > .rq-field:not(.rq-field--checkbox) { flex: 1 1 8rem; }
  /* Text search field gets more room so the input doesn't feel cramped. */
  .rq-filter-bar > .rq-field:has(> input[type="text"]) { flex: 2 1 12rem; }
  /* Type group quick capture (items.php): a wider, capped field so the
     title input reads as the row's primary control, not an equal-width
     filter. */
  .rq-filter-bar > .rq-field.rq-field--grow { flex: 1 1 16rem; max-width: 32rem; }
  /* Filter labels never wrap. */
  .rq-filter-bar .rq-field > label { white-space: nowrap; }
  .rq-filter-bar .rq-field { margin-bottom: 0; }
  .rq-filter-bar__actions {
    display: flex;
    flex-wrap: wrap;
    align-items: flex-end;
    gap: var(--rq-space-3);
    flex: 1 1 auto;
  }
  /* Below 72rem the action cluster wraps onto its own line as one unit
     rather than its own children wrapping independently. */
  @media (max-width: 72rem) {
    .rq-filter-bar__actions { flex-basis: 100%; }
  }
  .rq-field--checkbox { display: flex; align-items: center; margin-bottom: 0; }
  .rq-field--checkbox label { font-weight: 400; margin-bottom: 0; }
  /* §4.6 zoom (decision 21): last in the board's action cluster, pushed
     to the row's right end -- the only cluster child this applies to. */
  .rq-filter-bar__actions > .rq-board__zoom { margin-inline-start: auto; }

  /* View switcher / tab strip */
  /* View switcher / tab strip: a segmented control -- a ground-coloured track with
     the active tab as a raised paper pill; links, not a script widget (reference §9). */
  .rq-view-switcher, .rq-tab-strip { margin-bottom: var(--rq-space-4); }
  .rq-view-switcher ul, .rq-tab-strip ul {
    display: flex;
    gap: var(--rq-space-1);
    list-style: none;
    margin: 0;
    padding: 0.25rem;
    background: var(--rq-ground);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius-lg);
  }
  .rq-view-switcher li, .rq-tab-strip li { list-style: none; flex: 1 1 0; min-width: 0; }
  .rq-view-switcher a, .rq-tab-strip a {
    display: block;
    text-align: center;
    padding: var(--rq-space-2) var(--rq-space-3);
    border-radius: var(--rq-radius);
    text-decoration: none;
    color: var(--rq-ink-2);
    font-weight: 400;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
  }
  .rq-view-switcher a:hover, .rq-tab-strip a:hover { color: var(--rq-ink); }
  .rq-view-switcher a[aria-current="page"], .rq-tab-strip a[aria-current="page"] {
    background: var(--rq-paper);
    color: var(--rq-ink);
    font-weight: 600;
  }

  /* Type switcher (supporting items, one type at a time): a row of pill links */
  .rq-type-switcher ul { display: flex; flex-wrap: wrap; gap: var(--rq-space-2); list-style: none; margin: 0; padding: 0; }
  .rq-type-switcher a {
    display: inline-block;
    padding: var(--rq-space-1) var(--rq-space-3);
    border: 1px solid var(--rq-line);
    border-radius: 999px;
    text-decoration: none;
    color: var(--rq-ink-2);
    font-size: var(--rq-text-dense);
  }
  .rq-type-switcher a:hover { color: var(--rq-ink); }
  .rq-type-switcher a[aria-current="page"] { background: var(--rq-accent-soft); border-color: var(--rq-accent); color: var(--rq-accent); font-weight: 600; }

  /* Fieldsets never render raw: no border, legend as the group title
     (§7: h3/legend share the group-title role, body/1.4/600); .rq-group
     gives the bordered container itself. */
  fieldset { border: 0; padding: 0; margin: 0; min-width: 0; }
  legend { font-weight: 600; font-size: var(--rq-text-body); line-height: 1.4; padding: 0; margin-bottom: var(--rq-space-1); }
  .rq-radio-group { display: flex; flex-wrap: wrap; gap: var(--rq-space-4); }

  /* Bulk actions (reference §11.5): the fieldset is a plain .rq-group,
     legend as the title, no divider; rows below it keep an even
     --rq-space-4 rhythm, scoped to this partial. */
  .rq-table + .rq-group { margin-top: var(--rq-space-4); }
  [data-test="bulk-actions"] > .rq-bulk__count,
  [data-test="bulk-actions"] > .rq-field-grid,
  [data-test="bulk-actions"] > .rq-field--radio {
    margin-top: var(--rq-space-4);
  }
  .rq-bulk__count { color: var(--rq-ink-2); font-size: var(--rq-text-dense); }

  /* Form field (reference §9): 2.75rem controls, 6px radius, 0.75rem padding */
  .rq-field { margin-bottom: var(--rq-space-4); }
  .rq-field label { display: block; font-weight: 600; font-size: var(--rq-text-body); margin-bottom: var(--rq-space-1); }
  /* Must cascade after .rq-field label above (equal specificity) since a
     radio choice's fieldset also carries .rq-field -- else radio labels
     render block/bold instead of inline-flex/400. */
  .rq-radio-group label { display: inline-flex; align-items: center; gap: var(--rq-space-2); font-weight: 400; }
  .rq-field__help { color: var(--rq-ink-3); font-size: var(--rq-text-dense); margin-top: var(--rq-space-1); }
  .rq-field__error { color: var(--rq-danger); font-size: var(--rq-text-dense); margin-top: var(--rq-space-1); }
  .rq-field input[type="text"],
  .rq-field input[type="email"],
  .rq-field input[type="url"],
  .rq-field input[type="number"],
  .rq-field input[type="password"],
  .rq-field input[type="search"],
  .rq-field input[type="date"],
  .rq-field textarea,
  .rq-field select {
    width: 100%;
    height: 2.75rem;
    border: 1px solid var(--rq-line-strong);
    border-radius: var(--rq-radius);
    padding: 0 var(--rq-space-3);
    background: var(--rq-paper);
    color: var(--rq-ink);
  }
  .rq-field textarea { height: auto; padding: var(--rq-space-3); }
  .rq-field ::placeholder { color: var(--rq-ink-3); }
  /* Paired short fields (reference §9 "Form field": "a two-column
     auto-fit grid for short paired fields"): align-items: end bottom-
     aligns controls so a wrapped label can't drop its control below the
     row's others; items carry no bottom margin of their own -- the row
     gap already spaces them. */
  .rq-field-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(12rem, 1fr));
    gap: var(--rq-space-3) var(--rq-space-4);
    align-items: end;
  }
  .rq-field-grid > .rq-field { margin-bottom: 0; }
  .rq-field--span-2 { grid-column: span 2; }

  /* Validation summary */
  .rq-validation-summary {
    border: 1px solid var(--rq-danger);
    background: var(--rq-danger-soft);
    color: var(--rq-danger);
    border-radius: var(--rq-radius);
    padding: var(--rq-space-3) var(--rq-space-4);
    margin-bottom: var(--rq-space-5);
  }
  .rq-validation-summary a { color: inherit; }

  /* Buttons (reference §9, decision 14): primary filled accent, 2.5rem
     tall, 6px radius; default/quiet/danger variants. */
  .rq-btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: var(--rq-space-1);
    min-height: 2.5rem;
    padding: 0 var(--rq-space-4);
    border-radius: var(--rq-radius);
    border: 1px solid var(--rq-line-strong);
    background: var(--rq-paper);
    color: var(--rq-ink);
    font-weight: 600;
    font-size: var(--rq-text-dense);
    text-decoration: none;
    cursor: pointer;
    transition: background-color var(--rq-motion), border-color var(--rq-motion), color var(--rq-motion);
    white-space: nowrap;
  }
  .rq-btn:hover { border-color: var(--rq-ink-3); }
  .rq-btn--primary { background: var(--rq-accent); border-color: var(--rq-accent); color: var(--rq-paper); }
  .rq-btn--primary:hover { background: var(--rq-accent-hover); border-color: var(--rq-accent-hover); }
  .rq-btn--quiet { border-color: transparent; background: transparent; color: var(--rq-accent); }
  .rq-btn--danger { border-color: var(--rq-danger); color: var(--rq-danger); }
  .rq-btn--danger:hover { background: var(--rq-danger-soft); }
  .rq-btn--block { width: 100%; }
  .rq-btn .rq-icon { width: 1.1em; height: 1.1em; }
  .rq-btn--small { min-height: 1.75rem; padding: 0 var(--rq-space-2); font-size: var(--rq-text-meta); }

  /* §4.5/§9 overflow disclosure: no script, a <details> the browser
     already knows how to operate; the menu is a plain stack of
     buttons/links, not a positioned popover -- nothing here depends on
     JavaScript to be usable. */
  .rq-overflow { position: relative; }
  .rq-overflow > summary {
    list-style: none;
    display: inline-flex;
    align-items: center;
  }
  .rq-overflow > summary::-webkit-details-marker { display: none; }
  .rq-overflow__menu {
    display: flex;
    flex-direction: column;
    gap: var(--rq-space-1);
    position: absolute;
    right: 0;
    top: calc(100% + var(--rq-space-1));
    z-index: 5;
    background: var(--rq-paper);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius);
    box-shadow: var(--rq-shadow);
    padding: var(--rq-space-2);
    min-width: 12rem;
  }
  .rq-overflow__menu a, .rq-overflow__menu form { display: block; }
  .rq-overflow__menu .rq-btn { width: 100%; justify-content: flex-start; }
  /* UX-05/reference §4.5, decision 29: Delete last, visually separated. */
  .rq-overflow__divider { border: 0; border-top: 1px solid var(--rq-line); margin: 0; }

  /* Chip: markers, tags, column kinds -- word always present. Two
     variants (reference §9): bordered (markers, the default) and filled
     pill (status values, kind treatments -- rq-chip--fill). */
  .rq-chip {
    display: inline-flex;
    align-items: center;
    gap: var(--rq-space-1);
    border: 1px solid var(--rq-line-strong);
    border-radius: 1rem;
    padding: 0 var(--rq-space-2);
    font-size: var(--rq-text-dense);
    line-height: 1.6;
    color: var(--rq-ink-2);
    background: transparent;
  }
  .rq-chip--warn { border-color: var(--rq-warn); color: var(--rq-warn); background: var(--rq-warn-soft); }
  .rq-chip--danger { border-color: var(--rq-danger); color: var(--rq-danger); background: var(--rq-danger-soft); }
  .rq-chip--ok { border-color: var(--rq-ok); color: var(--rq-ok); background: var(--rq-ok-soft); }
  /* Filled pill variant: border colour doubles as the fill so a chip with
     no explicit kind still reads as a solid accent pill. */
  .rq-chip--fill { background: var(--rq-accent-soft); border-color: transparent; color: var(--rq-accent); font-weight: 600; }
  .rq-chip--fill.rq-chip--warn { background: var(--rq-warn-soft); color: var(--rq-warn); }
  .rq-chip--fill.rq-chip--danger { background: var(--rq-danger-soft); color: var(--rq-danger); }
  .rq-chip--fill.rq-chip--ok { background: var(--rq-ok-soft); color: var(--rq-ok); }

  /* Board card (reference §4.6, §5 "Board row"): paper on the column
     ground, no shadow -- a two-column grid so the priority chip sits at
     the card's top-right without overlapping the identifier or the
     title, whichever wraps. */
  .rq-card {
    display: grid;
    grid-template-columns: 1fr auto;
    column-gap: var(--rq-space-2);
    background: var(--rq-paper);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius);
    padding: var(--rq-space-3);
    margin-bottom: var(--rq-space-2);
  }
  .rq-card__identifier { grid-column: 1; font-family: var(--rq-font-mono); font-size: var(--rq-text-meta); color: var(--rq-ink-2); }
  /* Priority chip, top-right: grid-placed beside the identifier line. */
  .rq-card__priority { grid-column: 2; grid-row: 1; justify-self: end; align-self: start; }
  /* The one card title that carries weight (reference §4.6: "the one title
     that carries weight, because a card has no frame of its own to mark
     it") -- StylesheetGuardTest allows 400 and 600 only. */
  .rq-card__title {
    grid-column: 1 / -1;
    font-size: var(--rq-text-dense);
    line-height: 1.4;
    font-weight: 600;
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
    overflow: hidden;
  }
  .rq-card__meta { grid-column: 1 / -1; display: flex; flex-wrap: wrap; gap: var(--rq-space-1); color: var(--rq-ink-3); font-size: var(--rq-text-meta); margin-top: var(--rq-space-1); }
  .rq-card > .rq-move-dialog { grid-column: 1 / -1; }
  .rq-card--dragging { opacity: 0.4; }
  .rq-card--grabbed { outline: 2px solid var(--rq-accent); outline-offset: 2px; }
  [data-dragging] .rq-card { outline: 2px solid var(--rq-accent); outline-offset: 2px; }
  [data-dragging] { outline: 2px dashed var(--rq-accent); outline-offset: -2px; }

  /* §4.6/§6.2 column header: the kind cue is this header's own tint plus
     a 3px top border (never the column's left edge, decision 21) -- keyed
     off `[data-kind]` on the column section, scoped below in the state
     layer beside the rest of §6.2's kind treatments. */
  .rq-board__column-header {
    padding: var(--rq-space-2) var(--rq-space-3);
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: space-between;
    gap: var(--rq-space-2);
    font-weight: 600;
    border-bottom: 1px solid var(--rq-line);
    border-top: 3px solid transparent;
  }
  .rq-board__column-shown { font-weight: 400; color: var(--rq-ink-3); font-size: var(--rq-text-meta); }

  /* §4.6 "one dashed drop target with the sentence 'No requirements in
     this column'" -- one element, no separate paragraph. */
  .rq-board__empty-column {
    display: block;
    text-align: center;
    padding: var(--rq-space-4) var(--rq-space-2);
    border: 1px dashed var(--rq-line-strong);
    border-radius: var(--rq-radius);
    color: var(--rq-ink-2);
    font-size: var(--rq-text-meta);
  }

  /* §4.6 "Show more": the no-script/keyboard path; the board module
     converts it into scroll-loading in place without removing it. */
  .rq-board__show-more {
    display: block;
    text-align: center;
    padding: var(--rq-space-2);
    font-size: var(--rq-text-meta);
  }

  /* §4.6 "Rhythm above the frame": the board's own filter group sits
     1rem above the frame, like every other gap in the compact stack --
     the generic .rq-group carries no bottom margin of its own (other
     pages stack groups with .rq-group + .rq-group instead). No margin
     of its own on the frame beneath it: this gap is the whole of it. */
  .rq-board__filters { margin-bottom: var(--rq-space-4); }

  /* §4.6 zoom (decision 21): no separate toolbar row -- a segmented
     control of three fixed-width cells, last in the filter group's
     action cluster (.rq-filter-bar__actions > .rq-board__zoom above
     gives it margin-inline-start:auto so it sits at the row's right
     end), inside the filter group's own width so it never overflows
     past the frame's right edge, and never jumps width as the
     percentage's digit count changes. Adjoining cells share a border
     (border-left:0 on every cell but the first) inside one rounded,
     clipped track. */
  .rq-board__zoom {
    display: inline-flex;
    border-radius: var(--rq-radius);
    overflow: hidden;
  }
  .rq-board__zoom > a,
  .rq-board__zoom > span {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 2rem;
    height: 2rem;
    border: 1px solid var(--rq-line);
    background: var(--rq-paper);
    font-size: var(--rq-text-dense);
    font-weight: 400;
    text-decoration: none;
    color: var(--rq-accent);
  }
  .rq-board__zoom > a:not(:first-child),
  .rq-board__zoom > span:not(:first-child) {
    border-left: 0;
  }
  .rq-board__zoom > a:hover { background: var(--rq-accent-soft); }
  .rq-board__zoom > span[aria-disabled="true"] { color: var(--rq-ink-3); }
  .rq-board__zoom > .rq-board__zoom-level {
    width: 3.5rem;
    color: var(--rq-ink);
    font-variant-numeric: tabular-nums;
    text-align: center;
  }

  /* §11.4/§11.9 move control: a real <form> the reference calls a
     "dialog" enhancement -- server-rendered `open` (a plain in-flow
     block, fully usable with no script) so the no-script path never
     depends on <dialog>'s default (hidden-without-`open`) behaviour;
     board.js closes it and adds the trigger button that reopens it
     modally (see board.js's initBoardDialogs()). */
  /* Board dialogs (reference §11.9): without script the <dialog open> stays in flow as a
     plain bordered block inside its column; the module closes it and reopens it with
     showModal(), where :modal restores the centred overlay treatment. */
  .rq-move-dialog {
    position: static;
    width: auto;
    max-width: none;
    margin: 0 0 var(--rq-space-3);
    padding: var(--rq-space-3);
    border: 1px solid var(--rq-line);
    border-radius: var(--rq-radius);
    background: var(--rq-paper);
    color: inherit;
  }
  .rq-move-dialog:modal {
    position: fixed;
    inset: 0;
    width: min(28rem, calc(100% - 2rem));
    margin: auto;
    padding: var(--rq-space-5);
    border-radius: var(--rq-radius-lg);
    box-shadow: var(--rq-shadow), var(--rq-shadow);
  }

  .rq-move-dialog[open]::backdrop { background: rgb(21 32 43 / .35); }
  .rq-move-dialog[open] { box-shadow: var(--rq-shadow); }
  .rq-card__move-trigger { grid-column: 1 / -1; margin-top: var(--rq-space-2); min-height: 2rem; min-width: 2rem; }
  /* §4.6 Incoming column: the icon-only quick-capture trigger at the
     header's right end, pushed there by margin-inline-start:auto so it
     sits after the label/count/shown/ordering cluster regardless of how
     many of those are present. Hidden without script (the dialog itself
     renders open instead, reference §4.6); board.js reveals it. */
  .rq-board__add { margin-inline-start: auto; min-height: 2rem; min-width: 2rem; padding: 0; }

  /* §5 board column selector, phone only (below 40rem) -- a plain GET form/select. */
  .rq-board-column-select { display: none; }
  @media (max-width: 40rem) {
    .rq-board-column-select { display: block; margin-bottom: var(--rq-space-4); }
  }

  /* Criterion row / score summary: the fieldset also carries .rq-group
     (reference §5 "Containers", §9 "Criterion row") -- border, radius,
     padding and background come from that rule now, not from here. */
  .rq-criterion-row__status { display: flex; flex-wrap: wrap; gap: var(--rq-space-3); margin: var(--rq-space-2) 0; }
  .rq-score-summary { display: grid; grid-template-columns: max-content 1fr; gap: var(--rq-space-1) var(--rq-space-3); font-size: var(--rq-text-dense); }
  .rq-score-summary dt { color: var(--rq-ink-2); }

  /* §11.6 review screen: requirement pinned at reading width on the
     left, criteria on the right; below 52rem the requirement comes
     first and nothing is pinned (there is no room to pin against). */
  .rq-review-layout { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.3fr); gap: var(--rq-space-4); align-items: start; }
  .rq-review-layout__requirement { position: sticky; top: calc(4rem + var(--rq-space-4)); max-width: var(--rq-reading-max); }
  @media (max-width: 52rem) {
    .rq-review-layout { grid-template-columns: 1fr; }
    .rq-review-layout__requirement { position: static; max-width: none; }
  }

  /* Diff */
  .rq-diff { font-family: var(--rq-font-mono); font-size: var(--rq-text-dense); white-space: pre-wrap; }
  .rq-diff ins { background: var(--rq-ins-soft); text-decoration: none; }
  .rq-diff del { background: var(--rq-del-soft); text-decoration: line-through; }

  /* Version list */
  .rq-version-list { list-style: none; }
  .rq-version-list li { border-bottom: 1px solid var(--rq-line); padding: var(--rq-space-2) 0; }

  /* Attachment row */
  .rq-attachment-row { display: flex; align-items: center; gap: var(--rq-space-3); padding: var(--rq-space-2) 0; border-bottom: 1px solid var(--rq-line); }

  /* Comment thread */
  .rq-comment { border-left: 2px solid var(--rq-line); padding-left: var(--rq-space-3); margin-bottom: var(--rq-space-3); }
  .rq-comment ol { list-style: none; padding-left: var(--rq-space-5); }

  /* Empty state */
  .rq-empty { padding: var(--rq-space-6) var(--rq-space-4); text-align: center; color: var(--rq-ink-2); }

  /* Confirm page */
  .rq-confirm { max-width: var(--rq-reading-max); }
  .rq-confirm__consequences { background: var(--rq-paper); border: 1px solid var(--rq-line); border-radius: var(--rq-radius); padding: var(--rq-space-4); margin: var(--rq-space-4) 0; }

  /* Job status */
  .rq-job-status dt { color: var(--rq-ink-2); }

  /* Icon: aria-hidden use elements, always beside real text */
  .rq-icon { width: 1em; height: 1em; fill: currentColor; flex: none; }

  /* §7 reading face: exactly five places use it (requirement content,
     acceptance criteria, findings, release/baseline documents, print) */
  .rq-prose {
    font-family: var(--rq-font-read);
    font-size: var(--rq-text-read);
    line-height: 1.65;
    max-width: var(--rq-reading-max);
  }
  .rq-prose p { margin-bottom: var(--rq-space-3); }

  /* Notifications list (reference §4.7, Appendix A row 31) */
  .rq-notification-list { list-style: none; padding: 0; margin: var(--rq-space-4) 0 0; }
  .rq-notification { display: flex; align-items: center; flex-wrap: wrap; gap: var(--rq-space-2) var(--rq-space-3); padding: var(--rq-space-3) 0; border-bottom: 1px solid var(--rq-line); }
  .rq-notification--unread { background: var(--rq-accent-soft); border-radius: var(--rq-radius); padding-inline: var(--rq-space-2); }
  .rq-notification__summary { flex: 1 1 auto; }
  .rq-notification__date { color: var(--rq-ink-3); font-size: var(--rq-text-meta); }
  .rq-notification__mark-form { margin-inline-start: auto; }

  /* A short numeric field (e.g. the manage-panels order column, reference §4.10) */
  .rq-input--narrow { width: 4.5rem; }

  /* Baseline document member (reference §4.5, §7): reading face, one card per member */
  .rq-baseline-member { padding: var(--rq-space-4) 0; border-bottom: 1px solid var(--rq-line); }
  .rq-baseline-member:last-child { border-bottom: none; }

  /* Search results: grouped by spec, then object type (reference §13.2) */
  .rq-search-group { margin-bottom: var(--rq-space-5); }
  .rq-search-group h3 { margin-bottom: var(--rq-space-2); }
  .rq-search-group h4 { font-size: var(--rq-text-dense); color: var(--rq-ink-2); font-weight: 600; margin-bottom: var(--rq-space-1); }
  .rq-search-results { list-style: none; padding: 0; margin: 0 0 var(--rq-space-4); }
  .rq-search-results li { padding: var(--rq-space-2) 0; border-bottom: 1px solid var(--rq-line); }
  .rq-search-results mark { background: var(--rq-warn-soft); color: var(--rq-ink); }
}

/* ================================================================ state = */
@layer state {
  [aria-current="page"] { font-weight: 600; }

  /* §6.2 workflow column kinds: colour is never the only carrier. The 3px
     cue is the left border of a column chip everywhere except the board
     (§9 "Board card", §6.2) -- scoped to .rq-chip because decision 21
     moved `data-kind` onto the board column section too (below), and a
     bare attribute selector would otherwise tint that whole box. */
  .rq-chip[data-kind="incoming"] { color: var(--rq-ink-2); }
  .rq-chip[data-kind="active_review"] { color: var(--rq-accent); background: var(--rq-accent-soft); border-left: 3px solid var(--rq-accent); }
  .rq-chip[data-kind="waiting"] { color: var(--rq-warn); background: var(--rq-warn-soft); border-left: 3px dashed var(--rq-warn); }
  .rq-chip[data-kind="generic"] { color: var(--rq-ink-2); background: var(--rq-surface-alt); border-left: 3px solid var(--rq-line-strong); }
  .rq-chip[data-kind="approved"] { color: var(--rq-ok); background: var(--rq-ok-soft); border-left: 3px solid var(--rq-ok); }
  .rq-chip[data-kind="needs_rewrite"] { color: var(--rq-warn); background: var(--rq-warn-soft); border-left: 3px solid var(--rq-warn); }
  .rq-chip[data-kind="rejected"] { color: var(--rq-danger); background: var(--rq-danger-soft); border-left: 3px solid var(--rq-danger); }
  .rq-chip[data-kind="out_of_scope"] { color: var(--rq-ink-2); background: var(--rq-surface-alt); border-left: 3px solid var(--rq-line-strong); }
  .rq-chip[data-kind="deferred"] { color: var(--rq-ink-2); background: var(--rq-surface-alt); border-left: 3px dotted var(--rq-line-strong); }

  /* §4.6/§6.2 board column header: the same kind cue as a top border plus
     the header's own tint, keyed off `[data-kind]` on the column section
     (`.rq-board__column-header` itself carries no `data-kind`, decision
     21 -- `data-test="board-column"` stays on the header for tests). */
  .rq-board__column[data-kind="incoming"] > .rq-board__column-header { color: var(--rq-ink-2); }
  .rq-board__column[data-kind="active_review"] > .rq-board__column-header { color: var(--rq-accent); background: var(--rq-accent-soft); border-top-color: var(--rq-accent); }
  .rq-board__column[data-kind="waiting"] > .rq-board__column-header { color: var(--rq-warn); background: var(--rq-warn-soft); border-top-style: dashed; border-top-color: var(--rq-warn); }
  .rq-board__column[data-kind="generic"] > .rq-board__column-header { color: var(--rq-ink-2); background: var(--rq-surface-alt); border-top-color: var(--rq-line-strong); }
  .rq-board__column[data-kind="approved"] > .rq-board__column-header { color: var(--rq-ok); background: var(--rq-ok-soft); border-top-color: var(--rq-ok); }
  .rq-board__column[data-kind="needs_rewrite"] > .rq-board__column-header { color: var(--rq-warn); background: var(--rq-warn-soft); border-top-color: var(--rq-warn); }
  .rq-board__column[data-kind="rejected"] > .rq-board__column-header { color: var(--rq-danger); background: var(--rq-danger-soft); border-top-color: var(--rq-danger); }
  .rq-board__column[data-kind="out_of_scope"] > .rq-board__column-header { color: var(--rq-ink-2); background: var(--rq-surface-alt); border-top-color: var(--rq-line-strong); }
  .rq-board__column[data-kind="deferred"] > .rq-board__column-header { color: var(--rq-ink-2); background: var(--rq-surface-alt); border-top-style: dotted; border-top-color: var(--rq-line-strong); }

  /* §4.6 zoom (decision 21): five fixed levels, applied with the CSS
     `zoom` property (standard in every evergreen browser) so column
     width, card type and spacing scale together and the frame itself
     stays put -- carried by `data-zoom` on the board element, driven
     entirely by the URL (§2 principle 5), no script involved. `zoom`
     also scales the computed height of the element it's set on, so
     the frame's own height rule (base rule above) is divided by the
     same level here -- undoing the scaling -- to keep the on-screen
     height constant across levels instead of shrinking or overflowing.
     The floor is divided as well because zoom scales it too. */
  .rq-board[data-zoom="75"]  { zoom: 0.75; height: calc(max(16rem, 100vh - var(--rq-board-offset)) / 0.75); }
  .rq-board[data-zoom="90"]  { zoom: 0.9; height: calc(max(16rem, 100vh - var(--rq-board-offset)) / 0.9); }
  .rq-board[data-zoom="100"] { zoom: 1; height: calc(max(16rem, 100vh - var(--rq-board-offset)) / 1); }
  .rq-board[data-zoom="110"] { zoom: 1.1; height: calc(max(16rem, 100vh - var(--rq-board-offset)) / 1.1); }
  .rq-board[data-zoom="125"] { zoom: 1.25; height: calc(max(16rem, 100vh - var(--rq-board-offset)) / 1.25); }

  [data-tag-tint="blue"]   { background: var(--rq-tag-blue); }
  [data-tag-tint="teal"]   { background: var(--rq-tag-teal); }
  [data-tag-tint="green"]  { background: var(--rq-tag-green); }
  [data-tag-tint="olive"]  { background: var(--rq-tag-olive); }
  [data-tag-tint="amber"]  { background: var(--rq-tag-amber); }
  [data-tag-tint="orange"] { background: var(--rq-tag-orange); }
  [data-tag-tint="rose"]   { background: var(--rq-tag-rose); }
  [data-tag-tint="purple"] { background: var(--rq-tag-purple); }

  /* Untranslated marker (§14.5, §7): the superscript "EN" Translator::render()
     appends -- 0.7em is retired onto --rq-text-meta. */
  .rq-untranslated__mark { font-size: var(--rq-text-meta); vertical-align: super; color: var(--rq-warn); cursor: help; }

  [hidden] { display: none !important; }
}

/* ================================================================ print = */
@layer print {
  @media print {
    .rq-no-print,
    .rq-sidebar,
    .rq-topbar,
    .rq-banner,
    .rq-flash,
    .rq-breadcrumb-band,
    .rq-filter-bar,
    .rq-view-switcher,
    .rq-tab-strip {
      display: none !important;
    }
  }

  /* §15: the print document's own running header/footer, via @page.
     The document itself (its body content) is built in U3; this is the
     skeleton the print CSS layer reserves for it. */
  @page {
    margin: 2cm 1.5cm;
  }
}
