  /* project-specific only - Bootstrap handles layout, controls, table, dropdown, modal */
  /* The palette is a set of roles, not colours (docs/spec/15-palette-and-themes.md):
     every rule below names a role, and the two theme blocks give each role its
     value. Magenta is the brand and means "on" or "do this" (an active chip, a
     pressed toggle, the primary button, the open row's edge); links are the
     blue; the graph's four curve colours (~D and the three lines under it,
     config.RENDER_DEFAULT's color_d/nps/vps/kps, which every family shares
     in plot.py's assignment) and the three compare series are two separate
     sets, so no colour ever changes meaning; the four level colours
     are the spreadsheet's hue families saturated for each ground. --fw-brand is
     a FILL (white on it is 5.4:1) and never text: text in the brand colour is
     --fw-brand-text. Every text pair below measures 4.5:1 or better on its own
     ground and every swatch or clickable thing 3:1 (tests/page/contrast.js
     audits both themes); the ratios are in the spec. A dark ground is the
     default; light follows the OS or the header's toggle (static/js/theme.js). */
  :root, [data-bs-theme="light"] {
    --fw-bg:#fbfafd; --fw-bg-rgb:251,250,253;
    --fw-bg-raised:#f1eff6; --fw-bg-raised-rgb:241,239,246;
    --fw-bg-hover:#e7e4ee; --fw-bg-hover-rgb:231,228,238;
    --fw-border:#d3cfdc;
    --fw-text:#232030; --fw-text-rgb:35,32,48;
    --fw-strong:#000000; --fw-strong-rgb:0,0,0;
    --fw-dim:#5f5b6b; --fw-dim-rgb:95,91,107;
    --fw-brand:#b71fb7; --fw-brand-rgb:183,31,183; --fw-brand-text:#9a189a;
    --fw-link:#1a67b0; --fw-link-rgb:26,103,176;
    --fw-select:rgba(0,0,0,.08); --fw-backdrop:rgba(24,20,34,.6);
    --fw-curve-d:#b71fb7; --fw-curve-nps:#1a6fc0; --fw-curve-vps:#c85f14; --fw-curve-kps:#1e8449;
    --fw-series-a:var(--fw-curve-d); --fw-series-b:#0e8a8a; --fw-series-c:#9a7200;
    --fw-easy:#186f42; --fw-medium:#1f63a8; --fw-hard:#8a5a00; --fw-expert:#c02a4c;
  }
  [data-bs-theme="dark"] {
    --fw-bg:#1a1920; --fw-bg-rgb:26,25,32;
    --fw-bg-raised:#23222b; --fw-bg-raised-rgb:35,34,43;
    --fw-bg-hover:#2c2b36; --fw-bg-hover-rgb:44,43,54;
    --fw-border:#3b3945;
    --fw-text:#e4e2ea; --fw-text-rgb:228,226,234;
    --fw-strong:#ffffff; --fw-strong-rgb:255,255,255;
    --fw-dim:#a3a1ad; --fw-dim-rgb:163,161,173;
    --fw-brand:#b71fb7; --fw-brand-rgb:183,31,183; --fw-brand-text:#e879e8;
    --fw-link:#5eaee8; --fw-link-rgb:94,174,232;
    --fw-select:rgba(255,255,255,.12); --fw-backdrop:rgba(0,0,0,.85);
    --fw-curve-d:#c93cc9; --fw-curve-nps:#3b9ee0; --fw-curve-vps:#e58a3c; --fw-curve-kps:#3db56c;
    --fw-series-a:var(--fw-curve-d); --fw-series-b:#2fc7c7; --fw-series-c:#e6c03f;
    --fw-easy:#7fd8a3; --fw-medium:#8ec0f2; --fw-hard:#f4ad52; --fw-expert:#f78aa0;
  }
  /* Bootstrap reads these for its body, table, form controls, dropdowns and
     borders; bridged once, after both of its theme blocks, so its components
     stand on the page's ground rather than its own greys. */
  :root, [data-bs-theme="light"], [data-bs-theme="dark"] {
    --bs-body-bg:var(--fw-bg); --bs-body-bg-rgb:var(--fw-bg-rgb);
    --bs-body-color:var(--fw-text); --bs-body-color-rgb:var(--fw-text-rgb);
    --bs-emphasis-color:var(--fw-strong); --bs-emphasis-color-rgb:var(--fw-strong-rgb);
    --bs-secondary-color:var(--fw-dim); --bs-secondary-color-rgb:var(--fw-dim-rgb);
    --bs-tertiary-color:var(--fw-dim);
    --bs-secondary-bg:var(--fw-bg-hover); --bs-secondary-bg-rgb:var(--fw-bg-hover-rgb);
    --bs-tertiary-bg:var(--fw-bg-raised); --bs-tertiary-bg-rgb:var(--fw-bg-raised-rgb);
    --bs-border-color:var(--fw-border); --bs-border-color-translucent:var(--fw-border);
    --bs-heading-color:inherit;
    --bs-link-color:var(--fw-link); --bs-link-color-rgb:var(--fw-link-rgb);
    --bs-link-hover-color:var(--fw-link); --bs-link-hover-color-rgb:var(--fw-link-rgb);
    --bs-primary:var(--fw-brand); --bs-primary-rgb:var(--fw-brand-rgb);
  }
  html, body { height:100%; }
  body { font-size:13px; margin:0; display:flex; flex-direction:column; }
  :focus-visible { outline:2px solid var(--fw-brand-text); outline-offset:2px; }
  .fw-wrap tbody tr:focus-visible, .fw-wrap thead th .lbl:focus-visible {
    outline:2px solid var(--fw-brand-text); outline-offset:-2px; }
  .text-secondary { color:var(--fw-dim)!important; }
  .btn-check:checked + .btn, .btn-fw.active { background:var(--fw-brand); border-color:var(--fw-brand); color:#fff; }
  /* Bootstrap bakes its button colours into the compiled CSS rather than reading
     --bs-primary, so overriding that variable alone leaves the buttons blue; the
     focus glow, the checked box and the focused search box are blue there too. */
  .btn-outline-secondary { --bs-btn-color:var(--fw-dim); --bs-btn-border-color:var(--fw-border);
    --bs-btn-hover-color:var(--fw-strong); --bs-btn-hover-bg:var(--fw-bg-hover); --bs-btn-hover-border-color:var(--fw-dim);
    --bs-btn-focus-shadow-rgb:var(--fw-dim-rgb); }
  .btn-outline-primary { --bs-btn-color:var(--fw-brand-text); --bs-btn-border-color:var(--fw-brand);
    --bs-btn-hover-color:#fff; --bs-btn-hover-bg:var(--fw-brand); --bs-btn-hover-border-color:var(--fw-brand);
    --bs-btn-focus-shadow-rgb:var(--fw-brand-rgb); }
  .btn-primary { --bs-btn-bg:var(--fw-brand); --bs-btn-border-color:var(--fw-brand);
    --bs-btn-hover-bg:color-mix(in srgb, var(--fw-brand) 85%, black); --bs-btn-hover-border-color:color-mix(in srgb, var(--fw-brand) 85%, black);
    --bs-btn-focus-shadow-rgb:var(--fw-brand-rgb); }
  .form-control:focus { border-color:var(--fw-brand); box-shadow:0 0 0 .2rem rgba(var(--fw-brand-rgb), .25); }
  .form-check-input:checked { background-color:var(--fw-brand); border-color:var(--fw-brand); }
  .form-check-input:focus { border-color:var(--fw-brand); box-shadow:0 0 0 .2rem rgba(var(--fw-brand-rgb), .25); }
  /* the toast: the page's text on its ground, inverted, in either theme */
  #hint .badge { background:var(--fw-text); color:var(--fw-bg); }
  /* the theme toggle: a small icon button in the brand row; while the theme
     switches (theme.js) nothing fades, so the page changes as one */
  #theme { padding:0 6px; line-height:1.4; font-size:13px; }
  html.theming *, html.theming *::before, html.theming *::after { transition:none!important; }
  .fw-head { flex:0 0 auto; z-index:1030; }
  /* the table's own paint puts the scroller right after every repaint (table.js);
     the browser's scroll anchoring would add its own correction on top */
  .fw-wrap { flex:1 1 auto; min-height:0; overflow:auto; overflow-anchor:none; }
  /* .more is set from scroll.js, only while something is past the right edge */
  .more { mask-image:linear-gradient(to right, #000 calc(100% - 40px), transparent);
    -webkit-mask-image:linear-gradient(to right, #000 calc(100% - 40px), transparent); }
  .fw-foot { flex:0 0 auto; font-size:11px; color:var(--bs-secondary-color); }
  .fw-foot a { color:var(--bs-secondary-color); text-decoration:none; }
  .fw-foot a:hover { color:var(--fw-link); text-decoration:underline; }
  .sep { opacity:.35; margin:0 .35rem; }
  #src2 { display:none; }
  /* an underlined text link, not another chip: it opens an explanation, it does
     not change what the table shows */
  /* the strapline links to the changelog; the dotted underline is what says so,
     in the header and in the footer copy a phone shows (.fw-foot a drops underlines) */
  .fw-head #src a, #src2 a { color:inherit; text-decoration:underline dotted; text-underline-offset:2px; }
  .fw-head #src a:hover, #src2 a:hover { color:var(--bs-body-color); text-decoration:underline dotted; }
  .fw-head .info { background:none; border:0; padding:0; font-size:12px; cursor:pointer;
    color:var(--fw-link); text-decoration:underline; text-underline-offset:2px; }
  .fw-head .info:hover { color:var(--bs-body-color); }
  .beta { font-size:10px; font-weight:600; text-transform:uppercase; letter-spacing:.6px;
    color:var(--fw-brand-text); border:1px solid var(--fw-brand-text); border-radius:10px;
    padding:1px 6px; vertical-align:2px; }
  /* no measure cap: one footer line beats three, and it is a single sentence */
  .fw-foot .beta-note { color:var(--bs-body-color); }
  .fw-foot a.req { color:var(--fw-link); font-weight:600; }
  .fw-foot a.req:hover { color:var(--fw-link); }
  .fw-wrap table { margin-bottom:0; }
  .fw-wrap thead th { position:sticky; top:0; z-index:2; background:var(--bs-tertiary-bg);
    padding:0; font-size:11px; text-transform:uppercase; letter-spacing:.4px; white-space:nowrap; }
  .fw-wrap thead th .thw { display:flex; align-items:center; gap:2px;
    padding:6px 6px 6px 10px; position:relative; }
  .fw-wrap thead th .lbl { cursor:pointer; user-select:none; flex:1;
    overflow:hidden; text-overflow:ellipsis;
    background:none; border:0; padding:0; margin:0; text-align:left;
    color:inherit; font:inherit; letter-spacing:inherit; text-transform:inherit; }
  /* the drag target for column width: invisible until the header is hovered */
  .fw-wrap thead th .rz { position:absolute; top:0; right:0; width:7px; height:100%;
    cursor:col-resize; touch-action:none; opacity:0; background:var(--fw-brand-text); }
  .fw-wrap thead th:hover .rz { opacity:.45; }
  .fw-wrap thead th .rz:hover { opacity:1; }
  body.resizing { cursor:col-resize; user-select:none; }
  .fw-wrap thead th.sorted .lbl, .fw-wrap thead th.filtered .flt { color:var(--fw-brand-text); }
  .fw-wrap thead th.filtered { background:color-mix(in srgb, var(--fw-brand) 14%, var(--fw-bg-raised)); }
  .fw-wrap td { padding:5px 10px; white-space:nowrap; vertical-align:middle; }
  td.num { text-align:right; font-variant-numeric:tabular-nums; }
  /* rank is a view position, not data - keep it narrow and quiet */
  thead th.rank, td.rank { width:1%; }
  td.rank { color:var(--bs-secondary-color); }
  td.code { font-family:var(--bs-font-monospace); color:var(--fw-link); cursor:pointer; }
  td.code:hover { text-decoration:underline; }
  td.title { max-width:300px; white-space:normal; overflow-wrap:break-word; }
  td.song { min-width:150px; }
  /* the link columns: one arrow, the anchor for a row the file knows (a link,
     so the link colour), dim while the file is on its way, nothing for a row
     without the link */
  td.lnkc { text-align:center; padding-left:4px; padding-right:4px; font-size:14px; line-height:1; }
  td.lnkc a.ext { color:var(--fw-link); text-decoration:none; display:inline-block; padding:2px 6px; }
  td.lnkc a.ext:hover { text-decoration:underline; }
  td.lnkc .wait { color:var(--fw-dim); opacity:.5; }
  /* the row open in the details pane: a neutral wash (the colour is the edge,
     as a selection in an editor, so the brand still means only "on") and the
     brand on the left edge; in compare mode every row on the graph wears its
     series colour on that edge (a swatch, never text) with its legend letter
     after the rank, as the song grid's cells do */
  .fw-wrap .table-hover > tbody > tr.sel > * { --bs-table-bg-state: var(--fw-select); }
  .fw-wrap tbody tr.sel > td:first-child { box-shadow:inset 3px 0 0 var(--fw-brand-text), inset 0 0 0 9999px var(--bs-table-bg-state); }
  /* the second shadow is Bootstrap's own cell fill, with its fallback chain: an
     undefined --bs-table-bg-state (a row that is neither hovered nor .sel) would
     void the whole declaration and the edge with it */
  .fw-wrap tbody tr.on > td:first-child { box-shadow:inset 4px 0 0 var(--sc),
    inset 0 0 0 9999px var(--bs-table-bg-state, var(--bs-table-bg-type, var(--bs-table-accent-bg, transparent))); }
  .fw-wrap tbody tr .sl { margin-left:5px; font-size:10px; font-weight:700; font-style:normal; color:var(--bs-body-color); }
  td.artist { max-width:220px; }
  td.album { max-width:220px; }
  /* The four level colours are xlsx_format.py's hue families (green, blue,
     amber, rose), so the site and the spreadsheet agree on which colour means
     which level, saturated for each ground so the four read as four - and worn
     as an outline rather than as a filled block, which stops four saturated
     rectangles per row competing with the song titles. */
  .lvl { background:none; border:1px solid currentColor; font-weight:600; padding:0 7px; }
  .Easy{color:var(--fw-easy)}.Medium{color:var(--fw-medium)}.Hard{color:var(--fw-hard)}.Expert{color:var(--fw-expert)}
  /* D is the number the site exists for; weight says so without a colour ramp.
     Not called .lead - that is a Bootstrap utility and it is 1.25rem. */
  td.headline { font-weight:600; color:var(--bs-emphasis-color); }
  .blank { color:var(--bs-secondary-color); }
  #dd { position:fixed; width:255px; max-height:min(420px,70vh); overflow:auto;
        z-index:1050; text-transform:none; letter-spacing:normal; font-size:12px; }
  #dd .list { max-height:250px; overflow:auto; }
  #dd .form-check { margin-bottom:0; padding:2px 4px 2px 1.6rem; border-radius:4px; }
  #dd .form-check:hover { background:var(--bs-tertiary-bg); }
  #dd .form-check-label { display:flex; width:100%; gap:8px; cursor:pointer; }
  #dd .form-check-label .v { overflow:hidden; text-overflow:ellipsis; white-space:nowrap; }
  #dd .form-check-label .n { margin-left:auto; color:var(--bs-secondary-color); }
  tbody tr { cursor:pointer; }
  /* the two spacer rows standing for the rows not in the DOM (section 17):
     no padding, no border, no hover, their height the estimate of what they stand for */
  .fw-wrap tbody tr.pad { cursor:default; }
  .fw-wrap tbody tr.pad > td { padding:0; border:0; }
  .fw-wrap .table-hover > tbody > tr.pad:hover > * { --bs-table-bg-state:transparent; }
  td.code { font-family:var(--bs-font-monospace); color:var(--bs-secondary-color); }
  td.code .cp { visibility:hidden; margin-left:6px; opacity:.7; }
  tr:hover td.code { color:var(--fw-link); }
  tr:hover td.code .cp { visibility:visible; }
  td.code .cp:hover { opacity:1; }
  #cd { position:fixed; width:230px; max-height:min(420px,70vh); overflow:auto; z-index:1050; font-size:12px; }
  #cd .cc { display:flex; align-items:center; gap:4px; border-radius:4px; }
  #cd .cc:hover { background:var(--bs-tertiary-bg); }
  #cd .cc.dragging { opacity:.4; }
  #cd .cc .grip { cursor:grab; opacity:.6; padding:0 2px; user-select:none; }
  #cd .cc .grip:active { cursor:grabbing; }
  #cd .form-check { flex:1; margin-bottom:0; padding:2px 4px 2px 1.5rem; }
  #about { position:fixed; inset:0; background:var(--fw-backdrop); display:none;
           align-items:center; justify-content:center; z-index:1060; padding:24px; }
  #about.on { display:flex; }
  #about .mcard { max-width:100%; max-height:92vh; overflow:auto; }
  /* The details pane (section 14): a flex sibling under the table, so the table
     shrinks and nothing is positioned over it. It stands on the page's own
     ground, as the canvas does (graph.js paints --fw-bg), so there is one
     background and the graph is not a box. The grip is the top edge; .min is
     the heading alone. */
  .fw-pane { flex:0 0 auto; display:none; flex-direction:column; height:46vh; min-height:0;
    border-top:1px solid var(--bs-border-color); position:relative; }
  .fw-pane.on { display:flex; }
  .fw-pane.min { height:auto!important; }
  .fw-pane .pgrip { flex:0 0 auto; height:9px; cursor:row-resize; touch-action:none;
    display:flex; align-items:center; justify-content:center; background:var(--bs-tertiary-bg); }
  .fw-pane .pgrip span { width:44px; height:3px; border-radius:2px; background:var(--fw-dim); opacity:.75; }
  .fw-pane .pgrip:hover span { background:var(--fw-brand-text); opacity:1; }
  .fw-pane.min .pgrip { cursor:default; }
  body.resizing-v { cursor:row-resize; user-select:none; }
  .fw-pane .pcard { flex:1 1 auto; min-height:0; overflow:auto; scrollbar-gutter:stable; position:relative;
    display:flex; flex-direction:column; padding:8px 16px 10px; }
  .fw-pane.min .pcard > :not(.mhead):not(.pbtns) { display:none; }
  .fw-pane .mhead { padding-right:56px; margin-bottom:4px; flex:0 0 auto; }
  .fw-pane .mmeta, .fw-pane .gtools { flex:0 0 auto; }
  .fw-pane .pbtns { position:absolute; top:4px; right:8px; display:flex; gap:2px; }
  .fw-pane .pbtns button { background:none; border:0; color:var(--fw-dim); line-height:1; padding:0 4px; cursor:pointer; }
  .fw-pane .pbtns .x { font-size:22px; }
  .fw-pane .pbtns .pmin { font-size:11px; }
  .fw-pane .pbtns button:hover { color:var(--bs-body-color); }
  .fw-pane .gtools { margin:2px 0 6px; }
  .fw-pane .gtools a.ext { text-decoration:none; }
  /* Bootstrap gives a disabled button pointer-events:none, which also hides
     its title; the tip is the reason the button is off, so it stays hoverable */
  .fw-pane .gtools button:disabled { pointer-events:auto; cursor:not-allowed; }
  /* the graph beside the song grid when there is room; the graph fills the
     height it is given (graph.js's fill), the grid scrolls on its own */
  .fw-pane .pbody { display:flex; gap:18px; flex:1 1 auto; min-height:0; }
  .fw-pane .gbody { flex:1 1 60%; min-width:0; min-height:0; display:flex; flex-direction:column; }
  .fw-pane .gbody canvas { display:block; width:100%; touch-action:pan-y; border-radius:4px; flex:0 0 auto; }
  .fw-pane .sbody { flex:0 1 400px; min-width:280px; min-height:0; overflow:auto; font-size:12px; }
  .fw-pane .sbody p.meta, .fw-pane .sbody p.also { margin:0 0 6px; font-size:12px; color:var(--fw-dim); }
  .fw-pane .sbody p.also { color:var(--bs-body-color); }
  .sgrid { display:grid; grid-template-columns:auto repeat(4, 1fr); gap:4px; margin-top:6px; font-size:12px; }
  .sgrid .lvlh { text-align:center; font-weight:600; font-size:11px; text-transform:uppercase; letter-spacing:.4px;
    padding:2px 0; }
  .sgrid .inst { display:flex; flex-wrap:wrap; align-items:center; gap:4px 8px; padding:0 8px 0 0; font-weight:600; }
  .sgrid .tier { font-weight:400; color:var(--fw-dim); }
  .sgrid .cmp { background:none; border:1px solid var(--fw-border); border-radius:4px; color:var(--fw-dim); font-size:11px;
    padding:1px 6px; cursor:pointer; }
  .sgrid .cmp:hover { color:var(--fw-strong); border-color:var(--fw-dim); }
  .sgrid .cell { display:flex; flex-direction:column; align-items:center; justify-content:center; min-height:44px;
    border:1px solid var(--bs-border-color); border-radius:6px; background:none; color:var(--bs-body-color);
    font-variant-numeric:tabular-nums; padding:4px 2px; }
  .sgrid button.cell { cursor:pointer; }
  .sgrid button.cell:hover { background:rgba(var(--fw-strong-rgb), .06); }
  .sgrid .cell b { font-weight:600; }
  .sgrid .cell small { color:var(--fw-dim); font-size:11px; }
  .sgrid .cell.here { border-color:var(--fw-brand-text); box-shadow:inset 0 0 0 1px var(--fw-brand-text); }
  .sgrid .cell.none { color:var(--fw-dim); border-style:dashed; }
  /* in compare mode a cell on the graph wears its series colour as a top bar,
     never as text (the series colours are swatches, not words), with its
     legend letter in the corner; the primary keeps the ring as well */
  .sgrid .cell { position:relative; }
  .sgrid .cell.on { border-top:3px solid var(--sc); padding-top:2px; }
  .sgrid .cell.on.here { box-shadow:inset 0 0 0 1px var(--fw-brand-text); }
  .sgrid .cell .sl { font-size:10px; font-weight:700; font-style:normal; color:var(--fw-dim); margin-right:3px; }
  .sgrid button.cell:disabled { cursor:not-allowed; opacity:.55; }
  .sgrid .cmp[aria-pressed="true"] { background:var(--fw-brand); border-color:var(--fw-brand); color:#fff; }
  .mhead .lnk { display:flex; flex-wrap:wrap; align-items:baseline; gap:0; font-size:11px; }
  .mhead .lnk a { white-space:nowrap; }
  .mhead .lnk a { color:var(--fw-link); }
  #about .mcard { max-width:min(680px, 100%); background:var(--bs-body-bg);
    border:1px solid var(--bs-border-color); border-radius:8px; padding:20px 22px; }
  /* the card is wide enough for the video; the prose is not, so it keeps a measure */
  #about .vid { position:relative; aspect-ratio:16/9; margin:.9rem 0 .45rem; }
  #about .vid iframe { position:absolute; inset:0; width:100%; height:100%;
    border:0; border-radius:6px; }
  #about p.cap { font-size:11px; color:var(--fw-dim); }
  #about h2 { font-size:12px; text-transform:uppercase; letter-spacing:.6px;
    color:var(--fw-brand-text); margin:1.1rem 0 .3rem; }
  #about p { margin:0; font-size:13px; line-height:1.55; max-width:62ch; }
  #about .mhead { margin-bottom:0; align-items:center; justify-content:space-between; }
  #about .x { background:none; border:0; color:var(--fw-dim); font-size:22px;
    line-height:1; padding:0 2px; cursor:pointer; }
  #about .x:hover { color:var(--bs-body-color); }
  #about p.more { margin-top:1.4rem; font-size:11px; }
  #about p.more a { color:var(--fw-link); }
  .mhead .rpt { font-size:11px; white-space:nowrap; }
  .mhead .copies { flex-basis:100%; font-size:11px; }
  .mhead .copies a { color:var(--fw-link); }
  .mmeta { display:flex; flex-wrap:wrap; gap:2px 0; font-size:11px; color:var(--fw-dim); margin-bottom:6px; }
  .mmeta b { font-weight:600; color:var(--bs-body-color); }
  .readout { margin:6px 0 2px; font-size:12px; font-variant-numeric:tabular-nums; white-space:pre-wrap;
    min-height:1.2em; }
  .legend { list-style:none; margin:0 0 6px; padding:0; display:flex; flex-wrap:wrap; gap:4px 18px; font-size:11px; }
  .legend li { display:flex; align-items:center; gap:6px; }
  .legend .sw { display:inline-block; width:22px; border-top:2px solid; }
  .legend .sw.dot { border-top-style:dotted; }
  .legend .rm { background:none; border:0; color:var(--fw-dim); font-size:16px; line-height:1; padding:0 4px; cursor:pointer; }
  .legend .rm:hover { color:var(--bs-body-color); }
  .gtools { display:flex; flex-wrap:wrap; gap:6px; margin-top:6px; }
  /* the bar above the table while a chart to compare with is being chosen */
  .fw-pick { flex:0 0 auto; display:flex; flex-wrap:wrap; align-items:center; gap:8px; padding:6px 16px;
    font-size:12px; background:var(--bs-tertiary-bg); border-bottom:1px solid var(--bs-border-color); }
  /* the pane and the explainer share this header, so it is not scoped to either */
  .mhead { display:flex; align-items:baseline; gap:10px; flex-wrap:wrap; margin-bottom:8px; }
  /* under 900px the song grid goes under the graph, which draws at its aspect again */
  @media (max-width:899px) {
    .fw-pane .pbody { flex-direction:column; flex:0 0 auto; }
    .fw-pane .gbody { flex:0 0 auto; }
    .fw-pane .sbody { flex:0 0 auto; min-width:0; overflow:visible; }
  }
  /* narrow screens: tighten everything so the difficulty column is on screen
     without a sideways swipe, and give the strapline its own line */
  @media (max-width:640px) {
    /* The header was four wrapped rows and a quarter of a phone screen. Now it
       is three: the name, then search beside the count, then one strip of
       controls that scrolls sideways rather than wrapping. The strapline moves
       to the footer, where there is room for it. */
    .fw-head { padding-left:.5rem!important; padding-right:.5rem!important; }
    .fw-head #brand { white-space:nowrap; }
    .fw-head #src { display:none; }
    #src2 { display:block; }
    /* the search may not take the whole line, or the count is orphaned onto one
       of its own and the header grows back by a row */
    .fw-head #q { flex:1 1 55%; min-width:0!important; }
    .fw-head #count { order:1; }
    #tools { order:2; flex:1 1 100%; overflow-x:auto; scrollbar-width:none;
      scroll-padding-right:28px; }
    #tools::-webkit-scrollbar { display:none; }
    #tools > * { flex:0 0 auto; }
    /* the strip is short, so its fade is narrower than the table's */
    #tools.more { mask-image:linear-gradient(to right, #000 calc(100% - 34px), transparent);
      -webkit-mask-image:linear-gradient(to right, #000 calc(100% - 34px), transparent); }
    /* the attribution row scrolls sideways too, rather than wrapping to three
       lines and taking the screen back from the table */
    .fw-foot .d-flex { flex-wrap:nowrap!important; overflow-x:auto; scrollbar-width:none; }
    .fw-foot .d-flex::-webkit-scrollbar { display:none; }
    .fw-foot .d-flex > * { flex:0 0 auto; }
    .fw-wrap td { padding:5px 6px; }
    .fw-wrap thead th .thw { padding:6px 4px 6px 6px; gap:0; }
    /* a two-line header costs one row and buys the width that puts the
       difficulty column on screen without a sideways swipe */
    .fw-wrap thead th, .fw-wrap thead th .lbl { white-space:normal; }
    td.title { max-width:128px; }
    td.artist { max-width:100px; }
    td.album { max-width:100px; }
    td.song { min-width:120px; }
    td.num { font-size:12px; }
    /* a 7px drag target is not a touch target, and it would fight the scroll */
    .fw-wrap thead th .rz { display:none; }
    /* the link columns would push D off a phone screen; the pane's tool row
       carries the same links there */
    .fw-wrap th[data-c="Chart"], .fw-wrap th[data-c="Leaderboard"], .fw-wrap td.lnkc { display:none; }
    /* the pane is a bottom sheet under the table, which keeps a few rows; the
       grip drags it taller and the card scrolls */
    .fw-pane { height:44vh; }
    .fw-pane .pcard { padding:6px 8px 8px; }
    .fw-pane .mhead { padding-right:48px; }
    /* the song grid: the instrument heading on its own line, four cells across the card */
    .sgrid { grid-template-columns:repeat(4, 1fr); }
    .sgrid .corner { display:none; }
    .sgrid .inst { grid-column:1 / -1; margin-top:6px; }
  }
  #hint { position:fixed; bottom:16px; left:50%; transform:translateX(-50%);
          z-index:1070; opacity:0; transition:opacity .18s; pointer-events:none; }
  #hint.on { opacity:1; }

  /* The site guide above the footer (section 24): a <details> open in the HTML
     (a crawler, a reader mode, a visitor without scripts get a page) and closed
     before the first paint for the app, where its summary is one line the
     visitor can open; open, it takes at most 45vh and scrolls, so the table
     keeps its room. The tokens are the page's. */
  #static { flex:0 0 auto; border-top:1px solid var(--fw-border); padding:.1rem 1rem; font-size:11px; line-height:1.5; color:var(--fw-text); }
  #static summary { cursor:pointer; color:var(--fw-dim); list-style-position:inside; }
  #static summary:hover { color:var(--fw-text); }
  #static[open] { max-height:45vh; overflow:auto; padding-bottom:1rem; font-size:12px; }
  #static h1 { font-size:1.1rem; font-weight:600; margin:.6rem 0 .5rem; max-width:72ch; }
  #static h2 { font-size:.8rem; font-weight:600; text-transform:uppercase; letter-spacing:.5px; color:var(--fw-brand-text); margin:1.2rem 0 .4rem; }
  #static p { margin:0 0 .6rem; max-width:72ch; }
  #static a { color:var(--fw-link); }
  #static table { border-collapse:collapse; font-size:12px; }
  #static th, #static td { padding:.2rem .8rem .2rem 0; border-bottom:1px solid var(--fw-border); text-align:left; vertical-align:top; }
  #static td.r, #static th.r { text-align:right; }
  #static ul { columns:3; column-gap:2rem; padding-left:1.2rem; margin:0 0 .6rem; }
  #static ul.one { columns:1; }
  @media (max-width: 640px) { #static ul { columns:2; } }
