/* =============================================================================
   CLEAR analytical workspace — stylesheet (FCLEAR-APP-0002A)
   Owner: WS1 (claude-01). Integrated into templates/clear/map.html by CLAUDE-00.

   Plain CSS, no build step, no external fonts/CDNs. Font stacks degrade to
   system faces when IBM Plex is not installed locally.

   This file styles two overlapping layers on purpose:
     1. The new DOM-contract classes (.clear-tier1, .clear-workspace,
        .clear-pane, .clear-tile, .clear-hg-*, ...) that carry the redesign.
     2. Every class the previous inline <style> block in map.html styled
        (.clear-map-*, .layer-*, .maplibregl-*). Existing `data-clear-*` hooks
        are preserved verbatim per the DOM contract, and some markup this file
        does not own may still reference the old classes — nothing may regress
        while the integrator migrates markup, so old selectors stay themed
        with the new tokens rather than being deleted.
   ========================================================================== */

/* -----------------------------------------------------------------------
   1. Design tokens
   ----------------------------------------------------------------------- */
:root {
  /* commercial profile (default) — source of truth: design package, never
     sampled from mockups */
  --brand-ink: #1C465F;
  --brand-accent: #9ED6E6;
  --brand-ui: #9ECFEC;
  --sig-reg: #1C465F;
  --sig-com: #2E8C97;

  --canvas: #e9eef2;
  --surface: #ffffff;
  --surface-2: #f5f8fa;
  --surface-3: #eef3f7;
  --line: #dce4ea;
  --line-strong: #c4d0da;
  --ink: #16242f;
  --muted: #5e7387;
  --faint: #8598a6;
  --tile-border: #dce2ea;
  --good: #2e7d5b;
  --moderate: #b8860b;
  --unavail: #94a6b3;
  --focus: #1C465F;

  --r-sm: 6px;
  --r-md: 9px;
  --r-lg: 13px;
  --sh-1: 0 1px 2px rgba(16, 32, 48, .07);
  --sh-2: 0 2px 4px rgba(16, 32, 48, .06), 0 12px 28px -18px rgba(16, 32, 48, .3);
  --sh-3: 0 -2px 20px rgba(16, 32, 48, .13);

  /* No network access at runtime: IBM Plex is first-choice but every stack
     degrades cleanly through widely-installed faces to system-ui. */
  --f: 'IBM Plex Sans', Inter, system-ui, -apple-system, 'Segoe UI', sans-serif;
  --m: 'IBM Plex Mono', ui-monospace, 'SF Mono', Menlo, monospace;

  /* --- back-compat: the previous inline stylesheet's variables, re-declared
     so any rule that hasn't migrated to the tokens above still resolves.
     Mapped onto the new tokens where the old value and a token are close
     enough that re-pointing keeps the same intent (and now respects the
     foundation profile automatically); left as literal values where there is
     no sensible new-token equivalent (layer icon colours, size scales). */
  --clear-font-family: var(--f);
  --clear-shell-navy: var(--brand-ink);
  --clear-header-text: #ffffff;
  --clear-muted-on-navy: rgba(255, 255, 255, 0.72);
  --clear-primary-blue: var(--brand-ink);
  --clear-blue: var(--brand-ink);
  --clear-blue-dark: var(--ink);
  --clear-blue-soft: var(--surface-3);
  --clear-green: #2ca56f;
  --clear-green-soft: #e5f7ee;
  --clear-teal: var(--sig-com);
  --clear-teal-soft: #e2f2f5;
  --clear-purple: #7c4cc2;
  --clear-orange: #e98a24;
  --clear-wildfire: #e65f2d;
  --clear-mint: #a8e6ce;
  --clear-gray: var(--muted);
  --clear-border: var(--line);
  --clear-control-bg: var(--surface);
  --clear-card-radius: var(--r-lg);
  --clear-control-radius: var(--r-md);
  --clear-panel: var(--surface);
  --clear-panel-soft: var(--surface-2);
  --clear-map-bg: var(--canvas);
  --clear-text: var(--ink);
  --clear-text-muted: var(--muted);
  --clear-shadow: var(--sh-2);
  --clear-shadow-soft: var(--sh-1);
  --clear-panel-shadow: var(--sh-1);
  --clear-overlay-shadow: var(--sh-3);
  --clear-dashboard-value-size: 23px;
  --clear-dashboard-unit-scale: 0.8em;
  --clear-dashboard-secondary-size: 13px;
  --clear-condition-value-size: 20px;
  --clear-condition-unit-scale: 0.8em;
  --clear-condition-category-size: 12px;
  --clear-aqi-good: #16a34a;
  --clear-aqi-moderate: #ca8a04;
  --clear-aqi-unhealthy-sensitive: #f97316;
  --clear-aqi-unhealthy: #dc2626;
  --clear-aqi-very-unhealthy: #b91c1c;
  --clear-aqi-hazardous: #ff0000;
  --clear-aqi-unavailable: #64748b;
  --clear-history-pm25-good: #218c46;
  --clear-history-pm25-moderate: #e0ab16;
  --clear-history-pm25-usg: #ef8a28;
  --clear-history-pm25-unhealthy: #d64545;
  --clear-history-pm25-very-unhealthy: #75429a;
  --clear-history-pm25-hazardous: #7d2634;
  --clear-history-pm25-unavailable: var(--unavail);
  --clear-header-height: 86px;
  --clear-nav-height: 54px;
  --clear-left-width: 340px;
  --clear-detail-panel-width: 552px;
  --clear-right-width: var(--clear-detail-panel-width);
  --clear-focus: 0 0 0 3px rgba(28, 70, 95, 0.28);

  /* history-graph provenance palette (FCLEAR-APP-0001Q, extended here) */
  --clear-hg-regulatory: var(--sig-reg);
  --clear-hg-community: var(--sig-com);
  --clear-hg-grid: var(--line);
  --clear-hg-axis: var(--muted);
  --clear-hg-gap: var(--surface-3);
  --clear-hg-transition: var(--line-strong);
}

[data-clear-profile="foundation"] {
  --brand-ink: #012F68;
  --brand-accent: #029AA1;
  --brand-ui: #029AA1;
  --sig-reg: #012F68;
  --sig-com: #029AA1;
  --focus: #012F68;
  --clear-focus: 0 0 0 3px rgba(1, 47, 104, 0.28);
}

/* -----------------------------------------------------------------------
   2. Base / reset
   ----------------------------------------------------------------------- */
html,
body {
  height: 100%;
  margin: 0;
  overflow: hidden;
  background: var(--canvas);
  color: var(--ink);
  font-family: var(--f);
}

* { box-sizing: border-box; }
button, input, select { font: inherit; }
button { cursor: pointer; }
button:disabled, select:disabled { cursor: not-allowed; }

/* Focus rings use the profile's --focus token and are suppressed for pointer
   interaction (:focus-visible only) per the accessibility contract. */
a, button, input, select, [tabindex] { outline: none; }
a:focus-visible,
button:focus-visible,
input:focus-visible,
select:focus-visible,
[tabindex]:focus-visible {
  outline: 2px solid var(--focus);
  outline-offset: 2px;
}
/* legacy box-shadow focus treatment, kept for un-migrated controls */
button:focus-visible, a:focus-visible, input:focus-visible, select:focus-visible {
  box-shadow: var(--clear-focus);
}

@media (prefers-reduced-motion: reduce) {
  * { scroll-behavior: auto !important; }
  .clear-pane,
  .clear-rail,
  .clear-scrim,
  .clear-hg-scroll,
  .clear-hg-pindot,
  .clear-hg-focusdot,
  .clear-map-history-year-row {
    transition: none !important;
    animation: none !important;
  }
}

/* Numeric/identifier legibility: mono face + tabular figures wherever a
   column of digits needs to line up (readouts, coordinates, distances,
   axis labels, IDs). Non-obvious because it's applied by intent, not by
   element type — some <span> text is prose and must stay in --f. */
.clear-mono,
.clear-tier2-actions,
.clear-coord,
.clear-tile-value,
.clear-tile-unit,
.clear-hg-vlabel,
.clear-hg-ylabel,
.clear-hg-tip,
[data-clear-condition-pm25], [data-clear-condition-o3], [data-clear-condition-no2],
[data-clear-condition-so2], [data-clear-condition-co],
.clear-metric-primary, .clear-condition-number, .clear-map-history-value,
.clear-map-history-year-marker {
  font-family: var(--m);
  font-variant-numeric: tabular-nums;
}

/* -----------------------------------------------------------------------
   2b. App shell — viewport-height layout (defect 3)
   .clear-app was previously an unstyled div: it had no explicit height, so
   its children (tier1/tier2/workspace) sized to their content instead of the
   viewport and the whole page grew — the rail and pane never got a chance to
   hit their own overflow:auto because there was no bounded box to overflow.
   100dvh is primary (correct on mobile browser chrome show/hide); 100vh is
   the fallback for engines without dvh support.
   ----------------------------------------------------------------------- */
.clear-app {
  display: flex;
  flex-direction: column;
  height: 100vh;
  height: 100dvh;
  min-height: 0;
  overflow: hidden;
  background: var(--canvas);
}
.clear-tier1,
.clear-tier2 { flex: 0 0 auto; }

/* =============================================================================
   3. Tier 1 — product shell
   ========================================================================== */
.clear-tier1 {
  display: flex;
  align-items: center;
  gap: 14px;
  min-width: 0;
  height: 44px;
  padding: 0 16px;
  background: var(--brand-ink);
  color: #fff;
}
.clear-tier1-brand {
  display: flex;
  align-items: center;
  gap: 8px;
  min-width: 0;
  flex: 0 0 auto;
  color: #fff;
  text-decoration: none;
}
.clear-tier1-mark {
  width: 28px; height: 28px; border-radius: var(--r-sm); object-fit: contain; flex: 0 0 auto;
}

/* FCLEAR-APP-0002A branding correction, matched to the approved Commercial header mockup.
   ONE authoritative lung silhouette asset, drawn twice with different presentation:

     tier 1  white silhouette directly on the navy bar, no tile, wordmark as text beside it
     tier 2  the same silhouette in the pale --brand-accent, inside the rounded white tile

   Both are painted with a CSS mask, so the colour is entirely presentation and the mark's
   geometry is exactly the approved asset -- nothing is recoloured in the file, redrawn or traced.
   --clear-mark-src is set inline from deployment_profile.header_logo_url so the asset stays a
   straight swap and the stylesheet hard-codes no path. */
.clear-tier1-lung {
  /* The asset's aspect is 835:697, so a 20px box renders the silhouette ~20x16.7 -- the mockup's
     ~19x16. Sized by box rather than by cropping or rescaling the asset. */
  display: inline-block; flex: 0 0 auto; width: 20px; height: 20px;
  background-color: #fff;
  -webkit-mask: var(--clear-mark-src) no-repeat center / contain;
          mask: var(--clear-mark-src) no-repeat center / contain;
}
.clear-tile-lung {
  display: block; width: 30px; height: 30px;
  background-color: var(--brand-accent);
  -webkit-mask: var(--clear-mark-src) no-repeat center / contain;
          mask: var(--clear-mark-src) no-repeat center / contain;
}
.clear-tier1-wordmark { font-size: 14px; font-weight: 700; letter-spacing: .01em; white-space: nowrap; }
.clear-tier1-nav {
  display: flex;
  align-items: center;
  gap: 4px;
  min-width: 0;
  overflow-x: auto;
  flex: 1 1 auto;
}
.clear-tier1-link {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  height: 28px;
  padding: 0 10px;
  border: 0;
  border-radius: var(--r-sm);
  background: transparent;
  color: rgba(255, 255, 255, .78);
  font-size: 12.5px;
  font-weight: 600;
  text-decoration: none;
  white-space: nowrap;
}
.clear-tier1-link:hover { background: rgba(255, 255, 255, .10); color: #fff; }
.clear-tier1-link.is-active { background: rgba(255, 255, 255, .16); color: #fff; }
.clear-tier1-link:disabled, .clear-tier1-link[aria-disabled="true"] { color: rgba(255, 255, 255, .38); cursor: not-allowed; }
.clear-tier1-link:disabled:hover, .clear-tier1-link[aria-disabled="true"]:hover { background: transparent; }
.clear-tier1-meta { flex: 0 0 auto; display: flex; align-items: center; gap: 10px; min-width: 0; color: rgba(255, 255, 255, .78); font-size: 12px; }

/* =============================================================================
   4. Tier 2 — map chrome (lockup, search, actions)
   ========================================================================== */
.clear-tier2 {
  display: flex;
  align-items: center;
  gap: 14px;
  min-width: 0;
  height: 56px;
  padding: 0 16px;
  background: var(--surface);
  border-bottom: 1px solid var(--line);
}
.clear-lockup { display: flex; align-items: center; gap: 10px; min-width: 0; flex: 0 0 auto; }

/* The brand tile is CSS chrome — a white rounded frame around the mark — so
   the profile logo asset never needs to bake in its own presentation. Sizes
   below match the 44/38/40px contract for the three chrome contexts. */
.clear-brand-tile {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  border-radius: var(--r-md);
  background: #fff;
  border: 1px solid var(--tile-border);
  box-shadow: var(--sh-1);
  flex: 0 0 auto;
}
.clear-brand-tile img { width: 28px; height: 28px; object-fit: contain; display: block; }
.clear-lockup-text { display: flex; flex-direction: column; min-width: 0; line-height: 1.15; }
.clear-lockup-name { font-size: 16px; font-weight: 700; color: var(--brand-ink); letter-spacing: -.01em; }
.clear-lockup-descriptor { font-size: 11.5px; font-weight: 600; color: var(--muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }

.clear-search {
  display: flex;
  align-items: center;
  gap: 8px;
  flex: 1 1 320px;
  min-width: 0;
  max-width: 420px;
  height: 40px;
  padding: 0 12px;
  border-radius: var(--r-md);
  background: var(--surface-2);
  border: 1px solid var(--line);
}
.clear-search:focus-within { border-color: var(--focus); box-shadow: 0 0 0 3px color-mix(in srgb, var(--focus) 20%, transparent); }
.clear-search svg { width: 16px; height: 16px; color: var(--faint); flex: 0 0 auto; }
.clear-search input { flex: 1 1 auto; min-width: 0; border: 0; outline: 0; background: transparent; color: var(--ink); font-size: 13px; font-family: var(--f); }
.clear-search input::placeholder { color: var(--faint); }

.clear-tier2-actions { display: flex; align-items: center; gap: 8px; flex: 0 0 auto; margin-left: auto; }
.clear-action {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  height: 38px;
  padding: 0 12px;
  border-radius: var(--r-md);
  border: 1px solid var(--line);
  background: var(--surface);
  color: var(--ink);
  font-size: 12.5px;
  font-weight: 700;
  font-family: var(--f);
  white-space: nowrap;
}
.clear-action:hover { background: var(--surface-2); }
.clear-action svg { width: 16px; height: 16px; flex: 0 0 auto; }
.clear-action.is-primary { background: var(--brand-ink); border-color: var(--brand-ink); color: #fff; }
.clear-action.is-primary:hover { background: color-mix(in srgb, var(--brand-ink) 88%, #000); }
.clear-action[aria-pressed="true"] { background: var(--surface-3); border-color: var(--line-strong); }
/* Below 1320px the label text hides, the icon + aria-label remain — the
   button never moves into a menu (no hamburger above phone widths). */
@media (max-width: 1319px) {
  .clear-action-label { display: none; }
  .clear-action { padding: 0 10px; width: 38px; justify-content: center; }
}
.clear-user-chip { display: inline-flex; align-items: center; gap: 8px; height: 40px; padding: 0 4px 0 0; border: 0; background: transparent; color: var(--ink); }

/* =============================================================================
   5. Workspace layout
   ========================================================================== */
main.clear-workspace,
.clear-workspace {
  position: relative;
  display: flex;
  flex: 1 1 auto; /* fills the remaining height under .clear-app's tier1/tier2 */
  min-width: 0; /* mandatory safeguard: without this the pane's intrinsic
                   content width can push the flex container wider than the
                   viewport instead of yielding to the map */
  min-height: 0;
  height: 100%;
  overflow: hidden;
  background: var(--canvas);
}

.clear-rail {
  flex: 0 0 320px;
  min-width: 0;
  background: var(--surface);
  border-right: 1px solid var(--line);
  overflow-y: auto;
  overflow-x: hidden;
  padding: 18px 20px 0;
  display: flex;
  flex-direction: column;
}

.clear-canvas {
  position: relative;
  flex: 1 1 auto;
  min-width: 0;
  min-height: 0;
  height: 100%;
  overflow: hidden;
  background: #cddae5;
}

.clear-pane {
  flex: 0 0 468px;
  min-width: 0; /* mandatory safeguard: a wide history chart must not force
                   this track past its flex-basis and crush the map */
  background: var(--surface);
  border-left: 1px solid var(--line);
  display: flex;
  flex-direction: column;
  overflow: hidden;
}

.clear-scrim {
  position: absolute;
  inset: 0;
  z-index: 15;
  background: rgba(15, 27, 38, .38);
}
.clear-scrim[hidden] { display: none; }

/* --- Responsive modes ---------------------------------------------------
   Layout is driven by matching media queries (guaranteed correct before JS
   runs) *and* by the [data-clear-pane-mode] attribute the JS mode broker
   sets from its matchMedia list, per the DOM contract's "both" requirement —
   the attribute is also what lets JS gate sheet-drag behaviour to sheet mode
   only. The breakpoints below intentionally mirror each other. */

/* overlay: 1121–1319 — rail stays in-flow at 300px, pane becomes a floating
   drawer over the full-width map. */
@media (max-width: 1319px) {
  .clear-rail { flex-basis: 300px; }
  .clear-pane {
    position: absolute;
    top: 0;
    right: 0;
    bottom: 0;
    flex-basis: auto;
    width: 414px;
    z-index: 20;
    box-shadow: var(--sh-3);
  }
}
.clear-workspace[data-clear-pane-mode="overlay"] .clear-rail { flex-basis: 300px; }
.clear-workspace[data-clear-pane-mode="overlay"] .clear-pane {
  position: absolute;
  top: 0;
  right: 0;
  bottom: 0;
  flex-basis: auto;
  width: 414px;
  z-index: 20;
  box-shadow: var(--sh-3);
}

/* overlay: 768–1120 — rail also becomes a dismissible overlay with scrim. */
@media (max-width: 1120px) {
  .clear-rail {
    position: absolute;
    top: 0;
    left: 0;
    bottom: 0;
    width: 300px;
    z-index: 21;
    box-shadow: var(--sh-3);
    transform: translateX(-100%);
    transition: transform .2s ease;
  }
  .clear-rail.is-open { transform: translateX(0); }
}

/* sheet: ≤767 — map-first; rail is off-canvas behind a hamburger, pane
   becomes a bottom sheet. The map is never display:none at any width. */
@media (max-width: 767px) {
  .clear-rail {
    position: absolute;
    top: 0;
    left: 0;
    bottom: 0;
    width: min(84vw, 320px);
    z-index: 21;
    box-shadow: var(--sh-3);
    transform: translateX(-100%);
    transition: transform .2s ease;
  }
  .clear-rail.is-open { transform: translateX(0); }
  .clear-pane {
    position: fixed;
    inset: auto 0 0 0;
    top: auto;
    width: auto;
    height: 238px;
    max-height: 92vh;
    border-left: 0;
    border-top: 1px solid var(--line);
    border-radius: var(--r-lg) var(--r-lg) 0 0;
    box-shadow: var(--sh-3);
    z-index: 22;
    transition: height .2s ease;
  }
  .clear-pane[data-clear-pane-state="expanded"] { height: 92vh; }
}
.clear-workspace[data-clear-pane-mode="sheet"] .clear-pane {
  position: fixed;
  inset: auto 0 0 0;
  top: auto;
  width: auto;
  height: 238px;
  max-height: 92vh;
  border-left: 0;
  border-top: 1px solid var(--line);
  border-radius: var(--r-lg) var(--r-lg) 0 0;
  box-shadow: var(--sh-3);
  z-index: 22;
}
.clear-workspace[data-clear-pane-mode="sheet"] .clear-pane[data-clear-pane-state="expanded"] { height: 92vh; }

.clear-pane-grip {
  display: none;
  width: 100%;
  padding: 10px 0 6px;
  border: 0;
  background: transparent;
  flex: 0 0 auto;
}
.clear-pane-grip::before {
  content: "";
  display: block;
  width: 36px;
  height: 4px;
  margin: 0 auto;
  border-radius: 999px;
  background: var(--line-strong);
}
@media (max-width: 767px) {
  .clear-pane-grip { display: block; }
}

/* =============================================================================
   6. Floating map chrome — controls, legend, coordinate pill
   ========================================================================== */
.clear-map-floating-row { position: absolute; z-index: 5; display: flex; align-items: center; gap: 10px; }
.clear-map-floating-row.top-left { top: 16px; left: 18px; }
.clear-map-floating-row.top-right { top: 16px; right: 48px; }

.clear-map-toolbar-button {
  height: 40px;
  display: inline-flex;
  align-items: center;
  gap: 8px;
  border: 1px solid var(--line);
  border-radius: var(--r-md);
  background: var(--surface);
  color: var(--ink);
  padding: 0 14px;
  box-shadow: var(--sh-1);
  font-size: 13px;
  font-weight: 700;
  font-family: var(--f);
}
.clear-map-toolbar-button[aria-disabled="true"] { color: var(--muted); }

/* FCLEAR-APP-0002B, Gate B finding F: "clicking the Basemap control appears to do nothing".
   The control was already honest -- its title has always explained that no Standard basemap is
   published -- but `.clear-action` had no disabled treatment at all, so Basemap and Help rendered
   as fully clickable and the explanation only ever appeared on hover. A user clicks, nothing
   happens, and the reason is invisible. This mirrors the treatment `.clear-tier1-link` and
   `.clear-map-toolbar-button` already carry (:305, :588); it is not a new visual language.
   It disappears on its own the moment a control becomes enabled. */
.clear-action[aria-disabled="true"] { color: var(--faint); cursor: not-allowed; }
.clear-action[aria-disabled="true"]:hover { background: transparent; border-color: var(--line); }
.clear-action[aria-disabled="true"] .clear-action-state { opacity: .75; }
.clear-map-status-dot { width: 9px; height: 9px; border-radius: 50%; background: var(--good); box-shadow: 0 0 0 3px color-mix(in srgb, var(--good) 18%, transparent); }

.clear-map-aq-card {
  position: absolute;
  z-index: 5;
  left: 14px;
  bottom: 88px;
  width: 232px;
  border-radius: var(--r-md);
  padding: 13px 15px 14px;
  background: rgba(13, 39, 65, .94);
  color: #fff;
  box-shadow: var(--sh-3);
  backdrop-filter: blur(8px);
}
.clear-map-aq-kicker { font-size: 10px; font-weight: 800; letter-spacing: .13em; text-transform: uppercase; color: rgba(255, 255, 255, .70); font-family: var(--f); }
.clear-map-aq-title { margin-top: 5px; font-size: 15px; font-weight: 800; line-height: 1.2; }
.clear-map-aq-body { margin-top: 7px; color: rgba(255, 255, 255, .76); font-size: 12px; line-height: 1.4; }
.clear-map-aq-progress { margin-top: 11px; height: 6px; border-radius: 999px; background: rgba(255, 255, 255, .17); overflow: hidden; }
.clear-map-aq-progress span { display: block; width: 0; height: 100%; background: var(--brand-accent); border-radius: inherit; }
.clear-map-aq-value { margin-top: 10px; font-size: 26px; line-height: 1; font-weight: 800; color: #fff; font-family: var(--m); font-variant-numeric: tabular-nums; }
.clear-map-aq-value small { font-size: 12px; margin-left: 4px; color: rgba(255, 255, 255, .8); }
.clear-map-aq-foot { margin-top: 10px; color: rgba(255, 255, 255, .84); font-size: 11px; line-height: 1.45; }

.clear-coord,
.clear-coordinate-pill,
.clear-map-coordinate-pill {
  position: absolute;
  z-index: 5;
  right: 18px;
  bottom: 18px;
  display: inline-flex;
  align-items: center;
  gap: 10px;
  min-height: 34px;
  padding: 0 13px;
  border-radius: 999px;
  background: rgba(11, 28, 46, .86);
  color: #fff;
  box-shadow: var(--sh-1);
  backdrop-filter: blur(8px);
  font-size: 12px;
  font-weight: 700;
  letter-spacing: .01em;
}
.clear-coord span + span, .clear-coordinate-pill span + span, .clear-map-coordinate-pill span + span { padding-left: 10px; border-left: 1px solid rgba(255, 255, 255, .20); }

.clear-watermark,
.clear-map-watermark { position: absolute; z-index: 4; right: 24px; bottom: 74px; width: 142px; height: auto; opacity: .76; pointer-events: none; user-select: none; }

.clear-map-status { position: absolute; z-index: 6; max-width: 340px; border-radius: var(--r-md); padding: 13px 14px; background: rgba(13, 39, 65, .88); color: #fff; box-shadow: var(--sh-2); backdrop-filter: blur(8px); }
.clear-map-status strong { display: block; margin-bottom: 4px; font-size: 13px; }
.clear-map-status div { font-size: 12px; line-height: 1.4; color: rgba(255, 255, 255, .82); }
.clear-map-basemap-status { top: 74px; left: 18px; }
.clear-map-error { background: rgba(126, 36, 36, .92); }

/* =============================================================================
   7. Cards & disclosure
   ========================================================================== */
.clear-card {
  min-width: 0; /* mandatory safeguard — see .clear-pane */
  border: 1px solid var(--line);
  background: var(--surface);
  border-radius: var(--r-lg);
  box-shadow: var(--sh-1);
  margin-bottom: 10px;
}
.clear-card-head { display: flex; align-items: center; justify-content: space-between; gap: 10px; padding: 13px 14px 0; }
.clear-card-head h3 { margin: 0; font-size: 14px; font-weight: 700; color: var(--ink); }
.clear-card-tools { display: flex; align-items: center; gap: 6px; }
.clear-card-body { padding: 10px 14px 14px; }

.clear-disclosure {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  border: 1px solid var(--line);
  border-radius: var(--r-sm);
  background: var(--surface);
  color: var(--brand-ink);
  padding: 0 10px;
  height: 30px;
  font-size: 12px;
  font-weight: 700;
  font-family: var(--f);
}
.clear-disclosure::after { content: "▾"; font-size: 10px; transition: transform .15s ease; }
.clear-disclosure[aria-expanded="true"]::after { transform: rotate(180deg); }
.clear-disclosure-body { margin-top: 10px; }
.clear-disclosure-body[hidden] { display: none; }

/* =============================================================================
   8. Analytical pane — identity, tabs, panels
   ========================================================================== */
.clear-pane-identity { padding: 16px 18px 14px; border-bottom: 1px solid var(--line); }
.clear-pane-identity[hidden] { display: none; }
.clear-pane-tabs {
  display: flex;
  align-items: stretch;
  gap: 0;
  padding: 0 14px;
  border-bottom: 1px solid var(--line);
  overflow-x: auto;
  flex: 0 0 auto;
}
.clear-pane-tab {
  position: relative;
  min-width: max-content;
  height: 46px;
  border: 0;
  background: transparent;
  color: var(--muted);
  padding: 0 12px;
  font-size: 13px;
  font-weight: 700;
  font-family: var(--f);
}
.clear-pane-tab[aria-selected="true"] { color: var(--brand-ink); }
.clear-pane-tab[aria-selected="true"]::after {
  content: "";
  position: absolute;
  left: 10px;
  right: 10px;
  bottom: 0;
  height: 3px;
  border-radius: 999px 999px 0 0;
  background: var(--brand-ink);
}
.clear-pane-tab:disabled { color: var(--faint); }

.clear-pane-body { flex: 1 1 auto; min-height: 0; overflow-y: auto; overflow-x: hidden; padding: 16px; background: var(--surface-2); }
.clear-tabpanel[hidden] { display: none; }
.clear-pane-actions { display: grid; grid-template-columns: 1fr 1fr 1fr 34px; gap: 8px; padding: 14px 16px 16px; background: var(--surface); border-top: 1px solid var(--line); flex: 0 0 auto; }

/* Overview answer strip — states what is known before any chart, per the
   design thesis: the answer comes before the evidence. */
.clear-answer-strip { padding: 12px 14px; border-radius: var(--r-md); background: var(--surface-3); color: var(--ink); font-size: 13px; line-height: 1.5; margin-bottom: 12px; }
.clear-registry-caveat { display: inline-flex; align-items: center; gap: 6px; margin-top: 6px; color: var(--muted); font-size: 11.5px; }

/* =============================================================================
   9. Pollutant tiles — the only pollutant selector in the document
   ========================================================================== */
.clear-tiles {
  display: grid;
  grid-template-columns: repeat(6, minmax(0, 1fr));
  gap: 6px;
}
.clear-tile {
  min-width: 0;
  border: 1px solid var(--tile-border);
  border-radius: var(--r-md);
  background: var(--surface);
  padding: 8px 6px 7px;
  text-align: left;
  min-height: 76px;
}
.clear-tile-label { display: block; color: var(--ink); font-size: 12px; font-weight: 700; }
.clear-tile-value { display: block; margin-top: 6px; color: var(--ink); font-size: 18px; line-height: 1.05; font-weight: 800; letter-spacing: -.01em; }
.clear-tile-unit { font-size: .62em; font-weight: 700; margin-left: 2px; }
.clear-tile-condition { display: block; margin-top: 5px; color: var(--muted); font-size: 11px; font-weight: 700; }
.clear-tile:hover { border-color: var(--line-strong); }
.clear-tile.is-active { border: 2px solid var(--brand-ink); background: color-mix(in srgb, var(--brand-ink) 6%, var(--surface)); padding: 7px 5px 6px; }
.clear-tile:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }

/* PM10-style "not currently served" tile: reads as absence of data, never as
   good/zero/low. No condition colour, no value, no unit — just --unavail. */
.clear-tile.is-unavailable {
  border-style: dashed;
  color: var(--unavail);
  cursor: default;
}
.clear-tile.is-unavailable .clear-tile-label { color: var(--muted); }
.clear-tile.is-unavailable .clear-tile-condition { color: var(--unavail); font-weight: 600; text-transform: none; }

@media (max-width: 767px) {
  .clear-tiles { grid-auto-flow: column; grid-auto-columns: 118px; grid-template-columns: none; overflow-x: auto; padding-bottom: 4px; }
}

/* =============================================================================
   10. Reporting sources / nearby / radius / evidence rows
   ========================================================================== */
.clear-source-row {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  gap: 10px;
  align-items: start;
  padding: 10px 12px;
  border: 1px solid var(--line);
  border-radius: var(--r-md);
  background: var(--surface-2);
}
.clear-source-row + .clear-source-row { margin-top: 8px; }
.clear-source-row strong { display: block; color: var(--ink); font-size: 12px; line-height: 1.3; }
.clear-source-row span { display: block; color: var(--muted); font-size: 11.5px; line-height: 1.45; }
.clear-source-badge { flex: 0 0 auto; border-radius: 999px; padding: 3px 8px; font-size: 11px; font-weight: 700; white-space: nowrap; }
.clear-source-badge.is-regulatory { background: color-mix(in srgb, var(--sig-reg) 12%, var(--surface)); color: var(--sig-reg); }
.clear-source-badge.is-community { background: color-mix(in srgb, var(--sig-com) 12%, var(--surface)); color: var(--sig-com); }

.clear-radius-block { display: grid; gap: 12px; }
.clear-radius-toolbar { display: flex; flex-wrap: wrap; gap: 8px; }
.clear-radius-row { display: flex; align-items: center; justify-content: space-between; gap: 10px; }
.clear-radius-row label { color: var(--muted); font-size: 12px; font-weight: 700; }
.clear-radius-row output { font-family: var(--m); font-variant-numeric: tabular-nums; font-size: 12px; color: var(--ink); }
.clear-radius-disclaimer { margin: 0; color: var(--muted); font-size: 10.5px; line-height: 1.45; }

.clear-nearby-row,
.clear-detail-row {
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  gap: 10px;
  padding: 8px 0;
  border-top: 1px solid var(--line);
}
.clear-nearby-row:first-child,
.clear-detail-row:first-child { border-top: 0; padding-top: 0; }
.clear-nearby-distance { font-family: var(--m); font-variant-numeric: tabular-nums; color: var(--muted); font-size: 12px; white-space: nowrap; }

.clear-evidence-row { display: grid; grid-template-columns: minmax(0, 1fr) auto auto; gap: 10px; align-items: center; padding: 9px 0; border-top: 1px solid var(--line); }
.clear-evidence-row:first-child { border-top: 0; padding-top: 0; }
.clear-evidence-class { font-size: 12px; font-weight: 700; color: var(--ink); }
.clear-evidence-count { font-family: var(--m); font-variant-numeric: tabular-nums; font-size: 12px; color: var(--muted); }

/* =============================================================================
   11. History graph (.clear-hg-*)
   Regulatory = solid line, --sig-reg. Community = hollow diamond marker,
   --sig-com, never a line. Gaps = hatched band, never a line. Provenance is
   structural (different mark + geometry), never colour-only.
   ========================================================================== */
.clear-hg-toolbar { display: flex; flex-wrap: wrap; gap: 8px; align-items: center; justify-content: space-between; margin-bottom: 8px; }
.clear-hg-ranges { display: inline-flex; border: 1px solid var(--line); border-radius: var(--r-sm); overflow: hidden; }
.clear-hg-range { appearance: none; border: 0; background: var(--surface); color: var(--ink); font: inherit; font-family: var(--f); font-size: 11px; letter-spacing: .04em; padding: 5px 10px; cursor: pointer; }
.clear-hg-range + .clear-hg-range { border-left: 1px solid var(--line); }
.clear-hg-range.is-active { background: var(--sig-reg); color: #fff; }
.clear-hg-range:focus-visible { outline: 2px solid var(--focus); outline-offset: 1px; }

.clear-hg-serieses { display: inline-flex; align-items: center; gap: 10px; font-size: 11px; color: var(--muted); font-family: var(--f); }
.clear-hg-series-static { display: inline-flex; align-items: center; gap: 5px; }
.clear-hg-series-toggle { appearance: none; border: 1px solid var(--line); background: var(--surface); border-radius: var(--r-sm); font: inherit; font-family: var(--f); font-size: 11px; color: var(--muted); padding: 4px 8px; cursor: pointer; display: inline-flex; align-items: center; gap: 5px; }
.clear-hg-series-toggle.is-active { border-color: var(--sig-com); color: var(--ink); }
.clear-hg-series-toggle:focus-visible { outline: 2px solid var(--focus); outline-offset: 1px; }
.clear-hg-swatch { width: 9px; height: 9px; border-radius: 2px; flex: 0 0 auto; }
.clear-hg-swatch.is-regulatory { background: var(--sig-reg); border-radius: 1px; }
.clear-hg-swatch.is-community { background: transparent; border: 2px solid var(--sig-com); transform: rotate(45deg); }

/* Mandatory safeguard: a wide, unbroken chart must scroll horizontally
   inside its own track rather than forcing the pane wider than 100%. */
.clear-hg-scroll {
  max-width: 100%;
  overflow-y: hidden;
  overscroll-behavior-x: contain;
  /* NOT `scroll-behavior: smooth`. This scroller is DIRECT MANIPULATION: the pan handler writes
     scrollLeft once per animation frame while the finger moves. With smooth behaviour the browser
     animates towards each of those writes instead of applying it, so every frame starts a fresh
     eased animation towards a target the finger has already left -- the rendered timeline lags the
     finger and the gesture feels heavy. Measured on iPhone as the dominant cause. The only other
     scrollLeft writers here (keyboard month navigation, and the initial scroll to the newest
     month) also want an immediate reposition, so `auto` is correct for the whole component.

     `-webkit-overflow-scrolling: touch` was removed with it: it puts the scroller on a legacy iOS
     compositor scroll layer where programmatic scrollLeft is applied out of band from the touch
     stream, and it is redundant on modern iOS, which gives momentum scrolling by default. */
  scroll-behavior: auto;
  /* The scrollbar is part of the design: it is how the user knows the timeline continues past the
     viewport. It is deliberately always visible on a scrollable range, not overlay-on-hover. */
  /* The scrollbar is part of the design: it is how the user sees that the timeline continues past
     the viewport. `scrollbar-width: thin` yielded an OVERLAY scrollbar that reserved no space and
     was invisible until scrolled, so the timeline looked like it simply ended. `scroll` reserves
     the track permanently and the webkit rules below give it a visible thumb. Measured: the track
     must occupy real height, not 0. */
  overflow-x: scroll;
  scrollbar-color: var(--line-strong, #c7d2dd) var(--surface-3, #eef2f6);
  padding-bottom: 2px;
}
.clear-hg-scroll::-webkit-scrollbar { height: 10px; }
.clear-hg-scroll::-webkit-scrollbar-track { background: var(--surface-3, #eef2f6); border-radius: 999px; }
.clear-hg-scroll::-webkit-scrollbar-thumb {
  background: var(--line-strong, #c7d2dd); border-radius: 999px;
  border: 2px solid var(--surface, #fff);
}
.clear-hg-scroll::-webkit-scrollbar-thumb:hover { background: var(--muted, #5b7285); }
.clear-hg-canvas { display: block; }
.clear-hg-canvas:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }
.clear-hg-svg { display: block; }

.clear-hg-grid {}
.clear-hg-gridline { stroke: var(--line); stroke-width: 1; }
.clear-hg-yeartick { stroke: var(--line); stroke-width: 1; stroke-dasharray: 2 3; }
.clear-hg-vlabel, .clear-hg-ylabel { fill: var(--muted); font-size: 9px; }

/* Ordinary gaps: a hatched band, never a connecting line and never a solid
   fill — a repeating diagonal pattern reads as "unknown", not "zero". */
.clear-hg-gap { fill: var(--surface-3); }
.clear-hg-gap.is-hatched {
  fill: repeating-linear-gradient(45deg, var(--line) 0 2px, transparent 2px 6px);
}
.clear-hg-gap.is-uncovered_after_termination { fill: var(--surface-3); opacity: .6; }

path.clear-hg-reg { stroke: var(--sig-reg); stroke-width: 1.8; fill: none; stroke-linejoin: round; stroke-linecap: round; }
path.clear-hg-reg.is-provisional { stroke-dasharray: 3 2; }
circle.clear-hg-reg { fill: var(--sig-reg); stroke: none; }
circle.clear-hg-point,
circle.clear-hg-point-single { stroke: #fff; stroke-width: 1.4; }

/* Community: discrete hollow diamond markers only, never a line, never
   merged with the Regulatory series. */
.clear-hg-comm { fill: var(--surface); stroke: var(--sig-com); stroke-width: 1.8; }

.clear-hg-transition { stroke: var(--line-strong); stroke-width: 1; stroke-dasharray: 3 2; }
.clear-hg-focusline { stroke: var(--sig-reg); stroke-width: 1; opacity: .45; }
.clear-hg-focusdot { fill: #fff; stroke: var(--sig-reg); stroke-width: 1.8; }

/* Pinned state is a stronger, persistent variant of the transient hover
   focus ring — click pins a month, a second click (or Esc) unpins it. */
.clear-hg-pinline { stroke: var(--brand-ink); stroke-width: 1.5; opacity: .7; }
.clear-hg-pindot { fill: #fff; stroke: var(--brand-ink); stroke-width: 2.4; }

/* One invisible full-height rect per month: generous, y-position-independent
   hit targets for hover/click/keyboard nearest-month resolution. */
.clear-hg-hit { fill: transparent; pointer-events: all; cursor: pointer; }

.clear-hg-hint { margin: 4px 0 0; font-size: 10px; color: var(--faint); font-family: var(--f); }

/* Fixed region below the chart — never floats, never follows the cursor,
   never overlays the plot. */
.clear-hg-tip { min-height: 46px; margin-top: 6px; font-size: 11px; line-height: 1.45; color: var(--ink); }
.clear-hg-tip-class { display: inline-block; font-size: 10px; letter-spacing: .05em; text-transform: uppercase; font-family: var(--f); }
.clear-hg-tip-class.is-regulatory { color: var(--sig-reg); }
.clear-hg-tip-class.is-community { color: var(--sig-com); }
.clear-hg-tip-flag { color: var(--moderate); font-family: var(--f); }
.clear-hg-tip-inferred { color: var(--faint); font-size: 10px; font-family: var(--f); }

.clear-hg-empty { font-size: 12px; color: var(--muted); margin: 6px 0; font-family: var(--f); }
.clear-hg-details-toggle { margin-top: 8px; }
.clear-hg-table { margin-top: 8px; max-width: 100%; overflow-x: auto; }
.clear-hg-table table { border-collapse: collapse; width: 100%; font-size: 12px; }
.clear-hg-table th { position: sticky; top: 0; background: var(--surface); text-align: left; color: var(--muted); font-size: 10px; letter-spacing: .06em; text-transform: uppercase; padding: 6px 8px; border-bottom: 1px solid var(--line); }
.clear-hg-table td { padding: 6px 8px; border-bottom: 1px solid var(--surface-3); }

.clear-hg-visually-hidden { position: absolute; width: 1px; height: 1px; margin: -1px; padding: 0; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0; }

@media (prefers-reduced-motion: reduce) {
  .clear-hg-scroll { scroll-behavior: auto; }
}

/* =============================================================================
   12. Legacy structural shell — pre-redesign class names.
   These stay themed with the new tokens so nothing loses its styling if the
   integrator has not yet migrated a given fragment of markup.
   ========================================================================== */
.clear-map-app {
  height: 100vh;
  display: grid;
  grid-template-rows: var(--clear-header-height) var(--clear-nav-height) minmax(0, 1fr);
  background: var(--clear-map-bg);
}

.clear-map-app-header,
.clear-map-primary-nav {
  background: var(--clear-shell-navy);
  color: var(--clear-header-text);
}

.clear-map-app-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 24px;
  padding: 12px 24px 10px 20px;
  border-bottom: 0;
  box-shadow: none;
}

.clear-map-app-brand { display: flex; align-items: center; gap: 14px; min-width: 0; }
.clear-map-app-brand img { width: 48px; height: 48px; border-radius: var(--r-md); object-fit: contain; flex: 0 0 auto; box-shadow: var(--sh-1); }
.clear-map-app-kicker { font-size: 11px; font-weight: 800; letter-spacing: .18em; text-transform: uppercase; color: var(--clear-muted-on-navy); }
.clear-map-app-title { margin: 3px 0 0; font-size: 23px; line-height: 1.08; font-weight: 800; color: #fff; }
.clear-map-app-subtitle { margin-top: 5px; font-size: 12.5px; color: rgba(255, 255, 255, .78); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.clear-map-app-subtitle-attribution { font-size: .92em; opacity: .88; }

.clear-map-app-tools { display: flex; align-items: center; gap: 14px; min-width: 0; }
.clear-map-header-search {
  width: 295px;
  height: 44px;
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 0 14px;
  border-radius: var(--r-md);
  background: rgba(255, 255, 255, .13);
  border: 1px solid rgba(255, 255, 255, .14);
}
.clear-map-search-icon { width: 17px; height: 17px; color: rgba(255, 255, 255, .84); flex: 0 0 auto; }
.clear-map-header-search input, .clear-map-canvas-search input { width: 100%; min-width: 0; border: 0; outline: 0; background: transparent; }
.clear-map-header-search input { color: #fff; font-size: 14px; }
.clear-map-header-search input::placeholder { color: rgba(255, 255, 255, .66); }
.clear-map-header-divider { width: 1px; height: 40px; background: rgba(255, 255, 255, .18); }
.clear-map-icon-button {
  width: 44px; height: 44px; display: inline-flex; align-items: center; justify-content: center;
  border: 1px solid rgba(255, 255, 255, .16); border-radius: var(--r-md); background: rgba(255, 255, 255, .10); color: #fff;
}
.clear-map-user-chip { display: flex; align-items: center; gap: 11px; min-width: 216px; border: 0; background: transparent; color: #fff; padding: 0; text-align: left; }
.clear-map-user-avatar { width: 40px; height: 40px; border-radius: 50%; background: var(--brand-ink); display: inline-flex; align-items: center; justify-content: center; font-size: 13px; font-weight: 800; color: #fff; flex: 0 0 auto; }
.clear-map-user-meta { min-width: 0; line-height: 1.32; }
.clear-map-user-meta strong, .clear-map-user-meta span { display: block; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.clear-map-user-meta strong { font-size: 14px; font-weight: 800; }
.clear-map-user-meta span { font-size: 12px; color: rgba(255, 255, 255, .72); }

.clear-map-primary-nav {
  display: flex;
  align-items: center;
  gap: 7px;
  padding: 4px 18px 10px;
  overflow-x: auto;
  border-top: 0;
}
.clear-map-nav-link, .clear-map-nav-button {
  height: 36px;
  display: inline-flex;
  align-items: center;
  gap: 9px;
  padding: 0 13px;
  border-radius: var(--r-md);
  border: 0;
  background: transparent;
  color: rgba(255, 255, 255, .86);
  text-decoration: none;
  font-size: 13px;
  font-weight: 700;
  white-space: nowrap;
  flex: 0 0 auto;
}
.clear-map-nav-link.active { background: #fff; color: var(--clear-blue-dark); box-shadow: var(--sh-1); }
.clear-map-nav-link:not(.active):hover, .clear-map-nav-button:not(:disabled):hover { background: rgba(255, 255, 255, .10); }
.clear-map-nav-button:disabled { opacity: 1; }
.clear-map-nav-icon { width: 18px; height: 18px; display: inline-flex; align-items: center; justify-content: center; }
.clear-map-nav-icon svg, .clear-map-button-icon svg, .clear-map-search-icon svg { width: 100%; height: 100%; display: block; }

.clear-map-workspace {
  display: grid;
  grid-template-columns: var(--clear-left-width) minmax(0, 1fr) var(--clear-right-width);
  min-width: 0;
  min-height: 0;
  height: 100%;
  overflow: hidden;
  background: var(--clear-map-bg);
}

.clear-map-sidebar, .clear-map-detail-panel { background: var(--clear-panel); min-height: 0; overflow-y: auto; overflow-x: hidden; }
.clear-map-sidebar { border-right: 1px solid var(--clear-border); padding: 18px 20px 0; display: flex; flex-direction: column; }
.clear-map-panel-section + .clear-map-panel-section { margin-top: 22px; padding-top: 18px; border-top: 1px solid var(--clear-border); }
.clear-map-section-header { display: flex; align-items: center; justify-content: space-between; gap: 10px; margin-bottom: 12px; }
.clear-map-section-kicker { font-size: 11px; font-weight: 800; letter-spacing: .16em; color: var(--muted); text-transform: uppercase; }
.clear-map-reset-button { border: 0; background: transparent; color: var(--clear-blue); font-size: 12px; font-weight: 700; padding: 5px 0; }

.clear-map-layer-list { display: grid; gap: 3px; }
.clear-map-layer-item { min-height: 43px; display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; gap: 8px; border-radius: var(--r-md); padding: 5px 2px; }
.clear-map-layer-item.is-active { background: var(--clear-blue-soft); }
.clear-map-layer-item.is-regulatory-active { background: color-mix(in srgb, var(--sig-reg) 10%, var(--surface)); }
.clear-map-layer-item.is-community-active { background: color-mix(in srgb, var(--sig-com) 10%, var(--surface)); }
.clear-map-layer-item.disabled { color: var(--clear-gray); }
.clear-map-layer-item label { display: flex; align-items: center; gap: 10px; min-width: 0; }
.clear-map-layer-item input { width: 15px; height: 15px; accent-color: var(--brand-ink); flex: 0 0 auto; }
.clear-map-layer-name { min-width: 0; font-size: 13px; font-weight: 700; color: var(--clear-text); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.clear-map-layer-item[data-clear-layer-row="regulatory-air-monitors"] .clear-map-layer-name,
.clear-map-layer-item[data-clear-layer-row="community-air-sensors"] .clear-map-layer-name {
  overflow: visible;
  text-overflow: clip;
}
.clear-map-layer-item.disabled .clear-map-layer-name { color: var(--clear-gray); font-weight: 700; }
.clear-map-layer-state { font-size: 12px; line-height: 1.2; color: var(--ink); text-align: right; min-width: 58px; font-weight: 600; font-family: var(--m); font-variant-numeric: tabular-nums; }
.clear-map-layer-item.is-active .clear-map-layer-state,
.clear-map-layer-item.is-regulatory-active .clear-map-layer-state,
.clear-map-layer-item.is-community-active .clear-map-layer-state { font-weight: 800; }
.clear-map-layer-icon { width: 24px; height: 24px; border-radius: 50%; flex: 0 0 auto; display: inline-flex; align-items: center; justify-content: center; color: #fff; font-size: 12px; font-weight: 800; box-shadow: none; }
.layer-hospital { background: var(--clear-blue); }
.layer-monitor { background: var(--sig-reg); }
.layer-community { background: var(--sig-com); }
.layer-facility { background: var(--clear-purple); }
.layer-public-school { background: #2563eb; }
.layer-private-school { background: #b45309; }
.layer-postsecondary-school { background: #7c3aed; }
.layer-permit { background: var(--clear-orange); }
.layer-toxics { background: #a64d79; }
.layer-wildfire { background: var(--clear-wildfire); }
.layer-air { background: #7457d8; }
.layer-regulatory-airnow { background: var(--sig-reg); }

.clear-map-layer-subsection { margin: 15px 0 7px; color: var(--muted); font-size: 11px; font-weight: 800; letter-spacing: .16em; text-transform: uppercase; }
.clear-map-layer-subsection:first-of-type { margin-top: 2px; }

.clear-map-filter-list { display: grid; gap: 12px; }
.clear-map-filter label { display: block; margin-bottom: 6px; font-size: 12px; font-weight: 700; color: var(--muted); }
.clear-map-filter select { width: 100%; height: 44px; border-radius: var(--r-md); border: 1px solid var(--clear-border); background: var(--clear-panel-soft); color: var(--clear-text-muted); padding: 0 12px; }
.clear-map-source-status { margin-top: auto; display: flex; align-items: center; gap: 8px; padding: 14px 0 15px; color: var(--clear-text-muted); font-size: 12px; line-height: 1.35; border-top: 1px solid var(--line); background: transparent; }
.clear-map-source-status-dot { width: 8px; height: 8px; border-radius: 50%; background: var(--good); color: var(--good); flex: 0 0 auto; display: inline-flex; align-items: center; justify-content: center; }
.clear-map-source-status-dot::before { content: none; }
.clear-map-source-refresh { margin-left: auto; width: 18px; height: 18px; color: var(--clear-blue); display: inline-flex; align-items: center; justify-content: center; }
.clear-map-source-refresh svg { width: 15px; height: 15px; }

.clear-map-canvas { position: relative; min-width: 0; min-height: 0; height: 100%; overflow: hidden; background: #cddae5; }
.clear-map-surface { position: absolute; inset: 0; width: 100%; height: 100%; }
.clear-map-canvas-search { width: 315px; height: 44px; display: flex; align-items: center; gap: 10px; padding: 0 14px; border-radius: var(--r-md); background: #fff; border: 1px solid rgba(15, 35, 55, .10); box-shadow: var(--sh-1); }
.clear-map-canvas-search .clear-map-search-icon { color: var(--muted); }
.clear-map-canvas-search input { color: var(--clear-text); font-size: 14px; }
.clear-map-canvas-search input::placeholder { color: var(--faint); }

.clear-map-detail-panel { border-left: 1px solid var(--clear-border); display: flex; flex-direction: column; }
.clear-map-detail-header { padding: 19px 24px 16px; border-bottom: 1px solid var(--clear-border); }
.clear-map-detail-header-row { display: grid; grid-template-columns: 42px minmax(0, 1fr) 34px; gap: 13px; align-items: start; }
.clear-map-detail-icon { width: 38px; height: 38px; border-radius: 50%; background: var(--clear-blue); color: #fff; display: inline-flex; align-items: center; justify-content: center; font-size: 18px; font-weight: 800; box-shadow: none; margin-top: 0; }
.clear-map-detail-title-line { display: flex; align-items: center; gap: 8px; min-width: 0; justify-content: flex-start; }
.clear-map-detail-title { margin: 0; color: var(--clear-text); font-size: 18px; line-height: 1.22; font-weight: 700; min-width: 0; letter-spacing: -.01em; }
.clear-map-detail-badge { flex: 0 0 auto; border-radius: 999px; padding: 4px 8px; background: var(--clear-green-soft); color: #137448; font-size: 11px; font-weight: 800; }
.clear-map-detail-close { width: 32px; height: 32px; border: 1px solid var(--clear-border); border-radius: var(--r-md); background: #fff; color: var(--muted); display: inline-flex; align-items: center; justify-content: center; }
.clear-map-detail-address { margin-top: 5px; color: var(--clear-text-muted); font-size: 13px; line-height: 1.42; }
.clear-map-detail-submeta { margin-top: 8px; display: flex; flex-wrap: wrap; gap: 5px 8px; color: var(--muted); font-size: 12px; }
.clear-map-detail-submeta span { display: inline-flex; align-items: center; min-height: 16px; }
.clear-map-detail-submeta span + span::before { content: "•"; margin-right: 8px; color: var(--faint); }
.clear-map-detail-tabs { min-height: 52px; display: flex; align-items: stretch; gap: 0; padding: 0 18px; border-bottom: 1px solid var(--clear-border); overflow-x: auto; }
.clear-map-tab { position: relative; min-width: max-content; border: 0; background: transparent; color: var(--muted); padding: 0 13px; font-size: 13px; font-weight: 800; }
.clear-map-tab[aria-selected="true"] { color: var(--clear-blue); }
.clear-map-tab[aria-selected="true"]::after { content: ""; position: absolute; left: 12px; right: 12px; bottom: 0; height: 3px; border-radius: 999px 999px 0 0; background: var(--clear-blue); }
.clear-map-detail-body { min-height: 0; flex: 1 1 auto; overflow-y: auto; overflow-x: hidden; padding: 20px; background: var(--surface-2); }
.clear-map-detail-empty { display: grid; place-items: center; min-height: 100%; padding: 36px 24px; text-align: center; color: var(--clear-text-muted); }
.clear-map-detail-empty[hidden] { display: none; }
.clear-map-detail-empty-icon { width: 68px; height: 68px; border-radius: var(--r-lg); display: inline-flex; align-items: center; justify-content: center; background: var(--clear-blue-soft); color: var(--clear-blue); font-size: 28px; font-weight: 800; margin-bottom: 16px; }
.clear-map-detail-empty h3 { margin: 0 0 8px; color: var(--clear-text); font-size: 22px; line-height: 1.15; }
.clear-map-detail-empty p { margin: 0; font-size: 14px; line-height: 1.55; max-width: 280px; }
.clear-map-overview-grid { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 10px; margin-bottom: 14px; }
.clear-map-metric-card, .clear-map-detail-card { border: 1px solid var(--clear-border); background: #fff; border-radius: var(--r-lg); box-shadow: var(--sh-1); min-width: 0; }
.clear-map-metric-card { padding: 11px 12px; min-height: 92px; }
.clear-map-metric-label { color: var(--ink); font-size: 12px; line-height: 1.2; font-weight: 700; }
.clear-map-metric-value { margin-top: 6px; color: var(--clear-text); font-size: 13px; line-height: 1.35; font-weight: 700; }
.clear-map-metric-primary { display: block; color: var(--good); font-size: var(--clear-dashboard-value-size); line-height: 1.05; font-weight: 800; letter-spacing: -.02em; }
.clear-map-metric-secondary { display: block; margin-top: 5px; color: var(--muted); font-size: var(--clear-dashboard-secondary-size); line-height: 1.28; font-weight: 700; }
.clear-metric-reading { display: inline-grid; gap: 3px; align-items: start; }
.clear-metric-number { display: block; font-size: 1em; line-height: 1; font-weight: 800; }
.clear-metric-unit { display: block; font-size: var(--clear-dashboard-unit-scale); line-height: 1.05; font-weight: 700; white-space: nowrap; }
.clear-metric-status, .clear-metric-comparison { display: block; }
.clear-metric-comparison { margin-top: 4px; color: var(--muted); font-size: 12.5px; line-height: 1.25; font-weight: 700; }
.clear-map-detail-card { padding: 13px; margin-bottom: 10px; }
.clear-map-detail-card h3 { margin: 0 0 9px; font-size: 15px; color: var(--clear-text); }
.clear-map-detail-card p { margin: 0; color: var(--clear-text-muted); font-size: 13px; line-height: 1.5; }
.clear-map-detail-meta { display: grid; gap: 6px; margin: 0; }
.clear-map-detail-meta div { display: grid; grid-template-columns: 125px minmax(0, 1fr); gap: 10px; padding: 8px 0; border-top: 1px solid var(--surface-3); }
.clear-map-detail-meta div:first-child { border-top: 0; }
.clear-map-detail-meta dt { color: var(--muted); font-size: 12px; font-weight: 700; }
.clear-map-detail-meta dd { margin: 0; color: var(--clear-text); font-size: 12px; font-weight: 700; min-width: 0; overflow-wrap: anywhere; font-family: var(--m); }
.clear-map-condition-grid { display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: 6px; }
.clear-map-condition-source-note { margin-top: 9px; color: var(--clear-text-muted); font-size: 11.5px; line-height: 1.42; }
.clear-map-condition-source-list { margin-top: 12px; display: grid; gap: 8px; }
.clear-map-condition-source-row { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 10px; align-items: start; padding: 10px 12px; border: 1px solid var(--surface-3); border-radius: var(--r-md); background: var(--surface-2); }
.clear-map-condition-source-row strong { display: block; color: var(--clear-text); font-size: 12px; line-height: 1.3; }
.clear-map-condition-source-row span { display: block; color: var(--clear-text-muted); font-size: 11.5px; line-height: 1.45; }
.clear-map-panel-note { margin-top: 10px; color: var(--clear-text-muted); font-size: 11px; line-height: 1.45; }
.clear-map-link-action { margin-top: 10px; border: 1px solid var(--clear-border); border-radius: var(--r-md); background: #fff; color: var(--clear-blue); min-height: 32px; padding: 0 10px; font-size: 12px; font-weight: 800; }
.clear-map-condition { border: 1px solid var(--surface-3); border-radius: var(--r-md); padding: 10px 8px; text-align: center; background: var(--surface-2); min-height: 92px; }
.clear-map-condition strong { display: block; color: var(--ink); font-size: 12px; margin-bottom: 5px; font-weight: 800; text-align: center; }
.clear-map-condition span { display: block; margin-top: 6px; color: var(--clear-text); font-size: var(--clear-condition-value-size); line-height: 1.05; font-weight: 800; text-align: center; letter-spacing: -.01em; }
.clear-condition-reading { display: grid; gap: 2px; align-items: start; }
.clear-condition-number { display: block; font-size: 1em; line-height: 1; font-weight: 800; }
/* The pollutant tile's reading is the primary number on the card. The pre-redesign rule
   sized it explicitly; without this it inherits 1em and the tiles read as body text. */
.clear-tile .clear-condition-number { font-size: 24px; }

.clear-condition-unit { display: block; font-size: var(--clear-condition-unit-scale); line-height: 1.05; font-weight: 700; white-space: nowrap; }
.clear-map-condition small { display: block; margin-top: 5px; color: var(--clear-text-muted); font-size: var(--clear-condition-category-size); line-height: 1.22; font-weight: 700; text-align: center; }
/* The governed condition-category word under each tile value. The rule above is scoped to
   the pre-redesign selector, which no longer matches any element, so the category text was
   left unstyled by the rename. Same declarations, current selector. */
.clear-tile > small { display: block; margin-top: 5px; color: var(--muted); font-size: var(--clear-condition-category-size); line-height: 1.22; font-weight: 800; }

.clear-aqi-category-good { color: var(--clear-aqi-good) !important; }
.clear-aqi-category-moderate { color: var(--clear-aqi-moderate) !important; }
.clear-aqi-category-unhealthy-sensitive { color: var(--clear-aqi-unhealthy-sensitive) !important; }
.clear-aqi-category-unhealthy { color: var(--clear-aqi-unhealthy) !important; }
.clear-aqi-category-very-unhealthy { color: var(--clear-aqi-very-unhealthy) !important; }
.clear-aqi-category-hazardous { color: var(--clear-aqi-hazardous) !important; }
.clear-aqi-category-unavailable { color: var(--clear-aqi-unavailable) !important; }
.clear-map-condition-summary { margin-bottom: 8px; color: var(--muted); font-size: 12px; line-height: 1.45; }
.clear-map-history-subhead { margin: -5px 0 10px; color: var(--muted); font-size: 12px; line-height: 1.4; }
.clear-map-history-status { margin: 0 0 9px; color: var(--muted); font-size: 12px; line-height: 1.45; }
.clear-map-history-timeline { display: grid; gap: 0; min-width: 0; max-width: 100%; overflow: hidden; }
.clear-map-history-row { display: grid; grid-template-columns: minmax(0, 1fr) repeat(3, 44px); column-gap: 6px; align-items: center; min-width: 0; min-height: 29px; }
.clear-map-history-timeline.has-community .clear-map-history-row { grid-template-columns: minmax(72px, 1fr) repeat(3, 30px) 10px repeat(3, 30px); column-gap: 4px; }
.clear-map-history-row[role="row"] + .clear-map-history-row[role="row"] { border-top: 1px solid var(--surface-3); }
.clear-map-history-header { min-height: 21px; color: var(--muted); font-size: 10px; font-weight: 800; letter-spacing: .08em; }
.clear-map-history-group-header { min-height: 22px; padding-top: 1px; border-bottom: 0 !important; }
.clear-map-history-group { text-align: center; white-space: nowrap; }
.clear-map-history-group-regulatory { grid-column: 2 / span 3; }
.clear-map-history-group-community { grid-column: 6 / span 3; }
.clear-map-history-column-header span:not(:first-child) { text-align: right; }
.clear-map-history-community-divider { align-self: stretch; justify-self: center; width: 1px; min-width: 1px; background: var(--line); margin: 4px 0; }
.clear-map-history-group-header .clear-map-history-community-divider { margin: 2px 0; }
.clear-map-history-month { position: relative; display: flex; align-items: center; min-width: 0; color: var(--ink); font-size: 12px; font-weight: 700; }
.clear-map-history-timeline.is-graph { display: block; }
.clear-map-history-month::before { content: ""; width: 7px; height: 7px; margin-right: 9px; border: 2px solid var(--unavail); border-radius: 50%; background: var(--unavail); flex: 0 0 auto; }
.clear-map-history-month.is-pm25-good::before { border-color: var(--clear-history-pm25-good); background: var(--clear-history-pm25-good); }
.clear-map-history-month.is-pm25-moderate::before { border-color: var(--clear-history-pm25-moderate); background: var(--clear-history-pm25-moderate); }
.clear-map-history-month.is-pm25-usg::before { border-color: var(--clear-history-pm25-usg); background: var(--clear-history-pm25-usg); }
.clear-map-history-month.is-pm25-unhealthy::before { border-color: var(--clear-history-pm25-unhealthy); background: var(--clear-history-pm25-unhealthy); }
.clear-map-history-month.is-pm25-very-unhealthy::before { border-color: var(--clear-history-pm25-very-unhealthy); background: var(--clear-history-pm25-very-unhealthy); }
.clear-map-history-month.is-pm25-hazardous::before { border-color: var(--clear-history-pm25-hazardous); background: var(--clear-history-pm25-hazardous); }
.clear-map-history-row:not(:last-child) .clear-map-history-month::after { content: ""; position: absolute; left: 5px; top: 23px; bottom: -20px; width: 1px; background: var(--line); }
/* Governed value, restored: this row's background is the literal #f5f9fd, not --surface-2
   (#f5f8fa). The redesign re-tokenised it and shifted the colour. Same defect class the
   suite already caught once on the condition-category colours. */
.clear-map-history-year-row { width: 100%; padding: 0; border: 0; background: #f5f9fd; color: inherit; font: inherit; cursor: pointer; }
.clear-map-history-year-row:hover { background: var(--surface-3); }
.clear-map-history-year-row:focus-visible { position: relative; z-index: 1; outline: 2px solid var(--focus); outline-offset: -2px; }
.clear-map-history-year { position: relative; display: flex; align-items: center; gap: 7px; min-width: 0; color: var(--ink); font-size: 12px; font-weight: 800; text-align: left; }
.clear-map-history-year::after { content: ""; position: absolute; left: 5px; top: 24px; bottom: -20px; width: 1px; background: var(--line); }
.clear-map-history-year-marker { width: 12px; flex: 0 0 12px; color: var(--muted); font-size: 13px; font-weight: 800; text-align: center; }
.clear-map-history-value { min-width: 0; overflow: hidden; color: var(--ink); font-size: 11px; font-weight: 800; text-align: right; white-space: nowrap; }
.clear-map-history-value.is-missing { color: var(--faint); font-weight: 700; }
.clear-map-history-sources { display: grid; gap: 8px; margin-top: 11px; }
.clear-map-history-source { border-top: 1px solid var(--surface-3); padding-top: 9px; }
.clear-map-history-source h4 { margin: 0 0 5px; color: var(--muted); font-size: 11px; letter-spacing: .08em; font-weight: 800; }
.clear-map-history-source strong { display: block; color: var(--clear-text); font-size: 12px; line-height: 1.35; font-weight: 700; overflow-wrap: anywhere; }
.clear-map-history-source p { margin-top: 3px; color: var(--muted); font-size: 12px; line-height: 1.4; }
.clear-map-history-error { color: #8f4141 !important; }
.clear-map-radius-card { display: grid; gap: 12px; }
.clear-map-radius-toolbar { display: flex; flex-wrap: wrap; gap: 8px; }
.clear-map-radius-toolbar .clear-map-link-action { margin-top: 0; }
.clear-map-radius-toolbar .clear-map-link-action.is-active { background: var(--clear-blue); border-color: var(--clear-blue); color: #fff; }
.clear-map-radius-controls { display: grid; gap: 10px; }
.clear-map-radius-row { display: flex; align-items: center; justify-content: space-between; gap: 10px; }
.clear-map-radius-row label { color: var(--muted); font-size: 12px; font-weight: 700; }
.clear-map-radius-row output { color: var(--clear-text); font-size: 12px; font-weight: 700; }
.clear-map-radius-slider { width: 100%; }
.clear-map-radius-select { width: 100%; height: 36px; border-radius: var(--r-md); border: 1px solid var(--clear-border); background: var(--clear-panel-soft); color: var(--clear-text); padding: 0 10px; }
.clear-map-radius-disclaimer { margin: 0; color: var(--clear-text-muted); font-size: 10.5px; line-height: 1.45; }
.clear-map-radius-status { color: var(--ink); font-size: 12px; line-height: 1.45; }
.clear-map-nearest-card { border: 1px solid var(--clear-border); border-radius: var(--r-lg); padding: 13px; background: #fff; }
.clear-map-nearest-main { display: flex; align-items: center; justify-content: space-between; gap: 10px; }
.clear-map-nearest-name { min-width: 0; color: var(--clear-text); font-size: 13px; font-weight: 700; overflow-wrap: anywhere; }
.clear-map-nearest-badge { border-radius: 999px; padding: 3px 8px; background: var(--clear-green-soft); color: #137448; font-size: 11px; font-weight: 700; white-space: nowrap; }
.clear-map-nearest-meta { margin-top: 8px; color: var(--muted); font-size: 12px; line-height: 1.4; }
.clear-map-nearest-status { margin-top: 8px; display: flex; align-items: center; gap: 7px; color: var(--muted); font-size: 12px; }
.clear-map-comparison-panel { display: grid; gap: 10px; }
.clear-map-comparison-row { display: grid; gap: 3px; padding-bottom: 10px; border-bottom: 1px solid var(--surface-3); }
.clear-map-comparison-row:last-child { border-bottom: 0; padding-bottom: 0; }
.clear-map-comparison-row strong { color: var(--clear-text); font-size: 12px; line-height: 1.25; font-weight: 800; }
.clear-map-comparison-row span { color: var(--muted); font-size: 12px; line-height: 1.35; font-weight: 700; }
.clear-map-monitor-row { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; gap: 8px; align-items: start; padding: 7px 0; border-top: 1px solid var(--clear-border); }
.clear-map-monitor-row:first-child { border-top: 0; padding-top: 0; }
.clear-map-monitor-index { color: var(--clear-text-muted); font-size: 12px; font-weight: 800; padding-top: 2px; }
.clear-map-monitor-copy { min-width: 0; }
.clear-map-nearest-dot { width: 8px; height: 8px; border-radius: 50%; background: var(--good); flex: 0 0 auto; }
.clear-map-nearest-dot.is-aging { background: var(--moderate); }
.clear-map-nearest-dot.is-stale, .clear-map-nearest-dot.is-unavailable { background: #b64747; }
button.clear-map-condition { width: 100%; appearance: none; cursor: pointer; font: inherit; }
.clear-map-condition.is-active { border: 2px solid var(--clear-blue); background: color-mix(in srgb, var(--clear-blue) 6%, #fff); box-shadow: inset 0 0 0 1px #fff; }
.clear-map-condition:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }
.clear-map-condition-state { display: inline-block; margin-top: 7px; padding: 2px 5px; border-radius: 3px; background: var(--clear-blue); color: #fff !important; font-size: 10px !important; font-weight: 800; letter-spacing: .02em; }
.clear-map-actions { display: grid; grid-template-columns: 1fr 1fr 1fr 34px; gap: 8px; padding: 14px 18px 18px; background: #fff; border-top: 1px solid var(--clear-border); }
.clear-map-action { min-height: 38px; border-radius: var(--r-md); border: 1px solid var(--clear-border); background: #fff; color: var(--clear-text); font-size: 12px; font-weight: 800; }
.clear-map-action.primary { background: var(--clear-blue); color: #fff; border-color: var(--clear-blue); }
.clear-map-foundation-marker { width: 22px; height: 22px; display: flex; align-items: center; justify-content: center; padding: 0; border: 0; border-radius: 0; background: transparent; box-shadow: none; cursor: pointer; }
.clear-map-foundation-marker img { display: block; width: 22px; height: 22px; object-fit: contain; }
.clear-map-foundation-marker:focus-visible { outline: none; box-shadow: var(--clear-focus), var(--sh-1); }

/* -----------------------------------------------------------------------
   13. MapLibre chrome overrides + popups
   ----------------------------------------------------------------------- */
.maplibregl-popup-content { border-radius: var(--r-lg); padding: 14px 16px; font-family: var(--f); box-shadow: var(--sh-1); }
.clear-map-popup h3 { margin: 0 0 8px; font-size: 15px; color: var(--clear-text); }
.clear-map-popup p { margin: 0 0 6px; font-size: 12px; color: var(--clear-text-muted); }
.clear-map-popup p:last-child { margin-bottom: 0; }
.clear-map-popup .muted { color: var(--muted); }
.maplibregl-ctrl-bottom-left { display: flex; flex-direction: column; align-items: flex-start; gap: 5px; }
.maplibregl-ctrl-bottom-left .maplibregl-ctrl { margin-left: 14px; margin-bottom: 0; }
.maplibregl-ctrl-bottom-left .maplibregl-ctrl:first-child { margin-bottom: 12px; }
.maplibregl-ctrl-top-right { top: 96px; right: 14px; }
.maplibregl-ctrl-top-right .maplibregl-ctrl { border-radius: var(--r-md); box-shadow: var(--sh-1); overflow: hidden; }
.maplibregl-ctrl-scale { height: 20px; line-height: 18px; padding: 0 7px; border: 1px solid #111; border-top: 0; border-radius: 0; background: rgba(255, 255, 255, .92); color: #111; font-size: 10px; font-weight: 700; box-shadow: none; }
.maplibregl-ctrl-attrib { border: 1px solid rgba(15, 35, 55, .18); border-radius: 5px; background: rgba(255, 255, 255, .88); color: var(--ink); font-size: 10px; box-shadow: none; }
.maplibregl-ctrl-attrib a { color: var(--brand-ink); }

/* -----------------------------------------------------------------------
   14. Removed: the legacy fixed-breakpoint block.
   The pre-redesign stylesheet hid the analytical pane entirely below 1180px
   (.clear-map-detail-panel{display:none}) and the rail below 880px. Those
   selectors no longer exist in the markup, and carrying the rules forward
   would have re-created the exact defect FCLEAR-APP-0002A exists to fix.
   The responsive contract now lives in section 5 on .clear-workspace /
   .clear-rail / .clear-pane, where the pane MOVES between docked, overlay
   and bottom-sheet modes and is never display:none.
   ----------------------------------------------------------------------- */

/* =============================================================================
   15. Inline SVG sizing (defect 1)
   Every inline <svg> in the template carries a viewBox but no width/height,
   so with no rule to constrain it an icon renders at its layout-parent's
   full intrinsic size — the map search icon filling the canvas, the empty
   -state pin filling the pane. Each icon wrapper below gets an explicit box
   and its child svg is told to fill that box exactly; the catch-all at the
   end is the defensive backstop for any icon wrapper not listed here.
   ========================================================================== */
.clear-tier1-icon { width: 16px; height: 16px; display: inline-flex; align-items: center; justify-content: center; margin-right: 8px; flex: 0 0 auto; }
.clear-tier1-icon svg { width: 16px; height: 16px; display: block; }

.clear-action-icon { width: 16px; height: 16px; display: inline-flex; align-items: center; justify-content: center; flex: 0 0 auto; }
.clear-action-icon svg { width: 16px; height: 16px; display: block; }

.clear-search-icon { width: 16px; height: 16px; display: inline-flex; align-items: center; justify-content: center; flex: 0 0 auto; color: var(--faint); }
.clear-search-icon svg { width: 16px; height: 16px; display: block; }

.clear-rail-toggle svg { width: 20px; height: 20px; display: block; }
.clear-pane-close svg { width: 16px; height: 16px; display: block; }
.clear-pane-caveat svg { width: 14px; height: 14px; display: block; flex: 0 0 auto; }
.clear-layer-icon svg { width: 13px; height: 13px; display: block; }
.clear-pane-empty-icon svg { width: 44px; height: 44px; display: block; }
.clear-nearest-jump svg { width: 16px; height: 16px; display: block; }

/* Defensive base rule: any icon inside the app that isn't covered above
   still gets clamped to its box instead of expanding past it. */
/* Icons must not stretch to fill their container. The history chart is the deliberate exception:
   it is sized in real pixels and lives in its own horizontal scroller, and because it carries a
   viewBox, clamping its width does not clip it -- it SCALES THE WHOLE CHART DOWN. That is what
   compressed 13 years into the pane width and shrank the plot vertically at the same time. The
   clamp is scoped rather than removed, because every other inline svg in the app still needs it. */
.clear-app svg:not(.clear-hg-svg) { flex: none; max-width: 100%; }
.clear-hg-svg { flex: none; max-width: none; }

/* =============================================================================
   16. Tier 1 / Tier 2 — remaining missing classes
   ========================================================================== */
.clear-tier1-attribution { display: inline-flex; align-items: baseline; gap: 4px; white-space: nowrap; }
.clear-tier1-attribution-mark { color: rgba(255, 255, 255, .6); font-weight: 500; }

/* Rail affordance, not a product-nav hamburger — hidden above the rail's own
   overlay breakpoint (1120px) so there is never a hamburger above phone
   widths for the tier-1 nav. */
.clear-rail-toggle {
  display: none;
  width: 38px;
  height: 38px;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--line);
  border-radius: var(--r-md);
  background: var(--surface);
  color: var(--ink);
  flex: 0 0 auto;
}
@media (max-width: 1120px) {
  .clear-rail-toggle { display: inline-flex; }
}

.clear-user-avatar {
  width: 30px;
  height: 30px;
  border-radius: 50%;
  background: var(--brand-ink);
  color: #fff;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 11px;
  font-weight: 800;
  flex: 0 0 auto;
}
.clear-user-meta { display: flex; flex-direction: column; min-width: 0; line-height: 1.28; text-align: left; }
.clear-user-meta strong { font-size: 12.5px; font-weight: 700; color: var(--ink); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.clear-user-meta span { font-size: 11px; font-weight: 600; color: var(--muted); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }

/* =============================================================================
   17. Left rail — remaining missing classes
   ========================================================================== */
.clear-rail-section + .clear-rail-section { margin-top: 22px; padding-top: 18px; border-top: 1px solid var(--line); }
.clear-rail-purpose { padding-bottom: 4px; }
.clear-rail-about { padding-bottom: 18px; }
.clear-rail-kicker { font-size: 11px; font-weight: 800; letter-spacing: .14em; text-transform: uppercase; color: var(--muted); }
.clear-rail-head { display: flex; align-items: center; justify-content: space-between; gap: 10px; margin-bottom: 12px; }
.clear-rail-head .clear-rail-kicker { margin-bottom: 0; }
.clear-rail-reset { border: 0; background: transparent; color: var(--brand-ink); font-size: 12px; font-weight: 700; padding: 4px 0; }
.clear-rail-note { margin: 8px 0 0; color: var(--muted); font-size: 12px; line-height: 1.5; }
.clear-rail-attribution { margin-top: 6px; }
.clear-rail-attribution span { color: var(--faint); }
.clear-rail-subhead { margin: 15px 0 7px; color: var(--muted); font-size: 11px; font-weight: 800; letter-spacing: .14em; text-transform: uppercase; }
.clear-rail-subhead:first-of-type { margin-top: 2px; }

.clear-layer-list { display: grid; gap: 2px; }
.clear-layer-item { display: flex; align-items: center; justify-content: space-between; gap: 8px; min-height: 34px; padding: 5px 2px; border-radius: var(--r-sm); }
.clear-layer-item.is-active { background: var(--surface-3); }
.clear-layer-item.is-regulatory-active { background: color-mix(in srgb, var(--sig-reg) 10%, var(--surface)); }
.clear-layer-item.is-community-active { background: color-mix(in srgb, var(--sig-com) 10%, var(--surface)); }
.clear-layer-item label { display: flex; align-items: center; gap: 9px; min-width: 0; flex: 1 1 auto; }
.clear-layer-item input[type="checkbox"] { width: 14px; height: 14px; accent-color: var(--brand-ink); flex: 0 0 auto; }
.clear-layer-icon {
  width: 16px;
  height: 16px;
  border-radius: 4px;
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  color: #fff;
  font-size: 9px;
  font-weight: 800;
}
.clear-layer-name { min-width: 0; font-size: 13px; font-weight: 700; color: var(--ink); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
/* These two names are long and were deliberately un-truncated by an earlier package;
   the generic ellipsis rule above would have silently reintroduced the truncation. */
.clear-layer-item[data-clear-layer-row="regulatory-air-monitors"] .clear-layer-name,
.clear-layer-item[data-clear-layer-row="community-air-sensors"] .clear-layer-name {
  overflow: visible;
  text-overflow: clip;
  white-space: normal;
}
.clear-layer-state { flex: 0 0 auto; min-width: 44px; text-align: right; font-family: var(--m); font-variant-numeric: tabular-nums; font-size: 11.5px; font-weight: 700; color: var(--muted); }
.clear-layer-item.is-active .clear-layer-state,
.clear-layer-item.is-regulatory-active .clear-layer-state,
.clear-layer-item.is-community-active .clear-layer-state { color: var(--ink); font-weight: 800; }

.clear-filter-list { display: grid; gap: 12px; }
.clear-filter label { display: block; margin-bottom: 6px; font-size: 12px; font-weight: 700; color: var(--muted); }
.clear-filter select { width: 100%; height: 38px; border-radius: var(--r-md); border: 1px solid var(--line); background: var(--surface-2); color: var(--ink); padding: 0 10px; font-size: 12.5px; }
.clear-filter select:disabled { color: var(--faint); }
.clear-filter .clear-rail-note { margin-top: 6px; }

.clear-source-status { margin-top: 14px; padding-top: 14px; border-top: 1px solid var(--line); display: flex; align-items: center; gap: 8px; color: var(--muted); font-size: 11.5px; line-height: 1.35; }
.clear-source-status-dot { width: 8px; height: 8px; border-radius: 50%; background: var(--good); flex: 0 0 auto; }

/* =============================================================================
   18. Canvas floating chrome — remaining missing classes
   ========================================================================== */
.clear-canvas-search-row { position: absolute; z-index: 5; top: 16px; left: 18px; }
.clear-canvas-search {
  display: flex;
  align-items: center;
  gap: 8px;
  width: 240px;
  max-width: calc(100% - 36px);
  height: 40px;
  padding: 0 12px;
  border-radius: var(--r-md);
  background: var(--surface);
  border: 1px solid var(--line);
  box-shadow: var(--sh-1);
}
.clear-canvas-search input { flex: 1 1 auto; min-width: 0; border: 0; outline: 0; background: transparent; color: var(--ink); font-size: 13px; font-family: var(--f); }
.clear-canvas-search input::placeholder { color: var(--faint); }

.clear-aq-card {
  position: absolute;
  z-index: 5;
  top: 70px;
  left: 18px;
  width: 220px;
  border-radius: var(--r-md);
  padding: 13px 15px 14px;
  background: rgba(13, 39, 65, .94);
  color: #fff;
  box-shadow: var(--sh-3);
  backdrop-filter: blur(8px);
}
.clear-aq-kicker { font-size: 10px; font-weight: 800; letter-spacing: .13em; text-transform: uppercase; color: rgba(255, 255, 255, .70); font-family: var(--f); }
.clear-aq-title { margin-top: 5px; font-size: 15px; font-weight: 800; line-height: 1.2; }
.clear-aq-body { margin-top: 7px; color: rgba(255, 255, 255, .76); font-size: 12px; line-height: 1.4; }
.clear-aq-value { margin-top: 10px; font-size: 26px; line-height: 1; font-weight: 800; color: #fff; font-family: var(--m); font-variant-numeric: tabular-nums; }
.clear-aq-value[hidden] { display: none; }
.clear-aq-progress { margin-top: 11px; height: 6px; border-radius: 999px; background: rgba(255, 255, 255, .17); overflow: hidden; }
.clear-aq-progress span { display: block; width: 0; height: 100%; background: var(--brand-accent); border-radius: inherit; }
.clear-aq-foot { margin-top: 10px; color: rgba(255, 255, 255, .84); font-size: 11px; line-height: 1.45; }

.clear-legend-card {
  position: absolute;
  z-index: 5;
  left: 14px;
  bottom: 18px;
  width: 200px;
  border-radius: var(--r-md);
  padding: 12px 14px 13px;
  background: var(--surface);
  border: 1px solid var(--line);
  box-shadow: var(--sh-2);
}
.clear-legend-kicker { font-size: 10px; font-weight: 800; letter-spacing: .13em; text-transform: uppercase; color: var(--muted); margin-bottom: 8px; }
.clear-legend-list { list-style: none; margin: 0; padding: 0; display: grid; gap: 7px; }
.clear-legend-list li { display: flex; align-items: center; gap: 8px; font-size: 12px; color: var(--ink); font-weight: 600; }
.clear-legend-dot { width: 9px; height: 9px; border-radius: 50%; flex: 0 0 auto; }
.clear-legend-dot.is-facility { background: var(--clear-purple); }
.clear-legend-dot.is-place { background: var(--clear-blue); }
.clear-legend-dot.is-regulatory { background: var(--sig-reg); }
.clear-legend-dot.is-community { background: var(--sig-com); }

/* =============================================================================
   19. Analytical pane — remaining missing classes
   ========================================================================== */
.clear-pane-identity-row { display: grid; grid-template-columns: auto minmax(0, 1fr) auto; gap: 12px; align-items: start; }
.clear-pane-identity-icon { width: 34px; height: 34px; border-radius: 50%; background: var(--brand-ink); color: #fff; display: inline-flex; align-items: center; justify-content: center; font-size: 15px; font-weight: 800; flex: 0 0 auto; }
.clear-pane-identity-text { min-width: 0; }
.clear-pane-title-line { display: flex; align-items: center; gap: 8px; min-width: 0; }
.clear-pane-title { margin: 0; color: var(--ink); font-size: 16px; line-height: 1.25; font-weight: 700; min-width: 0; letter-spacing: -.01em; }
.clear-pane-badge { flex: 0 0 auto; border-radius: 999px; padding: 3px 8px; background: var(--clear-green-soft); color: #137448; font-size: 10.5px; font-weight: 800; }
.clear-pane-badge[hidden] { display: none; }
.clear-pane-address { margin-top: 4px; color: var(--muted); font-size: 12.5px; line-height: 1.4; }
.clear-pane-submeta { margin-top: 6px; display: flex; flex-wrap: wrap; gap: 4px 8px; color: var(--muted); font-size: 11.5px; }
.clear-pane-submeta span:empty { display: none; }
.clear-pane-submeta span + span:not(:empty)::before { content: "•"; margin-right: 8px; color: var(--faint); }
.clear-pane-close { width: 28px; height: 28px; border: 1px solid var(--line); border-radius: var(--r-sm); background: var(--surface); color: var(--muted); display: inline-flex; align-items: center; justify-content: center; flex: 0 0 auto; }
.clear-pane-close:hover { background: var(--surface-2); }
.clear-pane-caveat { display: inline-flex; align-items: center; gap: 6px; margin-top: 10px; color: var(--muted); font-size: 11.5px; }
.clear-pane-caveat[hidden] { display: none; }

.clear-pane-empty { display: flex; align-items: center; justify-content: center; min-height: 100%; padding: 40px 24px; text-align: center; }
.clear-pane-empty[hidden] { display: none; }
.clear-pane-empty-icon { width: 44px; height: 44px; margin: 0 auto 16px; color: var(--brand-ink); opacity: .55; }
.clear-pane-empty h3 { margin: 0 0 8px; color: var(--ink); font-size: 17px; line-height: 1.25; }
.clear-pane-empty p { margin: 0; color: var(--muted); font-size: 13px; line-height: 1.55; max-width: 280px; }

.clear-pane-note { margin: 10px 0 0; color: var(--muted); font-size: 11.5px; line-height: 1.5; }

.clear-answer-text { margin: 0; }

.clear-metric-row { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 8px; margin-bottom: 10px; }
.clear-metric-card { border: 1px solid var(--line); background: var(--surface); border-radius: var(--r-lg); box-shadow: var(--sh-1); padding: 11px 12px; min-width: 0; min-height: 88px; }
.clear-metric-label { color: var(--ink); font-size: 11.5px; line-height: 1.25; font-weight: 700; }
.clear-metric-value { margin-top: 8px; display: flex; flex-direction: column; gap: 3px; }
.clear-metric-primary { display: block; font-size: 16px; line-height: 1.1; font-weight: 800; color: var(--ink); letter-spacing: -.01em; }
.clear-metric-secondary { display: block; font-size: 11px; line-height: 1.3; font-weight: 700; color: var(--muted); }

.clear-card-kicker { font-size: 11px; font-weight: 700; color: var(--muted); font-family: var(--m); font-variant-numeric: tabular-nums; white-space: nowrap; }
.clear-condition-summary { margin-bottom: 10px; color: var(--muted); font-size: 12px; line-height: 1.5; }

/* Pollutant tile inner typography. Bare tags, not classes, because the
   template leaves the value/meta spans unclassed (only data-attributes
   select them) — targeted by the same attribute list the mono-font rule
   already uses, so the PM10 "not currently served" tile (which uses real
   classes, not these data-attributes) is never touched by this block. */
.clear-tile > strong { display: block; font-size: 11px; font-weight: 700; color: var(--ink); }
[data-clear-condition-pm25], [data-clear-condition-o3], [data-clear-condition-no2],
[data-clear-condition-so2], [data-clear-condition-co] {
  display: block;
  margin-top: 6px;
  font-size: 14px;
  font-weight: 800;
  line-height: 1.05;
  letter-spacing: -.01em;
}
[data-clear-condition-pm25-meta], [data-clear-condition-o3-meta], [data-clear-condition-no2-meta],
[data-clear-condition-so2-meta], [data-clear-condition-co-meta] {
  display: block;
  margin-top: 4px;
  font-size: 9.5px;
  font-weight: 700;
}
.clear-tile-state {
  display: block;
  margin-top: 6px;
  color: var(--brand-ink);
  font-size: 9.5px;
  font-weight: 800;
  letter-spacing: .04em;
  text-transform: uppercase;
}
.clear-tile-state[hidden] { display: none; }
.clear-tiles-hint { margin: 8px 0 0; color: var(--faint); font-size: 10.5px; line-height: 1.4; }

/* PM10 "not currently served" tile — real classes, styled to read as absence
   of data, never as a good/low/zero reading (see section 9's is-unavailable
   rule for the tile-level treatment). */
.clear-tile-unavailable-text { display: block; margin-top: 6px; color: var(--muted); font-size: 11px; font-weight: 700; }
.clear-tile-unavailable-note { display: block; margin-top: 4px; color: var(--unavail); font-size: 10px; font-weight: 600; }

.clear-condition-source-note { margin-top: 10px; color: var(--muted); font-size: 11.5px; line-height: 1.45; }
.clear-condition-source-note[hidden] { display: none; }
.clear-condition-source-list { margin-top: 10px; display: grid; gap: 8px; }
.clear-condition-source-list[hidden] { display: none; }

.clear-history-subhead { margin: -4px 0 10px; color: var(--muted); font-size: 12px; line-height: 1.4; }
.clear-history-status { margin: 0 0 10px; color: var(--muted); font-size: 12px; line-height: 1.45; }
.clear-history-timeline { display: grid; gap: 0; min-width: 0; max-width: 100%; overflow: hidden; }
.clear-history-sources { display: grid; gap: 8px; margin-top: 12px; }

.clear-sources-compact { display: grid; gap: 8px; margin-bottom: 12px; }
.clear-nearest-card { border: 1px solid var(--line); border-radius: var(--r-lg); padding: 13px; background: var(--surface); }
.clear-nearest-main { display: flex; align-items: center; gap: 8px; }
.clear-nearest-name { flex: 1 1 auto; min-width: 0; color: var(--ink); font-size: 13px; font-weight: 700; overflow-wrap: anywhere; }
.clear-nearest-badge { flex: 0 0 auto; border-radius: 999px; padding: 3px 8px; background: var(--surface-3); color: var(--muted); font-size: 10.5px; font-weight: 700; white-space: nowrap; }
.clear-nearest-jump { flex: 0 0 auto; width: 16px; height: 16px; border: 0; background: transparent; color: var(--brand-ink); display: inline-flex; align-items: center; justify-content: center; font-size: 15px; line-height: 1; padding: 0; }
.clear-nearest-jump:disabled { color: var(--faint); cursor: not-allowed; }
.clear-nearest-meta { margin-top: 8px; color: var(--muted); font-size: 11.5px; line-height: 1.4; }
.clear-nearest-status { margin-top: 8px; display: flex; align-items: center; gap: 7px; color: var(--muted); font-size: 11.5px; }
.clear-nearest-dot { width: 7px; height: 7px; border-radius: 50%; background: var(--good); flex: 0 0 auto; }
.clear-nearest-dot.is-unavailable { background: var(--unavail); }
.clear-nearest-dot.is-aging { background: var(--moderate); }
.clear-nearest-dot.is-stale { background: #b64747; }

.clear-link-action { display: inline-flex; align-items: center; gap: 6px; margin-top: 10px; border: 1px solid var(--line); border-radius: var(--r-sm); background: var(--surface); color: var(--brand-ink); height: 30px; padding: 0 10px; font-size: 12px; font-weight: 700; font-family: var(--f); }
.clear-link-action:disabled { color: var(--faint); border-color: var(--line); cursor: not-allowed; }

.clear-radius-status { color: var(--ink); font-size: 12px; line-height: 1.5; }
.clear-radius-controls { display: grid; gap: 10px; margin-top: 10px; }
.clear-radius-sublabel { display: block; margin-top: 4px; color: var(--muted); font-size: 12px; font-weight: 700; }
.clear-radius-slider { width: 100%; accent-color: var(--brand-ink); }
.clear-radius-select { width: 100%; height: 34px; border-radius: var(--r-md); border: 1px solid var(--line); background: var(--surface-2); color: var(--ink); padding: 0 10px; font-size: 12.5px; }

.clear-meta-list { display: grid; gap: 6px; margin: 0; }
.clear-meta-list div { display: grid; grid-template-columns: 120px minmax(0, 1fr); gap: 10px; padding: 8px 0; border-top: 1px solid var(--surface-3); }
.clear-meta-list div:first-child { border-top: 0; }
.clear-meta-list dt { color: var(--muted); font-size: 12px; font-weight: 700; }
.clear-meta-list dd { margin: 0; color: var(--ink); font-size: 12px; font-weight: 700; min-width: 0; overflow-wrap: anywhere; font-family: var(--m); }

.clear-pane-action { min-height: 38px; border-radius: var(--r-md); border: 1px solid var(--line); background: var(--surface); color: var(--ink); font-size: 12px; font-weight: 800; font-family: var(--f); }
.clear-pane-action.is-primary { background: var(--brand-ink); color: #fff; border-color: var(--brand-ink); }
.clear-pane-action:disabled { color: var(--faint); cursor: not-allowed; }
.clear-pane-action.is-primary:disabled { background: color-mix(in srgb, var(--brand-ink) 55%, var(--surface-3)); border-color: transparent; color: rgba(255, 255, 255, .75); }


/* -----------------------------------------------------------------------
   20. FCLEAR-APP-0002A integration pass — phone refinements.
   Captured from a rendered 390x844 screenshot: the tier-1 product nav
   overflowed the header, the lockup descriptor competed with the mark for
   width, and the five-tab strip clipped "Evidence".
   ----------------------------------------------------------------------- */
@media (max-width: 767px) {
  /* The product nav is reached through the rail toggle on phone. Leaving it in
     the header pushed sections off-screen with no way to scroll to them. */
  .clear-tier1-nav { display: none; }
  .clear-tier1 { gap: 10px; }
  .clear-tier1-wordmark { font-size: 15px; }

  /* DESIGN-SPEC 2: on phone the lockup reduces to the mark plus CLEAR. */
  .clear-lockup-descriptor { display: none; }

  /* Five tabs do not fit 390px. Scroll them rather than clipping or wrapping;
     the active tab is scrolled into view by the shell controller. */
  .clear-pane-tabs {
    overflow-x: auto;
    overflow-y: hidden;
    flex-wrap: nowrap;
    scrollbar-width: none;
    -webkit-overflow-scrolling: touch;
  }
  .clear-pane-tabs::-webkit-scrollbar { display: none; }
  .clear-pane-tab { flex: 0 0 auto; }

  /* Pollutant tiles scroll horizontally on phone (DESIGN-SPEC 7). */
  .clear-tiles {
    grid-auto-flow: column;
    grid-auto-columns: minmax(84px, 1fr);
    grid-template-columns: none;
    overflow-x: auto;
    scrollbar-width: none;
  }
  .clear-tiles::-webkit-scrollbar { display: none; }
}

/* -----------------------------------------------------------------------
   21. FCLEAR-APP-0002A — analytical pane renderer output.
   These classes are emitted from JavaScript (Reporting Sources, the source
   segment register, Evidence rows). They were missing rules, which made the
   Reporting Sources row overlap its own text on a 468px pane.
   ----------------------------------------------------------------------- */
.clear-source-row { grid-template-columns: minmax(0, 1fr); gap: 6px; }
.clear-source-row-main { display: flex; align-items: center; gap: 8px; min-width: 0; }
.clear-source-row-name {
  min-width: 0; flex: 1 1 auto;
  font-size: 12.5px; font-weight: 700; color: var(--ink); line-height: 1.35;
  overflow-wrap: anywhere;
}
.clear-source-row-meta {
  min-width: 0;
  font-family: var(--m); font-variant-numeric: tabular-nums;
  font-size: 11px; color: var(--muted); line-height: 1.5; overflow-wrap: anywhere;
}
.clear-source-row.is-absent { background: transparent; border-style: dashed; }
.clear-source-row.is-absent .clear-source-row-name { font-weight: 600; color: var(--muted); }
.clear-source-list { display: grid; gap: 8px; }

.clear-chip {
  flex: 0 0 auto; border-radius: 999px; padding: 2px 8px;
  font-size: 10.5px; font-weight: 800; letter-spacing: .04em; text-transform: uppercase;
  white-space: nowrap; border: 1px solid transparent;
}
.clear-chip.is-regulatory { background: color-mix(in srgb, var(--sig-reg) 12%, #fff); color: var(--sig-reg); border-color: color-mix(in srgb, var(--sig-reg) 26%, #fff); }
.clear-chip.is-community  { background: color-mix(in srgb, var(--sig-com) 12%, #fff); color: var(--sig-com); border-color: color-mix(in srgb, var(--sig-com) 30%, #fff); }

/* Source segment register: one row per governed segment. */
.clear-register { display: grid; gap: 8px; }
.clear-register-row {
  min-width: 0; padding: 9px 11px;
  border: 1px solid var(--line); border-left: 3px solid var(--sig-reg);
  border-radius: var(--r-sm); background: var(--surface-2);
}
.clear-register-row.is-gap { border-left-color: var(--line-strong); background: var(--surface-3); }
.clear-register-head {
  display: flex; align-items: baseline; justify-content: space-between; gap: 10px;
  min-width: 0; margin-bottom: 3px;
}
.clear-register-head strong { min-width: 0; font-size: 12px; color: var(--ink); overflow-wrap: anywhere; }
.clear-register-dist {
  flex: 0 0 auto;
  font-family: var(--m); font-variant-numeric: tabular-nums; font-size: 11px; color: var(--muted);
}
.clear-register-meta {
  font-family: var(--m); font-variant-numeric: tabular-nums;
  font-size: 10.5px; color: var(--muted); line-height: 1.5; overflow-wrap: anywhere;
}
.clear-register-reason { margin-top: 3px; font-size: 11px; font-weight: 700; color: var(--sig-reg); }
.clear-register-row.is-gap .clear-register-reason { color: var(--muted); font-weight: 600; }
.clear-register-flag { margin-top: 3px; font-size: 10.5px; font-weight: 700; color: var(--moderate); }
.clear-inferred { font-weight: 700; color: var(--faint); }

/* Evidence rows. */
.clear-evidence-row { min-width: 0; padding: 9px 0; border-bottom: 1px solid var(--line); }
.clear-evidence-row:last-child { border-bottom: 0; }
.clear-evidence-head { display: flex; align-items: center; gap: 8px; min-width: 0; margin-bottom: 4px; }
.clear-evidence-head strong { min-width: 0; font-size: 12.5px; color: var(--ink); overflow-wrap: anywhere; }
.clear-evidence-meta {
  font-size: 11.5px; color: var(--muted); line-height: 1.55; overflow-wrap: anywhere;
}
.clear-evidence-meta + .clear-evidence-meta { margin-top: 4px; }

/* Answer strip caveat and the FRS registry caveat block. */
.clear-answer-caveat { margin: 6px 0 0; font-size: 11.5px; color: var(--muted); line-height: 1.5; }
.clear-pane-caveat-block {
  margin: 0 0 10px; padding: 8px 10px;
  border: 1px dashed var(--line-strong); border-radius: var(--r-sm);
  background: var(--surface-3); color: var(--muted);
  font-size: 11.5px; line-height: 1.5;
}
.clear-pane-caveat-block[hidden] { display: none; }

/* An unclassified reporting source must be visually distinct from a governed class, never
   borrowing Regulatory or Community styling. Independent QA finding: coercing unknown -> regulatory
   presented a classification the data does not support. */
.clear-chip.is-unknown {
  background: var(--surface-3);
  color: var(--muted);
  border-color: var(--line-strong);
  border-style: dashed;
}
.clear-source-row-name:first-letter { text-transform: none; }

/* =======================================================================
   22. FCLEAR-APP-0002A — VISUAL FIDELITY PASS
   Gate B was rejected: the components were present but had been translated
   into the OLD application's density rather than into the approved design
   language. Every value below is measured against the approved stills in
   mockup-new/clear-design-package/mockups/ (authored at 1600x863, 1280x863
   and 390x783 CSS, exported at DPR 2).
   ======================================================================= */

/* --- 22.1 Analytical workspace width -----------------------------------
   The mockup's pane is ~469px at a 1600px viewport, which is what we had.
   But the operator's principle is "map primary WHILE analysis genuinely
   usable", not "maximise map pixels". On a large monitor the map can afford
   to give up width so the analysis stops reading as a sidebar. */
/* The pane is a flex item sized by flex-basis; the grid rule further up is dead legacy markup, so
   overriding --clear-right-width did nothing. Size the real track, and keep min-width:0 intact. */
@media (min-width: 1600px) { .clear-pane[data-clear-map-detail-panel] { flex-basis: 560px; } }
@media (min-width: 1920px) { .clear-pane[data-clear-map-detail-panel] { flex-basis: 640px; } }
@media (min-width: 2400px) { .clear-pane[data-clear-map-detail-panel] { flex-basis: 720px; } }

/* --- 22.2 Type scale ---------------------------------------------------
   Measured deltas against the stills. Density was being bought with tiny
   type; the mockup buys it with whitespace instead. */
.clear-pane-title { font-size: 19px; line-height: 1.2; letter-spacing: -.015em; }
.clear-pane-address { font-size: 13.5px; line-height: 1.45; }
.clear-pane-submeta { font-size: 13px; line-height: 1.45; }
.clear-pane-tab { font-size: 15px; }
.clear-card-head h3 { font-size: 15px; letter-spacing: .01em; }
.clear-card-kicker { font-size: 11.5px; }
.clear-answer-text { font-size: 15.5px; line-height: 1.6; }
.clear-answer-caveat { font-size: 12.5px; line-height: 1.55; }
.clear-pane-note { font-size: 12.5px; line-height: 1.55; }
.clear-condition-summary { font-size: 13.5px; line-height: 1.5; }
.clear-source-row-name { font-size: 13.5px; }
.clear-source-row-meta { font-size: 12px; }
.clear-evidence-meta { font-size: 12.5px; }
.clear-register-meta { font-size: 11.5px; }
.clear-metric-primary { font-size: 20px; }
.clear-metric-label { font-size: 11.5px; }

/* --- 22.3 Pollutant tiles are a core interaction ------------------------
   Measured 14px for the tile value against ~26px in the still. The primary
   analytical number was rendering at little over half size. Six tiles are
   allowed to wrap rather than be crushed into one unreadable row. */
.clear-tiles {
  grid-template-columns: repeat(auto-fit, minmax(74px, 1fr));
  gap: 7px;
}
@media (min-width: 1600px) { .clear-tiles { grid-template-columns: repeat(6, minmax(0, 1fr)); } }
.clear-tile {
  /* Measured 149px tall against the still's ~80px. The governed active-state chip ("FIND IT NOW")
     adds a line the design does not have, so it is pinned to the tile's foot instead of pushing
     every tile taller -- the grid stretches all tiles to the tallest one. */
  position: relative;
  padding: 10px 8px 9px;
  border-radius: var(--r-md);
  min-height: 86px;
  gap: 1px;
}
.clear-tile > strong { font-size: 13px; letter-spacing: .01em; }
/* The large size belongs to the READING, not to the placeholder word. Applying it to the whole
   value span made "Unavailable" render at 27px and overflow the tile. */
.clear-tile .clear-condition-reading { font-size: 27px; line-height: 1.05; letter-spacing: -.02em; }
.clear-tile .clear-condition-number { font-size: 27px; font-weight: 800; }
.clear-tile [data-clear-condition-pm25].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-o3].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-no2].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-so2].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-co].clear-aqi-category-unavailable {
  display: block;
  /* "Unavailable" is a single governed word that must neither break mid-syllable nor clip. At
     10.5px it measures ~54px and fits the ~69px tile content box. */
  font-size: 10.5px;
  line-height: 1.3;
  font-weight: 700;
  letter-spacing: -.01em;
  overflow-wrap: normal;
  word-break: keep-all;
  hyphens: none;
}
/* The meta line repeats "Unavailable" under the value. One statement is enough on a tile. */
.clear-tile [data-clear-condition-pm25-meta].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-o3-meta].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-no2-meta].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-so2-meta].clear-aqi-category-unavailable,
.clear-tile [data-clear-condition-co-meta].clear-aqi-category-unavailable { display: none; }
.clear-tile .clear-condition-unit { font-size: 11.5px; font-weight: 700; }
.clear-tile > small { font-size: 12px; margin-top: 4px; }
.clear-tile.is-active { box-shadow: inset 0 0 0 2px var(--brand-ink); border-color: var(--brand-ink); }
.clear-tile-state {
  position: absolute;
  left: 0; right: 0; bottom: 3px;
  font-size: 9.5px;
  letter-spacing: .04em;
  text-align: center;
  pointer-events: none;
}
.clear-tile.is-active { padding-bottom: 16px; }
/* The unavailable tile must not shout a large number it does not have. */
.clear-tile.is-unavailable .clear-tile-unavailable-text { font-size: 13px; line-height: 1.3; font-weight: 700; }
.clear-tile.is-unavailable .clear-tile-unavailable-note { font-size: 11.5px; }
.clear-tiles-hint { font-size: 12px; line-height: 1.5; }

/* --- 22.4 History is a primary reason to open the pane ------------------ */
.clear-history-subhead { font-size: 12.5px; }
.clear-history-status { font-size: 12.5px; line-height: 1.5; }
.clear-hg-range { font-size: 12.5px; padding: 5px 10px; }
.clear-hg-series-static, .clear-hg-series-toggle { font-size: 12px; }
.clear-hg-tip { font-size: 12.5px; line-height: 1.6; }
.clear-hg-hint { font-size: 11.5px; }
.clear-hg-vlabel, .clear-hg-ylabel { font-size: 11px; }

/* --- 22.5 Place identity is the anchor of the whole analysis ------------ */
.clear-pane-identity { padding: 18px 20px 14px; }
.clear-pane-identity-icon { width: 40px; height: 40px; border-radius: 11px; font-size: 15px; }
.clear-pane-caveat { font-size: 12px; padding: 6px 10px; }
.clear-pane-badge { font-size: 10.5px; letter-spacing: .06em; }

/* --- 22.6 Card rhythm: the mockup buys clarity with whitespace ---------- */
.clear-card { border-radius: var(--r-lg); }
.clear-card-head { padding: 14px 18px 10px; }
.clear-card-body { padding: 0 18px 16px; }
.clear-tabpanel { padding: 16px 18px 20px; }
.clear-card + .clear-card { margin-top: 14px; }
.clear-answer-strip { padding: 14px 16px; border-radius: var(--r-md); margin-bottom: 14px; }

/* --- 22.7 Left rail joins the same design system ------------------------ */
.clear-rail { padding: 18px 18px 8px; }
.clear-rail-kicker { font-size: 11.5px; letter-spacing: .1em; }
.clear-rail-subhead { font-size: 11px; letter-spacing: .1em; margin: 14px 0 8px; }
.clear-layer-name { font-size: 14px; font-weight: 600; }
.clear-layer-state { font-size: 12px; }
.clear-layer-item { padding: 8px 10px; border-radius: var(--r-sm); }
.clear-rail-note { font-size: 12.5px; line-height: 1.55; }
.clear-filter label { font-size: 12.5px; }
.clear-filter select { font-size: 13.5px; padding: 9px 10px; }
.clear-source-status { font-size: 12px; }
.clear-rail-reset { font-size: 12px; }

/* --- 22.8 Chrome hierarchy: tier 1 is a product bar, tier 2 is the
   working surface. They must not read as two equally dense toolbars.

   Scale matched to the approved Commercial mockup, measured off the mockup PNG rather than
   estimated: the mockup is 3200px wide at DPR 2, so its 84px navy band is 42 CSS px. The previous
   values ran roughly 24% tall in both bands. Geometry, navigation membership, profile behaviour
   and the mark itself are unchanged -- this is scale and spacing only, and the 44px lung tile is
   deliberately preserved because it already matched. ----- */
.clear-tier1 { height: 42px; gap: 14px; padding: 0 16px; }
.clear-tier1-link { font-size: 12.5px; height: 28px; padding: 0 10px; }
.clear-tier1-wordmark { font-size: 14.5px; }  /* +10%: balances the lung mark, stays above the nav labels */
.clear-tier2 { min-height: 55px; height: 55px; gap: 14px; padding: 0 16px; }
.clear-lockup-name { font-size: 18px; letter-spacing: -.01em; }
.clear-lockup-descriptor { font-size: 10.5px; }
.clear-search input { font-size: 14px; }
.clear-action { font-size: 13.5px; }
.clear-user-chip strong { font-size: 13.5px; }

/* The Current Air card carried two helper lines that pushed History below the fold. The design
   keeps one. The second (source provenance) belongs with the sources, not above the graph. */
.clear-tiles-hint { margin: 8px 0 0; }
[data-clear-card="current-air"] [data-clear-condition-note] { display: none; }
.clear-answer-strip { padding: 12px 14px; margin-bottom: 12px; }
.clear-answer-text { font-size: 15px; line-height: 1.5; }
.clear-answer-caveat { margin-top: 4px; }
[data-clear-card="current-air"] .clear-card-body { padding-bottom: 12px; }
[data-clear-card="current-air"] .clear-condition-summary { margin-bottom: 8px; }

/* =======================================================================
   23. FCLEAR-APP-0002A — independent visual review (WS8) findings.
   ======================================================================= */

/* WS8 #3 (HIGH): the mockup shows all six tiles on ONE row at 1600px AND at
   1280px. The auto-fit floor of 74px dropped to three per row inside the
   414px overlay drawer. Hold six columns down to the overlay band. */
@media (min-width: 1121px) { .clear-tiles { grid-template-columns: repeat(6, minmax(0, 1fr)); gap: 5px; } }
@media (min-width: 1121px) and (max-width: 1599px) {
  .clear-tile { padding: 9px 5px 8px; }
  .clear-tile > strong { font-size: 11.5px; }
  .clear-tile .clear-condition-reading, .clear-tile .clear-condition-number { font-size: 21px; }
  .clear-tile [data-clear-condition-pm25].clear-aqi-category-unavailable,
  .clear-tile [data-clear-condition-o3].clear-aqi-category-unavailable,
  .clear-tile [data-clear-condition-no2].clear-aqi-category-unavailable,
  .clear-tile [data-clear-condition-so2].clear-aqi-category-unavailable,
  .clear-tile [data-clear-condition-co].clear-aqi-category-unavailable { font-size: 9px; }
  .clear-tile > small { font-size: 10.5px; }
}

/* WS8 #8 (HIGH): tier 1 must recede behind tier 2. Icons are gone from the
   markup; quieten the remaining link treatment so the rows are not twins. */
.clear-tier1-link { font-weight: 500; opacity: .82; padding: 5px 9px; }
.clear-tier1-link.is-active { opacity: 1; font-weight: 700; }
.clear-tier1-nav { gap: 2px; }

/* WS8 #7 (MEDIUM/HIGH): the rail carried 24px coloured letter badges -- the
   old application's role-badge pattern, absent from the approved design. A
   small colour dot keeps the map-legend value without the admin look. */
.clear-layer-icon {
  width: 9px; height: 9px; min-width: 9px;
  border-radius: 50%;
  font-size: 0; line-height: 0;
  padding: 0; border: 0;
  overflow: hidden;
}
.clear-layer-icon svg { display: none; }

/* WS8 #2 (MEDIUM): "Current Air" and "HISTORY" are adjacent card headers in
   the same pane and the mockup gives them ONE treatment. Make the kicker
   treatment structural rather than dependent on the literal string's case. */
.clear-card-head h3 {
  text-transform: uppercase;
  letter-spacing: .08em;
  font-size: 12.5px;
  color: var(--muted);
}
.clear-pane-title, .clear-peek-name { text-transform: none; letter-spacing: -.015em; }

/* WS8 #10 / section 31: the collapsed-sheet composition is now the compact selected-place
   dashboard, defined in section 31 and shared with desktop and tablet. */

/* The approved phone still shows ONE bar: hamburger, mark, CLEAR. The tier-1 product bar is
   redundant there -- its nav already lives behind the rail toggle and its wordmark repeats the
   lockup -- and removing it returns ~52px to the map, which is primary on phone. */
@media (max-width: 767px) { .clear-tier1 { display: none; } }

/* Final tightening: at six-across the active tile clipped its own reading and state chip. */
@media (min-width: 1600px) {
  .clear-tile { padding: 10px 6px 9px; }
  .clear-tile .clear-condition-reading, .clear-tile .clear-condition-number { font-size: 24px; }
}
.clear-tile-state {
  font-size: 8.5px;
  padding: 0 2px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* =======================================================================
   24. FCLEAR-APP-0002A — user acceptance corrections.
   ======================================================================= */

/* --- 24.1 Pane / map balance -------------------------------------------
   The 560/640/720 escalation overcorrected: on a real desktop it took so much
   width that the map stopped being usable, violating "map remains primary".
   Clamp the pane instead, and switch to overlay EARLIER rather than letting
   rail + pane squeeze the map. */
.clear-pane[data-clear-map-detail-panel] { flex-basis: clamp(468px, 30vw, 500px); }
@media (min-width: 1600px) { .clear-pane[data-clear-map-detail-panel] { flex-basis: clamp(490px, 31vw, 540px); } }
@media (min-width: 1920px) { .clear-pane[data-clear-map-detail-panel] { flex-basis: clamp(520px, 30vw, 580px); } }
@media (min-width: 2400px) { .clear-pane[data-clear-map-detail-panel] { flex-basis: 600px; } }

/* --- 24.2 Desktop pane collapse: let the user reclaim the map ----------
   Presentation state only. Nothing about the selection, the active pollutant,
   the pinned month or the monitor relationship is touched. */
.clear-pane-collapse {
  position: absolute; top: 10px; right: 10px; z-index: 6;
  width: 26px; height: 26px; padding: 0;
  display: inline-flex; align-items: center; justify-content: center;
  border: 1px solid var(--line); border-radius: var(--r-sm);
  background: var(--surface); color: var(--muted); cursor: pointer;
}
.clear-pane-collapse svg { width: 14px; height: 14px; }
.clear-pane { position: relative; }
[data-clear-pane-mode="sheet"] .clear-pane-collapse { display: none; }

/* FCLEAR-APP-0002B Gate B. This is no longer only a user-invoked state: with nothing selected it
   is the LOAD state, because the product is map first and an empty analytical pane must not take
   a third of the workspace before a question has been asked.

   Both guards are deliberate and mirror each other, which is this stylesheet's standing convention
   for the responsive contract (see section 5): the MEDIA QUERY is correct before JS runs, and the
   `:not([data-clear-pane-mode="sheet"])` attribute guard is correct after it does. Either one
   alone would be enough at rest; together they close the FIRST PAINTED FRAME, where the markup
   ships `data-clear-pane-mode="docked"` and `data-clear-pane-collapsed="true"` and the broker has
   not yet resolved the real mode. Without the media guard, a 390px phone would spend that frame
   applying `width: 0` to the bottom sheet -- which would zero-width the phone air-quality rail,
   the very surface FCLEAR-APP-0002A added to stop an empty 238px panel standing over a 390px map.
   The sheet's map-first behaviour is its collapsed detent, never a zero width. */
@media (min-width: 768px) {
  .clear-workspace[data-clear-pane-collapsed="true"]:not([data-clear-pane-mode="sheet"])
    .clear-pane[data-clear-map-detail-panel] {
    flex-basis: 0; width: 0; min-width: 0; border-left: 0; overflow: hidden;
    /* The overlay drawer carries a shadow. At zero width that shadow is all that is left of it,
       and it paints a dark bar down the right edge of a map that is supposed to be unobstructed. */
    box-shadow: none;
  }
  .clear-workspace[data-clear-pane-collapsed="true"]:not([data-clear-pane-mode="sheet"])
    .clear-pane > * { display: none; }
}

/* The reopen affordance. It is anchored to the RIGHT EDGE, vertically centred, rather than to the
   top-right corner, and the reason is a measured collision rather than taste: at and below 1120px
   FCLEAR-APP-0002C's canvas search row spans the full canvas width at `top: 16px` with
   `z-index: 40`, so a top-right button sat underneath it and could not be clicked. The 0002C
   search contract -- one input at every width, that z-index, its 12px gutters -- is deliberately
   NOT retuned to make room; the pane's own affordance moves instead, to the one edge that belongs
   to the pane. One position at every width, so there is no second breakpoint here either.

   `min-height: 44px` is the tap-target floor QA F-8 established for this shell. */
.clear-pane-reopen {
  position: absolute; top: 50%; right: 0; transform: translateY(-50%); z-index: 7;
  display: none; align-items: center; gap: 7px;
  min-height: 44px;
  padding: 9px 12px 9px 11px;
  border: 1px solid var(--line); border-right: 0;
  border-radius: var(--r-md) 0 0 var(--r-md);
  background: var(--surface); color: var(--brand-ink);
  font: 700 13px/1 var(--f); cursor: pointer; box-shadow: var(--sh-2);
}
.clear-workspace[data-clear-pane-collapsed="true"] .clear-pane-reopen { display: inline-flex; }
/* The sheet has no reopen button at any time: its grip and its peek card are its own affordances,
   and the media query keeps that true in the pre-JS frame as well. */
[data-clear-pane-mode="sheet"] .clear-pane-reopen { display: none !important; }
@media (max-width: 767px) { .clear-pane-reopen { display: none !important; } }

/* --- 24.3 Evidence rows: a source name must never render one character per
   line. The grid was letting the identity column shrink to min-content. ---- */
[data-clear-evidence-body] .clear-evidence-row { display: block; width: 100%; }
[data-clear-evidence-body] .clear-evidence-head {
  display: flex; flex-wrap: wrap; align-items: baseline; gap: 6px 8px;
  width: 100%; margin-bottom: 5px;
}
[data-clear-evidence-body] .clear-evidence-head .clear-chip { flex: 0 0 auto; }
[data-clear-evidence-body] .clear-evidence-head strong {
  /* The identity gets the whole remaining line and a real minimum, so it can
     never be squeezed into a one-character column. */
  flex: 1 1 100%;
  min-width: 12rem;
  overflow-wrap: break-word;
  word-break: normal;
  white-space: normal;
  font-size: 13.5px; line-height: 1.35;
}
@media (min-width: 1px) {
  [data-clear-evidence-body] .clear-evidence-meta {
    display: block; width: 100%; min-width: 0;
    white-space: normal; word-break: normal; overflow-wrap: break-word;
  }
}
[data-clear-evidence-body] .clear-source-row,
[data-clear-nearby-body] .clear-source-row { grid-template-columns: minmax(0, 1fr); }
[data-clear-evidence-body] .clear-source-row-name,
[data-clear-nearby-body] .clear-source-row-name {
  flex: 1 1 100%; min-width: 12rem; word-break: normal; overflow-wrap: break-word;
}

/* --- 24.4 Air Quality density: make the sections visually distinct and put
   the segment register behind a disclosure so ordinary use is not a wall. --- */
[data-clear-air-quality-body] .clear-card + .clear-card { margin-top: 16px; }
.clear-register { max-height: 340px; overflow-y: auto; }

/* --- 24.5 Map balance, measured -----------------------------------------
   With rail 320 + pane 468 the map fell to 578px (42%) at 1366 and 652px (45%)
   at 1440 -- the uncomfortable case. Two changes, per the operator's rule that
   the pane should go to overlay rather than the map being squeezed:
     - hold the docked layout only from 1500px up;
     - trim the rail at mid widths, since rail + pane together caused it.
   Measured after: 1366 and 1440 use the overlay drawer with a full-width map;
   1600 gives the map ~52%. */
@media (min-width: 1320px) and (max-width: 1499px) {
  .clear-workspace[data-clear-pane-mode] { --clear-force-overlay: 1; }
}
@media (max-width: 1499px) {
  .clear-pane[data-clear-map-detail-panel] {
    position: absolute; top: 0; right: 0; bottom: 0; z-index: 5;
    flex-basis: auto; width: 414px;
    box-shadow: var(--sh-2);
  }
}
@media (min-width: 1500px) and (max-width: 1699px) { .clear-rail { flex-basis: 280px; width: 280px; } }

/* FCLEAR-APP-0002A: the basemap control names the active basemap. It is a state read-out, not a
   selector, because the governed map estate publishes only the Light style today (drift D-15). */
.clear-action-state {
  display: inline-block; margin-left: 6px; padding: 1px 6px; border-radius: 999px;
  background: var(--chip-bg, rgba(15, 42, 66, .08)); color: var(--muted);
  font-size: 11px; font-weight: 700; letter-spacing: .02em; vertical-align: baseline;
}


/* ============================================================================================
   25. Analytical pane density, matched to the approved mockup (01-commercial-wide-overview).
   The pane had drifted into a documentation panel: verbose prose above the tiles, a tall
   toolbar stack above the plot, and a graph that was a minority of its own card. The mockup is
   a compact analytical workspace -- one insight sentence, one tight tile row, then a large
   graph. Presentation only: no governed fact is removed, and every value still comes from the
   same resolved state.
   ============================================================================================ */

/* --- 25.1 Insight summary: compact, scannable, caveat subordinate -------------------------- */
.clear-answer-strip { padding: 12px 14px; }
.clear-answer-text { font-size: 14.5px; line-height: 1.45; }
.clear-answer-text strong { font-weight: 700; }
.clear-answer-caveat { margin-top: 5px; font-size: 11px; line-height: 1.35; opacity: .72; }

/* --- 25.2 Current Air: the mockup goes header -> tiles, with no prose in between ------------ */
/* The nearest-site line duplicates the card kicker and the Air Quality metric card. Demoted to a
   compact caption rather than a full-width summary block. */
.clear-condition-summary {
  font-size: 11.5px; line-height: 1.3; color: var(--muted);
  margin: 0 0 8px; padding: 0;
}
/* Governed explanatory prose stays in the document for Air Quality and for assistive tech, but
   must not compete with the analysis in the default Overview view. It remains available in the
   Air Quality tab, where the same nodes are rendered. */
[data-clear-card="current-air"] .clear-condition-source-note,
[data-clear-card="current-air"] .clear-condition-source-list { display: none; }
[data-clear-card="current-air"] .clear-card-head { padding-bottom: 8px; }
[data-clear-card="current-air"] .clear-card-body { padding-bottom: 12px; }

.clear-tiles { gap: 6px; }
.clear-tile { min-height: 72px; padding: 6px 3px 5px; gap: 1px; }
.clear-tile > strong { font-size: 11.5px; letter-spacing: .01em; }
/* Size the NUMBER, not the whole reading span: the span also carries the word "Unavailable", and
   at 22px in a 60px tile that word overflowed and broke mid-syllable. */
.clear-tile .clear-condition-number { font-size: 22px; line-height: 1.05; }
.clear-tile-state { font-size: 8.5px; letter-spacing: .04em; padding: 1px 3px; }
/* PM10's governed unavailable copy is kept verbatim and sits in the same shell as the others.
   Only its typography is tightened, so it no longer stretches the whole row to its own height --
   the tile grid sizes every tile to the tallest one. */
.clear-tile.is-unavailable .clear-tile-unavailable-text { font-size: 9.5px; line-height: 1.15; }
.clear-tile.is-unavailable .clear-tile-unavailable-note { font-size: 8.5px; line-height: 1.15; opacity: .8; }

.clear-tiles-hint { margin: 7px 0 0; font-size: 11px; line-height: 1.35; color: var(--muted); }

/* --- 25.3 History: the plot is the point ---------------------------------------------------- */
/* The card carried a subhead AND a status paragraph above a two-row toolbar -- ~160px of chrome
   before any data. The mockup shows one subline, then the graph. */
[data-clear-environmental-history-card] .clear-history-status { display: none; }
[data-clear-environmental-history-card] .clear-history-subhead {
  margin: 0 0 8px; font-size: 11.5px; line-height: 1.3; color: var(--muted);
}
[data-clear-environmental-history-card] .clear-card-head { padding-bottom: 6px; }
.clear-hg-toolbar {
  display: flex; flex-wrap: wrap; align-items: center; gap: 8px;
  margin: 0 0 8px; padding: 0;
}
.clear-hg-hint { margin: 6px 0 0; font-size: 10.5px; line-height: 1.3; opacity: .8; }
.clear-hg-tip { margin-top: 8px; }


/* --- 25.4 Tile row height is set by its tallest tile ---------------------------------------- */
/* The grid stretches every tile to the tallest, so PM10's two-line governed unavailable copy and
   the word "Unavailable" on empty tiles were dictating the height of the whole row -- 107px
   against the mockup's ~62px. The copy is kept verbatim; only its typography is tightened, and
   the "Unavailable" word is sized to fit a 60px tile instead of being clipped to "Unavailabl". */
.clear-tile .clear-condition-reading { font-size: 9.5px; line-height: 1.15; letter-spacing: -.01em; }
.clear-tile .clear-condition-number { font-size: 21px; line-height: 1.02; letter-spacing: -.02em; }
.clear-tile .clear-condition-unit { font-size: 8.5px; line-height: 1.1; }
.clear-tile.is-unavailable .clear-tile-unavailable-text { font-size: 8.5px; line-height: 1.1; }
.clear-tile.is-unavailable .clear-tile-unavailable-note { font-size: 8px; line-height: 1.1; opacity: .75; }
.clear-tile { min-height: 0; padding: 5px 3px 4px; }
.clear-tile > strong { font-size: 11px; line-height: 1.1; }


/* ============================================================================================
   26. Live acceptance corrections. Every item here was raised against the RUNNING product, not
   against a mockup crop, so each is a real interaction defect rather than a styling preference.
   ============================================================================================ */

/* --- 26.1 The collapse control must never sit on top of the close button -------------------- */
/* It was absolutely positioned at top-right of the pane, which is exactly where the identity
   row's close button lives -- two controls, one target. Moved to the pane's LEFT EDGE, vertically
   centred, which is the operator's second suggested model. It now collides with nothing, remains
   available whether or not a place is selected, and keeps its own click target. */
.clear-pane-collapse {
  position: absolute; top: 50%; left: 0; right: auto; transform: translateY(-50%);
  z-index: 6;
  width: 18px; height: 46px; padding: 0;
  display: inline-flex; align-items: center; justify-content: center;
  border: 1px solid var(--line); border-right: 0;
  border-radius: var(--r-sm) 0 0 var(--r-sm);
  background: var(--surface); color: var(--muted); cursor: pointer;
  box-shadow: var(--sh-1);
}
.clear-pane-collapse:hover { color: var(--ink); background: var(--surface-3); }
.clear-pane-collapse svg { width: 12px; height: 12px; }

/* --- 26.2 Every tab must be visible on desktop, never scrolled ------------------------------ */
/* The strip was overflow-x:auto with min-width:max-content tabs, so Evidence fell off the end of
   an ordinary desktop pane. The tabs now share the row and shrink their padding rather than their
   legibility. Horizontal scrolling is retained ONLY for the phone sheet.
   FCLEAR-APP-0002B, Gate B finding F-02: this rule was written for five equal tabs. The merged
   `pulm.ai & Evidence` tab replaced three of them, so the row now carries three tabs of very
   unequal natural width. `flex: 1 1 0` gave each an equal third, which is 419px of content in a
   413px box -- the long label's ink ran into the last pixel column at every width below 1600, and
   at 768 landscape it pushed `Overview` off its left edge too. Tabs now take their natural width
   and shrink only when they must, and the padding is tightened. Legibility is unchanged: the same
   font size, the same nowrap, no truncation and no ellipsis. */
.clear-pane-tabs { overflow-x: visible; padding: 0 6px; }
.clear-pane-tab {
  flex: 0 1 auto; min-width: 0; padding: 0 2px;
  font-size: 12.5px; text-align: center; white-space: nowrap;
}

/* --- 26.3 Five governed tiles, sized to be readable ----------------------------------------- */
/* With PM10 removed the row is five columns instead of six, so each tile gains real width and the
   value/unit/status typography returns to a readable size instead of collapsing. */
.clear-tiles { grid-template-columns: repeat(5, minmax(0, 1fr)); gap: 7px; }
.clear-tile { min-height: 76px; padding: 8px 5px 7px; }
.clear-tile > strong { font-size: 12px; }
.clear-tile .clear-condition-number { font-size: 24px; line-height: 1.05; }
.clear-tile .clear-condition-unit { font-size: 10px; }
.clear-tile .clear-condition-reading { font-size: 12px; line-height: 1.2; }
.clear-tile-state { font-size: 9px; }
@media (min-width: 1121px) {
  .clear-tiles { grid-template-columns: repeat(5, minmax(0, 1fr)); }
}

/* --- 26.4 The sticky footer must not own the bottom of the workspace ------------------------ */
/* Three large buttons, two of them permanently disabled placeholders for actions this release
   does not implement, were consuming vertical space that History needed. Unavailable actions are
   hidden rather than shown as dead affordances; they remain in the DOM for assistive tech and
   return the moment they are enabled. */
.clear-pane-actions { padding: 8px 14px; gap: 8px; }
.clear-pane-action { height: 30px; font-size: 12.5px; padding: 0 10px; }
.clear-pane-action:disabled { display: none; }
.clear-pane-actions:empty { display: none; }

/* --- 26.5 One spacing scale for the pane ---------------------------------------------------- */
/* Gutters were set per-component and drifted. These pin the pane to a single 14px gutter and a
   12px card rhythm so the left/right edges line up from identity to footer. */
.clear-pane-body { padding: 12px 14px 14px; }
.clear-pane-identity { padding: 12px 14px 10px; }
.clear-tabpanel { padding: 12px 0 4px; }
.clear-card + .clear-card { margin-top: 12px; }
.clear-card-head { padding: 12px 14px 8px; }
.clear-card-body { padding: 0 14px 12px; }
.clear-answer-strip { margin-bottom: 12px; }

/* TOUCH GESTURES BELONG TO THE BROWSER.
   ------------------------------------------------------------------------------------------
   This was `touch-action: pan-y`, which was the cause of the iOS defect reported on BOTH Safari
   and Chrome (both are WebKit on iOS, so the common denominator is WebKit plus our code).

   `pan-y` declares that the browser may pan VERTICALLY for a touch starting here -- and therefore
   that it may NOT pan horizontally. Native horizontal scrolling of the timeline was switched off
   at the CSS level, so the only thing that could move it was our JS scrollLeft writes. WebKit then
   arbitrated the gesture, decided the touch belonged to the sheet's vertical scroller, and fired
   pointercancel; our pan stopped there. Each swipe contributed only the few pixels delivered
   before cancellation, which is exactly the reported symptom -- one swipe barely moves, several
   swipes advance the timeline a little.

   `auto` gives the gesture back to WebKit, which already does directional locking natively and
   far better than we can: a horizontal swipe scrolls the nearest horizontally scrollable ancestor
   (this element), a vertical swipe scrolls the nearest vertically scrollable one (the sheet body).
   The History container owns horizontal, the bottom sheet owns vertical, one gesture goes to
   exactly one of them, and momentum/inertia is the platform's. The JS pan now declines touch
   pointers outright, so the two never act on the same touch stream.

   Do not reintroduce a touch-action value that constrains an axis here. */
.clear-hg-scroll { touch-action: auto; }
.clear-hg-scroll.is-panning { user-select: none; }

/* The grab affordance belongs only where drag-to-pan actually exists, which is now mouse and pen
   only. On a touch device the surface scrolls natively and there is no drag cursor to advertise. */
@media (hover: hover) and (pointer: fine) {
  .clear-hg-scroll { cursor: grab; }
  .clear-hg-scroll.is-panning { cursor: grabbing; }
}
.clear-hg-scroll.is-panning .clear-hg-canvas { pointer-events: none; }

/* --- 26.6 History header carries the range controls, as the mockup does -------------------- */
.clear-card-head-with-ranges {
  display: flex; align-items: center; justify-content: space-between; gap: 10px; flex-wrap: nowrap;
}
.clear-card-head-with-ranges .clear-hg-ranges { flex: 0 0 auto; margin: 0; }
/* With the ranges hoisted, the toolbar carries only the series legend, so it collapses from a
   two-row band into one compact line and the plot rises accordingly. */
.clear-hg-toolbar { margin: 0 0 6px; gap: 6px; }
.clear-hg-serieses { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.clear-hg-range { font-size: 11.5px; padding: 3px 7px; }


/* ============================================================================================
   27. Left rail compaction and Environmental Status responsive density.
   Measured against the approved mockup rail: ~209px wide, ~32px row pitch, ~15px checkbox,
   ~30px filter controls, labels on one line. The live rail was 280px with a 38px pitch, 38px
   filters, and BOTH monitor labels wrapping to two lines.
   ============================================================================================ */

/* --- 27.1 Rail geometry --------------------------------------------------------------------- */
/* The rail was also GROWING to 300px as the viewport shrank, which is backwards: it took map
   width exactly when the map had least to spare. It is now a fixed compact width, so tightening
   it returns width to the map rather than consuming more. */
.clear-rail { flex-basis: 248px; width: 248px; padding: 14px 12px 8px; }
@media (min-width: 1500px) and (max-width: 1699px) { .clear-rail { flex-basis: 248px; width: 248px; } }
@media (min-width: 1700px) { .clear-rail { flex-basis: 256px; width: 256px; } }

/* --- 27.2 Layer rows: a compact layer controller, not a settings form ----------------------- */
.clear-rail-head { margin-bottom: 8px; }
.clear-rail-kicker { font-size: 10.5px; letter-spacing: .12em; }
.clear-rail-subhead { margin: 12px 0 5px; font-size: 10.5px; letter-spacing: .12em; }
.clear-layer-item {
  min-height: 30px; padding: 4px 7px; border-radius: var(--r-sm);
  display: flex; align-items: center; gap: 7px;
}
.clear-layer-item label { display: flex; align-items: center; gap: 7px; min-width: 0; flex: 1 1 auto; }
.clear-layer-item input[type="checkbox"] { width: 15px; height: 15px; flex: 0 0 auto; margin: 0; }
.clear-layer-icon { flex: 0 0 auto; }
/* One line. "Regulatory Monitors" and "Community Sensors" both wrapped at the old width; they fit
   here. The governed no-ellipsis rule for those two names is preserved -- this clips rather than
   truncating with an ellipsis, exactly as before. */
.clear-layer-name { font-size: 13px; font-weight: 600; white-space: nowrap; min-width: 0; }
.clear-layer-state { font-size: 11.5px; flex: 0 0 auto; margin-left: auto; }

/* --- 27.3 Filters: shorter controls, tighter stack ------------------------------------------ */
.clear-filter { margin-top: 8px; }
.clear-filter label { font-size: 11.5px; margin-bottom: 3px; }
.clear-filter select { height: 30px; padding: 0 8px; font-size: 12.5px; }
.clear-rail-reset { font-size: 11.5px; }

/* --- 27.4 About this data stays a footnote, not a section ----------------------------------- */
.clear-rail-note { margin-top: 10px; font-size: 11.5px; line-height: 1.4; }

/* --- 27.5 Environmental Status: three densities, keyed to the MAP viewport ------------------ */
/* The card is good at large widths and must not be redesigned. It simply has to tighten as the
   map is squeezed. Pollutant, value, unit, condition and freshness survive at every density --
   only secondary framing is dropped, and it remains available in the analytical pane. */

/* COMPACT: smaller desktop and tablet. */
@media (max-width: 1439px) {
  .clear-aq-card { max-width: 232px; padding: 10px 12px; }
  .clear-aq-kicker { font-size: 9.5px; letter-spacing: .1em; }
  .clear-aq-title { font-size: 13px; }
  .clear-aq-value { font-size: 22px; }
  /* Network summary and represented-location count are framing, not the reading. */
  .clear-aq-body { display: none; }
  .clear-aq-progress { display: none; }
  .clear-aq-foot { font-size: 10.5px; line-height: 1.3; }
}

/* MINIMAL: narrow map. A status chip, not a panel over the map. */
@media (max-width: 900px) {
  .clear-aq-card {
    max-width: 168px; padding: 7px 9px; border-radius: var(--r-sm);
  }
  .clear-aq-kicker { font-size: 9px; }
  /* "Environmental Status" is the card's own framing; the pollutant kicker already names what
     this is, so the title is dropped before any governed value is. */
  .clear-aq-title { display: none; }
  .clear-aq-value { font-size: 19px; line-height: 1.1; }
  .clear-aq-foot { font-size: 9.5px; line-height: 1.25; }
  /* FCLEAR-APP-0002B Gate B, A4: `display: none` here was a SECOND, CSS-side legend state model
     that the Legend button could not see. The narrow-map decision it encoded (the legend is not a
     permanent overlay on a squeezed map) is preserved exactly -- it is now expressed as the
     shell's initial/auto-close state in section 34.4, driven by this same 900px boundary, so
     there is one source of truth and the button can never disagree with the panel. */
}


/* --- 27.6 Two corrections found by measuring the rendered rail ------------------------------ */

/* The rail was still 300px in the overlay pane-mode band, because
   `.clear-workspace[data-clear-pane-mode="overlay"] .clear-rail` outranks a bare `.clear-rail`.
   Matched here at the same specificity so the compact width holds in every mode. */
.clear-workspace[data-clear-pane-mode="overlay"] .clear-rail,
.clear-workspace[data-clear-pane-mode="docked"] .clear-rail { flex-basis: 248px; width: 248px; }
@media (max-width: 1319px) { .clear-rail { flex-basis: 248px; width: 248px; } }

/* "Regulatory Monitors" and "Community Sensors" carry a deliberate rule that stops them being
   TRUNCATED WITH AN ELLIPSIS -- an earlier package fixed that by letting them wrap instead. The
   no-ellipsis guarantee is the governed part and is kept exactly (overflow visible, text-overflow
   clip); only the wrapping is dropped, because at the compact rail width both names fit on one
   line. If a future translation did overflow, it clips -- it never renders a misleading ellipsis. */
.clear-layer-item[data-clear-layer-row="regulatory-air-monitors"] .clear-layer-name,
.clear-layer-item[data-clear-layer-row="community-air-sensors"] .clear-layer-name {
  overflow: visible;
  text-overflow: clip;
  white-space: nowrap;
}
/* The count column reserved 44px on a 248px rail, which is what pushed those two names to wrap. */
.clear-layer-state { min-width: 28px; }


/* --- 28. Map controls follow the visible map, not the container edge ------------------------ */
/* --clear-map-ctrl-right is published by clearShellUpdateMapControlOffset from the MEASURED
   overlap between the analytical pane and the map container, so the controls stay inside the
   visible map in docked, overlay, collapsed and sheet modes without any breakpoint-keyed magic
   number. The fallback keeps them correct before the first measurement. */
.maplibregl-ctrl-top-right { right: var(--clear-map-ctrl-right, 14px); }
.maplibregl-ctrl-bottom-right { right: var(--clear-map-ctrl-right, 14px); bottom: var(--clear-map-ctrl-bottom, 14px); }
.maplibregl-ctrl-bottom-left { bottom: var(--clear-map-ctrl-bottom, 14px); }


/* =======================================================================
   29. FCLEAR-APP-0002A — phone no-selection state.

   Reported outstanding item: on phone with nothing selected the collapsed
   bottom sheet rendered a 238px empty white panel over a 390px-wide map.
   Every child of the collapsed sheet is display:none except the peek, and
   the peek is hidden until a place is loaded -- so the sheet was 238px of
   nothing, taking 28% of an 844px viewport from the map that the binding
   decision calls primary.

   The sheet now reduces to a thin air-quality status rail in exactly that
   state. It carries the governed monitoring-network reading and is accented
   with the governed condition colour. It is presentation only: it does not
   fetch, does not change the selection, and does not alter the sheet's
   collapsed/expanded contract -- the grip still expands to the full panel,
   where the "Select a place on the map" guidance lives.
   ======================================================================= */

.clear-pane-idle { display: none; }
.clear-pane-idle[hidden] { display: none !important; }

/* Shown ONLY in the sheet's collapsed state with nothing selected. `:not([data-clear-detail-state
   ="loaded"])` covers the initial, cleared, loading and error states alike -- in none of them is
   there a place to describe, and in all of them the network summary is still the honest answer. */
.clear-workspace[data-clear-pane-mode="sheet"]:not([data-clear-detail-state="loaded"])
  .clear-pane[data-clear-pane-state="collapsed"] .clear-pane-idle:not([hidden]) {
  display: flex;
  align-items: center;
  gap: 11px;
  padding: 2px 16px 14px;
}

/* The rail replaces the fixed 238px sheet height with its own content height. Specificity beats
   both the `@media (max-width: 767px) .clear-pane` rule and the pane-mode rule, so no media query
   is needed here and the two stay in agreement. */
.clear-workspace[data-clear-pane-mode="sheet"]:not([data-clear-detail-state="loaded"])
  .clear-pane[data-clear-pane-state="collapsed"] {
  height: auto;
}

/* Condition-colour accent. The category classes set `color` (with !important), so painting the
   bar with currentColor reuses the governed category mapping exactly rather than restating it --
   including `unavailable`, which must read as absent, not as a reading. */
.clear-idle-accent {
  flex: 0 0 auto;
  width: 4px;
  align-self: stretch;
  min-height: 34px;
  border-radius: 999px;
  background: currentColor;
}

.clear-idle-text { min-width: 0; flex: 1 1 auto; }
.clear-idle-kicker {
  font-size: 9.5px; font-weight: 800; letter-spacing: .12em;
  text-transform: uppercase; color: var(--muted); font-family: var(--f);
}
.clear-idle-kicker sub { font-size: .8em; }
.clear-idle-meta {
  margin-top: 3px;
  font-size: 11.5px; line-height: 1.35; color: var(--muted);
}
.clear-idle-reading {
  flex: 0 0 auto;
  font-family: var(--m); font-variant-numeric: tabular-nums;
  font-size: 22px; font-weight: 800; line-height: 1; letter-spacing: -.02em;
  white-space: nowrap;
}
.clear-idle-reading small { font-size: 11px; margin-left: 4px; font-family: var(--f); font-weight: 700; }
/* Absence is stated in words at body size, never in the numeral's display size. */
.clear-idle-reading.clear-aqi-category-unavailable { font-size: 12px; font-family: var(--f); font-weight: 700; }

/* On phone the idle rail carries the identical governed network reading, so the floating card
   would be a second copy of the same fact over the smallest map in the estate. It is suppressed
   only while the rail is showing it, and returns the moment a selection replaces the rail with
   the place peek -- so exactly one surface states the network summary at any time. */
@media (max-width: 767px) {
  .clear-workspace[data-clear-pane-mode="sheet"]:not([data-clear-detail-state="loaded"]) .clear-aq-card { display: none; }
}


/* =======================================================================
   30. FCLEAR-APP-0002A — Current Air tile row: one column per governed tile.

   CORRECTED RATIONALE. This section first claimed the row still declared SIX
   columns for five tiles, and that the resulting narrow tile was what made the
   row ~100px against the mockup's ~72px. That was a misdiagnosis, caught by
   independent QA (kimi-01) and confirmed against the pre-change stylesheet:
   section 26.3 already declared `repeat(5, minmax(0, 1fr))` both globally and
   at >=1121px, and both sit AFTER the `repeat(6)` rules at equal specificity.
   The row was already five equal columns at every width, so this change does
   NOT alter the rendered column count or tile width.

   What it is still worth keeping is robustness. Two dead `repeat(6)` rules
   remain earlier in this file, live-looking but permanently overridden, and a
   hard-coded count is exactly what goes stale when the governed tile set
   changes. An implicit column track gives one equal column per tile whatever
   the count is, so restoring PM10 when serving exists stays the markup-only
   change the template comment promises, with no stylesheet edit and no third
   stale count to override.

   WHAT THIS DOES NOT FIX: the row-height gap is still open. Measured 106px at
   1600px with real readings against the mockup's ~72px. The excess is in the
   composition, not the column count -- the reading block alone measures 38px
   because the value and its unit are separate stacked lines, and the active
   tile reserves bottom padding for the governed "Find It Now" chip, which the
   mockup does not carry at all. Closing it means changing type scale and
   margins, or dropping governed content. Reported, not silently tuned.
   ======================================================================= */

@media (min-width: 1121px) {
  .clear-tiles {
    grid-auto-flow: column;
    grid-auto-columns: minmax(0, 1fr);
    grid-template-columns: none;
  }
}

/* With the tile ~20% wider the reading and the condition word each fit on one line, so the row
   no longer needs to reserve the height two wrapped lines used to take. The floor stays high
   enough for the tallest governed content -- label, reading, condition and the active-state chip
   pinned to the foot -- and the grid still equalises the tiles to the tallest of them. */
@media (min-width: 1121px) {
  .clear-tile { min-height: 72px; }
}


/* =======================================================================
   31. FCLEAR-APP-0002A — COMPACT SELECTED-PLACE DASHBOARD.

   Gate B defect: selecting a place produced largely linear text with weak
   hierarchy and no grouping -- it read as diagnostic output rather than a
   product surface. It was also two different undesigned surfaces: the
   collapsed sheet's peek on phone, and the pane identity header on desktop
   and tablet, which is why it looked wrong in both places.

   This is ONE component for every breakpoint, built to the approved mockup
   (mockups/04-commercial-phone-collapsed.png): identity with a category chip,
   a ruled metric block, a ruled source row with the distance right-aligned,
   then the expand affordance. Ruled groups and a label/value hierarchy, so it
   is scannable in a second or two.

   It does NOT redesign the expanded analytical pane. The tabs, cards and
   History below it are untouched.
   ======================================================================= */

.clear-pane-peek { display: none; }
.clear-pane-peek[hidden] { display: none !important; }

/* Shown in the collapsed phone sheet, and on desktop/tablet as the pane's identity header. */
[data-clear-pane-mode="sheet"] .clear-pane[data-clear-pane-state="collapsed"] .clear-pane-peek:not([hidden]),
.clear-workspace[data-clear-detail-state="loaded"]:not([data-clear-pane-mode="sheet"]) .clear-pane-peek:not([hidden]) {
  display: block;
  background: var(--surface);
}

/* Where the dashboard renders it IS the identity, so the old linear identity block stands down.
   Its hooks stay in the DOM -- the dashboard mirrors them -- so nothing that reads them breaks. */
[data-clear-pane-mode="sheet"] .clear-pane[data-clear-pane-state="collapsed"] .clear-pane-identity,
.clear-workspace[data-clear-detail-state="loaded"]:not([data-clear-pane-mode="sheet"]) .clear-pane-identity {
  display: none;
}

/* The collapsed sheet shows the compact dashboard and NOTHING else. Without this the tabs, the
   panel body and the sticky footer all render underneath it -- which the fixed 238px height used
   to hide by clipping, so releasing that height unfolded the entire analytical pane into the
   collapsed state. The clip was doing this rule's job; now the rule does it. */
[data-clear-pane-mode="sheet"] .clear-pane[data-clear-pane-state="collapsed"] .clear-pane-tabs,
[data-clear-pane-mode="sheet"] .clear-pane[data-clear-pane-state="collapsed"] .clear-pane-body,
[data-clear-pane-mode="sheet"] .clear-pane[data-clear-pane-state="collapsed"] .clear-pane-actions {
  display: none;
}

/* Measured off mockups/04-commercial-phone-collapsed.png (780x1566 @DPR2) and reconciled against
   prototype/clear-prototype.html, which carries the real code for this state. Sizes below are the
   measured values, not approximations. Divergences from the package are marked DIVERGENCE with a
   reason; everything else is the package.

   --- identity --------------------------------------------------------------------------------- */
.clear-peek-head {
  display: flex;
  align-items: flex-start;
  gap: 10px;
  padding: 12px 15px 10px;
  border-bottom: 1px solid var(--line);
}
/* The package hides the icon square in the collapsed phone sheet but shows it in the docked and
   overlay identity, so it follows the breakpoint rather than the component. */
.clear-peek-icon {
  flex: 0 0 auto;
  width: 30px; height: 30px;
  display: inline-flex; align-items: center; justify-content: center;
  border-radius: var(--r-sm);
  background: var(--brand-ink); color: #fff;
  font: 800 13px/1 var(--f);
}
[data-clear-pane-mode="sheet"] .clear-peek-icon { display: none; }

.clear-peek-headtext { flex: 1 1 auto; min-width: 0; }
.clear-peek-nameline { display: flex; align-items: center; gap: 7px; flex-wrap: wrap; min-width: 0; }
.clear-peek-name {
  margin: 0; min-width: 0;
  font-size: 14px; font-weight: 700; line-height: 1.4;
  color: var(--ink); letter-spacing: -.01em;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
/* Mono, uppercase, tinted from the same token family the mockup samples exactly. */
.clear-peek-badge {
  flex: 0 0 auto;
  padding: 2px 6px; border-radius: 4px;
  background: color-mix(in srgb, var(--good) 13%, transparent);
  color: var(--good);
  font-family: var(--m); font-size: 9.6px; font-weight: 600;
  letter-spacing: .07em; text-transform: uppercase; white-space: nowrap;
}
.clear-peek-badge[hidden] { display: none; }
.clear-peek-locality {
  margin-top: 2px; font-size: 11.85px; line-height: 1.5; color: var(--muted);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
/* DIVERGENCE: the package hides the classifier line in the collapsed sheet. Kept because the
   operator's brief requires the place type on the compact surface at every breakpoint. */
.clear-peek-type {
  margin-top: 1px; font-size: 11px; line-height: 1.45; color: var(--muted);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.clear-peek-type[hidden] { display: none; }
.clear-peek-close {
  flex: 0 0 auto;
  width: 28px; height: 28px; padding: 0;
  display: grid; place-items: center;
  border: 0; border-radius: var(--r-sm);
  background: none; color: var(--muted); cursor: pointer;
}
.clear-peek-close:hover { background: var(--surface-2); color: var(--ink); }
.clear-peek-close:focus-visible { outline: 2px solid var(--focus); outline-offset: 1px; }

/* DIVERGENCE: the package hides the registry caveat in the collapsed sheet, which reads against
   DESIGN-SPEC 4.1 calling it "a permanent affordance, not a tooltip-only disclosure". Kept
   visible: suppressing a governed disclosure is the riskier of the two readings. Recorded as
   drift for an operator decision rather than settled here. */
.clear-pane-peek .clear-pane-caveat { margin: 10px 15px 0; }
/* QA F-4/F-5/F-6: the card carried three different row gutters (11/9/10px), a 2px stagger between
   the header's 13px inset and the body's 15px, and one full-bleed rule against one inset rule.
   Unified: a single 15px gutter, a single 10px vertical step, and both rules full-bleed. The
   package's own 13px/15px asymmetry is an artefact of its two containers and is not reproduced. */

/* --- the pollutant metric block ------------------------------------------------------------- */
/* The number is INK, not the condition colour. The package carries the air-quality condition in
   exactly one place -- a 5px dot before the condition word -- and nowhere else: not the numeral,
   not the condition text, not a bar, tint or border. */
.clear-peek-metric {
  display: flex; align-items: center; gap: 11px;
  padding: 10px 15px;
}
.clear-peek-metric-value {
  flex: 0 0 auto;
  font-family: var(--m); font-variant-numeric: tabular-nums;
  font-size: 24px; font-weight: 600; line-height: 1; color: var(--ink);
  /* QA F-1: without Plex Mono the fallback's wide digit advance made "2.8" read as separate
     glyphs. Tightened just enough to restore the mockup's rendered density. */
  letter-spacing: -.02em;
}
.clear-peek-metric-meta { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.clear-peek-metric-label { font-size: 11.2px; font-weight: 600; color: var(--muted); line-height: 1.5; }
.clear-peek-metric-unit { margin-left: 4px; }
.clear-peek-metric-cond {
  display: flex; align-items: center; gap: 4px;
  font-size: 11.5px; line-height: 1.5; color: var(--muted);
  min-width: 0;
}
.clear-peek-dot { width: 5px; height: 5px; border-radius: 50%; background: currentColor; flex: 0 0 auto; }
/* Absence is stated in words at body size, never as a large numeral. */
.clear-peek-metric.is-unavailable .clear-peek-metric-value {
  font-family: var(--f); font-size: 12px; font-weight: 600; color: var(--muted);
}

/* --- the reporting source row --------------------------------------------------------------- */
/* No caption above this row: in the package the BADGE is the label. The row is the series, the
   name and the distance on one line, the distance flushed right. */
.clear-peek-source {
  display: flex; align-items: center; flex-wrap: wrap; gap: 9px;
  padding: 10px 15px;
  border-top: 1px solid var(--line);
}
.clear-peek-source .clear-source-badge {
  flex: 0 0 auto; min-width: 74px; text-align: center;
  padding: 2px 6px; border-radius: 4px;
  font-family: var(--m); font-size: 9.6px; font-weight: 600;
  letter-spacing: .07em; text-transform: uppercase;
}
.clear-peek-source-name {
  flex: 1 1 auto; min-width: 0;
  font-size: 12.65px; font-weight: 400; color: var(--ink); line-height: 1.5;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.clear-peek-source-dist {
  flex: 0 0 auto;
  font-family: var(--m); font-variant-numeric: tabular-nums;
  font-size: 11.5px; color: var(--muted); white-space: nowrap;
}
/* DIVERGENCE: the package has no caveat line here. Kept, quietly, because the brief requires that
   the compact surface never imply the reading was taken at the selected place, and because the
   badge and distance alone do not say where the measurement happened. */
.clear-peek-source-caveat {
  flex: 1 0 100%; margin: 1px 0 0;
  /* QA F-7: this is the card's only governance disclaimer and it measured 2.98:1 against white,
     well under the 4.5:1 floor for small text. --muted is 4.91:1, and the size comes up with it. */
  font-size: 11px; line-height: 1.45; color: var(--muted);
}
.clear-peek-source-absent {
  flex: 1 1 100%; margin: 0;
  font-size: 12px; line-height: 1.45; color: var(--muted);
}

/* --- expand affordance ----------------------------------------------------------------------- */
.clear-peek-action {
  display: flex; align-items: center; justify-content: center; gap: 6px;
  width: calc(100% - 30px); margin: 0 15px 12px;
  padding: 9px;
  border: 0; border-radius: var(--r-sm);
  background: var(--brand-ink); color: #fff;
  font-family: var(--f); font-size: 12.8px; font-weight: 600; line-height: 1.5;
  cursor: pointer;
}
.clear-peek-action svg { width: 13px; height: 13px; }
.clear-peek-action:focus-visible { outline: 2px solid var(--focus); outline-offset: 2px; }
/* On desktop and tablet the full analysis is already on screen below this card, so an expand
   control would point at nothing. The tabs are the affordance there. */
.clear-workspace:not([data-clear-pane-mode="sheet"]) .clear-peek-action { display: none; }
.clear-workspace:not([data-clear-pane-mode="sheet"]) .clear-pane-peek { padding-bottom: 12px; border-bottom: 1px solid var(--line); }

/* The collapsed sheet takes the card's own height. At the package's fixed 238px the expand button
   fell outside the sheet and off the bottom of a 390x844 screen entirely -- measured 273px of card
   in a 238px box. Letting the height follow the content is what keeps the affordance reachable,
   and it is the same treatment the no-selection rail already uses, so the sheet has one rule for
   its height rather than two competing constants. The expanded state is untouched. */
.clear-workspace[data-clear-pane-mode="sheet"][data-clear-detail-state="loaded"]
  .clear-pane[data-clear-pane-state="collapsed"] {
  height: auto;
}

/* QA F-8: 28px and 37px controls are under the ~40px tap-target floor, and on phone the close is
   the card's only dismiss control. Enlarged by hit area rather than by appearance -- the negative
   margins keep the glyph exactly where the mockup puts it. */
@media (max-width: 767px) {
  .clear-peek-close { width: 40px; height: 40px; margin: -6px -6px -6px 0; }
  .clear-peek-action { padding: 12px 9px; }
}

/* --- mobile: exactly one air-quality surface at a time --------------------------------------- */
/* The thin AQ rail carries the network reading while nothing is selected; this card carries the
   PLACE reading once something is. Showing the floating network card as well put two different
   large readings on one phone screen -- 6.8 network against 3.8 at the place -- which reads as a
   contradiction rather than as two facts. The network summary remains in the expanded pane. */
@media (max-width: 767px) {
  .clear-workspace[data-clear-pane-mode="sheet"] .clear-aq-card { display: none; }
}

/* =============================================================================
   32. FCLEAR-APP-0002A — SEARCH PLACEMENT.

   Two search inputs exist in this shell: the tier-2 header search
   (`.clear-tier2 .clear-search`) and the map-canvas search
   (`.clear-canvas-search-row`). Both are INERT — no listeners, no autocomplete,
   no endpoint. Search FUNCTIONALITY is deferred to a separate governed package;
   this section governs PLACEMENT only.

   The defect: neither carried a responsive rule, so both rendered together at
   every width. Measured on the deployed build, 360px -> 1920px, twenty widths:
   BOTH visible at all twenty.

   Measured usable header capacity (rendered width of the tier-2 search, and
   whether its own placeholder still fits):

       vw     header search   placeholder   tier-2 overflow
       1920      420px          fits            none
       1600      420px          fits            none
       1500      396px          fits            none
       1440      336px          CLIPPED         none
       1366      262px          CLIPPED         none
       1320      216px          CLIPPED         none
       1280      420px          fits            none
       1200      420px          fits            none
       1120      351px          fits            none
       1024      255px          CLIPPED         none
        900      131px          CLIPPED         none
        834       65px          CLIPPED         none
        768       26px          CLIPPED         28px
        390       26px          CLIPPED        269px

   Two things follow from that table.

   1. 1120/1121 is the real capacity boundary. At 1121+ the header is still a
      full desktop bar and the search holds 351-420px. At 1120 and below it
      collapses through 255 -> 131 -> 65 -> 26px, and below 768 the header
      itself overflows the viewport and pushes the user chip off-screen. 1121
      is also where this stylesheet already moves the rail into a dismissible
      drawer and reveals the hamburger, so the header changes character at
      exactly the same width. The search follows that boundary rather than a
      device label.

   2. The 1320-1499 dip is NOT caused by search placement. Above 1320 the
      Legend/Basemap/Help labels are still rendered, so the actions are wide and
      `flex: 1 1 320px; min-width: 0` makes the search absorb every pixel of the
      shortfall. That is why 1366 (262px) is more cramped than 1280 (420px).
      Fixing it means moving the `.clear-action-label` collapse breakpoint,
      which is navigation behaviour, not search placement. REPORTED, NOT
      CHANGED — see drift D-25. A second breakpoint here would flip the search
      between header and canvas twice on the way down, and would hand a 1366px
      laptop the constrained treatment while a smaller 1280px laptop kept the
      desktop one.

   3. Removing the header stub does NOT on its own take tier 2 back inside the
      viewport at every narrow width, and an earlier version of this comment
      claimed it did. It does at 768 and 700, where the 26px stub plus its 14px
      gap was the whole shortfall. Below that the row still overflows, because
      `.clear-tier2-actions` needs 411px by itself -- five 38px icon buttons,
      40px of gaps and a 181px user chip -- against an irreducible tier-2 content
      width of 602px. Measured after this pass: 0 at 768 and 700, then 2 / 122 /
      188 / 212 / 242 at 600 / 480 / 414 / 390 / 360. That is a pre-existing
      header capacity defect with no search component. REPORTED, NOT CHANGED --
      see drift D-26.

   The two queries below are exact complements, so "never both" and "never
   neither" are structural rather than asserted, and both are media queries so
   the state is correct before JS runs — this shell never places the search
   from script. `display: none` (not visibility/opacity) is deliberate: the
   hidden input must leave the accessibility tree and the tab order, or a
   screen-reader or keyboard user still meets two searches.
   ========================================================================== */

/* DESKTOP / LARGE LAPTOP — the header hosts the search; the canvas one is gone. */
@media (min-width: 1121px) {
  .clear-canvas-search-row { display: none; }
}

/* TABLET / MOBILE / CONSTRAINED — the canvas hosts the search; the header one is gone. */
@media (max-width: 1120px) {
  .clear-tier2 .clear-search { display: none; }

  /* The canvas bar is now the ONLY search, so it stops being a 204px shrink-to-fit
     chip and takes over the header search's own size contract instead: grow with
     the space available, but never past the 420px `.clear-search` is itself capped
     to. Nothing here is a new constant — 420px is that cap, and the 12px gutters
     are measured off mockups/04-commercial-phone-collapsed.png (780px at DPR 2, so
     390 CSS px: card edges at 12px and 378px, 366px wide, 40px tall).

     One rule rather than a phone-specific second one, because two would not be
     monotonic: a 700px landscape phone would get a wider bar than a 768px tablet.
     At 390 this resolves to exactly the mockup's 366px, and it is 420px from 480px
     upward — the same width the control has in the header at 1200px and above, so
     the search keeps its size and only changes surface.

     `width: auto` and `max-width` both have to be restated: the base rule pins
     width to 240px and caps it at `calc(100% - 36px)`, and that percentage
     resolves against the absolutely-positioned row's own shrink-to-fit width,
     which silently clamped a declared 320px down to a rendered 284px. */
  .clear-canvas-search-row { left: 12px; right: 12px; }
  .clear-canvas-search { width: auto; max-width: 420px; }
}

/* The vertical offset stays at the 16px this stylesheet uses for all canvas chrome.
   The mockup places the bar 1px below the header's bottom border, which welds a
   bordered card to another border and reads as a rendering artefact rather than as
   intent; 16px also keeps the bar clear of the Environmental Status card at top:70px.
   That single deviation from the mockup is recorded in visual-validation.md so the
   operator can redirect it at Gate B. */

/* =============================================================================
   33. FCLEAR-APP-0002C — SEARCH RESULTS POPUP.

   One popup style serving BOTH placements settled by FCLEAR-APP-0002A: the tier-2
   header search at >=1121px and the map-canvas search at <=1120px. The popup is a
   sibling of whichever `<label>` wraps the input, so it anchors to the input the
   user is actually typing in without either placement needing its own component.

   Anchoring works because the two containers already establish the right
   positioning context: `.clear-tier2` is a flex row in normal flow, and
   `.clear-canvas-search-row` is absolutely positioned over the map. Making the
   label the containing block in both cases keeps one rule instead of two.
   ========================================================================== */

/* ONLY the header label. `.clear-canvas-search-row` is deliberately left alone: FCLEAR-APP-0002A
   positions it `absolute` with `left: 12px; right: 12px` to hit the measured mockup gutters, and
   an absolutely-positioned element is ALREADY a containing block for absolutely-positioned
   descendants. Adding `position: relative` here overrode that `absolute`, the left/right pair
   stopped sizing the row, and the phone search bar's right edge moved from 378px to 402px --
   twelve pixels off the right edge of a 390px viewport. Caught by the 0002A runtime placement
   suite, which is exactly what it is for. */
/* Both LABELS are the containing block for their own popup, which is appended inside them.
   `.clear-canvas-search-row` is deliberately NOT touched: FCLEAR-APP-0002A positions that row
   `absolute` with `left: 12px; right: 12px` to hit the measured mockup gutters, and overriding
   its `position` moved the phone search bar's right edge from 378px to 402px -- off the edge of a
   390px viewport. The label inside it is a static flex item, so making it relative is free. */
.clear-tier2 .clear-search,
.clear-canvas-search { position: relative; }

/* The popup's own z-index is not enough on the canvas.
   `.clear-canvas-search-row` is absolutely positioned with `z-index: 5`, which makes it a
   STACKING CONTEXT: the popup's `z-index: 40` ranks it against its siblings inside that row, not
   against the rest of the map chrome. The Environmental Status card is also `z-index: 5` and
   comes later in the DOM, so at 1120px it painted on top of the first result and made it
   unclickable -- caught by hit-testing, not by any DOM assertion.
   Raising the ROW lifts the whole search context above the other canvas cards. Only the stacking
   is changed here; FCLEAR-APP-0002A's `position`, `left` and `right` on this row are untouched,
   because those are what hold the measured mockup gutters. */
.clear-canvas-search-row { z-index: 40; }

.clear-search-results {
  position: absolute;
  top: calc(100% + 6px);
  left: 0;
  right: 0;
  z-index: 40; /* above the map canvas chrome (z-index 5) and the pane overlay's shadow */
  margin: 0;
  padding: 4px;
  list-style: none;
  max-height: 320px;
  overflow-y: auto;
  background: var(--surface);
  border: 1px solid var(--line);
  border-radius: var(--r-md);
  box-shadow: var(--sh-3);
}
.clear-search-results[hidden] { display: none; }

/* The header search is a flex item, so its popup needs a width to resolve against;
   the canvas row is already sized by its own left/right gutters. */
.clear-tier2 .clear-search .clear-search-results { min-width: 320px; }

.clear-search-result {
  display: flex;
  flex-direction: column;
  gap: 2px;
  padding: 8px 10px;
  border-radius: var(--r-sm, 6px);
  cursor: pointer;
}

/* Hover and keyboard share ONE visual state. A separate hover colour would let the
   pointer and the arrow keys disagree about which row is current, which is exactly
   the ambiguity a combobox must not have. */
.clear-search-result:hover,
.clear-search-result.is-active {
  background: var(--surface-2);
}
.clear-search-result.is-active {
  outline: 2px solid var(--focus);
  outline-offset: -2px;
}

.clear-search-result-name {
  font-size: 13px;
  font-weight: 600;
  color: var(--ink);
  /* Governed names run long. Clip to one line rather than reflowing the row height,
     so arrow-key travel stays predictable. */
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.clear-search-result-meta {
  font-size: 11.5px;
  color: var(--muted);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}

/* Touch targets. 44px is the floor the phone refinements already adopted for the
   peek controls, and a result row is the primary target on a phone. */
@media (max-width: 767px) {
  .clear-search-result { padding: 11px 10px; }
  .clear-search-results { max-height: 60vh; }
}

@media (prefers-reduced-motion: reduce) {
  .clear-search-results { scroll-behavior: auto; }
}


/* ============================================================================================
   34. FCLEAR-APP-0002B — Gate B correction pass, Lane A.

   Every item below was raised by the operator against the RUNNING product. Sources of truth:
   the Revision 2 icon authority (`icons/defs.py` in the design package) for glyph geometry, and
   the existing `.layer-*` / `iconColor` values for colour, which are NOT redefined here --
   provenance colour and icon geometry are governed separately and stay that way.
   ============================================================================================ */

/* --- 34.1 The tab row must read as two groups, not one run-on phrase ------------------------ */
/* `Overview Air Quality [mark] pulm.ai & Evidence` ran together as a single sentence. Two
   changes, both purely spatial: a real gap between the analytical tabs, and the merged pulm.ai
   tab pushed to the END of the row with an auto margin so it cannot be read as a third word of
   "Overview Air Quality".

   THIS MUST NOT REINTRODUCE F-02's OVERFLOW. Measured on the base image, the three tabs need
   62.89 + 71.25 + 146.27 = 280.41px of content plus 12px of strip padding = 292.41px, inside a
   strip that is 413px at every desktop gate from 1440 down to 768 and 375px at the narrowest
   phone. A 14px gap costs 14px once (the auto margin absorbs the second gap), taking the
   requirement to 306.41px -- still 68.59px inside the narrowest measured strip. `flex: 0 1 auto`
   from 26.2 is untouched, so if a future translation ever did exceed the row the tabs still
   shrink rather than clip the strip.

   The auto margin is a MARGIN, not `justify-content`, so it degrades correctly: when there is no
   free space it collapses to zero and the phone strip's `overflow-x: auto` (section 20) still
   scrolls. Keyboard order, roving focus, `aria-selected` and the active underline are untouched. */
.clear-pane-tabs { gap: 14px; }
.clear-pane-tab-pulmai { margin-left: auto; }

/* --- 34.2 Left rail: governed glyphs, not coloured dots ------------------------------------- */
/* Supersedes 23 (WS8 #7), which replaced 24px letter badges with a 9px dot and hid the row's
   `<svg>` outright. The operator's Gate B finding is that the rail must speak the same icon
   vocabulary as the map and the layer list, so the badge returns -- at the rail's own compact
   scale, carrying the governed glyph rather than a letter. The letter badges WS8 objected to do
   not come back: there is no text in these badges at all. */
.clear-layer-icon {
  width: 17px; height: 17px; min-width: 17px;
  border-radius: 5px;
  padding: 0; border: 0;
  overflow: visible;
  font-size: 0; line-height: 0;
  display: inline-flex; align-items: center; justify-content: center;
  color: #fff;
}
.clear-layer-icon svg { display: block; width: 11px; height: 11px; fill: currentColor; }

/* --- 34.3 Selected entity icon replaces the letter badge ------------------------------------ */
/* The pane header showed a generic letter ("H"). It now carries the governed glyph for the
   feature's real class. `is-neutral` is the honest fallback for an unknown or ungoverned class
   and for the pre-selection state: `glyph-place`, the design package's generic located-thing
   marker, in the package's neutral badge colour. It is never a claim about what the feature is.
   Colour for a GOVERNED class is still written inline by the renderer, from the same values the
   map markers use, so the header and the map cannot drift apart. */
.clear-pane-identity-icon svg { display: block; width: 19px; height: 19px; fill: currentColor; }
.clear-peek-icon svg { display: block; width: 17px; height: 17px; fill: currentColor; }
.clear-pane-identity-icon.is-neutral,
.clear-peek-icon.is-neutral { background: #5E7387; }

/* --- 34.4 VISIBLE LAYERS is a controlled panel with ONE state model ------------------------- */
/* Three defects, all reported against the running product:
     1. the box sat at `bottom: 18px`, directly on top of the MapLibre scale bar and attribution,
     2. it was visible while the Legend button rendered inactive,
     3. clicking Legend did nothing.

   `workspace.dataset.clearLegendOpen` is now the only state. The panel's `hidden`, the button's
   `aria-pressed` and its `aria-expanded` are all written from it by `clearShellSetLegendOpen`,
   and nothing else writes any of the three. `display: none` for the narrow band was deleted from
   27.5 for exactly that reason -- it was a second model the button could not read.

   The vertical offset is MEASURED, not guessed: `clearShellUpdateLegendOffset` publishes
   `--clear-legend-bottom` from the real height of `.maplibregl-ctrl-bottom-left`, which is where
   ScaleControl and AttributionControl are added (`clear_map.js:8297-8298`), plus the same
   `--clear-map-ctrl-bottom` inset the controls themselves follow. The fallback covers the window
   before the first measurement. */
.clear-legend-card {
  bottom: var(--clear-legend-bottom, 92px);
  max-height: calc(100% - var(--clear-legend-bottom, 92px) - 14px);
  overflow-y: auto;
}
.clear-legend-card[hidden] { display: none; }

/* The Legend button uses the SAME active treatment every other toggling tier-2 action uses
   (section 4, `[aria-pressed="true"]`); it is restated for `aria-expanded` only so a reader of
   this section can see that the two attributes are kept in lockstep, not so a second style
   exists. */
.clear-action[data-clear-legend-button][aria-expanded="true"] {
  background: var(--surface-3);
  border-color: var(--line-strong);
  color: var(--brand-ink);
}
