/* ============ Backgammon Boom — dark-luxury design system ============
   Palette: deep charcoal night + brushed gold (matches the walnut/gold
   board), teal for success, ruby for danger. Glass cards, soft glows,
   bottom navigation, and micro-animations throughout. */

:root {
  --bg: #0c0e13;
  --bg-2: #12151d;
  --card: rgba(255, 255, 255, 0.045);
  --card-solid: #171b24;
  --stroke: rgba(255, 255, 255, 0.08);
  --text: #f0ede4;
  --hint: #8f97a8;
  --gold: #c9a227;
  --gold-2: #e8cd6b;
  --accent: var(--gold);
  --accent-text: #1a1405;
  --ok: #2ec4b6;
  --warn: #f0b429;
  --danger: #ef5a6a;
  --radius: 18px;
  --nav-h: 64px;
}

* { box-sizing: border-box; -webkit-tap-highlight-color: transparent; }

/* The app is a single vertical-scroll column at every screen size — nothing
   should ever be reachable by scrolling sideways, and vertical scroll must
   always work. html/body themselves never scroll (height locked to the
   viewport, overflow hidden on both axes) — actual scrolling happens inside
   the nested #app-scroll container below instead. This is deliberate: some
   Telegram WebViews hijack the *document's own* vertical drag for their
   swipe-to-close/minimize gesture, which blocked scrolling entirely for
   some users even with Telegram.WebApp.disableVerticalSwipes() called (that
   API doesn't exist on older clients, and even where it does this is a
   sturdier fix). A nested overflow:auto element's internal scroll isn't
   affected by that outer gesture recognizer the same way. */
html {
  overflow: hidden;
  width: 100%;
  height: 100%;
}
body {
  margin: 0;
  font-family: Vazirmatn, system-ui, "Segoe UI", Tahoma, sans-serif;
  background:
    radial-gradient(ellipse 90% 40% at 50% -5%, rgba(201, 162, 39, 0.13), transparent 60%),
    radial-gradient(ellipse 70% 30% at 85% 100%, rgba(46, 196, 182, 0.05), transparent 60%),
    linear-gradient(180deg, var(--bg-2), var(--bg) 40%);
  color: var(--text);
  direction: rtl;
  overscroll-behavior: none;
  height: 100%;
  width: 100%;
  overflow: hidden;
  touch-action: pan-y;
  position: relative;
}
/* The one true scrolling element: fills the viewport (absolute inset:0
   against body's position:relative), vertical scroll only. Fixed-position
   children of body (topbar, bottom-nav, overlays) render above it exactly
   as before regardless of where they sit in the DOM relative to this
   wrapper — position:fixed always escapes it. */
#app-scroll {
  position: absolute;
  inset: 0;
  overflow-y: auto;
  overflow-x: hidden;
  -webkit-overflow-scrolling: touch;
  touch-action: pan-y;
  overscroll-behavior-y: contain;
}
/* Emblem watermark: fixed behind every screen, sized to its own aspect ratio
   (never stretched) and kept low-opacity + blurred at the edges so it reads
   as ambient background texture behind cards/text, not a flat sticker. The
   image's own near-black background already matches --bg, so it blends in
   without a visible box. */
body::before {
  content: "";
  position: fixed;
  inset: 0;
  z-index: -1;
  background-image:
    radial-gradient(ellipse 60% 45% at 50% 38%, rgba(0,0,0,0) 0%, var(--bg) 78%),
    url("/static/img/bg-mask.jpg");
  background-repeat: no-repeat, no-repeat;
  background-position: center 30%, center 30%;
  background-size: 100% 100%, min(82vw, 540px) auto;
  opacity: 0.5;
  filter: saturate(1.15);
  pointer-events: none;
}

/* Intro splash: the complete video (object-fit:contain — never cropped/
   zoomed) shown at a moderate size, centered, with a pulsing gold glow
   halo behind it for a premium feel instead of a plain floating square.
   JS (app.js) adds .fade-out on the video's `ended` event, then removes
   the element once the transition finishes, revealing the app underneath
   — which carries the same emblem as its permanent background watermark
   (body::before above), so the fade reads as the logo settling into
   place. */
#intro-splash {
  position: fixed; inset: 0; z-index: 9999;
  background: var(--bg);
  display: flex; align-items: center; justify-content: center;
  opacity: 1;
  transition: opacity 1.1s ease;
}
#intro-splash.fade-out { opacity: 0; pointer-events: none; }
#intro-video-wrap {
  position: relative;
  width: min(78vw, 420px);
  height: min(78vw, 420px);
  border-radius: 20px;
  animation: introGlow 2.4s ease-in-out infinite;
}
@keyframes introGlow {
  0%, 100% { box-shadow: 0 0 26px 4px rgba(201,162,39,0.4), 0 0 60px 14px rgba(201,162,39,0.18), 0 12px 40px rgba(0,0,0,0.6); }
  50%      { box-shadow: 0 0 46px 12px rgba(232,205,107,0.65), 0 0 100px 28px rgba(201,162,39,0.32), 0 12px 40px rgba(0,0,0,0.6); }
}
#intro-video {
  width: 100%; height: 100%; object-fit: contain; display: block;
  border-radius: 20px;
}

.hidden { display: none !important; }

/* Latin usernames (@foo) keep their natural direction inside RTL text. */
.hero-name, .lb-name, .au-name, .hist-op, .aun { unicode-bidi: plaintext; }

.netbar {
  position: fixed; top: 0; left: 0; right: 0; z-index: 100;
  background: var(--danger); color: #fff; text-align: center;
  padding: 8px 12px; font-size: 13px; font-weight: 600;
}
.toast {
  position: fixed; bottom: calc(var(--nav-h) + 20px); left: 50%; transform: translateX(-50%);
  background: rgba(12, 14, 19, 0.92); border: 1px solid var(--stroke);
  color: #fff; padding: 10px 18px; box-shadow: 0 8px 24px rgba(0,0,0,0.5);
  border-radius: 999px; font-size: 13px; z-index: 100; max-width: 90%;
  animation: toastIn .22s ease;
}
@keyframes toastIn { from { opacity: 0; transform: translate(-50%, 8px); } }

/* ============ Top bar ============ */
.topbar {
  display: flex; align-items: center; gap: 10px;
  padding: 12px 14px 10px;
  position: sticky; top: 0; z-index: 10;
  background: linear-gradient(180deg, rgba(12,14,19,0.96), rgba(12,14,19,0.82));
  backdrop-filter: blur(12px); -webkit-backdrop-filter: blur(12px);
  border-bottom: 1px solid rgba(255,255,255,0.04);
}
.who-chip { display: flex; align-items: center; gap: 9px; flex: 1; min-width: 0; }
.avatar {
  width: 38px; height: 38px; border-radius: 13px; flex-shrink: 0;
  background: linear-gradient(135deg, var(--gold-2), var(--gold) 60%, #8a6a14);
  color: var(--accent-text); font-weight: 800; font-size: 16px;
  display: flex; align-items: center; justify-content: center;
  box-shadow: 0 3px 10px rgba(201, 162, 39, 0.35);
}
.chips { display: flex; gap: 6px; align-items: center; }
.chip {
  background: var(--card); border: 1px solid var(--stroke);
  border-radius: 999px; padding: 6px 11px; font-size: 12.5px; font-weight: 700;
  display: flex; gap: 5px; align-items: center;
}
.chip.vip { background: linear-gradient(135deg, #6a4a00, #b8860b); border: none; color: #fff; }
.icon-btn {
  background: var(--card); border: 1px solid var(--stroke);
  border-radius: 12px; padding: 7px 10px; font-size: 15px;
}
.icon-btn.active { background: linear-gradient(135deg, var(--gold-2), var(--gold)); color: var(--accent-text); border-color: transparent; }

/* ============ Layout & screens ============ */
.wrap { padding: 10px 14px calc(var(--nav-h) + 28px); max-width: 640px; margin: 0 auto; }
.screen { animation: screenIn .28s cubic-bezier(.2,.7,.3,1); }
@keyframes screenIn { from { opacity: 0; transform: translateY(10px); } }
h2 { font-size: 19px; margin: 6px 0 14px; font-weight: 800; }
.section-label { font-size: 13px; color: var(--hint); margin: 16px 2px 8px; font-weight: 700; }

/* ============ Bottom navigation ============ */
.bottom-nav {
  position: fixed; bottom: 0; left: 0; right: 0; z-index: 40;
  height: calc(var(--nav-h) + env(safe-area-inset-bottom, 0px));
  padding-bottom: env(safe-area-inset-bottom, 0px);
  display: flex; justify-content: space-around; align-items: stretch;
  background: rgba(15, 17, 24, 0.92);
  backdrop-filter: blur(16px); -webkit-backdrop-filter: blur(16px);
  border-top: 1px solid rgba(255,255,255,0.06);
}
.nav-item {
  flex: 1; display: flex; flex-direction: column; align-items: center; justify-content: center;
  gap: 3px; background: none; border: none; border-radius: 0;
  color: var(--hint); font-size: 10.5px; font-weight: 700; padding: 6px 0;
  position: relative; transition: color .18s;
}
.nav-item .ni { font-size: 21px; transition: transform .18s; filter: grayscale(0.4) opacity(0.75); }
.nav-item.active { color: var(--gold-2); }
.nav-item.active .ni { transform: translateY(-2px) scale(1.12); filter: none; }
.nav-item.active::after {
  content: ""; position: absolute; top: 0; width: 22px; height: 3px; border-radius: 0 0 4px 4px;
  background: linear-gradient(90deg, var(--gold-2), var(--gold));
  box-shadow: 0 2px 8px rgba(232, 205, 107, 0.6);
}

/* ============ Buttons ============ */
button {
  font-family: inherit; cursor: pointer; border: none; border-radius: 13px;
  padding: 11px 14px; font-size: 14px; font-weight: 700;
  background: var(--card-solid); color: var(--text);
  transition: transform .08s ease, opacity .2s, box-shadow .2s;
}
button:active { transform: scale(0.96); }
button:disabled { opacity: 0.45; }
button.primary, button.full.primary {
  background: linear-gradient(135deg, var(--gold-2), var(--gold) 65%, #a8861e);
  color: var(--accent-text);
  box-shadow: 0 4px 16px rgba(201, 162, 39, 0.35);
}
button.ghost { background: transparent; color: var(--hint); border: 1px solid var(--stroke); }
button.ghost.active { background: linear-gradient(135deg, var(--gold-2), var(--gold)); color: var(--accent-text); border-color: transparent; }
button.danger { background: var(--danger); color: #fff; }
button.full { width: 100%; margin-top: 8px; }

/* ============ Hero card (home) ============ */
.hero {
  position: relative; overflow: hidden;
  border-radius: 22px; padding: 18px 16px 16px;
  background:
    radial-gradient(120% 140% at 85% -20%, rgba(232, 205, 107, 0.22), transparent 55%),
    linear-gradient(150deg, #241c0d, #17141c 55%, #12151d);
  border: 1px solid rgba(232, 205, 107, 0.22);
  box-shadow: 0 12px 32px rgba(0,0,0,0.45);
  margin-bottom: 14px;
}
.hero::before {
  content: "🎲"; position: absolute; left: -14px; bottom: -22px; font-size: 110px;
  opacity: 0.07; transform: rotate(-18deg); pointer-events: none;
}
.hero-greet { font-size: 13px; color: var(--hint); font-weight: 600; }
.hero-name { font-size: 21px; font-weight: 900; margin: 3px 0 2px; }
.hero-band { display: inline-flex; align-items: center; gap: 5px; font-size: 12px; font-weight: 700; color: var(--gold-2); }
.level-row { display: flex; align-items: center; gap: 8px; margin-top: 8px; }
.level-badge { font-size: 11.5px; font-weight: 800; color: var(--text); white-space: nowrap; }
.level-bar { flex: 1; height: 6px; border-radius: 4px; background: rgba(255,255,255,0.08); overflow: hidden; min-width: 0; }
.level-bar-fill { height: 100%; background: linear-gradient(90deg, var(--gold-2), var(--gold)); border-radius: 4px; transition: width .4s ease; }
.level-next { font-size: 10px; color: var(--hint); font-weight: 700; white-space: nowrap; flex-shrink: 0; direction: ltr; }
.hero-stats { display: flex; gap: 8px; margin-top: 14px; }
.hstat {
  flex: 1; background: rgba(255,255,255,0.05); border: 1px solid rgba(255,255,255,0.07);
  border-radius: 14px; padding: 10px 6px; text-align: center;
}
.hstat .v { font-size: 17px; font-weight: 900; color: var(--gold-2); }
.hstat .k { font-size: 10.5px; color: var(--hint); margin-top: 2px; font-weight: 700; }

/* ============ Cards ============ */
.glass {
  background: var(--card); border: 1px solid var(--stroke);
  border-radius: var(--radius); padding: 14px;
  margin-bottom: 12px;
}
.card-row { display: flex; align-items: center; gap: 12px; }
.card-row .grow { flex: 1; min-width: 0; }
.card-title { font-size: 14.5px; font-weight: 800; }
.card-desc { font-size: 12px; color: var(--hint); margin-top: 2px; }
.card-emoji {
  width: 44px; height: 44px; border-radius: 14px; flex-shrink: 0; font-size: 22px;
  display: flex; align-items: center; justify-content: center;
  background: rgba(232, 205, 107, 0.1); border: 1px solid rgba(232, 205, 107, 0.18);
}

/* ---- Daily card ---- */
.streak-track { display: flex; gap: 5px; margin: 12px 0 4px; }
.streak-day { flex: 1; text-align: center; }
.streak-dot {
  height: 34px; border-radius: 10px; display: flex; align-items: center; justify-content: center;
  background: rgba(255,255,255,0.05); border: 1px solid var(--stroke);
  font-size: 10.5px; font-weight: 800; color: var(--hint);
}
.streak-day.done .streak-dot {
  background: linear-gradient(135deg, var(--gold-2), var(--gold));
  color: var(--accent-text); border-color: transparent;
  box-shadow: 0 2px 8px rgba(201,162,39,0.4);
}
.streak-day.next .streak-dot { border-color: var(--gold-2); color: var(--gold-2); animation: pulseDot 1.6s ease infinite; }
@keyframes pulseDot { 50% { box-shadow: 0 0 0 5px rgba(232,205,107,0.12); } }
.streak-day .sd-label { font-size: 9.5px; color: var(--hint); margin-top: 3px; }

/* ---- Play mode grid ---- */
.play-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; }
.play-tile {
  border-radius: 18px; padding: 16px 12px; text-align: right;
  background: var(--card); border: 1px solid var(--stroke);
  display: flex; flex-direction: column; gap: 6px; position: relative; overflow: hidden;
}
.play-tile .pt-emoji { font-size: 26px; }
.play-tile .pt-title { font-size: 14px; font-weight: 800; }
.play-tile .pt-desc { font-size: 11px; color: var(--hint); line-height: 1.5; }
.play-tile.gold { background: linear-gradient(150deg, rgba(232,205,107,0.14), var(--card) 60%); border-color: rgba(232,205,107,0.3); }

/* ============ Pickers ============ */
.pill-row { display: flex; flex-wrap: wrap; gap: 8px; }
.pill {
  background: var(--card-solid); border: 2px solid transparent; border-radius: 999px;
  padding: 9px 16px; font-size: 14px; font-weight: 700; position: relative;
}
.pill.active { border-color: var(--gold); color: var(--gold-2); box-shadow: 0 0 12px rgba(201,162,39,0.25); }
.pill.locked { opacity: 0.5; }

/* ============ Lobby ============ */
.grid { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; }
@media (max-width: 380px) { .grid { grid-template-columns: 1fr; } }
.table-card { background: var(--card); border-radius: var(--radius); padding: 14px; display: flex; flex-direction: column; gap: 10px; border: 1px solid var(--stroke); }
.table-card .row { display: flex; justify-content: space-between; align-items: center; }
.table-card h3 { margin: 0; font-size: 15px; }
.badge { font-size: 11px; padding: 3px 9px; border-radius: 999px; font-weight: 700; }
.badge.open { background: rgba(46,196,182,0.14); color: var(--ok); }
.badge.playing { background: rgba(240,180,41,0.14); color: var(--warn); }
.badge.finished { background: rgba(143,151,168,0.14); color: var(--hint); }
.tk-row { cursor: pointer; }
.tk-status { font-size: 11px; padding: 3px 9px; border-radius: 999px; font-weight: 700; flex-shrink: 0; }
.tk-status.open { background: rgba(46,196,182,0.14); color: var(--ok); }
.tk-status.closed { background: rgba(143,151,168,0.14); color: var(--hint); }
.seats { display: flex; flex-direction: column; gap: 6px; min-height: 40px; }
.seat { display: flex; align-items: center; gap: 8px; font-size: 13px; color: var(--hint); }
.seat.filled { color: var(--text); }
.dot { width: 8px; height: 8px; border-radius: 50%; background: var(--hint); }
.seat.filled .dot { background: var(--ok); box-shadow: 0 0 6px rgba(46,196,182,0.7); }

/* ============ Invite / friend room ============ */
.invite-box { margin-top: 18px; background: var(--card); border: 1px solid var(--stroke); border-radius: var(--radius); padding: 16px; text-align: center; }
.invite-link { background: rgba(0,0,0,0.3); border: 1px solid var(--stroke); border-radius: 10px; padding: 10px; font-size: 12px; word-break: break-all; margin: 10px 0; direction: ltr; }
.row-btns { display: flex; gap: 8px; }
.row-btns button { flex: 1; }

/* ============ Waiting / queue ============ */
.center { text-align: center; padding: 40px 16px; }
.spinner { width: 44px; height: 44px; margin: 18px auto; border: 4px solid rgba(255,255,255,0.12); border-top-color: var(--gold-2); border-radius: 50%; animation: spin 0.9s linear infinite; }
@keyframes spin { to { transform: rotate(360deg); } }

/* ============ Tabs / shop ============ */
.tabs { display: flex; gap: 6px; margin-bottom: 14px; }
.tab { flex: 1; background: var(--card-solid); color: var(--hint); padding: 9px 4px; font-size: 12.5px; border-radius: 12px; }
.tab.active { background: linear-gradient(135deg, var(--gold-2), var(--gold)); color: var(--accent-text); }
.shop-list { display: flex; flex-direction: column; gap: 10px; }
.shop-item { background: var(--card); border-radius: 14px; padding: 12px; display: flex; align-items: center; gap: 12px; border: 1px solid var(--stroke); }
.pm-item { background: var(--card); border-radius: 14px; padding: 12px; display: flex; align-items: center; gap: 12px; border: 1px solid var(--stroke); margin-bottom: 8px; }
.pm-icon { font-size: 22px; flex-shrink: 0; }
.pm-body { flex: 1; min-width: 0; }
.pm-title { font-size: 13.5px; font-weight: 800; }
.pm-kind { font-size: 11px; color: var(--hint); font-weight: 600; }
.pm-value { font-size: 13px; color: var(--gold-2); font-weight: 700; direction: ltr; text-align: right; word-break: break-all; margin-top: 2px; }
.pm-note { font-size: 11px; color: var(--hint); margin-top: 2px; }
.pm-action { flex-shrink: 0; font-size: 12px; padding: 8px 12px; }
.swatch { width: 54px; height: 40px; border-radius: 10px; flex-shrink: 0; display: flex; overflow: hidden; border: 1px solid var(--stroke); }
.swatch .half { flex: 1; }
.chk-swatch { width: 54px; height: 40px; border-radius: 10px; flex-shrink: 0; display: flex; align-items: center; justify-content: center; gap: 4px; border: 1px solid var(--stroke); }
.chk-swatch .disc { width: 16px; height: 16px; border-radius: 50%; border: 2px solid; }
.si-body { flex: 1; }
.si-name { font-size: 14px; font-weight: 800; }
.si-price { font-size: 12px; color: var(--hint); margin-top: 2px; }
.si-vip { color: var(--gold-2); }
.si-action { min-width: 76px; }
.si-action button { width: 100%; padding: 9px 8px; font-size: 13px; }
.si-owned-tag { font-size: 10.5px; color: var(--ok); font-weight: 700; margin-top: 2px; }
.av-swatch { font-size: 26px; }

.shop-toolbar { margin-bottom: 12px; }
.shop-toolbar input {
  width: 100%; border-radius: 12px; border: 1px solid var(--stroke);
  background: rgba(255,255,255,0.04); color: var(--text); padding: 10px 13px;
  font-size: 13px; font-family: inherit; margin-bottom: 8px;
}
.shop-toolbar input:focus { outline: none; border-color: var(--gold); }
.shop-empty { text-align: center; color: var(--hint); padding: 30px 0; font-size: 13px; }

/* ============ Profile ============ */
.stat-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; margin-bottom: 14px; }
.stat-tile { background: var(--card); border: 1px solid var(--stroke); border-radius: 14px; padding: 14px; text-align: center; }
.stat-tile .v { font-size: 20px; font-weight: 900; color: var(--gold-2); }
.stat-tile .k { font-size: 11.5px; color: var(--hint); margin-top: 3px; font-weight: 700; }
.vip-line { text-align: center; margin-bottom: 14px; font-weight: 800; padding: 10px; border-radius: 12px; background: var(--card); border: 1px solid var(--stroke); color: var(--hint); }
.vip-line.on { color: var(--gold-2); border-color: rgba(232,205,107,0.35); background: rgba(232,205,107,0.07); }
.shortcut-list { display: flex; flex-direction: column; gap: 8px; margin-top: 8px; }
.shortcut-list button { width: 100%; text-align: right; display: flex; align-items: center; gap: 8px; }

.profile-head { text-align: center; margin-bottom: 14px; }
.ph-avatar {
  width: 64px; height: 64px; margin: 0 auto 8px; border-radius: 20px; font-size: 32px;
  display: flex; align-items: center; justify-content: center;
  background: linear-gradient(150deg, rgba(232,205,107,0.18), rgba(232,205,107,0.04));
  border: 1px solid rgba(232,205,107,0.3);
}
.ph-name { font-size: 17px; font-weight: 900; unicode-bidi: plaintext; }
.ph-meta { font-size: 12px; color: var(--hint); margin-top: 3px; }

/* ---- Achievements ---- */
.ach-section { margin-bottom: 8px; }
.ach-section-head {
  width: 100%; display: flex; justify-content: space-between; align-items: center;
  background: var(--card); border: 1px solid var(--stroke); border-radius: 12px;
  padding: 10px 14px; font-size: 13px; font-weight: 800; color: var(--text); margin-bottom: 6px;
}
.ach-count { font-size: 11.5px; color: var(--gold-2); font-weight: 700; }
.ach-grid { display: grid; grid-template-columns: repeat(4, 1fr); gap: 8px; margin-bottom: 6px; }
.ach-badge {
  aspect-ratio: 1; border-radius: 14px; display: flex; flex-direction: column;
  align-items: center; justify-content: center; gap: 3px; text-align: center;
  background: var(--card); border: 1px solid var(--stroke); padding: 4px;
}
.ach-badge .ae { font-size: 22px; filter: grayscale(1) opacity(0.35); }
.ach-badge .an { font-size: 9px; color: var(--hint); font-weight: 700; line-height: 1.3; }
.ach-badge.unlocked { background: linear-gradient(160deg, rgba(232,205,107,0.16), var(--card)); border-color: rgba(232,205,107,0.4); }
.ach-badge.unlocked .ae { filter: none; }
.ach-badge.unlocked .an { color: var(--gold-2); }

/* ---- Edit profile ---- */
.ep-input {
  width: 100%; border-radius: 12px; border: 1px solid var(--stroke);
  background: rgba(255,255,255,0.04); color: var(--text); padding: 11px 14px;
  font-size: 14px; font-family: inherit; margin-top: 2px;
}
.ep-input:focus { outline: none; border-color: var(--gold); }
.pill-row.scroll-x { flex-wrap: nowrap; overflow-x: auto; padding-bottom: 4px; touch-action: pan-x; }
.pill-row.scroll-x .pill { flex-shrink: 0; }
/* Country pickers: only the first ~4 rows show, the rest scrolls vertically
   (never horizontally — that's already locked down globally, this just
   caps the height so a 194-country list doesn't push the whole page down). */
.pill-row.country-scroll { max-height: 190px; overflow-y: auto; overflow-x: hidden; align-content: flex-start; touch-action: pan-y; }

/* ============ History ============ */
.hist-list { display: flex; flex-direction: column; gap: 8px; }
.hist-row {
  display: flex; align-items: center; gap: 10px; background: var(--card);
  border: 1px solid var(--stroke); border-radius: 14px; padding: 11px 12px;
}
.hist-ico { width: 34px; height: 34px; border-radius: 11px; display: flex; align-items: center; justify-content: center; font-size: 15px; flex-shrink: 0; }
.hist-ico.w { background: rgba(46,196,182,0.13); }
.hist-ico.l { background: rgba(239,90,106,0.12); }
.hist-body { flex: 1; min-width: 0; }
.hist-op { font-size: 13.5px; font-weight: 800; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.hist-sub { font-size: 11px; color: var(--hint); margin-top: 2px; }
.hist-res { font-size: 12px; font-weight: 800; flex-shrink: 0; }
.hist-res.w { color: var(--ok); }
.hist-res.l { color: var(--danger); }

/* ============ Game screen (kept classes, restyled) ============ */
.players { display: flex; justify-content: space-between; gap: 8px; margin-bottom: 10px; }
.pcard { flex: 1; background: var(--card); border: 2px solid var(--stroke); border-radius: 14px; padding: 10px; text-align: center; transition: border-color .25s, box-shadow .25s; }
.pcard.turn { border-color: var(--gold); box-shadow: 0 0 14px rgba(201,162,39,0.3); }
.pcard .nm { font-size: 13px; font-weight: 700; }
.pcard .pip { font-size: 11px; color: var(--hint); }
.pcard .ck { display: inline-block; width: 12px; height: 12px; border-radius: 50%; margin-bottom: 4px; border: 2px solid #000; }
.pcard .gifts { font-size: 11px; color: var(--gold-2); font-weight: 800; margin-top: 2px; }
.pcard .pav { display: block; font-size: 20px; margin-bottom: 2px; }
#board { width: 100%; height: auto; display: block; border-radius: 14px; touch-action: manipulation; box-shadow: 0 10px 30px rgba(0,0,0,0.5); }
/* Transparent WebGL layer for real glTF checkers, pixel-aligned exactly over
   #board; clicks pass through untouched so the existing 2D hit-testing on
   #board keeps working unmodified. */
#board3d { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; border-radius: 14px; }
/* The action bar under the board.
   Every button used to be `flex: 1 1 auto` with different min/max widths, so
   the row filled itself greedily: on a 360px phone it wrapped into THREE
   ragged rows 149px tall, with widths ranging 84px to 190px and no two rows
   alike. Nothing overflowed, but it read as a pile of loose buttons.
   Now the bar has a fixed shape instead. The turn's primary actions each take
   a full row of their own, and the secondary actions share one row in equal
   columns -- same flex-basis and same grow, so they are always exactly the
   same width as each other however many of them are currently visible. */
.controls {
  display: flex; flex-wrap: wrap; gap: 8px; margin-top: 12px;
  align-items: center; justify-content: center;
  padding: 8px; border-radius: 16px;
  background: rgba(255, 255, 255, 0.035);
  border: 1px solid var(--stroke);
}
.controls button {
  /* A percentage basis, not a pixel one: it pins how many buttons share a row
     instead of letting the count fall out of whatever happens to fit. With a
     92px basis four buttons broke 3 + 1, leaving the odd one stretched across
     a full row on its own. Half-width means always a clean 2x2 (and 1x4 above
     the breakpoint), with every cell the same size as its neighbours. */
  flex: 1 1 calc(50% - 4px); min-width: 0;
  /* The cap is what stops the layout going ragged. With grow alone, an odd
     number of secondary buttons left the last one alone on its row and it
     stretched to the full width -- a lone giant button under two half ones.
     Capped at the same half-width, a leftover button is simply a centred
     half-width button, so every cell in the bar is identical no matter how
     many are on screen (Undo and Gift come and go mid-turn). */
  max-width: calc(50% - 4px);
  display: inline-flex; align-items: center; justify-content: center; gap: 6px;
  white-space: nowrap; padding: 10px; font-size: 13px;
  border-radius: 12px; font-weight: 700;
  overflow: hidden; text-overflow: ellipsis;
}
.controls .cb-ico { font-size: 14px; line-height: 1; flex: 0 0 auto; }
/* Roll is the turn's main action — it gets its own full-width row so it is
   never a same-size peer of "Quit". */
.controls #btn-roll { flex: 1 0 100%; max-width: none; font-size: 15px; padding: 13px 12px; }
/* Quit is destructive and rarely wanted mid-game: quietest of the set. */
.controls #btn-quit { font-weight: 600; opacity: 0.7; }
.controls #btn-quit:not(:disabled):active { opacity: 1; }
/* Bear-off is the rarest and most consequential move in the game, and it is
   only on screen while a checker is selected that can actually come off.
   Full width directly under Roll: impossible to miss, impossible to clip. */
.controls .off-btn {
  flex: 1 0 100%; max-width: none; font-size: 15px; padding: 13px 12px;
  background: linear-gradient(135deg, #2ecc71, #1e9e56);
  color: #05230f; font-weight: 800; border: none;
  box-shadow: 0 4px 14px rgba(46, 204, 113, 0.35);
}
/* Only appears once there's actually a move to undo this roll (see
   room.can_undo) -- a small pop-in instead of just materializing makes it
   read as "a new option just became available," not a layout jump. */
@keyframes undoPopIn { from { opacity: 0; transform: scale(0.85); } to { opacity: 1; transform: scale(1); } }
.undo-btn { color: #ffb648; border-color: rgba(255, 182, 72, 0.45); animation: undoPopIn 0.22s ease-out; }
.undo-btn:not(:disabled):active { background: rgba(255, 182, 72, 0.12); }
.msg { text-align: center; font-size: 13px; color: var(--hint); margin-top: 10px; min-height: 18px; }
.spectator-info { text-align: center; font-size: 12px; color: var(--hint); margin-bottom: 8px; }
.spectator-confirm-box { text-align: center; background: rgba(255,255,255,0.06); border: 1px solid var(--gold-2); border-radius: 12px; padding: 10px 12px; margin-bottom: 8px; }
.spectator-confirm-box p { margin: 0 0 8px; font-size: 13px; }
.spectator-confirm-box .row-btns { display: flex; gap: 8px; justify-content: center; }

/* ---- Timer ---- */
.timer { height: 6px; background: rgba(255,255,255,0.08); border-radius: 4px; overflow: hidden; margin-bottom: 10px; }
#timer-bar { height: 100%; width: 100%; background: linear-gradient(90deg, var(--ok), #58e0d2); transition: width 1s linear, background .3s; border-radius: 4px; }
#timer-bar.warn { background: var(--danger); }
/* A read-only status line that lives just above the action bar, not inside
   it. As a flex item among the buttons it broke the row wherever its text
   happened to end, so the button grouping changed from turn to turn. */
.moves-left {
  display: block; text-align: center;
  font-size: 12px; color: var(--hint); white-space: nowrap;
  margin-top: 10px;
}
.moves-left:empty { display: none; }

/* ---- Board wrapper + 3D dice (unchanged mechanics) ---- */
.board-wrap { position: relative; }
.dice3d { position: absolute; inset: 0; display: flex; align-items: center; justify-content: center; gap: 24px; pointer-events: none; perspective: 600px; }
.dice3d.hidden { display: none; }
/* A Board-Designer board with independent per-die anchors positions each die
   in its own absolutely-placed holder instead of the shared flex-centered
   pair above. */
.dice3d.dice3d-split { display: block; }
.die3d-holder { position: absolute; perspective: 600px; }
.die3d { width: 52px; height: 52px; position: relative; transform-style: preserve-3d; transition: transform .1s; }
.die3d.rolling { animation: tumble .12s linear infinite; }
/* A die whose value has already been played this turn -- faded + slightly
   shrunk so it visually recedes and the still-playable die reads clearly
   as the "live" one. */
.die3d.used { opacity: 0.35; filter: grayscale(0.6); transform: scale(0.88); transition: opacity .25s, filter .25s, transform .25s; }
@keyframes tumble { 0%{transform:rotateX(0)rotateY(0)} 100%{transform:rotateX(360deg)rotateY(360deg)} }
.die3d .face {
  position: absolute; width: 52px; height: 52px; border-radius: 14px;
  display: grid; grid-template-columns: repeat(3,1fr); grid-template-rows: repeat(3,1fr);
  padding: 7px; box-sizing: border-box;
  box-shadow: inset 0 0 8px rgba(0,0,0,0.25), inset 0 2px 3px rgba(255,255,255,0.35);
}
.die3d .face.sharp { border-radius: 5px; }
.die3d .face > div { display: flex; align-items: center; justify-content: center; }
.die3d .pip {
  display: block; width: 10px; height: 10px; border-radius: 50%;
  box-shadow: inset 0 1.5px 2.5px rgba(0,0,0,0.55), 0 0.5px 0 rgba(255,255,255,0.4);
}
.die3d .pip.diamond { border-radius: 2px; transform: rotate(45deg); }
.die3d .f1 { transform: translateZ(26px); }
.die3d .f6 { transform: rotateY(180deg) translateZ(26px); }
.die3d .f3 { transform: rotateY(90deg) translateZ(26px); }
.die3d .f4 { transform: rotateY(-90deg) translateZ(26px); }
.die3d .f2 { transform: rotateX(90deg) translateZ(26px); }
.die3d .f5 { transform: rotateX(-90deg) translateZ(26px); }

/* ============ Leaderboard ============ */
.leaderboard-list { display: flex; flex-direction: column; gap: 8px; margin-bottom: 14px; }
.lb-row {
  display: flex; align-items: center; gap: 10px; background: var(--card);
  border-radius: 14px; padding: 10px 12px; border: 1px solid var(--stroke);
}
.lb-row.me { border-color: rgba(232,205,107,0.5); background: rgba(232,205,107,0.06); }
.lb-rank { width: 26px; text-align: center; font-weight: 800; font-size: 14px; color: var(--hint); flex-shrink: 0; }
.lb-rank.top1 { color: #f0c04a; }
.lb-rank.top2 { color: #cfd4dc; }
.lb-rank.top3 { color: #c98a4a; }
.lb-av { font-size: 22px; flex-shrink: 0; }
.lb-body { flex: 1; min-width: 0; }
.lb-name { font-size: 14px; font-weight: 800; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.lb-sub { font-size: 11px; color: var(--hint); margin-top: 2px; display: flex; flex-wrap: wrap; gap: 8px; }
.lb-rating { font-size: 15px; font-weight: 900; color: var(--gold-2); flex-shrink: 0; text-align: center; }
.lb-empty { text-align: center; color: var(--hint); padding: 24px 0; font-size: 13px; }

/* ============ Gifts ============ */
.gift-bar { display: flex; flex-direction: column; gap: 8px; padding: 4px 2px; margin-top: 10px; }
.gift-pill-row { display: flex; gap: 8px; overflow-x: auto; touch-action: pan-x; }
.gift-target-row { display: flex; gap: 8px; overflow-x: auto; touch-action: pan-x; }
.gift-target-row .gift-target { flex-shrink: 0; font-size: 12px; padding: 6px 12px; }
.gift-pill {
  flex-shrink: 0; background: var(--card-solid); border: 1px solid var(--stroke);
  border-radius: 14px; padding: 8px 12px; text-align: center; font-size: 21px;
  display: flex; flex-direction: column; align-items: center; gap: 2px;
}
.gift-pill:disabled { opacity: 0.4; }
.gift-pill .price { font-size: 10px; color: var(--gold-2); font-weight: 700; }
.gift-fx { position: absolute; inset: 0; pointer-events: none; overflow: visible; }
.gift-float { position: absolute; left: 50%; bottom: 20%; font-size: 40px; animation: giftRise 1.8s ease-out forwards; text-shadow: 0 2px 8px rgba(0,0,0,0.4); }
@keyframes giftRise {
  0% { transform: translate(-50%, 0) scale(0.5); opacity: 0; }
  15% { opacity: 1; transform: translate(-50%, -10px) scale(1.2); }
  100% { transform: translate(-50%, -170px) scale(1); opacity: 0; }
}

/* ============ Chat ============ */
.chat-box { margin-top: 14px; background: var(--card); border: 1px solid var(--stroke); border-radius: 16px; padding: 10px; display: flex; flex-direction: column; gap: 8px; }
.chat-messages { max-height: 150px; overflow-y: auto; display: flex; flex-direction: column; gap: 6px; }
.chat-msg { font-size: 13px; background: rgba(255,255,255,0.05); border-radius: 12px; padding: 6px 11px; max-width: 85%; align-self: flex-start; word-break: break-word; }
.chat-msg .who { font-size: 11px; color: var(--hint); margin-bottom: 2px; font-weight: 700; }
.chat-msg.mine { align-self: flex-end; background: linear-gradient(135deg, var(--gold-2), var(--gold)); color: var(--accent-text); }
.chat-msg.mine .who { color: rgba(26,20,5,0.65); }
.chat-empty { text-align: center; font-size: 12px; color: var(--hint); padding: 8px 0; }
.chat-input-row { display: flex; gap: 8px; align-items: center; }
/* Fixed square so it can't be squeezed by the input's flex-grow. */
.chat-input-row .chat-emoji-btn {
  flex: 0 0 auto; width: 40px; height: 40px; padding: 0;
  border-radius: 999px; font-size: 19px; line-height: 1;
}
/* Capped height with its own scroll: the picker sits above the input inside
   the chat card, and an uncapped grid would push the input off-screen on a
   short phone exactly when the keyboard is up. */
.chat-emoji-panel {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(38px, 1fr));
  gap: 4px; max-height: 132px; overflow-y: auto;
  padding: 6px; border-radius: 12px;
  background: rgba(255, 255, 255, 0.04); border: 1px solid var(--stroke);
}
.chat-emoji-panel.hidden { display: none; }
.emoji-cell {
  background: none; border: 0; padding: 0; cursor: pointer;
  aspect-ratio: 1; font-size: 20px; line-height: 1; border-radius: 8px;
}
.emoji-cell:active { background: rgba(255, 255, 255, 0.12); }
.chat-input-row input {
  flex: 1; border-radius: 999px; border: 1px solid var(--stroke);
  background: rgba(255,255,255,0.04); color: var(--text); padding: 9px 14px; font-size: 13px; font-family: inherit;
}
.chat-input-row input:focus { outline: none; border-color: var(--gold); }
.chat-input-row button { border-radius: 999px; padding: 9px 18px; }

/* ============ Admin panel ============ */
.admin-tabs { display: flex; flex-wrap: wrap; gap: 6px; margin-bottom: 14px; }
.admin-tabs .tab { flex: 0 0 auto; }
.admin-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 8px; margin-bottom: 12px; }
.a-tile { background: var(--card); border: 1px solid var(--stroke); border-radius: 13px; padding: 11px 6px; text-align: center; }
.a-tile .v { font-size: 16px; font-weight: 900; color: var(--gold-2); }
.a-tile .k { font-size: 10px; color: var(--hint); margin-top: 2px; font-weight: 700; }
.bar-row { display: flex; align-items: center; gap: 8px; margin: 6px 0; font-size: 12px; }
.bar-row .bl { width: 64px; color: var(--hint); flex-shrink: 0; }
.bar-row .bar { flex: 1; height: 10px; background: rgba(255,255,255,0.06); border-radius: 6px; overflow: hidden; }
.bar-row .bar > i { display: block; height: 100%; background: linear-gradient(90deg, var(--gold-2), var(--gold)); border-radius: 6px; }
.bar-row .bv { width: 30px; text-align: left; font-weight: 800; }
.growth-row { display: flex; align-items: flex-end; gap: 5px; height: 74px; margin: 10px 2px 2px; }
.g-col { flex: 1; display: flex; flex-direction: column; align-items: center; gap: 4px; }
.g-col .g-bar { width: 100%; background: linear-gradient(180deg, var(--gold-2), var(--gold)); border-radius: 5px 5px 2px 2px; min-height: 3px; }
.g-col .g-lbl { font-size: 8.5px; color: var(--hint); }
.admin-search { display: flex; gap: 8px; margin-bottom: 10px; }
.admin-search input {
  flex: 1; border-radius: 12px; border: 1px solid var(--stroke);
  background: rgba(255,255,255,0.04); color: var(--text); padding: 10px 13px; font-size: 13px; font-family: inherit;
}
.admin-search input:focus { outline: none; border-color: var(--gold); }
.au-row {
  display: flex; align-items: center; gap: 10px; background: var(--card);
  border: 1px solid var(--stroke); border-radius: 13px; padding: 10px 12px; margin-bottom: 8px;
  width: 100%; text-align: right;
}
.au-row.banned { border-color: rgba(239,90,106,0.4); }
.au-name { font-size: 13.5px; font-weight: 800; flex: 1; min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.au-meta { font-size: 11px; color: var(--hint); flex-shrink: 0; }
.action-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; margin-top: 12px; }
.action-grid button { font-size: 12.5px; padding: 11px 6px; }
.admin-user-head { text-align: center; margin-bottom: 8px; }
.admin-user-head .aun { font-size: 18px; font-weight: 900; }
.admin-user-head .aui { font-size: 12px; color: var(--hint); direction: ltr; }
textarea.broadcast {
  width: 100%; min-height: 110px; resize: vertical; border-radius: 14px;
  border: 1px solid var(--stroke); background: rgba(255,255,255,0.04);
  color: var(--text); padding: 12px; font-size: 13.5px; font-family: inherit;
}
textarea.broadcast:focus { outline: none; border-color: var(--gold); }
.switch-row { display: flex; align-items: center; justify-content: space-between; background: var(--card); border: 1px solid var(--stroke); border-radius: 13px; padding: 12px 14px; margin-top: 10px; }
.switch { position: relative; width: 46px; height: 26px; border-radius: 999px; background: rgba(255,255,255,0.12); transition: background .2s; padding: 0; }
.switch::after { content: ""; position: absolute; top: 3px; right: 3px; width: 20px; height: 20px; border-radius: 50%; background: #fff; transition: transform .2s; }
.switch.on { background: var(--gold); }
.switch.on::after { transform: translateX(-20px); }

/* ---- Admin: grant / DM panels, logs, room list ---- */
.admin-panel-block { background: var(--card); border: 1px solid var(--stroke); border-radius: 14px; padding: 12px; margin-top: 10px; }
.admin-panel-block .apb-title { font-size: 12.5px; font-weight: 800; color: var(--gold-2); margin-bottom: 8px; }
.grant-row { display: flex; gap: 6px; margin-bottom: 8px; }
.grant-row select { flex: 1; }
select.a-select {
  border-radius: 10px; border: 1px solid var(--stroke); background: var(--card-solid);
  color: var(--text); padding: 9px 8px; font-size: 12.5px; font-family: inherit;
}
.music-lang-select {
  border-radius: 10px; border: 1px solid var(--stroke); background: var(--card-solid);
  color: var(--text); padding: 6px 8px; font-size: 11.5px; font-family: inherit; margin-top: 4px;
}
#music-upload-lang { width: 100%; padding: 9px 8px; margin-bottom: 10px; font-size: 13px; }
.log-row {
  background: var(--card); border: 1px solid var(--stroke); border-radius: 12px;
  padding: 9px 12px; margin-bottom: 6px; font-size: 12px;
}
.log-row .lr-top { display: flex; justify-content: space-between; color: var(--gold-2); font-weight: 700; }
.log-row .lr-detail { color: var(--hint); margin-top: 2px; word-break: break-word; }
.room-close-btn { background: var(--danger); color: #fff; padding: 8px 12px; font-size: 12px; flex-shrink: 0; }

/* ---- Admin: Board Designer ---- */
.dsg-steps { display: flex; gap: 4px; margin-bottom: 14px; }
.dsg-step {
  flex: 1; text-align: center; font-size: 9.5px; font-weight: 700; color: var(--hint);
  padding-bottom: 8px; border-bottom: 3px solid var(--stroke); display: flex; flex-direction: column; align-items: center; gap: 4px;
}
.dsg-step span {
  width: 20px; height: 20px; border-radius: 50%; background: var(--card-solid);
  display: flex; align-items: center; justify-content: center; font-size: 10.5px; font-weight: 800;
}
.dsg-step.active { color: var(--gold-2); border-bottom-color: var(--gold); }
.dsg-step.active span { background: linear-gradient(135deg, var(--gold-2), var(--gold)); color: var(--accent-text); }
.dsg-hint-text { font-size: 12.5px; color: var(--hint); margin-bottom: 10px; line-height: 1.6; }
.live-counts { font-size: 12px; font-weight: 700; color: var(--hint); text-align: center; margin: 6px 0 14px; }
.dsg-hint {
  display: flex; align-items: center; gap: 10px; background: linear-gradient(150deg, rgba(232,205,107,0.14), var(--card) 70%);
  border: 1px solid rgba(232,205,107,0.3); border-radius: 14px; padding: 12px 14px; margin-bottom: 10px; font-size: 13px; font-weight: 700;
}
.dsg-hint .dsg-arrow { font-size: 22px; animation: dsgArrowPulse 1.3s ease infinite; flex-shrink: 0; }
@keyframes dsgArrowPulse { 50% { transform: scale(1.22); } }
.dsg-progress { height: 8px; border-radius: 6px; background: rgba(255,255,255,0.06); overflow: hidden; margin-bottom: 10px; }
.dsg-progress-bar { height: 100%; background: linear-gradient(90deg, var(--gold-2), var(--gold)); border-radius: 6px; transition: width .2s; }
.dsg-photobox {
  position: relative; width: 100%; border-radius: 14px; overflow: hidden;
  border: 1px solid var(--stroke); cursor: crosshair; line-height: 0; user-select: none; touch-action: manipulation;
}
/* Steps that draw shapes by press-drag-release (points, trays) fully own
   touch gestures on the photo — otherwise the browser's native pan/scroll
   can fight the drag on a touchscreen. */
.dsg-photobox-draw { touch-action: none; }
.dsg-photobox img { width: 100%; display: block; pointer-events: none; }
.dsg-photobox-sm { max-width: 260px; margin: 0 auto 14px; cursor: default; }
.dsg-photobox-scroll {
  width: 100%; max-height: 56vh; overflow: auto; border-radius: 14px;
  border: 1px solid var(--stroke); -webkit-overflow-scrolling: touch; touch-action: pan-x pan-y;
}
.dsg-photobox-scroll .dsg-photobox { border-radius: 0; border: none; }
.dsg-zoom-bar {
  display: flex; align-items: center; justify-content: center; gap: 10px;
  margin-bottom: 8px; background: var(--card); border: 1px solid var(--stroke); border-radius: 12px; padding: 8px;
}
.dsg-zoom-btn { padding: 6px 14px; font-size: 15px; font-weight: 900; }
.dsg-zoom-label { font-size: 11.5px; color: var(--hint); font-weight: 700; min-width: 90px; text-align: center; }
.dsg-pin {
  position: absolute; width: 22px; height: 22px; margin: -11px 0 0 -11px; border-radius: 50%;
  background: linear-gradient(135deg, var(--gold-2), var(--gold)); color: var(--accent-text);
  font-size: 10.5px; font-weight: 900; display: flex; align-items: center; justify-content: center;
  box-shadow: 0 0 0 2px rgba(0,0,0,0.5), 0 2px 6px rgba(0,0,0,0.5); cursor: pointer;
}
.dsg-pin.editing {
  background: linear-gradient(135deg, #ff8a5a, #ef5a6a); width: 26px; height: 26px; margin: -13px 0 0 -13px;
  animation: dsgPinPulse 0.9s ease infinite; z-index: 2; touch-action: none;
}
@keyframes dsgPinPulse { 50% { box-shadow: 0 0 0 6px rgba(239,90,106,0.35), 0 2px 6px rgba(0,0,0,0.5); } }
.dsg-hint.editing { border-color: rgba(239,90,106,0.5); background: linear-gradient(150deg, rgba(239,90,106,0.16), var(--card) 70%); }
/* SVG overlay of the drawn point-triangles (viewBox 0..100 stretched over the
   photo). Stroke/fill kept subtle so the photo stays readable underneath. */
.dsg-tri-layer { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; z-index: 1; }
.dsg-tri polygon { fill: rgba(201,162,39,0.28); stroke: rgba(232,205,107,0.95); stroke-width: 0.5; vector-effect: non-scaling-stroke; }
.dsg-tri-edit polygon { fill: rgba(239,90,106,0.3); stroke: #ff8a5a; stroke-width: 0.8; vector-effect: non-scaling-stroke; }
/* The just-tapped base/corner, waiting for the second tap (tip / opposite corner). */
.dsg-basepin {
  position: absolute; width: 16px; height: 16px; margin: -8px 0 0 -8px; border-radius: 50%;
  background: #2ec4b6; box-shadow: 0 0 0 2px #fff, 0 0 10px 3px rgba(46,196,182,0.8);
  z-index: 3; animation: dsgPinPulse 0.9s ease infinite; pointer-events: none;
}
/* Live preview while press-dragging a triangle or rectangle: an SVG that
   tracks the pointer 1:1, so the shape's exact size/angle is visible the
   whole time it's being drawn instead of only after a second tap. */
#dsg-drag-preview { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; z-index: 4; }
.dsg-drag-tri { fill: rgba(46,196,182,0.35); stroke: #2ec4b6; stroke-width: 0.8; vector-effect: non-scaling-stroke; }
.dsg-drag-rect { fill: rgba(46,196,182,0.22); stroke: #2ec4b6; stroke-width: 0.8; vector-effect: non-scaling-stroke; }
/* Drag handle on a selected point's tip, so it can be resized without
   redrawing it from scratch (the base is handled by dragging the pin
   itself — see .dsg-pin.editing). Kept above everything (z-index 5) and
   touch-action:none so a grab doesn't get eaten by page scroll. */
.dsg-handle {
  position: absolute; width: 20px; height: 20px; margin: -10px 0 0 -10px; border-radius: 50%;
  border: 2px solid #fff; z-index: 5; cursor: grab; touch-action: none;
  box-shadow: 0 0 0 2px rgba(0,0,0,0.55), 0 2px 6px rgba(0,0,0,0.5);
}
.dsg-handle:active { cursor: grabbing; }
.dsg-handle-tip { background: #ff8a5a; }
/* Bear-off tray rectangles drawn over the photo. */
.dsg-tray-rect {
  position: absolute; box-sizing: border-box; border: 2px solid; border-radius: 6px; z-index: 2;
  display: flex; align-items: flex-start; justify-content: flex-start;
}
.dsg-tray-rect span { font-size: 10px; font-weight: 800; color: #fff; padding: 1px 5px; border-radius: 0 0 6px 0; line-height: 1.4; }
.dsg-tray-rect.p1 { border-color: #4aa3ff; background: rgba(74,163,255,0.18); }
.dsg-tray-rect.p1 span { background: #2f7fd0; }
.dsg-tray-rect.p2 { border-color: #ff6a6a; background: rgba(255,106,106,0.18); }
.dsg-tray-rect.p2 span { background: #d03a3a; }
.dsg-dicepin {
  position: absolute; font-size: 22px; transform: translate(-50%, -50%);
  filter: drop-shadow(0 2px 4px rgba(0,0,0,0.6)); pointer-events: none;
}
.dsg-dicepin.dsg-dicepin-2 { filter: drop-shadow(0 2px 4px rgba(0,0,0,0.6)) hue-rotate(140deg); }
.dsg-dice-zone-rect {
  position: absolute; box-sizing: border-box; border: 2px solid #ffb800; border-radius: 6px; z-index: 2;
  background: rgba(255,184,0,0.18); display: flex; align-items: flex-start; justify-content: flex-start;
}
.dsg-dice-zone-rect span { font-size: 10px; font-weight: 800; color: #241609; background: #ffb800; padding: 1px 5px; border-radius: 0 0 6px 0; line-height: 1.4; }
.dsg-point-actions { display: flex; gap: 8px; margin-top: 10px; }
.dsg-point-actions button { flex: 1; }
.dsg-nav { display: flex; gap: 8px; margin-top: 14px; }
.dsg-nav button { flex: 1; }
.dsg-warn { color: var(--danger); font-size: 12px; font-weight: 700; margin-bottom: 10px; }
.dsg-list { display: flex; flex-direction: column; gap: 8px; margin-top: 14px; }
.dsg-card {
  display: flex; align-items: center; gap: 10px; background: var(--card);
  border: 1px solid var(--stroke); border-radius: 13px; padding: 8px; padding-right: 10px;
}
.dsg-card-thumb { width: 46px; height: 46px; border-radius: 10px; background-size: cover; background-position: center; flex-shrink: 0; }
.dsg-card-body { flex: 1; min-width: 0; }
.dsg-card-name { font-size: 13px; font-weight: 800; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dsg-card-sub { font-size: 11px; color: var(--hint); margin-top: 2px; }
.dsg-edit-btn, .dsg-del-btn { flex-shrink: 0; padding: 8px 10px; font-size: 12px; }
.dsg-section-bar { display: flex; gap: 6px; margin-bottom: 14px; }
.dsg-section-bar .tab { flex: 1; }
.ckr-thumb-pair { display: flex; overflow: hidden; }
.ckr-thumb-pair span { flex: 1; background-size: cover; background-position: center; }
.dsg-checker-row { display: flex; gap: 12px; margin-bottom: 14px; }
.dsg-checker-row .dsg-upload-slot { flex: 1; }
.dsg-checker-row-preview, .dsg-dice-grid-preview { margin-bottom: 14px; }
.dsg-checker-row-preview .dsg-card-thumb, .dsg-dice-grid-preview .dsg-card-thumb { width: 100%; aspect-ratio: 1; border-radius: 12px; }
.dsg-dice-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px; margin-bottom: 14px; }
.dsg-dice-grid-preview { display: grid; grid-template-columns: repeat(3, 1fr); gap: 8px; }
.dsg-photobox-preview { position: relative; }
.dsg-scale-dot {
  position: absolute; border-radius: 50%; border: 2px solid rgba(0,0,0,0.45);
  box-shadow: 0 2px 5px rgba(0,0,0,0.55); pointer-events: none;
}
.dsg-upload-slot {
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 6px;
  aspect-ratio: 1; border-radius: 14px; border: 2px dashed var(--stroke); background: var(--card);
  cursor: pointer; overflow: hidden; position: relative;
}
.dsg-upload-slot img { width: 100%; height: 100%; object-fit: cover; position: absolute; inset: 0; }
.dsg-upload-plus { font-size: 26px; color: var(--gold-2); font-weight: 300; }
.dsg-upload-label {
  font-size: 10px; color: var(--hint); font-weight: 700; text-align: center; padding: 0 4px;
  position: relative; z-index: 1; background: rgba(12,14,19,0.55); border-radius: 6px; padding: 2px 5px;
}
.dsg-upload-slot img ~ .dsg-upload-label { position: absolute; bottom: 6px; }
/* A full-width variant for a horizontal "add" action (e.g. bulk music
   upload) instead of the default square photo-tile shape. */
.dsg-upload-slot.full-width { aspect-ratio: auto; flex-direction: row; padding: 14px; margin-bottom: 14px; }
.dsg-upload-slot.full-width .dsg-upload-label { position: static; background: none; padding: 0; font-size: 12px; }
.dsg-spin { font-size: 24px; animation: dsgSpin 1.1s linear infinite; }
@keyframes dsgSpin { 100% { transform: rotate(360deg); } }
.dsg-slider-row { display: flex; align-items: center; gap: 10px; background: var(--card); border: 1px solid var(--stroke); border-radius: 13px; padding: 10px 14px; margin-bottom: 10px; font-size: 12.5px; font-weight: 700; }
.dsg-slider-row input[type=range] { flex: 1; accent-color: var(--gold); }
.dsg-field { margin-bottom: 10px; }
.dsg-field label { display: block; font-size: 11.5px; color: var(--hint); font-weight: 700; margin-bottom: 5px; }
.dsg-field input[type=text], .dsg-field input[type=number] {
  width: 100%; border-radius: 12px; border: 1px solid var(--stroke); background: rgba(255,255,255,0.04);
  color: var(--text); padding: 10px 13px; font-size: 13.5px; font-family: inherit;
}
.dsg-field input:focus { outline: none; border-color: var(--gold); }
.dsg-vip-toggle { display: flex; align-items: center; gap: 8px; font-size: 13px; font-weight: 700; margin-bottom: 6px; }

/* ============ Overlay ============ */
.overlay { position: fixed; inset: 0; background: rgba(5,6,10,0.7); backdrop-filter: blur(4px); display: flex; align-items: center; justify-content: center; z-index: 50; }
.modal {
  background: linear-gradient(160deg, #1d2029, var(--card-solid));
  border: 1px solid var(--stroke);
  border-radius: 22px; padding: 28px 24px; text-align: center; max-width: 320px; width: 86%;
  animation: modalIn .25s cubic-bezier(.2,.7,.3,1.1);
  box-shadow: 0 20px 60px rgba(0,0,0,0.6);
}
@keyframes modalIn { from { opacity: 0; transform: scale(0.9) translateY(10px); } }
.modal h2 { margin: 0 0 8px; font-size: 22px; }
.modal p { color: var(--hint); margin: 0 0 20px; }

/* ---- Onboarding + join gate ---- */
.onboard-hero { text-align: center; margin: 18px 0 16px; }
.onboard-hero .onboard-emoji { font-size: 52px; margin-bottom: 8px; }
.onboard-hero h2 { margin: 0 0 8px; }
.joingate-row {
  display: flex; align-items: center; gap: 10px; background: var(--card);
  border: 1px solid var(--stroke); border-radius: 13px; padding: 12px; margin-bottom: 8px;
  color: var(--text); text-decoration: none;
}
.jg-emoji { font-size: 22px; flex-shrink: 0; }
.jg-body { flex: 1; min-width: 0; display: flex; flex-direction: column; }
.jg-body small { color: var(--hint); direction: ltr; text-align: right; }
.jg-tag {
  flex-shrink: 0; font-size: 10px; font-weight: 800; padding: 4px 8px; border-radius: 999px;
  background: rgba(239,90,106,0.15); color: var(--danger); border: 1px solid rgba(239,90,106,0.3);
}
.jg-tag.info { background: rgba(46,196,182,0.12); color: var(--ok); border-color: rgba(46,196,182,0.3); }

/* ---- Image avatars ---- */
.av-img { width: 100%; height: 100%; object-fit: cover; border-radius: inherit; display: block; }
.lb-av .av-img, .pcard .pav .av-img { width: 1.35em; height: 1.35em; border-radius: 50%; display: inline-block; vertical-align: middle; }
.ph-avatar .av-img { border-radius: 50%; }

/* ---- Admin: items manager ---- */
.item-row {
  background: var(--card); border: 1px solid var(--stroke); border-radius: 13px;
  padding: 10px 12px; margin-bottom: 8px;
}
.item-row.off { opacity: 0.55; border-style: dashed; }
.item-off { opacity: 0.55; }
.ir-head { display: flex; align-items: center; justify-content: space-between; gap: 8px; margin-bottom: 8px; }
.ir-name { font-size: 13.5px; font-weight: 800; }
.ir-edit { display: flex; gap: 6px; }
.ir-name-input, .ir-price-input {
  border-radius: 10px; border: 1px solid var(--stroke); background: rgba(255,255,255,0.04);
  color: var(--text); padding: 8px 10px; font-size: 12.5px; font-family: inherit; min-width: 0;
}
.ir-name-input { flex: 2; }
.ir-price-input { flex: 1; width: 80px; }
.ir-save { padding: 8px 12px; flex-shrink: 0; }
/* Chips listing the cosmetics bundled into the pack being built. */
.pack-items { display: flex; flex-wrap: wrap; gap: 6px; margin-bottom: 10px; }
.pack-chip {
  display: inline-flex; align-items: center; gap: 6px;
  background: rgba(201, 162, 39, 0.14); border: 1px solid rgba(201, 162, 39, 0.4);
  color: var(--text); border-radius: 999px; padding: 5px 6px 5px 10px; font-size: 12px;
}
.pack-chip-x {
  background: transparent; border: none; color: var(--hint);
  padding: 0 4px; font-size: 12px; line-height: 1; cursor: pointer;
}
.item-row.is-default { border-color: rgba(255, 182, 72, 0.55); }
.ir-default-row { margin-top: 8px; }
.ir-default { width: 100%; color: #ffb648; border-color: rgba(255, 182, 72, 0.45); }
.ir-default.active { background: rgba(255, 182, 72, 0.14); font-weight: 700; opacity: 1; }
