/* ████████████████████████████████████████████████████████ */
/* ██  base.css — tokens, reset, layout, nav, responsive  ██ */
/* ████████████████████████████████████████████████████████ */

/* ── 1. DESIGN TOKENS ──────────────────────────────────── */
:root {
  --bg:#1C1C1E; --surf:#252525; --surf2:#2A2A2C; --surf3:#333335;
  --border:rgba(255,255,255,0.07); --border2:rgba(255,255,255,0.13);
  --acc:#C0654A; --acc2:#a0523a; --acl:#d4785e;
  --gold:#C2A15A; --goldd:#a8883f;
  --green:#2E5E4E; --greenl:#3a7a63;
  --coral:#e11d48; --sky:#0284c7; --purp:#7c3aed;
  --tx:#F5F5F0; --muted:#8E8E93; --dim:#636366;
  --r:20px; --pill:100px;
  --nav-h:58px;
  --font-ui:'Plus Jakarta Sans',system-ui,sans-serif;
  --font-display:'Playfair Display',Georgia,serif;
}
body.light {
  --bg:#FAFAFA; --surf:#ffffff; --surf2:#F5F5F0; --surf3:#EEEEE8;
  --border:rgba(0,0,0,0.07); --border2:rgba(0,0,0,0.13);
  --acc:#2E5E4E; --acc2:#225040; --acl:#3a7a63;
  --tx:#1C1C1E; --muted:#8E8E93; --dim:#AEAEB2;
}
body.light .bni-map-orb{background:#2E5E4E;box-shadow:0 3px 14px rgba(46,94,78,0.35)}
body.light #map-type-toggle{background:var(--surf2)!important;border-color:var(--border)!important;backdrop-filter:none}
body.light .map-type-btn{color:var(--muted)!important}
body.light .map-type-btn.on{color:#fff!important}
body.light #map-loc-clear{color:rgba(0,0,0,0.4)}
body.light #map-loc-suggestions{background:var(--surf2)!important;border-color:var(--border)!important}
body.light #map-loc-suggestions div{color:var(--tx)!important;border-color:var(--border)!important}
body.light #map-loc-suggestions div:hover{background:var(--surf3)!important}
body.light #map-cal-btn{background:var(--surf2)!important;border-color:var(--border)!important;backdrop-filter:none}
body.light #map-cal-btn svg{stroke:var(--tx)!important}
body.light #map-cal-panel{background:var(--surf2)!important;border-color:var(--border)!important;font-family:'Plus Jakarta Sans',sans-serif!important;color:var(--tx)!important}
body.light #map-cal-panel input[type=date]{background:var(--surf2);border-color:var(--border);color:var(--tx);color-scheme:light}
body.light #map-cal-panel span,body.light #map-cal-panel div{color:var(--tx)!important;font-family:'Plus Jakarta Sans',sans-serif!important}
body.light #map-cal-panel button{background:var(--surf3)!important;color:var(--tx)!important;border-color:var(--border)!important;font-family:'Plus Jakarta Sans',sans-serif!important}
body.light #map-cal-panel button[onclick*="applyAndCloseMapCalendar"]{background:var(--acc)!important;color:#fff!important;border-color:var(--acc)!important}
body.light #cal-month-label{color:var(--tx)!important;font-family:'Plus Jakarta Sans',sans-serif!important}
body.light #cal-range-label{font-family:'Plus Jakarta Sans',sans-serif!important}
body.light #map-event-count{background:var(--surf2)!important;border-color:var(--border)!important;color:var(--tx)!important}
body.light #map-preview-card{background:var(--surf)!important;border-color:var(--border)!important;color:var(--tx)!important}
body.light #map-loc-suggestions .map-sug-item div{color:var(--tx)!important}
body.light #map-loc-suggestions .map-sug-item:not([style*="inset"]){background:transparent}
body.light .logo-sq{box-shadow:0 2px 10px rgba(46,94,78,0.25)}
body.light #toast{background:rgba(28,28,30,0.92);color:#F5F5F0}
.leaflet-control-attribution a,.leaflet-control-attribution{color:#a89880!important}
body,.surf,.col-main,.col-detail,.sidebar,.topbar,.bnav,.tabs,
.vc,.sc,.stbox,.phero,.nm,.ci,.fpill,.fp,
.ib,.sbtn,.dpill{
  transition:background 0.25s,border-color 0.25s,color 0.25s;
}

/* ── 2. RESET ──────────────────────────────────────────── */
*{margin:0;padding:0;box-sizing:border-box;-webkit-tap-highlight-color:transparent}
/* Keyboard focus — only visible on Tab, not on click.
   Inputs across the app use inline `outline:none` (for aesthetic control of
   the focus border-colour), which would kill the default outline-based ring
   on :focus-visible. To keep keyboard-only focus rings visible without fighting
   inline styles everywhere, the input/textarea/select rules use box-shadow
   (which isn't touched by inline `outline:none`). Non-input elements keep the
   lighter outline treatment. */
:focus-visible{outline:2px solid var(--acc);outline-offset:2px;border-radius:4px}
input:focus-visible,textarea:focus-visible,select:focus-visible{outline:none;box-shadow:0 0 0 2px var(--acc)}
button:focus-visible{outline:none;box-shadow:0 0 0 2px var(--acc)}
.tog:focus-visible{outline:2px solid var(--acc);outline-offset:3px}
.bni:focus-visible,.si:focus-visible{outline:2px solid var(--acc);outline-offset:-2px;border-radius:8px}
.cpost-submit:focus-visible,.ebtn:focus-visible,.pop-p:focus-visible,.pop-s:focus-visible{outline:2px solid #fff;outline-offset:2px}

/* iOS Safari zooms the viewport in on focus when a text input's font-size is
   smaller than 16px — which inside a native-app wrapper looks like the keyboard
   broke the layout. Force 16px on iOS only (WebKit + touch pointer), so other
   platforms (Android, macOS Safari desktop, Chrome, Firefox) keep the existing
   visual design. The :not(...) list leaves non-text inputs (checkboxes, radios,
   range sliders) alone — their font-size doesn't affect zoom. !important is
   required because most inputs set font-size via inline style. */
@supports (-webkit-touch-callout: none) {
  @media (pointer: coarse) {
    input:not([type='checkbox']):not([type='radio']):not([type='range']):not([type='color']):not([type='file']),
    textarea,
    select { font-size: 16px !important; }
  }
}
html{height:100%;height:100dvh;background:var(--bg)}
body{
  background:var(--bg);color:var(--tx);
  font-family:'Plus Jakarta Sans',system-ui,sans-serif;
  display:flex;flex-direction:column;width:100%;
  height:100vh;height:100dvh;overflow:hidden;
}
/* Edge-to-edge support — Android 15+ ignores setStatusBarColor and forces
   the WebView under the system bars. Padding the SCROLL panels (instead of
   body) keeps the bottom nav at its natural position while pushing scroll
   content below the status bar. The bnav handles its own gesture-pill
   padding via env(safe-area-inset-bottom) below. */
.panel{padding-top:env(safe-area-inset-top,0px)}
/* When a modal/sheet is open we want the underlying app to stop scrolling
   so swipes during the slide-in animation don't move content behind. */
body.cm-modal-open{overflow:hidden;touch-action:none}

/* ── 3. LOGO ───────────────────────────────────────────── */
.logo-wrap{display:flex;align-items:center;gap:9px}
.logo-sq{width:32px;height:32px;border-radius:9px;background:var(--surf2);display:flex;align-items:center;justify-content:center;font-size:18px;color:#fff;flex-shrink:0;overflow:hidden;box-shadow:0 2px 10px rgba(0,0,0,0.25)}
.logo-txt{font-family:'Playfair Display',Georgia,serif;font-weight:700;font-size:1.15rem;letter-spacing:-0.03em;line-height:1}
.logo-txt .d{color:var(--tx)}.logo-txt .t{color:var(--gold)}

/* ── 4. SHELL & COLUMNS ────────────────────────────────── */
.shell{display:flex;flex:1;overflow:hidden;min-height:0}
.sidebar{display:none;flex-direction:column;width:68px;flex-shrink:0;background:var(--surf);border-right:1px solid var(--border);padding:18px 0;align-items:center;gap:4px}
.sb-logo{display:flex;flex-direction:column;align-items:center;gap:6px;margin-bottom:22px}
.sb-logo .logo-sq{width:40px;height:40px;border-radius:12px;font-size:22px}
.sb-logo .sb-name{font-family:'Plus Jakarta Sans',sans-serif;font-weight:800;font-size:0.52rem;letter-spacing:0.04em;text-transform:uppercase;color:var(--muted)}
.si{width:48px;height:48px;border-radius:13px;display:flex;flex-direction:column;align-items:center;justify-content:center;gap:3px;cursor:pointer;border:1px solid transparent;color:var(--dim);transition:all 0.15s;padding-top:5px}
.si span.ico{font-size:1.1rem;position:relative;top:3px}.si span.lbl{font-family:'Plus Jakarta Sans',sans-serif;font-size:0.5rem;font-weight:700;letter-spacing:0.05em;text-transform:uppercase}
.si:hover{background:var(--surf2);color:var(--muted)}
.si.on{background:rgba(194,65,12,0.09);color:var(--acc);border-color:rgba(194,65,12,0.18)}
.sb-bot{margin-top:auto;display:flex;flex-direction:column;align-items:center;gap:4px}
.col-main{flex:1;display:flex;flex-direction:column;overflow:hidden;min-height:0;max-width:100%}
.col-detail{display:none!important;flex:1;background:var(--bg);overflow-y:auto;padding:28px;flex-direction:column;gap:16px}
.col-detail::-webkit-scrollbar{width:0}

/* ── 5. TOPBAR ─────────────────────────────────────────── */
.topbar{display:flex;align-items:center;justify-content:flex-end;padding:8px 14px;flex-shrink:0;z-index:10;gap:8px;position:relative}
.tb-r{display:flex;gap:8px;margin-left:auto}
.ib{width:36px;height:36px;border-radius:11px;background:var(--surf);border:1px solid var(--border);display:flex;align-items:center;justify-content:center;cursor:pointer;font-size:0.95rem;transition:all 0.15s;position:relative}
.ib:hover{background:var(--surf2)}
/* Numeric count badge — shared shape for the bell, social tab, and messages
   tab. Single digit "1"–"9" or "9+" (cap). The .on class controls visibility,
   set by setBadgeCount() in js/core.js. The legacy round-dot rules (.nd /
   .nav-dot) used to live here too — they were dead code that source-order-
   overrode this rule's background, leaving the bright #4ade80 dot showing
   even though .cm-count-badge was supposed to win. Removed for clarity. */
.cm-count-badge{
  display:none;align-items:center;justify-content:center;
  min-width:14px;height:14px;padding:0 4px;border-radius:8px;
  background:var(--acc);color:#fff;
  font-family:'Plus Jakarta Sans',sans-serif;font-size:0.58rem;font-weight:800;line-height:1;
  border:1.5px solid var(--bg);box-sizing:content-box;pointer-events:none;
  width:auto;
  /* Default position — top-right corner pin (iOS app-icon style). The bell
     and any other badges that sit on a small button use this verbatim. The
     sidebar + mobile-nav refine via the rules below. */
  position:absolute;top:-5px;right:-6px;transform:none;
}
.cm-count-badge.on{display:flex}

/* Sidebar nav (.si): badge sits at the top-right corner of the icon area
   when the sidebar is narrow. At ≥1380px the sidebar becomes wide and
   row-oriented with an inline label, so the badge moves to the right edge
   of the row for the inline placement that works with that layout. */
.si > .cm-count-badge{top:5px;right:8px}
@media(min-width:1380px){
  .si > .cm-count-badge{top:50%;right:10px;transform:translateY(-50%)}
}

/* Mobile bottom nav: badge lives inside .bni-ico (the 22×22 icon container)
   so its position scales with the icon, not with the variable .bni button
   width. Sticks out of the icon's top-right corner. The right offset is
   pushed further out (-12) so the badge clearly reads as separate from
   the icon glyph at small sizes — matching iOS/Android badge conventions. */
.bni-ico > .cm-count-badge{top:-5px;right:-12px}

/* ── City picker pill ────────────────────────────────────
   Replaces the city <input> after the user picks a verified suggestion.
   Same height/border-radius as the input so the field doesn't jump.
   .cm-city-pill is the wrapper, .cm-city-pill-text the label, .cm-city-pill-x
   the remove button. Toggled via JS in events.js (_showCityPill /
   _clearCityPill). Visible state set via inline style="display:flex" so
   nothing surprises external callers; the default is display:none. */
.cm-city-pill{
  display:none;align-items:center;justify-content:space-between;gap:10px;
  width:100%;box-sizing:border-box;
  background:var(--surf2);border:1.5px solid var(--acc);border-radius:11px;
  padding:9px 12px;
  font-family:'Plus Jakarta Sans',sans-serif;font-size:0.9rem;color:var(--tx);
}
.cm-city-pill-text{
  flex:1;min-width:0;font-weight:600;
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis;
}
.cm-city-pill-x{
  background:none;border:none;color:var(--muted);cursor:pointer;
  padding:4px;border-radius:6px;flex-shrink:0;
  display:flex;align-items:center;justify-content:center;
  transition:color 0.15s,background 0.15s;
}
.cm-city-pill-x:hover{color:var(--tx);background:var(--surf3)}

/* ── 6. TABS & PANELS ──────────────────────────────────── */
.tabs{display:flex;flex-shrink:0;border-bottom:1px solid var(--border)}
.tab{flex:1;padding:9px 4px;font-family:'Plus Jakarta Sans',sans-serif;font-size:0.7rem;font-weight:700;letter-spacing:0.02em;color:var(--dim);cursor:pointer;border:none;background:none;border-bottom:2px solid transparent;margin-bottom:-1px;transition:all 0.18s}
.tab.on{color:var(--acc);border-bottom-color:var(--acc)}
.tab:hover:not(.on){color:var(--muted)}
.panel{display:none;flex:1;overflow-y:auto;overflow-x:hidden;flex-direction:column}
.panel.on{display:flex}
.panel::-webkit-scrollbar{width:0}

/* Force the profile hero onto its own GPU compositor layer. Without this,
   the Android Chromium WebView occasionally double-paints elements with a
   linear-gradient background inside a relative-positioned container —
   visible as a ghost copy of the entire hero stacked just below itself.
   iOS WKWebView and desktop Chromium don't trigger the bug.
   translateZ(0) + will-change:transform promotes the element to its own
   layer so the paint can't smear across siblings. */
#profile-hero{transform:translateZ(0);will-change:transform}

/* ── 7. BOTTOM NAV ─────────────────────────────────────── */
.bnav{display:flex;background:var(--surf);border-top:1px solid var(--border);flex-shrink:0;height:var(--nav-h);align-items:center;padding-bottom:env(safe-area-inset-bottom,0px);position:relative;z-index:50}
.bnav-theme{width:42px;flex-shrink:0;display:flex;align-items:center;justify-content:center;align-self:stretch;cursor:pointer;border:none;background:none}
.bnav-theme-ico{display:flex;align-items:center;justify-content:center;transition:all 0.18s}
.bnav-theme-ico svg{width:14px;height:14px;stroke:var(--muted);fill:none}
.bnav-theme-ico:hover{border-color:var(--gold);background:rgba(194,161,90,0.1)}
.bni{flex:1;display:flex;flex-direction:column;align-items:center;justify-content:center;padding:0;cursor:pointer;border:none;background:none;color:var(--dim);transition:color 0.18s;gap:3px;height:100%;touch-action:manipulation;-webkit-tap-highlight-color:transparent}
.bni.on{color:var(--gold)}.bni:hover:not(.on){color:var(--muted)}
.bni-ico{width:22px;height:22px;display:flex;align-items:center;justify-content:center;position:relative}
.bni-ico svg{width:20px;height:20px;stroke:currentColor}
.bni-map-orb{width:40px;height:40px;border-radius:13px;background:var(--acc);display:flex;align-items:center;justify-content:center;box-shadow:0 3px 14px rgba(194,65,12,0.4);transition:box-shadow 0.2s,transform 0.15s}
.bni-map-orb svg{width:20px;height:20px;stroke:#fff}
.bni-map-orb:hover{transform:scale(1.06)}
.bnlbl{font-family:'Plus Jakarta Sans',sans-serif;font-size:0.52rem;font-weight:700;text-transform:uppercase;letter-spacing:0.05em}
/* Legacy .nav-dot round-dot styling removed — it source-order-overrode the
   .cm-count-badge background and display rules, which is why mobile nav
   badges kept showing as bright green even after the unified badge styles
   were in place. Only the class name remains on the badge HTML elements
   for DOM identification. */

/* ── 8. DETAIL WELCOME ─────────────────────────────────── */
.dw{display:flex;flex-direction:column;align-items:center;justify-content:center;height:100%;text-align:center;padding:32px 24px}
.dw-icon{width:64px;height:64px;border-radius:18px;background:var(--surf2);display:flex;align-items:center;justify-content:center;font-size:34px;color:#fff;box-shadow:0 6px 24px rgba(0,0,0,0.2);margin-bottom:16px;overflow:hidden;padding:0}
.dw-word{font-family:'Plus Jakarta Sans',sans-serif;font-weight:800;font-size:2.1rem;letter-spacing:-0.04em;margin-bottom:10px}
.dw-tag{font-size:0.93rem;color:var(--muted);line-height:1.6;margin-bottom:32px;max-width:220px}
.dw-stats{display:flex;align-items:stretch;background:var(--surf);border:1px solid var(--border);border-radius:16px;padding:18px 22px;margin-bottom:24px;box-shadow:0 2px 12px rgba(194,65,12,0.06);width:100%;max-width:380px}
.dws{flex:1;text-align:center;display:flex;flex-direction:column;align-items:center;justify-content:center}
.dwsn{font-family:'Plus Jakarta Sans',sans-serif;font-weight:800;font-size:1.75rem;color:var(--acc);line-height:1;margin-bottom:4px}
.dwsl{font-size:0.63rem;font-weight:600;color:var(--dim);text-transform:uppercase;letter-spacing:0.06em;min-height:2em;display:flex;align-items:flex-start;justify-content:center;line-height:1.2}
.dwdiv{width:1px;background:var(--border);margin:0 4px;flex-shrink:0;align-self:center;height:34px}
.dw-hint{font-size:0.75rem;color:var(--dim);font-style:italic}

/* ── 9. RESPONSIVE ─────────────────────────────────────── */
@media(min-width:768px){
  .topbar,.tabs,.bnav{display:none!important}
  .mobile-only{display:none!important}
  .shell{display:flex}
  .sidebar{display:flex}
  .col-main{min-width:0;max-width:none}
  #p-events{padding:14px 22px 20px;gap:12px}
  #p-social{padding:14px 22px;gap:10px}
  #p-map{padding:0}
  /* On desktop the messages panel keeps its mobile width — chat lists
     read better as a single narrow column than stretched edge-to-edge.
     The empty space to the right is reserved for a future companion
     surface (open conversation pane / contact preview / etc.). */
  #p-msg{padding:14px 22px 0;flex-direction:column;max-width:480px}
  #leaflet-map{height:100%;min-height:500px}
}
@media(min-width:1380px){
  .sidebar{width:192px;align-items:flex-start;padding:20px 14px}
  .sb-logo{flex-direction:row;gap:10px;margin-bottom:28px;margin-left:2px}
  .sb-logo .logo-sq{width:38px;height:38px;font-size:20px}
  .sb-logo .sb-name{display:none}
  .sidebar::before{display:none}
  .si{width:100%;height:42px;flex-direction:row;justify-content:flex-start;padding:0 10px;border-radius:11px;font-size:0.95rem}
  .si span.lbl{font-size:0.76rem;text-transform:none;letter-spacing:0.01em;font-weight:600}
}
@media(max-width:767px){
  #fab-fixed{bottom:80px!important}
  .topbar,.tabs,.sidebar{display:none!important}
  #p-map>div>div:first-child{flex-wrap:wrap}
  .ev-filter-btn-el{order:10;width:100%;justify-content:center;margin-top:2px}
  .vlist{padding-bottom:4px!important}
}
