/* Inter only — the whole site standardised on it, so the Fraunces family that
   used to load here was an unused download on every page view.

   Self-hosted, not imported from Google. The @import that used to sit here was
   blocked by the Content-Security-Policy in middleware/securityHeaders.js: an
   @import is a style fetch, and style-src is 'self' — and even past that,
   font-src 'self' would have blocked the woff2 files from fonts.gstatic.com.
   With nothing loaded, every weight fell back to a system font that only has
   Regular and Bold, so 500 and 600 both rendered as full Bold and the whole
   site looked heavy.

   Only the latin and latin-ext subsets are kept (this is a Spanish store);
   unicode-range means a visitor downloads only the file the text needs.

   To regenerate: fetch the URL below with a desktop browser User-Agent (an old
   one gets ttf instead of woff2), keep the latin/latin-ext @font-face blocks,
   and save each woff2 into public/fonts/ under the same names used here.
   https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600&display=swap */
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('/fonts/inter-400-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 400;
  font-display: swap;
  src: url('/fonts/inter-400-latin.woff2') format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url('/fonts/inter-500-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 500;
  font-display: swap;
  src: url('/fonts/inter-500-latin.woff2') format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 600;
  font-display: swap;
  src: url('/fonts/inter-600-latin-ext.woff2') format('woff2');
  unicode-range: U+0100-02BA, U+02BD-02C5, U+02C7-02CC, U+02CE-02D7, U+02DD-02FF, U+0304, U+0308, U+0329, U+1D00-1DBF, U+1E00-1E9F, U+1EF2-1EFF, U+2020, U+20A0-20AB, U+20AD-20C0, U+2113, U+2C60-2C7F, U+A720-A7FF;
}
@font-face {
  font-family: 'Inter';
  font-style: normal;
  font-weight: 600;
  font-display: swap;
  src: url('/fonts/inter-600-latin.woff2') format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}

:root {
  --black: #0B0B0D;
  --black-soft: #141416;
  --white: #FFFFFF;
  --lavender: #A99BE8;
  --lavender-band: #B6A2DA;
  --purple-hero-1: #B6A2DA;
  --purple-hero-2: #B6A2DA;
  --mint: #D4E9D3;
  --mint-text: #1F3A24;
  --ink-muted: #B8B4C2;
  --radius: 10px;
  /* Dark aurora ground (home + former lavender bands). A dark blue-navy base with
     a static purple lead glow and a deep-blue counter-glow painted over it — see
     the .site-aurora layer below; the white sub-pages hide it. */
  --bg-dark: #080A1A;           /* dark blue-navy ground */
  --aurora-lav: 110, 92, 176;   /* deep lavender-purple — the lead glow */
  --aurora-blue: 58, 86, 190;   /* deep blue — the static aurora's cool depth */
  --aurora-mint: 74, 140, 116;  /* muted mint — brand tint, kept for reuse */
  --aurora-plum: 140, 88, 158;  /* soft plum — depth */
  --aurora-wash: 169, 155, 232; /* faint lavender wash near the top */
  font-size: 16px;
}

* { box-sizing: border-box; }
/* Always show the vertical scrollbar so the page (and the full-width header) is
   the same width on every page — short pages no longer render ~15px wider than
   pages that scroll, which shifted the centered nav. Using overflow-y:scroll
   (rather than scrollbar-gutter:stable) means the reserved strip is painted as a
   real scrollbar instead of an empty gutter that would show the black body
   background as a strip against the purple sections. */
html { scroll-behavior: smooth; overflow-y: scroll; overflow-x: hidden; background: var(--bg-dark); }
body {
  margin: 0;
  /* Transparent so the fixed .site-aurora layer (z-index -1) shows through from
     behind: the dark base lives on <html>, the aurora paints over it, and the
     home's transparent bands/sections reveal it. An opaque body background here
     would hide the aurora entirely. body.light-page sets an opaque white back,
     which (with the aurora hidden there) keeps the sub-pages clean and light. */
  background: transparent;
  color: var(--white);
  font-family: 'Inter', sans-serif;
  line-height: 1.5;
  min-height: 100vh;
  display: flex;
  flex-direction: column;
  /* html has overflow-x:hidden, but iOS ignores it for pinch-zoom; clip on body
     too bounds the zoomable width to the viewport. clip (not hidden) doesn't
     create a scroll container, so the sticky header keeps working. */
  overflow-x: clip;
}
/* Sticky footer: on short pages the footer sits at the bottom of the viewport
   instead of floating with empty space below it. */
.site-footer { margin-top: auto; }
h1, h2, h3 { margin: 0; font-family: 'Inter', sans-serif; font-weight: 600; }
.serif-italic { font-family: 'Inter', sans-serif; font-style: normal; font-weight: 600; }
a { color: inherit; text-decoration: none; }
/* No drag ghost on a desktop, no iOS long-press "save image" sheet. Companion
   to the contextmenu handler in storefront.js, with the same caveat: a speed
   bump, not protection.
   Kept on the image rather than the body so long-pressing a link still opens
   its menu, and so page text is still selectable. */
img {
  max-width: 100%; display: block;
  -webkit-touch-callout: none;
  -webkit-user-drag: none;
  user-select: none;
  -webkit-user-select: none;
}

/* ---------- Dark aurora ground ----------
   A single fixed, STATIC gradient (z-index -1) behind everything: the dark
   blue-navy ground (--bg-dark on <html>) with a purple lead glow in the upper-left
   and a deep-blue counter-glow in the lower-right, giving the home one flowing dark
   background in place of the flat lavender bands. The home's coloured bands and
   dark sections are made transparent (below) so this shows through them; the white
   sub-pages hide it entirely. Markup: <div class="site-aurora"> in header.ejs.

   This was previously an animated blob. The animation was the biggest remaining
   GPU cost — every frame the compositor scaled and alpha-blended a ~full-quadrant
   semi-transparent layer — so it's now painted ONCE and never repaints (a static
   gradient costs the GPU nothing after the first paint). The drifting candy motes
   carry the "alive" feel. No blur filter (the gradient falloff is already soft),
   no mix-blend. Purely decorative: aria-hidden in header.ejs. */
.site-aurora {
  position: fixed; inset: 0; z-index: -1; pointer-events: none; overflow: hidden;
  background:
    radial-gradient(72% 62% at 16% 6%, rgba(var(--aurora-lav), 0.46), rgba(var(--aurora-lav), 0) 60%),
    radial-gradient(80% 72% at 88% 94%, rgba(var(--aurora-blue), 0.34), rgba(var(--aurora-blue), 0) 62%);
}
/* Adaptive safety net for the motes only (aurora is static now, so it needs none):
   if js/candy-motes.js measures a low frame rate, it hides the motes. */
html.rc-lowfps .candy-motes { display: none !important; }
/* The light-page class is gone (Phase 2: every page is dark aurora now); this
   rule stays as a no-op safety net should any old markup still set it. */
body.light-page .site-aurora { display: none; }
/* NOTE: the rules that make the home's bands/sections transparent so this shows
   through them live at the END of this file (search "Dark aurora — section
   overrides"), so they win over the original solid-fill rules further down. */

/* ---------- Ambient candy motes ----------
   A fixed, full-viewport layer of faint drifting specks, over the whole page to
   give the dark aurora ground a little life. z-index 8 puts it above the coloured
   sections but below the sticky header (60), the top banner (70), every
   dropdown/mega-menu (55-60) and all modals (150-200); pointer-events:none keeps
   it click-through. Decorative only — no layer at all under prefers-reduced-motion.

   Each mote is a <span> built by js/candy-motes.js; its drift/sway/fade is the
   rcMote CSS keyframe below, so the motion runs on the GPU compositor thread.
   This replaced an earlier 2D <canvas> that redrew the full viewport (clearRect +
   per-mote arc fills) on the MAIN thread every frame — the heaviest ambient cost,
   and the thing that competed with scrolling. Transform+opacity on the compositor
   costs the main thread nothing, so the motes no longer fight the scroll. */
.candy-motes {
  position: fixed;
  inset: 0;
  width: 100%;
  height: 100%;
  z-index: 8;
  pointer-events: none;
}
/* One composited layer per mote. top:100% seats it just below the viewport; the
   keyframe lifts it up through the screen and fades it in/out at the ends. Size,
   tint, opacity (--mote-a), horizontal drift (--mote-sway), duration and a
   negative delay (so they start already spread up the screen) are set inline. */
.candy-motes span {
  position: absolute;
  top: 100%;
  border-radius: 50%;
  opacity: 0;
  will-change: transform, opacity;
  animation-name: rcMote;
  animation-timing-function: linear;
  animation-iteration-count: infinite;
}
@keyframes rcMote {
  0%   { transform: translate3d(0, 0, 0); opacity: 0; }
  8%   { opacity: var(--mote-a, 0.2); }
  50%  { transform: translate3d(var(--mote-sway, 0px), -55vh, 0); }
  92%  { opacity: var(--mote-a, 0.2); }
  100% { transform: translate3d(0, -115vh, 0); opacity: 0; }
}
/* Freeze the mote drift while scrolling, exactly like the aurora above — hands
   the compositor back its cycles for the scroll. Toggled by js/candy-motes.js. */
html.rc-scrolling .candy-motes span { animation-play-state: paused; }
@media (prefers-reduced-motion: reduce) { .candy-motes span { animation: none; } }

/* ---------- Top banner ---------- */
/* A faint lavender-tinted dark strip rather than the old solid lavender, so it
   belongs to the dark theme and lets the aurora glow through; white text still
   reads. A hairline underline keeps it legible as its own announcement bar. */
.top-banner {
  background: rgba(var(--aurora-lav), 0.18);
  border-bottom: 1px solid rgba(255, 255, 255, 0.08);
  color: var(--white);
  text-align: center;
  padding: 6px 16px;
  font-size: 0.82rem;
}

/* ---------- Header ---------- */
.site-header { background: var(--black); position: sticky; top: 0; z-index: 60; }
.header-inner {
  max-width: 100%; margin: 0; padding: 4px clamp(16px, 3vw, 40px);
  display: grid; grid-template-columns: 1fr auto 1fr; align-items: center;
}
.logo { justify-self: start; }
.logo { display: flex; align-items: center; gap: 8px; font-size: 1.15rem; font-weight: 600; }
.logo .accent { color: var(--lavender); }
.logo .candy-icon { width: 22px; height: 22px; }
.logo-img { height: 34px; width: auto; object-fit: contain; display: block; }
.main-nav { display: flex; gap: 26px; justify-content: center; align-items: center; }
.main-nav > a, .main-nav > .has-menu > a {
  font-size: 0.9rem; color: var(--white); opacity: 0.9; padding: 6px 0; position: relative;
  display: inline-flex; align-items: center; gap: 7px;
}
/* Category glyphs inherit the link colour (currentColor) so they dim/brighten
   with the link on hover and turn purple on the accent hover state. */
.main-nav .nav-ico { width: 16px; height: 16px; flex: 0 0 auto; }
.main-nav a:hover { opacity: 1; }
.main-nav a.active { font-weight: 600; }
.header-icons { display: flex; gap: 18px; justify-content: flex-end; align-items: center; }
/* inline-flex centers each SVG glyph so the account/cart icons line up with
   the flex-centered search + hamburger (otherwise the anchors' SVGs sit on the
   text baseline, ~3px high). */
.header-icons a { opacity: 0.85; display: inline-flex; align-items: center; }
.header-icons svg { width: 19px; height: 19px; stroke: var(--white); }
.nav-toggle { display: none; background: none; border: none; padding: 0; cursor: pointer; align-items: center; }
.nav-toggle svg { width: 24px; height: 24px; stroke: var(--white); }

/* Header search */
#search-toggle { background: none; border: none; padding: 0; cursor: pointer; display: flex; }
.search-form {
  max-width: 0; max-height: 0; overflow: hidden; opacity: 0;
  transition: max-height 0.2s ease, opacity 0.2s ease;
  background: var(--black); border-top: 1px solid transparent;
}
/* overflow:visible only once open, so the suggestions can escape the collapsed
   (max-height) box without breaking the open/close animation. */
/* Full width, like the header it drops out of. Capped at the old 1280px content
   column it stayed left-aligned in a full-bleed header, so on a wide screen its
   background and top border stopped mid-window and left a visible cut.
   The padding matches .header-inner, so the field lines up with the logo on the
   left and the cart icon on the right instead of sitting 16px inside them. */
.search-form.open { max-width: 100%; max-height: 80px; opacity: 1; border-top-color: #26262b; padding: 12px clamp(16px, 3vw, 40px); overflow: visible; }
.search-inner { position: relative; }
.search-form input {
  width: 100%; display: block; background: transparent; border: none;
  border-bottom: 1px solid var(--ink-muted); color: var(--white); font-family: inherit; font-size: 0.95rem; padding: 6px 2px; outline: none;
}
@media (max-width: 860px) {
  /* iOS Safari zooms the page when a focused input's text is under 16px, and it
     does not zoom back — you tap search and the header is left scrolled off to
     the side. Same guard admin.css and the Candydex search use. */
  .search-form input { font-size: 16px; }
}

/* Live search suggestions */
/* Anchored to the left of the field and capped, rather than stretched to both
   its edges: now that the field runs the full width of the window, pinning
   right:0 spread five product rows across ~1800px of panel. Narrower than the
   input is the usual shape for an autocomplete, and it keeps the thumbnail,
   name and price in one glance. Below the cap it still tracks the field. */
.search-results {
  position: absolute; top: calc(100% + 10px); left: 0; z-index: 70;
  width: 100%; max-width: 560px;
  background: #fff; border-radius: 12px; box-shadow: 0 16px 40px rgba(11,11,13,0.35);
  overflow: hidden; max-height: min(60vh, 420px); overflow-y: auto;
}
.search-results[hidden] { display: none; }
.sr-item { display: flex; align-items: center; gap: 12px; padding: 10px 14px; color: #2B1930; text-decoration: none; }
.sr-item:hover, .sr-item.active { background: #f6f2fa; }
.sr-thumb { width: 44px; height: 44px; flex-shrink: 0; border-radius: 8px; overflow: hidden; background: #f1eef6; display: grid; place-items: center; }
.sr-thumb img { width: 100%; height: 100%; object-fit: cover; display: block; }
.sr-body { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.sr-name { font-weight: 600; font-size: 0.9rem; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.sr-meta { font-size: 0.8rem; color: #6C5A76; }
.sr-empty { padding: 16px 14px; color: #6C5A76; font-size: 0.88rem; text-align: center; }
.sr-all {
  display: block; width: 100%; padding: 11px 14px; border: none; border-top: 1px solid #ece7f1;
  background: #faf8fc; color: var(--candy-deep, #E63E82); font: inherit; font-size: 0.82rem; font-weight: 700; cursor: pointer;
}
.sr-all:hover { background: #f3edf8; }

/* Mega menu */
/* flex + align-items:center so the Catálogo link is blockified and vertically
   centered exactly like the sibling nav links (which are direct flex items of
   .main-nav); otherwise it stays display:inline and sits a few px lower. */
.has-menu { position: static; display: flex; align-items: center; }
/* Caret toggle is mobile-only; on desktop the mega opens on hover. */
.mega-toggle { display: none; }
.mega {
  position: absolute; left: 0; right: 0; top: 100%;
  background: var(--black); border-top: 1px solid #26262b;
  padding: 26px 24px 34px; z-index: 55;
  opacity: 0; visibility: hidden; transform: translateY(-12px); pointer-events: none;
  transition: opacity 0.24s ease, transform 0.24s ease, visibility 0.24s;
}
.has-menu:hover .mega, .has-menu:focus-within .mega, .has-menu.mega-open .mega {
  opacity: 1; visibility: visible; transform: translateY(0); pointer-events: auto;
}
.mega-col { opacity: 0; transform: translateY(-6px); transition: opacity 0.28s ease, transform 0.28s ease; }
.has-menu:hover .mega-col, .has-menu:focus-within .mega-col, .has-menu.mega-open .mega-col { opacity: 1; transform: translateY(0); }
.mega-col:nth-child(2) { transition-delay: 0.04s; }
.mega-col:nth-child(3) { transition-delay: 0.08s; }
.mega-col:nth-child(4) { transition-delay: 0.12s; }
.mega-col:nth-child(5) { transition-delay: 0.16s; }
.mega-inner { max-width: 1280px; margin: 0 auto; display: flex; gap: 60px; flex-wrap: wrap; }
.mega-col h4 { font-family: 'Inter', sans-serif; font-size: 0.75rem; text-transform: none; color: var(--lavender); font-weight: 600; margin: 0 0 12px; }
.mega-col a { display: block; font-size: 0.95rem; color: var(--white); opacity: 0.9; padding: 5px 0; }
.mega-col a:hover { opacity: 1; text-decoration: underline; }
.mega-soon { color: var(--white); font-weight: 600; align-self: flex-start; margin-left: auto; }

/* ---------- Brand marquee ---------- */
/* Marquee: flex + fixed gap + natural (square) logos, sized like the original */
/* Padding (not margin) so the space around the logos is the band's own purple,
   not the black body background showing through a gap. Equal top and bottom:
   the logos are a fixed 60px tall, so symmetric padding centers them in the
   band wherever it sits in the page order. */
.brand-band { background: var(--lavender-band); overflow: hidden; padding: 14px 0; }
.brand-track { display: flex; gap: 44px; align-items: center; width: max-content; animation: scroll-left 34s linear infinite; }
.brand-item {
  display: flex; align-items: center; justify-content: center;
  flex: 0 0 auto; height: 60px; color: var(--black);
  font-weight: 700; font-size: 1.05rem; white-space: nowrap;
}
.brand-item img { height: 60px; width: auto; max-width: 140px; object-fit: contain; }

/* Text marquee (below the logos) */
.text-marquee { background: var(--lavender-band); overflow: hidden; padding: 6px 0 10px; }
.text-marquee-track { display: flex; gap: 60px; width: max-content; animation: scroll-left 30s linear infinite; }
.text-marquee-track span { font-family: 'Inter', sans-serif; font-style: italic; font-weight: 600; color: var(--white); font-size: 1.05rem; white-space: nowrap; }

/* Novedades section (replaces the old hero, on the purple background) */
.novedades { background: var(--purple-hero-1); padding: 34px 0 46px; }
.novedades-head { text-align: center; padding: 0 24px 4px; }
/* Matches the "Comprá por categoría" heading standard (.collections-head):
   weight 600, the same size, and the short accent rule underneath. The rule is
   white here rather than lavender because this section sits on the lavender
   band, where a lavender rule would be invisible. */
.novedades-head h2 { font-family: 'Inter', sans-serif; font-weight: 600; font-size: clamp(1.9rem, 3vw, 2.5rem); color: #fff; }
.novedades-head h2::after { content: ''; display: block; width: 44px; height: 2px; background: rgba(255, 255, 255, 0.6); margin: 14px auto 0; }
.novedades-head p { color: rgba(255, 255, 255, 0.9); font-family: 'Inter', sans-serif; font-style: italic; font-size: 1rem; margin: 14px 0 0; }
.novedades-wrap { position: relative; max-width: 1280px; margin: 20px auto 0; }
.novedades-row {
  padding: 6px 24px;
  display: flex; gap: 20px; overflow-x: auto; scroll-snap-type: x proximity; scroll-behavior: smooth;
  scrollbar-width: none; -ms-overflow-style: none;
  align-items: stretch; /* every card stretches to the same (tallest) height */
  cursor: grab; user-select: none; /* drag-to-scroll, like the category carousel */
  /* Match scroll-padding to the side padding so scroll-snap keeps the edge
     gutter (otherwise snapping the first card to "start" scrolls the padding
     out of view and the card sits flush against the screen edge). */
  scroll-padding-inline: 24px;
}
.novedades-row::-webkit-scrollbar { display: none; }
.novedades-row.dragging { cursor: grabbing; scroll-behavior: auto; scroll-snap-type: none; }
.novedades-row.dragging .card { pointer-events: none; }
/* Soft edge fades so a card being scrolled past the border melts into the
   purple background instead of getting hard-cut. Toggled by JS (more-left/
   more-right) so the first/last card isn't faded at the ends. */
.novedades-wrap::before, .novedades-wrap::after {
  content: ''; position: absolute; top: 0; bottom: 0; width: 46px; z-index: 4;
  pointer-events: none; opacity: 0; transition: opacity 0.25s ease;
}
.novedades-wrap::before { left: 0; background: linear-gradient(to right, var(--purple-hero-1), rgba(182, 162, 218, 0)); }
.novedades-wrap::after { right: 0; background: linear-gradient(to left, var(--purple-hero-1), rgba(182, 162, 218, 0)); }
.novedades-wrap.more-left::before { opacity: 1; }
.novedades-wrap.more-right::after { opacity: 1; }
/* min-width:0 stops a card from auto-growing to fit its image (kept the width
   exact so all cards are identical); height:auto lets align-items stretch them
   to one shared height. */
.novedades-row .card { flex: 0 0 210px; width: 210px; min-width: 0; height: auto; scroll-snap-align: start; }
/* Apple-style round scroll arrows */
.nov-arrow {
  position: absolute; top: 116px; transform: translateY(-50%); z-index: 6;
  width: 42px; height: 42px; border-radius: 50%; border: none;
  background: rgba(255, 255, 255, 0.85); color: #1a1420; cursor: pointer;
  box-shadow: 0 2px 12px rgba(43, 25, 48, 0.16);
  display: flex; align-items: center; justify-content: center; transition: background 0.15s ease;
}
.nov-arrow:hover { background: #fff; }
.nov-arrow:active { transform: translateY(-50%) scale(0.93); }
.nov-arrow svg { width: 20px; height: 20px; }
.nov-arrow.prev { left: 6px; }
.nov-arrow.next { right: 6px; }
@media (max-width: 640px) { .nov-arrow { display: none !important; } }
.novedades-empty { text-align: center; color: rgba(255, 255, 255, 0.92); font-size: 1.05rem; padding: 34px 24px 40px; }
/* Optional "see everything" link under the row, for when the row is a teaser
   rather than the whole list. Outlined rather than solid so it reads as a way
   out of the section, not as the primary action the product cards already are. */
.novedades-foot { display: flex; justify-content: center; margin-top: 26px; padding: 0 24px; }
.novedades-cta {
  display: inline-block; padding: 11px 28px; border-radius: 999px;
  border: 1.5px solid rgba(255, 255, 255, 0.75); color: #fff;
  font-weight: 600; font-size: 0.95rem;
  transition: background 0.18s ease, color 0.18s ease, transform 0.18s ease;
}
.novedades-cta:hover { background: #fff; color: #2b1930; transform: translateY(-1px); }
@media (max-width: 640px) { .novedades-row .card { flex-basis: 168px; width: 168px; } }
@keyframes scroll-left { from { transform: translateX(0); } to { transform: translateX(-50%); } }

/* ---------- Announcement slider (home hero) ---------- */
/* Full-bleed: it sits outside the 1280px content column on purpose, like the
   header and footer, so the art runs to both edges of the window. */
.hero-slider {
  position: relative; width: 100%; overflow: hidden; background: var(--black-soft);
  /* The band takes its height from its own width and --hero-ratio (set per
     store in the admin, default 2.56 = 2560x1000). Art exported at that same
     ratio therefore fills it exactly, with nothing cropped — a fixed height
     could not do that, because the band's shape changed with the window.
     min-height keeps the copy readable on a narrow window; max-height stops an
     ultrawide monitor turning the hero into a full-screen wall.
     Both clamps override the ratio while they bind, and art exported at the
     recommended size is then cropped (or letterboxed, in "whole image" mode) —
     which is why they are set as loosely as they can be. 82vh, not 78: at 78 the
     cap bound on an ordinary maximised 1920x1080 window, where the band wants
     ~79vh, so the single most common desktop size cropped the art for no reason.
     Now only a genuinely ultrawide-and-short window trips it. Same for 280px
     instead of 320: at 2.56 the floor only bites below a 717px-wide window, a
     sliver above the 700px mobile breakpoint, rather than 120px of it. */
  aspect-ratio: var(--hero-ratio, 2.56);
  min-height: 280px;
  max-height: 82vh;
}
.hero-track {
  display: flex; height: 100%; width: 100%;
  transition: transform 0.6s cubic-bezier(0.4, 0, 0.2, 1);
  /* Deliberately NOT will-change: transform. It was tried, and it made the whole
     Inicio page slower rather than faster — the track is the full row of slides
     (five full-bleed images wide), so promoting it permanently holds a texture of
     slides × band size, and on a browser that is short of GPU memory or running
     without hardware acceleration that trades a 600ms transition for a page-long
     tax. The transition already gets composited for its own duration; that is
     enough. Anything promoted here has to earn it with a measurement. */
}
/* While a finger or the mouse is on the slide the track follows it 1:1 —
   animating during a drag would fight the gesture. */
.hero-track.dragging { transition: none; }
/* Grab cursor only when there is somewhere to drag to. */
.hero-slider:not(.single) .hero-slide { cursor: grab; }
.hero-slider .hero-track.dragging, .hero-slider .hero-track.dragging .hero-slide { cursor: grabbing; }
/* Vertical scrolling still belongs to the page; horizontal gestures are ours. */
.hero-slider { touch-action: pan-y; }
@media (prefers-reduced-motion: reduce) { .hero-track { transition: none; } }
.hero-slide {
  position: relative; flex: 0 0 100%; height: 100%; display: block;
  /* Slides are stacked in one row and moved by translating the track; the
     inactive ones stay in the DOM so their images are already decoded. */
  overflow: hidden;
}
.hero-art { position: absolute; inset: 0; display: block; }
.hero-art img { width: 100%; height: 100%; object-fit: cover; object-position: center; }
/* "Whole image" mode: never crop, even when the art's shape differs from the
   band's. The gap that leaves is filled by the blurred backdrop below. */
.hero-slide.fit-contain .hero-art img { object-fit: contain; }
.hero-art-blur {
  position: absolute; inset: 0; z-index: 0;
  background-size: cover; background-position: center;
  /* Scaled up so the blur's soft edges are pushed outside the band.
     No translateZ here either, for the same reason as the track: this element is
     full-bleed and carries a 26px blur, so pinning one per slide to its own layer
     is the most expensive thing on the page to hold open. It is the heaviest thing
     here even unpromoted — a slide only needs it in "whole image" mode, so art
     exported at the recommended size (which turns that mode off) skips it. */
  transform: scale(1.15); filter: blur(26px) saturate(1.2); opacity: 0.85;
}
/* Readability scrim, strongest behind the copy and clear on the far side, so a
   product photo isn't uniformly muddied just to carry a few words of text. */
.hero-scrim { position: absolute; inset: 0; pointer-events: none; }
.hero-slide.theme-light .hero-scrim { background: linear-gradient(90deg, rgba(8,7,12,var(--hero-overlay)) 0%, rgba(8,7,12,calc(var(--hero-overlay) * 0.15)) 65%); }
.hero-slide.theme-dark  .hero-scrim { background: linear-gradient(90deg, rgba(255,255,255,var(--hero-overlay)) 0%, rgba(255,255,255,calc(var(--hero-overlay) * 0.15)) 65%); }
.hero-slide.align-right .hero-scrim { transform: scaleX(-1); }
.hero-slide.align-center .hero-scrim { transform: none; }
.hero-slide.align-center.theme-light .hero-scrim { background: radial-gradient(ellipse at center, rgba(8,7,12,var(--hero-overlay)) 0%, rgba(8,7,12,calc(var(--hero-overlay) * 0.25)) 75%); }
.hero-slide.align-center.theme-dark  .hero-scrim { background: radial-gradient(ellipse at center, rgba(255,255,255,var(--hero-overlay)) 0%, rgba(255,255,255,calc(var(--hero-overlay) * 0.25)) 75%); }

.hero-copy {
  position: absolute; inset: 0; z-index: 2;
  display: flex; flex-direction: column; justify-content: center;
  /* Without this the column stretches its children, and the badge pill and CTA
     button widen to the whole copy panel instead of hugging their own text.
     The right/center variants override it below. */
  align-items: flex-start;
  gap: 14px; padding: clamp(28px, 5vw, 72px);
  /* Never let a long headline run the full width of a 2560px monitor. */
  max-width: min(560px, 46%);
}
.hero-slide.align-right .hero-copy { left: auto; right: 0; align-items: flex-end; text-align: right; }
.hero-slide.align-center .hero-copy { left: 50%; transform: translateX(-50%); align-items: center; text-align: center; max-width: min(720px, 82%); }
.hero-slide.theme-light .hero-copy { color: #fff; }
.hero-slide.theme-dark  .hero-copy { color: #14121a; }
.hero-badge {
  display: inline-block; padding: 5px 12px; border-radius: 999px;
  background: var(--lavender); color: #fff;
  font-size: 0.74rem; font-weight: 600; letter-spacing: 0.08em; text-transform: uppercase;
}
.hero-slide.theme-dark .hero-badge { background: #14121a; }
.hero-title { font-size: clamp(1.7rem, 3.6vw, 3.4rem); font-weight: 600; line-height: 1.08; letter-spacing: -0.01em; }
.hero-sub { margin: 0; font-size: clamp(0.95rem, 1.3vw, 1.25rem); line-height: 1.45; opacity: 0.92; }
.hero-cta {
  display: inline-block; margin-top: 6px; padding: 12px 26px; border-radius: 999px;
  background: var(--mint); color: var(--mint-text); font-weight: 600; font-size: 0.95rem;
  transition: transform 0.15s ease, box-shadow 0.15s ease;
}
a.hero-slide:hover .hero-cta { transform: translateY(-1px); box-shadow: 0 6px 20px rgba(0,0,0,0.28); }

/* Same round-glass arrows as the Novedades row, scaled up for a full-bleed band. */
.hero-arrow {
  position: absolute; top: 50%; transform: translateY(-50%); z-index: 6;
  width: 46px; height: 46px; border-radius: 50%; border: none;
  background: rgba(255, 255, 255, 0.82); color: #1a1420; cursor: pointer;
  box-shadow: 0 2px 14px rgba(0, 0, 0, 0.26);
  display: flex; align-items: center; justify-content: center;
  opacity: 0; transition: opacity 0.2s ease, background 0.15s ease;
}
/* Hidden until the band is hovered or an arrow is keyboard-focused, so the art
   is unobstructed at rest but the controls are still reachable without a mouse. */
.hero-slider:hover .hero-arrow, .hero-arrow:focus-visible { opacity: 1; }
.hero-arrow:hover { background: #fff; }
.hero-arrow svg { width: 22px; height: 22px; }
.hero-arrow.prev { left: 14px; }
.hero-arrow.next { right: 14px; }

.hero-controls {
  position: absolute; z-index: 6; left: 50%; transform: translateX(-50%);
  bottom: 16px; display: flex; align-items: center; gap: 9px;
  padding: 4px 9px; border-radius: 999px;
  /* Slightly more opaque than it was, because there is no longer a blur behind
     it: a backdrop-filter sitting on top of the animating track had to re-blur
     the artwork moving underneath it on every frame of every slide change, which
     is a lot of work for a pill this size. Flat translucent black reads the same
     over art this dark. */
  background: rgba(10, 9, 14, 0.55);
}
.hero-dots { display: flex; align-items: center; gap: 7px; }
.hero-dot {
  position: relative;
  width: 7px; height: 7px; padding: 0; border: none; border-radius: 50%; cursor: pointer;
  background: rgba(255, 255, 255, 0.45); transition: background 0.2s ease, transform 0.2s ease;
}
/* The dot is now too small to hit reliably, so each one carries an invisible
   target around itself covering the dot plus the gap beside it. */
.hero-dot::after { content: ''; position: absolute; inset: -5px; border-radius: 50%; }
.hero-dot:hover { background: rgba(255, 255, 255, 0.75); }
.hero-dot.active { background: #fff; transform: scale(1.3); }
.hero-play {
  width: 18px; height: 18px; padding: 0; border: none; background: none; cursor: pointer;
  color: #fff; display: flex; align-items: center; justify-content: center;
}
.hero-play svg { width: 11px; height: 11px; }
/* One icon at a time: pause while running, play once the user has paused it. */
.hero-play .ico-play { display: none; }
.hero-slider.paused .hero-play .ico-pause { display: none; }
.hero-slider.paused .hero-play .ico-play { display: block; }

@media (max-width: 700px) {
  /* 4:5 portrait, matching the 1200x1500 mobile crop the admin recommends, so
     that image fills the band uncropped the same way the desktop one does.
     max-height keeps the hero from swallowing a tall phone screen whole. */
  .hero-slider { aspect-ratio: 4 / 5; min-height: 380px; max-height: 80vh; }
  /* Copy moves to a full-width band at the bottom: on a portrait screen there
     is no room for a side column, and the art stays visible above it. */
  .hero-slide .hero-copy,
  .hero-slide.align-right .hero-copy,
  .hero-slide.align-center .hero-copy {
    inset: auto 0 0 0; transform: none; max-width: 100%;
    align-items: flex-start; text-align: left;
    padding: 24px 20px 62px; gap: 10px;
  }
  .hero-slide.theme-light .hero-scrim,
  .hero-slide.align-right.theme-light .hero-scrim,
  .hero-slide.align-center.theme-light .hero-scrim {
    transform: none;
    background: linear-gradient(0deg, rgba(8,7,12,calc(var(--hero-overlay) + 0.35)) 0%, rgba(8,7,12,var(--hero-overlay)) 38%, rgba(8,7,12,0) 78%);
  }
  .hero-slide.theme-dark .hero-scrim,
  .hero-slide.align-right.theme-dark .hero-scrim,
  .hero-slide.align-center.theme-dark .hero-scrim {
    transform: none;
    background: linear-gradient(0deg, rgba(255,255,255,calc(var(--hero-overlay) + 0.35)) 0%, rgba(255,255,255,var(--hero-overlay)) 38%, rgba(255,255,255,0) 78%);
  }
  .hero-arrow { display: none; }
  .hero-controls { bottom: 12px; left: 20px; transform: none; }
}

/* ---------- Hero ---------- */
.hero {
  background: linear-gradient(180deg, var(--purple-hero-1) 0%, var(--purple-hero-2) 100%);
  padding: 90px 24px 120px; text-align: center;
}
.hero h1 { font-size: clamp(2.4rem, 6vw, 4.2rem); font-weight: 400; color: var(--white); letter-spacing: 0.01em; }
.hero .rule { width: min(520px, 70%); height: 2px; background: rgba(255,255,255,0.7); margin: 22px auto 18px; }
.hero .sub { font-family: 'Inter', sans-serif; font-style: italic; color: var(--white); font-size: 1rem; opacity: 0.95; }

/* ---------- Custom home sections (admin-created bands) ---------- */
/* Full-bleed like the other home bands: the colour runs to both edges of the
   window and only the copy is held to the 1280px column. */
.home-block { position: relative; width: 100%; overflow: hidden; }
.home-block.bg-oscuro { background: var(--black); color: var(--white); }
.home-block.bg-lavanda { background: var(--lavender-band); color: #1d1526; }
.home-block.bg-blanco { background: #fff; color: #1d1526; }
.hb-inner {
  position: relative; z-index: 2;
  max-width: 1280px; margin: 0 auto;
  padding: clamp(44px, 6vw, 84px) clamp(16px, 4vw, 64px);
}
.hb-copy { display: flex; flex-direction: column; align-items: flex-start; gap: 14px; }
.hb-title { font-size: clamp(1.7rem, 3vw, 2.5rem); font-weight: 600; line-height: 1.15; }
.hb-sub { margin: 0; font-size: clamp(1rem, 1.3vw, 1.15rem); opacity: 0.85; }
.hb-body { font-size: 1rem; line-height: 1.65; opacity: 0.9; max-width: 68ch; }
.hb-body p { margin: 0 0 0.85em; }
.hb-body p:last-child { margin-bottom: 0; }
.hb-body ul, .hb-body ol { margin: 0 0 0.85em; padding-left: 1.3em; }
.hb-body a { text-decoration: underline; text-underline-offset: 3px; }
.hb-btn {
  display: inline-block; margin-top: 6px; padding: 12px 26px; border-radius: 999px;
  background: var(--mint); color: var(--mint-text); font-weight: 600; font-size: 0.95rem;
  transition: transform 0.15s ease, box-shadow 0.15s ease;
}
.hb-btn:hover { transform: translateY(-1px); box-shadow: 0 6px 20px rgba(0, 0, 0, 0.22); }

/* Copy-only: centred and held narrow, which is what makes a text band read as
   deliberate rather than as a paragraph that lost its picture. */
.home-block.layout-text .hb-copy { align-items: center; text-align: center; max-width: 74ch; margin: 0 auto; }
.home-block.layout-text .hb-body { text-align: left; }

/* Photo behind the copy. Always light text: the scrim below is what guarantees
   it stays readable, so the band's own colour choice does not apply here. */
.home-block.layout-banner { color: var(--white); }
.home-block.layout-banner .hb-art { position: absolute; inset: 0; background-size: cover; background-position: center; }
.home-block.layout-banner .hb-scrim { position: absolute; inset: 0; background: linear-gradient(90deg, rgba(8,7,12,0.82) 0%, rgba(8,7,12,0.45) 55%, rgba(8,7,12,0.25) 100%); }
.home-block.layout-banner .hb-inner { padding-block: clamp(64px, 9vw, 132px); }
.home-block.layout-banner .hb-copy { max-width: 56ch; }

/* Picture beside the copy. minmax(0,1fr) rather than 1fr so a wide image cannot
   push its column past half the row. */
.home-block.layout-split-left .hb-inner,
.home-block.layout-split-right .hb-inner {
  display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  gap: clamp(24px, 4vw, 56px); align-items: center;
}
.home-block.layout-split-right .hb-media { order: 2; }
.hb-media img { width: 100%; height: auto; border-radius: 16px; display: block; }

@media (max-width: 820px) {
  /* One column on a phone, picture first: the image introduces the copy rather
     than sitting under a call to action that has already asked for the tap. */
  .home-block.layout-split-left .hb-inner,
  .home-block.layout-split-right .hb-inner { grid-template-columns: 1fr; }
  .home-block.layout-split-right .hb-media { order: 0; }
  .home-block.layout-banner .hb-scrim { background: linear-gradient(0deg, rgba(8,7,12,0.88) 0%, rgba(8,7,12,0.6) 55%, rgba(8,7,12,0.35) 100%); }
}

/* ---------- Promo blocks ---------- */
.promos { background: var(--black); padding: 64px clamp(16px, 4vw, 64px) 84px; }
.promos-head { text-align: center; margin-bottom: 40px; }
.promos-head h2 { font-size: clamp(1.9rem, 3vw, 2.5rem); color: var(--white); }
.promos-head h2::after { content: ''; display: block; width: 44px; height: 2px; background: var(--lavender); margin: 14px auto 0; }
.promos-head p { color: var(--ink-muted); font-size: 1rem; margin: 14px 0 0; }
.promos-wrap { position: relative; max-width: 1280px; margin: 0 auto; }
.promos-track {
  display: flex; gap: 24px; overflow-x: auto; scroll-behavior: smooth;
  scroll-snap-type: x proximity; padding: 6px 2px;
  scrollbar-width: none; -ms-overflow-style: none;
  cursor: grab; user-select: none;
}
.promos-track::-webkit-scrollbar { display: none; }
.promos-track.dragging { cursor: grabbing; scroll-behavior: auto; scroll-snap-type: none; }
.promos-track.dragging .promo-card { pointer-events: none; }
.promo-card {
  flex: 0 0 calc((100% - 72px) / 4); scroll-snap-align: start;
  position: relative; display: block; min-height: 440px; border-radius: 18px; overflow: hidden;
  border: 1px solid rgba(255, 255, 255, 0.07); background: #14141a; isolation: isolate;
  transition: transform 0.3s ease, border-color 0.3s ease, box-shadow 0.3s ease;
}
.promo-card-img {
  position: absolute; inset: 0; -webkit-user-drag: none;
  background-size: cover; background-position: center; background-repeat: no-repeat;
  transition: transform 0.6s cubic-bezier(0.16, 0.8, 0.3, 1);
}
.promo-card::after {
  content: ''; position: absolute; inset: 0;
  background: linear-gradient(to top, rgba(11,11,13,0.92) 0%, rgba(11,11,13,0.55) 34%, rgba(11,11,13,0.05) 66%);
}
.promo-card-copy {
  position: relative; z-index: 2; height: 100%;
  display: flex; flex-direction: column; align-items: flex-start; justify-content: flex-end;
  gap: 12px; padding: 38px;
}
.promo-card-copy h2 { font-style: normal; font-size: clamp(1.7rem, 2.2vw, 2.1rem); color: var(--white); }
/* Always exactly two lines tall (1rem text at line-height 1.5), whatever the
   subtitle says. The copy block is bottom-anchored, so the subtitle's height is
   what decides where the title starts: one that fitted on a single line left its
   title a full line below its neighbours' -- "Cuadros" sat 24px under "Figuras"
   and "Singles" -- and on a narrower card a long one wrapped to three and threw
   the row out the other way.
   min-height covers the short case, the clamp covers the long one, and the <p>
   is rendered even when empty so a block with no subtitle lines up too. Two
   rather than three keeps the titles where they already sit on a wide screen;
   the cost is that a long subtitle ends in an ellipsis once the cards get
   narrow, which is the point at which it would not have fitted anyway. */
.promo-card-copy p {
  color: var(--ink-muted); font-size: 1rem; margin: 0; max-width: 34ch;
  min-height: 3em;
  display: -webkit-box; -webkit-box-orient: vertical; -webkit-line-clamp: 2; line-clamp: 2;
  overflow: hidden;
}
.promo-card-copy .btn-mint { margin-top: 6px; transition: transform 0.25s ease, filter 0.15s ease; }
.promo-card:hover { transform: translateY(-4px); border-color: rgba(169, 155, 232, 0.55); box-shadow: 0 18px 40px rgba(0, 0, 0, 0.45); }
.promo-card:hover .promo-card-img { transform: scale(1.06); }
.promo-card:hover .btn-mint { transform: translateY(-2px); }
/* Atmospheric variant: product photo floated on a branded lavender gradient.
   multiply drops the photo's white backdrop into the gradient so it feels ambient. */
.promo-card.atmos {
  background: radial-gradient(125% 100% at 50% 16%, #f2ecff 0%, #ddd2f4 38%, #bcaae2 72%, #9b88d0 100%);
}
.promo-card.atmos .promo-card-img {
  background-size: cover; background-position: center;
  mix-blend-mode: normal; transform-origin: center;
}
.promo-card.atmos::after {
  background: linear-gradient(to top, rgba(11,11,13,0.92) 0%, rgba(11,11,13,0.55) 34%, rgba(11,11,13,0.05) 66%);
}
/* No-image variant (e.g. "coming soon"): moody dark brand gradient */
.promo-card.no-img {
  background:
    radial-gradient(120% 90% at 50% 20%, rgba(169,155,232,0.30), rgba(169,155,232,0) 62%),
    linear-gradient(160deg, #1c1730 0%, #100d1a 72%);
}
.promo-card.no-img::after { background: none; }
/* Corner badge */
.promo-badge {
  position: absolute; top: 18px; left: 18px; z-index: 3;
  background: var(--lavender); color: #211a33;
  font-size: 0.72rem; font-weight: 600; letter-spacing: 0.05em; text-transform: uppercase;
  padding: 5px 11px; border-radius: 999px;
}
/* Carousel arrows — same round standard as .nov-arrow / .related-arrow */
.promo-arrow {
  position: absolute; top: 50%; transform: translateY(-50%); z-index: 6;
  width: 42px; height: 42px; padding: 0; border-radius: 50%; border: none;
  background: rgba(255, 255, 255, 0.85); color: #1a1420; cursor: pointer;
  box-shadow: 0 2px 12px rgba(43, 25, 48, 0.16);
  display: flex; align-items: center; justify-content: center; transition: background 0.15s ease;
}
.promo-arrow:hover { background: #fff; }
.promo-arrow:active { transform: translateY(-50%) scale(0.93); }
.promo-arrow svg { width: 20px; height: 20px; display: block; }
.promo-arrow.prev { left: 8px; }
.promo-arrow.next { right: 8px; }
/* 2-up on tablet; on phones each card fills the screen and snaps one-per-view */
@media (max-width: 980px) { .promo-card { flex-basis: calc((100% - 24px) / 2); } }
@media (max-width: 640px) {
  .promos-track { scroll-snap-type: x mandatory; }
  .promo-card { flex-basis: 100%; min-height: 380px; scroll-snap-align: center; }
}
.btn-mint {
  display: inline-block; background: var(--mint); color: var(--mint-text);
  padding: 12px 30px; border-radius: 999px; font-weight: 500; font-size: 0.9rem;
}
.btn-mint:hover { filter: brightness(0.95); }

/* ---------- Comprá por categoría (collections grid) ---------- */
.collections { background: var(--black-soft); padding: 60px clamp(16px, 4vw, 64px) 76px; }
.collections-head { text-align: center; margin-bottom: 36px; }
.collections-head h2 { font-size: clamp(1.9rem, 3vw, 2.5rem); color: var(--white); }
.collections-head h2::after { content: ''; display: block; width: 44px; height: 2px; background: var(--lavender); margin: 14px auto 0; }
.collections-head p { color: var(--ink-muted); font-size: 1rem; margin: 14px 0 0; font-style: italic; }
.collections-grid {
  max-width: 1280px; margin: 0 auto;
  display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); gap: 18px;
}
.collection-card {
  position: relative; display: flex; align-items: flex-end;
  aspect-ratio: 4 / 3; border-radius: var(--radius); overflow: hidden;
  background: linear-gradient(135deg, var(--purple-hero-1), var(--black));
  border: 1px solid #26262b; text-decoration: none;
  transition: transform 0.25s ease, border-color 0.2s ease, box-shadow 0.25s ease;
}
.collection-img {
  position: absolute; inset: 0; background-size: cover; background-position: center;
  transition: transform 0.4s ease;
}
.collection-card::after {
  content: ''; position: absolute; inset: 0;
  background: linear-gradient(180deg, rgba(11,11,13,0) 40%, rgba(11,11,13,0.82) 100%);
}
.collection-name {
  position: relative; z-index: 1; width: 100%;
  padding: 16px 18px; color: var(--white); font-weight: 600; font-size: 1.1rem;
}
.collection-card.no-img { align-items: center; justify-content: center; text-align: center; }
.collection-card.no-img::after { display: none; }
.collection-card.no-img .collection-name { text-align: center; font-size: 1.15rem; }
.collection-card:hover { transform: translateY(-4px); border-color: rgba(169, 155, 232, 0.55); box-shadow: 0 18px 40px rgba(0, 0, 0, 0.45); }
.collection-card:hover .collection-img { transform: scale(1.06); }
@media (max-width: 520px) { .collections-grid { grid-template-columns: repeat(2, 1fr); gap: 12px; } }

/* ---------- Bottom marquee ---------- */
/* color is the default text colour of the marquee; the band is now transparent
   over the dark aurora, so it must be light. The admin can override it per store
   via an inline `color` on the band (Configuración → Inicio → Cinta inferior);
   the span inherits so that override wins. */
.bottom-band { background: var(--lavender-band); overflow: hidden; padding: 9px 0; color: var(--white); }
.bottom-track { display: flex; gap: 60px; width: max-content; animation: scroll-left 26s linear infinite; }
.bottom-track span { color: inherit; font-size: 0.82rem; white-space: nowrap; font-style: italic; }

/* ---------- Collection / product-listing page (white) ---------- */
/* Light pages: keep the canvas white so the fade-in never reveals the dark body */
body.light-page { background: var(--white); }

/* Smooth page-enter animation (categories, products, pages, cart) */
@keyframes pageEnter {
  from { opacity: 0; transform: translateY(14px); }
  to { opacity: 1; transform: translateY(0); }
}
.collection-page, .product-detail, .related, .page-card, .cart-wrap, .promos, .novedades-wrap {
  animation: pageEnter 0.4s cubic-bezier(0.16, 0.8, 0.3, 1) both;
}
.related { animation-delay: 0.06s; }
.promos { animation-delay: 0.1s; }
/* Fade in the Novedades cards (the content, not the purple section — same
   reason as the hero: avoid a dark flash of the body behind it). */
.novedades-wrap { animation-delay: 0.05s; }
/* Hero: keep the purple background visible instantly and animate only its content,
   so there is no dark flash of the black body behind it while it fades in. */
.hero h1, .hero .rule, .hero .sub {
  animation: pageEnter 0.45s cubic-bezier(0.16, 0.8, 0.3, 1) both;
}
.hero .rule { animation-delay: 0.08s; }
.hero .sub { animation-delay: 0.15s; }
@media (prefers-reduced-motion: reduce) {
  .collection-page, .product-detail, .related, .page-content, .cart-wrap, .promos, .novedades-wrap,
  .hero h1, .hero .rule, .hero .sub { animation: none; }
}

.collection-page { background: var(--white); color: var(--black); min-height: 60vh; }
.collection-head { max-width: 1280px; margin: 0 auto; padding: 40px 24px 8px; }
.collection-head h1 { font-family: 'Inter', sans-serif; font-style: normal; font-size: 2.6rem; color: #0B0B0D; font-weight: 400; letter-spacing: 0.01em; }
.collection-head p { color: #555; margin: 6px 0 0; }
.collection-toolbar {
  max-width: 1280px; margin: 0 auto; padding: 18px 24px; display: flex; justify-content: space-between;
  align-items: center; font-size: 0.85rem; color: #444; border-bottom: 1px solid #eee;
}
.cat-jump { max-width: 1280px; margin: 0 auto; padding: 18px 24px 0; }
.cat-jump-label {
  display: block; color: #9a92a8; font-weight: 700; font-size: 0.72rem;
  text-transform: uppercase; letter-spacing: 0.06em; margin: 0 0 10px;
}
.cat-jump-row { display: flex; flex-wrap: wrap; gap: 9px; }
.cat-chip {
  flex: 0 0 auto; display: inline-flex; align-items: center; gap: 8px;
  background: #fff; border: 1px solid #e7e3ef; color: #2a2433;
  padding: 8px 9px 8px 15px; border-radius: 999px; font-weight: 600; font-size: 0.85rem;
  white-space: nowrap; transition: border-color 0.15s ease, box-shadow 0.15s ease, transform 0.15s ease;
}
.cat-chip:hover { border-color: var(--lavender); box-shadow: 0 4px 14px rgba(169,155,232,0.22); transform: translateY(-1px); }
.cat-chip .cc-count {
  background: #efe9fb; color: #6a4ea0; border-radius: 999px;
  min-width: 22px; text-align: center; padding: 2px 7px; font-size: 0.72rem; font-weight: 800;
}
/* Sections with nothing available are de-emphasized instead of adding noise */
.cat-chip.is-empty { color: #b3aec0; background: #fafafb; border-color: #eeebf3; }
.cat-chip.is-empty .cc-count { background: #f0eff3; color: #b3aec0; }

@media (max-width: 640px) {
  /* Single swipeable row instead of a ragged wrap; scroll-padding keeps the
     first/last chip off the screen edge. */
  .cat-jump { padding: 14px 0 2px; }
  .cat-jump-label { padding: 0 16px; }
  .cat-jump-row {
    flex-wrap: nowrap; overflow-x: auto; scroll-snap-type: x proximity;
    scrollbar-width: none; -ms-overflow-style: none;
    padding: 0 16px 4px; scroll-padding-inline: 16px;
  }
  .cat-jump-row::-webkit-scrollbar { display: none; }
  .cat-chip { scroll-snap-align: start; }
}

.availability-banner {
  max-width: 1280px; margin: 18px auto 0; padding: 14px 24px; border-radius: 10px;
  background: linear-gradient(90deg, var(--lavender) 0%, var(--purple-hero-2) 100%);
  color: #fff; display: flex; justify-content: space-between; align-items: center;
  font-weight: 600; font-size: 0.95rem;
}

.collection-toolbar .filters { display: flex; gap: 10px; }
.toolbar-right { display: flex; align-items: center; gap: 16px; }

/* Custom filter dropdowns */
.filter-dd { position: relative; }
.filter-trigger {
  display: inline-flex; align-items: center; gap: 6px; background: #fff; border: 1px solid #e2dce8;
  border-radius: 999px; padding: 7px 14px; font: inherit; font-size: 0.82rem; font-weight: 600; color: #333;
  cursor: pointer; transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.filter-trigger:hover { border-color: var(--lavender); }
.filter-dd.open .filter-trigger { border-color: var(--lavender); box-shadow: 0 0 0 3px rgba(169,155,232,0.18); }
.filter-trigger .caret { font-size: 0.75rem; transition: transform 0.2s ease; }
.filter-dd.open .filter-trigger .caret { transform: rotate(180deg); }
.filter-panel {
  position: absolute; top: calc(100% + 8px); left: 0; z-index: 40; min-width: 210px;
  background: #fff; border: 1px solid #ece7f1; border-radius: 12px; box-shadow: 0 10px 30px rgba(43,25,48,0.14);
  padding: 10px; transform: translateY(-6px);
  /* display:none (not just visibility) so the closed panel — which is wider than
     its trigger — doesn't reserve layout width and push the page wider than the
     viewport (that overflow let iOS zoom out into blank space). */
  display: none; opacity: 0;
  transition: opacity 0.16s ease, transform 0.16s ease;
}
.filter-dd.open .filter-panel { display: block; opacity: 1; transform: translateY(0); }
.toolbar-right .filter-panel { left: auto; right: 0; }

.filter-check { display: flex; align-items: center; gap: 10px; padding: 9px 10px; border-radius: 8px; font-size: 0.88rem; color: #333; cursor: pointer; white-space: nowrap; }
.filter-check:hover { background: #f6f2fa; }
.filter-check input { position: absolute; opacity: 0; width: 0; height: 0; }
.fc-box { width: 18px; height: 18px; border: 2px solid #cfc6dc; border-radius: 5px; flex-shrink: 0; position: relative; transition: background 0.15s ease, border-color 0.15s ease; }
.filter-check input:checked + .fc-box { background: var(--lavender); border-color: var(--lavender); }
.filter-check input:checked + .fc-box::after { content: ''; position: absolute; left: 5px; top: 1px; width: 5px; height: 10px; border: solid #fff; border-width: 0 2px 2px 0; transform: rotate(45deg); }

.price-panel { min-width: 300px; }
.price-range { display: flex; align-items: center; gap: 8px; }
.price-input { display: flex; align-items: center; border: 1px solid #ddd; border-radius: 8px; overflow: hidden; flex: 1; }
.price-input span { padding: 0 8px; color: #999; font-size: 0.85rem; }
.price-input input { width: 100%; border: none; padding: 8px 6px 8px 0; font: inherit; font-size: 0.85rem; outline: none; }
.price-input:focus-within { border-color: var(--lavender); }
.price-sep { color: #999; font-size: 0.85rem; }
.price-actions { display: flex; justify-content: space-between; margin-top: 12px; }
.price-clear { background: none; border: none; color: #999; font-size: 0.82rem; font-weight: 600; cursor: pointer; }
.price-clear:hover { color: #333; }
.price-apply { background: var(--black); color: #fff; border: none; border-radius: 8px; padding: 7px 18px; font-size: 0.82rem; font-weight: 700; cursor: pointer; }
.price-apply:hover { background: var(--lavender); color: var(--black); }

.sort-panel { min-width: 220px; }
.sort-opt { display: block; width: 100%; text-align: left; background: none; border: none; padding: 9px 10px; border-radius: 8px; font-size: 0.86rem; color: #333; cursor: pointer; }
.sort-opt:hover { background: #f6f2fa; }
.sort-opt.active { color: var(--mint-text); font-weight: 700; }

.view-toggle { display: flex; gap: 4px; }
.view-btn { display: inline-flex; align-items: center; justify-content: center; width: 34px; height: 34px; border: 1px solid #e2dce8; border-radius: 8px; background: #fff; color: #b3aac2; cursor: pointer; }
.view-btn svg { width: 18px; height: 18px; }
.view-btn:hover { color: #666; }
.view-btn.active { color: var(--black); border-color: var(--lavender); }
.grid.view-large { grid-template-columns: repeat(auto-fill, minmax(280px, 1fr)); gap: 34px 24px; }
@media (max-width: 640px) { .grid.view-large { grid-template-columns: 1fr; } }
.grid {
  max-width: 1280px; margin: 0 auto; padding: 28px 24px 70px;
  display: grid; grid-template-columns: repeat(auto-fill, minmax(200px, 1fr)); gap: 28px 20px;
  grid-auto-rows: 1fr; /* every row equal height -> all product cards the same size */
}
.card {
  background: #fff; border: 1px solid #ececf0; border-radius: 14px; padding: 10px;
  position: relative; display: flex; flex-direction: column; height: 100%; min-width: 0;
  transition: transform 0.18s ease, box-shadow 0.18s ease, border-color 0.18s ease;
}
.card:hover { transform: translateY(-4px); box-shadow: 0 14px 30px rgba(43, 25, 48, 0.13); border-color: #ddd5ea; }
.card-img {
  aspect-ratio: 1 / 1; background: #f7f5fa; border-radius: 10px; overflow: hidden;
  position: relative; display: flex; align-items: center; justify-content: center;
}
.card-img img { width: 100%; height: 100%; object-fit: contain; mix-blend-mode: multiply; transition: transform 0.28s ease; }
.card:hover .card-img img { transform: scale(1.05); }

/* Quick add-to-cart button (appears on hover, Shopify-style) */
.card-add {
  position: absolute; right: 8px; bottom: 8px; z-index: 3;
  display: flex; align-items: center; gap: 6px;
  background: var(--black); color: #fff; border: none; cursor: pointer;
  padding: 8px 14px; border-radius: 999px; font-size: 0.78rem; font-weight: 600;
  opacity: 0; transform: translateY(8px); transition: opacity 0.18s ease, transform 0.18s ease;
}
.card:hover .card-add { opacity: 1; transform: translateY(0); }
.card-add:hover { background: var(--lavender); color: var(--black); }
/* Nothing in store and nothing on the way: the tile still shows the control so
   the grid doesn't shuffle on hover, but it reads as unavailable and does
   nothing. The "Agotado" pill under the name is what carries the news. */
.card-add:disabled { background: #d9d5dd; color: #6f6a75; cursor: not-allowed; }
.card-add:disabled:hover { background: #d9d5dd; color: #6f6a75; }
.card-add svg { width: 15px; height: 15px; stroke: currentColor; fill: none; stroke-width: 1.8; }
/* Touch devices: the quick-add button is always visible, so show it as a
   compact round cart-icon button (no "Agregar" label) to keep it off the art. */
@media (hover: none) {
  .card-add { opacity: 1; transform: none; gap: 0; padding: 10px; border-radius: 50%; }
  .card-add .ca-label { display: none; }
}
.badge-out {
  position: absolute; top: 8px; left: 8px; background: #ececec; color: #333;
  font-size: 0.72rem; padding: 3px 9px; border-radius: 4px; z-index: 2;
}
.badge-soon {
  position: absolute; top: 8px; left: 8px; background: var(--lavender); color: #fff;
  font-size: 0.72rem; padding: 3px 9px; border-radius: 4px; z-index: 2; font-weight: 600;
}
.card-body { padding: 12px 4px 4px; display: flex; flex-direction: column; gap: 7px; flex: 1 1 auto; }
.card-name {
  font-size: 0.9rem; font-weight: 600; color: #1a1a1a; line-height: 1.3;
  display: -webkit-box; -webkit-line-clamp: 2; line-clamp: 2; -webkit-box-orient: vertical;
  overflow: hidden; min-height: 2.35rem;
}
.card-name:hover { text-decoration: underline; }
.card-avail { display: flex; flex-wrap: wrap; gap: 6px; min-height: 24px; }
/* white-space:normal lets the long "en camino · fecha" transit badge wrap
   inside narrow cards instead of spilling past the card edge. */
.avail { display: inline-flex; align-items: center; gap: 4px; font-size: 0.7rem; font-weight: 700; padding: 3px 8px; border-radius: 6px; white-space: normal; max-width: 100%; }
.avail-in { background: #E7F7EF; color: #1E7A50; }
.avail-low { background: #FFF1DF; color: #B9711A; }
.avail-out { background: #F0F0F3; color: #8a8a94; }
.avail-soon { background: #EDE7F6; color: #6a4ea0; }
.avail-transit { background: #EAF1FB; color: #3d6bb0; }
.avail-eta { background: #EEF1F6; color: #5b6673; }
.price { display: block; margin-top: auto; font-size: 1rem; font-weight: 700; color: #111; }
.price-compare { color: #999; text-decoration: line-through; margin-left: 6px; font-size: 0.82rem; font-weight: 400; }
/* "Desde" on a product whose subproducts don't all cost the same. Deliberately
   quieter than the number it qualifies. */
.price-from { font-size: 0.72rem; font-weight: 600; color: #8a8595; text-transform: uppercase; letter-spacing: 0.04em; }
.price-sub { font-size: 0.68rem; color: #b0aab8; margin-top: -3px; }

.empty-state { max-width: 1280px; margin: 0 auto; padding: 80px 24px; text-align: center; color: #777; }

/* ---------- Contact page ---------- */
/* The title sat in the 1280px column while the form was centered in 600px, so
   below ~1330px the two had different left edges and the heading floated off on
   its own. One column for the whole page instead, at the cart's 1080px. */
.contact-page .collection-head { max-width: 1080px; }
.contact-wrap {
  max-width: 1080px; margin: 0 auto; padding: 24px 24px 90px; color: #423a4a;
  display: grid; grid-template-columns: 340px 1fr; gap: 24px; align-items: start;
}

/* The two channels first in the source, so the order a screen reader and a
   phone get is the order the desktop shows -- and because tapping through to
   WhatsApp is what most people came here to do. The form is the longer path. */
.contact-channels { display: flex; flex-direction: column; gap: 12px; }
.channel {
  display: grid; grid-template-columns: 44px 1fr 18px; gap: 14px; align-items: center;
  background: #fff; border: 1px solid #ece6f2; border-radius: 16px; padding: 15px 16px;
  box-shadow: 0 2px 12px rgba(43, 25, 48, 0.05);
  transition: border-color 0.15s ease, box-shadow 0.15s ease, transform 0.15s ease;
}
.channel:hover {
  border-color: var(--lavender); box-shadow: 0 10px 26px rgba(122, 92, 142, 0.16);
  transform: translateY(-2px);
}
.channel-icon { width: 44px; height: 44px; border-radius: 12px; display: grid; place-items: center; color: #fff; }
.channel-icon svg { width: 24px; height: 24px; display: block; }
/* Each channel wears its own colour rather than the store's lavender: these are
   the two marks people scan for, and recolouring them costs that recognition. */
.channel-wa .channel-icon { background: #1E9E6B; }
.channel-ig .channel-icon { background: linear-gradient(135deg, #F58529, #DD2A7B, #8134AF); }
.channel-body { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.ch-label { font-size: 0.7rem; letter-spacing: 0.12em; text-transform: uppercase; font-weight: 800; color: #9a90a6; }
.ch-value { font-weight: 700; font-size: 0.98rem; color: #1a1420; overflow-wrap: anywhere; }
.ch-go { width: 18px; height: 18px; color: #c9c0d4; transition: color 0.15s ease, transform 0.15s ease; }
.channel:hover .ch-go { color: #7A5C8E; transform: translateX(2px); }
.contact-aside-note { font-size: 0.84rem; line-height: 1.6; color: #6C5A76; margin: 6px 2px 0; }

.contact-card {
  background: #fff; border: 1px solid #ece6f2; border-radius: 18px;
  box-shadow: 0 14px 44px rgba(43, 25, 48, 0.07); padding: clamp(20px, 3vw, 30px);
}
.contact-card h2 { font-size: 1.15rem; font-weight: 600; color: #1a1420; }
.contact-card-sub { font-size: 0.85rem; color: #857E95; margin: 4px 0 18px; }
.contact-row { display: grid; grid-template-columns: 1fr 1fr; gap: 14px; }
.contact-field { margin-bottom: 14px; }
.contact-row .contact-field { margin-bottom: 0; }
.contact-row + .contact-field { margin-top: 14px; }
/* Real labels, not placeholder-only: a placeholder disappears the moment you
   type, so a half-filled form stops saying which box is which -- and the phone
   field needs to say it is optional somewhere that survives being filled in. */
.contact-field label { display: block; font-size: 0.78rem; font-weight: 700; color: #444; margin-bottom: 5px; }
.contact-field label .opt { font-weight: 500; color: #a09aad; }
.contact-field input, .contact-field textarea {
  width: 100%; padding: 11px 13px; border: 1.5px solid #E1D9E8; border-radius: 10px;
  font-family: inherit; font-size: 0.92rem; color: #1B1020; background: #fff;
}
.contact-field input:focus, .contact-field textarea:focus {
  outline: none; border-color: #A99BE8; box-shadow: 0 0 0 3px rgba(169, 155, 232, 0.22);
}
.contact-field textarea { resize: vertical; min-height: 120px; }

/* Green, and carrying the WhatsApp mark, because that is literally where the
   button goes -- the POST redirects to a wa.me link. The old mint pill promised
   a quiet in-page submit. */
.btn-wa-submit {
  width: 100%; margin-top: 18px; background: #1E9E6B; color: #fff; border: none; cursor: pointer;
  padding: 13px; border-radius: 12px; font-family: inherit; font-weight: 700; font-size: 0.95rem;
  display: flex; align-items: center; justify-content: center; gap: 8px;
  transition: background 0.15s ease;
}
.btn-wa-submit svg { width: 17px; height: 17px; flex-shrink: 0; }
.btn-wa-submit:hover { background: #17845a; }
.contact-hint { font-size: 0.76rem; color: #9a90a6; text-align: center; margin: 10px 0 0; }

@media (max-width: 860px) {
  .contact-wrap { grid-template-columns: 1fr; gap: 18px; padding-bottom: 70px; }
}
/* .collection-head drops to a 16px gutter here, so the wrap has to follow or the
   title sits 8px left of the cards -- the same misalignment as above, in small. */
@media (max-width: 640px) {
  .contact-wrap { padding-left: 16px; padding-right: 16px; }
}
@media (max-width: 560px) {
  .contact-row { grid-template-columns: 1fr; }
  .contact-row + .contact-field { margin-top: 14px; }
}

/* ---------- Product detail ---------- */
.product-detail {
  background: var(--white); color: var(--black);
  max-width: 1120px; margin: 0 auto; padding: 48px 24px 80px;
  display: grid; grid-template-columns: 1fr 1fr; gap: 56px;
}
.pd-wrap { background: var(--white); }
.product-gallery { display: flex; flex-direction: column; gap: 12px; }
.product-detail-img { position: relative; border-radius: 8px; overflow: hidden; background: #f4f4f6; aspect-ratio: 1/1; display: flex; align-items: center; justify-content: center; }
.product-detail-img img { width: 100%; height: 100%; object-fit: contain; mix-blend-mode: multiply; }
#pd-main { transition: opacity 0.2s ease, transform 0.12s ease; transform-origin: center; will-change: transform; }
/* Hover magnifier: the main image scales up and pans toward the cursor so the
   fine print on a card can be read without leaving the page. JS sets both the
   transform-origin (from the pointer) and the scale — hover magnifies, then the
   wheel zooms in and out between 1x and 4x. The frame's overflow:hidden crops
   whatever falls outside. */
.product-detail-img.pd-zoomable { cursor: zoom-in; }
.product-detail-img.pd-zoomable.pd-max { cursor: zoom-out; }
@media (hover: none), (pointer: coarse) { .product-detail-img.pd-zoomable { cursor: default; } }
.pd-nav {
  position: absolute; top: 50%; transform: translateY(-50%); z-index: 4;
  width: 42px; height: 42px; padding: 0; border-radius: 50%; border: none;
  background: rgba(255, 255, 255, 0.85); color: #1a1420; cursor: pointer; box-shadow: 0 2px 12px rgba(43, 25, 48, 0.16);
  display: flex; align-items: center; justify-content: center; line-height: 0;
  opacity: 0; transition: opacity 0.16s ease, background 0.15s ease;
}
.pd-nav svg { width: 20px; height: 20px; display: block; }
.product-detail-img:hover .pd-nav { opacity: 1; }
.pd-nav:hover { background: #fff; }
.pd-nav:active { transform: translateY(-50%) scale(0.93); }
.pd-nav.prev { left: 10px; }
.pd-nav.next { right: 10px; }
@media (hover: none) { .pd-nav { opacity: 1; } }
.pd-thumbs { display: flex; flex-wrap: wrap; gap: 10px; }
.pd-thumb { padding: 0; border: 2px solid transparent; border-radius: 8px; overflow: hidden; cursor: pointer; background: #f4f4f6; width: 72px; height: 72px; }
.pd-thumb img { width: 100%; height: 100%; object-fit: contain; mix-blend-mode: multiply; }
.pd-thumb.active { border-color: var(--lavender); }
.desc ul, .desc ol { padding-left: 20px; margin: 8px 0; }
.desc a { color: #8367c7; text-decoration: underline; }
.desc p { margin: 0 0 10px; }

/* ---------- Related products carousel ---------- */
.related { background: var(--white); }
.related-title { text-align: center; font-family: 'Inter', sans-serif; font-weight: 400; font-size: 1.9rem; color: #111; padding: 8px 24px 6px; }
.related-title::after { content: ''; display: block; width: 44px; height: 2px; background: var(--lavender); margin: 12px auto 0; }
.related-wrap { position: relative; max-width: 1180px; margin: 20px auto 0; padding: 0 24px 80px; }
.related-track { display: flex; gap: 20px; overflow-x: auto; scroll-behavior: smooth; scroll-snap-type: x mandatory; padding: 6px 2px; scrollbar-width: none; -ms-overflow-style: none; }
.related-track::-webkit-scrollbar { display: none; }
.related-card { flex: 0 0 210px; scroll-snap-align: start; }
/* Soft fade on the right edge so the peeking card fades into "more" instead of a hard cut */
.related-wrap::after {
  content: ''; position: absolute; top: 6px; right: 24px; bottom: 86px; width: 60px;
  background: linear-gradient(to right, rgba(255,255,255,0), #fff);
  pointer-events: none; z-index: 3;
}
.related-arrow {
  position: absolute; top: 106px; transform: translateY(-50%); z-index: 6;
  width: 42px; height: 42px; padding: 0; border-radius: 50%; border: none;
  background: rgba(255, 255, 255, 0.85); color: #1a1420; cursor: pointer;
  box-shadow: 0 2px 12px rgba(43, 25, 48, 0.16);
  display: flex; align-items: center; justify-content: center; transition: background 0.15s ease;
}
.related-arrow:hover { background: #fff; }
.related-arrow:active { transform: translateY(-50%) scale(0.93); }
.related-arrow svg { width: 20px; height: 20px; display: block; }
.related-arrow.prev { left: 6px; }
.related-arrow.next { right: 6px; }
@media (max-width: 640px) { .related-card { flex-basis: 158px; } .related-arrow { display: none; } }
.pd-cat { font-size: 0.78rem; color: #8367c7; text-transform: uppercase; letter-spacing: 0.05em; font-weight: 600; }
.product-detail h1 { font-size: 2rem; margin: 8px 0; color: #0B0B0D; }
.product-detail .price { font-size: 1.5rem; margin: 4px 0 16px; }
.pd-stock { display: flex; flex-wrap: wrap; gap: 8px; margin: 14px 0 4px; }
.stock-badge { display: inline-flex; align-items: center; gap: 5px; font-size: 0.8rem; font-weight: 600; padding: 5px 12px; border-radius: 999px; }
.stock-badge.in { background: #E7F7EF; color: #1E7A50; }
.stock-badge.out { background: #FDECEC; color: #C0392B; }
.stock-badge.transit { background: #EDE7F6; color: #6a4ea0; }
.stock-badge.transit strong { font-weight: 800; }
.stock-badge.soon { background: #EDE7F6; color: #6a4ea0; }
.stock-badge.soon strong { font-weight: 800; }
/* ---------- Subproducts (variants) on the product page ---------- */
/* One availability block per variant, all rendered, all but the chosen one
   hidden. The rule is explicit because .pd-stock sets display:flex, and a class
   beats the browser's own [hidden] { display: none } — without this every
   variant's stock shows at once. */
.pd-stock[hidden] { display: none; }
/* A dropdown built from <details> + buttons, because each option carries the
   variant's photo and a native <option> cannot hold one. Shaped after the
   catalog toolbar's filter dropdowns so the store has one dropdown language. */
.pd-variants { margin: 18px 0 4px; max-width: 420px; }
.pd-var-title { display: block; font-size: 0.82rem; font-weight: 700; color: #0B0B0D; margin-bottom: 8px; }
.pd-dd { position: relative; }
.pd-dd-trigger {
  display: flex; align-items: center; gap: 10px;
  padding: 8px 14px 8px 8px; background: #fff; cursor: pointer;
  border: 2px solid #E6E2EF; border-radius: 12px;
  font-size: 0.9rem; font-weight: 600; color: #0B0B0D;
  list-style: none; /* Firefox: drop the disclosure triangle */
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.pd-dd-trigger::-webkit-details-marker { display: none; }
.pd-dd-trigger:hover { border-color: var(--lavender); }
.pd-dd[open] .pd-dd-trigger { border-color: #6a4ea0; }
.pd-dd-trigger:focus-visible { outline: none; border-color: #6a4ea0; box-shadow: 0 0 0 3px rgba(169, 155, 232, 0.22); }
.pd-dd-value { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.pd-dd-trigger .caret { font-size: 0.8rem; color: #6a4ea0; transition: transform 0.2s ease; }
.pd-dd[open] .pd-dd-trigger .caret { transform: rotate(180deg); }

/* The photo tile, shared by the trigger and every option. It keeps its size
   with no image inside so a variant that has none still lines up with the rest
   instead of shifting the text left. */
.pd-thumb-box {
  width: 38px; height: 38px; flex-shrink: 0; border-radius: 9px; overflow: hidden;
  background: #f4f4f6; display: block;
}
.pd-thumb-box img { width: 100%; height: 100%; object-fit: cover; display: block; }
.pd-thumb-box img[hidden] { display: none; }

.pd-dd-panel {
  position: absolute; top: calc(100% + 8px); left: 0; right: 0; z-index: 40;
  background: #fff; border: 1px solid #ece7f1; border-radius: 12px;
  box-shadow: 0 10px 30px rgba(43, 25, 48, 0.14);
  padding: 6px; max-height: 320px; overflow-y: auto;
}
.pd-opt {
  display: flex; align-items: center; gap: 10px; width: 100%;
  padding: 7px 8px; border: none; border-radius: 9px; background: none;
  font: inherit; text-align: left; color: #0B0B0D; cursor: pointer;
}
.pd-opt:hover, .pd-opt:focus-visible { background: #f6f2fa; outline: none; }
.pd-opt-body { flex: 1; min-width: 0; }
.pd-opt-name { display: block; font-size: 0.88rem; font-weight: 600; }
.pd-opt-meta { display: block; font-size: 0.76rem; color: #7a7683; margin-top: 1px; }
.pd-opt-check { color: #6a4ea0; font-weight: 800; opacity: 0; }
.pd-opt.is-active .pd-opt-check { opacity: 1; }
/* Still selectable — an out-of-stock variant can be ordered the same way an
   out-of-stock product can — just clearly the lesser option. */
.pd-opt.is-out .pd-opt-name { color: #7a7683; }
.pd-opt.is-out .pd-thumb-box img { opacity: 0.55; }

.product-detail .desc { color: #444; margin: 16px 0 26px; line-height: 1.7; }
.breadcrumb { background: var(--white); }
.breadcrumb-inner { max-width: 1120px; margin: 0 auto; padding: 20px 24px 0; font-size: 0.82rem; color: #888; }
.breadcrumb-inner a { color: #888; }

/* ---------- Footer ---------- */
.site-footer { background: var(--black); color: var(--ink-muted); padding: 22px clamp(16px, 3vw, 40px) 16px; border-top: 1px solid #1e1e22; }
.footer-inner { max-width: 100%; margin: 0; display: flex; justify-content: space-between; align-items: center; gap: 20px; flex-wrap: wrap; }
.footer-inner .footer-policies { margin: 0; }
.footer-inner h3 { color: var(--white); font-size: 1.1rem; margin-bottom: 10px; }
.footer-links a { display: block; color: var(--ink-muted); padding: 4px 0; font-size: 0.9rem; }
.footer-links a:hover { color: var(--white); }
.footer-social { display: flex; gap: 12px; }
.footer-social a { display: inline-flex; align-items: center; justify-content: center; width: 40px; height: 40px; border-radius: 50%; border: 1px solid #34343c; color: var(--ink-muted); transition: color 0.15s ease, border-color 0.15s ease; }
.footer-social a:hover { color: var(--white); border-color: var(--lavender); }
.footer-social svg { width: 20px; height: 20px; }
.footer-policies { max-width: 1280px; margin: 28px auto 0; display: flex; flex-wrap: wrap; align-items: center; gap: 10px; font-size: 0.82rem; }
.footer-policies a { color: var(--ink-muted); }
.footer-policies a:hover { color: var(--white); text-decoration: underline; }
.footer-policies .sep { color: var(--ink-muted); opacity: 0.5; }
.footer-bottom { max-width: 100%; margin: 14px 0 0; border-top: 1px solid #1e1e22; padding-top: 12px; font-size: 0.75rem; opacity: 0.7; display: flex; justify-content: space-between; flex-wrap: wrap; gap: 8px; }

/* Static content pages (policies, info) — professional layout */
.page-wrap { background: #F5F1F9; min-height: 72vh; }
.page-hero { text-align: center; padding: 50px 24px 26px; }
.page-logo { height: 64px; width: auto; margin: 0 auto 16px; display: block; object-fit: contain; }
.page-eyebrow { display: inline-block; font-size: 0.72rem; letter-spacing: 0.14em; text-transform: uppercase; color: var(--lavender); font-weight: 800; margin-bottom: 10px; }
.page-hero h1 { font-family: 'Inter', sans-serif; font-weight: 400; font-size: clamp(1.9rem, 4vw, 2.8rem); color: #1a1420; letter-spacing: 0.01em; }
.page-card {
  max-width: 820px; margin: 0 auto 72px; background: #fff; border: 1px solid #ece6f2;
  border-radius: 18px; box-shadow: 0 14px 44px rgba(43, 25, 48, 0.07);
  padding: clamp(24px, 4vw, 50px);
}
.page-content { color: #423a4a; line-height: 1.8; font-size: 0.98rem; }
.page-content > p:first-child { font-size: 1.05rem; color: #2c2534; }
.page-content h2 {
  font-family: 'Inter', sans-serif; font-weight: 600; font-size: 1.3rem; color: #1a1420;
  margin: 30px 0 12px; padding-top: 22px; border-top: 1px solid #f0ebf4;
}
.page-content h2:first-of-type { border-top: none; padding-top: 6px; }
.page-content h3 { font-weight: 700; font-size: 1.02rem; color: #2a2430; margin: 20px 0 6px; }
.page-content p { margin: 0 0 14px; }
.page-content ul, .page-content ol { padding-left: 22px; margin: 0 0 16px; }
.page-content li { margin: 6px 0; }
.page-content a { color: #8367c7; text-decoration: underline; }
.page-content strong { color: #1a1420; }
.page-content .policy-date { margin-top: 28px; padding-top: 16px; border-top: 1px solid #f0ebf4; color: #9a90a6; font-size: 0.82rem; font-style: italic; }
@media (max-width: 640px) { .page-hero { padding: 34px 20px 20px; } }

/* ---- FAQ ------------------------------------------------------------------
   The accordion is native <details>/<summary>: it needs no JavaScript, is fully
   keyboard-accessible, and still opens if scripting is off. Answers reuse
   .page-content, so links and lists match the policy pages. */
.faq-wrap { max-width: 820px; margin: 0 auto 72px; padding: 0 20px; }
.faq-group { margin-bottom: 34px; }
.faq-cat {
  font-family: 'Inter', sans-serif; font-weight: 700; font-size: 0.78rem;
  letter-spacing: 0.12em; text-transform: uppercase; color: var(--lavender, #8367c7);
  margin: 0 6px 12px; padding-bottom: 0;
}
.faq-items {
  background: #fff; border: 1px solid #ece6f2; border-radius: 18px;
  box-shadow: 0 14px 44px rgba(43, 25, 48, 0.07); overflow: hidden;
}
.faq-item { border-top: 1px solid #f0ebf4; }
.faq-item:first-child { border-top: none; }
.faq-item > summary {
  list-style: none; cursor: pointer; display: flex; align-items: center; gap: 16px;
  padding: 18px clamp(18px, 3vw, 26px); font-weight: 600; color: #1a1420;
  font-size: 1rem; line-height: 1.45; transition: background 0.15s ease;
}
.faq-item > summary::-webkit-details-marker { display: none; }
.faq-item > summary:hover { background: #faf7fd; }
.faq-item > summary:focus-visible { outline: 2px solid var(--lavender, #8367c7); outline-offset: -2px; }
.faq-q { flex: 1; }
.faq-caret { flex: none; color: #b0a4c2; transition: transform 0.2s ease; }
.faq-item[open] > summary { background: #faf7fd; }
.faq-item[open] > summary .faq-caret { transform: rotate(180deg); color: var(--lavender, #8367c7); }
.faq-a { padding: 0 clamp(18px, 3vw, 26px) 20px; font-size: 0.95rem; }
.faq-a > p:first-child { font-size: 0.95rem; color: #423a4a; }
.faq-a > :first-child { margin-top: 0; }
.faq-a > :last-child { margin-bottom: 0; }

.faq-contact { text-align: center; margin-top: 44px; }
.faq-contact p { color: #6b6175; margin-bottom: 16px; font-size: 1.02rem; }
.faq-contact-actions { display: flex; gap: 12px; justify-content: center; flex-wrap: wrap; }
/* Self-contained buttons: the storefront has no generic .btn, so the CTA carries
   its own styling rather than inheriting an invisible default link colour. */
.faq-contact-actions .faq-btn {
  display: inline-flex; align-items: center; justify-content: center; gap: 8px;
  padding: 12px 26px; border-radius: 999px; font-weight: 600; font-size: 0.9rem;
  text-decoration: none; border: 1.5px solid transparent; cursor: pointer;
  transition: background 0.15s ease, color 0.15s ease, border-color 0.15s ease;
}
.faq-contact-actions .faq-btn.is-primary { background: var(--black); color: #fff; }
.faq-contact-actions .faq-btn.is-primary:hover { background: var(--lavender); color: var(--black); }
.faq-contact-actions .faq-btn.is-ghost { background: #fff; color: #2a2430; border-color: #ded5e8; }
.faq-contact-actions .faq-btn.is-ghost:hover { border-color: var(--lavender); color: #1a1420; }

@media (prefers-reduced-motion: reduce) { .faq-caret { transition: none; } }

/* ---------- Cart badge in header ---------- */
.cart-link { position: relative; }
.cart-count {
  position: absolute; top: -7px; right: -9px; min-width: 16px; height: 16px; padding: 0 4px;
  background: var(--lavender); color: var(--black); border-radius: 999px;
  font-size: 0.65rem; font-weight: 700; display: none; align-items: center; justify-content: center; line-height: 16px; text-align: center;
}
.cart-count.show { display: block; }

/* ---------- Product detail buttons ---------- */
.pd-actions { display: flex; flex-wrap: wrap; gap: 10px; margin-top: 6px; }
.btn-dark {
  display: inline-flex; align-items: center; gap: 8px; background: var(--black); color: #fff;
  border: none; cursor: pointer; padding: 12px 26px; border-radius: 999px; font-weight: 600; font-size: 0.9rem;
}
.btn-dark:hover { background: var(--lavender); color: var(--black); }
/* Sold out with nothing in transit — see .card-add:disabled. */
.btn-dark:disabled, .btn-dark:disabled:hover { background: #d9d5dd; color: #6f6a75; cursor: not-allowed; }

/* Product-detail action buttons: compact, single-line, matched height.
   Both are inline-flex so their icon + label stay centered together (btn-mint is
   inline-block by default, which ignored the centering). */
.pd-actions .btn-dark, .pd-actions .btn-mint {
  display: inline-flex; align-items: center; justify-content: center; gap: 8px;
  padding: 9px 18px; font-size: 0.82rem; font-weight: 600; white-space: nowrap; line-height: 1.2;
}
.pd-actions .btn-dark svg, .pd-actions .btn-mint svg { width: 15px; height: 15px; flex-shrink: 0; }

/* ---------- Cart page ---------- */
.cart-page { background: var(--bg-soft, #F7F4F9); color: #1b1b1b; min-height: 70vh; }
.cart-wrap { max-width: 1080px; margin: 0 auto; padding: 40px 24px 90px; display: grid; grid-template-columns: 1fr 360px; gap: 24px; align-items: start; }
.cart-col h1 { font-family: 'Inter', sans-serif; font-weight: 400; font-size: 2rem; color: #111; margin-bottom: 4px; }
.cart-head { display: flex; align-items: center; justify-content: space-between; margin-bottom: 16px; }
.cart-clear { background: none; border: none; color: #c0392b; font-weight: 600; font-size: 0.82rem; cursor: pointer; }
.cart-items { display: flex; flex-direction: column; gap: 12px; }
.cart-item {
  display: grid; grid-template-columns: 72px 1fr auto; gap: 14px; align-items: center;
  background: #fff; border-radius: 14px; padding: 14px; box-shadow: 0 2px 10px rgba(43,25,48,0.05);
}
.cart-item-img { width: 72px; height: 72px; border-radius: 10px; background: #f4f4f6; object-fit: contain; }
.cart-item-name { font-weight: 700; font-size: 0.95rem; color: #111; }
.cart-item-meta { font-size: 0.8rem; color: #888; margin-top: 2px; }
/* Which subproduct this line is: the colour/character chosen on the product
   page. Sits right under the name because without it two lines of the same
   product are indistinguishable. */
.cart-item-variant { font-size: 0.8rem; color: #6a4ea0; font-weight: 600; margin-top: 2px; }
.cart-item-tag { display: inline-block; background: #EDE7F6; color: #6a4ea0; border-radius: 6px; padding: 1px 7px; font-size: 0.68rem; font-weight: 700; margin-top: 5px; }
.cart-item-right { display: flex; flex-direction: column; align-items: flex-end; gap: 8px; }
.qty { display: inline-flex; align-items: center; border: 1px solid #ddd; border-radius: 999px; overflow: hidden; }
.qty button { width: 28px; height: 28px; border: none; background: #fff; cursor: pointer; font-size: 1rem; color: #333; }
.qty button:hover { background: #f0f0f0; }
/* At the stock ceiling. Greyed rather than hidden: the control has to stay where
   it was, or the row reflows every time someone reaches the last unit. */
.qty button:disabled { color: #ccc; cursor: not-allowed; }
.qty button:disabled:hover { background: #fff; }
.qty span { min-width: 30px; text-align: center; font-weight: 700; font-size: 0.9rem; }
.cart-item-max { font-size: 0.7rem; color: #9a8aa8; font-weight: 600; }
.cart-item-price { font-weight: 700; font-size: 0.95rem; color: #111; }
.cart-item-remove { background: none; border: none; color: #bbb; cursor: pointer; font-size: 1.1rem; line-height: 1; }
.cart-item-remove:hover { color: #c0392b; }

.cart-empty { background: #fff; border-radius: 16px; padding: 60px 24px; text-align: center; box-shadow: 0 2px 10px rgba(43,25,48,0.05); }
.cart-empty p { color: #888; margin: 10px 0 20px; }

.summary-card { background: #fff; border-radius: 16px; padding: 22px; box-shadow: 0 2px 12px rgba(43,25,48,0.06); }
.summary-card h2 { font-size: 1.05rem; margin-bottom: 14px; color: #111; }
.summary-row { display: flex; justify-content: space-between; font-size: 0.9rem; color: #444; padding: 6px 0; }
.summary-row.muted { color: #999; font-size: 0.82rem; }
.summary-total {
  margin-top: 12px; background: #2B1930; color: #fff; border-radius: 12px; padding: 14px 16px;
}
.summary-total .lbl { font-size: 0.72rem; text-transform: uppercase; letter-spacing: 0.04em; opacity: 0.75; }
.summary-total .amt { font-size: 1.5rem; font-weight: 800; font-family: 'Inter', sans-serif; }
.summary-total .note { font-size: 0.72rem; opacity: 0.75; margin-top: 2px; }
.summary-deposit { display: flex; justify-content: space-between; align-items: center; margin-top: 12px; font-weight: 700; color: #111; }
.summary-deposit .amt { font-size: 1.1rem; }
.btn-checkout {
  width: 100%; margin-top: 16px; background: #2B1930; color: #fff; border: none; cursor: pointer;
  padding: 14px; border-radius: 12px; font-weight: 700; font-size: 0.95rem; display: flex; align-items: center; justify-content: center; gap: 8px;
}
.btn-checkout:hover { background: #40243f; }
.btn-checkout:disabled { background: #b9b3c0; cursor: not-allowed; }

/* Checkout form (light checkout on the cart page) */
.checkout-form { margin-top: 16px; border-top: 1px solid #EEE9F0; padding-top: 14px; }
.pay-first { background: #F3EFFA; border: 1px solid #E1D9F0; color: #3A2447; font-size: 0.82rem; line-height: 1.55; padding: 11px 13px; border-radius: 10px; margin-bottom: 8px; }
.checkout-form input[type="file"] { padding: 8px 10px; font-size: 0.84rem; cursor: pointer; }
.checkout-form label { display: block; font-size: 0.78rem; font-weight: 700; color: #444; margin: 10px 0 5px; }
.checkout-form input, .checkout-form textarea {
  width: 100%; padding: 10px 12px; border: 1.5px solid #E1D9E8; border-radius: 10px;
  font-family: inherit; font-size: 0.92rem; color: #1B1020; background: #fff;
}
.checkout-form input:focus, .checkout-form textarea:focus { outline: none; border-color: #A99BE8; box-shadow: 0 0 0 3px rgba(169,155,232,0.22); }
.checkout-form textarea { resize: vertical; min-height: 46px; }
.checkout-hint { font-size: 0.76rem; color: #999; text-align: center; margin: 8px 0 0; }
.checkout-error { background: #FCEAEA; color: #C0392B; font-size: 0.85rem; font-weight: 600; padding: 9px 12px; border-radius: 9px; margin-top: 10px; }
.checkout-done { text-align: center; padding: 8px 4px 4px; }
.checkout-done .co-check { width: 52px; height: 52px; margin: 4px auto 10px; border-radius: 50%; background: #E4F6EE; color: #129A66; font-size: 1.7rem; font-weight: 800; display: grid; place-items: center; }
.checkout-done h3 { font-size: 1.15rem; color: #111; margin-bottom: 6px; }
.checkout-done p { font-size: 0.9rem; color: #555; margin: 0 0 14px; }
.checkout-done .btn-dark { display: block; text-align: center; margin-top: 10px; }

.pay-card { background: #fff; border-radius: 16px; padding: 22px; box-shadow: 0 2px 12px rgba(43,25,48,0.06); margin-top: 20px; }
.pay-card h2 { font-size: 1rem; margin-bottom: 2px; color: #111; }
.pay-card .pay-sub { font-size: 0.8rem; color: #999; margin-bottom: 14px; }
.pay-method { display: flex; gap: 12px; align-items: flex-start; padding: 12px 0; border-top: 1px solid #eee; }
.pay-method .pm-icon { font-size: 1.3rem; }
.pay-method .pm-body { flex: 1; }
.pay-method .pm-title { font-weight: 700; font-size: 0.9rem; color: #111; }
.pay-method .pm-line { font-size: 0.85rem; color: #444; margin-top: 2px; }
.pm-copy { background: #EDE7F6; color: #6a4ea0; border: none; border-radius: 8px; padding: 4px 10px; font-size: 0.72rem; font-weight: 700; cursor: pointer; margin-top: 6px; }
.pm-copy:hover { background: #e0d6f2; }
.pay-method.transfer { background: #E7F7EF; border-radius: 12px; border-top: none; padding: 12px; margin-top: 12px; }
.pay-wa { display: inline-flex; align-items: center; gap: 6px; background: #1E9E6B; color: #fff; border-radius: 8px; padding: 6px 12px; font-size: 0.78rem; font-weight: 700; margin-top: 6px; }

.cart-toast {
  position: fixed; bottom: 24px; left: 50%; transform: translateX(-50%) translateY(20px);
  background: #2B1930; color: #fff; padding: 12px 22px; border-radius: 999px; font-size: 0.88rem; font-weight: 600;
  opacity: 0; pointer-events: none; transition: opacity 0.2s ease, transform 0.2s ease; z-index: 200;
}
.cart-toast.show { opacity: 1; transform: translateX(-50%) translateY(0); }

@media (max-width: 820px) { .cart-wrap { grid-template-columns: 1fr; } }

/* ---------- Mini-cart drawer ---------- */
/* Viewport-sized clip: keeps the off-screen (closed) drawer from extending the
   page width, which showed as blank space on the right when zoomed out. */
.drawer-root { position: fixed; inset: 0; overflow: hidden; pointer-events: none; z-index: 150; }
.drawer-backdrop { position: absolute; inset: 0; background: rgba(11, 11, 13, 0.45); opacity: 0; pointer-events: none; transition: opacity 0.25s ease; z-index: 150; }
.drawer-backdrop.show { opacity: 1; pointer-events: auto; }
.mini-cart {
  position: absolute; top: 0; right: 0; height: 100%; width: 380px; max-width: 90vw;
  background: #fff; color: #1b1b1b; z-index: 160; box-shadow: -8px 0 34px rgba(0,0,0,0.18);
  transform: translateX(100%); transition: transform 0.28s cubic-bezier(.4,0,.2,1), visibility 0.28s;
  display: flex; flex-direction: column;
  /* Hidden + clipped by .drawer-root when closed (see .drawer-root). visibility
     also drops it from the a11y tree; pointer-events:auto re-enables interaction
     since the .drawer-root parent is pointer-events:none. */
  visibility: hidden; pointer-events: auto;
}
.mini-cart.open { transform: translateX(0); visibility: visible; }
.mini-cart-head { display: flex; align-items: center; justify-content: space-between; padding: 18px 20px; border-bottom: 1px solid #eee; font-family: 'Inter', sans-serif; font-size: 1.2rem; color: #111; }
.mini-close { background: none; border: none; font-size: 1.1rem; cursor: pointer; color: #888; }
.mini-close:hover { color: #111; }
.mini-cart-body { flex: 1; overflow-y: auto; padding: 14px 16px; display: flex; flex-direction: column; gap: 14px; }
.mini-item { display: grid; grid-template-columns: 56px 1fr auto; gap: 10px; align-items: start; }
.mini-item-img { width: 56px; height: 56px; border-radius: 8px; background: #f4f4f6; object-fit: contain; }
.mini-item-name { font-weight: 700; font-size: 0.85rem; line-height: 1.25; color: #111; }
.mini-item-variant { font-size: 0.74rem; color: #6a4ea0; font-weight: 600; margin-top: 2px; }
.mini-item-tag { display: inline-block; background: #EDE7F6; color: #6a4ea0; border-radius: 5px; padding: 0 6px; font-size: 0.62rem; font-weight: 700; margin-top: 3px; }
.mini-item .qty { transform: scale(0.85); transform-origin: left; margin-top: 6px; }
.mini-item-price { font-weight: 700; font-size: 0.82rem; text-align: right; color: #111; margin-top: 4px; }
.mini-item-remove { background: none; border: none; color: #bbb; cursor: pointer; font-size: 0.9rem; float: right; }
.mini-item-remove:hover { color: #c0392b; }
.mini-empty { text-align: center; color: #888; padding: 50px 20px; }
.mini-empty p { margin: 10px 0 18px; }
.mini-cart-foot { border-top: 1px solid #eee; padding: 16px 20px; display: flex; flex-direction: column; gap: 10px; }
.mini-total { display: flex; justify-content: space-between; font-weight: 800; font-size: 1.05rem; color: #111; }
.mini-cart-foot .btn-checkout { margin-top: 0; }
.mini-view { text-align: center; justify-content: center; }

@media (max-width: 860px) {
  .header-inner { grid-template-columns: auto 1fr auto; }
  .nav-toggle { display: inline-flex; }
  /* Mobile menu: hamburger opens the nav as a full-width dropdown panel.
     Kept in the layout (not display:none) and hidden with visibility/opacity so
     it can animate. The reveal is a composited slide + fade (opacity/transform
     only), so it stays smooth on phones. */
  .main-nav {
    display: flex; position: absolute; top: 100%; left: 0; right: 0;
    flex-direction: column; align-items: stretch; gap: 0;
    background: var(--black); border-top: 1px solid #26262b;
    padding: 6px 0 12px; z-index: 58; max-height: calc(100vh - 56px); overflow-y: auto;
    visibility: hidden; opacity: 0; transform: translateY(-8px); pointer-events: none;
    transition: opacity 0.22s ease, transform 0.22s ease, visibility 0.22s;
    will-change: opacity, transform;
  }
  .main-nav.open { visibility: visible; opacity: 1; transform: translateY(0); pointer-events: auto; }
  /* While the menu is open, pause the marquees so the phone's compositor is
     free to animate the panel smoothly (they were the source of the jank). */
  body.nav-open .brand-track,
  body.nav-open .text-marquee-track,
  body.nav-open .bottom-track { animation-play-state: paused; }
  .main-nav > a, .main-nav > .has-menu > a {
    font-size: 1rem; padding: 13px 20px; opacity: 1; display: flex; gap: 12px;
  }
  .main-nav .nav-ico { width: 18px; height: 18px; }
  /* Catalog: parent text + caret share one row; the submenu collapses below it */
  .main-nav .has-menu { display: flex; flex-wrap: wrap; align-items: center; }
  .main-nav > .has-menu > a { flex: 1 1 auto; }
  .main-nav .mega-toggle {
    display: flex; align-items: center; justify-content: center; flex: 0 0 auto;
    padding: 13px 20px; background: none; border: none; color: #fff; cursor: pointer;
  }
  .main-nav .mega-toggle .caret { width: 18px; height: 18px; transition: transform 0.25s ease; }
  .main-nav .has-menu.sub-open .mega-toggle .caret { transform: rotate(180deg); }
  /* Submenu reveal. The height opens instantly (animating max-height/height on
     the main thread stutters on phones while the marquees run); the submenu
     CONTENT fades + slides in via opacity/transform, which are GPU-composited
     and stay smooth regardless of other work. */
  .main-nav .mega {
    flex-basis: 100%; position: static; transform: none; pointer-events: auto;
    opacity: 1; visibility: visible; background: transparent; border-top: none;
    max-height: 0; overflow: hidden; padding: 0;
  }
  .main-nav .has-menu.sub-open .mega { max-height: 1200px; }
  .main-nav .mega-inner {
    display: block; padding: 0 0 6px; max-width: none;
    opacity: 0; transform: translateY(-6px);
    transition: opacity 0.24s ease, transform 0.24s ease;
  }
  .main-nav .has-menu.sub-open .mega-inner { opacity: 1; transform: translateY(0); }
  .main-nav .mega-col { opacity: 1; transform: none; margin: 0; transition: none; }
  .main-nav .mega-col h4 { padding: 10px 20px 4px 36px; margin: 0; }
  .main-nav .mega-col a { display: block; padding: 9px 20px 9px 52px; font-size: 0.9rem; opacity: 0.85; }
  .product-detail { grid-template-columns: 1fr; }
  .promos { padding: 48px clamp(16px, 4vw, 40px) 60px; }
  .promo-arrow { display: none; }
  /* Prevent the collection toolbar from overflowing the viewport (horizontal scroll) */
  .collection-toolbar { flex-wrap: wrap; gap: 12px; padding: 14px 16px; }
  .collection-toolbar .filters { flex-wrap: wrap; }
  .toolbar-right { flex-wrap: wrap; gap: 10px 12px; }
  /* Keep an OPEN dropdown within the screen, but still wide enough to read: size
     each panel to its content width, capped to the viewport so it can never spill
     off the right. (Closed panels are display:none, so they never affect width.)
     min() keeps the cap winning on very narrow phones, where a bare min-width
     would otherwise beat max-width and overflow. */
  .filter-panel, .sort-panel { min-width: min(210px, calc(100vw - 24px)); }
  .price-panel { min-width: min(300px, calc(100vw - 24px)); }
  .filter-panel { max-width: calc(100vw - 24px); }
  /* Anchor the left-side dropdowns to the filters ROW rather than to their own
     trigger: a panel wider than the trigger's offset would otherwise hang off one
     edge of the screen. From the row's left edge it always opens on-screen. */
  .collection-toolbar .filters { position: relative; }
  .filters .filter-dd { position: static; }
  .filters .filter-panel { left: 0; right: auto; }
  /* Same for the right-hand group (Ordenar): anchor to the row's right edge. */
  .collection-toolbar .toolbar-right { position: relative; }
  .toolbar-right .filter-dd { position: static; }
  .toolbar-right .filter-panel { left: auto; right: 0; }
}
/* ============================================================
   Mobile fit pass (<=640px): right-size every section so the
   phone view is compact, tappable, and scrolls smoothly.
   Grouped here (after the 860px block) so these win the cascade.
   ============================================================ */
@media (max-width: 640px) {
  /* Header: bigger tap targets for the icon row + hamburger */
  .header-icons { gap: 4px; }
  .header-icons a, .header-icons button { padding: 8px; }
  /* ID selector needed to beat #search-toggle{padding:0} */
  #search-toggle { padding: 8px; }
  .header-icons svg { width: 20px; height: 20px; }
  .nav-toggle { padding: 8px; margin-left: -8px; }
  .cart-count { top: 1px; right: 1px; }

  /* Hero (used on some inner pages): drop the huge vertical padding */
  .hero { padding: 54px 20px 64px; }

  /* Homepage sections: trim desktop-scale spacing + headings.
     .brand-band is left alone: its padding is already symmetric and tight. */
  .novedades { padding: 22px 0 30px; }
  .novedades-row { gap: 14px; padding: 6px 20px; scroll-padding-inline: 20px; }

  .promos { padding: 34px 12px 44px; }
  .promos-head { margin-bottom: 22px; }
  .promos-head h2 { font-size: 1.6rem; }
  .promos-head p { font-size: 0.92rem; margin-top: 10px; }

  .collections { padding: 36px 12px 44px; }
  .collections-head { margin-bottom: 22px; }
  .collections-head h2 { font-size: 1.6rem; }

  /* Products listing: default 2 columns; the view toggle drops to 1 column.
     minmax(0,1fr) lets tracks shrink below card content min-size so a wide
     name/pill/image can never push the grid past the viewport (iOS-prone). */
  .grid { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 18px 12px; padding: 18px 12px 56px; }
  .grid.view-large { grid-template-columns: minmax(0, 1fr); gap: 18px; }
  .collection-head { padding: 26px 16px 4px; }
  .collection-head h1 { font-size: 1.9rem; }
  .collection-head p { font-size: 0.9rem; }
  .collection-toolbar { padding: 12px; }
  .cat-jump { padding: 12px 16px 0; }
  .availability-banner { margin-top: 14px; padding: 12px 16px; font-size: 0.85rem; }
  .card { padding: 8px; }
  .card-name { font-size: 0.86rem; min-height: 2.2rem; }
  /* Phones: quick-add is just the cart icon (no label), as a round button */
  .card-add { gap: 0; padding: 10px; border-radius: 50%; }
  .card-add .ca-label { display: none; }

  /* Product detail: tighter stacked layout + full-width tappable actions */
  .product-detail { padding: 24px 16px 48px; gap: 26px; }
  .product-detail h1 { font-size: 1.6rem; }
  .product-detail .price { font-size: 1.35rem; }
  .breadcrumb-inner { padding: 16px 16px 0; }
  .pd-actions { gap: 10px; }
  .pd-actions .btn-dark, .pd-actions .btn-mint {
    flex: 1 1 100%; justify-content: center;
    padding: 14px 16px; font-size: 0.92rem; white-space: normal;
  }

  /* Related carousel: smaller heading + tighter side padding */
  .related-title { font-size: 1.5rem; padding: 6px 16px 4px; }
  /* Match the Novedades 20px gutter. The gutter here comes from the wrap
     padding (outside the scroll track), so scroll-snap can't eat it — no
     scroll-padding needed, unlike .novedades-row. */
  .related-wrap { padding: 0 20px 56px; margin-top: 14px; }

  /* Cart page: tighter padding on the stacked layout */
  .cart-wrap { padding: 28px 16px 64px; }
}

@media (prefers-reduced-motion: reduce) { .brand-track, .bottom-track { animation: none; } * { transition: none !important; } }

/* ==========================================================================
   Customer accounts (/cuenta) — login, register, dashboard
   Reuses the cart's light-page language: white cards on white, #2B1930 ink,
   lavender focus rings.
   ========================================================================== */

/* Header: the account icon becomes an avatar/initial chip once signed in. */
.header-icons .account-chip {
  width: 24px; height: 24px; border-radius: 50%; object-fit: cover; display: block;
  border: 1.5px solid rgba(255,255,255,0.55);
}
.header-icons .account-chip.placeholder {
  display: grid; place-items: center; background: var(--lavender); color: var(--black);
  font-size: 0.72rem; font-weight: 800; line-height: 1; border-color: transparent;
}
.header-icons .account-link.is-in { opacity: 1; }

/* ---- Header account menu (signed-in dropdown) ---- */
.account-menu { position: relative; display: inline-flex; align-items: center; }
/* The chip toggle is a <button>; strip the native chrome so it reads as the
   other header glyphs, not a form control. */
.account-menu .account-link { background: none; border: none; padding: 0; cursor: pointer; }
.account-dd {
  position: absolute; top: calc(100% + 10px); right: 0; z-index: 60; min-width: 210px;
  background: #fff; border: 1px solid #ece7f1; border-radius: 12px;
  box-shadow: 0 12px 32px rgba(43,25,48,0.16); padding: 8px; overflow: hidden;
}
.account-dd[hidden] { display: none; }
.account-dd-head { padding: 8px 10px 10px; border-bottom: 1px solid #f0ebf4; margin-bottom: 6px; }
.account-dd-name { display: block; font-weight: 800; font-size: 0.9rem; color: #2B1930; line-height: 1.2; }
.account-dd-email { display: block; font-size: 0.76rem; color: #8a7f95; margin-top: 2px; word-break: break-all; }
.account-dd a,
.account-dd .account-dd-logout {
  display: block; width: 100%; text-align: left; box-sizing: border-box;
  padding: 9px 10px; border-radius: 8px; font: inherit; font-size: 0.88rem; font-weight: 600;
  color: #2B1930; background: none; border: none; cursor: pointer; text-decoration: none;
}
.account-dd a:hover,
.account-dd .account-dd-logout:hover { background: #f6f2fa; }
.account-dd .account-dd-logout { color: #C0392B; }
.account-dd .account-dd-logout:hover { background: #fbecea; }
.account-dd form { margin: 0; }

/* ---- Auth pages (login / register) ---- */
.auth-page { flex: 1; background: #FAF8FC; display: flex; justify-content: center; }
.auth-card {
  background: #fff; border-radius: 16px; padding: 32px; margin: 56px 20px 72px;
  width: 100%; max-width: 430px; box-shadow: 0 2px 12px rgba(43,25,48,0.06); align-self: flex-start;
}
.auth-card h1 { font-family: 'Inter', sans-serif; font-size: 1.6rem; color: #111; margin: 0 0 4px; }
.auth-sub { font-size: 0.86rem; color: #777; margin: 0 0 20px; }

.auth-error, .auth-notice {
  font-size: 0.85rem; font-weight: 600; padding: 10px 13px; border-radius: 10px; margin-bottom: 14px; line-height: 1.5;
}
.auth-error { background: #FCEAEA; color: #C0392B; }
.auth-notice { background: #E4F6EE; color: #0F7A51; }

/* Provider buttons */
.auth-providers { display: flex; flex-direction: column; gap: 9px; }
.auth-provider {
  display: flex; align-items: center; justify-content: center; gap: 10px;
  padding: 12px; border: 1.5px solid #E1D9E8; border-radius: 12px;
  font-weight: 700; font-size: 0.9rem; color: #2B1930; text-decoration: none; background: #fff;
  transition: border-color 0.15s, background 0.15s;
}
.auth-provider:hover { border-color: #A99BE8; background: #FAF8FC; }
.auth-provider svg { width: 18px; height: 18px; flex-shrink: 0; }

.auth-divider { display: flex; align-items: center; gap: 12px; margin: 18px 0 4px; }
.auth-divider::before, .auth-divider::after { content: ''; flex: 1; height: 1px; background: #EEE9F0; }
.auth-divider span { font-size: 0.75rem; color: #AAA; text-transform: uppercase; letter-spacing: 0.06em; }

/* Shared form styling for every account form */
.auth-form label { display: block; font-size: 0.78rem; font-weight: 700; color: #444; margin: 12px 0 5px; }
.auth-form label .opt { font-weight: 500; color: #AAA; }
.auth-form input {
  width: 100%; padding: 11px 12px; border: 1.5px solid #E1D9E8; border-radius: 10px;
  font-family: inherit; font-size: 0.92rem; color: #1B1020; background: #fff;
}
.auth-form input:focus { outline: none; border-color: #A99BE8; box-shadow: 0 0 0 3px rgba(169,155,232,0.22); }
.btn-auth {
  width: 100%; margin-top: 18px; background: #2B1930; color: #fff; border: none; cursor: pointer;
  padding: 13px; border-radius: 12px; font-weight: 700; font-size: 0.93rem; font-family: inherit;
}
.btn-auth:hover { background: #40243f; }

/* The 6-digit verification code. Big, spaced and centred so a code being copied
   across from a mail app can be checked at a glance. */
.auth-form input.code-input {
  text-align: center; font-size: 1.6rem; font-weight: 800; letter-spacing: 0.42em;
  /* The letter-spacing is applied after each character, including the last one,
     which pushes the whole string off-centre. Half of it back as padding puts
     the digits where they look centred. */
  padding: 14px 12px 14px 24px;
}
.auth-form input.code-input::placeholder { color: #D8D0DE; font-weight: 700; }

/* Phone: country picker + national number on one line. The picker takes a fixed
   share so a long country name can't squeeze the number field to nothing. */
.phone-row { display: grid; grid-template-columns: minmax(0, 1.15fr) minmax(0, 1fr); gap: 8px; }
.auth-form .phone-row select,
.auth-form .phone-row input { width: 100%; }
.auth-form .phone-country {
  padding: 11px 10px; border: 1.5px solid #E1D9E8; border-radius: 10px;
  font-family: inherit; font-size: 0.88rem; color: #1B1020; background: #fff;
  /* Long names ("Estados Unidos / Canadá") must not widen the control. */
  text-overflow: ellipsis;
}
.auth-form .phone-country:focus { outline: none; border-color: #A99BE8; box-shadow: 0 0 0 3px rgba(169,155,232,0.22); }
@media (max-width: 380px) {
  /* Stacked, because side by side neither half is usable at this width. */
  .phone-row { grid-template-columns: 1fr; }
}

/* Password requirements. Plain grey until you start typing, then each line goes
   green as it's satisfied — see public/js/auth-forms.js. */
.pw-rules {
  list-style: none; margin: 8px 0 0; padding: 0;
  /* Two columns while they fit, one on a narrow phone — the longest rule
     ("Un símbolo…") must never wrap mid-line into something unreadable. */
  display: grid; grid-template-columns: repeat(auto-fit, minmax(150px, 1fr)); gap: 3px 10px;
}
.pw-rules li {
  position: relative; padding-left: 16px;
  font-size: 0.72rem; line-height: 1.5; color: #999;
}
.pw-rules li::before {
  content: '•'; position: absolute; left: 3px; top: 0; font-weight: 700;
}
.pw-rules li.ok { color: #0F7A51; }
.pw-rules li.ok::before { content: '✓'; left: 2px; }
/* Once they're typing, what's still missing is the useful signal, so it stops
   being grey. Untouched, the list is just information and shouldn't look like
   five errors. */
.pw-rules.is-live li:not(.ok) { color: #A2645F; }

.auth-alt { font-size: 0.86rem; color: #666; text-align: center; margin: 18px 0 0; }
.auth-alt a { color: #2B1930; font-weight: 700; }

/* "Enviarme otro código": a form (it sends mail, so it can't be a link) that
   has to read as a link. */
.auth-resend { text-align: center; margin-top: 6px; }
.btn-text {
  background: none; border: none; padding: 4px; cursor: pointer;
  font-family: inherit; font-size: 0.82rem; font-weight: 700; color: #7A5C8E; text-decoration: underline;
}
.btn-text:hover { color: #2B1930; }
.auth-hint { font-size: 0.76rem; color: #999; margin: 8px 0 0; line-height: 1.5; }
.auth-hint a { color: #7A5C8E; font-weight: 600; }

/* Terms + privacy under the auth forms. Quiet but legible — this is the notice
   that makes accepting them meaningful, so it must not read as fine print. */
.auth-legal {
  margin: 16px 0 0; padding-top: 14px; border-top: 1px solid #F0EBF3;
  font-size: 0.76rem; line-height: 1.55; color: #8B8194; text-align: center;
}
.auth-legal a { color: #7A5C8E; font-weight: 700; text-decoration: underline; }
.auth-legal a:hover { color: #2B1930; }

/* ---- Account dashboard ---- */
.account-page { flex: 1; background: #FAF8FC; }
.account-wrap { max-width: 1000px; margin: 0 auto; padding: 40px 20px 72px; }
/* Configuración page: the settings cards pack into a balanced masonry (two
   columns on desktop, one on phones). A fixed grid left ragged voids because
   the cards vary so much in height; masonry keeps them tight, and stays tidy
   no matter which cards a given account actually shows. */
.account-settings { columns: 2 340px; column-gap: 20px; }
.account-settings .account-card { break-inside: avoid; margin: 0 0 20px; }

/* Card header: a soft icon chip beside the title so the six cards are scannable
   at a glance instead of a flat wall of identical headings. */
.account-card-head { display: flex; align-items: center; gap: 11px; margin-bottom: 15px; }
.account-card-head h2 { margin: 0; }
.card-ico {
  width: 34px; height: 34px; border-radius: 10px; flex-shrink: 0;
  background: #F3EFFA; color: #7A5C8E; display: grid; place-items: center;
}
.card-ico svg { width: 18px; height: 18px; }

.account-head { display: flex; justify-content: space-between; align-items: center; gap: 16px; margin-bottom: 22px; flex-wrap: wrap; }
.account-id { display: flex; align-items: center; gap: 14px; }
.account-avatar { width: 54px; height: 54px; border-radius: 50%; object-fit: cover; flex-shrink: 0; }
.account-avatar.placeholder {
  display: grid; place-items: center; background: #2B1930; color: #fff; font-size: 1.3rem; font-weight: 800;
}
.avatar-edit { display: flex; align-items: center; gap: 16px; }
.avatar-card .account-avatar { width: 76px; height: 76px; font-size: 1.8rem; }
.avatar-controls { flex: 1; min-width: 0; }
/* The native file control is hidden and driven by the label below, so the card
   shows a proper button and the chosen filename rather than "Choose File". */
/* Scoped under .auth-form so this width:1px beats `.auth-form input{width:100%}`
   (equal specificity there would let the 100% win and, since the control is
   position:absolute, blow it out to the body width — a horizontal-overflow bug
   on the settings page). */
.auth-form .avatar-file { position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0 0 0 0); border: 0; }
.btn-file {
  display: inline-block; cursor: pointer; padding: 9px 15px; border-radius: 10px;
  background: #fff; border: 1.5px solid #E1D9E8; color: #2B1930;
  font-family: inherit; font-weight: 700; font-size: 0.82rem;
}
.btn-file:hover { border-color: #A99BE8; background: #FAF8FC; }
.avatar-file:focus-visible + .btn-file { border-color: #A99BE8; box-shadow: 0 0 0 3px rgba(169,155,232,0.22); }
.avatar-filename { display: block; font-size: 0.8rem; color: #999; margin-top: 9px; word-break: break-all; }
.avatar-filename.has-file { color: #2B1930; font-weight: 600; }
.avatar-remove-form { margin-top: 12px; }
.btn-avatar-remove {
  background: none; border: none; color: #C0392B; cursor: pointer; padding: 0;
  font-family: inherit; font-size: 0.82rem; font-weight: 700; text-decoration: underline;
}
.btn-avatar-remove:hover { color: #96271b; }
.account-head h1 { font-family: 'Inter', sans-serif; font-size: 1.5rem; color: #111; margin: 0; }
.account-email { font-size: 0.85rem; color: #888; margin: 2px 0 0; }
.btn-logout {
  background: #fff; border: 1.5px solid #E1D9E8; color: #2B1930; cursor: pointer;
  padding: 9px 16px; border-radius: 10px; font-weight: 700; font-size: 0.82rem; font-family: inherit;
}
.btn-logout:hover { border-color: #C0392B; color: #C0392B; }

.account-grid { display: grid; grid-template-columns: 1.35fr 1fr; gap: 20px; align-items: start; }
.account-side { display: flex; flex-direction: column; gap: 20px; }
.account-card { background: #fff; border-radius: 16px; padding: 22px; box-shadow: 0 2px 12px rgba(43,25,48,0.06); }
.account-card h2 { font-size: 1.05rem; color: #111; margin: 0 0 12px; }
.account-empty { font-size: 0.88rem; color: #888; margin: 0 0 14px; }

/* Order history */
.order-list { display: flex; flex-direction: column; gap: 12px; }
.order-row { border: 1px solid #EEE9F0; border-radius: 12px; padding: 14px; }
.order-top { display: flex; justify-content: space-between; align-items: center; gap: 10px; }
.order-top strong { font-size: 0.95rem; color: #111; letter-spacing: 0.02em; }
.order-status {
  font-size: 0.7rem; font-weight: 800; text-transform: uppercase; letter-spacing: 0.05em;
  padding: 4px 9px; border-radius: 999px; background: #EEE9F0; color: #555;
}
.order-status.st-pendiente { background: #FFF3DC; color: #9A6A00; }
.order-status.st-pagado    { background: #E4F6EE; color: #0F7A51; }
.order-status.st-entregado { background: #E8EEFC; color: #2A4FA8; }
.order-status.st-cancelado { background: #FCEAEA; color: #C0392B; }
.order-meta { font-size: 0.8rem; color: #888; margin-top: 4px; }
.order-meta .order-pre { color: #7A5C8E; font-weight: 600; }
.order-items { list-style: none; margin: 10px 0 0; padding: 10px 0 0; border-top: 1px dashed #EEE9F0; }
.order-items li { display: flex; justify-content: space-between; gap: 10px; font-size: 0.85rem; color: #444; padding: 3px 0; }
.order-items a { color: #444; text-decoration: none; }
.order-items a:hover { color: #7A5C8E; text-decoration: underline; }
.order-items .qty { color: #999; flex-shrink: 0; }
/* The subproduct on a past order line. Pushed against the name (the qty holds
   the right edge with margin-left:auto) so it reads as part of it. */
.order-variant { color: #7A5C8E; font-weight: 600; margin-right: auto; }

/* Linked providers */
.linked-list { list-style: none; margin: 12px 0 0; padding: 0; }
.linked-list li { display: flex; align-items: center; gap: 10px; padding: 10px 0; border-top: 1px solid #EEE9F0; }
.linked-list li:first-child { border-top: none; }
.linked-name { font-weight: 700; font-size: 0.88rem; color: #111; flex: 1; }
.linked-ok { font-size: 0.72rem; font-weight: 800; text-transform: uppercase; letter-spacing: 0.05em; color: #0F7A51; }
.btn-unlink, .btn-link-provider {
  border-radius: 8px; font-weight: 700; font-size: 0.76rem; font-family: inherit;
  padding: 7px 12px; cursor: pointer; text-decoration: none;
}
.btn-unlink { background: none; border: 1.5px solid #E1D9E8; color: #888; }
.btn-unlink:hover { border-color: #C0392B; color: #C0392B; }
.btn-link-provider { background: #2B1930; border: 1.5px solid #2B1930; color: #fff; }
.btn-link-provider:hover { background: #40243f; }

/* Checkout: the "signed in as" / "log in to save" line above the form */
.co-signed-in {
  font-size: 0.78rem; color: #3A2447; background: #F3EFFA; border: 1px solid #E1D9F0;
  border-radius: 10px; padding: 9px 12px; margin: 0 0 4px; line-height: 1.5;
}
.co-signed-in.guest { color: #6C5A76; }
.co-signed-in a { color: #7A5C8E; font-weight: 700; }

@media (max-width: 860px) {
  .account-grid { grid-template-columns: 1fr; }
  .account-wrap { padding: 28px 16px 64px; }
  .auth-card { margin: 28px 16px 64px; padding: 26px 22px; }
  .account-head { align-items: flex-start; }
}

/* ============================ Candydex ============================ */
/* Reuses the light-page language (white surfaces, #0B0B0D ink, lavender accent)
   from the catalog. .dex-page rides on .collection-page for the white backdrop
   and min-height. */
/* End-of-page breathing room, owned here rather than by whatever happens to be
   last. .dex-series is padded at the top only, so consecutive series sit one gap
   apart; the set page's card grid used to carry its own bottom padding instead,
   which left the landing page — where the last element is a series, not a grid —
   with none, and its bottom row overlapping the footer. */
.dex-page { padding-bottom: 64px; }
.dex-head { display: flex; flex-direction: column; gap: 6px; }
.dex-kicker { font-size: 0.8rem; font-weight: 700; letter-spacing: 0.06em; color: #7A5C8E; text-transform: uppercase; }

/* ---- Landing: series sections + set grid ----
   Set tiles are square and hold the set's logo on a soft ground, so a wall of
   sets reads as a row of logos rather than a row of cards. The series label is
   a quiet rule-topped heading so the logos stay the loudest thing on the page. */
.dex-series { max-width: 1280px; margin: 0 auto; padding: 30px 24px 0; }
.dex-series-head {
  display: flex; align-items: baseline; gap: 12px; margin: 0 0 16px;
  padding-bottom: 9px; border-bottom: 1px solid #ece8f2;
}
.dex-series-head h2 {
  font-size: 0.76rem; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.13em; color: #7A5C8E;
}
.dex-series-count { font-size: 0.74rem; color: #9089A0; font-weight: 600; margin-left: auto; }

/* A set card is a framed tile: the pack shot sits on a white inset so the
   packaging reads cleanly, then a dark plum panel carries the name, the rarity
   spread, and a footer with the set code and card count. */
/* One horizontal row per series instead of a wrapping grid: a series with more
   sets than fit scrolls sideways, so the page stays a short stack of rows.
   232px is the width the old auto-fill grid gave a tile at full content width,
   so a series that does fit looks exactly as it did. */
.dex-set-wrap { position: relative; }
.dex-set-row {
  display: flex; gap: 18px; overflow-x: auto;
  scroll-snap-type: x proximity; scroll-behavior: smooth;
  scrollbar-width: none; -ms-overflow-style: none;
  align-items: stretch; /* every tile stretches to the same (tallest) height */
  cursor: grab; user-select: none;
  /* Vertical padding leaves room for the tile's hover lift and its shadow. */
  padding: 4px 2px 10px;
}
.dex-set-row::-webkit-scrollbar { display: none; }
.dex-set-row.dragging { cursor: grabbing; scroll-behavior: auto; scroll-snap-type: none; }
.dex-set-row.dragging .dex-set-card { pointer-events: none; }
.dex-set-row .dex-set-card { flex: 0 0 232px; width: 232px; min-width: 0; scroll-snap-align: start; }
/* Same round arrows as the home carousels, centred on the tile's 4/5 cover
   (232px wide → 290px tall) rather than on the whole tile. */
.dex-arrow {
  position: absolute; top: 149px; transform: translateY(-50%); z-index: 6;
  width: 42px; height: 42px; border-radius: 50%; border: 1.5px solid #2B1930;
  background: rgba(255, 255, 255, 0.92); color: #2B1930; cursor: pointer;
  box-shadow: 0 2px 12px rgba(43, 25, 48, 0.18);
  display: flex; align-items: center; justify-content: center; transition: background 0.15s ease;
}
.dex-arrow:hover { background: #fff; }
.dex-arrow:active { transform: translateY(-50%) scale(0.93); }
.dex-arrow svg { width: 20px; height: 20px; }
.dex-arrow.prev { left: -14px; }
.dex-arrow.next { right: -14px; }
@media (max-width: 640px) { .dex-arrow { display: none !important; } }
.dex-set-card {
  display: flex; flex-direction: column; overflow: hidden;
  background: linear-gradient(180deg, #efe9fb, #e6def7);
  border: 1.5px solid #2B1930; border-radius: 16px;
  box-shadow: 0 4px 14px rgba(43,25,48,0.10);
  transition: transform 0.18s ease, box-shadow 0.18s ease;
}
.dex-set-card:hover { transform: translateY(-4px); box-shadow: 0 14px 30px rgba(43,25,48,0.22); }
/* Full-bleed box in both fit modes, so the cover occupies the same height
   either way and every tile's body starts on the same line. A fitted cover
   draws its white frame with padding INSIDE this box rather than by insetting
   the box itself — insetting made the box narrower, and at a fixed 4/5 that
   made it shorter too, which pushed the two tiles out of alignment. */
.dex-set-cover {
  position: relative; aspect-ratio: 4 / 5; margin: 0;
  background: #fff; border-radius: 0; padding: 10px;
  display: flex; align-items: center; justify-content: center; overflow: hidden;
}
/* contain, not cover: the pack art must sit whole inside the frame, never cropped. */
/* Per-set choice (dex_sets.cover_fit): show the whole cover, or fill the frame
   and crop. Applies to the set tile here and the set page's banner. */
.dex-set-cover.is-fit img, .dex-set-hero-cover.is-fit img { object-fit: contain; }
.dex-set-cover.is-fill img, .dex-set-hero-cover.is-fill img { object-fit: cover; }
/* Filling means filling the tile, not just the white panel inside it: the frame
   and its inset are dropped so the art bleeds to the edge. The tile's own
   overflow:hidden rounds the top corners. Fitted covers keep the white frame,
   which is what letterboxed banner art needs to sit against. */
.dex-set-cover.is-fill { padding: 0; background: transparent; }
.dex-set-cover img { width: 100%; height: 100%; object-fit: contain; }
.dex-set-cover-fallback { font-family: 'Inter', sans-serif; font-size: 2.4rem; font-weight: 600; color: #b3a6d6; }
.dex-set-cover-fallback.big { font-size: 4.5rem; }
.dex-set-symbol { position: absolute; right: 8px; bottom: 8px; width: 30px; height: 30px; object-fit: contain; filter: drop-shadow(0 2px 4px rgba(0,0,0,0.25)); background: none; }

.dex-set-body { background: #2B1930; color: #fff; padding: 11px 13px 0; display: flex; flex-direction: column; gap: 8px; flex: 1 1 auto; }
.dex-set-title { font-size: 0.92rem; font-weight: 700; color: #fff; line-height: 1.25; }
.dex-set-foot {
  display: flex; align-items: center; justify-content: space-between; gap: 8px;
  margin: 0 -13px; padding: 9px 13px; border-top: 1px solid rgba(255,255,255,0.12);
  font-size: 0.74rem; margin-top: auto;
}
/* Gold, as in the reference — warm enough to carry strong contrast against the
   dark plum panel and to read as a distinct accent from the rarity colours. */
.dex-set-code { font-weight: 800; color: #FFC94A; letter-spacing: 0.04em; }
.dex-set-total { color: rgba(255,255,255,0.82); font-weight: 600; white-space: nowrap; }

/* ---- Rarity badge row (on the dark panel) ---- */
.dex-rarity-badges { display: flex; flex-wrap: wrap; gap: 4px; }
.dex-rb { display: inline-flex; align-items: baseline; gap: 3px; background: rgba(255,255,255,0.10); border: 1px solid rgba(255,255,255,0.14); border-radius: 6px; padding: 1px 5px; font-size: 0.63rem; }
/* Neutral, like the card captions and filter chips. Light rather than the
   captions' grey because these badges sit on the dark panel. */
.dex-rb-code { font-weight: 800; color: rgba(255,255,255,0.92); }
.dex-rb-n { color: rgba(255,255,255,0.7); font-weight: 700; }

/* ---- Set detail ---- */
.dex-set-page { padding-top: 8px; }
.dex-crumbs { max-width: 1280px; margin: 0 auto; padding: 26px 24px 0; font-size: 0.82rem; color: #9089A0; }
.dex-crumbs a { color: #7A5C8E; font-weight: 600; }
.dex-crumbs a:hover { text-decoration: underline; }
.dex-crumbs .sep { margin: 0 7px; }
.dex-set-hero { max-width: 1280px; margin: 14px auto 0; padding: 0 24px; display: grid; grid-template-columns: 260px 1fr; gap: 28px; align-items: start; }
/* 4/5 like the set tiles on the index, so a cover is framed the same way
   wherever it appears. Portrait pack art is the common case, and the old 16/10
   letterboxed it down to a sliver. */
.dex-set-hero-cover { border-radius: 14px; overflow: hidden; aspect-ratio: 4 / 5; background: linear-gradient(135deg, #efeafb, #e2f0e4); display: flex; align-items: center; justify-content: center; }
.dex-set-hero-cover img { width: 100%; height: 100%; object-fit: contain; }
/* Matches .collection-head h1 (the catalog page title) so Candydex reads as the
   same site: Inter, regular weight, slight tracking. */
.dex-set-hero-info h1 { font-family: 'Inter', sans-serif; font-style: normal; font-size: 2.2rem; font-weight: 400; letter-spacing: 0.01em; color: #0B0B0D; }
.dex-set-hero-meta { display: flex; flex-wrap: wrap; gap: 8px; margin: 12px 0; }
/* Set facts, styled like the card viewer's table so a set and a card read the
   same way. Sized to its content rather than the column, so a short value list
   doesn't stretch across the hero.

   Labels sit flush left. Right-aligning them pushed each one hard against its
   value and left a ragged gap down the left edge, so the column had no line to
   start from — the labels are the thing you scan, and they scan top to bottom. */
/* One grid for the whole table rather than a grid per row: the label column is
   sized to the longest label across every row, so a set that adds "Sobres por
   Booster Box" widens the column instead of wrapping that one label onto two
   lines. Per-row grids could not do this — each sized to its own content, which
   is why the column used to be pinned at 130px. */
.dex-set-facts {
  margin: 12px 0; border: 1px solid #e4dcec; border-radius: 10px; overflow: hidden;
  display: inline-grid; grid-template-columns: max-content minmax(120px, auto); min-width: 260px;
}
/* The rows exist for the markup's sake (a dl wants its pairs wrapped); the cells
   are what the grid lays out. */
.dex-set-facts > div { display: contents; }
.dex-set-facts dt, .dex-set-facts dd { align-self: stretch; font-size: 0.85rem; }
.dex-set-facts dt { margin: 0; padding: 8px 12px; background: #f4f1f8; color: #2B1930; font-weight: 800; white-space: nowrap; }
.dex-set-facts dt::after { content: ':'; }
.dex-set-facts dd { margin: 0; padding: 8px 12px; color: #7A5C8E; font-weight: 600; font-variant-numeric: tabular-nums; min-width: 0; overflow-wrap: anywhere; }
/* Separators live on the cells now that the row element draws nothing. */
.dex-set-facts > div + div dt, .dex-set-facts > div + div dd { border-top: 1px solid #efe9f4; }

/* The key to the rarity codes printed on every card tile. A horizontal band, so
   it can sit either under the details on a phone or beside them on a desktop
   without changing shape — as a tall column it left a hole down the side of the
   facts table, which is what it was before. */
.dex-rarity-key {
  margin: 14px 0 0; padding: 10px 14px; max-width: 60ch;
  border: 1px solid #e4dcec; border-radius: 10px; background: #fbf9fd;
}

/* Wide screens only. The facts table is a narrow column and leaves the width
   beside it empty, so the key moves up into it. Placed explicitly rather than by
   reordering the markup: below this width the whole block is ignored and the
   three pieces stack in document order — facts, description, key — which is how
   the phone already reads and did not need fixing.
   1150px, not the 861px where the hero stacks: the cover, the facts table and
   two entry columns side by side need about 1149px between them, and below that
   the key was squeezed into a 176px column where its entries wrapped and
   overflowed the box. Stacking early is better than side by side and broken. */
@media (min-width: 1150px) {
  .dex-set-top {
    display: grid; grid-template-columns: max-content minmax(0, 1fr);
    column-gap: 22px; align-items: start;
  }
  .dex-set-top > .dex-set-facts { grid-column: 1; grid-row: 1; }
  /* Spans both columns, and not only for the room: column 1 is max-content, so
     leaving the description in it made a long paragraph — not the facts table —
     decide how wide that column was, stretching the table to 559px on the one
     set that still has prose. It keeps its own 60ch cap for readability. */
  .dex-set-top > .dex-set-desc { grid-column: 1 / -1; grid-row: 2; }
  /* Same top margin as the facts table so the two boxes start on one line.
     Capped rather than filling the column: stretched to the full width beside
     the facts, two entries ended up ~150px apart with 90px of dead box after
     them. 460px is the width two entry columns actually need, so the box closes
     up around them and the space left over falls outside it, where it reads as
     page margin instead of a hole in a panel. */
  .dex-set-top > .dex-rarity-key { grid-column: 2; grid-row: 1; margin-top: 12px; max-width: 460px; }
}
.dex-rk-label {
  display: block; margin-bottom: 8px;
  font-size: 0.7rem; font-weight: 800; letter-spacing: 0.06em;
  text-transform: uppercase; color: #8A7A93;
}
/* Columns, not a grid: the rarities arrive in printed order (C, U, R, RR, ACE,
   AR, SR, SAR, UR) and that order has to read straight down the first column and
   then down the second. A grid — like the wrapping flex row before it — fills
   left to right, so it laid the sequence out across the rows instead and the eye
   had to zigzag to follow it. Multi-column fills top to bottom by definition,
   and balances the two columns, so an odd count puts the extra entry in the
   first one.
   "2 200px" caps it at two columns and gives each a 200px floor, which is what
   the widest entry in the data needs — the SAR box, "Special Art Rare" and a
   three-digit count measure 188px, and a 180px column wrapped that one entry
   onto two lines while every neighbour stayed on one. Below ~418px the floor
   wins and the list becomes a single column, as it did before. */
.dex-rk-items {
  columns: 2 200px; column-gap: 18px;
  /* Row spacing has to come from the entries themselves — a multi-column box has
     no row-gap — so it lives on .dex-rk-item as a bottom margin. No correction is
     needed here for the trailing one: a balanced column's height is measured to
     the last entry's box, not past its margin, so the panel already closes 11px
     under the last line, matching the 11px above the label. */
  margin: 0; padding: 0; list-style: none;
}
/* Three tracks inside each entry for the same reason: the code box is 2-3
   characters wide and would otherwise shift the reading beside it left or right
   depending on whether it says C or SAR. */
/* Content-sized tracks packed to the left, not a stretching 1fr for the reading:
   a 1fr pushed the count to the far edge of its column, so "Common" and its 183
   ended up a third of the band apart while "Special ART Rare" and its 34 nearly
   touched — the spacing changed with the length of the word. Packed left, every
   entry has the same 8px before its number and both columns read alike. */
.dex-rk-item { display: grid; grid-template-columns: 34px minmax(0, auto) auto; justify-content: start; align-items: center; gap: 8px; font-size: 0.85rem; margin-bottom: 8px; break-inside: avoid; }
/* The code gets the same boxed treatment it has on a card tile, so the eye can
   match "SAR" here to "SAR" down in the grid without being told to. */
.dex-rk-code {
  padding: 2px 0; border: 1px solid #e4dcec; border-radius: 6px; background: #f0eaf6;
  color: #2B1930; font-size: 0.78rem; font-weight: 800; text-align: center; white-space: nowrap;
}
.dex-rk-text { color: #5B4B6B; font-weight: 600; }
/* How many cards carry the rarity — present, but quieter than the reading. */
.dex-rk-n { color: #A08BB0; font-weight: 700; font-variant-numeric: tabular-nums; }
.dex-chip { font-size: 0.8rem; font-weight: 600; color: #5B4B6B; background: #f3effa; border: 1px solid #e8e0f3; border-radius: 999px; padding: 4px 11px; }
/* Written in the admin's rich-text field, so this arrives as real markup
   (paragraphs, lists, bold) rather than typed line breaks. */
.dex-set-desc { color: #555; margin: 8px 0 0; max-width: 60ch; }
.dex-set-desc > :first-child { margin-top: 0; }
.dex-set-desc > :last-child { margin-bottom: 0; }
.dex-set-desc p { margin: 0 0 8px; }
.dex-set-desc ul, .dex-set-desc ol { margin: 0 0 8px; padding-left: 20px; }
.dex-set-desc li { margin: 2px 0; }
.dex-set-desc h1, .dex-set-desc h2, .dex-set-desc h3,
.dex-set-desc h4, .dex-set-desc h5, .dex-set-desc h6 {
  font-size: 0.98rem; font-weight: 800; color: #2B1930; margin: 12px 0 6px;
}
.dex-set-desc strong, .dex-set-desc b { color: #2B1930; font-weight: 700; }
.dex-set-desc a { color: #7A5C8E; font-weight: 600; text-decoration: underline; }
.dex-login-hint { margin: 14px 0 0; font-size: 0.9rem; color: #6C5A76; background: #F3EFFA; border: 1px solid #E1D9F0; border-radius: 10px; padding: 10px 13px; }
.dex-login-hint a { color: #7A5C8E; font-weight: 700; }

/* ---- Cross-sell strip ---- */
.dex-crosssell { max-width: 1280px; margin: 30px auto 0; padding: 0 24px; }
.dex-crosssell h2 { font-size: 1.15rem; font-weight: 600; color: #0B0B0D; margin: 0 0 14px; }
.dex-crosssell-row { display: flex; gap: 16px; overflow-x: auto; padding-bottom: 6px; }
.dex-cs-card { flex: 0 0 170px; background: #fff; border: 1px solid #ece8f2; border-radius: 12px; overflow: hidden; transition: transform 0.16s ease, box-shadow 0.16s ease; }
.dex-cs-card:hover { transform: translateY(-2px); box-shadow: 0 8px 20px rgba(122,92,142,0.16); }
.dex-cs-img { aspect-ratio: 1; background: #faf8fc; display: flex; align-items: center; justify-content: center; }
.dex-cs-img img { width: 100%; height: 100%; object-fit: contain; mix-blend-mode: multiply; }
.dex-cs-body { padding: 9px 11px 12px; display: flex; flex-direction: column; gap: 5px; }
.dex-cs-name { font-size: 0.84rem; font-weight: 600; color: #0B0B0D; line-height: 1.3; }

/* ---- Filter chips + card grid ---- */
.dex-toolbar { max-width: 1280px; margin: 26px auto 0; padding: 0 24px; }
/* Search sits above the chips rather than beside them: the chip row already
   wraps to several lines on a big set, and a field sharing that row would be
   pushed somewhere different on every page. */
.dex-search { position: relative; max-width: 340px; margin: 0 0 14px; }
.dex-search input {
  width: 100%; font-family: inherit; font-size: 0.9rem; color: #2B1930;
  background: #fff; border: 1.5px solid #e8e0f3; border-radius: 999px;
  padding: 9px 36px 9px 38px; transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.dex-search input::placeholder { color: #a99fb5; }
.dex-search input:focus { outline: none; border-color: var(--lavender); box-shadow: 0 0 0 3px rgba(169,155,232,0.18); }
.dex-search-icon {
  position: absolute; left: 13px; top: 50%; transform: translateY(-50%);
  width: 16px; height: 16px; color: #9089A0; pointer-events: none;
}
.dex-search-clear {
  position: absolute; right: 6px; top: 50%; transform: translateY(-50%);
  display: grid; place-items: center; width: 26px; height: 26px; padding: 0;
  border: 0; border-radius: 50%; background: none; color: #9089A0; cursor: pointer;
}
.dex-search-clear:hover { background: #f4f1f8; color: #2B1930; }
.dex-search-clear[hidden] { display: none; }
.dex-search-clear svg { width: 14px; height: 14px; }
@media (max-width: 860px) {
  /* iOS Safari zooms the page when you focus an input whose text is under 16px,
     and it does not zoom back out — you are left scrolled sideways mid-search.
     Same threshold admin.css uses for the same reason. */
  .dex-search input { font-size: 16px; }
  .dex-search { max-width: none; }
}
.dex-filter-chips { display: flex; flex-wrap: wrap; gap: 8px; }
/* Same grey as the card captions: the rarity reads from its symbol, so the chips
   carry no colour swatch either. Selection is shown by the filled active state. */
.dex-fchip { display: inline-flex; align-items: center; gap: 6px; font-family: inherit; font-size: 0.82rem; font-weight: 600; color: #6C5A76; background: #fff; border: 1.5px solid #e8e0f3; border-radius: 999px; padding: 6px 12px; cursor: pointer; transition: border-color 0.15s ease, background 0.15s ease; }
.dex-fchip:hover { border-color: var(--lavender); }
.dex-fchip.active { background: #2B1930; border-color: #2B1930; color: #fff; }
.dex-fchip.active .dex-fchip-n { color: #cdbcd8; }
.dex-fchip-n { color: #9089A0; font-weight: 700; }
.dex-card-grid { max-width: 1280px; margin: 20px auto 0; padding: 0 24px; display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); gap: 18px; }
.dex-card { display: flex; flex-direction: column; gap: 8px; }
.dex-card-img { position: relative; aspect-ratio: 63 / 88; border-radius: 10px; overflow: hidden; background: #f4f1f8; display: flex; align-items: center; justify-content: center; box-shadow: 0 2px 8px rgba(43,25,48,0.08); }
.dex-card-img img { width: 100%; height: 100%; object-fit: cover; }
/* Per-set choice (dex_sets.card_fit): fill each tile and crop, or show the
   whole scan. 'contain' pads the tile so a bordered scan is not cut. */
.dex-card-grid.cards-fill .dex-card-img img { object-fit: cover; }
.dex-card-grid.cards-fit .dex-card-img img { object-fit: contain; }
.dex-card-grid.cards-fit .dex-card-img { background: #fff; }
.dex-card-noimg { font-size: 1.4rem; font-weight: 700; color: #c3bad2; }
/* One grey caption under the artwork — "Clefable - 01 01/07" — followed by the
   rarity as its own symbol, which keeps the rarity's colour so the tier is
   readable at a glance while the text stays uniform. Nothing is overlaid on the
   artwork, so the card image stays unobstructed. */
/* Laid out as inline text, not a flex row: a caption too long for the tile
   ("Basic Fighting Energy - 20 01/06") then wraps onto a second line with the
   rarity following the last word, instead of truncating away the number ID.
   The whole caption, symbol included, sits in one grey — the rarity reads from
   the symbol itself (● ◆ ★ ★★ ★★★), so colour would only add noise. */
.dex-card-info { padding: 0 2px; font-size: 0.78rem; line-height: 1.3; color: #6C5A76; }
.dex-card-name { font-weight: 600; }
.dex-card-rarity { font-weight: 800; letter-spacing: 0.02em; white-space: nowrap; }
/* Transparent overlay covering the artwork; the ownership toggle stacks above it
   so it stays clickable. */
.dex-card-open { position: absolute; inset: 0; z-index: 1; padding: 0; border: 0; background: none; cursor: zoom-in; font: inherit; }

/* ---- Candydex → Singles cross-link badge ---- */
/* Sits above the transparent viewer overlay so the link stays clickable. */
.dex-sale-badge { position: absolute; top: 8px; left: 8px; z-index: 2; font-size: 0.68rem; font-weight: 800; letter-spacing: 0.02em; text-transform: uppercase; color: #fff; background: #2fbf71; border-radius: 999px; padding: 3px 9px; text-decoration: none; box-shadow: 0 2px 6px rgba(0,0,0,0.18); }
.dex-sale-badge:hover { background: #27a862; }

/* ---- Singles & Slabs section ---- */
/* Built on the Candydex grid/modal; only the tabs, the price/buy rows and the
   grade badge are its own. */
.singles-tabs { max-width: 1280px; margin: 22px auto 0; padding: 0 24px; display: flex; gap: 8px; }
.singles-tab { font-family: inherit; font-size: 0.95rem; font-weight: 700; color: #6C5A76; background: #fff; border: 1.5px solid #e8e0f3; border-radius: 999px; padding: 8px 18px; cursor: pointer; display: inline-flex; align-items: center; gap: 8px; transition: border-color 0.15s ease, background 0.15s ease, color 0.15s ease; }
.singles-tab:hover { border-color: var(--lavender); }
.singles-tab.is-active { background: #2B1930; border-color: #2B1930; color: #fff; }
.singles-tab-n { font-weight: 800; font-size: 0.8rem; opacity: 0.8; }
.singles-panel { display: none; }
.singles-panel.is-active { display: block; }

/* Singles/Slabs caption: name and rarity on one line (rarity a compact tag right
   after the name, never wrapping to a lonely line of its own), so every tile's
   caption is exactly one line tall and the grid stays a single standard size. A
   name too long simply ellipses. The Candydex card number is not shown on the
   tile — only the name, rarity and (for slabs) the grade line appear. */
.singles-card-info { display: flex; align-items: baseline; gap: 6px; flex-wrap: nowrap; }
.singles-card-info .dex-card-name { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.singles-card-info .dex-card-rarity { flex: 0 0 auto; }
/* A dash separates the name from the rarity — "Brock's Scouting - SAR" — on
   both singles and slabs. Kept as a pseudo-element so the tile's searchable
   text stays clean, and it only appears when a rarity is present. */
.singles-card-info .dex-card-rarity::before { content: "- "; color: #6C5A76; font-weight: 600; }
/* The grade/condition line (e.g. "PSA 10") sits tight under the name — the
   negative margin cancels most of the card's flex gap so it reads as a label
   belonging to the name, not a detached row. */
.singles-detail { display: block; margin-top: -6px; padding: 0 2px; font-size: 0.72rem; color: #9089A0; }
.singles-buy { display: flex; align-items: center; justify-content: space-between; gap: 8px; padding: 6px 2px 2px; }
.singles-price { font-weight: 800; color: #2B1930; font-size: 0.9rem; }
.singles-compare { color: #b3a8bd; font-weight: 600; font-size: 0.78rem; margin-left: 4px; }
/* The colones charge shown under a dollar price. */
.singles-price-sub { display: block; font-weight: 600; font-size: 0.72rem; color: #9089A0; }
.sm-price-sub { font-size: 0.85rem; font-weight: 600; color: #9089A0; margin-left: 6px; }
/* The quick-add reuses the catalog's .card-add, which is opacity:0 + absolutely
   positioned so it only appears, pinned over the image, when a catalog card is
   hovered. The singles layout places it inline in a row (and in the modal), so
   it must sit static and stay visible — otherwise the whole button, cart icon
   included, is invisible. The icon itself is the catalog's, unchanged. On mobile
   the tile button collapses to the same circular icon the catalog uses (the
   shared @media rule hides the label and rounds it). The modal button keeps its
   label and pill shape at every size. */
/* Singles tiles show an icon-only add button at every size (not just mobile):
   the row is price + button and gets cramped with a text label, so the cart icon
   alone is the standard here. The modal keeps a full labeled pill. */
.singles-buy .card-add { position: static; opacity: 1; transform: none; padding: 9px; border-radius: 50%; gap: 0; }
.singles-buy .card-add .ca-label { display: none; }
.sm-actions .card-add { position: static; opacity: 1; transform: none; padding: 10px 16px; border-radius: 999px; }
.sm-actions .card-add .ca-label { display: inline; }

/* Singles viewer: the Candydex modal plus a price and a buy button. */
.sm-title { margin: 0 0 6px; font-size: 1.15rem; color: #2B1930; }
.sm-price { font-size: 1.1rem; font-weight: 800; color: #2B1930; margin-bottom: 12px; }
.sm-price s { color: #b3a8bd; font-weight: 600; font-size: 0.85rem; margin-left: 6px; }
.sm-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 10px; margin-top: 14px; }
.sm-actions .card-add { position: static; }
/* The Candydex link. Styled explicitly (it used .btn.ghost, which rendered white
   text — invisible on the white modal, leaving only the ↗ emoji on iOS). */
.sm-dex { display: inline-flex; align-items: center; gap: 6px; font-family: inherit; font-size: 0.85rem; font-weight: 600; color: #6a4ea0; background: #f4f1f8; border: 1px solid #e4dcec; border-radius: 999px; padding: 9px 16px; text-decoration: none; }
/* The script hides this for cards with no Candydex link by setting [hidden];
   the explicit display above would otherwise override the UA [hidden] rule and
   keep an inert "Ver en Candydex" button on unlinked cards. */
.sm-dex[hidden] { display: none; }
.sm-dex:hover { background: #ece5f5; color: #4d3a78; }
.sm-dex svg { width: 14px; height: 14px; }

/* Hover: the same "lift + shadow + gentle zoom" the catalog cards use, so a
   single/slab tile reads as interactive the same way a product does. Singles are
   never "owned", so they also drop the Candydex dimming and stay full-opacity. */
.singles-card { transition: transform 0.18s ease; }
.singles-card:hover { transform: translateY(-4px); }
.singles-card .dex-card-img { transition: box-shadow 0.18s ease; }
.singles-card:hover .dex-card-img { box-shadow: 0 14px 30px rgba(43, 25, 48, 0.16); }
.singles-card .dex-card-img img { opacity: 1; transition: transform 0.28s ease; }
.singles-card:hover .dex-card-img img { transform: scale(1.05); }
/* Slabs are taller than a raw card. Give the slab tiles the slab's own ratio
   (828×1400) and drop the white letterbox background, so the graded case fills
   the frame instead of floating on white bars. Uploads at the recommended size
   fill it exactly; anything slightly off letterboxes onto the page, not white. */
.dex-card-grid.singles-grid[data-kind="slab"] .dex-card-img { aspect-ratio: 828 / 1400; background: transparent; box-shadow: none; }

/* ---- Card viewer ---- */
body.dex-modal-open { overflow: hidden; }
.dex-modal { position: fixed; inset: 0; z-index: 200; display: flex; align-items: center; justify-content: center; padding: 20px; }
.dex-modal[hidden] { display: none; }
.dex-modal-backdrop { position: absolute; inset: 0; background: rgba(20,10,24,0.72); backdrop-filter: blur(3px); }
.dex-modal-panel {
  position: relative; z-index: 1; background: #fff; border-radius: 18px; overflow: hidden;
  width: min(420px, 100%); display: flex; flex-direction: column;
  box-shadow: 0 24px 60px rgba(0,0,0,0.4);
  /* Two declarations, coarsest first: a phone browser's vh is the height with the
     toolbars retracted, so a dialog sized in vh runs underneath the toolbar that is
     actually on screen. dvh is the height visible right now; browsers too old to
     know it keep the vh line. */
  max-height: calc(100vh - 40px);
  max-height: calc(100dvh - 40px);
}
/* Fixed-height stage rather than one sized by the artwork: every card then opens
   at the same dimensions, and portrait, landscape and square art all sit centred
   inside the same box instead of resizing the whole dialog. */
.dex-modal-media {
  position: relative; background: #f4f1f8; display: flex; align-items: center; justify-content: center;
  flex: 0 0 auto; padding: 14px;
  /* Same vh/dvh pair as the panel, and for the same reason. */
  height: min(56vh, 470px);
  height: min(56dvh, 470px);
}
.dex-modal-media img { max-width: 100%; max-height: 100%; width: auto; height: auto; object-fit: contain; display: block; margin: auto; }
.dex-modal-noimg { display: block; padding: 90px 0; font-size: 1.6rem; font-weight: 800; color: #c3bad2; }
.dex-modal-btn, .dex-modal-nav {
  position: absolute; display: flex; align-items: center; justify-content: center;
  border: 0; cursor: pointer; border-radius: 50%; background: rgba(23,12,26,0.55); color: #fff;
  backdrop-filter: blur(2px); transition: background 0.15s ease, transform 0.12s ease;
}
.dex-modal-btn { width: 34px; height: 34px; top: 10px; }
.dex-modal-btn svg { width: 17px; height: 17px; }
.dex-modal-btn:hover, .dex-modal-nav:hover { background: rgba(23,12,26,0.78); }
.dm-close { right: 10px; }
.dm-own { left: 10px; }
.dm-own[aria-pressed="true"] { background: #6a4ea0; }
.dex-modal-nav { width: 38px; height: 38px; top: 50%; transform: translateY(-50%); }
.dex-modal-nav svg { width: 20px; height: 20px; }
.dex-modal-nav:hover { transform: translateY(-50%) scale(1.06); }
.dm-prev { left: 10px; }
.dm-next { right: 10px; }
/* flex:1 1 auto + min-height:0 lets the info take the space the fixed-height
   media leaves and scroll inside it — otherwise a tall info (price + rows + the
   add/Candydex buttons) overflowed the panel and its bottom buttons were clipped
   and unreachable on a phone. */
.dex-modal-info { padding: 16px 18px 18px; overflow-y: auto; flex: 1 1 auto; min-height: 0; }
/* Label/value rows: shaded label column, value alongside — the card-information
   layout the printed listings use. */
/* One shared label column for the whole table: it is at least 88px and grows to
   fit the longest label ("Graduación"), and every row uses that same width via
   subgrid — so all the tinted label cells line up and share one right edge
   instead of each sizing to its own text. */
.dm-rows { margin: 0; border: 1px solid #e4dcec; border-radius: 10px; overflow: hidden; display: grid; grid-template-columns: minmax(88px, max-content) 1fr; }
.dm-rows > div { display: grid; grid-template-columns: subgrid; grid-column: 1 / -1; align-items: baseline; font-size: 0.85rem; }
/* display:grid above outranks the [hidden] attribute's display:none, so an
   optional row (variant) would stay visible without this. */
.dm-rows > div[hidden] { display: none; }
.dm-rows > div + div { border-top: 1px solid #efe9f4; }
.dm-rows dt { margin: 0; padding: 8px 12px; background: #f4f1f8; color: #2B1930; font-weight: 800; white-space: nowrap; }
.dm-rows dt::after { content: ':'; }
.dm-rows dd { margin: 0; padding: 8px 12px; color: #7A5C8E; font-weight: 600; font-variant-numeric: tabular-nums; min-width: 0; overflow-wrap: anywhere; }
.dm-rows dd a { color: #7A5C8E; }
.dm-rows dd a:hover { text-decoration: underline; }
.dm-code { font-weight: 700; color: #9089A0; }
/* No phone-specific override on purpose: the viewer is the same centred, rounded
   dialog at every width, which is what it is for. It used to go full-screen below
   480px — width and height 100%, square corners, no backdrop — and that broke the
   three things the desktop layout gets right:
   the panel was forced to the full 844px of a phone screen while its content
   needed 674, leaving 170px of dead white under the details box;
   there was no margin around the panel, so the artwork and the box below it had no
   shared edge to line up against;
   and it re-capped the image at 56vh (473px) inside a stage capped at 470px, so
   the card overflowed the very box meant to frame it.
   The base rules already fit a phone: min(420px, 100%) inside 20px of padding is a
   350px panel on a 390px screen, centred, with the backdrop showing around it. */

@media (max-width: 860px) {
  .dex-set-hero { grid-template-columns: 1fr; gap: 16px; }
  .dex-set-hero-cover { max-width: 320px; }
}
@media (max-width: 640px) {
  .dex-series, .dex-crumbs, .dex-set-hero, .dex-crosssell, .dex-toolbar, .dex-card-grid { padding-left: 16px; padding-right: 16px; }
  /* Two tiles to a screen, as the wrapping grid used to show — the rest of the
     series is a swipe away. */
  .dex-set-row { gap: 14px; }
  .dex-set-row .dex-set-card { flex-basis: calc(50% - 7px); width: calc(50% - 7px); }
  .dex-card-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 14px; }
  .dex-set-hero-info h1 { font-size: 1.7rem; }
  /* Shrink the image stage on a phone so the details and the action buttons
     below it fit without the buttons being pushed off the bottom of the modal. */
  .dex-modal-media { height: min(42dvh, 360px); }
}

/* ---- Candydex: ownership checklist ---- */
.dex-progress { max-width: 1280px; margin: 24px auto 0; padding: 0 24px; }
.dex-progress-head { display: flex; align-items: baseline; justify-content: space-between; margin-bottom: 7px; }
.dex-progress-label { font-size: 0.82rem; font-weight: 700; color: #5B4B6B; }
.dex-progress-count { font-size: 0.92rem; font-weight: 800; color: #0B0B0D; font-variant-numeric: tabular-nums; }
.dex-progress-bar { height: 9px; border-radius: 999px; background: #ece8f2; overflow: hidden; }
.dex-progress-bar span { display: block; height: 100%; border-radius: 999px; background: linear-gradient(90deg, #A99BE8, #E63E82); transition: width 0.28s ease; }

/* The "own it" checkmark button, bottom-left of each card image. */
.dex-own-toggle {
  position: absolute; left: 7px; bottom: 7px; z-index: 3; width: 28px; height: 28px; padding: 0;
  display: flex; align-items: center; justify-content: center; cursor: pointer;
  border-radius: 50%; border: 2px solid rgba(255,255,255,0.9); background: rgba(43,25,48,0.34);
  color: #fff; backdrop-filter: blur(2px); transition: background 0.15s ease, transform 0.12s ease, border-color 0.15s ease;
}
/* The checkmark fades with the button rather than popping, so the owned/unowned
   change reads as one motion. */
.dex-own-toggle svg { width: 15px; height: 15px; opacity: 0.55; transition: opacity 0.15s ease; }
.dex-own-toggle:hover { transform: scale(1.08); background: rgba(43,25,48,0.5); }
/* Disabled only while the toggle request is in flight — a few dozen ms. It must
   stay visually identical, or every click flashes the button dimmer and back,
   which reads as jank on top of the optimistic state change. */
.dex-own-toggle:disabled { cursor: default; }
.dex-card.is-owned .dex-own-toggle { background: #6a4ea0; border-color: #6a4ea0; }
.dex-card.is-owned .dex-own-toggle svg { opacity: 1; }
/* Owned cards read as "collected": full colour + a purple ring. Unowned stay
   slightly dimmed so the ones you still need stand out. Both the ring and the
   dimming are transitioned so toggling doesn't snap.

   The ring is the store's deep purple (the same one behind the stock and cart
   badges) rather than a generic green: card art in this hobby is mostly pastel
   pink and lavender, so a light brand tint would sink into it — this one holds
   its edge against the art while still belonging to the palette. */
.dex-card .dex-card-img { transition: box-shadow 0.15s ease; }
.dex-card.is-owned .dex-card-img { box-shadow: 0 0 0 2px #6a4ea0, 0 2px 8px rgba(43,25,48,0.12); }
.dex-card .dex-card-img img { transition: opacity 0.15s ease; }
.dex-card:not(.is-owned) .dex-card-img img { opacity: 0.9; }

/* ---- Candydex: "Mi colección" on the account dashboard ---- */
.dex-collection-card { margin-bottom: 24px; }
/* Standalone cards stacked above the account grid need their own vertical
   rhythm — the grid's gap only spaces the cards inside it, not these. */
.candy-summary-card { margin-bottom: 24px; }
.dcc-head { display: flex; align-items: baseline; justify-content: space-between; gap: 12px; flex-wrap: wrap; }
.dcc-explore { font-size: 0.85rem; font-weight: 700; color: #7A5C8E; }
.dcc-explore:hover { text-decoration: underline; }
.dcc-total { color: #555; margin: 4px 0 16px; }
.dcc-sets { display: grid; grid-template-columns: repeat(auto-fill, minmax(240px, 1fr)); gap: 14px; }
.dcc-set { display: block; padding: 12px 14px; border: 1px solid #ece8f2; border-radius: 12px; background: #fff; transition: border-color 0.15s ease, box-shadow 0.15s ease, transform 0.15s ease; }
.dcc-set:hover { border-color: var(--lavender); box-shadow: 0 6px 16px rgba(122,92,142,0.14); transform: translateY(-1px); }
.dcc-set-top { display: flex; align-items: baseline; justify-content: space-between; gap: 8px; margin-bottom: 8px; }
.dcc-set-name { font-weight: 700; color: #0B0B0D; font-size: 0.92rem; }
.dcc-set-count { font-size: 0.78rem; font-weight: 700; color: #857E95; white-space: nowrap; font-variant-numeric: tabular-nums; }
.dcc-bar { height: 8px; border-radius: 999px; background: #ece8f2; overflow: hidden; }
.dcc-bar span { display: block; height: 100%; border-radius: 999px; background: linear-gradient(90deg, #A99BE8, #E63E82); }


/* ============================ Giveaways ============================
   The rifas we run on Instagram: a flyer, a countdown, the participant list and
   the wheel we spin live. Laid out as one page rather than as a feed, because
   during a live everyone is looking at the same screen and scrolling past the
   part that matters is the failure mode.

   Colour-wise this stays inside the store's palette (lavender, pink, mint) so a
   giveaway page reads as the same site, not as a landing page bolted on. */
.gw-page { padding-bottom: 64px; }
/* Everything on this page that is shown and hidden by script — the result box,
   the counter once it runs out, the rows the search filter drops — is a flex or
   grid box, and a display rule beats the `hidden` attribute. Without this the
   empty "Ganador" panel sits there before the first spin and the search filter
   hides nothing. */
.gw-page [hidden] { display: none !important; }
.gw-kicker { font-size: 0.8rem; font-weight: 700; letter-spacing: 0.06em; color: #7A5C8E; text-transform: uppercase; }
.gw-head { max-width: 1280px; margin: 0 auto; padding: 40px 24px 0; display: flex; flex-direction: column; gap: 6px; }
.gw-head h1 { font-size: 2.6rem; font-weight: 400; letter-spacing: 0.01em; color: #0B0B0D; margin: 2px 0 0; }
.gw-collab { color: #555; margin: 0; }
.gw-collab strong { color: #7A5C8E; }
.gw-prize { color: #333; margin: 4px 0 0; font-size: 1.05rem; }

/* ---- Flyer ----
   Two files, one for each shape: the wide export on a desktop, the square
   Instagram post on a phone (picked by <picture> in the view). The band is
   centred and capped rather than full-bleed, so the art keeps its own edges
   instead of being cropped to the viewport. */
.gw-flyer-band { max-width: 1280px; margin: 22px auto 0; padding: 0 24px; }
.gw-flyer { display: block; }
.gw-flyer img {
  display: block; width: 100%; height: auto; max-height: 560px;
  object-fit: contain; border-radius: 16px; background: #f6f3fa;
  box-shadow: 0 10px 30px rgba(43, 25, 48, 0.13);
}

/* ---- Countdown ---- */
.gw-count-band { max-width: 1280px; margin: 22px auto 0; padding: 0 24px; text-align: center; }
.gw-count { display: inline-flex; gap: 10px; }
.gw-count .unit {
  min-width: 74px; padding: 10px 12px; border-radius: 14px;
  background: linear-gradient(160deg, #F3EEFC, #EDE6FA);
  border: 1px solid #e2d9f3; display: flex; flex-direction: column; gap: 2px;
}
.gw-count .n { font-size: 1.7rem; font-weight: 700; color: #3B2350; font-variant-numeric: tabular-nums; line-height: 1.1; }
.gw-count .l { font-size: 0.7rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.06em; color: #7A5C8E; }
.gw-count-eta, .gw-count-over, .gw-closed { color: #555; margin: 10px 0 0; }
.gw-count-over { font-weight: 700; color: #7A5C8E; }
.gw-closed { font-weight: 700; }

/* ---- Winners ---- */
.gw-winners { max-width: 1280px; margin: 22px auto 0; padding: 18px 24px; }
.gw-winners h2 { font-size: 0.78rem; text-transform: uppercase; letter-spacing: 0.06em; color: #7A5C8E; margin: 0 0 10px; }
.gw-winners ul { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 10px; }
.gw-winners li {
  display: flex; align-items: center; gap: 10px; padding: 12px 18px; border-radius: 14px;
  background: linear-gradient(135deg, #FFF3D6, #FFE3F0); border: 1px solid #f3d9e6;
}
.gw-trophy { font-size: 1.3rem; }
.gw-winner-user { font-weight: 700; color: #2B1930; }
.gw-winner-prize { color: #6C5A76; font-size: 0.9rem; }

/* ---- Rules ---- */
.gw-rules { max-width: 1280px; margin: 26px auto 0; padding: 0 24px; }
.gw-rules h2 { font-size: 0.78rem; text-transform: uppercase; letter-spacing: 0.06em; color: #7A5C8E; margin: 0 0 8px; }
/* ---- The instructions block ----
   This holds whatever the admin typed in the rich-text editor: a couple of
   questions as headings, two numbered lists, and a note or two in italics at
   the end. With browser defaults it came out as a flat wall — headings
   indistinguishable from paragraphs, numbers hugging the text, the notes lost
   at the bottom. Styled here rather than asked for again in a different shape:
   the text the store already writes for Instagram is the text that should look
   right. */
.gw-rules-body {
  color: #2B1930; line-height: 1.65; font-size: 0.98rem;
  background: #fff; border: 1px solid #ece8f2; border-radius: 16px; padding: 22px 24px;
  /* Deliberately ONE column. Two looked tighter and broke the first time it met
     real text: multi-column flows by height, so "¿Cómo obtener entradas?" was
     stranded at the foot of the left column with its list at the top of the
     right one. The markup comes from whatever the admin typed, so there is no
     wrapper to keep a heading with its list — and a layout that depends on the
     content being the right length is a layout that breaks on the next
     giveaway. The measure below is what keeps the lines readable instead. */
  max-width: 860px;
}
.gw-rules-body > *:first-child { margin-top: 0; }
.gw-rules-body > *:last-child { margin-bottom: 0; }
.gw-rules-body h3 {
  font-size: 0.82rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.05em;
  color: #7A5C8E; margin: 20px 0 8px; padding-bottom: 6px; border-bottom: 1px solid #f3f0f8;
}
.gw-rules-body p { margin: 8px 0; }
.gw-rules-body strong { color: #3B2350; }

.gw-rules-body ul, .gw-rules-body ol { margin: 8px 0 14px; padding: 0; list-style: none; counter-reset: gwstep; }
.gw-rules-body li { position: relative; margin: 7px 0; padding-left: 30px; }
/* Numbered steps get a filled pill, bullets a candy dot — both drawn, so the
   marker lines up with the text instead of hanging in the gutter. */
.gw-rules-body ol > li { counter-increment: gwstep; }
.gw-rules-body ol > li::before {
  content: counter(gwstep); position: absolute; left: 0; top: 1px;
  width: 21px; height: 21px; border-radius: 999px;
  background: linear-gradient(135deg, #A99BE8, #FF8FBA); color: #fff;
  font-size: 0.72rem; font-weight: 700; display: grid; place-items: center;
}
.gw-rules-body ul > li::before {
  content: ''; position: absolute; left: 7px; top: 9px;
  width: 8px; height: 8px; border-radius: 999px; background: var(--lavender);
}
/* The closing notes are typed in italics and are the two lines people most need
   to see — the entry cap, and what to do with a private profile. Lifted out as
   a highlighted note rather than left as small print. */
.gw-rules-body p > em:only-child {
  display: block; font-style: normal; font-weight: 600; color: #7A5410;
  background: #FFF6DE; border: 1px solid #f3e2b8; border-radius: 10px;
  padding: 9px 13px; margin: 4px 0;
}
.gw-rules-body a { color: #7A5C8E; font-weight: 600; text-decoration: underline; }

@media (max-width: 860px) {
  .gw-rules-body { padding: 16px 18px; }
}

/* ---- Spin log ----
   The audit trail, folded shut. Evidence has to be there and has to be
   findable; it does not have to be the loudest thing on the page. */
.gw-spinlog { border: 1px solid #ece8f2; border-radius: 16px; background: #fff; padding: 4px 18px; }
.gw-spinlog > summary {
  display: flex; align-items: center; gap: 10px; cursor: pointer; padding: 12px 0;
  font-size: 0.86rem; font-weight: 700; color: #2B1930;
}
.gw-spinlog > summary::-webkit-details-marker { color: #A2989E; }
.gw-spinlog-count {
  margin-left: auto; font-size: 0.74rem; font-weight: 700; color: #6a4ea0;
  background: #F3EEFC; border-radius: 999px; padding: 3px 9px;
}
.gw-spinlog-list { list-style: none; margin: 4px 0 14px; padding: 0; }
.gw-spinlog-list li {
  display: flex; align-items: baseline; gap: 12px; flex-wrap: wrap;
  padding: 8px 0; border-top: 1px solid #f5f2fa; font-size: 0.86rem;
}
.gw-spinlog-at { color: #A2989E; font-variant-numeric: tabular-nums; white-space: nowrap; min-width: 106px; }
.gw-spinlog-user { min-width: 0; font-weight: 700; color: #2B1930; overflow-wrap: break-word; }
.gw-spinlog-what { color: #6C5A76; margin-left: auto; }
.gw-spinlog-list li.is-rehearsal { opacity: 0.65; }
.gw-spinlog-list li.is-rehearsal .gw-spinlog-what { font-style: italic; }

/* ---- The live stage: participants beside the wheel ----
   Under the flyer, list on the left and wheel on the right - the two halves of
   the draw, visible at once so the name the wheel stops on can be found in the
   list without scrolling away from it. They stack in the same order on a
   phone. */
.gw-stage {
  max-width: 1280px; margin: 26px auto 0; padding: 0 24px;
  display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.05fr); gap: 22px; align-items: start;
}
/* min-width:0 because these are grid items, and a grid item refuses by default
   to shrink below the widest thing inside it. With usernames now set to break
   only as a last resort (overflow-wrap: break-word), the widest thing inside is
   a whole handle — so a long one pushed the card 30px past the edge of a phone
   screen. The page's own overflow-x:hidden swallowed the scrollbar, which made
   it look fine while the right-hand column of every row sat behind the bezel. */
.gw-card { border: 1px solid #ece8f2; border-radius: 16px; background: #fff; padding: 18px; min-width: 0; }
.gw-card-head { display: flex; align-items: baseline; justify-content: space-between; gap: 12px; flex-wrap: wrap; margin-bottom: 12px; }
.gw-card-head h2 { font-size: 1.05rem; margin: 0; font-weight: 700; color: #0B0B0D; }
.gw-totals { font-size: 0.82rem; color: #857E95; }
.gw-totals strong { color: #3B2350; }
.gw-empty { color: #777; margin: 6px 0 0; }

.gw-find input {
  width: 100%; padding: 9px 12px; border: 1px solid #e2dcec; border-radius: 10px;
  font: inherit; font-size: 0.9rem; background: #fbfaff; color: #2B1930;
}
.gw-find input:focus { outline: none; border-color: var(--lavender); box-shadow: 0 0 0 3px rgba(169, 155, 232, 0.22); }
.gw-find-none { color: #777; font-size: 0.86rem; margin: 8px 0 0; }

/* The list scrolls inside its own card: a giveaway with 400 participants must
   not push the wheel a screen and a half down the page. */
.gw-participants {
  list-style: none; margin: 12px 0 0; padding: 0; max-height: 460px; overflow-y: auto;
  border: 1px solid #f1edf7; border-radius: 12px;
}
.gw-p {
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  padding: 8px 12px; border-bottom: 1px solid #f5f2fa;
}
.gw-p:last-child { border-bottom: 0; }
/* The name takes the slack so the two numbers stay together at the right edge,
   reading as one pair: entries, then what they're worth. */
/* Same reason as .gw-card, one level down: a flex item will not shrink past its
   own content either. min-width:0 lets the name give way, and break-word then
   splits it — but only once it genuinely cannot fit, which is the difference
   between "@nombre.larguisimo" wrapping onto two lines and "@patrivd" being
   stacked one letter at a time. */
.gw-p-user { flex: 1 1 auto; min-width: 0; color: #2B1930; font-size: 0.92rem; overflow-wrap: break-word; }
.gw-p-entries {
  flex: none; min-width: 26px; text-align: center; padding: 2px 7px; border-radius: 999px;
  background: #F3EEFC; color: #6a4ea0; font-size: 0.78rem; font-weight: 700; font-variant-numeric: tabular-nums;
}
/* Probability of winning. Quieter than the entry pill: it is derived from it,
   not a second thing someone earned. */
.gw-p-odds {
  flex: none; min-width: 48px; text-align: right; color: #857E95;
  font-size: 0.78rem; font-weight: 700; font-variant-numeric: tabular-nums;
}
/* The row the wheel just landed on, so the announced name is findable in the
   published list at a glance. */
.gw-p.is-winner { background: linear-gradient(90deg, #FFF3D6, #FFE3F0); }
.gw-p.is-winner .gw-p-user { font-weight: 700; }
.gw-list-note { color: #857E95; font-size: 0.8rem; margin: 10px 0 0; }

/* ---- Wheel ---- */
.gw-wheel-card { text-align: center; }
.gw-wheel-wrap { position: relative; margin: 4px auto 0; max-width: 460px; }
.gw-wheel { display: block; width: 100%; height: auto; aspect-ratio: 1 / 1; }
/* The pointer sits on top of the wheel's edge, pointing down into it - the
   wheel is drawn so that its wedge boundaries are measured from exactly here. */
.gw-wheel-pointer {
  position: absolute; top: -6px; left: 50%; transform: translateX(-50%);
  width: 0; height: 0; z-index: 2;
  border-left: 13px solid transparent; border-right: 13px solid transparent;
  border-top: 22px solid #E63E82;
  filter: drop-shadow(0 2px 3px rgba(43, 25, 48, 0.25));
}
.gw-result {
  margin: 16px auto 0; padding: 12px 18px; border-radius: 14px; display: inline-flex;
  flex-direction: column; gap: 2px;
  background: linear-gradient(135deg, #FFF3D6, #FFE3F0); border: 1px solid #f3d9e6;
}
.gw-result-label { font-size: 0.72rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.06em; color: #7A5C8E; }
.gw-result-user { font-size: 1.5rem; font-weight: 700; color: #2B1930; overflow-wrap: break-word; }
.gw-wheel-actions { display: flex; flex-wrap: wrap; gap: 10px; justify-content: center; margin-top: 16px; }
.gw-spin { font-size: 1rem; padding: 12px 26px; }
.gw-spin[disabled] { opacity: 0.6; cursor: default; }
.gw-secondary {
  padding: 10px 16px; border-radius: 10px; border: 1px solid #e2dcec; background: #fff;
  color: #6a4ea0; font: inherit; font-size: 0.88rem; font-weight: 700; cursor: pointer;
}
.gw-secondary:hover { border-color: var(--lavender); background: #fbfaff; }
.gw-wheel-note { color: #857E95; font-size: 0.8rem; margin: 14px 0 0; }
/* Marked as staff-only so it is never mistaken for something a customer is
   being told — it only renders for a signed-in administrator. */
.gw-admin-note {
  border: 1px dashed #e2d9f3; border-radius: 12px; padding: 9px 12px;
  background: #FBF9FF; color: #7A5C8E;
}

/* ---- Landing (only rendered when more than one giveaway is published) ---- */
.gw-index-head { display: flex; flex-direction: column; gap: 6px; }
.gw-index-group { max-width: 1280px; margin: 0 auto; padding: 26px 24px 0; }
.gw-index-group-title {
  font-size: 0.76rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.06em;
  color: #7A5C8E; margin: 0 0 14px; padding-bottom: 9px; border-bottom: 1px solid #ece8f2;
}
.gw-index-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(280px, 1fr)); gap: 18px; }
.gw-index-card {
  display: flex; flex-direction: column; border: 1px solid #ece8f2; border-radius: 16px;
  overflow: hidden; background: #fff; transition: border-color 0.15s ease, box-shadow 0.15s ease, transform 0.15s ease;
}
.gw-index-card:hover { border-color: var(--lavender); box-shadow: 0 8px 20px rgba(122, 92, 142, 0.16); transform: translateY(-2px); }
.gw-index-card.is-finished { opacity: 0.82; }
.gw-index-flyer { aspect-ratio: 1 / 1; background: #f6f3fa; display: flex; align-items: center; justify-content: center; }
.gw-index-flyer img { width: 100%; height: 100%; object-fit: cover; }
.gw-index-fallback { font-size: 2.4rem; }
.gw-index-body { padding: 14px 16px 16px; display: flex; flex-direction: column; gap: 4px; }
.gw-index-body h2 { font-size: 1.05rem; margin: 0; color: #0B0B0D; }
.gw-index-prize { color: #555; font-size: 0.9rem; margin: 0; }
.gw-index-meta { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 8px; }
.gw-chip {
  font-size: 0.74rem; font-weight: 700; padding: 4px 9px; border-radius: 999px;
  background: #F3EEFC; color: #6a4ea0;
}
.gw-chip.is-done { background: #EFEDF2; color: #6C5A76; }
.gw-chip.is-quiet { background: #F6F5F8; color: #857E95; }

@media (max-width: 900px) {
  .gw-stage { grid-template-columns: 1fr; }
}
@media (max-width: 760px) {
  .gw-head { padding-top: 26px; }
  .gw-head h1 { font-size: 1.9rem; }
  /* On a phone the flyer is the square Instagram export, shown at its own
     proportions - the same picture people saw in the post. */
  .gw-flyer img { max-height: none; }
  .gw-count { display: flex; gap: 8px; width: 100%; }
  .gw-count .unit { min-width: 0; flex: 1; padding: 9px 6px; }
  .gw-count .n { font-size: 1.35rem; }
  .gw-participants { max-height: 380px; }
}

/* ---- Giveaways: winner history ----
   The record that outlives the live. Grouped by event and dated, because after
   a rifa is over the only questions left are which one and who won it. */
.gw-history-link { color: #7A5C8E; font-weight: 700; font-size: 0.9rem; }
.gw-history-link:hover { text-decoration: underline; }
.gw-history-back { max-width: 1280px; margin: 30px auto 0; padding: 0 24px; }
.gw-history-back a { color: #7A5C8E; font-weight: 700; }
.gw-history-back a:hover { text-decoration: underline; }

.gw-history { display: flex; flex-direction: column; gap: 14px; }
.gw-history-event { border: 1px solid #ece8f2; border-radius: 16px; background: #fff; padding: 16px 18px; }
.gw-history-head {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: 12px; flex-wrap: wrap; margin-bottom: 12px;
  padding-bottom: 10px; border-bottom: 1px solid #f3f0f8;
}
.gw-history-head h3 { margin: 0; font-size: 1.05rem; }
.gw-history-head h3 a { color: #0B0B0D; }
.gw-history-head h3 a:hover { color: #7A5C8E; }
.gw-history-date { color: #857E95; font-size: 0.84rem; font-weight: 700; white-space: nowrap; }
.gw-history-winners { list-style: none; margin: 0; padding: 0; display: flex; flex-wrap: wrap; gap: 10px; }
.gw-history-winners li {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  padding: 10px 16px; border-radius: 14px;
  background: linear-gradient(135deg, #FFF3D6, #FFE3F0); border: 1px solid #f3d9e6;
}
.gw-winner-entries { color: #857E95; font-size: 0.8rem; font-variant-numeric: tabular-nums; }

/* The people who have won more than once. A podium only makes sense once
   somebody is on it twice, so the page leaves this out entirely otherwise. */
.gw-tally { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 8px; }
.gw-tally-row {
  display: grid; grid-template-columns: 34px minmax(0, 1fr) auto; gap: 12px; align-items: center;
  padding: 9px 14px; border: 1px solid #ece8f2; border-radius: 12px; background: #fff;
}
.gw-tally-pos {
  display: grid; place-items: center; width: 26px; height: 26px; border-radius: 999px;
  background: #F3EEFC; color: #6a4ea0; font-size: 0.78rem; font-weight: 700;
}
.gw-tally-user { min-width: 0; font-weight: 700; color: #2B1930; overflow-wrap: break-word; }
.gw-tally-wins { color: #857E95; font-size: 0.82rem; font-weight: 700; white-space: nowrap; }

/* Shown only to a signed-in administrator looking at a giveaway the public
   cannot reach yet, so a rehearsal is never mistaken for the live page. */
.gw-preview-banner {
  max-width: 1280px; margin: 18px auto 0; padding: 11px 16px;
  display: flex; gap: 10px; align-items: baseline; flex-wrap: wrap;
  border: 1px dashed #e2d9f3; border-radius: 12px; background: #FBF9FF; color: #7A5C8E;
  font-size: 0.88rem;
}
.gw-preview-banner strong { color: #5B3E77; }

/* ---- Requisitos + the draw record ----
   The requirements are published before the draw and the outcome after it, in
   the order it happened — including anyone who was disqualified and why. A name
   that appears and then quietly disappears is what makes a draw look rigged;
   the trail is the thing that makes this one checkable. */
/* The requirements read as a checklist, because that is exactly what they are:
   the list an admin ticks through, on camera, against the person the wheel
   picked. Same card as the instructions above so the two blocks belong
   together. */
.gw-req-intro { color: #857E95; font-size: 0.86rem; margin: 0 0 12px; }
.gw-reqs {
  list-style: none; margin: 0; padding: 0; color: #2B1930; line-height: 1.6;
  display: flex; flex-direction: column; gap: 8px; max-width: 860px;
}
.gw-reqs li {
  position: relative; margin: 0; padding: 10px 14px 10px 40px;
  background: #fff; border: 1px solid #ece8f2; border-radius: 12px;
}
.gw-reqs li::before {
  content: '✓'; position: absolute; left: 12px; top: 10px;
  width: 20px; height: 20px; border-radius: 999px;
  background: #EAF6EE; color: #2DA478; border: 1px solid #cfe9da;
  font-size: 0.72rem; font-weight: 700; display: grid; place-items: center;
}

.gw-results { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 8px; }
.gw-result-row {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap; min-width: 0;
  padding: 12px 18px; border-radius: 14px;
  background: linear-gradient(135deg, #FFF3D6, #FFE3F0); border: 1px solid #f3d9e6;
}
/* Quieter than a win, and never red-alarm: a disqualification is the rule
   working, not an incident. */
.gw-result-row.is-out, .gw-history-winners li.is-out {
  background: #F7F6F9; border-color: #ece8f2;
}
.gw-result-row.is-out .gw-winner-user, .gw-history-winners li.is-out .gw-winner-user {
  text-decoration: line-through; color: #6C5A76;
}
.gw-result-mark { color: #A2989E; font-weight: 800; }
.gw-result-why { color: #6C5A76; font-size: 0.86rem; }

/* ---- The live verification panel (admins only) ---- */
.gw-verify {
  margin: 16px 0 0; padding: 14px 16px; text-align: left;
  border: 1px dashed #e2d9f3; border-radius: 14px; background: #FBF9FF;
}
.gw-verify h3 { margin: 0 0 10px; font-size: 0.95rem; color: #3B2350; }
.gw-verify-list { list-style: none; margin: 0 0 12px; padding: 0; display: flex; flex-direction: column; gap: 7px; }
.gw-verify-list label { display: flex; align-items: flex-start; gap: 9px; cursor: pointer; font-size: 0.9rem; color: #2B1930; }
.gw-verify-list input { margin-top: 3px; flex: none; }
.gw-verify-empty { color: #857E95; font-size: 0.86rem; margin: 0 0 12px; }
.gw-verify-field { display: flex; flex-direction: column; gap: 4px; margin-bottom: 10px; }
.gw-verify-field span { font-size: 0.78rem; font-weight: 700; color: #7A5C8E; }
.gw-verify-field input {
  padding: 9px 12px; border: 1px solid #e2dcec; border-radius: 10px;
  font: inherit; font-size: 0.9rem; background: #fff; color: #2B1930;
}
.gw-verify-field input:focus { outline: none; border-color: var(--lavender); box-shadow: 0 0 0 3px rgba(169,155,232,0.22); }
.gw-verify-actions { display: flex; flex-wrap: wrap; gap: 10px; }
.gw-secondary.is-danger { color: #B23A6B; border-color: #f0d5e0; }
.gw-secondary.is-danger:hover { background: #FFF5F9; border-color: #e8b9cd; }
.gw-draw-error { color: #B23A6B; font-size: 0.86rem; margin: 12px 0 0; font-weight: 700; }

/* Already drawn — kept visible in the list, out of the wheel. */
.gw-p.is-drawn { opacity: 0.55; }
.gw-p.is-drawn .gw-p-user { text-decoration: line-through; }

/* ---- Live draw ----
   The badge that says the wheel on this page is turning right now, for everyone
   watching. Deliberately the broadcast red, not the store's pink: it means
   "happening now", not "promotion". */
.gw-live {
  display: inline-flex; align-items: center; gap: 6px; padding: 3px 10px; border-radius: 999px;
  background: #FFE8EC; color: #C42B4E; border: 1px solid #f6cdd6;
  font-size: 0.72rem; font-weight: 700; letter-spacing: 0.05em;
}
.gw-live-dot { width: 7px; height: 7px; border-radius: 999px; background: #E0324F; animation: gwPulse 1.4s ease-in-out infinite; }
@keyframes gwPulse { 0%, 100% { opacity: 1; transform: scale(1); } 50% { opacity: 0.35; transform: scale(0.82); } }
@media (prefers-reduced-motion: reduce) { .gw-live-dot { animation: none; } }
.gw-spin-error { color: #B23A6B; font-size: 0.86rem; font-weight: 700; margin: 10px 0 0; }

/* ---- Winner leaderboard ----
   A podium, four counts, then the standings — the shape people already know
   from a scoreboard, so nobody has to be taught how to read it. Built in the
   store's own palette rather than a dashboard's: lavender and pink, the same
   cards and radii as the rest of the site. */
.gw-board { padding-bottom: 72px; }
.gw-board-head { max-width: 1280px; margin: 0 auto; padding: 44px 24px 8px; display: flex; flex-direction: column; gap: 6px; }
/* The oversized word the podium sits on top of. Decorative only — it repeats the
   h1 above, so it is hidden from screen readers and never carries meaning. */
.gw-podium-band { position: relative; }
.gw-board-ghost {
  position: absolute; left: 50%; top: 0; transform: translateX(-50%); z-index: 0;
  font-size: clamp(3.4rem, 12vw, 8.5rem); font-weight: 700; letter-spacing: -0.03em;
  color: #F3EFFA; line-height: 1; user-select: none; pointer-events: none; white-space: nowrap;
}
.gw-podium { position: relative; z-index: 1; }
.gw-board-head h1 { font-size: 2.6rem; font-weight: 400; letter-spacing: 0.01em; color: #0B0B0D; margin: 2px 0 0; }
.gw-board-head p { color: #555; margin: 6px 0 0; max-width: 60ch; }

/* ---- Podium ---- */
.gw-podium {
  max-width: 1280px; margin: 52px auto 0; padding: 0 24px;
  display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 16px; align-items: end;
}
.gw-podium-card {
  display: flex; flex-direction: column; align-items: center; gap: 6px; text-align: center; min-width: 0;
  padding: 22px 18px 20px; border-radius: 20px; border: 1px solid #ece8f2; background: #fff;
  box-shadow: 0 10px 26px rgba(122, 92, 142, 0.10);
}
/* First place: taller, centred, and the only one that carries the gradient —
   the reference puts the winner physically above the other two. */
.gw-podium-card.is-rank-1 {
  order: 2; padding-top: 30px; padding-bottom: 26px;
  background: linear-gradient(160deg, #FFF6D8, #FFE7F1 55%, #EFE7FB);
  border-color: #f2dfc7;
}
.gw-podium-card.is-rank-2 { order: 1; background: linear-gradient(160deg, #F7F5FC, #FFFFFF); }
.gw-podium-card.is-rank-3 { order: 3; background: linear-gradient(160deg, #FBF3F7, #FFFFFF); }
.gw-podium-rank { font-size: 0.82rem; font-weight: 700; color: #A2989E; letter-spacing: 0.04em; }
.gw-podium-card.is-rank-1 .gw-podium-rank { color: #B98A2E; }
.gw-podium-avatar {
  width: 58px; height: 58px; border-radius: 999px; display: grid; place-items: center;
  background: linear-gradient(135deg, #A99BE8, #FF8FBA); color: #fff;
  font-size: 1.5rem; font-weight: 700;
  box-shadow: 0 4px 12px rgba(122, 92, 142, 0.22);
}
.gw-podium-card.is-rank-1 .gw-podium-avatar { width: 70px; height: 70px; font-size: 1.8rem; }
.gw-podium-user { margin: 4px 0 0; font-size: 1.02rem; font-weight: 700; color: #2B1930; overflow-wrap: break-word; }
.gw-podium-last { margin: 0; font-size: 0.82rem; color: #857E95; }
.gw-podium-stats { display: flex; gap: 16px; margin: 12px 0 0; }
.gw-podium-stats div { display: flex; flex-direction: column; gap: 1px; }
.gw-podium-stats dt { font-size: 0.68rem; text-transform: uppercase; letter-spacing: 0.05em; color: #A2989E; font-weight: 700; }
.gw-podium-stats dd { margin: 0; font-size: 0.9rem; font-weight: 700; color: #3B2350; font-variant-numeric: tabular-nums; }

/* ---- The four counts ---- */
.gw-board-stats {
  max-width: 1280px; margin: 18px auto 0; padding: 0 24px;
  display: grid; grid-template-columns: repeat(auto-fit, minmax(190px, 1fr)); gap: 14px;
}
.gw-stat {
  display: grid; grid-template-columns: 38px 1fr; grid-template-rows: auto auto; column-gap: 12px;
  align-items: center; padding: 14px 16px; border: 1px solid #ece8f2; border-radius: 16px; background: #fff;
}
.gw-stat-ico {
  grid-row: 1 / 3; width: 38px; height: 38px; border-radius: 12px; display: grid; place-items: center;
  background: #F3EEFC; font-size: 1.1rem;
}
.gw-stat-label { font-size: 0.72rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.05em; color: #A2989E; }
.gw-stat-value { font-size: 1.5rem; font-weight: 700; color: #2B1930; font-variant-numeric: tabular-nums; line-height: 1.1; }
.gw-stat-value.is-name { font-size: 1rem; min-width: 0; overflow-wrap: break-word; }

/* ---- Standings table ---- */
.gw-table-wrap { overflow-x: auto; border: 1px solid #ece8f2; border-radius: 16px; background: #fff; }
.gw-table { width: 100%; border-collapse: collapse; min-width: 640px; }
.gw-table th {
  text-align: left; padding: 12px 16px; font-size: 0.7rem; font-weight: 700;
  text-transform: uppercase; letter-spacing: 0.05em; color: #A2989E;
  border-bottom: 1px solid #f1edf7; white-space: nowrap;
}
.gw-table td { padding: 12px 16px; border-bottom: 1px solid #f5f2fa; color: #2B1930; font-size: 0.9rem; }
.gw-table tr:last-child td { border-bottom: 0; }
.gw-table .is-num, .gw-table th.is-num { text-align: right; font-variant-numeric: tabular-nums; }
.gw-table .is-pos, .gw-table th.is-pos { width: 56px; }
.gw-table .is-date { color: #857E95; white-space: nowrap; }
/* The top three keep the podium's colours, so the two blocks read as one
   ranking rather than two lists that happen to share names. */
.gw-table tr.is-top td { background: #FDFBFF; }
.gw-pos {
  display: grid; place-items: center; width: 26px; height: 26px; border-radius: 999px;
  background: #F3EEFC; color: #6a4ea0; font-size: 0.78rem; font-weight: 700;
}
.gw-table tr.is-rank-1 .gw-pos { background: linear-gradient(135deg, #FFE7A8, #FFC978); color: #7A5410; }
.gw-table tr.is-rank-2 .gw-pos { background: #E9E6EF; color: #58525F; }
.gw-table tr.is-rank-3 .gw-pos { background: #F6DFCB; color: #85552A; }
/* The name column keeps room for a name.
   Every username on these pages used to carry `overflow-wrap: anywhere`, which
   does something subtle and wrong here: unlike `break-word`, it lowers an
   element's MIN-CONTENT width to a single character. A table lays its columns
   out from exactly that measurement, so the browser was free to squeeze this
   column to nothing and stack "@patrivd" as @ / pa / tri / vd. With break-word
   the column is never narrower than the longest name, and the wrapper scrolls
   sideways instead — which it was already built to do. */
.gw-table-user { display: inline-flex; align-items: center; gap: 9px; font-weight: 600; overflow-wrap: break-word; }
.gw-table td:nth-child(2), .gw-table th:nth-child(2) { min-width: 172px; }
.gw-table-avatar {
  width: 28px; height: 28px; border-radius: 999px; display: grid; place-items: center; flex: none;
  background: linear-gradient(135deg, #A99BE8, #FF8FBA); color: #fff; font-size: 0.8rem; font-weight: 700;
}

@media (max-width: 860px) {
  /* Stacked, and in rank order: source order is 1, 2, 3, so the flex order that
     lifts first place into the middle is dropped here. */
  .gw-podium { grid-template-columns: 1fr; align-items: stretch; }
  .gw-podium-card.is-rank-1, .gw-podium-card.is-rank-2, .gw-podium-card.is-rank-3 { order: 0; }
  .gw-board-ghost { top: 0; font-size: clamp(2.6rem, 15vw, 4rem); }
  .gw-board-head h1 { font-size: 1.9rem; }
}

/* The admin's undo, sitting inside a result row. Small and quiet: it is a
   correction, not one of the two buttons the draw is decided with. */
.gw-undo { margin-left: auto; }
.gw-undo button {
  border: 1px solid #e2dcec; background: #fff; color: #857E95;
  font: inherit; font-size: 0.76rem; font-weight: 700;
  padding: 4px 10px; border-radius: 999px; cursor: pointer;
}
.gw-undo button:hover { border-color: #e8b9cd; color: #B23A6B; background: #FFF7FA; }

/* ---- Candies (loyalty currency) ---------------------------------------
   The storefront is a dark theme (body text is white); the account pages sit
   on white cards via .light-page, which only flips the background. So every
   text element here sets an explicit dark ink — without it the numbers render
   white-on-white and vanish. */
.candy-code {
  font-family: ui-monospace, SFMono-Regular, Menlo, monospace;
  font-weight: 800; letter-spacing: 0.06em;
  background: #FFF2D6; color: #7a4a00; border: 1px solid #f2d79a;
  padding: 4px 12px; border-radius: 8px; display: inline-block;
}
.candy-newcode .candy-code { font-size: 1.25rem; margin-top: 6px; }
.candy-balance-row { color: #2b1930; }
.candy-tiers { display: flex; flex-direction: column; gap: 12px; margin-top: 4px; }
.candy-tier {
  display: grid; grid-template-columns: minmax(84px, auto) auto 1fr auto; align-items: center;
  gap: 16px; padding: 16px 18px; border: 1px solid #ece7f2; border-radius: 14px;
  background: #faf8fd; color: #2b1930;
}
.candy-tier.is-ready { border-color: #e3d9f2; background: #fbf7ff; }
.candy-tier.is-locked { opacity: 0.6; }
.candy-tier .ct-amount { font-weight: 800; white-space: nowrap; color: #2b1930; font-size: 1.05rem; }
.candy-tier .ct-arrow { color: #b7aecb; }
.candy-tier .ct-reward { font-weight: 600; color: #2b1930; }
.candy-tier form { margin: 0; }
.candy-tier .btn-dark { white-space: nowrap; }
.candy-tier .btn-dark[disabled] { opacity: 0.5; cursor: not-allowed; }
.candy-code-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 12px; }
.candy-code-list li { display: flex; flex-direction: column; gap: 4px; }
.candy-code-list .cc-meta { font-size: 0.8rem; color: #857E95; }
.candy-ledger { list-style: none; margin: 0; padding: 0; color: #2b1930; }
.candy-ledger li {
  display: grid; grid-template-columns: 1fr auto auto; align-items: center; gap: 14px;
  padding: 11px 0; border-bottom: 1px solid #f0ecf5;
}
.candy-ledger li:last-child { border-bottom: 0; }
.candy-ledger .cl-reason { font-weight: 600; }
.candy-ledger .cl-date { font-size: 0.8rem; color: #857E95; white-space: nowrap; }
.candy-ledger .cl-delta { font-weight: 800; white-space: nowrap; }
.candy-ledger .cl-delta.pos { color: #1a7f4b; }
.candy-ledger .cl-delta.neg { color: #c0392b; }
@media (max-width: 560px) {
  .candy-tier { grid-template-columns: 1fr auto; row-gap: 10px; padding: 14px 16px; }
  .candy-tier .ct-arrow { display: none; }
  .candy-tier .ct-reward { grid-column: 1 / -1; order: 3; }
  .candy-tier form { grid-column: 1 / -1; order: 4; }
  .candy-tier .btn-dark { width: 100%; }
}

/* ---- Candy code entry in the cart summary ----------------------------- */
.candy-apply { margin: 14px 0; padding-top: 14px; border-top: 1px dashed #e6e0ef; }
.candy-apply > label { display: block; font-size: 0.82rem; font-weight: 700; color: #6a6280; margin-bottom: 6px; }
.candy-apply-row { display: flex; gap: 8px; }
.candy-apply-row input {
  flex: 1; min-width: 0; padding: 9px 11px; border: 1px solid #ddd6e8; border-radius: 9px;
  font: inherit; text-transform: uppercase; letter-spacing: 0.05em;
}
.candy-apply-row .btn-dark { padding: 9px 16px; white-space: nowrap; }
.candy-apply-msg { margin-top: 7px; font-size: 0.82rem; }
.candy-apply-msg.ok { color: #1a7f4b; }
.candy-apply-msg.err { color: #c0392b; }
.summary-row.candy-discount-row { color: #1a7f4b; font-weight: 700; }

/* ============================================================
   Home: shared section header (mirrors .collections-head so the
   new home sections read as the same family as the existing ones)
   ============================================================ */
.home-sec-head { text-align: center; margin-bottom: 36px; }
.home-sec-head h2 { font-size: clamp(1.9rem, 3vw, 2.5rem); color: var(--white); }
.home-sec-head h2::after { content: ''; display: block; width: 44px; height: 2px; background: var(--lavender); margin: 14px auto 0; }
.home-sec-head p { color: var(--ink-muted); font-size: 1rem; margin: 14px auto 0; max-width: 52ch; font-style: italic; }

/* ============================================================
   Home: Sorteo en vivo (giveaway spotlight)
   ============================================================ */
.sorteo { background: var(--black); padding: 60px clamp(16px, 4vw, 64px) 76px; }
.sorteo-band {
  position: relative; max-width: 1120px; margin: 0 auto;
  display: grid; grid-template-columns: minmax(0, 300px) 1fr; gap: clamp(20px, 3vw, 40px);
  background: linear-gradient(160deg, #1a1726, #121016);
  border: 1px solid #24242b; border-radius: 20px; padding: clamp(18px, 2.4vw, 26px); overflow: hidden;
}
.sorteo-band::before {
  content: ''; position: absolute; z-index: 0; width: 60%; aspect-ratio: 1; right: -12%; top: -40%;
  background: radial-gradient(circle, rgba(212, 233, 211, 0.22), transparent 68%); filter: blur(50px);
}
.sorteo[data-sstate="live"] .sorteo-band::before { background: radial-gradient(circle, rgba(224, 50, 79, 0.28), transparent 68%); }
.sorteo-flyer {
  position: relative; z-index: 1; display: block; border-radius: var(--radius); overflow: hidden;
  aspect-ratio: 4 / 5; border: 1px solid rgba(255, 255, 255, 0.1);
  background: linear-gradient(150deg, #7b5cff, #ff5ca8 55%, #ffb35c);
}
.sorteo-flyer img { width: 100%; height: 100%; object-fit: cover; }
.sorteo-flyer-ph { position: absolute; inset: 0; display: grid; place-items: center; font-size: 52px; }
.sorteo-flyer-badge { position: absolute; top: 12px; left: 12px; font-size: 0.7rem; font-weight: 600; background: rgba(0,0,0,0.4); color: #fff; padding: 5px 10px; border-radius: 999px; }
.sorteo-info { position: relative; z-index: 1; display: flex; flex-direction: column; gap: 12px; min-width: 0; }
.sorteo-kicker { display: flex; align-items: center; gap: 10px; font-size: 0.85rem; font-weight: 600; color: var(--ink-muted); flex-wrap: wrap; }
.sorteo .gw-live { display: none; background: #E0324F; color: #fff; border-color: #E0324F; }
.sorteo[data-sstate="live"] .gw-live { display: inline-flex; }
.sorteo .gw-live-dot { background: #fff; }
.sorteo-title { margin: 0; font-weight: 600; font-size: clamp(1.4rem, 3vw, 1.9rem); letter-spacing: -0.01em; }
.sorteo-prize {
  margin: 0; align-self: flex-start; font-size: 0.92rem; color: var(--mint);
  background: rgba(102, 214, 166, 0.1); border: 1px solid rgba(102, 214, 166, 0.28);
  padding: 7px 12px; border-radius: 10px;
}
.sorteo-count { display: flex; gap: 10px; margin-top: 2px; }
.sorteo-count .unit { background: rgba(255,255,255,0.04); border: 1px solid #24242b; border-radius: 12px; padding: 10px 4px; min-width: 60px; text-align: center; }
.sorteo-count .n { display: block; font-size: 1.7rem; font-weight: 600; font-variant-numeric: tabular-nums; line-height: 1; }
.sorteo-count .l { display: block; font-size: 0.68rem; text-transform: uppercase; letter-spacing: 0.08em; color: var(--ink-muted); margin-top: 6px; }
.sorteo-eta { margin: 0; font-size: 0.8rem; color: var(--ink-muted); }
.sorteo-live-line { display: none; margin: 0; font-size: 0.98rem; font-weight: 500; color: #fff; }
.sorteo-live-line strong { color: #ff8095; }
.sorteo[data-sstate="live"] .sorteo-count,
.sorteo[data-sstate="live"] .sorteo-eta { display: none; }
.sorteo[data-sstate="live"] .sorteo-live-line { display: block; }
.sorteo-foot { display: flex; align-items: center; gap: 18px; flex-wrap: wrap; margin-top: 6px; }
.sorteo-stats { font-size: 0.86rem; color: var(--ink-muted); }
.sorteo-stats strong { color: var(--white); font-weight: 600; font-variant-numeric: tabular-nums; }
.sorteo-cta { margin-left: auto; }
.sorteo-cta-live { display: none; }
.sorteo[data-sstate="live"] .sorteo-cta { background: #E0324F; color: #fff; }
.sorteo[data-sstate="live"] .sorteo-cta-count { display: none; }
.sorteo[data-sstate="live"] .sorteo-cta-live { display: inline; }
@media (max-width: 720px) {
  .sorteo-band { grid-template-columns: 1fr; }
  .sorteo-flyer { aspect-ratio: 16 / 10; }
  .sorteo-cta { margin-left: 0; width: 100%; justify-content: center; text-align: center; }
}

/* ============================================================
   Home: Cartas destacadas (holographic tilt cards)
   ============================================================ */
.destacadas { background: var(--black); padding: 60px clamp(16px, 4vw, 64px) 76px; }
.destacadas-deck {
  max-width: 1120px; margin: 0 auto;
  display: flex; flex-wrap: wrap; justify-content: center; align-items: flex-start;
  gap: clamp(18px, 3vw, 42px);
}
.holo-scene { position: relative; width: 240px; max-width: 74vw; perspective: 1100px; }
.holo-aura {
  position: absolute; inset: 4% 6% 18%; z-index: 0; border-radius: 26px;
  filter: blur(34px); opacity: 0.5; background: radial-gradient(circle at 50% 45%, var(--holo-accent), transparent 70%);
  transition: opacity 0.4s ease, transform 0.4s ease;
}
.holo-scene[data-accent="mint"] { --holo-accent: #66d6a6; }
.holo-scene[data-accent="lavender"] { --holo-accent: #A99BE8; }
.holo-scene[data-accent="gold"] { --holo-accent: #E9C46A; }
.holo-scene:hover .holo-aura, .holo-scene.lit .holo-aura { opacity: 0.9; transform: scale(1.05); }
.holo-card {
  position: relative; z-index: 1; border-radius: var(--radius); overflow: hidden;
  transform-style: preserve-3d; transform: rotateX(var(--rx, 0deg)) rotateY(var(--ry, 0deg));
  transition: transform 0.5s cubic-bezier(0.2, 0.8, 0.25, 1); will-change: transform;
  box-shadow: 0 22px 44px rgba(0, 0, 0, 0.55); border: 1px solid rgba(255,255,255,0.1);
}
.holo-scene.lit .holo-card { transition: transform 0.08s linear; }
.holo-photo { display: block; aspect-ratio: 63 / 88; }
.holo-photo img { width: 100%; height: 100%; object-fit: cover; }
.holo-photo-ph { display: grid; place-items: center; width: 100%; height: 100%; font-size: 40px; color: rgba(255,255,255,0.25); background: linear-gradient(160deg, #221a4a, #12101a); }
.holo-foil {
  position: absolute; inset: 0; z-index: 3; pointer-events: none; mix-blend-mode: color-dodge; opacity: 0.42;
  background: linear-gradient(115deg, transparent 18%, rgba(255,0,150,0.5) 32%, rgba(0,231,255,0.5) 44%, rgba(120,120,255,0.45) 52%, rgba(0,255,170,0.5) 62%, rgba(255,220,80,0.5) 74%, transparent 86%);
  background-size: 260% 260%; background-position: var(--mx, 50%) var(--my, 50%); transition: opacity 0.4s ease;
}
.holo-foil::after {
  content: ''; position: absolute; inset: 0;
  background-image: repeating-linear-gradient(125deg, rgba(255,255,255,0.1) 0 2px, transparent 2px 5px);
  background-size: 220% 220%; background-position: var(--mx, 50%) var(--my, 50%); mix-blend-mode: overlay; opacity: 0.5;
}
.holo-glare {
  position: absolute; inset: 0; z-index: 4; pointer-events: none; mix-blend-mode: overlay; opacity: 0;
  transition: opacity 0.3s ease;
  background: radial-gradient(circle at var(--px, 50%) var(--py, 50%), rgba(255,255,255,0.5), transparent 42%);
}
.holo-scene:hover .holo-glare, .holo-scene.lit .holo-glare { opacity: 0.85; }
.holo-meta { margin-top: 14px; text-align: center; display: flex; flex-direction: column; gap: 4px; }
.holo-name { color: var(--white); font-weight: 600; font-size: 0.95rem; line-height: 1.3; }
.holo-name:hover { color: var(--lavender); }
.holo-meta .price { color: var(--white); font-weight: 600; }
.destacadas-foot { display: flex; justify-content: center; margin-top: 34px; }
.destacadas-cta {
  color: var(--white); background: transparent; border: 1px solid #24242b; border-radius: 10px;
  padding: 11px 22px; font-weight: 600; transition: border-color 0.2s ease, background 0.2s ease;
}
.destacadas-cta:hover { border-color: rgba(169,155,232,0.6); background: rgba(169,155,232,0.12); }
/* Idle shimmer at rest, so the section is alive in a still frame; the pointer
   handler adds .lit to take over, and reduced motion drops it entirely. */
@keyframes holoIdleFoil { 0%, 100% { background-position: 20% 30%; } 50% { background-position: 80% 70%; } }
@keyframes holoIdleTilt { 0%, 100% { transform: rotateX(3deg) rotateY(-6deg); } 50% { transform: rotateX(-2deg) rotateY(6deg); } }
.holo-scene:not(.lit) .holo-card { animation: holoIdleTilt 9s ease-in-out infinite; }
.holo-scene:not(.lit) .holo-foil { animation: holoIdleFoil 9s ease-in-out infinite; }
.holo-scene:nth-child(2):not(.lit) .holo-card, .holo-scene:nth-child(2):not(.lit) .holo-foil { animation-delay: -3s; }
.holo-scene:nth-child(3):not(.lit) .holo-card, .holo-scene:nth-child(3):not(.lit) .holo-foil { animation-delay: -6s; }
@media (prefers-reduced-motion: reduce) {
  .holo-scene:not(.lit) .holo-card, .holo-scene:not(.lit) .holo-foil { animation: none; }
  .holo-card { transition: none; }
}

/* ============================================================
   Dark aurora — section overrides (Phase 1: home only)
   Placed at the end on purpose: these beat the original solid-fill rules above
   at equal specificity, so the home's bands and dark sections go transparent
   and the single .site-aurora ground (behind everything) shows through them.
   Header, footer and the hero keep their own opaque fills. Owner-chosen
   home-blocks in lavender/white are left alone — those are deliberate per-block
   choices. The white sub-pages are untouched (they hide the aurora entirely).
   ============================================================ */
.brand-band, .text-marquee, .novedades, .bottom-band,
.promos, .collections, .home-block.bg-oscuro { background: transparent; }
/* The Novedades edge-fades melted a scrolled card into the old purple; fade to
   the dark ground now instead. */
/* Old edge-fade painted a flat --bg-dark strip that didn't match the aurora
   behind it — it read as a dark square by the arrows. Replace it with a MASK on
   the scroll row: the cards themselves fade to transparent at the edge, so the
   aurora shows through and there's nothing to mismatch. Driven by the same
   more-left / more-right classes the JS already toggles, so the first/last card
   still isn't faded at the ends. The colour pseudo-elements are switched off. */
.novedades-wrap::before, .novedades-wrap::after { background: none; content: none; }
.novedades-wrap.more-left  .novedades-row {
  -webkit-mask-image: linear-gradient(to right, transparent 0, #000 52px);
          mask-image: linear-gradient(to right, transparent 0, #000 52px);
}
.novedades-wrap.more-right .novedades-row {
  -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 52px), transparent 100%);
          mask-image: linear-gradient(to right, #000 calc(100% - 52px), transparent 100%);
}
.novedades-wrap.more-left.more-right .novedades-row {
  -webkit-mask-image: linear-gradient(to right, transparent 0, #000 52px, #000 calc(100% - 52px), transparent 100%);
          mask-image: linear-gradient(to right, transparent 0, #000 52px, #000 calc(100% - 52px), transparent 100%);
}
/* The logo marquee's rare text labels were dark-on-lavender; light them for the
   dark ground (the logos themselves are images and unaffected). */
.brand-item { color: var(--white); }

/* ============================================================
   Glassy product cards on the dark ground (Phase 1: dark pages only)
   On the dark aurora the solid-white card read as a hard slab; here it becomes
   frosted glass — a translucent, blurred frame with light text — so the aurora
   shows softly through it. Scoped to body:not(.light-page) so the white
   sub-pages (catálogo, producto…) keep their solid cards until Phase 2 darkens
   them. The image well (.card-img) is left light on purpose: product photos use
   mix-blend-mode:multiply and need a near-white backdrop to sit on, so only the
   card frame and text change, never the art.
   ============================================================ */
body:not(.light-page) .card {
  background: rgba(255, 255, 255, 0.06);
  border-color: rgba(255, 255, 255, 0.14);
}
body:not(.light-page) .card:hover {
  border-color: rgba(169, 155, 232, 0.5);
  box-shadow: 0 16px 36px rgba(0, 0, 0, 0.5);
}
/* Image well — one consistent frosted-lavender tile on every card. It must be
   OPAQUE: the product photos are a mix of transparent PNGs and opaque white-
   background shots, and a translucent well let the white-background ones show
   through as bright white while the transparent ones went frosted — the "some
   cards still white" inconsistency. An opaque panel means the multiply blend
   lands the same for both, so every well matches. isolation:isolate keeps the
   blend off the moving aurora too. Tinted to the theme so it reads as a frosted
   tile, not a hard white slab. (Truly see-through glass would need every product
   image to have a transparent background — that white is baked into the files.)
   No backdrop-filter on purpose: blur over the animated aurora was the Opera
   lag; a plain fill costs a fraction. */
body:not(.light-page) .card-img { isolation: isolate; background: #E8E6F4; }
/* Text lightens for the glass; the coloured badges stay. */
body:not(.light-page) .card-name { color: #ECEAF4; }
body:not(.light-page) .price { color: #FFFFFF; }
body:not(.light-page) .price-compare { color: #B6AFC4; }
body:not(.light-page) .price-from { color: #B8AADF; }
body:not(.light-page) .price-sub { color: #A99FB8; }


/* ============================================================
   Dark aurora — Phase 2: sub-pages
   The white sub-pages (catálogo, producto, carrito, cuenta,
   candydex, singles, rifas, políticas, FAQ, contacto, 404) now
   sit on the same dark aurora ground as the home: their
   body.light-page class is gone, the .site-aurora layer shows
   on every page, and these overrides — at the END of the file,
   so they win over the original light rules at equal or lower
   specificity — flip their white surfaces to the frosted-glass
   language the home cards already use.
   Rules of the dark ground (kept from Phase 1 + legibility):
   - NO backdrop-filter/blur over the moving aurora (the Opera
     lag); frosted = a plain translucent fill.
   - Image wells stay OPAQUE and light (#E8E6F4 / #f4f4f6):
     product art uses mix-blend-mode:multiply and needs a light
     backdrop, so only frames and text change, never the art.
   - High contrast: headings #FFFFFF, body #DDD7EA-ish, never
     the old mid-greys (#555/#777/#888) on the dark ground.
   - Pastel status chips (avail-*, order-status, gw winner
     cards…) keep their light fills + dark ink: a light chip on
     dark ground reads fine and keeps its meaning.
   ============================================================ */

/* Native controls (selects, scrollbars, date pickers) render dark. */
html { color-scheme: dark; }

/* ---------- Page wrappers: transparent so the aurora shows ---------- */
body:not(.light-page) .collection-page,
body:not(.light-page) .page-wrap,
body:not(.light-page) .cart-page,
body:not(.light-page) .auth-page,
body:not(.light-page) .account-page,
body:not(.light-page) .pd-wrap,
body:not(.light-page) .product-detail,
body:not(.light-page) .related,
body:not(.light-page) .breadcrumb {
  background: transparent;
}
body:not(.light-page) .collection-page,
body:not(.light-page) .cart-page,
body:not(.light-page) .product-detail { color: #E4DFF0; }

/* ---------- Shared frosted surface (cards, panels, drawers) ---------- */
body:not(.light-page) .page-card,
body:not(.light-page) .faq-items,
body:not(.light-page) .contact-card,
body:not(.light-page) .channel,
body:not(.light-page) .summary-card,
body:not(.light-page) .pay-card,
body:not(.light-page) .cart-item,
body:not(.light-page) .cart-empty,
body:not(.light-page) .auth-card,
body:not(.light-page) .account-card,
body:not(.light-page) .mini-cart,
body:not(.light-page) .dex-cs-card,
body:not(.light-page) .dcc-set,
body:not(.light-page) .gw-card,
body:not(.light-page) .gw-rules-body,
body:not(.light-page) .gw-spinlog,
body:not(.light-page) .gw-index-card,
body:not(.light-page) .gw-history-event,
body:not(.light-page) .gw-tally-row,
body:not(.light-page) .gw-stat,
body:not(.light-page) .gw-table-wrap,
body:not(.light-page) .gw-reqs li,
body:not(.light-page) .dex-modal-panel {
  background: rgba(255, 255, 255, 0.055);
  border: 1px solid rgba(255, 255, 255, 0.13);
  box-shadow: 0 14px 40px rgba(0, 0, 0, 0.35);
  color: #DDD7EA;
}
/* Hover lifts keep a lavender edge like the home cards. */
body:not(.light-page) .channel:hover,
body:not(.light-page) .dcc-set:hover,
body:not(.light-page) .dex-cs-card:hover,
body:not(.light-page) .gw-index-card:hover {
  border-color: rgba(169, 155, 232, 0.5);
}
/* The mini-cart is a full-height drawer, not a small inline card, so it needs to
   read as its own solid surface — the shared 5.5%-white frosted fill above is far
   too see-through at that size (it vanishes into the dark ground). Near-opaque dark
   violet-navy panel, a touch lighter than the ground, with a lavender left edge and
   a deeper shadow so it lifts clearly off the page. */
body:not(.light-page) .mini-cart {
  background: rgba(20, 19, 34, 0.97);
  border: none;
  border-left: 1px solid rgba(169, 155, 232, 0.22);
  box-shadow: -14px 0 48px rgba(0, 0, 0, 0.55);
  color: #F2EFF8;
}

/* ---------- Shared dark form fields ---------- */
body:not(.light-page) .contact-field input,
body:not(.light-page) .contact-field textarea,
body:not(.light-page) .checkout-form input,
body:not(.light-page) .checkout-form textarea,
body:not(.light-page) .auth-form input,
body:not(.light-page) .auth-form .phone-country,
body:not(.light-page) .dex-search input,
body:not(.light-page) .gw-find input,
body:not(.light-page) .gw-verify-field input,
body:not(.light-page) .candy-apply-row input {
  background: rgba(255, 255, 255, 0.07);
  border-color: rgba(255, 255, 255, 0.20);
  color: #F2EFF8;
}
body:not(.light-page) .contact-field input::placeholder,
body:not(.light-page) .contact-field textarea::placeholder,
body:not(.light-page) .checkout-form input::placeholder,
body:not(.light-page) .checkout-form textarea::placeholder,
body:not(.light-page) .auth-form input::placeholder,
body:not(.light-page) .dex-search input::placeholder,
body:not(.light-page) .gw-find input::placeholder,
body:not(.light-page) .gw-verify-field input::placeholder {
  color: #8A8296;
}
body:not(.light-page) .auth-form input.code-input::placeholder { color: #6b6478; }

/* ---------- Catalog (collection) page ---------- */
body:not(.light-page) .collection-head h1 { color: #FFFFFF; }
body:not(.light-page) .collection-head p { color: #C9C2D8; }
body:not(.light-page) .collection-toolbar { color: #C9C2D8; border-bottom-color: rgba(255,255,255,0.12); }
body:not(.light-page) .cat-jump-label { color: #B8B0C8; }
body:not(.light-page) .cat-chip {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.14); color: #EDE9F6;
}
body:not(.light-page) .cat-chip .cc-count { background: rgba(169,155,232,0.22); color: #C9B8F0; }
body:not(.light-page) .cat-chip.is-empty { color: #7d7689; background: rgba(255,255,255,0.03); border-color: rgba(255,255,255,0.08); }
body:not(.light-page) .cat-chip.is-empty .cc-count { background: rgba(255,255,255,0.06); color: #7d7689; }
body:not(.light-page) .empty-state { color: #B8B0C8; }

/* Filter / sort / price dropdowns — dark panels under the dark header. */
body:not(.light-page) .filter-trigger {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.16); color: #EDE9F6;
}
body:not(.light-page) .filter-panel,
body:not(.light-page) .pd-dd-panel {
  background: #17121F; border-color: rgba(255,255,255,0.14);
  box-shadow: 0 16px 40px rgba(0,0,0,0.5);
}
body:not(.light-page) .filter-check { color: #E4DFF0; }
body:not(.light-page) .filter-check:hover,
body:not(.light-page) .sort-opt:hover,
body:not(.light-page) .pd-opt:hover,
body:not(.light-page) .pd-opt:focus-visible { background: rgba(255,255,255,0.07); }
body:not(.light-page) .fc-box { border-color: #6b6478; }
body:not(.light-page) .sort-opt { color: #E4DFF0; }
body:not(.light-page) .sort-opt.active { color: #8FD9AE; }
body:not(.light-page) .price-input { border-color: rgba(255,255,255,0.22); }
body:not(.light-page) .price-input span,
body:not(.light-page) .price-sep { color: #A99FB8; }
body:not(.light-page) .price-input input { background: transparent; color: #F2EFF8; }
body:not(.light-page) .price-clear { color: #A99FB8; }
body:not(.light-page) .price-clear:hover { color: #FFFFFF; }
/* Black-on-dark would vanish; lavender fill keeps the apply button loud. */
body:not(.light-page) .price-apply { background: var(--lavender); color: #1A1420; }
body:not(.light-page) .price-apply:hover { background: #FFFFFF; color: #1A1420; }
body:not(.light-page) .view-btn {
  background: rgba(255,255,255,0.05); border-color: rgba(255,255,255,0.16); color: #C9C2D8;
}
body:not(.light-page) .view-btn:hover { color: #FFFFFF; }
body:not(.light-page) .view-btn.active { color: #FFFFFF; border-color: var(--lavender); }

/* ---------- Product detail ---------- */
body:not(.light-page) .breadcrumb-inner,
body:not(.light-page) .breadcrumb-inner a { color: #B8B0C8; }
body:not(.light-page) .product-detail h1 { color: #FFFFFF; }
body:not(.light-page) .pd-cat { color: #B8AADF; }
body:not(.light-page) .product-detail .desc { color: #DDD7EA; }
body:not(.light-page) .desc a { color: #B8AADF; }
body:not(.light-page) .pd-var-title { color: #FFFFFF; }
body:not(.light-page) .pd-dd-trigger {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.20); color: #F2EFF8;
}
body:not(.light-page) .pd-dd-trigger .caret { color: #B8AADF; }
body:not(.light-page) .pd-dd[open] .pd-dd-trigger { border-color: var(--lavender); }
body:not(.light-page) .pd-opt { color: #EDE9F6; }
body:not(.light-page) .pd-opt-meta,
body:not(.light-page) .pd-opt.is-out .pd-opt-name { color: #A99FB8; }
body:not(.light-page) .pd-opt-check { color: #C9B8F0; }
/* Related strip: the white edge-fade painted a white strip on the dark ground;
   a mask on the track fades the peeking card into the aurora instead. */
body:not(.light-page) .related-wrap::after { background: none; content: none; }
body:not(.light-page) .related-track {
  -webkit-mask-image: linear-gradient(to right, #000 calc(100% - 60px), transparent 100%);
          mask-image: linear-gradient(to right, #000 calc(100% - 60px), transparent 100%);
}
body:not(.light-page) .related-title { color: #FFFFFF; }
/* The black action pill disappears on the dark ground — lavender instead. */
body:not(.light-page) .btn-dark { background: var(--lavender); color: #1A1420; }
body:not(.light-page) .btn-dark:hover { background: #FFFFFF; color: #1A1420; }
body:not(.light-page) .btn-dark:disabled,
body:not(.light-page) .btn-dark:disabled:hover { background: #3a3546; color: #8A8296; }

/* ---------- Static pages + FAQ ---------- */
body:not(.light-page) .page-hero h1 { color: #FFFFFF; }
body:not(.light-page) .page-content { color: #DDD7EA; }
body:not(.light-page) .page-content > p:first-child { color: #F2EFF8; }
body:not(.light-page) .page-content h2 { color: #FFFFFF; border-top-color: rgba(255,255,255,0.12); }
body:not(.light-page) .page-content h3,
body:not(.light-page) .page-content strong { color: #FFFFFF; }
body:not(.light-page) .page-content a { color: #B8AADF; }
body:not(.light-page) .page-content .policy-date { color: #A99FB8; border-top-color: rgba(255,255,255,0.12); }
body:not(.light-page) .faq-item { border-top-color: rgba(255,255,255,0.10); }
body:not(.light-page) .faq-item > summary { color: #F2EFF8; }
body:not(.light-page) .faq-item > summary:hover,
body:not(.light-page) .faq-item[open] > summary { background: rgba(255,255,255,0.06); }
body:not(.light-page) .faq-contact p { color: #C9C2D8; }
body:not(.light-page) .faq-contact-actions .faq-btn.is-primary { background: var(--lavender); color: #1A1420; }
body:not(.light-page) .faq-contact-actions .faq-btn.is-primary:hover { background: #FFFFFF; color: #1A1420; }
body:not(.light-page) .faq-contact-actions .faq-btn.is-ghost {
  background: transparent; color: #EDE9F6; border-color: rgba(255,255,255,0.35);
}
body:not(.light-page) .faq-contact-actions .faq-btn.is-ghost:hover { border-color: var(--lavender); color: #FFFFFF; }

/* ---------- Contact ---------- */
body:not(.light-page) .contact-wrap { color: #DDD7EA; }
body:not(.light-page) .ch-label { color: #B8B0C8; }
body:not(.light-page) .ch-value { color: #F2EFF8; }
body:not(.light-page) .channel:hover .ch-go { color: #C9B8F0; }
body:not(.light-page) .contact-aside-note { color: #B8B0C8; }
body:not(.light-page) .contact-card h2 { color: #FFFFFF; }
body:not(.light-page) .contact-card-sub { color: #B8B0C8; }
body:not(.light-page) .contact-field label { color: #DDD7EA; }
body:not(.light-page) .contact-field label .opt { color: #9a92a8; }
body:not(.light-page) .contact-hint { color: #A99FB8; }

/* ---------- Cart + checkout ---------- */
body:not(.light-page) .cart-col h1 { color: #FFFFFF; }
body:not(.light-page) .cart-clear { color: #FF8F8F; }
body:not(.light-page) .cart-item-name { color: #F2EFF8; }
body:not(.light-page) .cart-item-meta { color: #A99FB8; }
body:not(.light-page) .cart-item-variant { color: #B8AADF; }
body:not(.light-page) .cart-item-price { color: #FFFFFF; }
body:not(.light-page) .cart-item-max { color: #A99FB8; }
body:not(.light-page) .qty { border-color: rgba(255,255,255,0.22); }
body:not(.light-page) .qty button { background: none; color: #EDE9F6; }
body:not(.light-page) .qty button:hover { background: rgba(255,255,255,0.10); }
body:not(.light-page) .qty button:disabled { color: #6b6478; }
body:not(.light-page) .qty button:disabled:hover { background: none; }
body:not(.light-page) .cart-empty p { color: #B8B0C8; }
body:not(.light-page) .summary-card h2,
body:not(.light-page) .pay-card h2 { color: #FFFFFF; }
body:not(.light-page) .summary-row { color: #DDD7EA; }
body:not(.light-page) .summary-row.muted { color: #A99FB8; }
body:not(.light-page) .summary-deposit { color: #FFFFFF; }
body:not(.light-page) .btn-checkout { border: 1px solid rgba(255,255,255,0.16); }
body:not(.light-page) .btn-checkout:disabled { background: #3a3546; color: #8A8296; border-color: transparent; }
body:not(.light-page) .checkout-form { border-top-color: rgba(255,255,255,0.14); }
body:not(.light-page) .checkout-form label { color: #DDD7EA; }
body:not(.light-page) .checkout-hint { color: #A99FB8; }
body:not(.light-page) .checkout-done h3 { color: #FFFFFF; }
body:not(.light-page) .checkout-done p { color: #C9C2D8; }
body:not(.light-page) .pay-card .pay-sub { color: #A99FB8; }
body:not(.light-page) .pay-method { border-top-color: rgba(255,255,255,0.12); }
body:not(.light-page) .pay-method .pm-title { color: #F2EFF8; }
body:not(.light-page) .pay-method .pm-line { color: #DDD7EA; }

/* ---------- Mini-cart drawer ---------- */
body:not(.light-page) .mini-cart-head { color: #FFFFFF; border-bottom-color: rgba(255,255,255,0.12); }
body:not(.light-page) .mini-close { color: #B8B0C8; }
body:not(.light-page) .mini-close:hover { color: #FFFFFF; }
body:not(.light-page) .mini-item-name { color: #F2EFF8; }
body:not(.light-page) .mini-item-variant { color: #B8AADF; }
body:not(.light-page) .mini-item-price { color: #FFFFFF; }
body:not(.light-page) .mini-empty { color: #B8B0C8; }
body:not(.light-page) .mini-cart-foot { border-top-color: rgba(255,255,255,0.12); }
body:not(.light-page) .mini-total { color: #FFFFFF; }

/* ---------- Account: auth pages ---------- */
body:not(.light-page) .auth-card h1 { color: #FFFFFF; }
body:not(.light-page) .auth-sub { color: #B8B0C8; }
body:not(.light-page) .auth-provider {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.20); color: #EDE9F6;
}
body:not(.light-page) .auth-provider:hover { border-color: var(--lavender); background: rgba(255,255,255,0.10); }
body:not(.light-page) .auth-divider::before,
body:not(.light-page) .auth-divider::after { background: rgba(255,255,255,0.14); }
body:not(.light-page) .auth-form label { color: #DDD7EA; }
body:not(.light-page) .btn-auth { border: 1px solid rgba(255,255,255,0.16); }
body:not(.light-page) .pw-rules li.ok { color: #4CC38A; }
body:not(.light-page) .pw-rules.is-live li:not(.ok) { color: #D89A94; }
body:not(.light-page) .auth-alt { color: #B8B0C8; }
body:not(.light-page) .auth-alt a { color: #C9B8F0; }
body:not(.light-page) .btn-text { color: #B8AADF; }
body:not(.light-page) .btn-text:hover { color: #FFFFFF; }
body:not(.light-page) .auth-hint { color: #A99FB8; }
body:not(.light-page) .auth-hint a { color: #B8AADF; }
body:not(.light-page) .auth-legal { border-top-color: rgba(255,255,255,0.12); color: #A99FB8; }
body:not(.light-page) .auth-legal a { color: #B8AADF; }
body:not(.light-page) .auth-legal a:hover { color: #FFFFFF; }

/* ---------- Account: dashboard ---------- */
body:not(.light-page) .account-head h1 { color: #FFFFFF; }
body:not(.light-page) .account-email { color: #B8B0C8; }
body:not(.light-page) .btn-file {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.20); color: #EDE9F6;
}
body:not(.light-page) .btn-file:hover { border-color: var(--lavender); background: rgba(255,255,255,0.10); }
body:not(.light-page) .avatar-filename { color: #A99FB8; }
body:not(.light-page) .avatar-filename.has-file { color: #F2EFF8; }
body:not(.light-page) .btn-avatar-remove { color: #FF8F8F; }
body:not(.light-page) .btn-avatar-remove:hover { color: #FFB3B3; }
body:not(.light-page) .btn-logout {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.20); color: #EDE9F6;
}
body:not(.light-page) .btn-logout:hover { border-color: #FF8F8F; color: #FF8F8F; }
body:not(.light-page) .account-card h2 { color: #FFFFFF; }
body:not(.light-page) .account-empty { color: #B8B0C8; }
body:not(.light-page) .order-row { border-color: rgba(255,255,255,0.12); }
body:not(.light-page) .order-top strong { color: #F2EFF8; }
body:not(.light-page) .order-meta { color: #A99FB8; }
body:not(.light-page) .order-meta .order-pre { color: #B8AADF; }
body:not(.light-page) .order-items { border-top-color: rgba(255,255,255,0.14); }
body:not(.light-page) .order-items li,
body:not(.light-page) .order-items a { color: #DDD7EA; }
body:not(.light-page) .order-items a:hover { color: #B8AADF; }
body:not(.light-page) .order-items .qty { color: #A99FB8; }
body:not(.light-page) .order-variant { color: #B8AADF; }
body:not(.light-page) .linked-list li { border-top-color: rgba(255,255,255,0.12); }
body:not(.light-page) .linked-name { color: #F2EFF8; }
body:not(.light-page) .linked-ok { color: #4CC38A; }
body:not(.light-page) .btn-unlink { border-color: rgba(255,255,255,0.20); color: #B8B0C8; }
body:not(.light-page) .btn-unlink:hover { border-color: #FF8F8F; color: #FF8F8F; }
body:not(.light-page) .btn-link-provider { border: 1.5px solid rgba(255,255,255,0.16); }

/* ---------- Candies (loyalty) ---------- */
body:not(.light-page) .candy-balance-row { color: #F2EFF8; }
body:not(.light-page) .candy-tier {
  background: rgba(255,255,255,0.05); border-color: rgba(255,255,255,0.12); color: #E4DFF0;
}
body:not(.light-page) .candy-tier.is-ready { background: rgba(169,155,232,0.10); border-color: rgba(169,155,232,0.35); }
body:not(.light-page) .candy-tier .ct-amount,
body:not(.light-page) .candy-tier .ct-reward { color: #F2EFF8; }
body:not(.light-page) .candy-tier .ct-arrow { color: #8A8296; }
body:not(.light-page) .candy-code-list .cc-meta { color: #A99FB8; }
body:not(.light-page) .candy-ledger { color: #E4DFF0; }
body:not(.light-page) .candy-ledger li { border-bottom-color: rgba(255,255,255,0.10); }
body:not(.light-page) .candy-ledger .cl-date { color: #A99FB8; }
body:not(.light-page) .candy-ledger .cl-delta.pos,
body:not(.light-page) .candy-apply-msg.ok,
body:not(.light-page) .summary-row.candy-discount-row { color: #4CC38A; }
body:not(.light-page) .candy-ledger .cl-delta.neg,
body:not(.light-page) .candy-apply-msg.err { color: #FF8F8F; }
body:not(.light-page) .candy-apply { border-top-color: rgba(255,255,255,0.14); }
body:not(.light-page) .candy-apply > label { color: #C9C2D8; }

/* ---------- Candydex + singles ---------- */
body:not(.light-page) .dex-kicker,
body:not(.light-page) .dex-series-head h2 { color: #B8AADF; }
body:not(.light-page) .dex-series-head { border-bottom-color: rgba(255,255,255,0.12); }
body:not(.light-page) .dex-series-count { color: #A99FB8; }
body:not(.light-page) .dex-crumbs { color: #A99FB8; }
body:not(.light-page) .dex-crumbs a { color: #B8AADF; }
body:not(.light-page) .dex-set-hero-info h1,
body:not(.light-page) .dex-crosssell h2 { color: #FFFFFF; }
body:not(.light-page) .dex-set-facts,
body:not(.light-page) .dm-rows { border-color: rgba(255,255,255,0.14); }
body:not(.light-page) .dex-set-facts dt,
body:not(.light-page) .dm-rows dt { background: rgba(255,255,255,0.08); color: #F2EFF8; }
body:not(.light-page) .dex-set-facts dd,
body:not(.light-page) .dm-rows dd,
body:not(.light-page) .dm-rows dd a { color: #C9C2D8; }
body:not(.light-page) .dex-set-facts > div + div dt,
body:not(.light-page) .dex-set-facts > div + div dd,
body:not(.light-page) .dm-rows > div + div { border-top-color: rgba(255,255,255,0.10); }
body:not(.light-page) .dm-code { color: #A99FB8; }
/* Card-viewer modal panel: a darker, near-solid surface matching the mini-cart
   drawer instead of the shared glassy card fill (rgba 255,255,255,0.055), so the
   info rows read clearly over the blurred backdrop. Only the info area shows it —
   the media well above keeps its own opaque light bg for the card's multiply blend. */
body:not(.light-page) .dex-modal-panel {
  background: rgba(20, 19, 34, 0.97);
  border-color: rgba(169, 155, 232, 0.18);
}
body:not(.light-page) .dex-rarity-key { background: rgba(255,255,255,0.05); border-color: rgba(255,255,255,0.14); }
body:not(.light-page) .dex-rk-label { color: #B8B0C8; }
body:not(.light-page) .dex-rk-text { color: #DDD7EA; }
body:not(.light-page) .dex-rk-n { color: #A99FB8; }
body:not(.light-page) .dex-set-desc { color: #DDD7EA; }
body:not(.light-page) .dex-set-desc h1, body:not(.light-page) .dex-set-desc h2,
body:not(.light-page) .dex-set-desc h3, body:not(.light-page) .dex-set-desc h4,
body:not(.light-page) .dex-set-desc h5, body:not(.light-page) .dex-set-desc h6,
body:not(.light-page) .dex-set-desc strong, body:not(.light-page) .dex-set-desc b { color: #F2EFF8; }
body:not(.light-page) .dex-set-desc a { color: #B8AADF; }
body:not(.light-page) .dex-cs-img { background: #E8E6F4; }
body:not(.light-page) .dex-cs-name { color: #F2EFF8; }
body:not(.light-page) .dex-search-icon,
body:not(.light-page) .dex-search-clear { color: #A99FB8; }
body:not(.light-page) .dex-search-clear:hover { background: rgba(255,255,255,0.10); color: #FFFFFF; }
body:not(.light-page) .dex-fchip {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.16); color: #C9C2D8;
}
body:not(.light-page) .dex-fchip:hover { border-color: var(--lavender); }
body:not(.light-page) .dex-fchip.active { background: var(--lavender); border-color: var(--lavender); color: #1A1420; }
body:not(.light-page) .dex-fchip.active .dex-fchip-n { color: #3A2E52; }
body:not(.light-page) .dex-card-info { color: #C9C2D8; }
body:not(.light-page) .dex-progress-label { color: #C9C2D8; }
body:not(.light-page) .dex-progress-count { color: #FFFFFF; }
body:not(.light-page) .dex-progress-bar,
body:not(.light-page) .dcc-bar { background: rgba(255,255,255,0.12); }
body:not(.light-page) .dcc-explore { color: #B8AADF; }
body:not(.light-page) .dcc-total { color: #C9C2D8; }
body:not(.light-page) .dcc-set-name { color: #F2EFF8; }
body:not(.light-page) .dcc-set-count { color: #A99FB8; }
/* Singles */
body:not(.light-page) .singles-tab {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.16); color: #C9C2D8;
}
body:not(.light-page) .singles-tab:hover { border-color: var(--lavender); }
body:not(.light-page) .singles-tab.is-active { background: var(--lavender); border-color: var(--lavender); color: #1A1420; }
body:not(.light-page) .singles-detail { color: #A99FB8; }
body:not(.light-page) .singles-price { color: #FFFFFF; }
body:not(.light-page) .singles-price-sub,
body:not(.light-page) .sm-price-sub { color: #A99FB8; }
body:not(.light-page) .sm-title,
body:not(.light-page) .sm-price { color: #FFFFFF; }
body:not(.light-page) .sm-dex {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.16); color: #B8AADF;
}
body:not(.light-page) .sm-dex:hover { background: rgba(255,255,255,0.10); color: #FFFFFF; }

/* ---------- Giveaways ---------- */
body:not(.light-page) .gw-kicker { color: #B8AADF; }
body:not(.light-page) .gw-head h1,
body:not(.light-page) .gw-board-head h1 { color: #FFFFFF; }
body:not(.light-page) .gw-collab,
body:not(.light-page) .gw-count-eta,
body:not(.light-page) .gw-count-over,
body:not(.light-page) .gw-closed,
body:not(.light-page) .gw-board-head p { color: #C9C2D8; }
body:not(.light-page) .gw-collab strong { color: #B8AADF; }
body:not(.light-page) .gw-prize { color: #EDE9F6; }
body:not(.light-page) .gw-winners h2,
body:not(.light-page) .gw-rules h2,
body:not(.light-page) .gw-index-group-title { color: #B8AADF; }
body:not(.light-page) .gw-index-group-title { border-bottom-color: rgba(255,255,255,0.12); }
body:not(.light-page) .gw-rules-body h3 { color: #C9B8F0; border-bottom-color: rgba(255,255,255,0.10); }
body:not(.light-page) .gw-rules-body strong { color: #FFFFFF; }
body:not(.light-page) .gw-rules-body a { color: #B8AADF; }
body:not(.light-page) .gw-spinlog > summary { color: #F2EFF8; }
body:not(.light-page) .gw-spinlog-list li { border-top-color: rgba(255,255,255,0.10); }
body:not(.light-page) .gw-spinlog-at { color: #A99FB8; }
body:not(.light-page) .gw-spinlog-user { color: #F2EFF8; }
body:not(.light-page) .gw-spinlog-what { color: #C9C2D8; }
body:not(.light-page) .gw-card-head h2 { color: #FFFFFF; }
body:not(.light-page) .gw-totals { color: #B8B0C8; }
body:not(.light-page) .gw-totals strong { color: #FFFFFF; }
body:not(.light-page) .gw-empty,
body:not(.light-page) .gw-find-none,
body:not(.light-page) .gw-list-note,
body:not(.light-page) .gw-wheel-note { color: #B8B0C8; }
body:not(.light-page) .gw-participants { border-color: rgba(255,255,255,0.12); }
body:not(.light-page) .gw-p { border-bottom-color: rgba(255,255,255,0.08); }
body:not(.light-page) .gw-p-user { color: #EDE9F6; }
body:not(.light-page) .gw-p-odds { color: #A99FB8; }
body:not(.light-page) .gw-secondary {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.20); color: #C9B8F0;
}
body:not(.light-page) .gw-secondary:hover { border-color: var(--lavender); background: rgba(255,255,255,0.10); }
body:not(.light-page) .gw-secondary.is-danger { color: #FF9DB8; border-color: rgba(255,157,184,0.35); }
body:not(.light-page) .gw-secondary.is-danger:hover { background: rgba(255,120,160,0.12); border-color: rgba(255,157,184,0.55); }
body:not(.light-page) .gw-admin-note,
body:not(.light-page) .gw-preview-banner,
body:not(.light-page) .gw-verify {
  background: rgba(255,255,255,0.05); border-color: rgba(255,255,255,0.25); color: #C9C2D8;
}
body:not(.light-page) .gw-preview-banner strong { color: #F2EFF8; }
body:not(.light-page) .gw-draw-error,
body:not(.light-page) .gw-spin-error { color: #FF9DB8; }
body:not(.light-page) .gw-index-body h2,
body:not(.light-page) .gw-history-head h3 a { color: #FFFFFF; }
body:not(.light-page) .gw-history-head h3 a:hover { color: #B8AADF; }
body:not(.light-page) .gw-index-prize { color: #C9C2D8; }
body:not(.light-page) .gw-history-link,
body:not(.light-page) .gw-history-back a { color: #B8AADF; }
body:not(.light-page) .gw-history-date { color: #A99FB8; }
body:not(.light-page) .gw-history-head { border-bottom-color: rgba(255,255,255,0.10); }
body:not(.light-page) .gw-tally-user { color: #F2EFF8; }
body:not(.light-page) .gw-tally-wins { color: #A99FB8; }
body:not(.light-page) .gw-req-intro { color: #B8B0C8; }
body:not(.light-page) .gw-reqs { color: #E4DFF0; }
body:not(.light-page) .gw-verify h3 { color: #FFFFFF; }
body:not(.light-page) .gw-verify-list label { color: #E4DFF0; }
body:not(.light-page) .gw-verify-empty { color: #A99FB8; }
body:not(.light-page) .gw-verify-field span { color: #B8AADF; }
body:not(.light-page) .gw-board-ghost { color: rgba(255,255,255,0.06); }
body:not(.light-page) .gw-stat-label { color: #B8B0C8; }
body:not(.light-page) .gw-stat-value { color: #FFFFFF; }
body:not(.light-page) .gw-table th { color: #B8B0C8; border-bottom-color: rgba(255,255,255,0.12); }
body:not(.light-page) .gw-table td { color: #E4DFF0; border-bottom-color: rgba(255,255,255,0.08); }
body:not(.light-page) .gw-table .is-date { color: #A99FB8; }
body:not(.light-page) .gw-table tr.is-top td { background: rgba(255,255,255,0.06); }
body:not(.light-page) .gw-undo button {
  background: rgba(255,255,255,0.06); border-color: rgba(255,255,255,0.16); color: #A99FB8;
}
body:not(.light-page) .gw-undo button:hover { border-color: rgba(255,157,184,0.5); color: #FF9DB8; background: rgba(255,120,160,0.10); }
