/* ─────────────────────────────────────────────────────────────────────────────
   curation-page.css — Curation page local styles.

   Ported 2026-08-24 from the operator-approved reference frame
   `claude-design/skills/dc-skill/dc-curation.html` (two feedback rounds). The
   page otherwise composes existing components: `.ig-workspace` / `.ig-rail` /
   `.ig-rail-gutter` (dc-components.css), `dc_table` (dc-table.css), the
   canonical film drawer (drawer.css) and `.dc-pill` (dc-theme.css).

   Only three surfaces are genuinely local and live here:
     1. the playlist rail rows
     2. the weights disclosure row + its toggle
     3. the score / axes cell chrome the two new dc_table formatters emit

   SHARED WITH AVAILS (2026-09-09, feature_avails_intake.md Round 3). The
   Avails page's Votes/Voted-by columns reuse this page's `dcVotes`/
   `dcVoteSort`/`dcPeople` formatters (www/dc/dc-table.js) and, with them,
   the `.cur-vote*`/`.cur-people*` rules below — a Curation restyle of
   either changes Avails silently. `.cur-idc*` (dcFilmPlain) is shared the
   same way. Its own vote-button click listener is scoped to `.cur-page`
   so a vote cast on Avails cannot also land here — see pages/curation.py's
   page script.
   ──────────────────────────────────────────────────────────────────────────── */

/* ── 1 · Playlist rail rows ─────────────────────────────────────────────────
   The rail itself is `.ig-rail`; these are its list items, following the same
   4px state-edge motif every other selectable row in the app uses. */
.cur-plrow {
  padding: 8px 12px;
  border-bottom: 1px solid var(--dc-line);
  border-left: 4px solid transparent;
  cursor: pointer;
}
.cur-plrow:hover { background: var(--dc-panel-2); }
.cur-plrow.is-active {
  background: var(--dc-primary-soft);
  border-left-color: var(--dc-primary);
}
.cur-plrow__name {
  display: block;
  font-size: 13px;
  font-weight: var(--dc-fw-semi);
  color: var(--dc-ink);
}
.cur-plrow__meta {
  font-size: 11px;
  color: var(--dc-faint);
  font-family: var(--dc-font-mono);
}
.cur-plrow__desc {
  display: block;
  font-size: 11px;
  color: var(--dc-muted);
  margin-top: 2px;
}

/* ── 2 · Weights, as a disclosure row under the filter band ─────────────────
   Collapsed is the resting state (operator 2026-08-24): the ranking is the
   page, the knobs that produced it are not. The toggle carries the current
   split as a mono summary so the row only has to be OPENED to change the
   weights, never to read them. */
.cur-wtoggle {
  display: inline-flex; align-items: center; gap: 6px;
  /* Strip-control size (2026-09-14): 30px in the 48px head, 12px label. */
  height: var(--dc-strip-ctl-h); padding: 0 11px;
  border: 1px solid var(--dc-line);
  border-radius: var(--dc-radius);
  background: var(--dc-panel);
  color: var(--dc-muted);
  font-size: var(--dc-fs-sm);
  cursor: pointer;
}
.cur-wtoggle:hover { border-color: var(--dc-line-2); color: var(--dc-ink); }
.cur-wtoggle.is-open {
  background: var(--dc-primary-soft);
  border-color: var(--dc-primary-line);
  color: color-mix(in oklch, var(--dc-primary) 72%, black);
}
.cur-wtoggle .bi-chevron-down { font-size: 9px; transition: transform var(--dc-dur-fast); }
.cur-wtoggle.is-open .bi-chevron-down { transform: rotate(180deg); }

/* The row itself sits in the ACTION register — same 34px band and bottom
   rule as `.ig-rail__filters`, so it lines up with every other strip. */
.cur-weights {
  display: none;
  align-items: center; gap: 16px;
  height: var(--dc-topbar-h); box-sizing: border-box;
  padding: 0 12px;
  border-bottom: 1px solid var(--dc-line);
  background: var(--dc-panel);
  flex: 0 0 auto;
}
.cur-weights.is-open { display: flex; }
.cur-w { display: flex; align-items: center; gap: 6px; }
/* Strip label register (CHEATSHEET §4j) — the weights row is a strip, and its
   axis labels were the last thing in one still shouting in 700-weight
   uppercase. Sentence case also lets them say "Recognition" instead of the
   four-character "reco" that only ever read as an abbreviation because the
   uppercase treatment forced it short. */
.cur-w__lbl {
  font-size: var(--dc-fs-xs); font-weight: var(--dc-fw-normal);
  letter-spacing: normal; text-transform: none;
  color: var(--dc-muted); white-space: nowrap;
}
.cur-w input[type="range"] { width: 70px; accent-color: var(--dc-primary); height: 14px; }
.cur-w__val {
  font-family: var(--dc-font-mono); font-size: 11px;
  color: var(--dc-muted); width: 26px; text-align: right;
}
.cur-weights__end {
  margin-left: auto;
  display: flex; align-items: center; gap: 9px;
  font-size: 11px; color: var(--dc-faint);
  font-family: var(--dc-font-mono);
}

/* Filter band above it — the in-library segmented control. */
/* RETIRED 2026-08-31 (two-pane port). `.cur-filters` was a page-local strip,
   `.cur-seg` a lookalike of `.ig-seg`, and `.cur-count` a hand-styled count.
   The pane heads are `.ig-canvas-head` now and carry the shared `.ig-seg` and
   `.ig-canvas-head__meta` — three page-local components deleted, nothing
   re-declared. */

/* Medium, not bold (operator 2026-08-31). The score should read as the
   strongest NUMBER in the row without competing with the film's title, which
   is the only thing on this page that stays semi-bold. */
.cur-score { font-weight: var(--dc-fw-medium); font-size: 13px; color: var(--dc-ink); }
.cur-score--none { color: var(--dc-faint); font-weight: var(--dc-fw-normal); }
.cur-tier { font-size: 10px; color: var(--dc-faint); margin-left: 4px; }
.cur-bars { display: inline-flex; gap: 1px; height: 15px; align-items: flex-end; width: 50px; }
.cur-bars > i { display: block; flex: 1; background: var(--dc-line-2); border-radius: 1px 1px 0 0; }
.cur-bars > i.on { background: var(--dc-primary); }
/* Hatched, not empty — "no evidence" is not "scored zero". See dcAxes. */
.cur-bars > i.na {
  height: 100% !important;
  background: repeating-linear-gradient(45deg,
    var(--dc-line), var(--dc-line) 2px, transparent 2px, transparent 4px);
}

/* ── Drawer: Playlists section ──────────────────────────────────────────── */
.cur-pl-line { display: flex; align-items: baseline; gap: 8px; font-size: 12.5px; padding: 5px 0; border-bottom: 1px solid var(--dc-line); }
/* Same size and weight as the picker label and the popover rows, so the
   playlist UI reads as one thing wherever it appears. */
.cur-pl-line__name { font-size: 13px; font-weight: var(--dc-fw-normal);
  color: var(--dc-ink); }
.cur-pl-line__meta { color: var(--dc-faint); font-family: var(--dc-font-mono); font-size: 11px; margin-left: auto; }


/* ── 4 · Row height, page-scoped ────────────────────────────────────────────
   The app's dense 34px grid (33px cell + 1px border, `dc-table.css`) assumes
   ONE line of content per cell. This page breaks that assumption on purpose,
   in two columns at once: the Film cell is the two-line identity block
   (international title over original title, operator 2026-08-24) and the Tags
   and Playlists cells hold pills that wrap. At 34px the title's first line was
   clipping into the row above and a three-tag cell was bleeding across two
   neighbours.

   So the height is raised HERE and only here, rather than loosening the global
   grid — every other table in the app still sits in phase with the sidebar
   bands and the drawer sections, which is what that grid buys and what the
   operator approved it for on 2026-07-21.

   Kept FIXED rather than made content-driven: Tabulator's vertical virtual DOM
   assumes uniform row height, and a variable-height table needs its scrolling
   verified at length before it can be trusted. 48px is two 15px lines plus
   padding, which is the tallest cell this page can produce.

   The wider question — whether the global scale is too tight for dense tables
   at all — is the design-system overhaul in docs/Todo.md, not this page. */
/* CONTENT-DRIVEN, not a taller fixed row. A fixed 48px still clipped seven
   cells: a three-tag list wrapping to three lines needs 51px, a long
   co-production country list 72px, and a long title over its original title
   53px. Picking a number tall enough for the worst row wastes the height on
   every other one, which is the same mistake as 34px in the other direction.

   `height: auto` on the cell plus `align-items: stretch` on the row lets the
   tallest cell set the row, which is what the operator asked for on
   2026-08-24: "it should be based on needed height".

   THE CAVEAT, and it is real: Tabulator's vertical virtual DOM is happiest
   with uniform rows. It measures variable ones, but scroll behaviour wants
   checking at LENGTH — this page is 34 rows today and the operator has said
   they routinely work 100+. Verified clean at 34; re-check when a batch that
   size lands, and if it jitters the fallback is a fixed height at the 72px
   worst case rather than reverting to 34. */
/* MOVED to dc-table.css as `.dc-table--gallery` on 2026-08-26. The Library
   table adopted this treatment (operator: match Curation's layout — poster
   left, title and original title stacked), and a row/cell rule that two
   pages share is table styling, not page styling. */
/* NO `display:flex` here. An earlier version set it to stretch the cells, and
   it worked visually while quietly changing the row's hit area — Tabulator
   lays its own cells out, and overriding that left a strip of row that looked
   clickable and was not. The cells already stretch via their own
   `align-items`, so the row only needs a floor. */
.cur-page .dc-table-output .film-cell { align-items: center; }
.cur-page .dc-table-output .tags { row-gap: 2px; }

/* ── 5 · Votes, provenance, and the drawer's Playlists section ───────────── */

/* The vote control. Filled caret = you voted; the voter names live on the
   title attribute, because at 100+ films a name list per row is unreadable
   and the count is what you sort on. */
.cur-vote {
  display: inline-flex; align-items: center; gap: 4px;
  border: 1px solid var(--dc-line); border-radius: var(--dc-radius);
  background: var(--dc-panel); color: var(--dc-muted);
  font-size: 11px; padding: 1px 7px; height: 22px; cursor: pointer;
}
.cur-vote:hover { border-color: var(--dc-primary-line); color: var(--dc-ink); }
.cur-vote.is-mine {
  background: var(--dc-primary-soft);
  border-color: var(--dc-primary-line);
  color: color-mix(in oklch, var(--dc-primary) 72%, black);
  font-weight: var(--dc-fw-semi);
}
.cur-vote__n { font-family: var(--dc-font-mono); }

/* Added by / when. Two lines, the date quieter than the name. */
.cur-added { display: flex; flex-direction: column; line-height: 1.25; }
.cur-added__who { font-size: 12px; color: var(--dc-ink); }
.cur-added__at { font-size: 10.5px; color: var(--dc-faint); font-family: var(--dc-font-mono); }
.cur-added--none { color: var(--dc-faint); }

/* Drawer section — sits above the canonical drawer, same idiom as
   Scheduling's Schedule block. */
.cur-pl-section { padding: 0 var(--dc-space-6) var(--dc-space-4); }
.cur-pl-line--empty { color: var(--dc-faint); font-style: italic; }
.cur-pl-add { display: flex; align-items: center; gap: 6px; margin-top: 8px;
  flex-wrap: wrap; }
/* The reason line (2026-09-08) takes a row of its own under the picker;
   the buttons follow it. */
.cur-pl-add__reason { flex: 1 1 100%; height: 28px; font-size: 12px; }
.cur-pl-add .shiny-input-container { flex: 1 1 auto; margin-bottom: 0; }

/* Search box and Add button pinned to the SAME height (operator 2026-08-25).
   Selectize sizes itself from its own line-height and Bootstrap sizes .btn-sm
   from its padding, so the two arrived at different heights and the row read
   as stepped. Both are pinned to 28px — the app's standard control height,
   the one `.ig-input` uses — so the row is flat whatever either library
   computes.

   Same fix and same reason as `.dc-modal .selectize-input` (dc-components.css),
   and scoped the same way: neither `.btn` nor the global selectize rule is
   touched, so nothing outside this row changes. */
.cur-pl-add .selectize-input {
  box-sizing: border-box;
  min-height: 28px; height: 28px;
  padding: 3px 8px; line-height: 20px;
}
.cur-pl-add .selectize-control.single .selectize-input::after { margin-top: -2px; }
.cur-pl-add .btn {
  box-sizing: border-box;
  height: 28px;
  padding-top: 0; padding-bottom: 0;
  white-space: nowrap; flex: 0 0 auto;
}

/* ── 6 · Poster column, and the strips that must not clip ───────────────── */

/* The poster gets its own column and fills the row's full height (operator
   2026-08-24). Inside the film cell it floated against a two- or three-line
   cell instead of filling it, which is why it moved out. */

.cur-poster {
  display: block; width: 100%; height: 100%;
  /* `contain`, not `cover` (operator 2026-08-25): the whole poster is always
     visible and centred, letterboxed by the cell background when the row is
     taller than a 2:3 crop. `cover` filled the cell but silently cut the top
     and bottom off every poster, which is the one thing a poster column
     exists to show.

     The letterbox is --dc-panel-2 rather than white so it stays correct in
     dark mode; it reads as white space on a light theme. */
  object-fit: contain;
  object-position: center;
  background: var(--dc-panel-2);
}
/* No poster is not a loading failure. 18 of the 34 candidates have none, so
   the empty state has to read as "we do not have one" rather than as broken. */
.cur-poster--none {
  display: flex; align-items: center; justify-content: center;
  width: 100%; height: 100%;
  background: var(--dc-panel-2); color: var(--dc-line-2); font-size: 13px;
}

/* Identity cell without the poster stub (dcFilmPlain). */
.cur-idc { display: flex; flex-direction: column; line-height: 1.3; }
.cur-idc__t { font-weight: var(--dc-fw-semi); color: var(--dc-ink); }
.cur-idc__o { font-size: 11.5px; color: var(--dc-faint); font-style: italic; line-height: 1.35; }

/* The strips share the canvas's width, so they narrow when the drawer opens.
   At 768px the weights row needed 810 and simply clipped its total and Reset
   off the right edge. Two changes: the sliders may shrink, and whatever still
   does not fit scrolls rather than disappearing. Both strips keep their 34px
   band either way, so they stay in phase with the rail's own bands. */
.cur-weights { overflow-x: auto; overflow-y: hidden; scrollbar-width: thin; }
.cur-weights .cur-w { flex: 0 1 auto; min-width: 0; }
.cur-weights .cur-w input[type="range"] { flex: 0 1 70px; min-width: 42px; }
.cur-weights__end { flex: none; }


/* ── Add-to-list, per row (2026-08-25) ──────────────────────────────────────
   The operator's workflow: make a list, go to All films, put films in it from
   there. Before this the only way in was the drawer, which meant opening a
   film to file it — fine for one, wrong for working down a ranked table.

   A bare `.ig-input` select at the table's own 12px, not a button that opens
   a menu: one control, one action. The cell carries `data-dc-no-rowclick`
   (set in the formatter) so using it does not also open the drawer. */
/* RETIRED 2026-08-31. The add-to-list datalist column answered "which
   playlist?" from a one-table page; the right pane answers it by being open,
   so the control collapsed to a single `+` (`.cur-act` below). `dcAddTo` in
   dc-table.js and the `dc_cur_add_row` handler went with it. */

.cur-plrow { position: relative; }
.cur-plrow__del { position: absolute; top: 5px; right: 6px;
  opacity: 0; transition: opacity var(--dc-dur-fast); font-size: 11px; }
.cur-plrow:hover .cur-plrow__del,
.cur-plrow__del:focus-visible { opacity: 1; }
.cur-plrow__del:hover { color: var(--dc-danger); }


/* ═══════════════════════════════════════════════════════════════════════
   TWO-PANE CURATION (2026-08-31) — reference frame `dc-curation-v2.html`.
   The collapsible pane itself is shared (`.ig-pane-edge`, dc-components.css
   + dc-components.js, CHEATSHEET §4k); nothing about it is page-local.
   ═══════════════════════════════════════════════════════════════════════ */

/* A third for the pool, two thirds for the playlist pane (operator
   2026-09-08: "the same 1/3, 2/3 default" as Scheduling) — the playlist pane
   is the one with columns to read. A dragged divider still overrides this
   with an inline width. The drawer is fixed by `.ig-drawer-pane`. */
.cur-page #curPool { flex: 1 1 0; min-width: 300px; }
.cur-page #curList { flex: 2 1 0; min-width: 300px; }

/* ── The playlist picker: the right pane's head ──────────────────────────
   Shell, search and footer are `.dc-hf-pop` from dc-table.css — the console
   has exactly one searchable popover and a second would be a lookalike. Only
   the ROW is page-local: a single-select playlist row is not `.dc-hf-check`.
   The popover is `position: fixed` and placed by the page's JS because
   `.ig-canvas` is `overflow: hidden` and would clip it to the pane. */
.cur-plpick { position: relative; display: flex; align-items: center; min-width: 0; }
/* The inset-pill rule (dc-components.css) sets flex:none; the picker has to
   be allowed to shrink — it is the widest thing in a 300px pane head. */
.cur-plpick__btn { flex: 0 1 auto !important; min-width: 0; max-width: 260px;
  overflow: hidden; justify-content: flex-start !important; gap: 8px !important; }
.cur-plpick__btn > i:first-child, .cur-plpick__btn .bi-chevron-down { flex: none; }
.cur-plpick__btn .bi-chevron-down { font-size: 9px; margin-left: auto; }
/* The pane's NAME is the picker now, so it carries the pane-label weight. */
/* Matches `.cur-plrow__name` — the rows inside the popover it opens
   (operator 2026-08-31: "non bold and smaller just like the elements in the
   actual dropdown"). It was --dc-fw-bold, on the reasoning that the picker had
   become the pane's title and should carry the pane-label weight; next to the
   list it opens, a 700-weight button just read as shouting. */
.cur-plpick__cur { font-size: var(--dc-fs-xs); font-weight: var(--dc-fw-normal);
  color: var(--dc-muted);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cur-plpick .dc-hf-pop { display: none; }
.cur-plpick.is-open .dc-hf-pop { display: block; }
/* .dc-hf-pop carries 6px padding; playlist rows go edge to edge. */
.cur-plpick .cur-plrow { margin: 0 -6px; }

/* Non-tab controls in a strip must opt into centring — the shared guard
   covers `.ig-seg`/`.ig-rail__search-box`/`.ig-canvas-head__meta`, these two
   are page-local species. See CHEATSHEET §4j. */
.ig-canvas-head > .cur-plpick, .ig-canvas-head > .cur-wtoggle { align-self: center; }

/* ── The + / − column. Icon-only, and it EXECUTES: there is no staged
      selection to apply afterwards. A film already in the list shows a tick,
      not a disabled button — a control you can press that does nothing is
      worse than no control. ─────────────────────────────────────────────── */
.cur-act-col { overflow: visible; }
.cur-act { display: flex; align-items: center; justify-content: center; }
.cur-act .dc-iconbtn { width: 22px; height: 22px; }
.cur-act .dc-iconbtn i { font-size: 12px; }
.cur-act__in { color: var(--dc-ok); font-size: 12px; }
.dc-iconbtn--rm:hover { color: var(--dc-danger);
  background: color-mix(in oklch, var(--dc-danger) 12%, transparent); }

/* ── Drag a film from the pool onto the playlist ─────────────────────────
   The whole receiving table is the drop zone. The dashed inset is the only
   dashed border in the console and means exactly one thing. */
.cur-page .tabulator-row.is-dragging { opacity: .45; }
.cur-page .dc-table-output.is-drop { outline: 2px dashed var(--dc-primary);
  outline-offset: -6px; background: var(--dc-primary-soft); }


/* ── THE DRAWER OVERLAYS, IT DOES NOT PUSH (operator 2026-08-31) ──────────
   With two panes plus a drawer, opening the drawer squeezed BOTH tables at
   once — 300px minimum each against a 440px drawer needs 1100px of window
   before anything is readable. Floating it costs the panes nothing: the
   playlist is partly covered while you read a film, and whole again the
   moment you close it.

   `.ig-drawer-pane` is shared with Delivery / Encoding / Intake, so this is
   scoped to `.cur-page` until the operator has seen it here. If it is right,
   it belongs on all four.

   The shadow is legitimate under rule 5 — this is now a genuinely floating
   thing, which is the one case the flat/hairline rule exempts. */
.cur-page { position: relative; --cur-drawer-w: 440px; }

.cur-page .ig-drawer-pane {
  position: absolute; top: 0; right: 0; bottom: 0;
  width: var(--cur-drawer-w);
  z-index: 20;
  background: var(--dc-panel);
  border-left: 1px solid var(--dc-line);
  box-shadow: var(--dc-shadow-lg);
}
/* The gutter rides the drawer's leading edge, so dragging it still resizes
   the drawer — it writes `--cur-drawer-w` (data-width-var) and both this
   rule and the pane above follow. */
.cur-page #curDrawerGutter {
  position: absolute; top: 0; bottom: 0;
  right: var(--cur-drawer-w);
  z-index: 21;
}


/* ═══════════════════════════════════════════════════════════════════════
   PROPOSALS (2026-09-08) — feature_curation_proposals.md.
   Two tiers in the action columns: "+" commits (operator), the lightbulb
   proposes (everyone). The playlist pane's action cell draws by status:
   accept / decline for the operator, withdraw for the proposer. All of it
   is `.cur-act .dc-iconbtn` — the only additions are hover colours that say
   what the click will do, and the picker's open-count badge.
   ═══════════════════════════════════════════════════════════════════════ */
.cur-act__prop { color: var(--dc-muted); font-size: 12px; }
.cur-act__propose:hover { color: var(--dc-primary);
  background: color-mix(in oklch, var(--dc-primary) 12%, transparent); }
.cur-act__ok:hover { color: var(--dc-ok);
  background: color-mix(in oklch, var(--dc-ok) 12%, transparent); }
.cur-act__no:hover { color: var(--dc-danger);
  background: color-mix(in oklch, var(--dc-danger) 12%, transparent); }
.cur-act__undo:hover { color: var(--dc-ink); }
/* Two buttons in a 38px column: tighten. */
.cur-act > .dc-iconbtn + .dc-iconbtn { margin-left: 1px; }

/* Open-count badge on the picker button. NOT `.dc-nav__badge` — that one is
   hidden while the sidebar is collapsed, which it always is. A pill in the
   RUNNING (amber) register: something is waiting on a decision. */
.cur-plpick__n { flex: none; margin-left: 4px; padding: 0 6px; height: 16px;
  line-height: 16px; font-size: 10.5px; }

/* Scope segment inside the popover, under the search box. */
.cur-plpick .dc-hf-pop .ig-seg { margin: 4px 0 6px; }
.cur-plpick .dc-hf-pop .ig-seg > button { padding: 0 9px; height: 22px; }

/* Per-row actions in the picker: was a single trash button (`.cur-plrow__del`,
   above); now a container so a proposed playlist can carry accept / decline
   or withdraw in the same slot. Same show-on-hover behaviour. */
.cur-plrow__acts { position: absolute; top: 4px; right: 6px; display: flex;
  gap: 2px; opacity: 0; transition: opacity var(--dc-dur-fast); }
.cur-plrow:hover .cur-plrow__acts,
.cur-plrow__acts:focus-within { opacity: 1; }
.cur-plrow__acts .dc-iconbtn { width: 20px; height: 20px; }
.cur-plrow__acts .dc-iconbtn i { font-size: 11px; }
.cur-plrow__pill { margin-left: 6px; vertical-align: 1px; }
.cur-plrow__meta .cur-plrow__open { color: var(--dc-warn, #b7791f); }


/* Round-2 feedback (2026-09-08). */
/* Your own pick: the count without the button. */
.cur-vote--own { cursor: default; opacity: .55; }
.cur-vote--own:hover { border-color: var(--dc-line); color: inherit; }
/* Who voted, named under the count. */
.cur-vote__who { display: block; font-size: 10.5px; color: var(--dc-faint);
  font-family: var(--dc-font-mono); white-space: nowrap; overflow: hidden;
  text-overflow: ellipsis; max-width: 118px; margin-top: 1px; }
/* Notes count: the message board is one click away. */
.cur-notes { display: inline-flex; align-items: center; gap: 3px; font-size: 12px;
  color: var(--dc-muted); }
.cur-notes--none { color: var(--dc-faint); opacity: .5; }
.cur-notes__n { font-family: var(--dc-font-mono); font-size: 11px; }
/* The Add-playlist button beside the picker. */
#curPlAdd { flex: none; }


/* Picker popover (2026-09-08 feedback: "show more items, more compact,
   wider and longer"). Placed by the page's JS at up to 560px wide; the list
   runs to most of the viewport; a row is one line: name · meta, with the
   note as a single ellipsised line under it. */
.cur-plpick .dc-hf-pop__list { max-height: min(72vh, 720px); }
.cur-plpick .cur-plrow { padding: 4px 10px; display: grid;
  grid-template-columns: minmax(0, 1fr) auto; column-gap: 10px;
  align-items: baseline; }
.cur-plpick .cur-plrow__name { display: inline; font-size: 12.5px;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.cur-plpick .cur-plrow__meta { white-space: nowrap; padding-right: 66px; }
.cur-plpick .cur-plrow__desc { grid-column: 1 / -1; margin-top: 0;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.cur-plpick .cur-plrow__acts { top: 3px; }

/* Voters, one pill each. */
.cur-people { display: flex; flex-wrap: wrap; gap: 3px; }
.cur-people__pill { display: inline-block; padding: 1px 7px; border-radius: 999px;
  font-size: 11px; line-height: 16px; background: var(--dc-panel-2);
  border: 1px solid var(--dc-line); color: var(--dc-ink); white-space: nowrap; }
.cur-people--none { color: var(--dc-faint); }
