/* Monitor surfaces that used to ship as <style id="monitor-extra-css">
   appended by js/views/monitor.js. scripts/build.mjs ensure: monitor-extra
   hashes this file and links it AFTER every other sheet — the cascade
   position that <style> had — so equal-specificity rules still win.
   Dev, with no hashed link yet, appends <link href="styles/monitor-extra.css">.
   Where views-monitor.css set the same property, this sheet won; those
   declarations are merged here and deleted there. Properties only the
   earlier sheet set are merged in too, because nothing between the two
   sheets targets these selectors.
   Do not converge: --mon-1 chart surfaces, the #ff2828 trace-dot fallback,
   canvas domain colours, series palettes, Leaflet overlays, and print
   --paper-* stay literal. Breakpoints are --bp-phone / --bp-narrow; var()
   cannot go inside @media, so the queries repeat those px values. */

.m-subhdr .m-back svg{transform:translateX(-1px)}
.m-aggdot{width:22px;height:22px;border-radius:50%;border:1px solid transparent;background:transparent;cursor:pointer;display:inline-flex;align-items:center;justify-content:center;flex:none;padding:0}
.m-aggdot::after{content:'';width:10px;height:10px;border-radius:50%}
.m-aggdot.ok::after{background:var(--live);box-shadow:0 0 8px var(--live)}
.m-aggdot.stale::after{background:var(--warn);box-shadow:0 0 8px var(--warn-dim)}
.m-aggdot.err::after{background:var(--danger-strong);box-shadow:0 0 8px rgba(225,19,19,.6)}
.m-aggdot.none::after{background:var(--text-faint)}
.m-aggdot:hover{border-color:var(--border)}
.m-role{color:var(--warn);font-size:var(--fs-9);letter-spacing:.08em}
.m-modewrap{margin-left:12px;display:flex;align-items:center}
.m-tabghost{font-family:var(--font-ui);font-size:var(--fs-12);padding:6px 12px;border:none;background:transparent;color:var(--text-faint);cursor:not-allowed;border-radius:var(--r-sm)}
.m-countbtn{position:relative;width:auto;padding:0 9px;gap:5px}
.m-countbtn .cnt{font-family:var(--font-mono);font-size:var(--fs-10);color:var(--accent-text)}
.m-iconbtn[disabled]{opacity:.5;cursor:not-allowed}

/* Settings overlay — centered popup; the event header is raised above the
   backdrop (z-index in JS) so it stays visible + clickable. Backdrop/×/Esc/tab
   close it. */
.m-settings-backdrop{position:fixed;inset:0;z-index:var(--z-backdrop);background:rgba(0,0,0,0.55);display:flex;align-items:flex-start;justify-content:center;padding:60px 16px 24px;overflow:auto}
.m-settings-panel{width:min(920px,100%);max-height:calc(100dvh - 84px);background:var(--bg-1);border:1px solid var(--border);border-radius:var(--r-lg);box-shadow:0 24px 64px rgba(0,0,0,.55);display:flex;flex-direction:column;overflow:hidden}
.m-settings-head{flex:none;display:flex;align-items:center;gap:10px;padding:12px 16px;border-bottom:1px solid var(--border-subtle)}
.m-settings-head .h{flex:1;font-size:var(--fs-14);font-weight:700;color:var(--text-1)}
.m-settings-body{min-height:0;overflow:auto}
.m-settings-body .settings-view{padding-top:1rem}
.m-settings-stale{margin:12px 16px 0;padding:8px 12px;border:1px solid var(--warn);border-radius:var(--r-sm);background:var(--warn-dim);color:var(--text-1);font-size:var(--fs-12);line-height:1.45}

/* scan-review banner */
.m-scanbanner{display:flex;align-items:center;gap:10px;padding:9px 16px;background:var(--warn-dim);border-bottom:1px solid var(--warn);color:#fde68a;font-size:var(--fs-12-5)}
.m-scanbanner .i{font-size:var(--fs-14)}
.m-scanbanner .spacer{margin-left:auto}

/* mode bodies */
.m-livechrome{flex:1;min-height:0;display:flex;flex-direction:column;gap:6px}
.m-lazycard{background:var(--mon-1);border:1px solid var(--border-subtle);border-radius:var(--r-md);padding:20px}
.m-lazycard .h{font-weight:600;color:var(--text-1);margin-bottom:6px}
.m-lazycard .p{color:var(--text-muted);font-size:var(--fs-12-5);margin-bottom:12px;line-height:1.5}

/* chart-wrap-outer + custom scrollbar */
.m-chart-wrap-outer{flex:1;min-height:0;position:relative;display:flex;gap:6px}
/* At 1× the chart panel is height-constrained; the host wrappers must carry that
   flex height down to .m-chartwrap so Chart.js fits the panel instead of sizing
   the canvas from its 2:1 aspect. >1× (.accented) opts out → natural height + scroll. */
.m-chartpanel:not(.accented) .m-chart-hostwrap,
.m-chartpanel:not(.accented) .m-chart-host{display:flex;flex-direction:column;flex:1 1 0;min-height:0}
.m-scrollhost{flex:1;min-height:0;min-width:0;max-height:none;display:flex;flex-direction:column;gap:6px;overflow:visible;padding-right:14px;scrollbar-width:none}
.m-scrolltrack{position:relative;top:0;right:0;width:8px;height:100%;background:var(--mon-0);border-left:1px solid #1c1c1c;border-radius:var(--r-pill);z-index:var(--z-float);user-select:none;cursor:pointer;display:none;flex:none}
.m-scrollthumb{position:absolute;left:1px;right:1px;background:var(--border-strong);border-radius:var(--r-pill);min-height:28px;cursor:grab}
.m-scrollthumb:hover{background:var(--text-faint)}

/* panel label group dots */
.m-labelgrp{display:flex;align-items:center;gap:7px;min-width:0}
.m-toggledot{width:13px;height:13px;border-radius:50%;border:1.5px solid var(--text-faint);background:transparent;cursor:pointer;flex:none;padding:0}
/* Fine pointer: the dot stays 13px. ::before is the 24px hit target. */
button.m-toggledot{position:relative}
button.m-toggledot::before{content:'';position:absolute;top:50%;left:50%;width:24px;height:24px;transform:translate(-50%,-50%)}
/* "on" dot fills with the trace's own color (--dot-color, set inline per source
   from SOURCE_COLORS) so the legend dot matches that trace's line. The inline
   value overrides the per-class var() fallback (live → green, max → red). */
.m-toggledot.on.live{background:var(--dot-color,var(--live));border-color:var(--dot-color,var(--live));box-shadow:0 0 6px var(--dot-color,var(--live))}
.m-toggledot.on.max{background:var(--dot-color,#ff2828);border-color:var(--dot-color,#ff2828);box-shadow:0 0 6px var(--dot-color,#ff2828)}
.m-toggledot:disabled{opacity:.35;cursor:not-allowed}
/* Touch: the 13px dot is the whole hit area. An invisible 44x44 overlay (::before,
   so the dot and the layout stay exactly as-is) makes it tappable. A live+max pair sits
   20px apart (13px dot + 7px gap), so two centred 44px boxes would overlap: the live
   overlay reaches left and the max overlay right, meeting at the midpoint of the gap
   (each still 44 wide). Buttons only - the Replay header dot is a non-interactive span.
   The overlays reach over the neighbouring source names, so the name is stacked above
   them: a tap on a name must not toggle the next source's live line. */
@media (pointer:coarse), (max-width:760px){
  button.m-toggledot{position:relative}
  button.m-toggledot::before{content:'';position:absolute;top:50%;left:-15px;width:44px;height:44px;transform:translateY(-50%)}
  button.m-toggledot.live::before{left:-27px}
  button.m-toggledot.max::before{left:-3px}
  .m-labelgrp .m-srcname{position:relative;z-index:var(--z-local)}
}
.m-panelctrls{display:flex;align-items:center;gap:6px;flex-wrap:wrap}
.m-cyc-lab{font-variant-numeric:tabular-nums}
.m-overload-chip{border:0;cursor:pointer;font-family:var(--font-ui);font-size:var(--fs-11);font-weight:600;padding:2px 8px;line-height:1.4;white-space:nowrap}
.m-overload-chip[hidden]{display:none}
.m-overload-pop{max-width:280px;font-size:var(--fs-12);line-height:1.45}
.m-overload-pop-title{font-weight:600;color:var(--warn);margin-bottom:4px}
.m-overload-pop p{margin:0}
/* Per-trace header span/height cyclers — the shared .chip primitive (border /
   pill radius / accent .active state) at a compact mono header metric. Height is
   normalized to the header row by the .m-panelhdr .m-panelcyc rule in views-monitor.css. */
.m-panelcyc{display:inline-flex;align-items:center;gap:5px;padding:0 10px;font-family:var(--font-mono);font-size:var(--fs-11);font-weight:600}
.m-panelcyc svg{display:block;flex:none}
/* Jump input + freq-history caret joined (no gap) into one boxed control on the
   shared input/.select tokens (--bg-input, --border, --r-sm); accent border on
   focus. Height comes from the shared .m-panelhdr row rule so it lines up. */
.m-paneljump{display:flex;align-items:stretch;gap:0}/* stretch, NOT center: the ▾ button has no vertical padding (font-size:11px;line-height:1), so centering left it 13px tall beside a 24px input — measured. It LOOKED full-height because the input next to it is, but ~5.5px above and below was dead container space, so a click aimed slightly high or low hit nothing and the arrow appeared to work only sometimes. Stretch makes the hit target 24px (312 -> 577 px²). */
.m-paneljump .m-jump{border-radius:var(--r-sm) 0 0 var(--r-sm)}
.m-histtoggle{background:var(--bg-input);border:1px solid var(--border);border-left:none;color:var(--text-2);border-radius:0 var(--r-sm) var(--r-sm) 0;padding:0 8px;cursor:pointer;font-size:var(--fs-11);display:inline-flex;align-items:center;line-height:1}
.m-histtoggle:hover{color:var(--text-1)}
.m-paneljump:focus-within .m-jump,.m-paneljump:focus-within .m-histtoggle{border-color:var(--accent)}

/* trim grip */
.m-trimgrip{position:absolute;top:0;right:0;width:14px;height:100%;display:flex;align-items:center;justify-content:center;cursor:ns-resize;z-index:var(--z-grip)}
.m-trimgrip.off{cursor:not-allowed;opacity:.4}
.m-trimgrip .gripline{width:3px;height:30px;border-radius:3px;background:var(--text-faint)}
.m-trimgrip:hover .gripline{background:var(--warn)}

/* sources popover */
.m-sources{min-width:340px;max-width:440px}
.m-sources-head{display:flex;align-items:center;margin-bottom:10px}
.m-sources-head .h{font-weight:600;color:var(--text-1)}
.m-sheet-x{margin-left:auto;background:none;border:none;color:var(--text-muted);cursor:pointer;font-size:var(--fs-13)}
.m-sources-grid{display:flex;flex-direction:column;gap:2px}
/* Device group header: match the 4px horizontal inset of .m-sources-hdr /
   .m-sources-row below it (it had margin but no padding, so it sat flush against
   the popover edge while every row was inset — the "text edge" report). */
.m-sources-dev{font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted);margin:8px 0 3px;padding:0 4px}
.m-sources-dev:first-child{margin-top:0}
/* ONE column template for the group row, the header row and every trace row:
   tick · NAME · LIVE · MAX · STATUS · DETECT · REC. */
.m-sources{--src-cols:18px minmax(0,1fr) 26px 26px 58px 34px 22px;--src-gap:9px}
/* Group headers: "Your view" over tick … MAX, nothing over STATUS (information,
   not a setting), "For everyone" over DETECT + REC. A bracket line under each
   label shows the span. */
.m-sources-grp{display:grid;grid-template-columns:var(--src-cols);gap:var(--src-gap);padding:0 4px 3px;font-family:var(--font-mono);font-size:var(--fs-8-5);letter-spacing:.09em;text-transform:uppercase;font-weight:600}
.m-sources-grp>span{white-space:nowrap;padding-bottom:2px;border-bottom:1px solid currentColor;text-align:center;min-width:0}
.m-sources-grp .g-view{grid-column:1 / 5;color:var(--text-2);text-align:left}
.m-sources-grp .g-none{grid-column:5 / 6;border-bottom-color:transparent}
.m-sources-grp .g-all{grid-column:6 / 8;color:var(--accent-text);letter-spacing:.02em}
/* DETECT switch — a pill with a knob; accent-filled when on, like REC's red
   dot. .ro = read-only (reader / observer): no pointer, dimmed. */
.m-detsw{width:30px;height:16px;border-radius:var(--r-pill);border:1px solid var(--border);background:var(--mon-2);cursor:pointer;flex:none;padding:0;position:relative}
.m-detsw .k{position:absolute;top:2px;left:2px;width:10px;height:10px;border-radius:50%;background:var(--text-faint);transition:left .12s}
.m-detsw.on{background:var(--accent-soft,rgba(80,160,255,.25));border-color:var(--accent)}
.m-detsw.on .k{left:16px;background:var(--accent);box-shadow:0 0 5px var(--accent)}
.m-detsw.ro{cursor:default;opacity:.55}
.m-detsw.busy{opacity:.6;cursor:progress}
.m-detsw:focus-visible{outline:none;box-shadow:var(--ring)}
/* Column-header row labelling the dot columns (NAME · LIVE · MAX · STATUS · REC),
   matching the live app. Same grid template as .m-sources-row so they align. */
.m-sources-hdr{display:grid;grid-template-columns:var(--src-cols);gap:var(--src-gap);padding:0 4px 5px;margin-bottom:3px;border-bottom:1px solid var(--border-subtle);font-family:var(--font-mono);font-size:var(--fs-8-5);letter-spacing:.09em;text-transform:uppercase;color:var(--text-muted)}
.m-sources-hdr>*{justify-self:center;white-space:nowrap}
.m-sources-hdr>:nth-child(2){justify-self:start}
.m-sources-row{display:grid;grid-template-columns:var(--src-cols);align-items:center;gap:var(--src-gap);padding:6px 4px;border-radius:var(--r-sm)}
.m-sources-row>:nth-child(n+3){justify-self:center}
.m-sources-row:hover{background:var(--bg-raised)}
.m-sources-row .nm{min-width:0}
.m-sources-row .nm .tn{font-size:var(--fs-12-5);color:var(--text-1)}
.m-sources-row .nm .chips{display:flex;gap:4px;margin-top:3px;flex-wrap:wrap}
.m-bandchip{font-family:var(--font-mono);font-size:var(--fs-8-5);letter-spacing:.04em;color:var(--text-muted);border:1px solid var(--border);border-radius:var(--r-sm);padding:1px 5px;background:var(--mon-2)}
.m-stepchip[hidden]{display:none}
.m-stepchip.coarse{color:var(--warn);border-color:var(--warn)}
.m-dt-approx{font-family:var(--font-mono);font-weight:700;font-size:var(--fs-12-5);color:var(--warn);cursor:help;margin-right:-2px}
.m-status{display:inline-flex;align-items:center;gap:5px;background:none;border:1px solid transparent;border-radius:var(--r-sm);cursor:pointer;padding:3px 6px;font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-2)}
.m-status:hover{border-color:var(--border)}
.m-status .d{width:7px;height:7px;border-radius:50%}
.m-status.up .d{background:var(--live);box-shadow:0 0 5px var(--live)}
.m-status.down .d{background:var(--danger-strong)}
.m-status.stale .d{background:var(--warn)}
.m-status.badge{text-transform:none;letter-spacing:0;background:none;padding:3px 6px}
.m-status .badge-dot{animation:none}
.m-status.paused .d{background:var(--warn)}
.m-status.muted .d{background:var(--text-muted)}
.m-status.away .d{background:var(--text-faint)}
.m-status.flat .d{width:9px;height:3px;border-radius:1px;background:var(--warn)}
.m-status.silent .d{background:transparent;box-shadow:inset 0 0 0 1.5px var(--danger-strong)}
.m-recdot{width:18px;height:18px;border-radius:50%;border:1px solid var(--border);background:transparent;cursor:pointer;flex:none;padding:0;position:relative}
.m-recdot::after{content:'';position:absolute;inset:4px;border-radius:50%;background:var(--text-faint)}
.m-recdot.on::after{background:var(--danger-strong);box-shadow:0 0 5px var(--danger-strong)}
.m-sources-sub{font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-muted);margin-top:10px}

/* status detail + aggregate health */
.m-statusdetail,.m-aggpop{min-width:260px}
.m-statusdetail .h,.m-aggpop .sum{font-weight:600;color:var(--text-1);margin-bottom:8px}
.m-statusdetail .kv{display:grid;grid-template-columns:auto 1fr;gap:4px 12px;font-family:var(--font-mono);font-size:var(--fs-11)}
.m-statusdetail .kv .k{color:var(--text-muted)}
.m-statusdetail .kv .v{color:var(--text-1);text-align:right}
.m-agg-grid{display:grid;grid-template-columns:auto 1fr auto auto;gap:6px 12px;font-size:var(--fs-11-5);align-items:center}
.m-agg-grid .hh{font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:.08em;text-transform:uppercase;color:var(--text-muted)}
.m-agg-grid .sc{display:inline-flex;align-items:center;gap:6px;font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-2)}
.m-agg-grid .nm{color:var(--text-1)}
.m-agg-grid .ls{font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-muted)}
.m-agg-empty,.m-statdot.down{}
.m-statdot.down{background:var(--danger-strong)}
.m-statdot.flat{width:9px;height:3px;border-radius:1px;background:var(--warn)}
.m-statdot.silent{background:transparent;box-shadow:inset 0 0 0 1.5px var(--danger-strong)}
.m-statdot.away{background:var(--text-faint)}

/* listen popover + floating panel */
.m-listenpop{min-width:300px}
.m-listenpop .h{font-weight:600;color:var(--text-1);margin-bottom:10px}
.m-listenpop .empty{color:var(--text-muted);font-size:var(--fs-12);line-height:1.5}
.m-listenrow{display:flex;align-items:center;gap:10px;width:100%;text-align:left;background:var(--bg-input);border:1px solid var(--border);border-radius:var(--r-sm);padding:8px 10px;margin-bottom:6px;cursor:pointer}
.m-listenrow:hover{border-color:var(--accent)}
.m-listenrow .ic{font-size:var(--fs-16)}
.m-listenrow .n{color:var(--text-1);font-size:var(--fs-12-5)}
.m-listenrow .s{color:var(--text-muted);font-size:var(--fs-10-5);font-family:var(--font-mono);margin-top:2px}
.m-listenrow .st{color:var(--ok);font-size:var(--fs-10-5);font-family:var(--font-mono);margin-top:2px}
.m-listenrow .st .rec{color:var(--danger);font-weight:700}

/* pin/watch popover */
.m-pinwatch{display:inline-flex;align-items:center;gap:1px;margin-left:6px;vertical-align:middle}
.m-pinwatch .pw{display:inline-flex;align-items:center;justify-content:center;width:24px;height:22px;background:none;border:1px solid transparent;border-radius:var(--r-sm);cursor:pointer;color:var(--text-2);padding:3px;line-height:0;opacity:.6;transition:.13s}
.m-pinwatch .pw svg{display:block;width:13px;height:13px}
.m-pinwatch .pw:hover{opacity:1;color:var(--text-1);background:var(--bg-raised);border-color:var(--border)}
.m-pinwatch .pw.is-on{opacity:1;color:var(--accent-text);border-color:var(--accent-soft);background:var(--accent-soft)}
.m-pinwatch .pw:disabled{opacity:.35;cursor:default}
.m-pw-pop{display:flex;flex-direction:column;gap:var(--s2);min-width:250px}
.m-pw-pop .h{font-weight:600;font-size:var(--fs-13);color:var(--text-1);padding-bottom:var(--s2);border-bottom:1px solid var(--border-subtle);margin-bottom:8px}
.m-pw-pop .rad{display:flex;flex-direction:column;gap:4px;margin-bottom:8px}
.m-pw-pop .radrow{display:flex;align-items:center;gap:8px;padding:4px 5px;border-radius:var(--r-sm);font-size:var(--fs-12);color:var(--text-1);cursor:pointer}
.m-pw-field{display:flex;align-items:center;gap:8px;font-size:var(--fs-12);color:var(--text-1);margin:8px 0}
.m-num{background:var(--bg-input);border:1px solid var(--border);color:var(--text-1);border-radius:var(--r-sm);padding:4px 7px;font-family:var(--font-mono);font-size:var(--fs-11);width:74px}
.m-num.sm{width:62px}
.m-detsettings .hint{font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-muted);line-height:1.5;margin-top:6px}
.m-pw-pop .hint{font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-muted);line-height:1.5;font-style:italic;margin:6px 0 0 5px}

/* freq history dropdown */
.m-histdrop{min-width:280px}
.m-histdrop .sec-h{font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted);margin:10px 2px 4px}
.m-histdrop .sec-h:first-child{margin-top:0}
.m-histdrop .empty{font-size:var(--fs-11);color:var(--text-muted);padding:2px 4px}
.m-histrow{display:flex;align-items:center;gap:8px;padding:4px;border-radius:var(--r-sm)}
.m-histrow:hover{background:var(--bg-raised)}
.m-histrow .star{font-size:var(--fs-11)}
.m-histrow .lbl{flex:1;text-align:left;background:none;border:none;color:var(--text-1);font-family:var(--font-mono);font-size:var(--fs-11);cursor:pointer;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.m-histrow .age{font-family:var(--font-mono);font-size:var(--fs-10);color:var(--text-muted)}
.m-histrow .rm{background:none;border:none;color:var(--text-muted);cursor:pointer;font-size:var(--fs-11)}
.m-histsave{display:flex;gap:6px;margin-top:10px;padding-top:8px;border-top:1px solid var(--border-subtle)}
.m-histsave .m-jump{flex:1;width:auto}

/* marker info popup — fully styled in styles/views-monitor.css (.popover--marker
   / .m-markerinfo). The old baseline rules that lived here were removed so that
   stylesheet is the single source (they collided with it at equal specificity
   on .mi-field, muting the marker-colored "pops" look). */

/* details summary styling for the marker-info popup (the View ▾ menu's lists
   became unfolding section rows with spec D/E and no longer use <details>) */
.m-viewdetails{border-top:1px solid var(--border-subtle);margin-top:6px;padding-top:4px}
.m-viewdetails summary{font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted);cursor:pointer;padding:4px 2px;list-style:none}
.m-viewdetails summary::-webkit-details-marker{display:none}
.m-viewdetails summary::before{content:'▸ ';color:var(--text-muted)}
.m-viewdetails[open] summary::before{content:'▾ '}

/* detection-settings popover */
.m-detsettings{min-width:260px}
.m-detsettings .h{font-weight:600;color:var(--text-1);margin-bottom:10px}
.m-detsettings .fld{margin-bottom:10px}
.m-detsettings .fld .lab{display:flex;justify-content:space-between;font-size:var(--fs-11-5);color:var(--text-2);margin-bottom:5px}
.m-detsettings .fld .lab .val{color:var(--warn)}
.m-detsettings .divider{height:1px;background:var(--border-subtle);margin:10px 0}

/* detection pane strip extras */
/* select-all sits in the checkbox <th scope="col">; no horizontal padding so its checkbox
   shares the exact left offset of the per-row .m-check checkboxes below it. */
.m-selall{display:inline-flex;align-items:center;justify-content:flex-start;min-height:24px;padding:0;margin:0}
.m-panebar-right-inner .m-iconbtn{width:26px;height:26px}

/* ── Table controls: status multi-toggle chips (inline pane bar) ─────────────── */
.m-statuschip{padding:3px 9px;font-size:var(--fs-11);line-height:1.3;font-weight:600;display:inline-flex;align-items:center;gap:5px;white-space:nowrap}
.m-statuschip:not(.active){color:var(--text-muted)}

/* ── Table controls: per-column header (label · sort glyph · funnel) ─────────── */
.m-th-inner{display:inline-flex;align-items:center;gap:4px;min-height:24px}
.m-dt th.num .m-th-inner{justify-content:flex-end}
.m-th-inner .lbl{white-space:nowrap;line-height:1;display:inline-flex;align-items:center}
/* sort glyph: dim ↥↧ when idle, single accent arrow when active */
.tc-sort{background:none;border:none;cursor:pointer;padding:4px 3px;line-height:1;min-width:24px;min-height:24px;display:inline-flex;align-items:center;justify-content:center;font-size:var(--fs-18);font-weight:700;color:var(--text-muted);letter-spacing:-2px;font-family:var(--font-mono);transition:color .12s}
.tc-sort:hover{color:var(--text-2)}
.tc-sort.active{color:var(--accent-text);letter-spacing:normal}
/* funnel: ghost icon, fills with accent when a filter is set on the column */
.m-th-funnel{background:none;border:none;cursor:pointer;padding:4px 2px;min-width:24px;min-height:24px;display:inline-flex;align-items:center;justify-content:center;color:var(--text-muted);transition:color .12s}
.m-th-funnel svg{width:14px;height:14px}
.m-th-funnel:hover{color:var(--text-2)}
.m-th-funnel.on{color:var(--accent-text)}
.m-th-funnel.on svg path{fill:color-mix(in srgb,var(--accent) 22%,transparent)}

/* ── Table controls: filter-chip + reset strip ──────────────────────────────── */
.m-tc-strip{display:flex;align-items:center;gap:6px;flex-wrap:wrap;padding:6px 12px;background:var(--bg-1);border-bottom:1px solid var(--border-subtle)}
.m-tc-strip .lead{font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:.1em;text-transform:uppercase;color:var(--text-muted)}
.m-tc-strip .spacer{margin-left:auto}
.tc-chip{display:inline-flex;align-items:center;gap:6px;font-family:var(--font-mono);font-size:var(--fs-10-5);color:var(--accent-text);background:var(--accent-soft);border:1px solid color-mix(in srgb,var(--accent) 35%,transparent);border-radius:var(--r-pill);padding:2px 4px 2px 9px;line-height:1.4}
.tc-chip .rm{background:none;border:none;color:inherit;cursor:pointer;font-size:var(--fs-10);opacity:.7;padding:0 3px;line-height:1}
.tc-chip .rm:hover{opacity:1}
.m-tc-reset{font-family:var(--font-ui);font-size:var(--fs-11);font-weight:600;color:var(--text-2);background:var(--bg-input);border:1px solid var(--border);border-radius:var(--r-sm);padding:3px 11px;cursor:pointer;line-height:1.4}
.m-tc-reset:hover{border-color:var(--border-strong);color:var(--text-1)}
/* The named-sort control is now a shared Button() + openMenu single-select
   (see openSortMenu) — the bespoke .m-sortbtn/.m-sortlist/.m-sortopt CSS was
   retired in the control-standard sweep (PR3). */

/* ── Table controls: filter popovers ────────────────────────────────────────── */
.m-tc-filter{min-width:220px}
.m-tc-filter .h{font-weight:600;color:var(--text-1);margin-bottom:9px;font-size:var(--fs-12-5)}
.m-tc-rangerow{display:flex;align-items:center;gap:6px}
.m-tc-rangerow .m-num{width:74px}
.m-tc-rangerow .dash{color:var(--text-muted)}
.m-tc-rangerow .unit{font-family:var(--font-mono);font-size:var(--fs-10-5);color:var(--text-muted);margin-left:2px}
.m-tc-filter .hint{font-size:var(--fs-10-5);color:var(--text-muted);margin-top:8px;line-height:1.5}
.m-tc-toggles{display:flex;gap:6px}
.m-tc-foot{display:flex;justify-content:flex-end;gap:6px;margin-top:11px}

/* detection row extras */
.m-freqrow{display:flex;align-items:center;flex-wrap:wrap;gap:8px}
/* live-status dot (recency): green+pulse = live, amber = stale, red = offline */
.m-livedot{flex:none;width:9px;height:9px;border-radius:50%;display:inline-block;background:var(--text-faint)}
.m-livedot.live{background:var(--live);animation:m-livepulse 1.8s ease-out infinite}
.m-livedot.stale{background:var(--warn)}
.m-livedot.offline{background:var(--danger)}
@keyframes m-livepulse{0%{box-shadow:0 0 0 0 color-mix(in srgb,var(--live) 70%,transparent)}70%{box-shadow:0 0 0 5px transparent}100%{box-shadow:0 0 0 0 transparent}}
/* detection click → the panel that hears it loudest gets a brief accent outline */
.m-chartpanel.m-panel-flash{animation:m-panelflash 1.4s ease-out 1}
@keyframes m-panelflash{0%{box-shadow:0 0 0 2px var(--accent),0 0 18px color-mix(in srgb,var(--accent) 55%,transparent)}100%{box-shadow:0 0 0 0 transparent}}
@media (prefers-reduced-motion:reduce){.m-chartpanel.m-panel-flash{animation:none;box-shadow:0 0 0 2px var(--accent)}}
.m-dt-freq{font-family:var(--font-mono);font-weight:600;color:var(--text-1);background:none;border:none;cursor:pointer;padding:0;font-size:var(--fs-12-5)}
.m-dt-freq:hover{color:var(--accent-text);text-decoration:underline}
.m-dt-note{display:inline-flex;align-items:center;gap:5px;font-size:var(--fs-11);color:var(--warn);margin-top:3px;margin-left:78px;background:none;border:none;cursor:pointer;padding:0;max-width:340px}
.m-dt-note svg{display:block;width:13px;height:13px}
.m-dt-note .pv{color:var(--text-muted);overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.m-dt-note:hover .pv{color:var(--text-2)}
.m-dt-trace .lead{display:inline-flex;align-items:center;color:var(--accent-text)}
.m-dt-trace .lead svg{display:block;width:13px;height:13px}
.m-seenwrap{display:flex;flex-direction:column;gap:3px}
.m-seenrow{display:flex;align-items:center;gap:6px}
.m-agg-badge.badge,.m-track-badge.badge{text-transform:none;letter-spacing:0;background:none}
.m-agg-badge.badge{padding:0;font-size:inherit}
/* on-air state (LAST SEEN): solid green = on air, grey = off air, dashed amber = source silent.
   inline-flex + no min-width so the pill hugs its label instead of stretching full-width;
   sized (incl. the longest label, "source silent") to stay under 80px. */
.m-onair{display:inline-flex;align-items:center;flex:0 0 auto;font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:normal;padding:1px 3px;border:1px solid transparent;border-radius:var(--r-sm);white-space:nowrap}
.m-onair.on_air{color:var(--live);border-color:var(--live)}
.m-onair.off_air{color:var(--text-muted);border-color:var(--border)}
.m-onair.source_silent{color:var(--warn);border-color:var(--warn);border-style:dashed}
.m-sweephint{font-size:var(--fs-9-5);color:var(--text-muted);white-space:nowrap}
.m-recent-head td{padding:4px 8px;border-top:1px solid var(--border-subtle)}
.m-recent-toggle{display:inline-flex;align-items:center;gap:8px;background:transparent;border:none;color:var(--text-muted);font:inherit;font-size:var(--fs-11-5);cursor:pointer;padding:2px 0}
.m-recent-toggle .lbl{color:var(--text-2, var(--text-1));font-weight:600}
.m-recent-toggle .sub{color:var(--text-muted);font-size:var(--fs-10-5)}
.m-recent-toggle .sub.warn{color:var(--warn)}
.m-recent-toggle .sub.m-recent-sel{color:var(--accent-text)}
.m-silent-warn{display:flex;align-items:center;gap:8px;margin:6px 0;padding:6px 10px;border:1px dashed var(--warn);border-radius:var(--r-md);color:var(--text-1);font-size:var(--fs-12)}
.m-silent-warn .i{color:var(--warn)}
.m-silent-warn .t{flex:1;min-width:0}
.m-silent-warn-show{background:transparent;border:1px solid var(--warn);border-radius:var(--r-sm);color:var(--text-1);font:inherit;font-size:var(--fs-11);padding:2px 8px;cursor:pointer}
.m-silent-warn-show:hover{background:var(--warn-dim)}
.cnt.cnt-warn{color:var(--warn);border-color:var(--warn)}
.m-recent-row{opacity:.8}
.m-onair-warn{display:flex;align-items:flex-start;gap:10px;margin:6px 0;padding:8px 12px;background:var(--warn-dim);border:1px solid var(--warn);border-radius:var(--r-md);color:var(--text-1);font-size:var(--fs-12)}
.m-onair-warn .i{color:var(--warn);font-size:var(--fs-14);line-height:1.2}
.m-onair-warn .b{flex:1;min-width:0}
.m-onair-warn .links{display:flex;flex-wrap:wrap;align-items:center;gap:6px;margin-top:6px}
.m-onair-warn .lab{color:var(--text-muted);font-size:var(--fs-11)}
.m-onair-warn-link{background:transparent;border:1px solid var(--warn);border-radius:var(--r-sm);color:var(--text-1);font:inherit;font-size:var(--fs-11);padding:2px 8px;cursor:pointer}
.m-onair-warn-link:hover{background:var(--warn-dim)}
.m-onair-warn-x{background:transparent;border:none;color:var(--text-muted);font-size:var(--fs-16);line-height:1;cursor:pointer;padding:0 2px}
.m-dt-actions.always{opacity:1}
.m-tri .tri-row .pk{width:60px;color:var(--text-muted);text-align:right;flex:none;font-size:var(--fs-11)}
.m-tri .tri-row .nm .lead{color:var(--accent-text)}

/* "Record for 1 minute" capture-for-scan empty-state (interference pane) */
.m-iface-capture{padding:16px 14px;display:flex;flex-direction:column;gap:8px;border-bottom:1px solid #11151c}
.m-iface-capture-title{margin:0;font-size:var(--fs-13);font-weight:600;color:var(--text-1)}
.m-iface-capture-text{margin:0;font-size:var(--fs-12);line-height:1.5;color:var(--text-2)}
.m-iface-capture-actions{display:flex;align-items:center;gap:14px;flex-wrap:wrap;margin-top:4px}
.m-iface-capture-link{font-size:var(--fs-12);color:var(--accent-text);text-decoration:none}
.m-iface-capture-link:hover{text-decoration:underline}
.m-iface-capture-bar{height:6px;border-radius:999px;background:var(--mon-1,#11151c);overflow:hidden;margin-top:2px}
.m-iface-capture-fill{height:100%;background:var(--accent);border-radius:999px;transition:width .3s linear}
.m-iface-capture-count{margin:0;font-family:var(--font-mono);font-size:var(--fs-11);color:var(--text-muted)}
/* "…or scan an existing capture" separator + picker slot in the empty-state */
.m-iface-capture-or{margin:6px 0 0;font-size:var(--fs-11-5);color:var(--text-muted)}
/* Why the pane's controls are disabled, said in the pane (not only in a tooltip
   on a disabled control). Muted helper text, the .m-iface-capture-or voice. */
.m-iface-hint{margin:0;padding:8px 12px 0;font-size:var(--fs-11-5);line-height:1.4;color:var(--text-muted)}
.m-iface-capture-source{display:flex;align-items:center;gap:10px;flex-wrap:wrap;margin-top:4px}
/* Control-standard reskin (PR2): the scan-source / band pickers are now the shared
   Select() primitive (.select in components.css) and the past-scans list is the
   shared openMenu — the old .m-iface-source native-select chrome and the bespoke
   .m-iface-pastscans* popover styles were retired here. */
/* Caret glyph appended to a menu-opening Button() (e.g. Past scans ▾). */
.m-menubtn-caret{margin-left:1px;display:inline-flex;align-items:center;color:var(--text-muted)}
.m-menubtn-caret svg{width:10px;height:10px;display:block}
/* interference rich rows — field-based layout (START/BW/STOP + description) */
.m-iface-row2{display:flex;align-items:center;gap:10px;padding:9px 12px;border-bottom:1px solid #11151c;flex-wrap:wrap}
.m-iface-row2:last-child{border-bottom:none}
.m-iface-row2:hover{background:var(--mon-1)}
.m-iface-row2.sel{background:#0e1c33}
/* leading status dot: ok=confirmed, danger=rejected, warn=pending, muted=missing */
.m-cand-dot{width:8px;height:8px;border-radius:50%;display:inline-block;flex:none;background:var(--text-faint)}
.m-cand-dot.confirmed{background:var(--ok);box-shadow:0 0 6px var(--ok)}
.m-cand-dot.rejected{background:var(--danger)}
.m-cand-dot.pending{background:var(--warn);box-shadow:0 0 6px var(--warn)}
.m-cand-dot.missing{background:var(--text-muted)}
/* compact mono frequency fields: small caps label · narrow number input · unit */
.m-cand-field{display:inline-flex;align-items:center;gap:5px;flex:none}
.m-cand-field .lbl{font-family:var(--font-mono);font-size:var(--fs-9);letter-spacing:.06em;color:var(--text-muted)}
.m-cand-field .unit{font-family:var(--font-mono);font-size:var(--fs-9-5);color:var(--text-muted)}
.m-cand-field .m-num.sm{width:96px}
.m-cand-field .m-num.sm::-webkit-inner-spin-button,.m-cand-field .m-num.sm::-webkit-outer-spin-button{-webkit-appearance:none;margin:0}
.m-cand-field .m-num.sm{-moz-appearance:textfield}
/* wider description / label field flexes to fill the row */
.m-cand-name{flex:0 1 380px;min-width:140px;background:var(--bg-input);border:1px solid var(--border);color:var(--text-1);border-radius:var(--r-sm);padding:5px 9px;font-size:var(--fs-12)}
.m-cand-name:focus{outline:none;border-color:var(--accent);box-shadow:var(--ring)}
.m-cand-name::placeholder{color:var(--text-muted)}
/* confidence · level readout */
.m-cand-stats{font-family:var(--font-mono);font-size:var(--fs-11);color:var(--text-2);white-space:nowrap;flex:none}
.m-cand-acts{display:flex;gap:2px;margin-left:auto;flex:none}
.m-rowbtn.ok{color:var(--ok)}
.m-rowbtn.ok:hover{background:var(--ok-soft,var(--bg-raised));color:var(--ok);border-color:var(--ok-dim)}
.m-rowbtn.warn{color:var(--danger)}
.m-rowbtn.warn:hover{background:var(--bg-raised);color:var(--danger);border-color:var(--danger-dim)}
@media(max-width:760px){
  .m-cand-field .m-num.sm{width:84px}
  .m-cand-name{min-width:100%;order:5}
  .m-cand-acts{order:6;margin-left:0}
}

/* unified pane */
.m-unified-legend{flex:0 0 auto;display:flex;align-items:center;gap:14px;flex-wrap:wrap;padding:10px 12px;border-bottom:1px solid var(--border-subtle)}
.m-legend-item{display:flex;align-items:center;gap:6px;font-size:var(--fs-11);color:var(--text-2)}
.m-legend-item .sw{width:14px;height:3px;border-radius:2px}
.m-legend-item .nm{font-family:var(--font-mono);font-size:var(--fs-10-5)}
.m-unified-chart{flex:1 1 0;min-height:0;display:flex;flex-direction:column;position:relative;height:300px;background:var(--mon-0)}
.m-unified-chart svg{display:block;width:100%;height:100%}

/* clean-freq pane */
.m-cf-target{flex:1;min-width:200px;background:var(--bg-input);border:1px solid var(--border);color:var(--text-1);border-radius:var(--r-sm);padding:7px 10px;font-family:var(--font-mono);font-size:var(--fs-11-5)}
.m-cf-result{padding:0}
.m-risk{font-family:var(--font-mono);font-size:var(--fs-10);text-transform:uppercase;padding:1px 7px;border-radius:var(--r-pill);border:1px solid}
.m-risk.low{color:var(--live);border-color:var(--ok-dim)}
.m-risk.med{color:var(--warn);border-color:var(--warn-dim)}
.m-risk.high{color:var(--danger);border-color:var(--danger-dim)}
.m-cf-best{padding:10px 12px;font-family:var(--font-mono);font-size:var(--fs-11);color:var(--text-2);border-top:1px solid var(--border-subtle)}

/* alerts strip */
.m-alerts{display:flex;flex-direction:column;gap:6px}

/* notes + tag modals */
.m-notes{min-width:0}
.m-notes-thread{display:flex;flex-direction:column;gap:10px;max-height:300px;overflow:auto;margin-bottom:14px}
.m-notes-thread .empty{color:var(--text-muted);font-size:var(--fs-12);padding:8px 0}
.m-note{position:relative;background:var(--bg-input);border:1px solid var(--border-subtle);border-radius:var(--r-sm);padding:8px 10px}
.m-note .meta{display:flex;align-items:center;gap:8px;margin-bottom:4px}
.m-note .meta .a{font-weight:600;color:var(--text-1);font-size:var(--fs-12)}
.m-note .meta .t{font-family:var(--font-mono);font-size:var(--fs-9-5);color:var(--text-muted)}
.m-note .body{font-size:var(--fs-12-5);color:var(--text-1);line-height:1.5}
.m-note .body .mention{color:var(--accent-text);font-weight:600}
.m-note .del{position:absolute;top:6px;right:6px;background:none;border:none;color:var(--text-muted);cursor:pointer;font-size:var(--fs-11)}
.m-notes-add{position:relative}
.m-textarea{background:var(--bg-input);border:1px solid var(--border);color:var(--text-1);border-radius:var(--r-sm);padding:8px 10px;font-size:var(--fs-12-5);resize:vertical;font-family:var(--font-ui)}
.m-textarea[data-field="fill"]{width:100%}
.m-mention-pop{position:absolute;left:8px;bottom:100%;margin-bottom:4px;background:var(--bg-raised);border:1px solid var(--border-strong);border-radius:var(--r-sm);box-shadow:0 8px 22px rgba(0,0,0,.5);display:flex;flex-direction:column;z-index:var(--z-float)}
.m-mention-pop .mn{background:none;border:none;color:var(--text-1);text-align:left;padding:6px 12px;cursor:pointer;font-family:var(--font-mono);font-size:var(--fs-11)}
.m-mention-pop .mn:hover{background:var(--accent-soft)}
.m-mention-pop .mn-empty{color:var(--text-muted);cursor:default;font-style:italic}
.m-mention-pop .mn-empty:hover{background:none}
/* X4 annotation composer — scope/visibility row (mockup .row2/.field/.hint) */
.m-anno-meta{display:grid;grid-template-columns:1fr 1fr;gap:12px;margin-top:12px}
.m-anno-field{display:flex;flex-direction:column;gap:7px;font-size:var(--fs-12);color:var(--text-2)}
.m-anno-field label{font-weight:500;font-size:var(--fs-12);color:var(--text-1)}
.m-anno-hint{color:var(--text-muted);font-size:var(--fs-11);line-height:1.35}
@media(max-width:520px){.m-anno-meta{grid-template-columns:1fr}}
.m-tagpick .grid{display:flex;gap:8px;flex-wrap:wrap}
.m-tagpick .tagchip{font-family:var(--font-mono);font-size:var(--fs-11);letter-spacing:.04em;background:transparent;border:1px solid;border-radius:var(--r-pill);padding:5px 12px;cursor:pointer}
.m-notraces{background:var(--mon-1);border:1px dashed var(--border);border-radius:var(--r-md);padding:30px;text-align:center}
.m-notraces .h{font-weight:600;color:var(--text-1);margin-bottom:6px}
.m-notraces .p{color:var(--text-muted);font-size:var(--fs-12-5);margin-bottom:14px;line-height:1.5}
.m-settings-stub p{color:var(--text-2);font-size:var(--fs-13);line-height:1.6;margin:0 0 10px}
.m-settings-stub .sub{color:var(--text-muted);font-size:var(--fs-11-5)}

@media(max-width:760px){
  .m-sources,.m-markerinfo,.m-histdrop,.m-pw-pop,.m-detsettings{min-width:0;max-width:90vw}
  /* Phones (MEASURED at 375 px): the tick grows to the touch size (~30 px)
     and overlapped NAME in an 18 px track; the card hugged 268 px. Give the
     tick its size, tighten the gaps, and let the card take the width. */
  .m-sources{--src-cols:30px minmax(0,1fr) 22px 22px 58px 32px 20px;--src-gap:5px;width:92vw}
  .m-sources-grp .g-all{letter-spacing:0}
  .m-panelctrls{order:3}
}
