/* ── phone & tablet layer ────────────────────────────────────────────────
   Every responsive rule lives here, loaded last. The phone layout is
   designed for one hand and a 375px screen, not a shrunken desktop:

   - lens switching is a bottom tab bar (thumb reach, always visible, the
     Complaints tab carries the live count)
   - only the filter row is sticky: date + "Filters" (a bottom sheet of
     native pickers) + removable chips; the brand bar scrolls away
   - the page action is dropped (the Complaints tab is the same link)
   - Pulse reads numbers → map → issues → trend
   - tables become card rows; nothing needs sideways scrolling
   - inputs are 16px (iOS doesn't zoom on focus), targets ≥ 40px, no
     hover-only affordances, safe-area insets respected
   ──────────────────────────────────────────────────────────────────────── */

@media (max-width: 1100px) {
  /* stacked: nothing to share a row with, so the map sets its own height */
  .pv-grid { grid-template-columns: 1fr; }
  .gm-stage { flex: none; height: clamp(420px, 70vh, 640px); }
}

@media (max-width: 860px) {
  /* one geometry for every box on a phone: only the tokens change */
  :root { --gutter: 16px; --pad: 16px; --gap: 12px; }

  /* ── chrome ── */
  body { padding-bottom: calc(64px + env(safe-area-inset-bottom)); }
  body.sheet-open { overflow: hidden; }
  a, button, select, [role='button'] { -webkit-tap-highlight-color: transparent; }

  /* the brand bar scrolls away; only the filter row sticks. .top gives up
     its box so the filter bar can stick to the viewport, not to .top. */
  .top { display: contents; }
  #nav { padding: 8px var(--gutter); border-bottom: 1px solid var(--line); background: var(--canvas); }
  .brand-name { font-size: 18px; }
  .nav-right { gap: 4px; }

  /* bottom tab bar (z below the filter bar, whose sheet must cover it) */
  .tabs {
    position: fixed; left: 0; right: 0; bottom: 0; z-index: 80; margin: 0;
    display: grid; grid-template-columns: repeat(3, 1fr); gap: 4px;
    padding: 6px 8px calc(6px + env(safe-area-inset-bottom));
    background: color-mix(in srgb, var(--canvas) 92%, transparent);
    backdrop-filter: saturate(1.2) blur(14px); -webkit-backdrop-filter: saturate(1.2) blur(14px);
    border-top: 1px solid var(--line);
  }
  .tab { position: relative; flex-direction: column; justify-content: center; gap: 3px; min-height: 50px; padding: 6px 4px; font-size: 11.5px; font-weight: 600; border-radius: var(--r-sm); }
  .tab:hover, .tab.is-active { background: transparent; }
  .tab.is-active { color: var(--brand-hi); }
  :root[data-theme='light'] .tab.is-active { color: var(--brand-deep); }
  .tab-n { position: absolute; top: 3px; left: calc(50% + 8px); padding: 0 5px; font-size: 10px; line-height: 16px; }

  /* sticky filter row. No backdrop-filter here: it would become the
     containing block for the fixed-position sheet inside it. */
  #filterbar { position: sticky; top: 0; z-index: 90; background: var(--canvas); border-top: 0; border-bottom: 1px solid var(--line); }
  .fbar-inner { padding-top: 8px; padding-bottom: 8px; }
  .fbar-controls { flex-wrap: nowrap; overflow-x: auto; scrollbar-width: none; margin: 0 calc(-1 * var(--gutter)); padding: 0 var(--gutter); }
  .fbar-controls::-webkit-scrollbar { display: none; }
  .fbar-controls > * { flex-shrink: 0; }
  .fbar-controls > .freset { display: none; } /* reset lives in the sheet */
  .fsel, .fmore, .fchip { height: 40px; }
  .fmore { display: inline-flex; }
  .phone-only { display: inline-flex; }
  .fsel select, .fdates input, .search input { font-size: 16px; }
  .fdates input { height: 40px; }

  /* the Filters sheet: same controls, stacked, as native pickers */
  .fbar-more {
    position: fixed; left: 0; right: 0; bottom: 0; z-index: 300;
    display: flex; flex-direction: column; gap: 10px;
    max-height: 86vh; overflow-y: auto;
    padding: 6px var(--gutter) calc(var(--gutter) + env(safe-area-inset-bottom));
    background: var(--surface); border-top: 1px solid var(--line-2); border-radius: 20px 20px 0 0; box-shadow: var(--shadow-lg);
    transform: translateY(100%); visibility: hidden;
    transition: transform 0.26s var(--ease), visibility 0s 0.26s;
  }
  .fbar-more.is-open { transform: none; visibility: visible; transition-delay: 0s; }
  .fbar-more::before { content: ''; align-self: center; width: 36px; height: 4px; border-radius: 99px; background: var(--line-2); margin: 4px 0 2px; }
  .sheet-head { display: flex; align-items: center; justify-content: space-between; }
  .sheet-head h2 { font-family: var(--display); font-size: 18px; font-weight: 650; }
  .fbar-more .fsel { width: 100%; max-width: none; height: 50px; }
  .fbar-more .fsel select { width: 100%; }
  .sheet-foot { display: flex; gap: 10px; margin-top: 6px; }
  .sheet-foot > * { flex: 1; justify-content: center; height: 48px; font-size: 15px; white-space: nowrap; }
  .fbar-scrim { display: block; position: fixed; inset: 0; z-index: 290; background: rgba(3, 8, 10, 0.5); opacity: 0; visibility: hidden; transition: opacity 0.2s, visibility 0s 0.2s; }
  .fbar-scrim.is-open { opacity: 1; visibility: visible; transition-delay: 0s; }

  /* ── page ── */
  .page-head { padding: 18px 0 12px; }
  .page-title { font-size: 24px; }
  .page-scope { font-size: 13px; }
  .page-act { display: none; } /* the Complaints tab is the same link, with the count */
  footer { margin-top: 32px; }

  /* touch targets */
  .icon-btn.sm { width: 40px; height: 40px; }
  .seg button, .seg a { padding: 9px 12px; }
  .pill { padding: 9px 13px; }

  /* ── Pulse: numbers → map → issues → trend ── */
  /* stretch: every card takes the full content width, never its own content's */
  .pv-grid { display: flex; flex-direction: column; align-items: stretch; gap: var(--gap); }
  .pv-side { display: contents; }
  .pv-kpis { order: 1; }
  .pv-map { order: 2; }
  .pv-issues { order: 3; }
  .pv-trend { order: 4; }
  .gm-stage { height: clamp(340px, 58vh, 520px); }
  .gm-zoom button { width: 40px; height: 40px; }
  .gm-legend { width: 156px; }
  /* the zoom controls get their own column so they never cover the city,
     and the same width is reserved on the left so the map stays centred */
  /* (explicit width: 'auto' would size an absolutely positioned SVG from its
     aspect ratio and ignore the right inset) */
  .gm-svg { left: calc(var(--pad) + 48px); width: calc(100% - 2 * (var(--pad) + 48px)); }
  .pv-sel { position: relative; gap: 8px 14px; }
  .pv-sel-main { padding-right: 44px; }
  .pv-sel #pvSelClear { position: absolute; top: 8px; right: 8px; }
  .pv-sel-act { flex: 1 1 100%; }
  .pv-sel-act .btn-primary { width: 100%; justify-content: center; height: 42px; }
}

@media (max-width: 640px) {
  .lens-hint, .hide-sm, .hide-md { display: none; }
  /* phones keep the latest-complaint date, stacked to fit beside the brand */
  .nav-asof { flex-direction: column; align-items: flex-end; gap: 0; margin-right: 4px; font-size: 10.5px; line-height: 1.25; }
  .nav-asof svg { display: none; }

  /* KPIs 2×2 */
  .kpi-grid { grid-template-columns: 1fr 1fr; }
  .kpi:nth-child(3)::before { display: none; }
  .kpi:nth-child(n + 3) { border-top: 1px solid var(--line); border-radius: 0; }
  .kpi-v { font-size: 24px; }
  .issue-btn { grid-template-columns: 24px minmax(0, 1fr) 40px 52px; gap: 10px; padding: 10px; }
  .issue-bar { display: none; }

  /* a map needs no title on a phone: the level switch leads the card */
  .pv-map .card-h > div:first-child { display: none; }

  /* segmented controls span the width: bigger targets, no ragged edge */
  #pvLevel { flex: 1 1 100%; }
  #pvLevel .seg { display: flex; width: 100%; }
  #pvLevel .seg > * { flex: 1; }

  /* lens bars: full-width controls */
  .lens-bar .seg { display: flex; width: 100%; }
  .lens-bar .seg > * { flex: 1; text-align: center; }
  .acc-sort { width: 100%; max-width: none; height: 44px; }
  .acc-sort select { width: 100%; }
  .search { flex: 1 1 100%; max-width: none; height: 44px; }
  .pills { flex-wrap: nowrap; overflow-x: auto; scrollbar-width: none; margin: 0 calc(-1 * var(--gutter)); padding: 0 var(--gutter); width: calc(100% + 2 * var(--gutter)); }
  .pills::-webkit-scrollbar { display: none; }
  .pills .pill { flex-shrink: 0; }

  /* ── tables → card rows ── */
  .tbl-rows, .tbl-rank, .tbl-rows tbody, .tbl-rank tbody { display: block; }
  .tbl-rows thead, .tbl-rank thead { display: none; }
  .tbl-rows tbody tr, .tbl-rank tbody tr { padding: 12px var(--pad); border-bottom: 1px solid var(--line); }
  .tbl-rows tbody tr:last-child, .tbl-rank tbody tr:last-child { border-bottom: 0; }
  .tbl-rows td, .tbl-rank td { display: block; padding: 0; border: 0; }
  /* the row carries the inset; cells don't (overrides the table's edge padding) */
  .tbl-rows td:first-child, .tbl-rank td:first-child, .tbl-rows td:last-child, .tbl-rank td:last-child { padding: 0; }
  .tbl-rows td.hide-md, .tbl-rows td.hide-sm { display: none; }

  /* Complaints: issue + status / where + date */
  .tbl-rows tbody tr { display: grid; grid-template-columns: minmax(0, 1fr) auto; grid-template-areas: 'iss st' 'where date'; column-gap: 12px; row-gap: 3px; }
  .tbl-rows .c-id { display: none; }
  .tbl-rows .c-iss { grid-area: iss; max-width: none; }
  .tbl-rows .c-iss b { white-space: normal; display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; }
  .tbl-rows .c-st { grid-area: st; align-self: start; }
  .tbl-rows .c-where { grid-area: where; display: flex; gap: 6px; min-width: 0; max-width: none; font-size: 12px; }
  .tbl-rows .c-where b { font-weight: 500; font-size: 12px; color: var(--fg-muted); flex-shrink: 0; }
  .tbl-rows .c-where small { font-size: 12px; }
  .tbl-rows .c-date { grid-area: date; font-size: 12px; color: var(--fg-faint); text-align: right; }

  /* Accountability: owner + unresolved / measures on one line */
  .tbl-rank tbody tr { display: flex; flex-wrap: wrap; align-items: center; column-gap: 14px; row-gap: 4px; }
  .tbl-rank tbody tr::after { content: ''; order: 2; flex-basis: 100%; height: 0; }
  .tbl-rank .c-rank, .tbl-rank .c-issue { display: none; }
  .tbl-rank .c-owner { order: 1; flex: 1 1 0; min-width: 0; }
  .tbl-rank .c-bar { order: 2; min-width: 0; text-align: right; }
  .tbl-rank .c-bar .bar { display: none; }
  .tbl-rank .c-bar .num { font-family: var(--display); font-size: 20px; font-weight: 700; color: var(--fg); }
  .tbl-rank .c-bar::after { content: attr(data-l); display: block; font-size: 11px; color: var(--fg-faint); }
  .tbl-rank td.c-meta { order: 3; display: inline-block; font-size: 12px; color: var(--fg-muted); text-align: left; }
  .tbl-rank td.c-meta::after { content: ' ' attr(data-l); color: var(--fg-faint); }
  .tbl-rank td.c-meta.is-nil { display: none; }
  .tbl-rank .c-meta .delta { font-size: 12px; }

  .pager { flex-direction: column; gap: 8px; }

  /* drawer: full screen */
  .drawer { width: 100%; border-left: 0; }
  .drawer-body { padding-bottom: calc(32px + env(safe-area-inset-bottom)); }
}

/* touch screens: no sticky hover states, visible affordances, press feedback */
@media (hover: none) {
  .tbl tbody tr:hover, .issue-btn:hover, .kpi.is-link:hover { background: transparent; }
  .tbl tbody tr.is-sel:hover { background: var(--brand-tint); }
  .owner:hover b { color: inherit; }
  .gm-shapes path:hover { filter: none; stroke: var(--map-edge); stroke-width: 0.6; }
  .kpi-go { opacity: 1; }
  .kpi.is-link:hover::before, .kpi.is-link:hover + .kpi::before { opacity: 1; }
  .tbl tbody tr:active, .issue-btn:active, .kpi.is-link:active, .tab:active { background: var(--raised); }
}

/* the sort select replaces tappable headers only where headers are hidden */
@media (min-width: 641px) { .acc-sort { display: none !important; } }
