/* map-shell.css — shared theme primitives for the map apps.
   extracted verbatim from the global map (apps/global) so the research
   maps can adopt the same design language without copying styles that
   then drift. this sheet owns tokens, chrome containers, and framework
   controls; each app keeps its own layout, machinery, and semantic
   colours (status colours on research surfaces stay app-side).
   contract: docs/development/theme-primitives-to-research-maps.md.
   load order: link this sheet before the app stylesheet so app rules
   can override it. */

/* tokens: safe-area insets with minimums, surface and text colours.
   apps override per token after linking (e.g. a different --bg). */
:root {
  --bg: #f8fafc;
  --panel: rgba(13, 16, 23, 0.82);
  --text: #e8edf2;
  --accent: #cbd5f5;
  --muted: #94a3b8;
  --safe-top: max(12px, env(safe-area-inset-top, 0px));
  --safe-right: max(12px, env(safe-area-inset-right, 0px));
  --safe-bottom: max(10px, env(safe-area-inset-bottom, 0px));
  --safe-left: max(12px, env(safe-area-inset-left, 0px));
}

/* base: one box model, full-bleed page, the shared type stack */
* { box-sizing: border-box; }
body, html { margin: 0; height: 100%; background: var(--bg); color: var(--text); font-family: "Work Sans", -apple-system, "Segoe UI", sans-serif; }

/* any author display rule silently defeats the hidden attribute; restore
   its authority once here instead of per-element companion rules */
[hidden] { display: none !important; }

/* the dark pill: every floating control wears this. sizing, typography,
   and display stay with the app; the knobs let a control brighten,
   tint, or drop the shadow without leaving the recipe. */
.shell-pill {
  --pill-bg: rgba(15, 23, 42, 0.72);
  --pill-border: rgba(255, 255, 255, 0.08);
  --pill-shadow: 0 6px 14px rgba(0, 0, 0, 0.25);
  --pill-opacity: 0.85;
  background: var(--pill-bg);
  border: 1px solid var(--pill-border);
  border-radius: 999px;
  color: #e2e8f0;
  box-shadow: var(--pill-shadow);
  opacity: var(--pill-opacity);
}

/* corner grammar: where chrome may sit. top-left carries transient
   state only, top-centre the key, top-right identity, bottom-left the
   refresh button, bottom-centre the action row, bottom-right stays with
   the stock map controls. amendment (2026-07-16): the action row also
   seats the switch-country pill — cross-map navigation, not a map
   action — a deliberate breach recorded in
   docs/development/datamaps-pill-review-2026-07.md.
   amendment (2026-07-17, jb): the transient set-north badge rides the
   right edge — below the wordmark on desktop, the corner itself on
   phones where the wordmark hides — so the left edge stays clear for
   the key. */
.shell-top-left { position: fixed; left: var(--safe-left); top: var(--safe-top); z-index: 13; }
.shell-top-right { position: fixed; right: var(--safe-right); top: var(--safe-top); z-index: 12; }
/* full-width so its content centres, but the empty flanks must let clicks
   through to whatever sits beneath (e.g. the top-right wordmark); only the
   actual controls inside catch pointer events */
.shell-top-centre { position: fixed; left: 0; right: 0; top: var(--safe-top); z-index: 13; display: flex; flex-direction: column; align-items: center; pointer-events: none; }
.shell-top-centre > * { pointer-events: auto; }
.shell-bottom-left { position: fixed; left: var(--safe-left); bottom: var(--safe-bottom); z-index: 13; }
.shell-bottom-centre { position: fixed; left: 50%; bottom: var(--safe-bottom); transform: translateX(-50%); z-index: 13; }

/* identity-pill internals: a quiet divider between entries, and selects
   stripped of native chrome so they sit in the pill as text with a
   caret, not as a widget */
.shell-divided > * + * { border-left: 1px solid rgba(255, 255, 255, 0.18); padding-left: 8px; }
.shell-pill-select {
  appearance: none;
  -webkit-appearance: none;
  background: transparent url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='8' height='6'%3E%3Cpath d='M1 1l3 3 3-3' stroke='%2394a3b8' stroke-width='1.5' fill='none' stroke-linecap='round'/%3E%3C/svg%3E") no-repeat right center;
  border: none;
  border-left: 1px solid rgba(255, 255, 255, 0.18);
  border-radius: 0;
  padding-left: 8px;
  padding-right: 13px;
  color: #e2e8f0;
  font-size: 12px;
  line-height: 1;
  cursor: pointer;
}
.shell-pill-select:focus { outline: none; }

/* toast: centred fixed pill, large type on desktop; on phones it
   shrinks and wraps inside the screen instead of running off it */
.shell-toast {
  position: fixed;
  left: 50%;
  top: 48%;
  transform: translate(-50%, -50%);
  background: rgba(15, 23, 42, 0.72);
  border: 1px solid rgba(255, 255, 255, 0.12);
  color: #e2e8f0;
  border-radius: 999px;
  padding: 10px 18px;
  font-size: 28px;
  opacity: 0;
  pointer-events: none;
  transition: opacity 180ms ease;
  z-index: 12;
  white-space: nowrap;
}
.shell-toast.visible { opacity: 0.8; }
@media (max-width: 640px) {
  .shell-toast {
    font-size: 14px;
    padding: 8px 14px;
    max-width: 86vw;
    white-space: normal;
    text-align: center;
    border-radius: 16px;
  }
}

/* touch floor: thumb-sized targets on phones (style-guide rule) */
@media (max-width: 640px) {
  .shell-touch { min-height: 44px; min-width: 44px; }
}

/* phones are exploration surfaces (jb ruling 2026-07-16): the whole
   top-right wordmark pill hides below 640px. its contents are desktop
   affordances — evidence submission, the OSM editor, the theme select,
   the repo link — and cross-map travel already rides the bottom-bar
   data maps pill. this supersedes the member-by-member hide, which
   since the data-maps link retirement left the global page's pill an
   empty lozenge on phones. the class qualifier outranks the surface
   sheets' unqualified #wordmark display rules, which load after this
   sheet and would otherwise win the cascade tie */
@media (max-width: 640px) {
  #wordmark.shell-pill { display: none; }
}

/* popup idiom: dark translucent card, no tip, pill close button,
   attribute grid, footnotes in white — never the grey whisper */
.maplibregl-popup-content {
  max-width: min(1080px, 92vw);
  background: rgba(15, 23, 42, 0.72);
  border: 1px solid rgba(255, 255, 255, 0.12);
  border-radius: 16px;
  box-shadow: 0 18px 32px rgba(0, 0, 0, 0.22);
  color: #e2e8f0;
  overflow: hidden;
}
.maplibregl-popup-tip { display: none; }
.maplibregl-popup-close-button {
  width: 28px;
  height: 28px;
  font-size: 20px;
  line-height: 26px;
  border-radius: 999px;
  color: #f8fafc;
  background: rgba(15, 23, 42, 0.6);
}
/* the idiom's content classes are scoped to maplibre popups so pages
   with their own popup-actions (e.g. the leaflet verification surface)
   are untouched by this sheet */
.maplibregl-popup-content .popup-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  margin-top: 8px;
}
.maplibregl-popup-content .popup-actions a,
.maplibregl-popup-content .popup-actions button {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 9px;
  padding: 8px 12px;
  border-radius: 12px;
  border: 1px solid rgba(255, 255, 255, 0.12);
  background: rgba(15, 23, 42, 0.45);
  color: #e2e8f0;
  font-size: 17px;
  text-decoration: none;
  cursor: pointer;
}
.maplibregl-popup-content .place-attrs {
  display: grid;
  grid-template-columns: auto 1fr;
  gap: 2px 14px;
  margin: 4px 0 2px;
  font-size: 13px;
  color: #cbd5e1;
}
.maplibregl-popup-content .place-attr { display: contents; }
.maplibregl-popup-content .place-attr-key {
  color: #94a3b8;
  font-weight: 600;
}
.maplibregl-popup-content .place-attr-val { color: #e2e8f0; }
.maplibregl-popup-content .place-note {
  margin: 4px 0 2px;
  font-size: 11px;
  color: #e2e8f0;
}

/* stock controls: attribution at the true corner, credits always
   legible (the places data is odbl), and the collapsed credit disc
   stays thumb-tappable despite the tiny text */
.maplibregl-ctrl-bottom-right { bottom: 0; }
.maplibregl-ctrl-attrib,
.maplibregl-ctrl-attrib.maplibregl-compact {
  background: rgba(255, 255, 255, 0.82);
  color: #0f172a;
  border: 1px solid rgba(15, 23, 42, 0.2);
  border-radius: 6px;
  padding: 0 3px;
  font-size: 7px;
  line-height: 1.05;
  box-shadow: 0 5px 10px rgba(15, 23, 42, 0.2);
}
.maplibregl-ctrl-attrib a {
  color: #0f172a;
}
.maplibregl-ctrl-attrib a:hover {
  color: #1e293b;
}
.maplibregl-ctrl-attrib.maplibregl-compact:not(.maplibregl-compact-show) {
  min-width: 24px;
  min-height: 24px;
  border-radius: 12px;
}
.maplibregl-ctrl-attrib-button {
  width: 24px;
  height: 24px;
}
