/* OpenCE-5 — full-screen globe layout.

   Loaded after style.css, which keeps all the component styling (buttons, chips,
   step cards, modals, glance bar). This file only replaces the old fixed
   three-column grid with: a globe filling the screen, and everything else as a
   floating overlay on top of it.

   The order of `z-index` here matters more than it looks: MapLibre's canvas and
   its own controls sit inside #map, so every overlay must stack above it, and
   the modals above the overlays. */

html, body {
  height: 100%;
  margin: 0;
  overflow: hidden;            /* the map is the scroll surface, not the page */
  overscroll-behavior: none;
}

#app {
  position: relative;
  height: 100vh;
  height: 100dvh;              /* mobile: excludes the browser chrome */
  display: block;
  overflow: hidden;
}

/* ---------- The globe ---------- */

#map {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  z-index: 0;
  background: #05080c;
}

/* MapLibre paints a white flash before the first tile; keep it dark. */
.maplibregl-canvas { outline: none; }
.maplibregl-ctrl-attrib {
  background: rgba(10, 14, 20, .72) !important;
  color: var(--muted) !important;
  font-size: 10px;
  border-radius: 4px;
}
.maplibregl-ctrl-attrib a { color: var(--muted) !important; }
.maplibregl-ctrl-group {
  background: var(--panel2) !important;
  border: 1px solid var(--line) !important;
}
.maplibregl-ctrl-group button + button { border-top-color: var(--line) !important; }
.maplibregl-ctrl-icon { filter: invert(.8); }
.maplibregl-popup-content {
  background: var(--panel) !important;
  color: var(--text) !important;
  border: 1px solid var(--line);
  border-radius: 9px;
  font: 12px/1.45 system-ui, sans-serif;
  padding: 9px 11px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, .6);
}
.maplibregl-popup-tip { border-top-color: var(--panel) !important; }

/* ---------- Overlays ---------- */

/* The top offset of the drawers is computed from the real heights of the topbar
   and the controls bar rather than hard-coded: the controls wrap to a second row
   at narrower widths, and a fixed offset let them overlap the panel headings. */
:root {
  --topbar-h: 52px;
  --controls-h: 46px;
}

.overlay {
  position: absolute;
  z-index: 10;
  background: color-mix(in srgb, var(--panel) 88%, transparent);
  backdrop-filter: blur(10px) saturate(120%);
  -webkit-backdrop-filter: blur(10px) saturate(120%);
  border: 1px solid var(--line);
  border-radius: 11px;
  box-shadow: 0 12px 34px rgba(0, 0, 0, .55);
}

#topbar.overlay {
  top: 0; left: 0; right: 0;
  z-index: 40;
  border-radius: 0 0 11px 11px;
  border-top: none;
  padding: 8px 14px;
  display: flex;
  align-items: center;
  gap: 12px;
}

/* ---------- Drawers ----------
   Desktop: three floating panels around the globe. Their geometry is expressed
   against the measured topbar and controls heights (app.js writes those into
   --topbar-h / --controls-h), so a wrapping controls bar pushes them down
   instead of landing on top of them. */

.drawer {
  display: flex;
  flex-direction: column;
  min-height: 0;
  overflow: hidden;
}

.drawer.left,
.drawer.right {
  top: calc(var(--topbar-h) + var(--controls-h) + 18px);
  bottom: 214px;
  max-height: none;
}
.drawer.left { left: 12px; width: 322px; }
.drawer.right { right: 12px; width: 372px; }

.drawer.bottom {
  left: 346px;
  right: 396px;
  bottom: 12px;
  height: 192px;
}

.panel-bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  padding: 8px 10px;
  border-bottom: 1px solid var(--line);
  flex: 0 0 auto;
}

.panel-bar h2, .panel-bar h3 { margin: 0; }
.panel-actions { display: flex; align-items: center; gap: 6px; }

/* One scroll surface per panel. Two nested scrollers is how a panel ends up
   with a scrollbar inside a scrollbar and the timer clipped off the bottom. */
.panel-body {
  padding: 10px;
  overflow: auto;
  min-height: 0;
  flex: 1 1 auto;
}
/* The cockpit scrolls as a whole. Pinning the step card and the field box and
   letting only the step list scroll clips them on a short window — the timer is
   the one number you read from a distance, and it was being cut in half. One
   scroller, and everything in the panel is reachable by scrolling it. */
#cockpit .panel-body { padding-bottom: 2px; }
#cockpit .step-list { flex: 0 0 auto; }
#debunk .panel-body { display: flex; flex-direction: column; overflow: hidden; }
#obs .panel-body { padding: 0; overflow: auto; }

.panel-toggle {
  padding: 1px 8px;
  line-height: 1.4;
  font-size: 14px;
  color: var(--muted);
}

/* Collapsed: only the title bar survives, so the globe gets the screen back.
   The side drawers stretch between a top anchor and a bottom anchor, so a
   collapsed one releases its bottom to shrink to the bar. The bottom drawer is
   anchored to the bottom instead — releasing *its* bottom left it with no
   vertical anchor at all, so it snapped to the document top, slid behind the
   header, and took its own "+" (the only way back) with it. Only the side
   drawers drop their bottom. */
.panel.collapsed { max-height: none; height: auto !important; }
.panel.collapsed .panel-body { display: none; }
.drawer.left.collapsed, .drawer.right.collapsed { bottom: auto !important; }

/* ---------- Map controls ---------- */

#map-controls.overlay {
  top: calc(var(--topbar-h) + 8px);
  left: 50%;
  transform: translateX(-50%);
  z-index: 30;
  display: flex;
  align-items: center;
  gap: 12px;
  flex-wrap: wrap;
  justify-content: center;
  padding: 6px 10px;
  max-width: min(880px, calc(100vw - 24px));
  border-radius: 999px;
}

#map-controls .basemap-select { width: auto; margin: 0; }
#map-controls .layer-toggles { display: flex; gap: 10px; flex-wrap: wrap; margin: 0; }
#map-controls .map-foot {
  display: flex; align-items: center; gap: 10px;
  margin: 0; padding-left: 10px; border-left: 1px solid var(--line);
  font-size: 10px;
}
/* Phone-only affordances: the layer toggle and the ⋯ overflow menu. On a wide
   screen both are already on show, so the buttons that reveal them are not. */
.layers-btn, .more-btn { display: none; }

/* ---------- Markers ---------- */

.map-dot {
  width: 11px; height: 11px;
  border-radius: 50%;
  background: var(--sw-obs);
  border: 2px solid #0a0e14;
  box-shadow: 0 0 0 3px rgba(245, 158, 11, .22);
  cursor: pointer;
}
.map-dot-site { background: var(--sw-site); border-radius: 3px; box-shadow: 0 0 0 3px rgba(74, 222, 128, .22); }
.map-dot-pass { background: var(--sw-pass); box-shadow: 0 0 0 3px rgba(167, 139, 250, .22); }

.map-pin {
  width: 21px; height: 21px;
  border-radius: 50%;
  display: flex; align-items: center; justify-content: center;
  color: #0a0e14;
  font-weight: 800;
  font-size: 12px;
  border: 2px solid #0a0e14;
  cursor: pointer;
  box-shadow: 0 2px 8px rgba(0, 0, 0, .5);
}

.air-marker {
  font-size: 10px;
  font-family: var(--mono);
  color: #06220f;
  background: var(--sw-aircraft);
  border-radius: 3px;
  padding: 1px 3px;
  white-space: nowrap;
  border: 1px solid rgba(0, 0, 0, .35);
  cursor: pointer;
}

.sat-marker {
  font-size: 10px;
  font-family: var(--mono);
  color: #2a0a1c;
  background: var(--sw-sat);
  border-radius: 3px;
  padding: 1px 3px;
  white-space: nowrap;
  border: 1px solid rgba(0, 0, 0, .35);
  cursor: pointer;
}

/* ---------- Modals above everything ---------- */

.modal { z-index: 2000; }
.toast { z-index: 3000; }

/* ---------- The phone tab bar ----------
   Hidden wherever the drawers have room. On a phone it is the only way to reach
   the cockpit and the debunk panel, which cannot share a small screen. */

#sheet-tabs { display: none; }

.sheet-tab {
  flex: 1 1 0;
  padding: 7px 4px;
  border: 1px solid transparent;
  border-radius: 8px;
  background: transparent;
  color: var(--muted);
  font: inherit;
  font-size: 12px;
  letter-spacing: .02em;
  cursor: pointer;
}
.sheet-tab.active {
  background: var(--panel2);
  border-color: var(--line);
  color: var(--text);
  font-weight: 600;
}
.sheet-tab:focus-visible { outline: 2px solid var(--accent2); outline-offset: 1px; }

/* ---------- Tablet: the side drawers get narrower, the bottom one stays ---- */

@media (max-width: 1100px) {
  .drawer.left { width: 292px; }
  .drawer.right { width: 320px; }
  .drawer.bottom { left: 316px; right: 344px; }
  #map-controls { max-width: calc(100vw - 24px); padding: 5px 8px; gap: 8px; }
  #map-controls .map-foot { display: none; }
}

/* ---------- Phone: one sheet at a time ----------
   Everything here exists because the three panels cannot all be on a 390 px
   screen. The globe stays the background; the header shrinks to what you need
   in the dark; one sheet is open and the tab bar chooses it. */

/* Phone-only chrome, hidden on wide screens. */
#more, .record-fab, .nav-toggle { display: none; }

/* If the map cannot start (no WebGL, or tiles unreachable) it must say so
   rather than leaving a silent black square over the globe. */
.map-fallback {
  position: absolute; inset: 0; z-index: 30;
  display: flex; align-items: center; justify-content: center; padding: 24px;
  background: color-mix(in srgb, #05080c 82%, transparent);
}
.map-fallback-card {
  max-width: 430px; padding: 18px; border-radius: 14px;
  background: var(--panel); border: 1px solid var(--line);
  box-shadow: 0 16px 40px rgba(0, 0, 0, .6);
  display: flex; flex-direction: column; gap: 12px;
}
.map-fallback-card p { margin: 0; line-height: 1.5; }
.more-body { display: flex; flex-direction: column; gap: 8px; }
.more-body .btn.wide { width: 100%; text-align: left; }
.more-status { margin: 6px 2px 0; }

@media (max-width: 760px) {
  :root { --sheet-h: 56dvh; --nav-h: 54px; }

  #topbar.overlay {
    padding: 6px 10px;
    gap: 8px;
    /* Wraps rather than crushing the session picker. At 360 px with the field
       chip on screen there is not room for both on one line, and "— select" is
       not a session picker. */
    flex-wrap: wrap;
    row-gap: 6px;
    border-radius: 0 0 10px 10px;
  }
  /* The name is on the splash screen and the home icon; the bar is for work. */
  .brand { display: none; }
  .session-picker { margin-left: 0; flex: 1 1 auto; min-width: 0; }
  #session-select { flex: 1 1 auto; min-width: 132px; max-width: none; }
  .topbar-right { margin-left: auto; }
  #btn-new-session { padding: 6px 9px; white-space: nowrap; }
  .topbar-right { gap: 4px; }

  /* Status as a dot: the words do not fit and are not the point. */
  #net-state { font-size: 0; padding: 0; width: 10px; height: 10px; border-radius: 50%;
               background: var(--ok); border: none; }
  #net-state.offline { background: var(--danger); }
  #server-btn { display: none; }
  #freshness { display: none; }
  #pair-state { display: none; }
  #local-chip { font-size: 10px; padding: 2px 6px; }
  /* Secondary actions live in the More tab now, and Record is the raised action,
     so the header keeps only the session picker, "+ Session", and the status dot. */
  #btn-record, #btn-more { display: none; }

  /* The centre action, above the bottom nav, in thumb reach. */
  .record-fab {
    display: flex; align-items: center; justify-content: center;
    position: absolute; right: 14px; bottom: calc(var(--nav-h) + 16px);
    z-index: 36; padding: 12px 18px; border-radius: 26px;
    background: #7f1d1d; color: #fee2e2; border: 1px solid #991b1b;
    font-weight: 600; box-shadow: 0 8px 20px rgba(0, 0, 0, .45);
  }

  /* The tabs can be tucked away — to free the map — and brought back. */
  .nav-toggle {
    display: flex; align-items: center; justify-content: center;
    position: absolute; left: 50%; transform: translateX(-50%);
    bottom: calc(var(--nav-h) + 16px);
    width: 40px; height: 24px; z-index: 42; padding: 0;
    border-radius: 12px; background: var(--panel); color: var(--muted);
    border: 1px solid var(--line); font-size: 12px; line-height: 1;
  }
  body.nav-collapsed #sheet-tabs.overlay,
  body.nav-collapsed .record-fab { display: none !important; }
  body.nav-collapsed .nav-toggle { bottom: 10px; }
  body.nav-collapsed .drawer.left,
  body.nav-collapsed .drawer.right,
  body.nav-collapsed .drawer.bottom { bottom: 44px; }

  /* Secondary actions fold into the ⋯ menu. */
  .topbar-more { display: none; }
  .topbar-more.open {
    display: flex;
    position: absolute;
    top: calc(var(--topbar-h) + 6px);
    right: 8px;
    z-index: 45;
    flex-direction: column;
    gap: 4px;
    padding: 6px;
    background: var(--panel);
    border: 1px solid var(--line);
    border-radius: 10px;
    box-shadow: 0 12px 34px rgba(0, 0, 0, .6);
  }
  .topbar-more.open .btn { text-align: left; }
  .more-btn { display: inline-flex; }

  /* The controls sit in a compact pill under the header rather than in a full
     bar above the tab bar. Stacked there, a whole row of chrome split the map
     from the sheet and left the map a thin strip; pinned to the top the map is
     one piece and the sheet gets the space. The basemap picker folds into the
     Layers reveal so the resting control is a single button. */
  #map-controls.overlay {
    top: calc(var(--topbar-h) + 6px);
    bottom: auto;
    left: 8px; right: auto;
    width: auto; max-width: calc(100vw - 16px);
    transform: none;
    border-radius: 12px;
    padding: 5px 8px;
    gap: 8px;
    justify-content: flex-start;
    flex-wrap: wrap;
  }
  #map-controls.layers-open { right: 8px; width: auto; }
  #map-controls .basemap-select { display: none; flex: 1 1 100%; min-width: 0; }
  #map-controls.layers-open .basemap-select { display: block; }
  #map-controls .layers-btn { display: inline-flex; }
  #map-controls .layer-toggles { display: none; width: 100%; gap: 6px 12px; }
  #map-controls.layers-open .layer-toggles { display: flex; }
  #map-controls .map-foot { display: none; }

  /* The tab bar, pinned to the bottom edge as the phone's primary navigation. */
  #sheet-tabs.overlay {
    display: flex;
    gap: 4px;
    align-items: center;
    justify-content: space-between;
    left: 8px; right: 8px;
    bottom: 8px;
    z-index: 40;
    padding: 4px;
    border-radius: 12px;
  }
  #sheet-tabs .sheet-tab { flex: 1 1 0; text-align: center; }

  /* One sheet, chosen by the tab bar. */
  .drawer { display: none; }
  .drawer.left, .drawer.right, .drawer.bottom {
    left: 8px; right: 8px; bottom: calc(var(--nav-h) + 14px);
    top: auto;
    width: auto;
    height: var(--sheet-h);
    max-height: var(--sheet-h);
    border-radius: 14px;
  }
  body[data-sheet="cockpit"] #cockpit,
  body[data-sheet="debunk"] #debunk,
  body[data-sheet="obs"] #obs,
  body[data-sheet="more"] #more { display: flex; }

  /* The per-panel button peeks the sheet down to its bar, so the globe gets the
     screen back without losing the page (the tab bar still switches pages). */
  .panel-toggle { display: inline-flex; }
  body.sheet-peeked .drawer.left,
  body.sheet-peeked .drawer.right,
  body.sheet-peeked .drawer.bottom {
    height: 58px; min-height: 58px; max-height: 58px; overflow: hidden;
  }
  body.sheet-peeked .drawer .panel-body { display: none; }

  .modal { align-items: flex-end; }
  .modal-card {
    width: 100%;
    max-width: none;
    max-height: 92dvh;
    border-radius: 16px 16px 0 0;
    padding: 14px 14px calc(14px + env(safe-area-inset-bottom, 0px));
  }
  .row3 { grid-template-columns: 1fr 1fr; }
  #map-controls .layer-toggles .chk { font-size: 11px; }

  /* The PC-address panel becomes a full-width card under the header. */
  .server-panel {
    left: 10px; right: 10px; top: 78px;
    width: auto; z-index: 2200;
  }
}

.onboard-input {
  flex: 1 1 auto; min-width: 0; padding: 10px 12px; font: inherit; color: inherit;
  background: rgba(255, 255, 255, .05);
  border: 1px solid var(--line); border-radius: 8px;
}

/* Short windows: a laptop with the browser chrome open, or a small window on a
   big screen. The fixed 192 px bottom drawer was eating the cockpit — the step
   card did not fit, so the timer sat half below the fold on a window that has
   plenty of width. Give the side panels the space and shrink the card. */

@media (min-width: 761px) and (max-height: 760px) {
  .drawer.bottom { height: 148px; }
  .drawer.left, .drawer.right { bottom: 170px; }
  #topbar.overlay { padding: 5px 12px; }
  #map-controls.overlay { padding: 4px 9px; }
  .timer { font-size: 26px; margin: 6px 0 4px; }
  .step-card { padding: 9px 10px; margin-bottom: 8px; }
  .step-instructions { max-height: 46px; }
  .field-box { padding: 6px 9px; margin-bottom: 8px; }
  #cockpit .panel-body { padding: 8px 10px 2px; }
}

/* Very short screens (a phone in landscape): the sheet gets less, the map more. */
@media (max-width: 900px) and (max-height: 460px) {
  :root { --sheet-h: 54dvh; }
  #sheet-tabs.overlay { bottom: calc(var(--sheet-h) + 10px); }
  #map-controls.overlay { bottom: calc(var(--sheet-h) + 58px); }
}

/* ---------- Replay: the sky through the lens ----------
   A panel docked to the side so the globe stays visible beside it — the footage
   with every known object projected into the frame it was recorded in, on the
   left the site, the camera's field of view and the tracks. Above the map
   overlays, below the modals. */

.replay {
  position: absolute;
  z-index: 50;
  top: calc(var(--topbar-h) + 8px);
  right: 12px;
  bottom: 12px;
  width: min(440px, 46vw);
  display: flex;
  flex-direction: column;
  background: color-mix(in srgb, var(--panel) 95%, transparent);
  backdrop-filter: blur(8px) saturate(120%);
  -webkit-backdrop-filter: blur(8px) saturate(120%);
  border: 1px solid var(--line);
  border-radius: 12px;
  box-shadow: 0 12px 34px rgba(0, 0, 0, .6);
}

.replay-bar {
  display: flex; align-items: center; justify-content: space-between;
  gap: 12px; padding: 9px 12px; border-bottom: 1px solid var(--line);
}
.replay-bar h2 { margin: 0; font-size: 15px; }

.replay-stage {
  flex: 1 1 auto; min-height: 0;
  display: flex; flex-direction: column; gap: 10px; padding: 10px;
}

.replay-media {
  position: relative; flex: 1 1 auto; min-height: 0;
  display: flex; align-items: center; justify-content: center;
  background: #05080c; border: 1px solid var(--line);
  border-radius: 10px; overflow: hidden;
}
.replay-media img, .replay-media video { max-width: 100%; max-height: 100%; display: block; }
/* Projected positions sit on the frame at the pixel the server computed. */
.replay-overlay { position: absolute; inset: 0; pointer-events: none; }
.replay-dot {
  position: absolute; width: 12px; height: 12px; margin: -6px 0 0 -6px;
  border-radius: 50%; border: 2px solid #05080c;
  box-shadow: 0 0 0 3px rgba(0, 0, 0, .35);
}
.replay-dot.air { background: var(--sw-aircraft); }
.replay-dot.sat { background: var(--sw-sat); }
.replay-empty {
  position: absolute; inset: 0; display: none;
  align-items: center; justify-content: center; padding: 22px; text-align: center;
}

.replay-side {
  flex: 0 0 auto; max-height: 34%; overflow: auto;
  display: flex; flex-direction: column; gap: 8px;
}
.replay-verdict { font-weight: 700; letter-spacing: .02em; }

.replay-scrub {
  display: flex; align-items: center; gap: 8px;
  padding: 9px 12px; border-top: 1px solid var(--line);
}
.replay-scrub input[type=range] { flex: 1 1 auto; }

@media (max-width: 760px) {
  .replay {
    top: auto; left: 8px; right: 8px; bottom: 8px;
    width: auto; height: 62dvh;
  }
}

/* ---------- The quick Record button ---------- */
.record-btn {
  background: #7f1d1d; color: #fee2e2; border: 1px solid #991b1b;
  padding: 5px 10px; white-space: nowrap;
}
.record-btn.recording { animation: rec-pulse 1.2s ease-in-out infinite; }
@keyframes rec-pulse { 0%, 100% { opacity: 1; } 50% { opacity: .5; } }

/* ---------- The recorder: capture in the app, pointing tracked ---------- */
.recorder {
  position: absolute; z-index: 1600;
  left: 50%; top: 50%; transform: translate(-50%, -50%);
  width: min(560px, 92vw); max-height: 92dvh;
  display: flex; flex-direction: column;
  background: var(--panel); border: 1px solid var(--line);
  border-radius: 14px; box-shadow: 0 20px 60px rgba(0, 0, 0, .7);
}
.recorder-bar {
  display: flex; align-items: center; gap: 10px; justify-content: space-between;
  padding: 10px 12px; border-bottom: 1px solid var(--line);
}
.recorder-bar h2 { margin: 0; font-size: 15px; }
.rec-mode { display: inline-flex; gap: 4px; }
.rec-mode .btn { padding: 5px 10px; font-size: 13px; opacity: 0.55; }
.rec-mode .btn.on { opacity: 1; box-shadow: inset 0 0 0 1px var(--accent, #4c8bf5); }
.recorder-stage {
  flex: 1 1 auto; min-height: 180px; margin: 10px;
  display: flex; align-items: center; justify-content: center;
  background: #05080c; border-radius: 8px; overflow: hidden;
}
.recorder-video { width: 100%; max-height: 60dvh; display: block; }
.recorder-info { padding: 0 12px 8px; }
.recorder-controls {
  display: flex; align-items: center; gap: 10px;
  padding: 10px 12px; border-top: 1px solid var(--line);
}
@media (max-width: 760px) { .recorder { width: 94vw; } }

/* Quick locate: the "you are here" dot. */
.me-marker {
  width: 16px; height: 16px; border-radius: 50%; box-sizing: border-box;
  background: #2b8fff; border: 3px solid #fff;
  box-shadow: 0 0 0 3px rgba(43, 143, 255, .35);
}
/* Community trust: the vote row on a record. */
.vote-row { display: flex; align-items: center; gap: 8px; margin-top: 10px; }
.vote-row .vote-score { min-width: 2ch; text-align: center; font-weight: 600; }
.vote-row .vote-report { margin-left: auto; }
/* Reproduce: re-run the machine check and diff it against the verdict on record. */
.reproduce-row { margin-top: 10px; }
.reproduce-out { margin-top: 8px; padding: 8px 10px; border-radius: 8px;
  font-size: 13px; background: rgba(34, 197, 94, .12);
  border: 1px solid rgba(34, 197, 94, .35); }
.reproduce-out.is-bad { background: rgba(239, 68, 68, .12);
  border-color: rgba(239, 68, 68, .4); }
.reproduce-out ul { margin: 6px 0 0; padding-left: 18px; }
.reproduce-verdict { font-weight: 600; }
.reproduce-detail { opacity: .8; margin-top: 2px; }
/* Signed, evidence-bearing reviews. */
.reviews { margin-top: 14px; border-top: 1px solid rgba(255, 255, 255, .12); padding-top: 10px; }
.reviews-head { display: flex; align-items: center; justify-content: space-between; margin-bottom: 6px; }
.reviews-list { display: flex; flex-direction: column; gap: 8px; }
.review { border: 1px solid rgba(255, 255, 255, .12); border-radius: 8px; padding: 8px 10px; }
.review-top { display: flex; gap: 8px; align-items: center; font-size: 12px; }
.review-kind { text-transform: uppercase; letter-spacing: .04em; font-size: 10px;
  padding: 1px 6px; border-radius: 999px; background: rgba(43, 143, 255, .18); }
.review-who { opacity: .75; }
.review-status { margin-left: auto; opacity: .7; font-size: 10px; text-transform: uppercase; }
.review-status.accepted { color: #22c55e; opacity: 1; }
.review-status.rejected { color: #ef4444; opacity: 1; }
.review-body { margin-top: 4px; font-size: 13px; }
.review-evidence { margin-top: 3px; font-size: 12px; opacity: .8; font-style: italic; }
.review-vote { display: flex; gap: 8px; align-items: center; margin-top: 6px; }
.review-form { margin-top: 8px; display: flex; flex-direction: column; gap: 6px; }
.review-form textarea, .review-form input, .review-form select { width: 100%; box-sizing: border-box; }
.review-form-actions { display: flex; gap: 8px; }

/* ---------- The discussion: stance-taking, rated arguments -----------------
   A comment carries a stance (debunked/neutral/plausible) and is itself rated;
   the highest-rated arguments sort to the top. */
.discussion { margin-top: 14px; border-top: 1px solid rgba(255, 255, 255, .12); padding-top: 10px; }
.disc-head { display: flex; align-items: baseline; gap: 8px; margin-bottom: 6px; }
.disc-hint { display: block; margin-bottom: 8px; line-height: 1.35; }
.disc-list { display: flex; flex-direction: column; gap: 8px; margin-bottom: 10px; }
.comment { border: 1px solid rgba(255, 255, 255, .12); border-radius: 8px; padding: 8px 10px; }
.comment-top { display: flex; gap: 8px; align-items: center; font-size: 12px; }
.comment-who { font-weight: 600; }
.comment-body { margin-top: 4px; font-size: 13px; white-space: pre-wrap; }
.comment-vote { display: flex; gap: 8px; align-items: center; margin-top: 6px; }
.comment-vote .cv-score { min-width: 18px; text-align: center; font-weight: 700; font-variant-numeric: tabular-nums; }
.stance-badge { font-size: 10px; text-transform: uppercase; letter-spacing: .04em;
  border: 1px solid; border-radius: 6px; padding: 1px 6px; font-weight: 700; }
.disc-form { display: flex; flex-direction: column; gap: 6px; }
.stance-pick { display: flex; gap: 6px; flex-wrap: wrap; }
.stance-btn { flex: 1 1 auto; padding: 6px 8px; border: 1px solid rgba(255, 255, 255, .18);
  background: transparent; color: inherit; border-radius: 8px; cursor: pointer; font-size: 12px; }
.stance-btn.on { border-color: #4c8dff; background: rgba(76, 141, 255, .16); }
.disc-body { width: 100%; box-sizing: border-box; }
.disc-form-actions { display: flex; gap: 8px; }

/* What a clip was captured with — sensors and quality, made legible. */
.capture-info { margin-top: 12px; border: 1px solid rgba(255, 255, 255, .12);
  border-radius: 8px; padding: 8px 10px; }
.cap-head { font-size: 12px; margin-bottom: 4px; }
.cap-row { font-size: 12px; opacity: .9; }
.cap-row .cap-kind { text-transform: uppercase; letter-spacing: .04em; font-size: 10px;
  opacity: .7; margin-right: 4px; }

/* What a record actually captured — the evidence strip. Read from the record itself,
   so the panel says what is present and what the check can use, rather than leaving
   the observer to work it out. */
.evidence { margin-top: 12px; border: 1px solid rgba(255, 255, 255, .12);
  border-radius: 8px; padding: 8px 10px; }
.ev-head { font-size: 12px; margin-bottom: 6px; }
.ev-row { font-size: 12px; padding: 2px 0; display: flex; gap: 6px; align-items: baseline;
  flex-wrap: wrap; }
.ev-row.ok { color: var(--ink, #e6edf3); }
.ev-row.no { color: var(--muted, #94a3b8); }
.ev-row.ok > :first-child { color: #34d399; font-weight: 700; }
.ev-row.no > :first-child { color: #f59e0b; font-weight: 700; }
.ev-note { margin-top: 6px; line-height: 1.35; }

/* When the native Camera2 recorder is driving, its overlay covers the <video>; hide the
   (empty) web element so nothing shows through behind it. */
.recorder video.native { visibility: hidden; }

/* Recording mode: a standalone page. Hiding the globe and the panels also stops MapLibre
   drawing and the app polling — the contention that starved the encoder. */
body.recording { background: #000; }
body.recording #map,
body.recording #map-controls,
body.recording #topbar,
body.recording #sheet-tabs,
body.recording .drawer,
body.recording .panel.overlay { display: none !important; }
body.recording .recorder {
  position: fixed; inset: 0; width: 100vw; max-width: none; margin: 0;
  height: 100dvh; max-height: none; border-radius: 0; z-index: 4000;
  /* The base .recorder is a centred modal (translate(-50%,-50%)). Without resetting that,
     `inset: 0` shoves it half off-screen into the top-left corner. */
  transform: none;
}
body.recording .recorder-stage { max-height: 72dvh; }

/* Drag the top of a phone sheet to size it — the grabber bar and the drag cursor. */
@media (max-width: 760px) {
  .drawer .panel-head.sheet-grab { position: relative; padding-top: 13px; touch-action: none; }
  .drawer .panel-head.sheet-grab::before {
    content: ""; position: absolute; top: 5px; left: 50%; transform: translateX(-50%);
    width: 42px; height: 4px; border-radius: 2px; background: rgba(255, 255, 255, .30);
  }
  body.sheet-dragging { user-select: none; }
}

/* ---------- Community: the review queue and the top-rated leaderboard ------
   A full-screen page (not a drawer) so it reads the same on a phone and on the
   PC. The queue puts the fewest-voted records first, so nothing is missed. */
.community {
  position: fixed; inset: 0; z-index: 1500;
  display: flex; flex-direction: column;
  background: #0a0e14;
}
.community.hidden { display: none; }
.community-bar {
  display: flex; align-items: center; justify-content: space-between;
  gap: 12px; padding: 14px 16px;
  border-bottom: 1px solid rgba(255, 255, 255, .1);
}
.community-bar h2 { margin: 0; font-size: 18px; }
.community-seg { display: flex; gap: 6px; padding: 10px 16px 0; }
.community-seg .seg { flex: 1 1 0; }
.community-seg .seg.active { background: rgba(43, 143, 255, .2); border-color: rgba(43, 143, 255, .5); }
.community-body { flex: 1 1 auto; overflow: auto; padding: 12px 16px calc(16px + env(safe-area-inset-bottom, 0px)); }
.q-card { border: 1px solid rgba(255, 255, 255, .12); border-radius: 12px; padding: 14px; max-width: 720px; }
.q-progress { font-size: 12px; opacity: .7; }
.q-title { margin: 6px 0 2px; }
.q-meta { margin-bottom: 6px; }
.q-desc { margin: 6px 0 10px; }
.q-nav { display: flex; gap: 8px; margin-top: 12px; }
.q-nav .btn { flex: 1 1 0; }
.top-list { display: flex; flex-direction: column; gap: 6px; max-width: 720px; }
.top-row { display: flex; align-items: center; gap: 10px; padding: 8px 10px;
  border: 1px solid rgba(255, 255, 255, .1); border-radius: 10px; }
.top-rank { width: 22px; text-align: right; opacity: .6; font-variant-numeric: tabular-nums; }
.top-main { flex: 1 1 auto; min-width: 0; }
.top-title { font-weight: 600; }
.top-score { font-weight: 700; font-variant-numeric: tabular-nums; }
.top-kind { display: flex; gap: 6px; margin-bottom: 10px; }
/* Provenance badge, overlaid on a media thumbnail. */
.media-grid .thumb { position: relative; }
.media-grid .thumb .thumb-del {
  position: absolute; top: 2px; right: 2px; z-index: 2;
  padding: 2px 6px; font-size: 14px; line-height: 1.2; border-radius: 6px;
  background: rgba(0, 0, 0, .55); color: #fff;
}
.prov-badge {
  position: absolute; top: 4px; right: 4px; z-index: 2;
  min-width: 20px; height: 20px; padding: 0 5px; border-radius: 999px;
  display: inline-flex; align-items: center; justify-content: center;
  font-size: 12px; font-weight: 700; line-height: 1; cursor: pointer;
  background: rgba(0, 0, 0, .55); border: 1px solid rgba(255, 255, 255, .35); color: #fff;
}
.prov-badge.captured { background: rgba(34, 197, 94, .92); border-color: #22c55e; color: #06210f; }
.prov-badge.imported { background: rgba(245, 158, 11, .92); border-color: #f59e0b; color: #2a1a02; }
.prov-badge.modified { background: rgba(239, 68, 68, .95); border-color: #ef4444; color: #2a0606; }
.prov-badge.missing { background: rgba(120, 120, 120, .9); border-color: #888; }
/* Recording quality picker in the recorder bar. */
.recorder-quality { display: inline-flex; align-items: center; gap: 6px; font-size: 12px; }
.recorder-quality select { padding: 4px 6px; }

/* Torch (camera light) toggle — beside the still button and in the recorder bar. */
.torch-toggle { display: inline-flex; align-items: center; gap: 5px; font-size: 12px;
  color: var(--muted, #8a8f98); cursor: pointer; user-select: none; white-space: nowrap; }
.torch-toggle input { margin: 0; accent-color: var(--accent, #6ea8fe); }

/* ---------- First-run walkthrough ---------- */
.onboard {
  position: absolute; inset: 0; z-index: 2200;
  display: flex; align-items: center; justify-content: center;
  background: color-mix(in srgb, #05080c 90%, transparent);
  backdrop-filter: blur(6px) saturate(120%);
  -webkit-backdrop-filter: blur(6px) saturate(120%);
}
.onboard-card {
  width: min(520px, 92vw); max-height: 90dvh;
  display: flex; flex-direction: column;
  background: var(--panel); border: 1px solid var(--line);
  border-radius: 16px; box-shadow: 0 24px 70px rgba(0, 0, 0, .7);
}
.onboard-head {
  display: flex; align-items: center; justify-content: space-between;
  padding: 12px 14px; border-bottom: 1px solid var(--line);
}
.onboard-label { font: 12px var(--mono); color: var(--muted); letter-spacing: .06em; }
.onboard-body { padding: 16px; overflow: auto; }
.onboard-body h2 { margin: 0 0 8px; }
.onboard-text { line-height: 1.5; }
.onboard-actions { display: flex; flex-direction: column; gap: 8px; margin-top: 14px; }
.onboard-perm { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.onboard-foot {
  display: flex; align-items: center; justify-content: space-between;
  padding: 12px 14px; border-top: 1px solid var(--line);
}
