  @font-face {
    font-family: "Ableton Sans Small";
    src: url("fonts/AbletonSansSmall-Regular.ttf") format("truetype");
    font-weight: 300 500; font-style: normal; font-display: swap;
  }
  @font-face {
    font-family: "Ableton Sans Small";
    src: url("fonts/AbletonSansSmall-Bold.ttf") format("truetype");
    font-weight: 600 900; font-style: normal; font-display: swap;
  }
  @font-face {
    font-family: "Ableton Sans Small";
    src: url("fonts/AbletonSansSmall-RegularItalic.ttf") format("truetype");
    font-weight: 300 500; font-style: italic; font-display: swap;
  }
  @font-face {
    font-family: "Ableton Sans";
    src: url("fonts/AbletonSans-Light.ttf") format("truetype");
    font-weight: 200 400; font-style: normal; font-display: swap;
  }

  /* ------------------------------------------------------------------ *
   * Palette lifted verbatim from Live 12's own theme file,
   * Resources/Themes/Default Dark Neutral Medium.ask. The .ask name for
   * each value is kept in the comment so it can be re-derived.
   * ------------------------------------------------------------------ */
  :root {
    color-scheme: dark;
    --vvb: 0px;
    --desktop:   #2a2a2a;   /* Desktop */
    --bg:        #242424;   /* SurfaceArea — the sunk content field */
    --panel:     #363636;   /* SurfaceBackground — chrome: bars, drawers */
    --detail:    #3e3e3e;   /* DetailViewBackground — device panels */
    --highlight: #464646;   /* SurfaceHighlight — hover */
    --sunk:      #1e1e1e;   /* ControlBackground */
    --display:   #181818;   /* DisplayBackground / MeterBackground */
    --line:      #1a1a1a;   /* ~ControlContrastFrame — control framing */
    --line-soft: #2e2e2e;   /* list separators */

    /* Live's text is low-contrast by design, but it carries far less running
       prose than an index does, so the two dimmest tiers are lifted a step. */
    --ink:       #d2d2d2;   /* titles */
    --ctl:       #b5b5b5;   /* ControlForeground — control labels, verbatim */
    --dim:       #8a8a8a;   /* ~TextDisabled #757575, lifted */
    --dimmer:    #6e6e6e;   /* ~ControlFillHandle #5d5d5d, lifted */
    --on-ink:    #070707;   /* ControlOnForeground — text on a lit control */

    /* Live has exactly one chrome accent. Everything that lights up uses it. */
    --chosen:    #ffad56;   /* ChosenDefault */
    --alt:       #03c3d5;   /* ChosenAlternative */
    --play:      #00d38d;   /* ChosenPlay */
    --record:    #ff5559;   /* ChosenRecord */
    --alert:     #e76942;   /* ChosenAlert */
    --select:    #b0ddeb;   /* SelectionBackground */
    --select-fg: #070707;   /* SelectionForeground */
    --standby:   #637e86;   /* StandbySelectionBackground — selected, list unfocused */
    --scroll:    #696969;   /* ScrollbarInnerHandle */

    /* Text tiers re-based for surfaces on --panel/--detail (see below). */
    --ink-panel:    #ededed;
    --ctl-panel:    #cfcfcf;
    --dim-panel:    #b5b5b5;
    --dimmer-panel: #9d9d9d;

    /* Live's Chooser triangle, in ControlForeground. */
    --chooser-arrow: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='7' height='4' viewBox='0 0 7 4'%3E%3Cpath d='M0 0h7L3.5 4z' fill='%23b5b5b5'/%3E%3C/svg%3E");

    /* Device types keep Live's clip palette — that is categorisation, not chrome. */
    --t-instrument: #ffa829;
    --t-audio: #56c0de;
    --t-midi: #b9e44c;
    --t-gen: #c08bf0;
    --t-trans: #ff7f7f;

    --ui:   "Ableton Sans Small", "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
    --sans: var(--ui);
    --mono: var(--ui);  /* Live uses no monospace; tabular figures do the aligning */
    --code: ui-monospace, "Cascadia Mono", Menlo, Consolas, monospace;
  }

  * { box-sizing: border-box; }
  [hidden] { display: none !important; }
  html { background: var(--desktop); }

  body {
    margin: 0;
    background: var(--bg);
    color: var(--ink);
    font: 400 13px/1.45 var(--sans);
    /* Ableton Sans Small replaces the monospace the table used to align on,
       so the figures have to do the aligning themselves. */
    font-variant-numeric: tabular-nums;
    -webkit-font-smoothing: antialiased;
  }

  a { color: inherit; }

  /* ---------- masthead ---------- */

  .masthead {
    position: sticky; top: 0; z-index: 10;
    background: var(--panel);
    border-bottom: 1px solid var(--line);
  }

  .masthead-inner { max-width: 1400px; margin: 0 auto; padding: 18px 18px 16px; }

  .wordmark { display: flex; align-items: baseline; gap: 14px; flex-wrap: wrap; }

  .wordmark h1 {
    margin: 0;
    font: 700 15px/1 var(--mono);
  }

  .tally { font: 400 11px/1.5 var(--mono); color: var(--dim); }
  .tally b { color: var(--ink); font-weight: 600; }

  .viewtabs { display: flex; margin-left: auto; }

  .viewtab {
    font: 500 11px/1 var(--mono);
    padding: 5px 12px;
    background: transparent; color: var(--dim);
    border: 1px solid var(--line); cursor: pointer;
  }
  .viewtab:first-child { border-radius: 2px 0 0 2px; }
  .viewtab:last-child { border-radius: 0 2px 2px 0; }
  .viewtab + .viewtab { border-left: none; }
  .viewtab[aria-pressed="true"] { background: var(--chosen); color: var(--on-ink); }
  .viewtab:hover { color: var(--ink); }

  .controls { display: flex; flex-wrap: wrap; gap: 9px 14px; align-items: flex-start; margin-top: 11px; }
  .controls + .controls { margin-top: 8px; padding-top: 9px; border-top: 1px solid var(--line-soft); }

  .search-wrap { flex: 1 1 220px; min-width: 180px; }

  input[type="search"], input[type="number"], select {
    font: 400 12px var(--sans);
    color: var(--ctl); background: var(--sunk);
    border: 1px solid var(--line); border-radius: 2px;
    padding: 4px 8px; width: 100%;
  }
  /* Live's Chooser: a flat sunken box with a small solid triangle, no OS
     widget, and a highlight only on hover. */
  select {
    width: auto; padding-right: 20px; cursor: pointer;
    appearance: none; -webkit-appearance: none;
    background-image: var(--chooser-arrow);
    background-repeat: no-repeat; background-position: right 7px center;
  }
  select:hover { background-color: var(--highlight); }
  select option { background: var(--panel); color: var(--ctl); }

  /* Live's number box: sunken, centred, no spinners, and dragged rather than
     typed — see bindNumberDrag(). */
  input[type="number"] {
    width: 74px; text-align: center; cursor: ns-resize;
    appearance: textfield; -webkit-appearance: textfield;
  }
  input[type="number"]::-webkit-outer-spin-button,
  input[type="number"]::-webkit-inner-spin-button { -webkit-appearance: none; margin: 0; }
  input[type="number"]:hover { background: var(--highlight); }
  input[type="number"].dragging { background: var(--highlight); color: var(--ink); }

  input:focus-visible, select:focus-visible, button:focus-visible {
    outline: 2px solid var(--select); outline-offset: 1px;
  }
  ::placeholder { color: var(--dimmer); }

  .pills { display: flex; flex-wrap: wrap; gap: 5px; align-items: center; margin: auto; }

  .pill {
    font: 500 11px/1 var(--mono);
    padding: 4px 9px; border-radius: 2px;
    border: 1px solid var(--line); background: transparent; color: var(--dim);
    cursor: pointer;
  }
  .pill:hover { color: var(--ink); border-color: var(--dimmer); }
  .pill[aria-pressed="true"] {
    color: var(--on-ink); background: var(--pc, var(--chosen)); border-color: var(--pc, var(--chosen));
  }
  .pill.cycle[data-state] {
    color: var(--on-ink); background: var(--pc, var(--chosen)); border-color: var(--pc, var(--chosen));
  }
  .pill.cycle[data-state="both"],
  .pill.cycle[data-state="any"] {
    color: var(--dim); background: transparent; border-color: var(--line);
  }
  .pill.cycle[data-state="both"]:hover,
  .pill.cycle[data-state="any"]:hover {
    color: var(--ink); border-color: var(--dimmer);
  }
  .pill[aria-pressed="true"] {
    color: var(--on-ink); background: var(--pc, var(--chosen)); border-color: var(--pc, var(--chosen));
  }
  .custom-floor {
    width: 84px;
  }
  /* Tri-state tag chips: neutral -> include -> exclude -> neutral. */
  .tag-grid {
    display: flex; flex-wrap: wrap; gap: 5px; flex: 1 1 100%; min-width: 0;
    max-height: 340px; overflow-y: auto;
  }
  /* Group label: a full-width run like Live's "Sounds ▾" heading over each chip row. */
  .tg-label {
    flex: 1 1 100%; margin-top: 6px;
    font: 500 10px/1 var(--mono); color: var(--dimmer);
    text-transform: uppercase; letter-spacing: 0.04em;
  }
  .tg-label:first-child { margin-top: 0; }
  .tri-chip {
    display: inline-flex; align-items: center; gap: 6px;
    font: 500 11px/1 var(--mono);
    padding: 5px 8px; border-radius: 3px; cursor: pointer;
    border: 1px solid var(--line); background: transparent; color: var(--dim);
  }
  .tri-chip:hover { color: var(--ink); border-color: var(--dimmer); }
  .tri-chip .tc-n { color: var(--dimmer); font-weight: 400; }
  .tri-chip.inc {
    color: var(--on-ink); background: var(--alt); border-color: var(--alt);
  }
  .tri-chip.inc .tc-n { color: color-mix(in srgb, var(--on-ink) 55%, transparent); }
  .tri-chip.exc {
    color: var(--record); border-color: var(--record); text-decoration: line-through;
  }
  .tri-chip.exc .tc-n { color: var(--record); text-decoration: none; }
  .tag-empty { font: 400 11px/1.5 var(--mono); color: var(--dimmer); }
  .seg.disabled { opacity: 0.4; }
  .active-row { margin-top: 8px; }

  /* Two parts: the body opens the panel at the section that owns the filter,
     the cross clears it. */
  .achip {
    display: inline-flex; align-items: stretch;
    border: 1px solid var(--line); border-radius: 2px; overflow: hidden;
  }
  .achip-body, .achip-x {
    font: 500 11px/1 var(--mono);
    padding: 5px 8px; white-space: nowrap;
    background: transparent; border: none; color: var(--dim); cursor: pointer;
  }
  .achip-body:hover, .achip-x:hover { color: var(--ink); background: var(--highlight); }
  .achip-x { border-left: 1px solid var(--line); color: var(--dimmer); }

  .field {
    display: inline-flex; align-items: center; gap: 7px;
    font: 400 11px/1 var(--mono);
    color: var(--dim); white-space: nowrap;
  }
  .field input[type="checkbox"] { accent-color: var(--chosen); margin: 0; }
  .field:hover { color: var(--ink); }

  .sep { width: 1.5px; height: 18px; background: var(--line); }

  .ghost {
    font: 500 11px/1 var(--mono);
    padding: 5px 10px; border: 1px solid var(--line); border-radius: 2px;
    background: transparent; color: var(--dim); cursor: pointer;
  }
  .ghost:hover { color: var(--ink); background: var(--highlight); }

  /* Sort lives in the toolbar, not the table header, so it works in Cards and
     Uploaders too. */
  .sortbar { display: inline-flex; align-items: center; gap: 7px; }
  .sortbar select { max-width: 150px; }
  .sort-dir { padding: 5px 9px; line-height: 1; }
  .sort-help { width: 100%; font: 400 11px/1.5 var(--mono); color: var(--dimmer); }
  .search-hint {
    display: block; margin-top: 4px;
    font: 400 11px/1.4 var(--mono); color: var(--dimmer);
    overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
  }

  /* Overflow menu — view and output options, which were never filters. */
  .overflow { position: relative; display: inline-flex; }
  .menu {
    position: absolute; top: calc(100% + 6px); right: 0; z-index: 25;
    min-width: 180px; padding: 6px;
    display: flex; flex-direction: column; gap: 2px;
    background: var(--panel); border: 1px solid var(--line); border-radius: 2px;
    box-shadow: 0 12px 28px rgba(0, 0, 0, 0.45);
  }
  .menu-item {
    display: flex; align-items: center; gap: 9px; width: 100%;
    font: 500 11px/1 var(--mono);
    padding: 8px 10px; border: none; border-radius: 3px;
    background: transparent; color: var(--dim); cursor: pointer; text-align: left;
  }
  .menu-item:hover { color: var(--ink); background: var(--highlight); }
  .menu-item input[type="checkbox"] { accent-color: var(--chosen); margin: 0; }
  .menu-sep { height: 1px; background: var(--line); margin: 4px 2px; }
  .menu-select select { margin-left: auto; max-width: 150px; font-size: 11px; padding: 3px 18px 3px 6px; }

  .filter-toggle { margin-left: auto; }
  .filter-toggle[aria-pressed="true"] { color: var(--on-ink); background: var(--chosen); }

  /* ---------- segmented controls ---------- */
  .seg {
    display: inline-flex; align-items: stretch;
    border: 1px solid var(--line); border-radius: 2px; overflow: hidden;
  }
  .seg-btn {
    font: 500 11px/1 var(--mono);
    padding: 5px 9px; white-space: nowrap;
    background: transparent; color: var(--dim);
    border: none; cursor: pointer;
  }
  .seg-btn + .seg-btn { border-left: 1px solid var(--line); }
  .seg-btn:hover { color: var(--ink); background: var(--highlight); }
  .seg-btn[aria-pressed="true"] { color: var(--on-ink); background: var(--sc, var(--chosen)); }
  /* A neutral state (Both / Any) is selected but isn't narrowing anything, so it
     reads as a plain selection rather than one of the accent colours. */
  .seg-btn.neutral[aria-pressed="true"] { color: var(--ink); background: var(--highlight); }
  .seg-btn:focus-visible { outline-offset: -2px; }

  /* ---------- filter panel ---------- */

  /* A right-hand drawer on desktop, a bottom sheet on a phone. It lives outside
     the masthead so opening it never changes --headh. */
  .filter-backdrop {
    position: fixed; inset: 0 var(--vvb) var(--vvb) 0; z-index: 19;
    background: rgba(0, 0, 0, 0.55);
    opacity: 0; visibility: hidden;
    transition: opacity 180ms ease, visibility 0s linear 180ms;
  }
  .filter-backdrop.open {
    opacity: 1; visibility: visible;
    transition: opacity 180ms ease, visibility 0s;
  }
  @media (min-width: 761px) { .filter-backdrop { display: none; } }

  .filter-panel {
    position: fixed; top: 0; right: var(--vvb); bottom: var(--vvb); z-index: 20;
    width: 320px; max-width: 100vw;
    display: flex; flex-direction: column;
    background: var(--panel); border-left: 1px solid var(--line);
    box-shadow: -12px 0 32px rgba(0, 0, 0, 0.35);
    transform: translateX(100%); visibility: hidden;
    transition: transform 180ms ease, visibility 0s linear 180ms;
  }
  .filter-panel.open {
    transform: none; visibility: visible;
    transition: transform 180ms ease, visibility 0s;
  }
  /* Content shrinks rather than hides under the drawer, so the stats panels
     re-measure at their real width. */
  body.panel-open { padding-right: 320px; }
  @media (max-width: 1000px) {
    .filter-panel { width: 280px; }
    body.panel-open { padding-right: 280px; }
  }

  /* Wide screens dock the panel on the left as a permanent column, the way
     Live keeps its browser: no shadow, no overlay, and the Info View sits at
     the foot of the column with the status bar beneath both. */
  @media (min-width: 1200px) {
    .filter-panel {
      left: 0; right: auto; width: 320px;
      border-left: none; border-right: 1px solid var(--line); box-shadow: none;
      transform: translateX(-100%);
    }
    body.panel-open { padding-right: 0; padding-left: 320px; }
    body.panel-open.info-open .filter-panel { bottom: calc(217px + var(--vvb)); }
    body.panel-open .infoview { width: 320px; border-right: none; }
    /* The count sits in the status bar and nothing needs closing, so the
       footer only appears when it has a filter to clear. */
    body.panel-open .fp-foot:has(.fp-apply[data-act="close"]) { display: none; }
  }

  .fp-head {
    display: flex; align-items: center; gap: 9px;
    padding: 14px; border-bottom: 1px solid var(--line);
  }
  .fp-head h2 {
    margin: 0; font: 700 12px/1 var(--mono);
  }
  .fp-count {
    font: 600 11px/1 var(--mono);
    color: var(--on-ink); background: var(--chosen);
    border-radius: 2px; padding: 4px 7px;
  }
  .fp-head .ghost { margin-left: auto; }
  .fp-close {
    flex: none; width: 26px; height: 26px;
    background: transparent; border: 1px solid var(--line); border-radius: 3px;
    color: var(--dim); cursor: pointer; font: 400 14px/1 var(--sans);
  }
  .fp-close:hover { color: var(--ink); background: var(--highlight); }

  .fp-body { flex: 1 1 auto; overflow-y: auto; overscroll-behavior: contain; padding: 0 14px; }

  .fp-sec + .fp-sec { border-top: 1px solid var(--line-soft); }
  .fp-sec-head {
    display: flex; align-items: center; gap: 8px; width: 100%;
    padding: 11px 0; background: none; border: none; cursor: pointer;
    font: 500 11px/1 var(--mono);
    color: var(--dim); text-align: left;
  }
  .fp-sec-head:hover { color: var(--ink); }
  .fp-dot { width: 6px; height: 6px; border-radius: 50%; background: var(--chosen); flex: none; }
  .fp-caret {
    margin-left: auto; color: var(--dimmer); font-size: 9px;
    transition: transform 140ms ease;
  }
  .fp-sec-head[aria-expanded="true"] .fp-caret { transform: rotate(90deg); }

  .fp-sec-body { display: flex; flex-wrap: wrap; gap: 9px; align-items: center; padding: 0 0 14px; }

  /* Collections: Live's browser sidebar rows — a small coloured square, the
     name, and the lit row in the selection colour. */
  .collections { display: flex; flex-direction: column; gap: 1px; width: 100%; }
  .collection {
    display: flex; align-items: center; gap: 9px; width: 100%;
    padding: 6px 8px; border: none; border-radius: 2px;
    background: transparent; color: var(--ctl); cursor: pointer; text-align: left;
    font: 500 11px/1 var(--mono);
  }
  .collection:hover { background: var(--highlight); color: var(--ink); }
  .collection[aria-pressed="true"] { background: var(--select); color: var(--select-fg); }
  .col-swatch { flex: none; width: 9px; height: 9px; border-radius: 1px; }
  .col-count { margin-left: auto; font-weight: 400; opacity: 0.7; }
  .filter-field {
    display: flex; flex-direction: column; align-items: flex-start; gap: 7px;
    flex: 1 1 100%; min-width: 0;
  }
  .filter-field > .field { color: var(--dimmer); }
  .fp-sec-body .pills { margin: 0; }
  .filter-field select { width: 100%; }
  .fp-hint { font: 400 11px/1.5 var(--mono); color: var(--dimmer); flex: 1 1 100%; min-width: 0; }

  .fp-foot {
    border-top: 1px solid var(--line); padding: 11px 14px 13px;
    display: flex; flex-direction: column; gap: 9px; background: var(--panel);
  }
  .fp-apply {
    width: 100%; padding: 10px; border-radius: 3px; cursor: pointer;
    font: 600 11px/1 var(--mono);
    background: var(--chosen); color: var(--on-ink); border: 1px solid var(--chosen);
  }
  .fp-apply:hover { filter: brightness(1.08); }
  .fp-apply[data-act="clear"] {
    background: transparent; color: var(--record); border-color: var(--record);
  }

  @media (max-width: 760px) {
    .filter-panel {
      top: 56px; left: 0; width: auto;
      border-left: none; border-top: 1px solid var(--line);
      border-radius: 12px 12px 0 0;
      transform: translateY(100%);
    }
    .filter-panel.open { transform: none; }
    body.panel-open { padding-right: 0; }

    /* Masthead: wordmark and tally share one line, the mode tabs take the next. */
    .masthead-inner { padding: 11px 12px 12px; }
    .wordmark { flex-wrap: wrap; row-gap: 9px; column-gap: 10px; }
    .wordmark h1 { font-size: 13px; }
    .tally { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
    .viewtabs { margin-left: 0; width: 100%; }
    .viewtab { flex: 1 1 0; min-height: 38px; }

    /* The active chips are the only persistent filter display, so they scroll
       sideways rather than stacking the masthead ever taller. */
    .active-row { flex-wrap: nowrap; }
    #activeChips {
      flex-wrap: nowrap; overflow-x: auto; scroll-snap-type: x proximity;
      padding-bottom: 2px;
    }
    #activeChips > * { flex: none; scroll-snap-align: start; }

    /* 44px minimum on everything you can hit. */
    .menu-item { min-height: 38px; }
    .pill, .seg-btn, .ghost, .tri-chip, .get, .tag-chip, .achip-body, .achip-x, .fp-close {
      min-height: 38px;
      display: inline-flex; align-items: center; justify-content: center;
    }
    .fp-sec-head { min-height: 42px; }
    .fp-apply { min-height: 42px; }
    input[type="search"], input[type="number"], select { min-height: 38px; }
    .field input[type="checkbox"] { width: 20px; height: 20px; }
    .tag-grid { max-height: 46vh; }
  }

  /* ---------- table ---------- */

  main { max-width: 1400px; margin: 0 auto; padding: 0 18px; }

  .colhead {
    display: grid; grid-template-columns: var(--cols); gap: 12px;
    align-items: center;
    padding: 7px 12px;
    font: 500 11px/1.2 var(--mono);
    color: var(--ctl);
    border-bottom: 1px solid var(--line);
    position: sticky; top: var(--headh, 140px);
    background: var(--panel); z-index: 5;
  }

  .colhead > span {
    display: flex;
    align-items: center;
    min-height: 20px;
  }

  .colhead .sortable {
    background: none; border: none; padding: 0; margin: 0;
    font: inherit; color: inherit; cursor: pointer; text-align: inherit;
    letter-spacing: inherit; text-transform: inherit;
    line-height: 1;
  }
  .colhead .sortable:hover { color: var(--ink); }
  .colhead .sortable[data-on="1"] { color: var(--chosen); }
  .colhead .r {
    text-align: center;
    justify-content: center;
  }
  .col-more {
    background: none; border: 1px solid transparent; border-radius: 2px;
    padding: 2px 6px; color: var(--dim); cursor: pointer;
    font: 500 13px/1 var(--mono);
  }
  .col-more:hover, .col-more[aria-expanded="true"] { color: var(--ink); background: var(--highlight); }
  .col-menu { min-width: 150px; }

  .row {
    position: relative;
    display: grid; grid-template-columns: var(--cols); gap: 12px;
    align-items: center; padding: 5px 12px;
    border-bottom: 1px solid var(--line-soft);
  }

  /* Meter: whatever metric is currently ranked, drawn behind the row. */
  .row::before {
    content: ""; position: absolute; inset: 0 auto 0 0;
    width: calc(var(--meter, 0) * 100%);
    background: linear-gradient(90deg,
      color-mix(in srgb, var(--row-color, var(--chosen)) 10%, transparent),
      color-mix(in srgb, var(--row-color, var(--chosen)) 3%, transparent));
    border-left: 2px solid color-mix(in srgb, var(--row-color, var(--chosen)) 55%, transparent);
    pointer-events: none; transition: width 140ms ease-out;
  }
  .row[data-nometer="1"]::before { display: none; }
  .row:hover { background: var(--highlight); }

  /* The metric tracks are fixed-width and need ~680px between them. When the
     filter drawer — or just a narrow window — squeezes the content below that,
     the one flexible track is the device name, so the name is what collapses,
     down to a character per line. Past that point lift the name onto its own
     line above the metrics instead. Both the column head and the rows switch
     together and auto-place identically, so the columns stay aligned under
     their headings.

     Keyed off the content width rather than the viewport, so it responds to
     the drawer opening as well as to the window resizing. */
  main { container-type: inline-size; }

  /* 860px is where the name track drops under ~180px and the title starts
     wrapping to three lines; below that, stacking is strictly more readable. */
  @container (max-width: 860px) {
    .colhead, .row {
      grid-template-columns: var(--cols-stack, var(--cols));
      column-gap: 9px; row-gap: 4px;
    }
    .colhead > .c-name,
    .row > .c-info { grid-column: 1 / -1; grid-row: 1; }
    .row > .c-info { padding-bottom: 2px; }
    /* The heading now sits over the full-width name rather than over a column. */
    .colhead > .c-name { padding-bottom: 3px; border-bottom: 1px solid var(--line-soft); }
  }

  /* Live's selection bar: SelectionBackground with dark text, every tier
     re-based so the byline and figures stay legible on the light bar. */
  .row.selected, .colhead .row.selected {
    background: var(--select);
    --ink: var(--select-fg); --ctl: var(--select-fg);
    --dim: color-mix(in srgb, var(--select-fg) 78%, var(--select));
    --dimmer: color-mix(in srgb, var(--select-fg) 62%, var(--select));
    --line: color-mix(in srgb, var(--select-fg) 30%, var(--select));
    --highlight: color-mix(in srgb, var(--select-fg) 12%, var(--select));
    color: var(--ink);
  }
  .row.selected::before { display: none; }
  .row.selected .num.measured { text-decoration-color: var(--select-fg); }
  .row.selected .dl-badge { color: var(--select-fg); border-color: var(--line); }
  .device-card.selected { border-color: var(--select); box-shadow: 0 0 0 1px var(--select) inset; }

  /* ---------- info view + status bar ---------- */

  /* Live's Info View is a fixed box at the bottom of the browser column, not a
     tooltip: it never moves, never covers the pointer, and stays populated
     with the last thing you touched. Long descriptions scroll normally. */
  .infoview {
    position: fixed; left: 0; bottom: calc(25px + var(--vvb)); z-index: 34;
    width: 340px; max-width: 100vw; height: 192px;
    display: flex; gap: 10px; padding: 9px 10px;
    background: var(--panel);
    border-top: 1px solid var(--line); border-right: 1px solid var(--line);
    overflow: hidden;
    transform: translateZ(0); contain: layout paint;
  }
  .infoview[hidden] { display: none; }
  .iv-thumb {
    flex: none; width: 102px; height: 68px; border-radius: 2px;
    background: var(--display); overflow: hidden; display: block;
  }
  .iv-thumb img { width: 100%; height: 100%; object-fit: cover; display: block; }
  .iv-text { flex: 1 1 auto; min-width: 0; overflow-y: auto; display: block; padding-right: 4px; }
  .iv-scroll { display: block; }
  .iv-title { display: block; font: 600 12px/1.35 var(--ui); color: var(--ink); }
  .iv-meta  { display: block; font: 400 11px/1.4 var(--ui); color: var(--dim); }
  .iv-body  { display: block; font: 400 11px/1.5 var(--ui); color: var(--ctl); margin-top: 3px; white-space: pre-line; }
  .iv-tags  { display: block; margin-top: 5px; }
  .iv-tag {
    display: inline-block; margin: 0 3px 3px 0;
    font: 500 10px/1 var(--ui); padding: 3px 5px; border-radius: 2px;
    color: var(--on-ink); background: var(--dimmer);
  }
  .iv-devtag {
    display: inline-block; margin: 0 3px 3px 0;
    font: 400 10px/1 var(--ui); padding: 2px 5px; border-radius: 2px;
    color: var(--ctl); border: 1px solid var(--line);
  }

  .statusbar {
    position: fixed; left: 0; right: var(--vvb); bottom: var(--vvb); z-index: 35;
    display: flex; align-items: center; gap: 12px;
    height: 25px; padding: 0 10px;
    background: var(--panel); border-top: 1px solid var(--line);
    font: 400 11px/1 var(--ui); color: var(--ctl);
    white-space: nowrap;
    transform: translateZ(0); contain: layout paint;
  }
  .statusbar .tally {
    flex: 1 1 auto; min-width: 0; font: inherit; color: var(--ctl);
    overflow: hidden; text-overflow: ellipsis;
  }
  .statusbar b { color: var(--ink); font-weight: 600; }
  .sb-right { flex: none; color: var(--dim); }

  /* The (i) at the far left of Live's status bar. Lit in ChosenDefault while
     the Info View is showing, dropped to the disabled grey when it is hidden. */
  .sb-info {
    flex: none; display: inline-flex; align-items: center; justify-content: center;
    width: 18px; height: 18px; margin-left: -3px; padding: 0;
    border: 0; border-radius: 2px; background: transparent; cursor: pointer;
    color: var(--dim);
  }
  .sb-info svg { display: block; }
  .sb-info svg circle { fill: currentColor; }
  .sb-info svg path { fill: var(--panel); }
  .sb-info[aria-pressed="true"] { color: var(--chosen); }
  .sb-info:hover { background: var(--highlight); }
  .sb-info:focus-visible { outline: 1px solid var(--chosen); outline-offset: 1px; }

  /* Nothing should end up permanently underneath either bar. */
  main { padding-bottom: 148px; }

  @media (max-width: 760px) {
    .infoview, .sb-info { display: none; }
    main { padding-bottom: 54px; }
  }

  .tag-chip {
    font: 500 11px/1 var(--mono);
    padding: 3px 6px; border-radius: 2px; color: var(--dim);
    border: 1px solid var(--line); background: transparent; cursor: pointer;
    white-space: nowrap;
  }
  .tag-chip:hover { color: var(--ink); border-color: var(--dimmer); }

  .card-list {
    display: grid; grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
    gap: 16px; padding-top: 14px;
  }
  .device-card {
    display: flex; flex-direction: column; gap: 10px; min-height: 100%;
    padding: 12px; border: 1px solid var(--line); border-radius: 3px;
    background: var(--detail);
    transition: border-color 120ms ease, background 120ms ease;
  }
  .device-card:hover { border-color: var(--dimmer); background: var(--highlight); }
  .device-card .card-image { width: 100%; aspect-ratio: 3 / 2; object-fit: cover; border-radius: 2px; background: var(--sunk); }
  .device-card .card-title { font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
  .device-card .card-title:hover { text-decoration: underline; }
  .device-card .card-meta { color: var(--dim); font-size: 12px; }
  .device-card .card-desc { color: var(--dimmer); font-size: 12px; line-height: 1.4; display: -webkit-box; -webkit-line-clamp: 3; line-clamp: 3; -webkit-box-orient: vertical; overflow: hidden; }
  .device-card .card-footer { margin-top: auto; display: flex; flex-wrap: wrap; gap: 6px; align-items: center; color: var(--dim); font: 500 11px/1 var(--mono); }
  .device-card .card-pill {
    display: inline-block; padding: 3px 6px; border-radius: 2px; color: var(--on-ink); background: var(--dimmer);
    font: 500 11px/1 var(--mono);
  }

  /* The text tiers above are set for the dark content field (SurfaceArea).
     Live's device panels are the lightest surface on screen, so anything
     sitting on --detail needs its tiers re-based or the prose disappears. */
  .device-card, .kpi, .panel, .infoview, .note,
  .masthead, .filter-panel, .menu, .statusbar, .colhead {
    --ink: var(--ink-panel);
    --ctl: var(--ctl-panel);
    --dim: var(--dim-panel);
    --dimmer: var(--dimmer-panel);
  }

  .shot {
    width: 100%; aspect-ratio: 3 / 2; object-fit: cover;
    background: var(--sunk); border-radius: 2px; display: block;
  }

  .title { font-weight: 600; text-decoration: none; overflow-wrap: anywhere; }
  .title:hover { text-decoration: underline; }
  .ver { color: var(--dim); font: 400 11px var(--mono); }

  .byline { color: var(--dim); font-size: 12px; margin-top: 1px; }
  .byline a { text-decoration: none; }
  .byline a:hover { text-decoration: underline; color: var(--ink); }
  .byline .chip {
    font: 400 10px var(--mono); color: var(--dimmer);
    border: 1px solid var(--line); border-radius: 2px; padding: 1px 4px; margin-left: 6px;
  }

  .desc {
    color: var(--dimmer); font-size: 12px; margin-top: 3px;
    display: -webkit-box; -webkit-line-clamp: 2; line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;
  }

  .tags { display: flex; flex-wrap: wrap; gap: 4px; align-items: center; margin: auto; }
  .c-get { justify-self: center; margin: auto; }
  .tag {
    font: 500 11px/1 var(--mono);
    padding: 3px 6px; border-radius: 2px; color: var(--on-ink); background: var(--dimmer);
    white-space: nowrap;
  }

  .num { font: 500 13px var(--mono); text-align: center; }
  .num.zero, .num.none { color: var(--dimmer); }
  .num.none { font-size: 11px; }
  /* Estimated rather than measured — the caveat has to survive on a phone,
     where a title attribute is invisible. */
  /* Almost every rate is an estimate, so the exception worth marking is the
     handful that were actually measured between two crawls. */
  .num.measured { text-decoration: underline solid var(--chosen); text-underline-offset: 3px; }
  .num .sub { display: block; font: 400 10px var(--mono); color: var(--dimmer); margin-top: 1px; }
  .date { font: 400 11px var(--mono); color: var(--dim); text-align: center; }
  .date .sub { display: block; color: var(--dimmer); font-size: 10px; margin-top: 1px; }

  .stars { font: 500 13px var(--mono); text-align: center; white-space: nowrap; }
  .stars .votes { color: var(--dimmer); font-size: 10px; display: block; margin-top: 1px; }
  .stars.unrated { color: var(--dimmer); font-size: 11px; font-weight: 400; }

  .get {
    font: 500 11px/1 var(--mono);
    padding: 5px 10px; border: 1px solid var(--line); border-radius: 2px;
    background: transparent; color: var(--dim); cursor: pointer;
    white-space: nowrap; text-decoration: none; display: inline-block;
  }
  /* Nearly every row is hosted, so hosted is the neutral case and gets Live's
     ordinary framed button. The accent stays reserved for things that are on. */
  .get.hosted { color: var(--ctl); border-color: var(--line); }
  .get.hosted:hover { color: var(--ink); background: var(--highlight); }
  .get.got { color: var(--dimmer); border-color: var(--line); }
  .get.got:hover { color: var(--ink); border-color: var(--dimmer); }
  .get:hover { background: var(--highlight); color: var(--ink); }
  .get form { margin: 0; }

  .dl-badge {
    display: inline-block; vertical-align: middle; margin-left: 6px;
    font: 500 11px/1 var(--mono);
    padding: 2px 5px; border-radius: 2px;
    color: var(--chosen); border: 1px solid color-mix(in srgb, var(--chosen) 30%, transparent);
  }
  .row.downloaded .title,
  .row.downloaded .byline { opacity: 0.45; }
  .device-card.downloaded .card-title,
  .device-card.downloaded .card-meta { opacity: 0.45; }

  .uploader-name {
    font-weight: 600; background: none; border: none; padding: 0;
    color: var(--ink); font-size: 14px; cursor: pointer; text-align: left;
    font-family: var(--sans);
  }
  .uploader-name:hover { text-decoration: underline; }

  /* ---------- states ---------- */

  .note {
    border: 1px solid var(--line); border-radius: 3px; background: var(--panel);
    padding: 22px; margin-top: 28px; max-width: 640px;
  }
  .note h2 { margin: 0 0 10px; font: 600 12px/1 var(--mono); }
  .note p { margin: 0 0 12px; color: var(--dim); }
  .note code {
    font: 400 12px var(--code); background: var(--sunk); padding: 2px 5px;
    border-radius: 2px; color: var(--chosen);
  }

  .banner {
    margin-top: 14px; padding: 9px 12px;
    border: 1px solid var(--line); border-left: 2px solid var(--alert);
    border-radius: 2px; background: var(--panel);
    font: 400 11px/1.6 var(--mono); color: var(--dim);
  }
  .banner b { color: var(--alert); font-weight: 600; }
  .banner code { font-family: var(--code); color: var(--chosen); background: var(--sunk); padding: 1px 4px; border-radius: 2px; }

  .end {
    text-align: center; padding: 24px;
    font: 400 11px var(--mono); color: var(--dimmer);
  }

  .drag-lit { outline: 2px dashed var(--select); outline-offset: -8px; }

  @media (max-width: 900px) {
    .colhead { display: none; }
    .row {
      grid-template-columns: 60px 1fr auto;
      grid-template-areas: "shot info get";
      row-gap: 6px;
    }
    .row .c-shot { grid-area: shot; }
    .row .c-info { grid-area: info; min-width: 0; }
    .row .c-get  { grid-area: get; }
    .row > :not(.c-shot):not(.c-info):not(.c-get) { display: none; }
    .inline-meta {
      display: flex; gap: 10px; flex-wrap: wrap; align-items: center; margin-top: 5px;
      font: 500 11px var(--mono); color: var(--dim);
    }
  }
  @media (min-width: 901px) { .inline-meta { display: none; } }
  @media (prefers-reduced-motion: reduce) { * { transition: none !important; } }

  /* ---------- stats ---------- */

  .stats-wrap {
    display: grid; grid-template-columns: repeat(auto-fit, minmax(min(380px, 100%), 1fr));
    gap: 14px; padding-top: 16px;
  }
  .stats-note {
    grid-column: 1 / -1;
    font: 400 11px/1.5 var(--mono); color: var(--dimmer);
  }
  .kpis {
    grid-column: 1 / -1;
    display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: 14px;
  }
  .kpi {
    border: 1px solid var(--line); border-radius: 3px;
    background: var(--detail);
    padding: 12px 14px; min-width: 0;
  }
  .kpi .k-label {
    font: 500 11px/1.3 var(--mono);
    color: var(--dim);
  }
  /* Live sets its large read-outs in the Light cut of Ableton Sans. */
  .kpi .k-value {
    font: 300 27px/1.2 "Ableton Sans", var(--ui); margin-top: 5px; color: var(--ink);
  }
  .kpi .k-sub { font: 400 11px/1.5 var(--mono); color: var(--dimmer); margin-top: 2px; overflow-wrap: anywhere; }

  .panel {
    border: 1px solid var(--line); border-radius: 3px;
    background: var(--detail);
    padding: 14px; min-width: 0;
  }
  .panel.wide { grid-column: 1 / -1; }
  .panel h3 {
    margin: 0 0 3px;
    font: 600 12px/1 var(--mono);
  }
  .panel .p-sub { font: 400 11px/1.5 var(--mono); color: var(--dimmer); margin-bottom: 10px; }
  .panel svg { display: block; width: 100%; height: auto; }
  .panel svg [data-tip]:hover { filter: brightness(1.18); }

  .legend { display: flex; flex-wrap: wrap; gap: 5px 14px; margin-top: 9px; }
  .legend .li {
    display: inline-flex; align-items: center; gap: 6px;
    font: 500 11px/1 var(--mono);
    color: var(--dim);
  }
  .legend .sw { width: 9px; height: 9px; border-radius: 2px; flex: none; }

  .hbar {
    display: grid; grid-template-columns: minmax(80px, 10%) 1fr auto;
    gap: 10px; align-items: center; padding: 4px 0;
  }
  .hbar .hb-label {
    font: 500 11px/1.3 var(--mono);
    color: var(--dim); text-align: right;
    overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
  }
  .hbar .hb-track { height: 12px; background: var(--sunk); border-radius: 2px; overflow: hidden; }
  .hbar .hb-fill { display: block; height: 100%; border-radius: 2px 3px 3px 2px; }
  .hbar .hb-val { font: 500 11px/1 var(--mono); white-space: nowrap; }
  .hbar .hb-val .pct { color: var(--dimmer); font-weight: 400; }

  .cmp-table { width: 100%; border-collapse: collapse; }
  .cmp-table th {
    font: 500 11px/1.3 var(--mono);
    color: var(--dim); text-align: right; padding: 4px 0 6px; font-weight: 500;
  }
  .cmp-table th:first-child { text-align: left; }
  .cmp-table td {
    font: 500 12px/1.3 var(--mono); text-align: right; padding: 5px 0;
    border-top: 1px solid var(--line-soft);
  }
  .cmp-table td:first-child {
    font: 500 11px/1.3 var(--mono);
    color: var(--dim); text-align: left;
  }
  .cmp-table td .sub2 { display: block; font: 400 10px var(--mono); color: var(--dimmer); }

  .db-track { position: relative; height: 12px; background: var(--sunk); border-radius: 2px; }
  .db-center { position: absolute; left: 50%; top: -2px; bottom: -2px; width: 1px; background: var(--dimmer); }
  .db-fill { position: absolute; top: 0; bottom: 0; border-radius: 2px; }

  .chart-tip {
    position: fixed; z-index: 50; pointer-events: none;
    background: var(--display); border: 1px solid var(--line); border-radius: 2px;
    padding: 7px 9px; font: 400 11px/1.55 var(--mono); color: var(--ink);
    opacity: 0; transition: opacity 100ms ease; max-width: 280px;
  }
  .chart-tip.show { opacity: 1; }
  .chart-tip b { color: var(--chosen); font-weight: 600; }

  /* ---------- scrollbar ---------- */
  /* Live's scrollbars are a plain grey handle on a transparent track — the
     accent is reserved for things that are switched on. */
  :root {
    scrollbar-width: thin;
    scrollbar-color: var(--scroll) transparent;
  }
  ::-webkit-scrollbar { width: 8px; height: 8px; }
  ::-webkit-scrollbar-track { background: transparent; }
  ::-webkit-scrollbar-thumb {
    background: var(--scroll);
    border-radius: 2px;
    border: 2px solid transparent; background-clip: padding-box;
  }
  ::-webkit-scrollbar-thumb:hover { background-color: var(--dim); }

  /* ---------- back to top ---------- */
  .back-to-top {
    position: fixed; bottom: calc(133px + var(--vvb)); right: calc(22px + var(--vvb)); z-index: 30;
    width: 34px; height: 34px; border-radius: 50%;
    background: var(--panel); border: 1px solid var(--line);
    color: var(--dim); cursor: pointer;
    display: flex; align-items: center; justify-content: center;
    font: 500 15px/1 var(--sans);
    box-shadow: 0 4px 18px rgba(0,0,0,0.35);
    opacity: 0; transform: translateY(10px); pointer-events: none;
    transition: opacity 200ms ease, transform 200ms ease,
                border-color 200ms ease, color 200ms ease, box-shadow 200ms ease;
  }
  .back-to-top.visible { opacity: 1; transform: translateZ(0); pointer-events: auto; }
  .back-to-top:hover {
    color: var(--ink);
    border-color: var(--chosen);
    box-shadow: 0 0 0 1px var(--chosen), 0 4px 18px rgba(0,0,0,0.35);
  }

  @media (max-width: 760px) { .back-to-top { bottom: calc(38px + var(--vvb)); } }

  /* filter count badge */
  .filter-toggle b { color: var(--chosen); font-weight: 700; }