/* =========================================================
   PLATFORM LAYER — hero, catalogue grid, cards, promos,
   jackpot, winners, footer.

   Design rules, applied everywhere with no exceptions:
     radius   6px cards / 4px controls
     motion   160-280ms, cubic-bezier(.4,0,.2,1)
     surface  var(--bg-surface) card on #080808 ground
     accent   gold, on no more than one element per block
   ========================================================= */

/* El espaciado, los radios, los tiempos y las superficies los define
   tokens.css. Este :root los redeclaraba con los valores antiguos y, al
   cargarse despues, ganaba: los radios se quedaban en 6px y las superficies
   en gris neutro por mucho que se cambiara el sistema de diseno. */

/* ---------------- HERO CARRUSEL ---------------- */
.hero-carousel{
  position:relative;
  border:1px solid var(--border);
  border-radius:var(--r-card);
  overflow:hidden;
  margin-bottom:var(--sp-4);
  background:var(--bg-surface);
}
/* 400px, no 330. Esta altura fija ganaba sobre el min-height del slide,
   asi que la ilustracion se seguia recortando aunque el slide pidiera mas
   sitio. La altura del carrusel y la del slide tienen que ir a la par. */
.hero-track{position:relative; height:400px;}
@media (max-width:760px){ .hero-track{ height:360px; } }
.hero-slide{
  position:absolute; inset:0;
  display:flex; align-items:center;
  padding:0 clamp(24px, 5vw, 60px);
  opacity:0; visibility:hidden;
  transform:scale(1.02);
  transition:opacity var(--t-slow) var(--ease),
             transform 600ms var(--ease),
             visibility 0s linear var(--t-slow);
}
.hero-slide.active{opacity:1; visibility:visible; transform:none; transition-delay:0s;}

/* Each slide gets its own light, not its own colour scheme. */
.hero-scratch{background:radial-gradient(680px 340px at 78% 50%, rgba(245,185,66,.16), transparent 65%), linear-gradient(100deg,var(--bg-elevated),#080808);}
.hero-crash  {background:radial-gradient(680px 340px at 78% 50%, rgba(122,23,23,.20), transparent 65%), linear-gradient(100deg,var(--bg-elevated),#080808);}
/* .hero-vip tenia aqui su degradado; ahora lleva la ilustracion del
   cliente y su bloque esta mas abajo, con el mismo tratamiento que el de
   Crash. Dejarlo aqui solo servia para pintar dos veces. */

.hero-crest{
  position:absolute; right:4%; top:50%; transform:translateY(-50%);
  height:118%; width:auto; opacity:.10; color:var(--gold);
  pointer-events:none;
  -webkit-mask-image:linear-gradient(90deg, transparent, #000 55%);
  mask-image:linear-gradient(90deg, transparent, #000 55%);
}
.hero-body{position:relative; z-index:2; max-width:520px;}
.hero-kicker{
  display:inline-block; margin-bottom:var(--sp-2);
  font-size:.58rem; font-weight:700; letter-spacing:.32em; text-transform:uppercase;
  color:var(--gold);
  border:1px solid rgba(245,185,66,.32); border-radius:2px;
  padding:5px 11px;
}
.hero-title{
  font-family:var(--font-display);
  font-size:clamp(1.9rem, 4vw, 2.9rem); font-weight:400;
  letter-spacing:.08em; text-transform:uppercase;
  color:var(--text-0); line-height:1.05; margin-bottom:var(--sp-2);
}
.hero-copy{
  color:var(--text-1); font-size:.86rem; line-height:1.7;
  max-width:400px; margin-bottom:var(--sp-3);
}
.hero-cta{padding:13px 30px; font-size:.7rem;}
.hero-dots{
  position:absolute; bottom:var(--sp-3); left:clamp(24px,5vw,60px);
  display:flex; gap:7px; z-index:3;
}
.hero-dot{
  width:22px; height:3px; border:none; border-radius:2px;
  background:rgba(255,255,255,.20); cursor:pointer; padding:0;
  transition:background var(--t-fast) var(--ease), width var(--t-fast) var(--ease);
}
.hero-dot.on{background:var(--gold); width:34px;}

/* ---------------- QUICK CHIPS ---------------- */
.qchips{
  display:flex; gap:var(--sp-1); overflow-x:auto;
  padding-bottom:var(--sp-1); margin-bottom:var(--sp-4);
  scrollbar-width:none;
}
.qchips::-webkit-scrollbar{display:none;}
.qchip{
  flex-shrink:0;
  display:inline-flex; align-items:center; gap:7px;
  background:var(--surface); border:1px solid var(--border);
  color:var(--text-2);
  border-radius:var(--r-ctl); padding:9px 14px;
  font-size:.64rem; font-weight:600; letter-spacing:.12em; text-transform:uppercase;
  white-space:nowrap;
  transition:color var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease),
             background var(--t-fast) var(--ease);
}
.qchip svg{width:13px; height:13px; opacity:.7;}
.qchip:hover{color:var(--text-0); border-color:#333;}
.qchip.on{
  color:var(--gold-light); border-color:rgba(245,185,66,.45);
  background:rgba(245,185,66,.07);
}
.qchip.on svg{opacity:1;}

/* ---------------- JACKPOT ---------------- */
.jackpot{
  border:1px solid var(--border-gold); border-radius:var(--r-card);
  background:radial-gradient(600px 200px at 50% 0%, rgba(245,185,66,.10), transparent 70%), #0C0C0C;
  margin-bottom:var(--sp-5);
  overflow:hidden;
}
.jackpot-inner{padding:var(--sp-4) var(--sp-3); text-align:center;}
.jackpot-label{
  display:block; font-size:.56rem; letter-spacing:.30em;
  text-transform:uppercase; color:var(--text-2); margin-bottom:var(--sp-2);
}
.jackpot-amount{
  font-family:var(--font-display);
  font-size:clamp(1.8rem, 5vw, 3rem); font-weight:400; letter-spacing:.04em;
  color:var(--gold-light);
  text-shadow:0 0 32px rgba(245,185,66,.28);
}
.jackpot-amount.tick{animation:jpTick 320ms var(--ease);}
@keyframes jpTick{ 0%{transform:translateY(2px); opacity:.7;} 100%{transform:none; opacity:1;} }
.jackpot-note{
  display:block; margin-top:var(--sp-2);
  font-size:.54rem; letter-spacing:.18em; text-transform:uppercase; color:var(--text-2);
}

/* ---------------- CATALOGUE ROWS ---------------- */
.cat-row{margin-bottom:var(--sp-5);}
.cat-head{
  display:flex; align-items:baseline; justify-content:space-between;
  margin-bottom:var(--sp-3); gap:var(--sp-2);
}
.cat-head h2{
  font-family:var(--font-display);
  font-size:.95rem; font-weight:600;
  letter-spacing:.18em; text-transform:uppercase; color:var(--text-0);
}
.cat-more{
  font-size:.6rem; letter-spacing:.14em; text-transform:uppercase;
  color:var(--text-2); transition:color var(--t-fast) var(--ease);
}
.cat-more:hover{color:var(--gold);}

/* One grid definition drives every surface, so cards can never drift. */
.gc-grid{
  display:grid;
  grid-template-columns:repeat(6, 1fr);
  gap:var(--sp-3);
}

/* ---------------- GAME CARD ---------------- */
.gc{
  background:var(--surface);
  border:1px solid var(--border);
  border-radius:var(--r-card);
  overflow:hidden;
  cursor:pointer;
  transition:transform var(--t-mid) var(--ease),
             border-color var(--t-mid) var(--ease),
             box-shadow var(--t-mid) var(--ease);
}
.gc:hover, .gc:focus-visible{
  transform:translateY(-3px);
  border-color:rgba(245,185,66,.5);
  box-shadow:0 16px 34px -22px rgba(0,0,0,.95);
  outline:none;
}
.gc-art{
  position:relative;
  aspect-ratio:4/3;
  display:flex; align-items:center; justify-content:center;
  overflow:hidden;
  border-bottom:1px solid var(--border-soft);
}

/* ---- Cover art ----
   The art sits under the existing overlays, which keep their own z-index, so
   badges, the favourite button and the hover label all stay on top. When a
   cover is present the line icon is hidden; if the image fails to load, JS
   marks the card .no-img and the icon comes straight back — the card is never
   an empty hole. */
.gc-img{
  position:absolute; inset:0;
  width:100%; height:100%;
  object-fit:cover; display:block;
  background:var(--bg-surface);
  transition:transform var(--t-slow) var(--ease);
}
.gc-art:has(.gc-img) .gc-icon{display:none;}
.gc-art.no-img .gc-img{display:none;}
.gc-art.no-img .gc-icon{display:block;}
.gc:hover .gc-img{transform:scale(1.06);}
/* Readability scrim: the covers are bright, the overlays are light text. */
.gc-art:has(.gc-img)::after{
  content:""; position:absolute; inset:0; pointer-events:none;
  background:linear-gradient(180deg, rgba(0,0,0,.34) 0%, transparent 32%,
                             transparent 58%, rgba(0,0,0,.60) 100%);
}
.gc-icon{
  width:44%; height:44%; color:var(--gold); opacity:.92;
  transition:transform var(--t-mid) var(--ease);
}
.gc:hover .gc-icon{transform:scale(1.06);}

/* Each game reads as a distinct plate without introducing a new hue. */
.art-scratch {background:linear-gradient(155deg,#1E1A12,var(--bg-surface));}
.art-crash   {background:linear-gradient(155deg,#1C1414,var(--bg-surface));}
.art-dice    {background:linear-gradient(155deg,#181818,var(--bg-surface));}
.art-mines   {background:linear-gradient(155deg,#1A1512,var(--bg-surface));}
.art-slots   {background:linear-gradient(155deg,#1E1B12,var(--bg-surface));}
.art-penalty {background:linear-gradient(155deg,#131A16,var(--bg-surface));}
.art-chickenroad{background:linear-gradient(155deg,#1A1710,var(--bg-surface));}
.art-roulette{background:linear-gradient(155deg,#1B1313,var(--bg-surface));}
.art-cards   {background:linear-gradient(155deg,#15171C,var(--bg-surface));}
.art-plinko  {background:linear-gradient(155deg,#191919,var(--bg-surface));}
.art-pump    {background:linear-gradient(155deg,#141B26,var(--bg-surface));}
.art-highlow {background:linear-gradient(155deg,#161616,var(--bg-surface));}

.gc-badges{position:absolute; top:8px; left:8px; display:flex; gap:5px; z-index:2;}
.gc-badge{
  font-size:.5rem; font-weight:700; letter-spacing:.12em; text-transform:uppercase;
  padding:3px 7px; border-radius:2px;
}
/* NUEVO es identidad -> morado. POPULAR dice "aqui hay accion" -> dorado.
   Estaban los dos en dorado, y con todo dorado el color deja de informar. */
.gc-badge.is-new{background:var(--purple); color:#fff;}
.gc-badge.is-hot{background:var(--gold); color:var(--bg-surface);}

.gc-fav{
  position:absolute; top:6px; right:6px; z-index:3;
  width:28px; height:28px; border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  background:rgba(8,8,8,.55); border:1px solid transparent;
  backdrop-filter:blur(4px);
  opacity:0; transform:scale(.9);
  transition:opacity var(--t-fast) var(--ease), transform var(--t-fast) var(--ease),
             border-color var(--t-fast) var(--ease);
}
.gc:hover .gc-fav, .gc-fav.on, .gc:focus-within .gc-fav{opacity:1; transform:none;}
.gc-fav svg{width:14px; height:14px; fill:none; stroke:var(--text-1); stroke-width:1.8;}
.gc-fav:hover{border-color:rgba(245,185,66,.5);}
.gc-fav:hover svg{stroke:var(--gold);}
.gc-fav.on svg{fill:var(--gold); stroke:var(--gold);}
.gc-fav.pop{animation:favPop 320ms var(--ease);}
@keyframes favPop{ 0%{transform:scale(1);} 45%{transform:scale(1.28);} 100%{transform:scale(1);} }

.gc-hover{
  position:absolute; inset:0;
  display:flex; align-items:center; justify-content:center;
  background:rgba(6,6,6,.66);
  opacity:0;
  transition:opacity var(--t-mid) var(--ease);
}
.gc:hover .gc-hover, .gc:focus-visible .gc-hover{opacity:1;}
.gc-play{
  background:linear-gradient(180deg,#D9B845,#9B7619);
  color:var(--bg-surface);
  font-size:.6rem; font-weight:700; letter-spacing:.16em; text-transform:uppercase;
  padding:9px 20px; border-radius:var(--r-ctl);
  transform:translateY(5px);
  transition:transform var(--t-mid) var(--ease);
}
.gc:hover .gc-play{transform:none;}
.gc.is-soon .gc-play{background:none; border:1px solid var(--border); color:var(--text-2);}
.gc.is-soon .gc-icon{opacity:.45;}

.gc-meta{padding:10px 11px 12px;}
.gc-name{
  font-size:.7rem; font-weight:600; letter-spacing:.06em;
  color:var(--text-0); margin-bottom:3px;
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}
.gc-cat{
  font-size:.55rem; letter-spacing:.14em; text-transform:uppercase; color:var(--text-2);
}

/* ---------------- PROMOS ---------------- */
.promo-grid{display:grid; grid-template-columns:repeat(3,1fr); gap:var(--sp-3);}
.promo{
  border:1px solid var(--border); border-radius:var(--r-card);
  padding:var(--sp-4) var(--sp-3);
  position:relative; overflow:hidden;
  transition:border-color var(--t-mid) var(--ease), transform var(--t-mid) var(--ease);
}
.promo:hover{border-color:rgba(245,185,66,.4); transform:translateY(-2px);}
.promo-a{background:radial-gradient(420px 200px at 90% 0%, rgba(245,185,66,.12), transparent 65%), var(--bg-surface);}
.promo-b{background:radial-gradient(420px 200px at 90% 0%, rgba(154,154,154,.10), transparent 65%), var(--bg-surface);}
.promo-c{background:radial-gradient(420px 200px at 90% 0%, rgba(122,23,23,.14), transparent 65%), var(--bg-surface);}
.promo-kicker{
  font-size:.52rem; letter-spacing:.26em; text-transform:uppercase; color:var(--gold);
  display:block; margin-bottom:var(--sp-2);
}
.promo h3{
  font-family:var(--font-display); font-size:1.05rem; font-weight:600;
  letter-spacing:.08em; color:var(--text-0); margin-bottom:6px;
}
.promo p{font-size:.74rem; color:var(--text-1); line-height:1.6; margin-bottom:var(--sp-3);}
.promo .btn-ghost{padding:10px 18px; font-size:.62rem;}

/* ---------------- WINNERS ---------------- */
.winners{display:flex; flex-direction:column;}
.win-row{
  display:flex; align-items:center; gap:9px;
  padding:8px 0; border-bottom:1px solid var(--border-soft);
  animation:winIn 300ms var(--ease) both;
}
.win-row:last-child{border-bottom:none;}
@keyframes winIn{ from{opacity:0; transform:translateY(-6px);} to{opacity:1; transform:none;} }
.win-ico{
  width:26px; height:26px; flex-shrink:0;
  border:1px solid var(--border); border-radius:3px;
  display:flex; align-items:center; justify-content:center; color:var(--gold);
}
.win-ico svg{width:14px; height:14px;}
.win-who{flex:1; min-width:0; display:flex; flex-direction:column; gap:1px;}
.win-who b{font-size:.7rem; color:var(--text-0); font-weight:600;
  overflow:hidden; text-overflow:ellipsis; white-space:nowrap;}
.win-who em{font-size:.56rem; font-style:normal; letter-spacing:.1em;
  text-transform:uppercase; color:var(--text-2);}
.win-amt{font-size:.72rem; font-weight:700; color:var(--emerald-light); white-space:nowrap;}

/* ---------------- CASINO TOOLBAR ---------------- */
.casino-toolbar{
  display:flex; align-items:center; gap:var(--sp-3);
  margin-bottom:var(--sp-3); flex-wrap:wrap;
}
.casino-toolbar .games-search-box{flex:1; min-width:240px;}
.casino-count{
  font-size:.58rem; letter-spacing:.16em; text-transform:uppercase; color:var(--text-2);
  white-space:nowrap;
}

/* ---------------- EMPTY STATE ---------------- */
.empty{
  grid-column:1 / -1;
  padding:var(--sp-6) var(--sp-3); text-align:center;
  border:1px dashed var(--border); border-radius:var(--r-card);
}
.empty-ico{width:34px; height:34px; color:var(--text-2); opacity:.6; margin-bottom:var(--sp-2);}
.empty p{color:var(--text-1); font-size:.82rem; margin-bottom:var(--sp-3);}
.empty p b{color:var(--gold);}

/* ---------------- TOAST ---------------- */
.toast{
  position:fixed; left:50%; bottom:26px; transform:translate(-50%, 14px);
  background:var(--bg-elevated); border:1px solid var(--border-gold);
  color:var(--text-0); font-size:.74rem;
  padding:11px 18px; border-radius:var(--r-ctl);
  z-index:800; opacity:0; pointer-events:none;
  box-shadow:0 18px 40px -22px rgba(0,0,0,.9);
  transition:opacity var(--t-mid) var(--ease), transform var(--t-mid) var(--ease);
}
.toast.show{opacity:1; transform:translate(-50%, 0);}

/* ---------------- TOP-UP ---------------- */
.topup-note{
  font-size:.76rem; color:var(--text-1); line-height:1.65;
  background:var(--bg-surface); border:1px solid var(--border);
  border-radius:var(--r-ctl); padding:13px 15px;
}
.topup-note.muted{color:var(--text-2); font-size:.7rem;}
.topup-note b{color:var(--gold-light);}
.topup-amounts{display:grid; grid-template-columns:repeat(4,1fr); gap:8px;}
.topup-amounts .sr-price:disabled{opacity:.4; cursor:not-allowed;}

/* ---------------- FOOTER ---------------- */
.site-footer{
  border-top:1px solid var(--border-soft);
  background:var(--bg-deep);
  padding:var(--sp-6) clamp(16px,4vw,48px) 0;
  margin-top:var(--sp-6);
}
.foot-grid{
  display:grid; grid-template-columns:2fr 1fr 1fr 1fr;
  gap:var(--sp-5); max-width:1200px; margin:0 auto var(--sp-5);
}
.foot-brand{max-width:320px;}
.foot-crest{width:40px; height:40px; color:var(--gold); margin-bottom:var(--sp-2);}
.foot-word{
  display:block; font-family:var(--font-display);
  font-size:.85rem; letter-spacing:.28em; text-transform:uppercase;
  color:var(--gold-light); margin-bottom:var(--sp-2);
}
.foot-tag{font-size:.68rem; color:var(--text-2); line-height:1.7;}
.foot-col h4{
  font-size:.56rem; letter-spacing:.2em; text-transform:uppercase;
  color:var(--text-1); margin-bottom:var(--sp-2); font-weight:600;
}
.foot-col a{
  display:block; font-size:.72rem; color:var(--text-2);
  padding:4px 0; transition:color var(--t-fast) var(--ease);
}
.foot-col a:hover{color:var(--gold);}
.foot-bar{
  border-top:1px solid var(--border-soft);
  padding:var(--sp-3) 0;
  display:flex; justify-content:space-between; gap:var(--sp-2); flex-wrap:wrap;
  max-width:1200px; margin:0 auto;
  font-size:.6rem; letter-spacing:.12em; text-transform:uppercase; color:var(--text-2);
}

/* ---------------- RESPONSIVE ---------------- */
@media (max-width:1500px){ .gc-grid{grid-template-columns:repeat(5,1fr);} }
@media (max-width:1280px){ .gc-grid{grid-template-columns:repeat(4,1fr);} }
@media (max-width:980px){
  .gc-grid{grid-template-columns:repeat(3,1fr);}
  .promo-grid{grid-template-columns:1fr;}
  /* subido de 290: a esa altura la ilustracion volvia a recortarse */
  .hero-track{height:360px;}
  .foot-grid{grid-template-columns:1fr 1fr; gap:var(--sp-4);}
  .foot-brand{grid-column:1 / -1;}
  /* Touch has no hover: keep the affordances permanently visible. */
  .gc-fav{opacity:1; transform:none;}
  .gc-hover{display:none;}
}
@media (max-width:680px){
  .gc-grid{grid-template-columns:repeat(2,1fr);}
  /* subido de 250: la mascota necesita alto para verse entera */
  .hero-track{height:340px;}
  .hero-copy{font-size:.78rem;}
  .casino-toolbar{flex-direction:column; align-items:stretch;}
  .casino-count{text-align:right;}
  .jackpot-inner{padding:var(--sp-3);}
  .topup-amounts{grid-template-columns:repeat(2,1fr);}
  .site-footer{padding-bottom:80px;}
  .foot-bar{justify-content:center; text-align:center;}
}
@media (prefers-reduced-motion: reduce){
  .hero-slide, .gc, .gc-icon, .promo{transition:none;}
  .jackpot-amount.tick, .gc-fav.pop, .win-row{animation:none;}
}


/* =========================================================
   CRASH — cielo, cohete y explosion

   EL COHETE YA NO SE CLAVA CONTRA LA PARED. El porque esta
   razonado en game-crash.js, junto a la camara. Lo que cambia
   aqui es COMO se coloca: antes con left/bottom, que obliga al
   navegador a recalcular el diseno del escenario sesenta veces
   por segundo; ahora con transform, que es cosa del compositor.

   TRES CAPAS Y NO UNA. .crash-rocket coloca, .crash-hop flota y
   sale despedida al explotar, y el sprite se inclina. Si
   compartieran elemento, cada animacion pisaria el transform de
   la anterior: el mismo fallo que ya costo caro en el pollo.
   ========================================================= */

/* --- cielo -----------------------------------------------------------
   Se desplaza con transform y da la vuelta cada mosaico. El archivo
   esta espejado por dentro, asi que el empalme cae sobre columnas
   identicas y no se ve la costura. El ancho lo calcula el JS porque
   depende de la altura: el mosaico se escala a ella. */
.crash-sky{
  position:absolute;
  top:-7%; height:114%;
  left:0; width:100%;
  background:url('assets/crash/sky.webp') repeat-x left center/auto 100%;
  transform:translate3d(0,0,0);
  will-change:transform;
  opacity:.92;
  z-index:0;
  pointer-events:none;
}
/* Orden de capas explicito: sin el, la rejilla del escenario quedaba
   por debajo del cielo y desaparecia. */
.crash-stage::before{ z-index:1; }
.crash-chart-svg{ z-index:2; }
.crash-sparks{ z-index:3; }
.crash-cashmark{ z-index:5; }
.crash-boom{ z-index:6; }

/* --- cohete ---------------------------------------------------------- */
.crash-rocket{
  position:absolute;
  left:0; top:0;
  width:0; height:0;              /* punto de anclaje, nada mas */
  font-size:0;
  z-index:4;
  pointer-events:none;
  transform:translate3d(0,0,0);
  will-change:transform;
}
.crash-hop{ position:absolute; left:0; top:0; width:0; height:0; }

.crash-plane{
  position:absolute; left:0; top:0;
  width:var(--plane-w, 100px);
  height:auto;
  /* (30%, 76%) es el punto del dibujo por donde sale la estela.
     Poniendo ahi el desplazamiento Y el origen de giro, ese punto
     queda soldado a la punta de la curva pase lo que pase con la
     inclinacion: girar deja de despegar el cohete de su rastro. */
  transform:translate(-30%, -76%) rotate(0deg);
  transform-origin:30% 76%;
  filter:drop-shadow(0 0 10px rgba(168,44,255,.45)) drop-shadow(0 3px 6px rgba(0,0,0,.5));
  will-change:transform;
}

/* Flotado: ya no mueve margin-top (que era diseno) sino transform. */
.crash-rocket.floating .crash-hop{ animation:cohetePulso 2.6s ease-in-out infinite; }
@keyframes cohetePulso{
  0%,100%{ transform:translate3d(0,0,0); }
  50%    { transform:translate3d(0,-4px,0); }
}

/* Al explotar sale despedido y cae girando, en vez de desvanecerse. */
.crash-rocket.exploded .crash-hop{
  animation:coheteCaida 760ms cubic-bezier(.25,.6,.4,1) forwards;
}
@keyframes coheteCaida{
  0%  { transform:translate3d(0,0,0) rotate(0deg) scale(1); opacity:1; }
  16% { transform:translate3d(8px,-12px,0) rotate(-10deg) scale(1.1); opacity:1; }
  100%{ transform:translate3d(70px,96px,0) rotate(78deg) scale(.5); opacity:0; }
}
.crash-rocket.exploded .crash-plane{
  filter:drop-shadow(0 0 16px rgba(255,120,60,.85)) brightness(1.25) saturate(.45);
}

/* Fogonazo del impacto: un solo degradado que crece y se va. */
.crash-boom{
  position:absolute; left:0; top:0; width:0; height:0;
  pointer-events:none; opacity:0;
  transform:translate3d(0,0,0);
}
.crash-boom::after{
  content:"";
  position:absolute; left:-64px; top:-64px; width:128px; height:128px;
  border-radius:50%;
  background:radial-gradient(circle,
    rgba(255,240,200,.95) 0%, rgba(255,150,60,.72) 26%,
    rgba(197,45,255,.34) 54%, transparent 72%);
}
.crash-boom.on{ animation:boomFlash 540ms cubic-bezier(.2,.8,.3,1) forwards; }
@keyframes boomFlash{
  0%  { opacity:0; transform:translate3d(var(--bx,0),var(--by,0),0) scale(.25); }
  16% { opacity:1; transform:translate3d(var(--bx,0),var(--by,0),0) scale(.95); }
  100%{ opacity:0; transform:translate3d(var(--bx,0),var(--by,0),0) scale(2.2); }
}

/* Marca de retiro: se queda clavada en el punto EXACTO de la curva donde
   el jugador salio. Sin ella, el numero del retiro no se relaciona con
   ningun sitio del grafico. */
.crash-cashmark{
  position:absolute; left:0; top:0;
  transform:translate3d(0,0,0);
  opacity:0;
  transition:opacity .2s ease;
  pointer-events:none;
  --cs:#35B57D; --cs-suave:rgba(53,181,125,.18); --cs-borde:rgba(53,181,125,.5);
}
.crash-cashmark.cs-2{
  --cs:#F5C54E; --cs-suave:rgba(245,197,78,.18); --cs-borde:rgba(245,197,78,.55);
}
.crash-cashmark.show{ opacity:1; }
.crash-cashmark b{
  position:absolute; left:12px; top:-9px;
  font-size:0.66rem; font-weight:800;
  padding:2px 7px; border-radius:6px; white-space:nowrap;
  background:var(--cs-suave);
  border:1px solid var(--cs-borde);
  color:var(--cs);
}
/* El numero va DENTRO del punto. Con dos apuestas, distinguirlas solo por
   el color deja fuera a quien no separa verde de dorado. */
.crash-cashmark i{
  position:absolute; left:-7px; top:-7px;
  width:14px; height:14px; border-radius:50%;
  display:flex; align-items:center; justify-content:center;
  font-size:9px; font-weight:900; font-style:normal;
  color:#0A0710;
  background:var(--cs);
  box-shadow:0 0 0 2px rgba(10,7,16,.65), 0 0 12px var(--cs-borde);
}

/* Sacudida del impacto, corta para que se lea como golpe y no como fallo. */
.crash-stage.shake{animation:crashShake 190ms cubic-bezier(.36,.07,.19,.97);}
@keyframes crashShake{
  0%,100%{ transform:translate(0,0); }
  15%{ transform:translate(-5px, 3px); }
  30%{ transform:translate(5px,-3px); }
  45%{ transform:translate(-4px,-2px); }
  60%{ transform:translate(4px, 2px); }
  80%{ transform:translate(-2px, 1px); }
}

/* Chispas del propulsor: solo mientras la subida es rapida de verdad. */
.crash-sparks{position:absolute; inset:0; pointer-events:none;}
.spark{
  position:absolute; width:5px; height:5px; border-radius:50%;
  background:radial-gradient(circle, #FFE9B0 0%, #C52DFF 58%, transparent 74%);
  animation:sparkFade 700ms linear forwards;
  will-change:transform, opacity;
}
@keyframes sparkFade{
  0%  { opacity:.95; transform:translate3d(0,0,0) scale(1); }
  100%{ opacity:0;   transform:translate3d(-42px, 24px, 0) scale(.3); }
}

/* El escenario crece: el cohete con personaje pide mas aire que el
   glifo al que sustituye, y la camara necesita sitio por delante. */
.crash-stage{ height:268px; }
@media (max-width:600px){
  .crash-stage{ height:224px; }
  .crash-plane{ --plane-w:76px; }
}
@media (prefers-reduced-motion: reduce){
  .crash-rocket.floating .crash-hop{animation:none;}
  .crash-stage.shake{animation:none;}
  .spark{display:none;}
}
html.menos-animacion .spark{ display:none; }


/* =========================================================
   CRASH — las dos apuestas

   Dos paneles identicos generados desde una plantilla, cada uno
   con su color: la 1 en verde, la 2 en dorado. Ese color es el
   mismo que lleva su linea de objetivo y su marca de retiro en
   el grafico, que es lo unico que permite mirar el escenario y
   saber cual es cual sin leer nada.
   ========================================================= */
.crash-slots{ display:flex; flex-direction:column; gap:12px; }

.crash-slot{
  --cs:#35B57D; --cs-borde:rgba(53,181,125,.42);
  position:relative;
  padding:12px 12px 14px;
  border:1px solid var(--border);
  border-radius:var(--r-card, 12px);
  background:var(--bg-surface);
}
.crash-slot.cs-2{ --cs:#F5C54E; --cs-borde:rgba(245,197,78,.45); }

/* Mientras vuela, la que sigue viva se resalta y la que ya salio se apaga:
   de un vistazo se ve cual queda en el aire. */
.crash-slot.viva{ border-color:var(--cs-borde); box-shadow:0 0 0 1px var(--cs-borde); }
.crash-slot.fuera{ opacity:.62; }

.cs-head{
  display:flex; align-items:center; justify-content:space-between;
  margin-bottom:10px;
}
.cs-tag{
  display:inline-flex; align-items:center; gap:6px;
  font-size:0.68rem; font-weight:800;
  letter-spacing:0.08em; text-transform:uppercase;
  color:var(--cs);
}
.cs-tag::before{
  content:""; width:8px; height:8px; border-radius:50%;
  background:var(--cs); box-shadow:0 0 8px var(--cs-borde);
}
.cs-close{
  width:26px; height:26px; border-radius:7px;
  display:flex; align-items:center; justify-content:center;
  color:var(--text-dim); font-size:0.8rem;
  border:1px solid transparent;
  transition:color var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease);
}
.cs-close:hover{ color:var(--text-primary); border-color:var(--border); }
/* La zona sensible sube a 44 por pseudo-elemento: el aspa se ve pequena,
   como debe, pero el dedo no tiene que acertarle a 26 pixeles. */
.cs-close::after{
  content:""; position:absolute; inset:50% auto auto 50%;
  width:44px; height:44px; transform:translate(-50%,-50%);
}

.cs-auto{
  display:flex; align-items:center; gap:9px;
  margin:10px 0 12px;
  font-size:0.76rem; color:var(--text-muted);
  cursor:pointer;
}
.cs-auto input[type="checkbox"]{
  width:16px; height:16px; accent-color:var(--cs); flex:none;
}

/* Anadir la segunda: un solo boton, y desaparece cuando ya esta puesta. */
.crash-add{
  width:100%;
  margin-top:12px;
  padding:11px;
  border:1px dashed var(--border);
  border-radius:var(--r-ctl, 10px);
  background:transparent;
  color:var(--text-dim);
  font-size:0.76rem; font-weight:700;
  letter-spacing:0.05em; text-transform:uppercase;
  transition:color var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease);
}
.crash-add:hover{ color:var(--gold); border-color:var(--gold); }
.crash-add[hidden]{ display:none; }
.crash-add:disabled{ opacity:.4; }

.crash-hint{
  margin:10px 2px 0;
  font-size:0.72rem; line-height:1.45;
  color:var(--text-dim);
}
.crash-hint:empty{ display:none; }

/* En el escenario, el boton de cada panel es el que se pulsa para salir,
   asi que hereda el color de su apuesta. */
.crash-slot .crash-action-btn.mode-cashout{
  background:linear-gradient(180deg, var(--cs), color-mix(in srgb, var(--cs) 72%, #000));
  border-color:var(--cs);
  color:#0A0710;
}

@media (hover:none){ .cs-close{ width:34px; height:34px; } }
.cs-close{ position:relative; }

/* =========================================================
   MOBILE PAINT BUDGET
   Three things dominated the cost on phones:
     1. background-attachment:fixed  -> full repaint on every scroll
     2. the full-page grain + vignette overlays
     3. eight stacked backdrop-filter blurs
   1 is removed outright; 2 and 3 are dropped below 760px, where
   they were least visible and most expensive.
   ========================================================= */
@media (max-width:760px){
  body::before{ display:none; }          /* grain */
  body::after { display:none; }          /* vignette */

  /* A solid bar reads the same at this size and costs nothing. */
  .topbar{ backdrop-filter:none; background:var(--bg-deep); }
  .mobile-bottom-nav{ backdrop-filter:none; background:var(--bg-deep); }
  .dice-overlay{ backdrop-filter:none; background:rgba(4,4,4,.94); }
  .sidebar-backdrop{ backdrop-filter:none; }
  .gc-fav{ backdrop-filter:none; }
  .multiplier-tag, .gh-stat{ backdrop-filter:none; }

  /* Shadows are the other silent cost; keep borders, drop the blur. */
  .gc:hover, .gc:focus-visible{ box-shadow:none; }
  .hero-carousel, .jackpot, .promo{ box-shadow:none; }

  /* Long lists render only what is on screen. */
  .lb-body, .mn-history, .sr-history, .ad-table{
    content-visibility:auto;
    contain-intrinsic-size:auto 300px;
  }
}

/* Promote only what actually animates, and only while it animates. */
.hero-slide{ will-change:auto; }
.hero-slide.active{ will-change:opacity, transform; }


/* =========================================================
   BRAND LOCKUP
   These four slots used to hold the line-drawn crest <symbol>; they now carry
   the real BFF Casino Royale logo as an <img>. Two consequences:

   - An <img> needs object-fit, where the <svg> only needed `color`, and the
     drop-shadow that lifted the flat crest off the page would just muddy
     artwork that already carries its own glow.
   - The selectors are element+class on purpose. Sizes for these classes are
     set in three stylesheets across two load orders, and plain .foot-crest
     here would still lose to platform.css's own earlier rule. img.foot-crest
     outranks all of them wherever they sit.

   The lockup is square and busy, so it is given a little more room than the
   thin crest needed before the wordmark beside it stops feeling cramped.
   ========================================================= */
img.logo-mark, img.rl-crest, img.foot-crest, img.auth-crest{
  display:block;
  object-fit:contain;
  filter:none;
}
img.logo-mark{height:42px; width:42px;}
img.auth-crest{width:76px; height:76px; margin:0 auto 14px;}
img.foot-crest{width:52px; height:52px;}

@media (max-width:600px){
  img.logo-mark{height:34px; width:34px;}
}
@media (prefers-reduced-motion: reduce){
  .gc-img{transition:none !important;}
  .gc:hover .gc-img{transform:none;}
}

/* =========================================================
   GAME CABINET
   Every game opens filling the screen, with the loading pass,
   the fullscreen button and the close button in one top bar.
   Injected by js/game-shell.js; the auth dialog is excluded and
   keeps its small card.
   ========================================================= */
.dice-overlay:has(.gs-modal){ padding:0; }

/* Two classes on purpose: Mines and Scratch carry their own .wide / .mines-wide
   max-width, and a single .gs-modal would lose the tie and leave those two
   games in a narrower cabinet than the rest. */
.dice-modal.gs-modal{
  --gs-load-ms:1150ms;
  width:100%;
  max-width:min(1180px, 100%);
  height:100dvh;
  max-height:100dvh;
  border-radius:0;
  border:none;
  display:flex;
  flex-direction:column;
  overflow:hidden;              /* the body scrolls, not the cabinet */
  position:relative;
}
@media (min-width:900px){
  .dice-overlay:has(.gs-modal){ padding:22px; }
  .dice-modal.gs-modal{
    height:min(94dvh, 900px);
    max-height:94dvh;
    border-radius:16px;
    border:1px solid var(--border);
  }
}

/* Top bar stays put while the game scrolls under it. */
.gs-modal .dice-modal-head{
  flex:none;
  position:sticky; top:0; z-index:6;
  padding-top:max(14px, env(safe-area-inset-top));
}
.gs-modal .dice-modal-body{
  flex:1 1 auto;
  overflow-y:auto;
  -webkit-overflow-scrolling:touch;
  padding-bottom:max(24px, env(safe-area-inset-bottom));
}

.gs-fs{
  display:inline-flex; align-items:center; justify-content:center;
  width:34px; height:34px;
  margin-right:2px;
  border:1px solid var(--border);
  border-radius:8px;
  background:rgba(255,255,255,.03);
  color:var(--text-1);
  cursor:pointer;
  transition:color var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease),
             background var(--t-fast) var(--ease);
}
.gs-fs svg{width:17px; height:17px;}
.gs-fs:hover{color:var(--gold-light); border-color:var(--border-gold); background:rgba(245,185,66,.08);}

/* ---- loading pass ----
   Painted over the modal, never replacing it: the games measure their boards
   from the live DOM on open, and hiding the content would zero those reads. */
.gs-load{
  position:absolute; inset:0; z-index:20;
  display:flex; align-items:center; justify-content:center;
  background:
    radial-gradient(680px 420px at 50% 38%, rgba(245,185,66,.10), transparent 68%),
    #090909;
  opacity:0; visibility:hidden;
  transition:opacity .38s var(--ease), visibility 0s linear .38s;
}
.gs-load.running{opacity:1; visibility:visible; transition-delay:0s;}
/* Explicit end state. Leaving this to the base rule made the loader's
   disappearance depend on a transition completing; if that transition is ever
   interrupted the cabinet stays behind a curtain the player cannot click
   through. Stated outright, it cannot get stuck. */
.gs-load.done{opacity:0; visibility:hidden; pointer-events:none;}
.gs-load-inner{
  display:flex; flex-direction:column; align-items:center; gap:var(--sp-3);
  padding:0 32px; text-align:center;
}
.gs-load-logo{
  width:clamp(96px, 22vw, 148px); height:auto;
  object-fit:contain;
  filter:drop-shadow(0 10px 26px rgba(0,0,0,.6));
}
.gs-load-name{
  font-family:var(--font-display);
  font-size:clamp(.92rem, 3.4vw, 1.15rem); font-weight:600;
  letter-spacing:.22em; text-transform:uppercase;
  color:var(--text-0);
}
.gs-load-bar{
  position:relative;
  width:min(280px, 62vw); height:7px;
  border-radius:6px;
  background:#1B1B1B;
  border:1px solid var(--border);
  overflow:hidden;
}
.gs-load-bar i{
  position:absolute; inset:0 auto 0 0;
  width:0;
  border-radius:6px;
  background:linear-gradient(90deg, var(--gold-deep), var(--gold) 45%, #F2E4B0);
  box-shadow:0 0 14px rgba(245,185,66,.5);
}
.gs-load.running .gs-load-bar i{ animation:gsFill var(--gs-load-ms) linear forwards; }
@keyframes gsFill{ from{width:0;} to{width:100%;} }
.gs-load-pct{
  font-size:.68rem; font-weight:700; letter-spacing:.2em;
  color:var(--gold-light);
  font-variant-numeric:tabular-nums;
}

@media (prefers-reduced-motion: reduce){
  .gs-load{transition:none;}
  .gs-load.running .gs-load-bar i{animation:none; width:100%;}
}

/* =========================================================
   CABINET — TWO COLUMNS
   The reference puts the controls in a fixed column on the left and gives the
   whole remaining width to the board. Applied generically: every game modal
   already has its controls in .dice-controls and its board in the siblings
   before it, so one grid on the shared body reshapes all eight at once — no
   per-game markup, and a game added later inherits it.

   Only from 900px up. Below that the column would be narrower than the
   controls need, so the phone keeps the stacked order it was designed for.
   ========================================================= */
@media (min-width:900px){
  .gs-modal .dice-modal-body{
    display:grid;
    grid-template-columns:340px minmax(0, 1fr);
    grid-auto-rows:min-content;
    align-content:start;
    gap:0 var(--sp-4);
    padding-top:var(--sp-3);
  }
  /* Controls: one block down the left, sticky so a long board never scrolls
     the bet away from the player. */
  .gs-modal .dice-controls{
    grid-column:1;
    grid-row:1 / span 99;
    position:sticky; top:0;
    align-self:start;
    background:var(--surface);
    border:1px solid var(--border);
    border-radius:12px;
    padding:var(--sp-3);
  }
  /* Everything else stacks in the right-hand column, in source order. */
  /* :not() adds its argument's specificity, so this selector scored higher
     than the Mines rule below and pinned .mn-layout into the right column —
     which is why that game sat squeezed into half the cabinet with a black
     band beside it. The games that own their layout are excluded here. */
  .gs-modal .dice-modal-body > *:not(.dice-controls):not(.mn-layout):not(.sr-layout):not(.rl-panel):not(.rp-panel){
    grid-column:2;
  }
  /* Roulette is the THIRD game to fall into the catch-all above (Mines and
     Scratch were the first two), because its controls are .rl-panel and only
     .dice-controls claims the left column. The symptom is always the same: a
     340px dead band on the left and the game crushed into the right half.
     Anything added here that owns its own panel needs the same exclusion. */
  .gs-modal .rl-panel,
  .gs-modal .rp-panel{
    grid-column:1;
    grid-row:1 / span 99;
    position:sticky; top:0;
    align-self:start;
  }
  /* The board should use the height it has been given, not overflow it. */
  .gs-modal .cr-stage,
  .gs-modal .pk-stage,
  .gs-modal .crash-stage{
    max-height:none;
  }
}

/* Mines and Scratch build their own inner columns; inside the cabinet those
   would fight the grid, so they span the full right-hand column instead. */
@media (min-width:900px){
  .gs-modal .mn-layout, .gs-modal .sr-layout{grid-column:2; width:100%;}
}

/* The modal body is a flex column, so its children shrink when the content is
   taller than the cabinet. That is what clipped the Plinko board: the canvas
   kept its 312px while the stage around it was squashed to 163px, cutting the
   pegs and pushing the bucket row out of sight. Boards must keep their size
   and let the body scroll instead. */
.gs-modal .dice-modal-body > *{ flex-shrink:0; }

/* =========================================================
   MINES — cabinet layout and tile language
   ========================================================= */
@media (min-width:900px){
  /* Mines and Scratch have no .dice-controls, so the generic 340px column was
     left empty and the whole game sat in the right half with a black band
     beside it. They span both columns and re-declare the split themselves,
     with the panel FIRST so the controls land on the left like every other
     game in the cabinet. */
  .gs-modal .mn-layout, .gs-modal .sr-layout{
    grid-column:1 / -1;
    width:100%;
  }
  .gs-modal .mn-layout{
    grid-template-columns:340px minmax(0, 1fr);
    gap:var(--sp-4);
  }
  .gs-modal .mn-panel-col{
    grid-column:1; grid-row:1;
    background:var(--surface);
    border:1px solid var(--border);
    border-radius:12px;
    padding:var(--sp-3);
  }
  .gs-modal .mn-board-col{grid-column:2; grid-row:1;}
}

/* The tiles lost their surface when the neutrals were re-mixed: --bg-2 landed
   almost on the board's own background, so the grid read as a black hole.
   Given their own tone instead of borrowing one. */
.mines-tile{
  background:linear-gradient(180deg, #2C2438 0%, #221C2D 100%);
  border:1px solid #3A3049;
  box-shadow:inset 0 1px 0 rgba(255,255,255,.05), 0 2px 0 rgba(0,0,0,.45);
}
.mines-tile:hover:not(.revealed):not(:disabled){
  background:linear-gradient(180deg, #392F49, #2A2338);
}

/* =========================================================
   LA GEMA Y LA BOMBA SON ILUSTRACIONES, NO CSS.

   Aqui habia un tema anterior de Minas que dibujaba la gema con
   un clip-path de cinco puntas y fondo verde, y la bomba con el
   caracter estrella. Cuando llego el arte del cliente, ese tema
   NO desaparecio: seguia ganando por especificidad
   --.mines-tile.revealed.safe::before pesa mas que
   .mines-tile.safe::before-- y ademas forzaba el fondo con
   !important.

   Resultado en el movil del cliente: un pentagono verde plano
   encima de la gema morada, y las casillas en turquesa en vez del
   morado del arte. Se veia como dos juegos pegados.

   Ahora estas reglas solo AJUSTAN lo que hace falta y dejan que
   el arte mande. El pseudo-elemento se apaga explicitamente: si
   se borrara la regla sin mas, volveria a heredar el ::before de
   styles.css y el destello se pintaria dos veces.
   ========================================================= */
/* EL COLOR DE LAS CASILLAS VIVE AQUI, Y NO EN styles.css, POR EL ORDEN DE
   LAS HOJAS. Se cargan tokens -> styles -> royale -> platform, asi que lo
   que se escriba en styles.css lo pisan las dos siguientes con la misma
   especificidad. El tema morado estaba en styles.css y royale.css lo
   sobreescribia con su verde y su rojo de la version anterior: las casillas
   salian turquesa con una gema morada dentro, como dos juegos pegados.

   Regla practica para quien venga despues: cualquier cosa de Minas que
   royale.css tambien toque, hay que escribirla en este archivo. */
.mines-tile.safe,
.mines-tile.revealed.safe{
  background:
    radial-gradient(120% 100% at 50% 15%, rgba(168,85,247,.34), transparent 62%),
    linear-gradient(160deg, rgba(108,43,190,.40), rgba(22,14,36,.72));
  border-color:rgba(196,140,255,.55);
}
.mines-tile.mine,
.mines-tile.revealed.mine{
  background:
    radial-gradient(120% 100% at 50% 20%, rgba(255,138,40,.22), transparent 60%),
    linear-gradient(160deg, rgba(72,26,110,.62), rgba(18,12,26,.82));
}
/* Sin destapar: un relieve suave para que el tablero no sea una cuadricula
   plana antes de la primera jugada. */
.mines-tile:not(.revealed){
  background:linear-gradient(160deg, rgba(60,40,96,.55), rgba(18,14,28,.75));
  box-shadow:inset 0 1px 0 rgba(255,255,255,.06);
}
.mines-tile:hover:not(.revealed){
  border-color:rgba(196,140,255,.65);
  box-shadow:0 6px 16px -6px rgba(168,85,247,.55), inset 0 1px 0 rgba(255,255,255,.10);
}
.mines-tile.revealed.safe::before{
  clip-path:none;
  background:linear-gradient(105deg,
    transparent 38%, rgba(255,255,255,.30) 50%, transparent 62%);
  filter:none;
}
.mines-tile.revealed.safe .mines-tile-mult{
  position:absolute; left:0; right:0; bottom:4px;
  font-size:0.56rem; font-weight:800; color:#e9c9ff; letter-spacing:0;
  text-shadow:0 1px 3px rgba(0,0,0,.85);
  z-index:3;
}

/* La mina que revento. El fondo se queda calido para que resalte, pero el
   dibujo es la bomba: el caracter estrella que habia aqui se pintaba ENCIMA
   de ella. Se apaga con content:none, no borrando la regla, porque la
   propiedad se hereda de styles.css. */
.mines-tile.revealed.mine{
  border-color:rgba(245,185,66,.60);
  box-shadow:0 0 18px rgba(255,138,40,.28);
}
.mines-tile.revealed.mine::before{ content:none; }

/* Las minas que solo estaban ahi: apagadas, para que la que acabo la ronda
   siga siendo la culpable evidente. */
.mines-tile.revealed.mine.mn-passive{
  border-color:rgba(255,255,255,.12);
  box-shadow:none;
}

/* Draws the eye to the instruction when auto is started with no pattern. */
.mn-pattern-hint.mn-hint-pulse{
  color:var(--gold-light);
  animation:mnHintPulse .9s var(--ease) 2;
}
@keyframes mnHintPulse{
  0%,100%{opacity:1; transform:none;}
  50%{opacity:.45; transform:translateY(-2px);}
}
@media (prefers-reduced-motion: reduce){ .mn-pattern-hint.mn-hint-pulse{animation:none;} }

/* The board filled the whole 743px column, so a 5x5 grid gave ~140px tiles:
   the row heights pushed the last row out of view and the grid stopped
   reading as a board. Capped to a comfortable size and centred. */
@media (min-width:900px){
  .gs-modal .mn-board-col .mines-board{
    max-width:460px;
    margin-inline:auto;
  }
  .gs-modal .mn-board-col .mn-board-stack{max-width:460px; margin-inline:auto;}
}

/* =========================================================
   PRESUPUESTO DE PINTADO — AHORA EN TODAS LAS PANTALLAS

   El bloque MOBILE PAINT BUDGET de arriba resolvia esto bien,
   pero vivia dentro de @media (max-width:760px): solo protegia
   a los telefonos. El lag reportado era en portatiles, que
   estan por encima de ese umbral y pagaban el coste integro.

   MEDIDO en 1280x720 antes de tocar nada:
     · 3256 nodos DOM, de los que solo 509 se ven
     · recalculo de estilo: 100 ms  (el frame a 60fps son 16,7)
     · 82 animaciones corriendo, la mayoria dentro de modales
       CERRADOS que nadie esta mirando
   ========================================================= */

/* --- 1. Los modales cerrados dejan de existir para el motor ---
   Son 1700 de los 3256 nodos. Estaban en opacity:0 pero con
   display:flex, o sea con layout, pintado y animaciones al
   completo. content-visibility los saca del trabajo de render
   sin sacarlos del flujo, asi que el fundido de apertura sigue
   funcionando y no hay que tocar ni una linea de los 11 juegos.

   Se descarto display:none: rendia casi igual (16,9 vs 17,6 ms)
   pero rompia la transicion y obligaba a reescribir el
   abrir/cerrar de cada juego. */
.dice-overlay:not(.open){
  content-visibility:hidden;
}

/* Pausadas, no eliminadas: con animation:none un juego que se
   cierra a media animacion nunca recibiria su animationend y se
   quedaria colgado esperandolo. */
.dice-overlay:not(.open) *{
  animation-play-state:paused !important;
}

/* --- 2. Las dos capas fijas a pantalla completa ---
   Grano y vinneta se componen sobre todo lo demas en cada frame.
   A opacity 0.035 y 0.025 el ojo no las distingue; el compositor
   si. Se van en todos los tamannos, no solo en movil. */
body::before, body::after{ display:none; }

/* --- 3. Blur solo donde se lee ---
   El desenfoque es lo mas caro que se le puede pedir al
   compositor. En la barra superior aporta profundidad real
   porque el contenido pasa por debajo. Repetido en decenas de
   corazones de favorito y etiquetas pequennas, no lo ve nadie. */
.gc-fav, .multiplier-tag, .gh-stat, .sidebar-backdrop{
  backdrop-filter:none;
}

/* --- 4. La barra lateral deja de repintarse sola ---
   sidebarDrift animaba background-position en bucle infinito
   sobre .sidebar, que esta SIEMPRE visible en escritorio: un
   repintado continuo de una columna de pantalla completa a
   cambio de un degradado que se mueve muy despacio. */
.sidebar{ animation:none; }

/* =========================================================
   PARIDAD ESCRITORIO / MOVIL

   El cliente lo dijo con todas las letras: "en telefono va bien,
   en PC esta muy lento". Eso descarta la potencia bruta y apunta
   a lo que SOLO corre en escritorio. Y habia bastante:

   El bloque MOBILE PAINT BUDGET desactivaba en telefono cosas
   que en PC seguian encendidas. La suposicion de fondo era que
   el escritorio aguanta mas -- cierto para la CPU, falso para el
   compositor, que en un portatil sin GPU dedicada es justo lo
   que va justo.
   ========================================================= */

/* La barra superior se desenfocaba en escritorio y no en movil.
   Un blur sobre una barra fija significa recomponer esa franja
   cada vez que algo se mueve por debajo: en cada scroll, siempre.
   Solida cuesta cero y ademas es como se ve en la referencia. */
.topbar{
  backdrop-filter:none;
  background:var(--bg-surface);
}

/* Las listas largas solo renderizaban lo visible en movil. El
   navegador puede saltarse el layout de lo que esta fuera de
   pantalla en cualquier tamanno; no habia razon para limitarlo. */
/* Por ID, no por clase: estas tres listas no tienen clase propia (son
   div y tbody sueltos dentro de .panel-block), asi que los selectores de
   clase que puse primero no acertaban a nada. Verificado en el DOM. */
.lb-body, .mn-history, .sr-history, .ad-table,
#leaderList, #feedList, #betsBody, .chat-mini{
  content-visibility:auto;
  contain-intrinsic-size:auto 320px;
}

/* Las sombras grandes de los bloques del lobby se quitaban en
   movil y en PC seguian. Se sustituyen por una sombra corta:
   se sigue leyendo la elevacion y no hay un blur enorme que
   recomponer detras de cada bloque. */
.hero-carousel, .jackpot, .promo{
  box-shadow:var(--shadow-card);
}

/* =========================================================
   TARJETAS DE JUEGO — hacia la referencia del cliente

   En la referencia la ILUSTRACION es la tarjeta: ocupa casi
   todo, el nombre va debajo en una franja estrecha y el badge
   flota en la esquina. Aqui eran 152x176 con el arte en 4:3
   apaisado ocupando poco mas de la mitad: leia como una ficha
   de catalogo, no como un cartel de juego.

   El arte pasa a CUADRADO, no a 3:4 vertical, y esa decision
   viene de los archivos: cuatro portadas solo existen en 880x660
   apaisado y no hay original cuadrado. Recortarlas a 3:4 las
   habria destrozado. En 1:1 las apaisadas pierden los laterales
   -- los titulos van centrados, sobreviven -- y las cuadradas
   entran enteras. La tarjeta entera queda vertical igual, que es
   la silueta que da la referencia.
   ========================================================= */

/* Menos columnas y mas grandes. auto-fill con minimo: se adapta
   solo al ancho disponible sin media queries por cada corte. */
/* MINIATURAS MAS GRANDES

   El cliente pedia que se vieran mas y ocuparan mas sitio. El limite no es
   el gusto sino los pixeles: las portadas son de 600x600, asi que en una
   pantalla retina (dpr 2) el ancho maximo sin que se vean blandas es 300px.
   Se sube hasta ahi y no mas.

   auto-fill con minimo alto en vez de un numero fijo de columnas: en cuanto
   no caben, salta a una menos y las tarjetas CRECEN, en vez de encogerse
   todas para mantener el conteo. */
.gc-grid{
  grid-template-columns:repeat(auto-fill, minmax(230px, 1fr));
  gap:var(--sp-3);
}

.gc{
  border-radius:var(--r-card);
  background:var(--bg-surface);
  border:1px solid var(--border);
  overflow:hidden;
  /* Solo transform: cualquier otra propiedad aqui costaria layout
     o pintado en cada hover, que es lo que acabamos de limpiar. */
  transition:transform var(--t-fast) var(--ease);
}
.gc:hover, .gc:focus-visible{
  transform:scale(1.04);
  /* El "brillo" es borde de color, no un blur grande: cuesta
     practicamente cero y se lee igual de bien. */
  box-shadow:var(--glow-purple);
  outline:none;
}

/* El arte manda: cuadrado y sin recortes verticales raros. */
.gc-art{
  aspect-ratio:1 / 1;
  position:relative;
  overflow:hidden;
  background:var(--bg-elevated);
}
.gc-art .gc-img{
  width:100%; height:100%;
  object-fit:cover;
  display:block;
}

/* Franja inferior estrecha, como en la referencia: el nombre
   pesa y el proveedor queda de apoyo. */
.gc-meta{
  padding:var(--sp-2) 10px calc(var(--sp-2) + 2px);
  display:flex; flex-direction:column; gap:2px;
  background:var(--bg-surface);
}
.gc-name{
  font-family:var(--font-display);
  font-weight:400;
  font-size:0.95rem;
  line-height:1.15;
  letter-spacing:0.02em;
  color:var(--text-primary);
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}
.gc-cat{
  font-size:0.66rem;
  letter-spacing:0.08em;
  text-transform:uppercase;
  color:var(--text-muted);
}

/* Badges flotando en la esquina del arte. Morado = identidad,
   dorado = lo que llama a jugar. */
.gc-badges{
  position:absolute; top:8px; left:8px;
  display:flex; gap:4px; z-index:2;
}
/* Los colores de badge se definen arriba, en su bloque original. Repetirlos
   aqui creaba dos fuentes de verdad compitiendo por especificidad. */
.gc-badge{ border:none; }

/* =========================================================
   JACKPOT — el numero es el protagonista

   En la referencia el bote es lo mas grande de la pantalla y
   lo primero que ve el ojo. Aqui estaba en 48px, del tamanno
   de un titulo cualquiera, y se perdia entre el hero y las
   tarjetas.

   Todo lo de abajo es CSS sobre el DOM que ya existe: ni un
   nodo nuevo ni un temporizador mas. El contador ya corre.
   ========================================================= */
.jackpot{
  border-radius:var(--r-panel);
  border:1px solid var(--border);
  /* Luz morada detras del oro: es lo que hace que el dorado
     parezca encendido en vez de amarillo plano. Estatica. */
  background:
    radial-gradient(120% 180% at 50% 0%, rgba(168,85,247,0.18), transparent 60%),
    var(--bg-surface);
  padding:var(--sp-4) var(--sp-3);
}
.jackpot-inner{
  display:flex; flex-direction:column; align-items:center; gap:6px;
  text-align:center;
}
.jackpot-label{
  font-size:0.7rem; letter-spacing:0.22em; text-transform:uppercase;
  color:var(--text-muted);
}
.jackpot-amount{
  font-family:var(--font-display);
  font-weight:400;
  /* clamp para que el numero mande en escritorio sin desbordar
     el telefono: es la cifra mas larga de toda la interfaz. */
  font-size:clamp(2.4rem, 6.5vw, 4.6rem);
  line-height:1;
  letter-spacing:0.01em;

  /* Oro con volumen: el degradado recortado al texto da el
     efecto de metal de la referencia. background-clip no
     cuesta nada -- se resuelve una vez al pintar, no por frame. */
  background:linear-gradient(180deg, #ffe6ad 0%, var(--gold) 45%, var(--gold-deep) 100%);
  -webkit-background-clip:text;
  background-clip:text;
  color:transparent;

  /* tabular-nums es obligatorio aqui: sin el, cada tick del
     contador cambia el ancho de las cifras y el importe entero
     "baila" de lado. Con un numero de 10 digitos se nota mucho. */
  font-variant-numeric:tabular-nums;
}
.jackpot-note{
  font-size:0.68rem; letter-spacing:0.06em;
  color:var(--text-2);
}

/* =========================================================
   HERO — cartel, no cabecera
   ========================================================= */
.hero-carousel{ border-radius:var(--r-panel); }

.hero-kicker{
  display:inline-block;
  font-size:0.6rem; font-weight:700;
  letter-spacing:0.16em; text-transform:uppercase;
  padding:4px 10px; border-radius:999px;
  background:var(--purple); color:#fff;
  margin-bottom:var(--sp-2);
}
.hero-title{
  font-family:var(--font-display);
  font-weight:400;
  font-size:clamp(1.9rem, 4.4vw, 3.4rem);
  line-height:0.98;
  letter-spacing:0.01em;
  color:var(--text-primary);
  margin-bottom:var(--sp-2);
}
.hero-copy{
  color:var(--text-muted);
  font-size:0.92rem;
  max-width:42ch;
  margin-bottom:var(--sp-3);
}
.hero-cta{
  font-family:var(--font-ui);
  font-weight:700;
  letter-spacing:0.06em;
  text-transform:uppercase;
  padding:13px 26px;
  border-radius:var(--r-ctl);
}

/* En un telefono de 375px quedaban 345 utiles, y con minimo 180px solo
   cabia UNA tarjeta por fila: 347x400, un juego por pantalla completa.
   Con 140 entran dos (140*2 + 16 de hueco = 296) y el catalogo vuelve a
   leerse de un vistazo, que es como se ve en la referencia. */
@media (max-width:560px){
  /* Dos columnas, pero lo mas grandes que quepan: en el telefono la
     miniatura es practicamente todo lo que el jugador ve del juego. */
  .gc-grid{ grid-template-columns:repeat(2, 1fr); gap:var(--sp-2); }
  .gc-name{ font-size:0.86rem; }
  .gc-cat{ font-size:0.6rem; }
  .gc-players{ font-size:0.62rem; }
}

/* =========================================================
   BARRA LATERAL — jerarquia de la referencia

   El item activo se marca con TRES cosas a la vez porque una
   sola no basta sobre fondo oscuro: fondo elevado, barra
   dorada a la izquierda e icono dorado. El dorado aqui no
   contradice la regla del sistema: "donde estoy" es la accion
   en curso del jugador.
   ========================================================= */
.side-group-label{
  font-size:0.6rem; font-weight:600;
  letter-spacing:0.18em; text-transform:uppercase;
  color:var(--text-2);
  padding:0 10px;
  margin:var(--sp-3) 0 var(--sp-1);
}

.side-item{
  position:relative;
  display:flex; align-items:center; gap:10px;
  padding:9px 10px;
  border-radius:var(--r-ctl);
  color:var(--text-muted);
  font-size:0.86rem;
  /* Solo color y transform: nada que provoque layout al pasar el raton. */
  transition:color var(--t-fast) var(--ease), background-color var(--t-fast) var(--ease);
}
.side-item:hover{
  background:var(--bg-elevated);
  color:var(--text-primary);
}
.side-item.active{
  background:var(--bg-elevated);
  color:var(--text-primary);
  font-weight:600;
}
/* La barra de la izquierda es un pseudo-elemento, no un borde: un borde
   desplazaria el contenido 3px al activarse y la lista "saltaria". */
.side-item.active::before{
  content:'';
  position:absolute; left:0; top:50%;
  transform:translateY(-50%);
  width:3px; height:64%;
  border-radius:0 3px 3px 0;
  background:var(--gold);
}
.side-item.active .ic{ color:var(--gold); }
.side-item .ic{ display:flex; width:18px; height:18px; flex:none; }
.side-item .ic svg{ width:100%; height:100%; }

/* Badge NUEVO de la lista lateral: mismo lenguaje que las tarjetas. */
.side-item .side-badge, .side-item .badge{
  margin-left:auto;
  font-size:0.55rem; font-weight:700; letter-spacing:0.1em;
  padding:2px 6px; border-radius:999px;
  background:var(--purple); color:#fff;
}

/* =========================================================
   BARRA SUPERIOR
   ========================================================= */
.topbar{
  border-bottom:1px solid var(--border);
}
/* La pildora del saldo: el importe en dorado porque es dinero,
   la etiqueta DEMO en neutro para que no compita. */
.balance-pill, .top-balance{
  display:flex; align-items:center; gap:8px;
  padding:7px 12px;
  border-radius:999px;
  background:var(--bg-elevated);
  border:1px solid var(--border);
}
/* El color del saldo se define en royale.css (.balance-pill .amt), que gana
   por especificidad. Repetirlo aqui creaba dos reglas compitiendo. */
[data-balance-display]{ font-variant-numeric:tabular-nums; }
[data-balance-mode]{
  font-size:0.6rem; letter-spacing:0.1em; text-transform:uppercase;
  color:var(--text-2);
}

.search-box input{
  background:var(--bg-input);
  border:1px solid var(--border);
  border-radius:var(--r-ctl);
  color:var(--text-primary);
}
.search-box input::placeholder{ color:var(--text-2); }
.search-box input:focus{
  outline:none;
  border-color:var(--purple);
}

/* =========================================================
   HERO DE CRASH — ilustracion del cliente

   La imagen viene recortada a proposito: el archivo original
   traia su propio titulo y su propio boton "JUGAR AHORA"
   pintados dentro, y habrian chocado con los que pone el HTML.
   Recortado el panel de texto, queda arte puro y el HTML manda
   sobre el, igual que en las otras diapositivas.

   Es imagen ESTATICA, sin particulas ni degradados en bucle
   detras, que es lo que pedia el encargo.

   WebP: 148 KB frente a los 2.040 KB del PNG original. Un 93%
   menos por el mismo pixel en pantalla.
   ========================================================= */
.hero-crash{
  background-color:var(--bg-deep);

  /* El degradado va PRIMERO: cae encima de la imagen y le da al
     texto un fondo legible sin tapar la mascota. */
  background-image:
    linear-gradient(90deg,
      var(--bg-deep) 0%,
      rgba(7,5,11,0.94) 22%,
      rgba(7,5,11,0.55) 40%,
      rgba(7,5,11,0) 58%),
    image-set(url('assets/hero/crash.webp') type('image/webp'),
              url('assets/hero/crash.jpg')  type('image/jpeg'));

  /* `auto 100%` en vez de `cover`, y esta es LA correccion.

     El hero es muy apaisado (unos 3,2:1) y la ilustracion es 1,72:1.
     Con cover el navegador la agranda hasta cubrir el ancho y recorta
     casi 290px de alto: se perdian la cabeza del personaje por arriba
     y el cohete por abajo, que es justo lo que hay que ver.

     Con `auto 100%` la imagen ajusta a la ALTURA y conserva su
     proporcion, asi que se ve ENTERA. Anclada a la derecha, ocupa su
     mitad y deja la izquierda al texto, igual que el banner original
     del que salio. */
  background-size:cover, auto 100%;
  background-position:center, right center;
  background-repeat:no-repeat, no-repeat;

  /* Mas alto para que la ilustracion tenga sitio: a 332px la mascota
     salia diminuta al respetar su proporcion. */
  min-height:400px;
}

/* En movil no hay sitio para texto Y mascota lado a lado: la
   imagen se va arriba y el texto se lee sobre un velo mas
   opaco, en vez de pelearse por el mismo espacio. */
/* En movil no hay ancho para texto Y mascota lado a lado. La imagen
   se ancla arriba a la derecha ajustando por ANCHO (para que se siga
   viendo entera de lado a lado) y el texto se lee debajo, sobre un
   velo que se opaca hacia abajo. */
@media (max-width:760px){
  .hero-crash{
    min-height:360px;
    background-size:cover, 128% auto;
    background-position:center, right top;
    background-image:
      linear-gradient(180deg,
        rgba(7,5,11,0.25) 0%,
        rgba(7,5,11,0.72) 46%,
        rgba(7,5,11,0.97) 72%),
      image-set(url('assets/hero/crash.webp') type('image/webp'),
                url('assets/hero/crash.jpg')  type('image/jpeg'));
  }
  /* El contenido baja para no pisar a la mascota. */
  .hero-crash .hero-body{ margin-top:auto; padding-bottom:var(--sp-3); }
}

/* =========================================================
   PIEZAS QUE FALTABAN RESPECTO A LA REFERENCIA
   ========================================================= */

/* --- Jackpot: corona, cifra y delta en tres zonas --- */
.jackpot{
  display:grid;
  grid-template-columns:auto 1fr auto;
  align-items:center;
  gap:var(--sp-3);
}
.jk-crown{
  width:56px; height:56px;
  color:var(--gold);
  flex:none;
}
.jk-delta{
  text-align:right;
  font-size:0.64rem;
  letter-spacing:0.08em;
  text-transform:uppercase;
  color:var(--text-2);
  line-height:1.35;
}
.jk-delta b{
  display:block;
  font-size:1.05rem;
  font-weight:700;
  letter-spacing:0.01em;
  text-transform:none;
  color:var(--win);
  font-variant-numeric:tabular-nums;
}
/* En movil los tres bloques no caben en fila: la corona se va y la cifra
   se queda sola, que es lo unico que de verdad hay que leer. */
@media (max-width:760px){
  .jackpot{ grid-template-columns:1fr; text-align:center; }
  .jk-crown{ display:none; }
  .jk-delta{ text-align:center; }
}

/* --- Fila "jugando ahora" --- */
.np-row{ margin:var(--sp-4) 0; }
.np-head{
  display:flex; align-items:center; justify-content:space-between;
  gap:var(--sp-2);
  /* Aire de verdad entre el titulo y las pildoras: con 8px la seccion
     parecia apelotonada contra el jackpot de arriba. */
  margin-bottom:var(--sp-3);
}
.np-row{ margin:var(--sp-5) 0 var(--sp-4); }
.np-title{
  font-family:var(--font-display); font-weight:400;
  font-size:1.05rem; letter-spacing:0.03em;
  color:var(--text-primary);
}
.np-all{
  font-size:0.66rem; letter-spacing:0.1em; text-transform:uppercase;
  color:var(--text-muted);
  background:var(--bg-elevated);
  border:1px solid var(--border);
  border-radius:999px;
  padding:5px 12px;
}
.np-all:hover{ color:var(--text-primary); border-color:var(--purple); }

.np-track{
  display:flex; gap:var(--sp-2);
  overflow-x:auto;
  /* Snap en el movil para que las pildoras no queden a medias al deslizar. */
  scroll-snap-type:x proximity;
  scrollbar-width:none;
  padding-bottom:4px;
  /* La ultima pildora no se queda pegada al borde al llegar al final. */
  scroll-padding-inline:2px;
  position:relative;
}
.np-track::-webkit-scrollbar{ display:none; }

.np-pill{
  flex:none;
  scroll-snap-align:start;
  display:flex; align-items:center; gap:9px;
  padding:9px 14px 9px 10px;
  border-radius:var(--r-card);
  background:var(--bg-surface);
  border:1px solid var(--border);
  text-align:left;
  transition:transform var(--t-fast) var(--ease);
}
.np-pill:hover{ transform:translateY(-2px); border-color:var(--purple); }
.np-ic{ width:26px; height:26px; color:var(--gold); flex:none; }
.np-meta{ display:flex; flex-direction:column; gap:1px; }
.np-name{
  font-size:0.82rem; font-weight:600; color:var(--text-primary);
  white-space:nowrap;
}
.np-count{
  font-size:0.62rem; letter-spacing:0.04em; color:var(--text-2);
  white-space:nowrap; font-variant-numeric:tabular-nums;
}

/* --- Boton de ganadores --- */
.feed-all{
  width:100%; margin-top:var(--sp-2);
  padding:11px 14px;
  border-radius:var(--r-ctl);
  background:var(--purple);
  color:#fff;
  font-size:0.72rem; font-weight:700;
  letter-spacing:0.1em; text-transform:uppercase;
  border:none;
  transition:transform var(--t-fast) var(--ease);
}
.feed-all:hover{ transform:translateY(-1px); background:var(--purple-glow); }

/* --- Cartera al pie de la barra lateral --- */
.side-wallet{
  margin-top:auto;
  display:flex; flex-direction:column; gap:var(--sp-2);
  padding-top:var(--sp-2);
}
.side-topup{
  width:100%;
  padding:12px 14px;
  border-radius:var(--r-ctl);
  background:var(--gold-metal);
  color:var(--bg-surface);
  font-weight:700; font-size:0.8rem;
  letter-spacing:0.08em; text-transform:uppercase;
  border:none;
  transition:transform var(--t-fast) var(--ease);
}
.side-topup:hover{ transform:translateY(-1px); }
.side-balance{
  display:flex; flex-direction:column; gap:2px;
  padding:10px 12px;
  border-radius:var(--r-ctl);
  background:var(--bg-elevated);
  border:1px solid var(--border);
}
.side-balance-label{
  font-size:0.58rem; letter-spacing:0.14em; text-transform:uppercase;
  color:var(--text-2);
}
.side-balance-amt{
  font-size:1rem; font-weight:700;
  color:var(--gold);
  font-variant-numeric:tabular-nums;
}
/* Hermano de .side-wallet, no hijo: cuando data-when-authed lo oculta para
   un visitante sin cuenta, esto ocupa su mismo lugar al fondo de la barra
   lateral en vez de dejar un hueco vacio. */
.side-login-cta{
  margin-top:auto;
  display:block;
  width:100%;
  padding:12px 14px;
  border-radius:var(--r-ctl);
  background:var(--gold-metal);
  color:var(--bg-surface);
  font-weight:700; font-size:0.8rem;
  letter-spacing:0.04em; text-transform:uppercase;
  text-align:center; text-decoration:none;
  transition:transform var(--t-fast) var(--ease);
}
.side-login-cta:hover{ transform:translateY(-1px); }

/* =========================================================
   REDISEÑO PREMIUM — ESTRUCTURA

   La maqueta nueva no tiene barra lateral fija: header, una
   fila de navegacion y contenido a todo el ancho. Comprobado
   antes de tocar nada que es seguro -- la lateral solo tenia
   cuatro destinos (lobby, juegos, admin, recargar) y los
   cuatro ya existen arriba, y los filtros horizontales ya
   estaban con las mismas categorias.

   No se BORRA: pasa a ser cajon en todos los tamannos, con el
   mismo mecanismo que ya usaba en movil. Asi el VIP, el
   historial y los ajustes siguen alcanzables y no se pierde
   nada por el camino.
   ========================================================= */
.app{
  grid-template-columns:1fr;
  grid-template-rows:78px 1fr;
  grid-template-areas:
    "topbar"
    "content";
}

/* Cajon a cualquier ancho, no solo en movil. */
.sidebar{
  position:fixed; top:78px; left:0; bottom:0;
  width:264px; z-index:250;
  transform:translateX(-100%);
  transition:transform var(--t-slow) var(--ease);
  border-right:1px solid var(--border);
}
.sidebar.open{ transform:translateX(0); }
.hamburger{ display:flex; }

/* El contenido respira con margenes elegantes y no se estira sin
   fin en un monitor ancho: 1600 es donde una fila de tarjetas
   deja de leerse como una fila. */
/* El tope va en el CONTENEDOR, no en .main.

   Puesto en .main no servia de nada: .main vive en una celda de rejilla
   junto a la columna derecha, y una celda ya tiene ancho fijo, asi que
   margin-inline:auto no tenia nada que repartir. En un monitor de 1920 el
   contenido arrancaba pegado al borde izquierdo. */
#view-dashboard, #view-games{
  max-width:1720px;
  margin-inline:auto;
  width:100%;
}
.main, .games-view-main{
  width:100%;
  min-width:0;
  padding:var(--sp-4) var(--sp-4) 96px;
}

/* A partir de cierto ancho, mas columnas solo hacen las tarjetas mas
   pequennas y el catalogo mas dificil de leer. Se sube el minimo para que
   crezcan en vez de multiplicarse. */
@media (min-width:1600px){
  /* 270 de minimo: en un monitor ancho salen unas 300px reales, que es
     justo el techo de nitidez de una fuente de 600px a dpr 2. */
  .gc-grid{ grid-template-columns:repeat(auto-fill, minmax(270px, 1fr)); }
}

/* =========================================================
   HEADER
   ========================================================= */
.topbar{
  height:78px;
  display:flex; align-items:center; gap:var(--sp-3);
  padding:0 var(--sp-4);
  background:var(--bg-surface);
  border-bottom:1px solid var(--border);
  position:sticky; top:0; z-index:300;
}

/* Buscador grande pero elegante: ocupa el hueco central sin
   convertirse en el protagonista. */
.search-box{
  display:flex; align-items:center;
  flex:1; max-width:720px;
  height:46px;
}
.search-box input{
  width:100%; height:100%;
  background:var(--bg-input);
  border:1px solid var(--border);
  border-radius:12px;
  padding:0 14px;
  color:var(--text-primary);
  font-size:0.88rem;
}
.search-box input::placeholder{ color:var(--text-dim); }
.search-box input:focus{
  outline:none;
  border-color:var(--purple);
  box-shadow:0 0 0 3px rgba(168,44,255,0.12);
}

.top-actions{
  margin-left:auto;
  display:flex; align-items:center; gap:10px;
}

/* Saldo: borde y texto dorados sobre fondo casi negro. Es un
   boton informativo, no una llamada a la accion, asi que no
   compite con el de deposito. */
.balance-pill{
  height:46px;
  display:flex; align-items:center; gap:8px;
  padding:0 14px;
  border-radius:12px;
  background:var(--bg-input);
  border:1px solid var(--border-gold);
}
/* Boton de refrescar el saldo: el mismo glifo circular en dos tamanos,
   uno junto a la pildora del header y otro junto al saldo de la lateral. */
.balance-refresh, .side-balance-refresh{
  display:flex; align-items:center; justify-content:center;
  background:none; border:none; padding:0;
  color:var(--text-2); cursor:pointer;
  transition:color var(--t-fast) var(--ease), transform var(--t-fast) var(--ease);
}
.balance-refresh{ width:18px; height:18px; margin-left:2px; }
.side-balance-row{ display:flex; align-items:center; gap:6px; }
.side-balance-refresh{ width:16px; height:16px; margin-left:auto; }
.balance-refresh svg, .side-balance-refresh svg{ width:100%; height:100%; }
.balance-refresh:hover, .side-balance-refresh:hover{ color:var(--gold-light, #f5c54e); transform:rotate(45deg); }
.balance-refresh.is-spinning svg, .side-balance-refresh.is-spinning svg{ animation:balanceRefreshSpin .6s linear infinite; }
@keyframes balanceRefreshSpin{ to{ transform:rotate(360deg); } }

/* Deposito: el unico dorado solido del header. */
.btn-deposit{
  height:46px;
  padding:0 20px;
  border-radius:12px;
  background:var(--gold-metal);
  color:#120C05;
  font-weight:800; font-size:0.82rem;
  letter-spacing:0.06em; text-transform:uppercase;
  border:none;
  transition:transform var(--t-fast) var(--ease), box-shadow var(--t-fast) var(--ease);
}
.btn-deposit:hover{
  transform:translateY(-1px);
  box-shadow:0 8px 22px -10px rgba(245,197,78,0.5);
}

.icon-btn{
  width:46px; height:46px;
  border-radius:12px;
  background:var(--bg-input);
  border:1px solid var(--border);
  color:var(--text-muted);
  display:grid; place-items:center;
  transition:border-color var(--t-fast) var(--ease), color var(--t-fast) var(--ease);
}
.icon-btn:hover{ border-color:var(--purple); color:var(--text-primary); }

/* =========================================================
   NAVEGACION HORIZONTAL
   La activa lleva dorado solido; las demas, oscuras con borde
   fino. Un solo elemento dorado a la vez: en cuanto hay dos,
   deja de senalar donde estas.
   ========================================================= */
.qchips, .quick-chips{
  display:flex; gap:9px;
  overflow-x:auto;
  padding:var(--sp-3) 0;
  scrollbar-width:none;
  scroll-snap-type:x proximity;
}
.qchips::-webkit-scrollbar, .quick-chips::-webkit-scrollbar{ display:none; }

.qchip{
  flex:none;
  scroll-snap-align:start;
  display:flex; align-items:center; gap:7px;
  height:42px; padding:0 18px;
  border-radius:10px;
  background:var(--bg-surface);
  border:1px solid var(--border);
  color:var(--text-dim);
  font-size:0.74rem; font-weight:700;
  letter-spacing:0.08em; text-transform:uppercase;
  white-space:nowrap;
  transition:color var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease);
}
.qchip:hover{ color:var(--text-primary); border-color:var(--purple-deep); }
.qchip svg{ width:15px; height:15px; }
.qchip.on, .qchip.active{
  background:var(--gold-metal);
  border-color:var(--gold);
  color:#120C05;
  /* Glow sutil: sombra corta y de poca opacidad, no un halo. */
  box-shadow:0 6px 18px -10px rgba(245,197,78,0.55);
}

/* =========================================================
   HERO PREMIUM
   ========================================================= */
.hero-carousel{
  border-radius:18px;
  border:1px solid var(--border);
  min-height:330px;
  box-shadow:var(--shadow-card);
}
.hero-slide{ padding:0 clamp(28px, 4vw, 56px); }

/* El resplandor morado del hero es un degradado ESTATICO en el
   fondo, no una sombra animada: se pinta una vez y se queda en
   la capa de fondo sin coste por frame. */
/* =========================================================
   HERO SCRATCH — la ilustracion del cliente

   Esta NO se trata como las otras dos, y por una razon: viene
   dibujada como banner, con el tercio izquierdo vacio a
   proposito para que ahi vaya el texto.

   Aqui `cover` SI sirve. El banner es 2,26:1 y la ilustracion
   2,65:1, o sea mas ancha: cover escala por la ALTURA y recorta
   ancho, no alto. Anclada a la derecha se come un 15% por la
   izquierda, que es justo el hueco vacio. No se pierde ni la
   corona de arriba ni los dados de abajo.

   El velo llega mas lejos que en los otros heroes (62% contra
   64%, pero saliendo del 34% opaco) porque el carrete del 7 cae
   sobre el texto: en vez de esconderlo, se deja asomar detras
   del titulo, que es como se ven estos banners de casino.
   ========================================================= */
.hero-scratch{
  background-color:var(--bg-deep);
  background-image:
    linear-gradient(90deg,
      var(--bg-deep) 0%,
      rgba(7,5,11,0.92) 34%,
      rgba(7,5,11,0.72) 46%,
      rgba(7,5,11,0) 62%),
    image-set(url('assets/hero/scratch.webp') type('image/webp'),
              url('assets/hero/scratch.jpg')  type('image/jpeg'));
  background-size:cover, cover;
  background-position:center, right center;
  background-repeat:no-repeat, no-repeat;
  min-height:400px;
}

/* En movil la ilustracion se va arriba y el texto se lee debajo, igual que
   en los otros dos heroes. Al ser tan apaisada se ancla a la derecha para
   no dejar fuera de cuadro el escudo del leon. */
@media (max-width:760px){
  .hero-scratch{
    min-height:360px;
    background-size:cover, 168% auto;
    background-position:center, right top;
    background-image:
      linear-gradient(180deg,
        rgba(7,5,11,0.25) 0%,
        rgba(7,5,11,0.72) 46%,
        rgba(7,5,11,0.97) 72%),
      image-set(url('assets/hero/scratch.webp') type('image/webp'),
                url('assets/hero/scratch.jpg')  type('image/jpeg'));
  }
  .hero-scratch .hero-body{ margin-top:auto; padding-bottom:var(--sp-3); }
}

/* =========================================================
   HERO VIP — la ilustracion del cliente

   Mismo tratamiento que el de Crash, y por la misma razon: el
   hero es muy apaisado (unos 3,2:1) y la ilustracion es 1,78:1.
   Con `cover` el navegador la agranda hasta cubrir el ancho y
   recorta por arriba y por abajo: se perderian la corona y la
   copa, que es justo lo que hay que ver.

   Con `auto 100%` ajusta a la ALTURA y conserva su proporcion,
   asi que entra ENTERA. Anclada a la derecha ocupa un 56% del
   ancho, y el degradado de la izquierda -- que va PRIMERO, o
   sea encima -- se apaga al 58%: el personaje queda entre el
   77% y el 94%, con el texto sin pisarlo.
   ========================================================= */
.hero-vip{
  background-color:var(--bg-deep);
  background-image:
    /* Medido en el navegador: el texto acaba al 49% y el personaje empieza
       al 68%. El velo se apaga al 64%, o sea despues del texto y antes de
       el: el titulo nunca cae sobre dibujo visible y el personaje nunca
       queda tapado. */
    linear-gradient(90deg,
      var(--bg-deep) 0%,
      rgba(7,5,11,0.94) 30%,
      rgba(7,5,11,0.62) 50%,
      rgba(7,5,11,0) 64%),
    image-set(url('assets/hero/vip.webp') type('image/webp'),
              url('assets/hero/vip.jpg')  type('image/jpeg'));
  background-size:cover, auto 100%;
  background-position:center, right center;
  background-repeat:no-repeat, no-repeat;
  min-height:400px;
}

/* En movil no hay ancho para texto Y personaje lado a lado: la
   ilustracion se va arriba y el texto se lee debajo, sobre un velo que
   se opaca hacia abajo. Igual que el hero de Crash. */
@media (max-width:760px){
  .hero-vip{
    min-height:360px;
    background-size:cover, 128% auto;
    background-position:center, right top;
    background-image:
      linear-gradient(180deg,
        rgba(7,5,11,0.25) 0%,
        rgba(7,5,11,0.72) 46%,
        rgba(7,5,11,0.97) 72%),
      image-set(url('assets/hero/vip.webp') type('image/webp'),
                url('assets/hero/vip.jpg')  type('image/jpeg'));
  }
  .hero-vip .hero-body{ margin-top:auto; padding-bottom:var(--sp-3); }
}

.hero-kicker{
  background:transparent;
  border:1px solid var(--purple);
  color:var(--purple-glow);
  letter-spacing:0.24em;
}

/* =========================================================
   JACKPOT PREMIUM
   ========================================================= */
.jackpot{
  border:1px solid var(--border-gold);
  border-radius:16px;
  background:
    radial-gradient(680px 200px at 50% 50%, rgba(245,197,78,0.10), transparent 70%),
    radial-gradient(400px 160px at 50% 0%, rgba(168,44,255,0.10), transparent 65%),
    var(--bg-surface);
  /* Glow dorado MUY sutil hacia fuera: una sombra corta, no un halo. */
  box-shadow:0 0 40px -22px rgba(245,197,78,0.55);
  padding:var(--sp-4) var(--sp-4);
}
.jackpot-label{ letter-spacing:0.34em; color:var(--text-dim); }
.jackpot-amount{
  background:linear-gradient(180deg, var(--gold-light2) 0%, var(--gold) 50%, var(--gold-deep) 100%);
  -webkit-background-clip:text; background-clip:text;
  color:transparent;
}
.jk-crown{ width:64px; height:64px; }
.jk-delta b{ color:var(--win); }

/* =========================================================
   TARJETAS "JUGANDO AHORA" — producto, no div con texto
   ========================================================= */
.np-pill{
  padding:12px 16px 12px 12px;
  border-radius:14px;
  background:linear-gradient(145deg, var(--bg-elevated), var(--bg-deep));
  border:1px solid var(--border);
  position:relative;
  transition:transform var(--t-mid) var(--ease), border-color var(--t-mid) var(--ease),
             box-shadow var(--t-mid) var(--ease);
}
.np-pill:hover{
  transform:translateY(-3px);
  border-color:var(--purple);
  box-shadow:var(--glow-purple);
}
/* El icono en disco: le da peso de producto sin necesitar una
   imagen distinta por juego. */
.np-ic{
  width:44px; height:44px;
  padding:9px;
  border-radius:50%;
  background:rgba(168,44,255,0.10);
  border:1px solid var(--border);
  color:var(--gold);
  box-sizing:border-box;
}
/* OJO: .np-ic esta definida DOS veces en este archivo, y manda esta, la de
   mas abajo. La version ilustrada tiene que ir despues de ella o pierde --
   me paso: se quedaba en los 44px de aqui en vez de en los suyos.

   La ilustracion trae su propia insignia redonda dibujada, asi que se le
   quitan el relleno, el fondo y el borde: si no, quedaba una insignia
   dentro de otra. */
.np-ic-art{
  padding:0;
  background:none;
  border:0;
  object-fit:cover;
  display:block;
}
.np-count{ color:var(--gold); }

/* Badge LIVE DENTRO de la pildora, no asomando por encima.

   Estaba en top:-7px, o sea sobresaliendo. Y la pista tiene
   overflow-x:auto, que en cuanto se declara en un eje hace que el
   navegador recorte TAMBIEN en el otro: el badge quedaba cortado por
   arriba y, al asomar, se pegaba al titulo de la seccion, que en el
   telefono solo tenia 8px de aire. Se veia como si el titulo estuviera
   partido.

   Metido dentro no hay nada que recortar y no invade a nadie. */
.np-pill{ padding-top:16px; }
.np-pill::before{
  content:'LIVE';
  position:absolute; top:6px; right:10px;
  font-size:0.5rem; font-weight:800; letter-spacing:0.12em;
  padding:2px 6px; border-radius:4px;
  background:var(--win); color:#06210F;
  line-height:1.3;
}

/* =========================================================
   ORIGINALES — tarjetas de producto destacado
   ========================================================= */
.gc{
  background:linear-gradient(145deg, var(--bg-elevated), var(--bg-deep));
  box-shadow:var(--shadow-card);
  transition:transform var(--t-mid) var(--ease), box-shadow var(--t-mid) var(--ease),
             border-color var(--t-mid) var(--ease);
}
.gc:hover, .gc:focus-visible{
  transform:translateY(-4px) scale(1.02);
  border-color:var(--purple);
  box-shadow:var(--glow-purple);
}
/* Velo oscuro al pie del arte: separa la ilustracion del texto
   sin necesidad de una franja opaca que corte la imagen. */
.gc-art::after{
  content:'';
  position:absolute; inset:auto 0 0 0; height:42%;
  background:linear-gradient(180deg, transparent, rgba(7,5,11,0.85));
  pointer-events:none;
}
/* Boton de jugar que aparece al pasar el raton, como pide el encargo. */
.gc-play{
  position:absolute; left:50%; bottom:12px;
  transform:translate(-50%, 8px);
  opacity:0;
  padding:9px 20px; border-radius:8px;
  background:var(--gold-metal); color:#120C05;
  font-size:0.7rem; font-weight:800; letter-spacing:0.08em; text-transform:uppercase;
  border:none; z-index:3;
  transition:opacity var(--t-mid) var(--ease), transform var(--t-mid) var(--ease);
}
.gc:hover .gc-play, .gc:focus-within .gc-play{
  opacity:1; transform:translate(-50%, 0);
}
@media (hover:none){
  /* En tactil no hay hover: el boton se queda visible en vez de
     ser inalcanzable. */
  .gc-play{ opacity:1; transform:translate(-50%, 0); }
}

/* Cinturon y tirantes contra el desborde horizontal: el encargo pide que
   NINGUN elemento se salga, y en un catalogo con tantas filas deslizables
   basta un descuido para romperlo. html tambien, no solo body: con body en
   hidden y html visible el documento sigue pudiendo desplazarse. */
html, body{ overflow-x:hidden; max-width:100%; }

/* =========================================================
   JUGADORES POR JUEGO

   El punto verde es lo que convierte una cifra en "hay gente
   ahi ahora mismo". Sin el es un numero mas; con el, es un
   indicador de estado.

   No parpadea: un punto latiendo en cada una de las 11 tarjetas
   son once animaciones infinitas simultaneas en el lobby, que es
   justo lo que quitamos del proyecto. Verde solido basta.
   ========================================================= */
.gc-sub{
  display:flex; align-items:center; justify-content:space-between;
  gap:8px; min-width:0;
}
.gc-cat{
  min-width:0; overflow:hidden; text-overflow:ellipsis; white-space:nowrap;
}
.gc-players{
  display:inline-flex; align-items:center; gap:5px;
  flex:none;
  font-size:0.66rem; font-weight:700;
  color:var(--text-muted);
  font-variant-numeric:tabular-nums;
}
.gc-dot{
  width:6px; height:6px; border-radius:50%;
  background:var(--win);
  /* Un halo minimo, del propio color: da sensacion de "encendido"
     sin costar un blur de verdad. */
  box-shadow:0 0 0 2px rgba(34,197,94,0.18);
  flex:none;
}
/* Cifra vacia (juego proximamente): que no quede el punto suelto. */
.gc-players:has(b:empty){ display:none; }

.np-count b{ color:var(--gold); font-weight:700; }

/* La franja de texto crece con la tarjeta: con miniaturas grandes, un pie
   de 10px se queda raquitico y desequilibra la tarjeta. */
.gc-meta{ padding:11px 12px 13px; }
.gc-name{ font-size:1rem; }

/* La imagen se pide al tamanno que de verdad se va a usar. Sin esto el
   navegador reserva el hueco con las medidas del atributo width/height del
   HTML (440x330, que ya no es la proporcion real) y provoca un salto de
   maquetacion al cargar. */
.gc-img{ aspect-ratio:1 / 1; }

/* =========================================================
   HERO: el boton tiene que responder SIEMPRE

   El cliente reportaba que en el movil pulsaba JUGAR AHORA y no
   pasaba nada. El manejador estaba bien; el problema era de
   capas y de tiempo:

   1. Las diapositivas inactivas tenian pointer-events:auto, o
      sea que seguian capturando toques aunque no se vieran.
   2. La transicion de `visibility` lleva 260ms de RETARDO, asi
      que al cambiar de banner el saliente se queda "visible"
      para el navegador durante ese cuarto de segundo -- invisible
      al ojo pero capturando dedos.
   3. hero-vip es la ultima del DOM y, con z-index igual, queda
      ENCIMA de las otras dos.

   Juntando las tres: con el carrusel girando cada 6,5 s, un toque
   caia con facilidad en esa ventana y lo recogia un banner que no
   era el que el jugador estaba viendo.
   ========================================================= */
.hero-slide{ pointer-events:none; }
.hero-slide.active{ pointer-events:auto; z-index:2; }

/* 44px es el minimo comodo para un pulgar. Estaba en 40, y con el
   parrafo justo encima no perdona un dedo poco preciso. */
.hero-cta{
  min-height:48px;
  padding-inline:26px;
}
@media (max-width:760px){
  .hero-cta{ min-height:50px; width:auto; }
  /* Aire entre el texto y el boton: pegados, un toque alto cae en
     el parrafo y parece que el boton no responde. */
  .hero-copy{ margin-bottom:var(--sp-3); }
}

/* =========================================================
   OBJETIVOS TACTILES

   Auditados 367 botones a 375px: 225 quedaban por debajo de
   44px de alto, el minimo comodo para un pulgar. Los de la
   lista lateral estaban en 36.

   Se sube el AREA de toque sin engordar el diseno: los items
   de lista crecen de verdad (ahi sobra sitio) y los iconos
   pequenos usan un pseudo-elemento que extiende la zona
   sensible sin cambiar nada de lo que se ve.
   ========================================================= */
@media (hover:none){
  .side-item{ min-height:46px; }
  .qchip{ min-height:46px; }
  .np-pill{ min-height:64px; }
  .hero-dot{ position:relative; }
  /* Los puntos del carrusel miden 3px de alto: imposible acertar.
     El pseudo-elemento les da 44px de zona sensible sin verse. */
  .hero-dot::after{
    content:''; position:absolute;
    left:-6px; right:-6px; top:-20px; bottom:-20px;
  }
  .gc-fav{ min-width:44px; min-height:44px; }
  .mobile-bottom-nav a, .mobile-bottom-nav button{ min-height:52px; }
}

/* =========================================================
   SOPORTE Y AJUSTES
   ========================================================= */
.sp-modal, .st-modal{ max-width:460px; }
.sp-body, .st-body{ display:flex; flex-direction:column; gap:var(--sp-2); padding:var(--sp-3); }

.sp-intro{ color:var(--text-muted); font-size:0.86rem; margin-bottom:var(--sp-1); }
.sp-note, .st-note{
  color:var(--text-dim); font-size:0.72rem; line-height:1.5;
  margin-top:var(--sp-2);
}

/* Tarjeta de canal: toda la fila es el enlace, no solo el texto. En el
   telefono acertarle a un enlace de una linea es innecesariamente dificil. */
.sp-card{
  display:flex; align-items:center; gap:var(--sp-3);
  padding:14px 16px;
  min-height:64px;
  border-radius:var(--r-card);
  background:var(--bg-elevated);
  border:1px solid var(--border);
  text-decoration:none;
  transition:transform var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease);
}
.sp-card:hover{ transform:translateY(-2px); }
.sp-wa:hover{ border-color:#25D366; }
.sp-tg:hover{ border-color:#2AABEE; }

.sp-ic{
  width:42px; height:42px; flex:none;
  display:grid; place-items:center;
  border-radius:50%;
}
.sp-ic svg{ width:24px; height:24px; }
/* Cada canal con su color de marca: es como los reconoce el ojo al instante,
   sin tener que leer la etiqueta. */
.sp-wa .sp-ic{ background:rgba(37,211,102,0.14); }
.sp-wa .sp-ic svg{ fill:#25D366; }
.sp-tg .sp-ic{ background:rgba(42,171,238,0.14); }
.sp-tg .sp-ic svg{ fill:#2AABEE; }

.sp-txt{ display:flex; flex-direction:column; gap:2px; min-width:0; }
.sp-txt b{ color:var(--text-primary); font-size:0.95rem; }
.sp-txt small{
  color:var(--text-muted); font-size:0.78rem;
  font-variant-numeric:tabular-nums;
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}
.sp-go{ margin-left:auto; color:var(--text-dim); font-size:1.5rem; line-height:1; flex:none; }

/* ---------------- ajustes ---------------- */
.st-row{
  display:flex; align-items:center; gap:var(--sp-3);
  padding:12px 4px;
  min-height:60px;
}
.st-info{ display:flex; flex-direction:column; gap:3px; min-width:0; }
.st-info b{ color:var(--text-primary); font-size:0.9rem; }
.st-info small{ color:var(--text-dim); font-size:0.74rem; line-height:1.4; }
.st-sep{ height:1px; background:var(--border); margin:var(--sp-1) 0; }

.st-switch{
  margin-left:auto; flex:none;
  width:52px; height:30px;
  border-radius:999px;
  background:var(--bg-input);
  border:1px solid var(--border);
  position:relative;
  transition:background-color var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease);
}
.st-switch .st-knob{
  position:absolute; top:3px; left:3px;
  width:22px; height:22px; border-radius:50%;
  background:var(--text-dim);
  transition:transform var(--t-fast) var(--ease), background-color var(--t-fast) var(--ease);
}
.st-switch.on{ background:rgba(245,197,78,0.18); border-color:var(--gold); }
.st-switch.on .st-knob{ transform:translateX(22px); background:var(--gold); }

.st-danger{
  margin-left:auto; flex:none;
  padding:10px 18px; min-height:44px;
  border-radius:var(--r-ctl);
  background:transparent;
  border:1px solid var(--danger);
  color:var(--danger);
  font-size:0.78rem; font-weight:700; letter-spacing:0.06em; text-transform:uppercase;
  transition:background-color var(--t-fast) var(--ease);
}
.st-danger:hover{ background:rgba(239,68,68,0.12); }

/* La preferencia de "menos animaciones" del panel. Se respeta ademas la del
   sistema operativo, que ya tiene su propio bloque mas abajo. */
html.menos-animacion *,
html.menos-animacion *::before,
html.menos-animacion *::after{
  animation-duration:0.01ms !important;
  animation-iteration-count:1 !important;
  transition-duration:0.01ms !important;
}

/* Pista de "jugando ahora": pista visual de que se desliza.
   La tercera pildora cortada a media palabra parece un fallo de
   maquetacion; con el degradado se lee como "hay mas a la derecha". */
.np-row{ position:relative; }
.np-row::after{
  content:'';
  position:absolute; right:0; bottom:4px;
  width:34px; height:72px;
  pointer-events:none;
  background:linear-gradient(90deg, rgba(7,5,11,0), var(--bg-deep));
}
/* El degradado NO se oculta en escritorio. Lo di por hecho ("ahi caben
   todas") y al medirlo resulta que son 8 pildoras y tampoco caben: se
   deslizan igual, asi que la pista visual hace la misma falta. */

/* =========================================================
   SELECTOR DE DIFICULTAD — comun a todos los juegos

   Antes cada juego pedia su parametro a su manera: Minas con un
   desplegable de 24 entradas, Plinko con dos deslizadores, Dados
   con un deslizador de 97 posiciones. Demasiada decision para
   algo que en la practica se juega en tres modos.

   Tres botones, y el que esta a la derecha siempre paga mas. La
   etiqueta de abajo dice CUANTO paga, que es la unica razon por
   la que alguien elegiria el dificil.
   ========================================================= */
.dif-row{
  display:grid; grid-template-columns:repeat(3,1fr); gap:8px;
  margin-top:6px;
}
.dif-row.locked{ opacity:.45; pointer-events:none; }

.dif-btn{
  display:flex; flex-direction:column; align-items:center; gap:3px;
  padding:11px 6px;
  background:var(--bg-elevated);
  border:1px solid var(--border);
  border-radius:var(--r-ctl);
  min-height:56px;
  transition:transform var(--t-fast) var(--ease), border-color var(--t-fast) var(--ease);
}
.dif-btn:hover{ transform:translateY(-2px); border-color:var(--purple); }

.dif-btn b{
  font-size:0.76rem; font-weight:700;
  letter-spacing:0.06em; text-transform:uppercase;
  color:var(--text-muted);
}
.dif-btn small{
  font-size:0.66rem;
  color:var(--text-dim);
  font-variant-numeric:tabular-nums;
}

/* El activo en dorado: es la eleccion que determina lo que se cobra. */
.dif-btn.on{
  background:var(--gold-metal);
  border-color:var(--gold);
  box-shadow:0 6px 18px -10px rgba(245,197,78,0.5);
}
.dif-btn.on b, .dif-btn.on small{ color:#120C05; }
.dif-btn.on small{ opacity:.75; }

@media (hover:none){ .dif-btn{ min-height:60px; } }

/* =========================================================
   GRAN PREMIO — cartel de victoria

   Ninguna animacion aqui se repite: todas terminan y el
   overlay se retira. El casino se limpio de animaciones
   infinitas y esto no las reintroduce.
   ========================================================= */
.bw-overlay{
  position:fixed; inset:0;
  z-index:900;
  display:grid; place-items:center;
  background:radial-gradient(60% 60% at 50% 45%, rgba(7,5,11,.72), rgba(7,5,11,.92));
  opacity:0;
  pointer-events:none;
  /* Sin `show` no existe para el motor de render: cero coste mientras no
     hay premio, que es el 99% del tiempo. */
  content-visibility:hidden;
  transition:opacity 220ms var(--ease);
}
.bw-overlay.show{
  opacity:1;
  pointer-events:auto;
  content-visibility:visible;
}

.bw-card{
  position:relative;
  padding:34px 40px;
  text-align:center;
  transform:scale(.82);
  opacity:0;
}
.bw-overlay.show .bw-card{
  animation:bwIn 520ms cubic-bezier(.2,1.5,.35,1) forwards;
}
@keyframes bwIn{
  0%   {transform:scale(.82) translateY(14px); opacity:0;}
  60%  {transform:scale(1.05) translateY(0);   opacity:1;}
  100% {transform:scale(1) translateY(0);      opacity:1;}
}

.bw-inner{ position:relative; z-index:2; display:flex; flex-direction:column; gap:6px; }

.bw-kicker{
  font-family:var(--font-display); font-weight:400;
  font-size:clamp(1rem, 3.4vw, 1.5rem);
  letter-spacing:0.22em;
  color:var(--gold-light2);
}
.bw-amount{
  font-family:var(--font-display); font-weight:400;
  font-size:clamp(2.6rem, 11vw, 5.2rem);
  line-height:1;
  font-variant-numeric:tabular-nums;
  background:linear-gradient(180deg, #fff3cf 0%, var(--gold) 46%, var(--gold-deep) 100%);
  -webkit-background-clip:text; background-clip:text; color:transparent;
}
.bw-mult{
  font-family:var(--font-display);
  font-size:clamp(1.1rem, 4vw, 1.8rem);
  color:var(--purple-glow);
  font-variant-numeric:tabular-nums;
}
.bw-game{
  font-size:0.72rem; letter-spacing:0.18em; text-transform:uppercase;
  color:var(--text-dim);
}

/* Rayos: un unico degradado conico girando una vez. No es un sprite ni
   decenas de nodos, es un solo elemento pintado por el compositor. */
.bw-rays{
  position:absolute; left:50%; top:50%;
  width:min(150vw, 900px); aspect-ratio:1;
  margin:-0 0 0 0;
  transform:translate(-50%,-50%) scale(.6);
  opacity:0;
  background:conic-gradient(from 0deg,
    rgba(245,197,78,.20) 0deg 8deg, transparent 8deg 30deg,
    rgba(245,197,78,.20) 30deg 38deg, transparent 38deg 60deg,
    rgba(245,197,78,.20) 60deg 68deg, transparent 68deg 90deg,
    rgba(245,197,78,.20) 90deg 98deg, transparent 98deg 120deg,
    rgba(245,197,78,.20) 120deg 128deg, transparent 128deg 150deg,
    rgba(245,197,78,.20) 150deg 158deg, transparent 158deg 180deg,
    rgba(245,197,78,.20) 180deg 188deg, transparent 188deg 210deg,
    rgba(245,197,78,.20) 210deg 218deg, transparent 218deg 240deg,
    rgba(245,197,78,.20) 240deg 248deg, transparent 248deg 270deg,
    rgba(245,197,78,.20) 270deg 278deg, transparent 278deg 300deg,
    rgba(245,197,78,.20) 300deg 308deg, transparent 308deg 330deg,
    rgba(245,197,78,.20) 330deg 338deg, transparent 338deg 360deg);
  -webkit-mask-image:radial-gradient(closest-side, transparent 22%, #000 42%, transparent 78%);
  mask-image:radial-gradient(closest-side, transparent 22%, #000 42%, transparent 78%);
  z-index:1;
}
.bw-overlay.show .bw-rays{ animation:bwRays 2600ms ease-out forwards; }
@keyframes bwRays{
  0%   {transform:translate(-50%,-50%) scale(.55) rotate(0deg);   opacity:0;}
  18%  {opacity:1;}
  100% {transform:translate(-50%,-50%) scale(1.05) rotate(42deg); opacity:0;}
}

/* Monedas: caen una vez y se van. El numero lo fija el nivel del premio. */
.bw-coins{ position:absolute; inset:-10% -10% auto; height:130%; z-index:1; pointer-events:none; }
.bw-coins i{
  position:absolute; top:-40px;
  width:20px; height:20px; border-radius:50%;
  background:radial-gradient(circle at 34% 30%, #fff0c2, var(--gold) 48%, var(--gold-deep) 100%);
  box-shadow:0 0 0 1px rgba(212,144,26,.6);
  opacity:0;
  animation:bwCoin 1500ms cubic-bezier(.3,.5,.5,1) forwards;
}
@keyframes bwCoin{
  0%   {transform:translateY(0) rotate(0deg) scale(.7);   opacity:0;}
  12%  {opacity:1;}
  100% {transform:translateY(78vh) rotate(var(--giro)) scale(1); opacity:0;}
}

/* El nivel tinte el cartel sin cambiar su estructura. */
.bw-overlay.enorme .bw-kicker{ color:#fff3cf; }
.bw-overlay.epico  .bw-kicker{ color:var(--purple-glow); letter-spacing:0.28em; }
.bw-overlay.epico  .bw-mult{ color:var(--gold-light2); }

/* Con "menos animaciones" el cartel sigue apareciendo -- es informacion,
   no adorno -- pero sin rayos ni monedas. */
html.menos-animacion .bw-rays,
html.menos-animacion .bw-coins{ display:none; }

/* =========================================================
   PANEL DEL OPERADOR

   Deliberadamente sobrio: es la pantalla donde se mueve
   dinero. Los botones que suman van en verde y los que restan
   en rojo, y son de tamanos distintos a proposito -- aqui
   equivocarse de boton cuesta.
   ========================================================= */
.adm-modal{ max-width:860px; }
.adm-body{ max-height:74vh; overflow-y:auto; }

.adm-tabs{
  display:flex; gap:6px; flex-wrap:wrap;
  border-bottom:1px solid var(--border);
  padding-bottom:10px; margin-bottom:14px;
}
.adm-tab{
  padding:8px 14px; border-radius:var(--r-ctl, 8px);
  border:1px solid transparent; background:transparent;
  color:var(--text-dim); font-size:0.8rem; font-weight:700;
  letter-spacing:0.04em;
  transition:color var(--t-fast) var(--ease), background-color var(--t-fast) var(--ease);
}
.adm-tab:hover{ color:var(--text-primary); }
.adm-tab.on{ background:var(--bg-elevated); border-color:var(--border); color:var(--gold); }

.adm-aviso{
  margin:0 0 12px; padding:0; font-size:0.82rem;
  max-height:0; overflow:hidden; opacity:0;
  transition:max-height var(--t-fast) var(--ease), opacity var(--t-fast) var(--ease);
}
.adm-aviso.show{ max-height:80px; opacity:1; padding:9px 12px; border-radius:8px; }
.adm-aviso.ok{  background:rgba(53,181,125,.14); color:#6ee7b7; }
.adm-aviso.mal{ background:rgba(192,51,77,.16); color:#ff9db0; }

.adm-sec{ margin-bottom:22px; }
.adm-sec h3{ font-size:0.95rem; margin:0 0 4px; color:var(--text-primary); }
.adm-nota{ font-size:0.78rem; color:var(--text-dim); margin:0 0 12px; line-height:1.5; }
.adm-sec-nota{ border-top:1px solid var(--border); padding-top:16px; }

.adm-campo{ display:block; margin-bottom:10px; }
.adm-lbl{
  display:block; font-size:0.68rem; font-weight:700;
  letter-spacing:0.08em; text-transform:uppercase;
  color:var(--text-dim); margin-bottom:5px;
}
.adm-input{
  width:100%; padding:9px 11px;
  background:var(--bg-input); color:var(--text-primary);
  border:1px solid var(--border); border-radius:var(--r-ctl, 8px);
  font-size:0.88rem; font-family:inherit;
}
.adm-input:focus{ outline:2px solid var(--purple); outline-offset:1px; }
.adm-input:disabled{ opacity:.45; }
.adm-corto{ width:120px; flex:none; }

.adm-check{ display:flex; align-items:center; gap:9px; margin:10px 0 14px; font-size:0.84rem; color:var(--text-muted); }
.adm-check input{ width:16px; height:16px; accent-color:var(--purple); }

.adm-btn{
  padding:9px 14px; border-radius:var(--r-ctl, 8px);
  border:1px solid var(--border); background:var(--bg-elevated);
  color:var(--text-muted); font-size:0.78rem; font-weight:700;
  white-space:nowrap; cursor:pointer;
  transition:border-color var(--t-fast) var(--ease), color var(--t-fast) var(--ease);
}
.adm-btn:hover{ border-color:var(--purple); color:var(--text-primary); }
.adm-btn.ok{  border-color:rgba(53,181,125,.45); color:#6ee7b7; }
.adm-btn.mal{ border-color:rgba(192,51,77,.45); color:#ff9db0; }
.adm-btn.primario{ background:var(--gold-metal, var(--gold)); color:#120C05; border-color:var(--gold); }
.adm-btn:focus-visible{ outline:2px solid var(--purple); outline-offset:2px; }

.adm-lista{ display:flex; flex-direction:column; gap:8px; margin-top:12px; }
.adm-fila{
  display:flex; align-items:center; gap:8px; flex-wrap:wrap;
  padding:11px 13px;
  background:var(--bg-surface); border:1px solid var(--border);
  border-radius:var(--r-card, 10px);
}
.adm-fila-col{ align-items:flex-start; }
.adm-fila-info{ display:flex; flex-direction:column; gap:2px; flex:1 1 190px; min-width:0; }
.adm-fila-info b{ font-size:0.86rem; color:var(--text-primary); }
.adm-sub{ font-size:0.72rem; color:var(--text-dim); }
.adm-hash{
  font-family:ui-monospace, monospace; font-size:0.68rem;
  color:var(--text-dim); background:var(--bg-input);
  padding:3px 7px; border-radius:5px;
}

@media (max-width:600px){
  .adm-fila{ flex-direction:column; align-items:stretch; }
  .adm-corto{ width:100%; }
  .adm-body{ max-height:78vh; }
}

/* =========================================================
   BANNER DE EVENTO — el que el operador crea desde su panel

   Mismo tratamiento que .hero-crash, pero con la imagen puesta
   desde JavaScript en la variable --art en vez de escrita aqui:
   el operador cambia la direccion en su panel y no hace falta
   tocar el CSS ni desplegar.

   El degradado va PRIMERO para que caiga ENCIMA de la imagen y
   el texto se lea sin tapar el dibujo. `auto 100%` en vez de
   cover porque el hero es muy apaisado (3,2:1) y casi ninguna
   ilustracion lo es: con cover se recorta por arriba y por
   abajo, que es donde suele estar lo que hay que ver.
   ========================================================= */
.hero-evento{
  background-color:var(--bg-deep);
  background-image:
    linear-gradient(90deg,
      var(--bg-deep) 0%,
      rgba(7,5,11,0.94) 22%,
      rgba(7,5,11,0.55) 40%,
      rgba(7,5,11,0) 58%),
    var(--art, none);
  background-size:cover, auto 100%;
  background-position:center, right center;
  background-repeat:no-repeat, no-repeat;
  min-height:400px;
}

/* Sin imagen no hace falta el velo: sin nada que tapar, ese
   degradado solo ensuciaba el fondo. Queda el mismo tono
   morado de la casa que llevan los banners sin ilustracion. */
.hero-evento:not([style*="--art"]){
  background-image:
    radial-gradient(680px 340px at 78% 50%, rgba(138,43,226,.18), transparent 65%),
    linear-gradient(100deg, var(--bg-elevated), #080808);
  background-size:cover, cover;
  min-height:332px;
}

/* En movil no hay ancho para texto Y dibujo lado a lado: la
   imagen se va arriba ajustando por ANCHO --asi se sigue viendo
   de lado a lado-- y el texto se lee debajo, sobre un velo que
   se opaca hacia abajo. */
@media (max-width:760px){
  .hero-evento{
    min-height:360px;
    background-size:cover, 128% auto;
    background-position:center, right top;
    background-image:
      linear-gradient(180deg,
        rgba(7,5,11,0.25) 0%,
        rgba(7,5,11,0.60) 46%,
        rgba(7,5,11,0.93) 68%,
        var(--bg-deep) 88%),
      var(--art, none);
  }
  .hero-evento .hero-body{ margin-top:auto; padding-bottom:var(--sp-3); }
}

/* ---- vista previa del banner, dentro del panel del operador ----
   Reproduce el mismo apilado que .hero-evento (velo encima de la
   imagen, imagen ajustada por altura y anclada a la derecha) a
   escala de panel. Sin esto el operador publica a ciegas: la unica
   forma de ver como queda seria sacarlo al lobby con los jugadores
   delante. */
.adm-prev{
  position:relative;
  min-height:132px;
  border-radius:12px;
  border:1px solid rgba(255,255,255,.10);
  overflow:hidden;
  display:flex; align-items:center;
  padding:14px 16px;
  background-color:#07050b;
  background-image:
    linear-gradient(90deg, #07050b 0%, rgba(7,5,11,.94) 24%,
                    rgba(7,5,11,.55) 44%, rgba(7,5,11,0) 62%),
    var(--art, none);
  background-size:cover, auto 100%;
  background-position:center, right center;
  background-repeat:no-repeat, no-repeat;
}
.adm-prev-body{ position:relative; z-index:2; max-width:62%; }
.adm-prev-kicker{
  display:inline-block; font-size:9px; letter-spacing:.14em; text-transform:uppercase;
  color:#d9b6ff; border:1px solid rgba(217,182,255,.45);
  border-radius:99px; padding:2px 8px; margin-bottom:6px;
}
.adm-prev-title{
  margin:0 0 4px; font-size:19px; line-height:1.1; font-weight:800;
  color:#fff; text-transform:uppercase; letter-spacing:.01em;
  overflow-wrap:anywhere;
}
.adm-prev-copy{
  margin:0 0 8px; font-size:11px; line-height:1.35;
  color:rgba(255,255,255,.72); overflow-wrap:anywhere;
}
.adm-prev-cta{
  display:inline-block; font-size:10px; font-weight:700;
  background:var(--gold, #f5b942); color:#1a1206;
  border-radius:8px; padding:5px 12px;
}

/* La fila que se esta editando. Sin marcarla, el formulario de arriba se
   rellena con datos de una fila de abajo y no hay forma de saber de cual:
   con varios banners parecidos se acaba guardando encima del que no era. */
.adm-fila-on{
  border-left:3px solid var(--gold, #f5b942);
  background:rgba(245,185,66,.07);
}

/* ---- panel: aviso destacado, control de retorno y ficha de jugador ----
   El aviso va con fondo ambar y no rojo: no es un error, es algo que hay
   que leer antes de mover una barra que afecta al dinero de todos. */
.adm-alerta{
  margin:0 0 16px;
  padding:14px 16px;
  border-radius:12px;
  background:rgba(245,185,66,.09);
  border:1px solid rgba(245,185,66,.30);
  border-left:3px solid #f5b942;
}
.adm-alerta b{ display:block; color:#f5cf8a; margin-bottom:6px; font-size:13px; }
.adm-alerta p{
  margin:0 0 7px; font-size:12.5px; line-height:1.5;
  color:rgba(255,255,255,.72);
}
.adm-alerta p:last-child{ margin-bottom:0; }

/* Una fila que apila cabecera y detalle, en vez de ponerlo todo en linea. */
.adm-fila-col{ display:block; }
.adm-fila-col > .adm-fila{ border:0; padding:0; margin-bottom:8px; background:none; }

.adm-rtp{ display:flex; align-items:center; gap:10px; margin:4px 0 6px; }
.adm-rango{
  flex:1; min-width:0; height:4px;
  accent-color:#19c9a2;
  cursor:pointer;
}
.adm-input-corto{ width:88px; flex:0 0 auto; text-align:center; }
.adm-rtp-pct{ color:rgba(255,255,255,.5); font-size:13px; }
.adm-rtp-efecto{
  display:block; font-size:12px; margin-bottom:4px;
  color:rgba(255,255,255,.55);
}
/* Por debajo del 92% el jugador lo nota en una tarde. */
.adm-rtp-duro{ color:#f5b942; }

/* Cifras de un jugador. Grid y no flex: las columnas se alinean entre
   filas distintas, que es lo que permite comparar cuentas de un vistazo. */
.adm-cifras{
  display:grid;
  grid-template-columns:repeat(6, minmax(0, 1fr));
  gap:8px;
  margin-top:6px;
}
.adm-celda{ display:flex; flex-direction:column; gap:2px; min-width:0; }
.adm-celda-lbl{
  font-size:10px; letter-spacing:.08em; text-transform:uppercase;
  color:rgba(255,255,255,.38);
}
.adm-celda b{
  font-size:13px; color:#fff;
  font-variant-numeric:tabular-nums;
  overflow-wrap:anywhere;
}
.adm-celda-ok  b{ color:#19c9a2; }
.adm-celda-mal b{ color:#ff8a80; }
/* Cifra que todavia no significa nada por falta de volumen. */
.adm-celda-flojo b{ color:rgba(255,255,255,.34); }

.adm-chip{
  display:inline-block; margin-left:7px; padding:1px 7px;
  border-radius:99px; font-size:9.5px; font-weight:700; letter-spacing:.06em;
  background:rgba(138,43,226,.28); color:#d9b6ff;
  vertical-align:middle;
}
.adm-chip-mal{ background:rgba(255,80,70,.20); color:#ff9c94; }

@media (max-width:560px){
  .adm-cifras{ grid-template-columns:repeat(3, minmax(0, 1fr)); }
}

/* =========================================================
   RECARGA POR TRANSFERENCIA

   Verde para la caja de datos, como en la referencia: es la
   parte que el jugador tiene que copiar bien, y separarla del
   morado del casino la hace destacar sin decorarla.
   ========================================================= */
.tu-modal{ max-width:480px; }
.tu-icon{ color:#19c9a2; }
.tu-body{ padding:clamp(14px,3vw,22px); }
.tu-cargando{
  text-align:center; color:rgba(255,255,255,.55);
  font-size:14px; padding:28px 10px; margin:0;
}

.tu-reloj{
  display:flex; align-items:center; justify-content:center; gap:8px;
  background:linear-gradient(135deg,#1d8145,#19c9a2);
  color:#fff; font-weight:800;
  border-radius:10px; padding:11px;
  margin-bottom:16px;
  font-variant-numeric:tabular-nums;
  letter-spacing:.04em;
}
.tu-reloj-ic{ font-size:15px; }
.tu-reloj-t{ font-size:17px; }

.tu-caja{
  background:rgba(25,201,162,.07);
  border:1px solid rgba(25,201,162,.24);
  border-radius:12px;
  padding:14px 16px;
  margin-bottom:18px;
}
.tu-caja-t{
  margin:0 0 10px; text-align:center;
  color:#5eead4; font-weight:800; font-size:15px;
}
.tu-fila{
  display:flex; align-items:center; justify-content:space-between;
  gap:12px; padding:9px 0;
  border-bottom:1px solid rgba(255,255,255,.07);
}
.tu-fila:last-child{ border-bottom:0; }
.tu-lbl{ color:rgba(255,255,255,.62); font-size:13.5px; flex:0 0 auto; }
.tu-val{
  display:flex; align-items:center; gap:9px;
  min-width:0; flex:1 1 auto; justify-content:flex-end;
}
/* La CLABE son 18 digitos y en un movil de 375 no caben en una linea: se
   parte en vez de desbordar, y en cifras tabulares para que se lea de
   corrido al compararla con la app del banco. */
.tu-val b{
  color:#fff; font-size:14.5px; font-weight:700;
  font-variant-numeric:tabular-nums;
  overflow-wrap:anywhere; text-align:right;
}
.tu-copiar{
  flex:0 0 auto;
  background:rgba(25,201,162,.16);
  border:1px solid rgba(25,201,162,.34);
  color:#5eead4;
  border-radius:7px; padding:4px 10px;
  font-size:11.5px; font-weight:700; cursor:pointer;
  transition:background .15s, color .15s;
}
.tu-copiar:hover{ background:rgba(25,201,162,.28); }
.tu-copiado{ background:#19c9a2; color:#04201a; border-color:#19c9a2; }

.tu-pasos{ margin-bottom:18px; }
.tu-paso{ display:flex; gap:12px; padding:9px 0; }
.tu-paso-n{
  flex:0 0 auto;
  width:24px; height:24px; border-radius:50%;
  display:grid; place-items:center;
  background:rgba(138,43,226,.30); color:#d9b6ff;
  font-size:12px; font-weight:800;
}
.tu-paso-c{ min-width:0; }
.tu-paso-c b{ display:block; color:#fff; font-size:14px; margin-bottom:2px; }
.tu-paso-c p{
  margin:0; color:rgba(255,255,255,.62);
  font-size:13px; line-height:1.45; overflow-wrap:anywhere;
}

.tu-envio{ display:grid; gap:9px; }
.tu-monto{
  width:100%;
  background:#1c1920; border:1px solid rgba(255,255,255,.12);
  border-radius:10px; padding:13px 14px;
  color:#fff; font-size:15px; font-weight:600;
  -moz-appearance:textfield;
}
.tu-monto::-webkit-outer-spin-button,
.tu-monto::-webkit-inner-spin-button{ -webkit-appearance:none; margin:0; }
.tu-enviar{
  width:100%;
  background:linear-gradient(135deg,#1d8145,#19c9a2);
  color:#fff; border:0; border-radius:10px;
  padding:14px; font-size:15px; font-weight:800; cursor:pointer;
  transition:filter .15s;
}
.tu-enviar:hover:not(:disabled){ filter:brightness(1.1); }
.tu-enviar:disabled{ filter:grayscale(.6) brightness(.7); cursor:default; }

.tu-nota{
  margin:12px 0 0; font-size:12px; line-height:1.45;
  color:rgba(255,255,255,.42); text-align:center;
}

.tu-mios{ margin-top:18px; }
.tu-mios-t{
  margin:0 0 8px; font-size:11px; letter-spacing:.10em;
  text-transform:uppercase; color:rgba(255,255,255,.38);
}
.tu-mio{
  display:flex; align-items:center; gap:10px;
  padding:8px 0; border-bottom:1px solid rgba(255,255,255,.06);
  font-size:13px;
}
.tu-mio:last-child{ border-bottom:0; }
.tu-mio b{ color:#fff; flex:0 0 auto; font-variant-numeric:tabular-nums; }
.tu-estado{
  flex:1 1 auto;
  font-size:11.5px; font-weight:700;
  padding:2px 9px; border-radius:999px;
  justify-self:start; max-width:max-content;
}
.tu-e-pend{ background:rgba(245,185,66,.16); color:#f5cf8a; }
.tu-e-ok  { background:rgba(25,201,162,.16); color:#5eead4; }
.tu-e-mal { background:rgba(255,80,70,.16); color:#ff9c94; }
.tu-fecha{
  flex:0 0 auto; color:rgba(255,255,255,.34);
  font-size:11.5px; font-variant-numeric:tabular-nums;
}

/* Chips de estado en la bandeja de recargas. */
.adm-chip-warn{ background:rgba(245,185,66,.20); color:#f5cf8a; }
.adm-chip-ok  { background:rgba(25,201,162,.20); color:#5eead4; }

/* Version fina del aviso, para colgarla de un campo concreto en vez de
   encabezar una seccion entera. */
.adm-alerta-fina{
  margin:2px 0 14px; padding:11px 13px;
  font-size:12.5px; line-height:1.45;
  color:rgba(255,255,255,.72);
}
.adm-alerta-fina b{ display:none; }

/* Saldo por encima de lo depositado: el momento de mirar antes de pagar. */
.adm-aviso-saldo{
  margin:8px 0 0; padding:10px 12px;
  border-radius:9px;
  background:rgba(245,185,66,.10);
  border-left:3px solid #f5b942;
  color:#f5cf8a;
  font-size:12.5px; line-height:1.45;
}

/* ---- recarga: tarjeta de activos y rejilla de importes ----
   El lima es del original y se gana el sitio: en un modal morado y verde,
   la unica pieza que grita es la que dice cuanto dinero tienes. */
.tu-activos{
  position:relative;
  background:linear-gradient(135deg,#c8f231,#a5d916);
  border-radius:14px;
  padding:20px 18px 16px;
  margin-bottom:14px;
}
.tu-activos-t{
  position:absolute; top:-1px; left:14px;
  transform:translateY(-50%);
  background:#12101a; color:#c8f231;
  font-size:11px; font-weight:700;
  padding:3px 11px; border-radius:999px;
}
.tu-activos-par{ display:grid; grid-template-columns:1fr 1fr; gap:10px; }
.tu-dato{ text-align:center; min-width:0; }
.tu-dato b{
  display:block; color:#12101a;
  font-size:clamp(20px, 5.5vw, 27px); font-weight:900;
  font-variant-numeric:tabular-nums;
  overflow-wrap:anywhere; line-height:1.1;
}
.tu-dato span{
  display:block; color:rgba(18,16,26,.66);
  font-size:12px; font-weight:600; margin-top:2px;
}

.tu-bloqueo{
  margin:0 0 14px; padding:10px 13px;
  border-radius:10px;
  background:rgba(245,185,66,.10);
  border-left:3px solid #f5b942;
  color:#f5cf8a; font-size:12.5px; line-height:1.45;
}

.tu-seccion{
  margin:0 0 10px;
  font-size:14px; font-weight:800; color:#fff;
}

/* Cuatro por fila como el original. En pantallas muy estrechas bajan a tres
   para que el "100k" no se parta. */
.tu-grid{
  display:grid; grid-template-columns:repeat(4, 1fr);
  gap:8px; margin-bottom:12px;
}
@media (max-width:360px){ .tu-grid{ grid-template-columns:repeat(3, 1fr); } }

.tu-chip{
  position:relative;
  background:#1c1920;
  border:1px solid rgba(255,255,255,.10);
  border-radius:10px;
  padding:16px 4px 10px;
  cursor:pointer;
  transition:border-color .15s, background .15s;
  overflow:hidden;
}
.tu-chip:hover{ border-color:rgba(200,242,49,.45); }
.tu-chip.on{
  border-color:#c8f231;
  background:rgba(200,242,49,.10);
}
.tu-chip-n{
  display:block; color:#fff;
  font-size:15px; font-weight:700;
  font-variant-numeric:tabular-nums;
}
/* La banderita del bono, arriba a la izquierda como en la referencia. */
.tu-flag{
  position:absolute; top:0; left:0;
  background:#e3342f; color:#fff;
  font-size:9.5px; font-weight:800;
  padding:2px 7px 2px 5px;
  border-bottom-right-radius:8px;
  line-height:1.3;
}

.tu-libre{
  width:100%;
  background:#1c1920;
  border:1px solid rgba(200,242,49,.35);
  border-radius:10px; padding:13px 14px;
  color:#fff; font-size:15px; font-weight:600;
  -moz-appearance:textfield;
}
.tu-libre::-webkit-outer-spin-button,
.tu-libre::-webkit-inner-spin-button{ -webkit-appearance:none; margin:0; }

.tu-calculo{
  margin:8px 0 12px; min-height:1.2em;
  font-size:12.5px; color:rgba(255,255,255,.45);
}
.tu-calculo-on{ color:#c8f231; font-weight:600; }

.tu-reglas{ margin-bottom:14px; }
.tu-reglas p{
  margin:0 0 4px; font-size:12px; line-height:1.5;
  color:rgba(255,255,255,.50);
}
/* La condicion del bono no se esconde entre la letra pequena: es lo que
   evita la discusion el dia del primer retiro. */
.tu-reglas-clave{
  color:rgba(255,255,255,.78) !important;
  font-weight:600;
  margin-top:7px !important;
}

.tu-volver{
  background:none; border:0; cursor:pointer;
  color:rgba(255,255,255,.55);
  font-size:13px; padding:0 0 12px;
}
.tu-volver:hover{ color:#fff; }

.tu-resumen{
  text-align:center; margin-bottom:16px;
}
.tu-resumen b{
  display:block; color:#c8f231;
  font-size:30px; font-weight:900;
  font-variant-numeric:tabular-nums;
}
.tu-resumen span{
  display:block; color:rgba(255,255,255,.55);
  font-size:12.5px; margin-top:2px;
}

/* =========================================================
   CANJEAR CODIGO
   ========================================================= */
.rd-modal{ max-width:420px; }
.rd-icon{ color:#f5b942; }
.rd-body{ padding:clamp(16px,3.5vw,24px); }

.rd-intro{
  margin:0 0 16px; font-size:13px; line-height:1.55;
  color:rgba(255,255,255,.62);
}

.rd-caja{ display:flex; gap:8px; margin-bottom:4px; }
.rd-input{
  flex:1; min-width:0;
  background:#1c1920; border:1px solid rgba(245,185,66,.35);
  border-radius:10px; padding:13px 14px;
  color:#fff; font-size:16px; font-weight:700;
  letter-spacing:.05em;
  text-transform:uppercase;
}
.rd-input::placeholder{ color:rgba(255,255,255,.28); text-transform:none; letter-spacing:normal; font-weight:500; }
.rd-enviar{
  flex:0 0 auto;
  background:linear-gradient(135deg,#f7c809,#f27b05);
  color:#1a1206; border:0; border-radius:10px;
  padding:0 20px; font-size:14px; font-weight:800; cursor:pointer;
  transition:filter .15s;
}
.rd-enviar:hover:not(:disabled){ filter:brightness(1.08); }
.rd-enviar:disabled{ filter:grayscale(.6) brightness(.7); cursor:default; }

.rd-resultado{ min-height:1px; margin:14px 0 0; }
.rd-resultado-ok{
  padding:12px 14px; border-radius:10px;
  background:rgba(25,201,162,.10); border:1px solid rgba(25,201,162,.32);
}
.rd-resultado-ok b{ display:block; color:#5eead4; font-size:14px; margin-bottom:3px; }
.rd-resultado-ok p{ margin:0; color:rgba(255,255,255,.72); font-size:12.5px; }
.rd-resultado-mal{
  padding:12px 14px; border-radius:10px; font-size:12.5px;
  background:rgba(255,80,70,.10); border:1px solid rgba(255,80,70,.30);
  color:#ff9c94;
}

.rd-mios{ margin-top:18px; }
.rd-mios-t{
  margin:0 0 8px; font-size:11px; letter-spacing:.10em;
  text-transform:uppercase; color:rgba(255,255,255,.38);
}
.rd-mio{
  display:flex; align-items:center; gap:10px;
  padding:8px 0; border-bottom:1px solid rgba(255,255,255,.06);
  font-size:13px;
}
.rd-mio:last-child{ border-bottom:0; }
.rd-mio b{ color:#f5cf8a; flex:0 0 auto; letter-spacing:.03em; }
.rd-mio > span:not(.rd-fecha){ color:#fff; font-variant-numeric:tabular-nums; }
.rd-fecha{
  margin-left:auto; color:rgba(255,255,255,.34);
  font-size:11.5px; font-variant-numeric:tabular-nums;
}

/* El puntero desde Recargar hacia el canje de codigos. */
.tu-codigo-link{
  display:block; width:100%; margin-top:2px;
  background:rgba(245,185,66,.08); border:1px dashed rgba(245,185,66,.35);
  border-radius:10px; padding:11px 14px;
  color:#f5cf8a; font-size:12.5px; font-weight:600; text-align:center;
  cursor:pointer; transition:background .15s;
}
.tu-codigo-link:hover{ background:rgba(245,185,66,.14); }

/* ---- panel: codigos de canje ---- */
.adm-fila-apagada{ opacity:.55; }
.adm-codigo-nuevo{
  display:flex; align-items:center; gap:10px;
  background:rgba(25,201,162,.10); border:1px solid rgba(25,201,162,.30);
  border-radius:10px; padding:12px 14px; margin:4px 0 14px;
  font-size:13.5px; color:rgba(255,255,255,.75);
}
.adm-codigo-nuevo b{
  color:#5eead4; font-size:15px; letter-spacing:.04em;
  font-family:ui-monospace, "SF Mono", monospace;
}
.adm-detalle-canjes{ margin-top:6px; padding-left:2px; }

/* =========================================================
   RETIRAR — botones junto a Recargar
   ========================================================= */
.btn-withdraw{
  height:46px;
  padding:0 20px;
  border-radius:12px;
  background:transparent;
  border:1.5px solid rgba(245,197,78,.55);
  color:var(--gold-light, #f5c54e);
  font-weight:800; font-size:0.82rem;
  letter-spacing:0.06em; text-transform:uppercase;
  transition:background .15s, transform var(--t-fast) var(--ease);
}
.btn-withdraw:hover{ background:rgba(245,197,78,.10); transform:translateY(-1px); }

.side-wallet-btns{ display:flex; gap:8px; }
.side-wallet-btns .side-topup{ flex:1 1 0; }
.side-withdraw{
  flex:1 1 0;
  padding:12px 10px;
  border-radius:var(--r-ctl);
  background:transparent;
  border:1.5px solid rgba(245,197,78,.5);
  color:var(--gold-light, #f5c54e);
  font-weight:700; font-size:0.8rem;
  letter-spacing:0.06em; text-transform:uppercase;
  transition:background .15s, transform var(--t-fast) var(--ease);
}
.side-withdraw:hover{ background:rgba(245,197,78,.10); transform:translateY(-1px); }

/* =========================================================
   MODAL RETIRAR — comparte esqueleto visual con Recargar (tu-*)
   ========================================================= */
.wd-modal{ max-width:440px; }
.wd-icon{ color:#f5b942; }
.wd-body{ padding:clamp(16px,3.5vw,24px); }
.wd-cargando{ text-align:center; color:rgba(255,255,255,.55); font-size:14px; padding:28px 10px; margin:0; }

.wd-activos{
  display:flex; align-items:baseline; justify-content:space-between;
  background:rgba(245,185,66,.08); border:1px solid rgba(245,185,66,.26);
  border-radius:12px; padding:14px 16px; margin-bottom:16px;
}
.wd-activos span{ font-size:12.5px; color:rgba(255,255,255,.62); }
.wd-activos b{ font-size:22px; color:#f5cf8a; font-variant-numeric:tabular-nums; }

.wd-vacio{
  text-align:center; color:rgba(255,255,255,.55);
  font-size:13.5px; line-height:1.6; padding:12px 4px 4px;
}

.wd-campo{ display:block; margin-bottom:12px; }
.wd-lbl{ display:block; font-size:11.5px; letter-spacing:.05em; color:rgba(255,255,255,.55); margin-bottom:6px; }
.wd-input{
  width:100%;
  background:#1c1920; border:1px solid rgba(255,255,255,.12);
  border-radius:10px; padding:12px 14px;
  color:#fff; font-size:15px; font-weight:600;
}
.wd-fila-monto{ display:flex; gap:8px; }
.wd-fila-monto .wd-input{ flex:1; min-width:0; }
.wd-chip{
  flex:0 0 auto;
  background:var(--btn-bg, #38373f); color:#fff;
  border:0; border-radius:10px; padding:0 16px;
  font-size:12.5px; font-weight:700; cursor:pointer;
}
.wd-clabe-aviso{ margin:6px 0 0; font-size:11.5px; min-height:1.2em; }
.wd-clabe-ok{ color:#5eead4; }
.wd-clabe-mal{ color:#ff9c94; }

.wd-enviar{
  width:100%;
  background:linear-gradient(135deg,#f7c809,#f27b05);
  color:#1a1206; border:0; border-radius:10px;
  padding:14px; font-size:15px; font-weight:800; cursor:pointer;
  margin-top:4px;
  transition:filter .15s;
}
.wd-enviar:hover:not(:disabled){ filter:brightness(1.08); }
.wd-enviar:disabled{ filter:grayscale(.6) brightness(.7); cursor:default; }

.wd-resultado{ min-height:1px; margin-top:12px; }
.wd-resultado-ok{
  padding:12px 14px; border-radius:10px; font-size:12.5px;
  background:rgba(25,201,162,.10); border:1px solid rgba(25,201,162,.32); color:#5eead4;
}
.wd-resultado-mal{
  padding:12px 14px; border-radius:10px; font-size:12.5px;
  background:rgba(255,80,70,.10); border:1px solid rgba(255,80,70,.30); color:#ff9c94;
}

.wd-bloqueo{
  background:rgba(255,80,70,.06); border:1px solid rgba(255,80,70,.24);
  border-radius:12px; padding:16px; margin-bottom:16px;
}
.wd-bloqueo b{ display:block; color:#ff9c94; font-size:15px; margin-bottom:6px; }
.wd-bloqueo p{ margin:0; color:rgba(255,255,255,.68); font-size:13px; line-height:1.55; }

.wd-pendiente{
  text-align:center;
  background:rgba(245,185,66,.08); border:1px solid rgba(245,185,66,.26);
  border-radius:12px; padding:22px 18px; margin-bottom:16px;
}
.wd-pendiente-ic{ display:block; font-size:26px; margin-bottom:6px; }
.wd-pendiente b{ display:block; color:#f5cf8a; font-size:16px; margin-bottom:6px; }
.wd-pendiente p{ margin:0; color:rgba(255,255,255,.62); font-size:12.5px; line-height:1.55; }

.wd-mios{ margin-top:18px; }
.wd-mios-t{
  margin:0 0 8px; font-size:11px; letter-spacing:.10em;
  text-transform:uppercase; color:rgba(255,255,255,.38);
}
.wd-mio{
  padding:9px 0; border-bottom:1px solid rgba(255,255,255,.06); font-size:13px;
}
.wd-mio:last-child{ border-bottom:0; }
.wd-mio-cab{ display:flex; align-items:center; gap:10px; }
.wd-mio-cab b{ color:#fff; font-variant-numeric:tabular-nums; }
.wd-estado{ font-size:11.5px; font-weight:700; padding:2px 9px; border-radius:999px; }
.wd-e-pend{ background:rgba(245,185,66,.16); color:#f5cf8a; }
.wd-e-ok  { background:rgba(25,201,162,.16); color:#5eead4; }
.wd-e-mal { background:rgba(255,80,70,.16); color:#ff9c94; }
.wd-fecha{ margin-left:auto; color:rgba(255,255,255,.34); font-size:11.5px; font-variant-numeric:tabular-nums; }
.wd-motivo{ margin:4px 0 0; color:rgba(255,138,128,.85); font-size:12px; }
.wd-ver-comprobante{
  margin-top:6px; background:none; border:1px solid rgba(255,255,255,.18);
  color:rgba(255,255,255,.72); border-radius:8px; padding:5px 11px;
  font-size:11.5px; cursor:pointer;
}
.wd-comprobante-img{
  display:block; max-width:100%; margin-top:8px;
  border-radius:8px; border:1px solid rgba(255,255,255,.12);
}

/* ---- panel: comprobante de retiro ---- */
.adm-comprobante-previa{
  display:block; max-width:280px; margin-top:8px;
  border-radius:8px; border:1px solid rgba(255,255,255,.14);
}
