/* ============================================================================
   Tienda — hoja de estilos única
   ============================================================================

   REFERENCIA v4: Cult Gaia × House of CB. La eligió el dueño (16/07/2026),
   con spec propio — y son dos de sus nueve proveedores: quiere verse del
   nivel de las tiendas a las que compra. EL SISTEMA COMPLETO VIVE EN
   design.md, en la raíz — ese archivo manda sobre esta cabecera.

   LAS REGLAS DE ESTA CASA
   ─────────────────────────────────────────────────────────────────────────────
   1. MARFIL Y CHOCOLATE, no blanco y negro. El vino aparece en el precio
      rebajado y en detalles contados (<5% de la pantalla). El rosa viejo es
      SOLO fondo, jamás texto.

   2. DOS TIPOGRAFÍAS: Bodoni Moda (serif didona, títulos, SIEMPRE roman) +
      Manrope (interfaz y cuerpo). Los precios van en Manrope: un precio es un
      dato, no un titular.

   3. LAS FOTOS RESPIRAN. `gap: var(--aire)` en la rejilla y márgenes de
      revista. El muro gap:0 era la firma de Zara y murió con v3. Ni bordes,
      ni sombras, ni esquinas redondeadas — eso sigue.

   4. EL TEXTO ACOMPAÑA: cuerpo 14px, etiquetas 11px mayúscula. La foto manda.

   HISTORIAL (para no repetir)
   · v1 editorial crema + Cormorant → era el default de la IA. Lo destrozó
     Impeccable: fuente en lista negra, fondo crema delator, etiquetitas de
     andamiaje encima de cada sección.
   · v2 terracota + Young Serif → mejor ejecutado, pero no era la tienda que el
     dueño quería: el color mandaba demasiado para ropa de mujer.
   · v3 Zara (negro/blanco, Archivo, muro gap:0) → referencia real pedida por
     el dueño; vivió bien hasta que él mismo pidió subir de categoría.
   · v4 (esta) editorial de lujo → spec del dueño, sistema en design.md.

   LO QUE NO CAMBIA NUNCA
   · Contraste calculado, no estimado (scratchpad/contraste.js).
   · Nada de interfaz pasa de 300ms; todo lo que se pulsa baja a scale(0.97);
     jamás ease-in; hover tras @media (hover:hover)  [criterio de Emil Kowalski].
   · `.revelar` NUNCA lleva opacity:0 de base — eso dejó la página EN BLANCO
     cuando la animación no llegaba a correr.
   · Fotos con `contain`: el dueño sube formatos mixtos y `cover` recorta
     cabezas y dobladillos. Con fotos 3:4 en marco 3:4 se ven idénticas.
   ========================================================================== */

/* Hallmark · genre: editorial-lujo · macrostructure: escaparate-mosaico ·
   design-system: design.md · designed-as-app · theme: custom
   (vibe: "boutique de lujo, revista, femenina, cálida" · paper #FBF9F5 ·
    accent #722F37 vino · Bodoni Moda + Manrope) */

:root {
  /* ── Color v4: marfil, chocolate y vino ──────────────────────────────────
     ⚠️ LOS NOMBRES VIEJOS SE QUEDAN, LOS VALORES CAMBIAN. --blanco ya no es
     blanco: es el marfil del papel. 1700 líneas referencian estos nombres y
     re-apuntarlos ES el retema — renombrarlos sería tocar cada línea para
     nada. El nombre dice el PAPEL del color (fondo, texto…), no su pintura.
     El porqué de cada valor vive en design.md, que manda sobre este bloque. */
  --blanco:  #FBF9F5;   /* papel: marfil cálido (era #FFF) */
  --negro:   #241D17;   /* chocolate profundo: botones, wordmark */
  /* ⭐ v4.1 (pedido del dueño, 16/07): LA LETRA ES VINOTINTO — como House of
     CB escribe toda su página en su berry. La ÚNICA excepción son los
     PRECIOS, que van en chocolate (--precio): el precio es el dato que se
     busca con el ojo, y tener su propio color es lo que permite encontrarlo
     dentro de una página escrita en vino. */
  --tinta:   #722F37;   /* texto: vinotinto — 8.6:1 sobre el marfil */
  --gris:    #8A5158;   /* secundario: vino desteñido — 4.6:1 */
  --precio:  #2B241D;   /* SOLO precios: chocolate. La excepción que pidió él. */
  --tenue:   #B0858A;   /* deshabilitado, tallas agotadas (vino lavado) */
  --linea:   #E8DCD6;   /* filos: rosa arena */
  --lienzo:  #F2EDE5;   /* fondo de las fotos: beige suave */
  --vino:    #722F37;   /* el mismo tono, con su nombre para acentos */
  --rebaja:  var(--vino);
  --rosa:    #EBDCD5;   /* rosa viejo: SOLO fondos suaves. Jamás texto. */

  /* ── Tipo: serif editorial + sans de interfaz ── */
  --serif: "Bodoni Moda", "Didot", Georgia, serif;
  --ui: "Manrope", "Helvetica Neue", Helvetica, Arial, sans-serif;

  /* ── Movimiento (reglas de Emil, intactas de v3) ── */
  --ease-out: cubic-bezier(0.23, 1, 0.32, 1);
  --pulso:  140ms;
  --rapido: 180ms;
  --medio:  240ms;

  /* ── Espacio: márgenes de revista (v3 pegaba al borde; v4 respira) ── */
  --margen: clamp(1rem, 4vw, 3rem);
  --aire: clamp(1rem, 2.5vw, 2rem);   /* el gap de la rejilla — muro NO más */
  --z-sticky: 50;
  --z-nota:   80;
}

/* ── Base ─────────────────────────────────────────────────────────────────── */
*, *::before, *::after { box-sizing: border-box; }

html {
  -webkit-text-size-adjust: 100%;
  /* La cabecera es pegajosa. Sin esto, CUALQUIER salto (pulsar un filtro, abrir
     la guía de tallas, un ancla) deja el destino enterrado debajo de ella:
     medido, el título aterrizaba en y=0 con 62px de cabecera encima.
     Vale para todos los saltos de la página a la vez, sin tocar cada uno. */
  scroll-padding-top: 76px;
}
@media (max-width: 800px) {
  /* En móvil la nav baja a su propia fila y la cabecera crece a 90px. */
  html { scroll-padding-top: 104px; }
}

body {
  margin: 0;
  background: var(--blanco);
  color: var(--tinta);
  font-family: var(--ui);
  font-size: 14px;      /* v4: 13→14. El editorial se lee, no se descifra. */
  font-weight: 400;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
}

img { display: block; max-width: 100%; }
a { color: inherit; text-decoration: none; }

button {
  font: inherit;
  color: inherit;
  background: none;
  border: 0;
  padding: 0;
  cursor: pointer;
}

p { text-wrap: pretty; margin: 0; }
h1, h2, h3 { text-wrap: balance; margin: 0; font-weight: 400; }

.contenedor { padding-inline: var(--margen); }

/* La voz de la casa: mayúscula pequeña, tracking corto. NO es un adorno de
   sección — es como Zara nombra sus prendas y sus enlaces. */
.rotulo {
  font-size: 11px;
  font-weight: 400;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--gris);
}

.salto-contenido {
  position: absolute;
  left: -9999px;
  top: 0;
  background: var(--negro);
  color: var(--blanco);
  padding: 1rem 1.5rem;
  z-index: 100;
}
.salto-contenido:focus { left: 0; }

:focus-visible { outline: 2px solid var(--negro); outline-offset: 2px; }

/* ── Anuncio ──────────────────────────────────────────────────────────────────
   Delgadísimo. Contesta "¿me llega?" y "¿cómo pago?" sin robarle sitio a la
   ropa. En Zara sería una línea y nada más.
   -------------------------------------------------------------------------- */
.anuncio {
  position: relative;
  height: 24px;                /* más pequeño (pedido del dueño): era 32px */
  background: var(--negro);
  color: var(--blanco);
  overflow: hidden;
}
.anuncio__pista {
  position: absolute;
  inset: 0;
  display: grid;
  place-items: center;
  padding-inline: 1rem;
  text-align: center;
  font-size: 9px;
  letter-spacing: 0.07em;
  text-transform: uppercase;
  opacity: 0;
  transform: translateY(100%);
  transition: opacity 280ms var(--ease-out), transform 280ms var(--ease-out);
}
.anuncio__pista[data-estado="dentro"] { opacity: 1; transform: none; }
.anuncio__pista[data-estado="fuera"]  { opacity: 0; transform: translateY(-100%); }

/* ── Cabecera ─────────────────────────────────────────────────────────────── */
/* La cabecera SEMITRANSPARENTE (pedido del dueño): al bajar sobre los vídeos y
   las fotos se ve a través — el vídeo asoma y quedan flotando las letras y los
   iconos. El `backdrop-filter` desenfoca lo de detrás lo justo para que el
   texto se lea siempre, sobre una foto clara o un vídeo oscuro. El respaldo
   `rgba` más opaco es para el navegador que no entienda backdrop-filter:
   mejor legible que con el texto perdido sobre una foto. */
.cabecera {
  position: sticky;
  top: 0;
  z-index: var(--z-sticky);
  /* VINOTINTO de verdad: sobre el vídeo rosado del hero, un vino muy translúcido
     se lee ROSA. Se usa un vino más profundo y saturado con opacidad media +
     desenfoque fuerte: lee claramente vinotinto y conserva el vidrio esmerilado
     (se ve borroso lo de atrás, esa es la translucidez que pidió el dueño). */
  /* Vinotinto MÁS ROJIZO (pedido): #8C2A33 = rgb(140,42,51), sube el rojo
     respecto al #722F37. Casi sólido (0.9) para que se lea sí o sí en móvil. */
  background: rgba(140, 42, 51, 0.9);
  -webkit-backdrop-filter: blur(14px) brightness(0.92);
  backdrop-filter: blur(14px) brightness(0.92);
}
@supports not ((backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px))) {
  .cabecera { background: rgba(140, 42, 51, 0.95); }   /* #8C2A33 opaco: sin blur, para que se lea */
}
/* Sobre el vino, la letra y los iconos van en MARFIL: el vino es oscuro y la
   tinta chocolate se perdería. Solo dentro de la cabecera. */
.cabecera .logo,
.cabecera .nav__enlace,
.cabecera .favs,
.cabecera .bolsa { color: var(--blanco); }
.cabecera .nav__enlace[aria-current="true"] { border-bottom-color: var(--blanco); }
@media (hover: hover) and (pointer: fine) {
  .cabecera .nav__enlace:hover { color: #fff; }
}
/* Los iconos (bolsa, corazón) van por `stroke`, no por `color`: se pintan a
   mano en marfil dentro de la cabecera vino. */
.cabecera .bolsa__icono,
.cabecera .corazon__icono { stroke: var(--blanco); }

/* ── Al bajar, la cabecera se FUNDE con el marfil de la web ────────────────────
   Arriba (sobre el hero) va vino sólido; en cuanto la clienta baja unos px, el
   fondo pasa a MARFIL translúcido y la letra/iconos a VINO — así combina con el
   fondo claro de la web y sigue legible. El JS solo pone/quita [data-fundida];
   la transición la hace el CSS (suave, se ve "gradual" como pidió el dueño).
   Solo transform/opacity van por GPU, pero un fundido de cabecera es un repintado
   pequeño y puntual: aceptable. */
.cabecera {
  transition: background 350ms var(--ease-out);
}
.cabecera .logo, .cabecera .nav__enlace, .cabecera .favs, .cabecera .bolsa,
.cabecera .bolsa__icono, .cabecera .corazon__icono {
  transition: color 350ms var(--ease-out), stroke 350ms var(--ease-out);
}
.cabecera[data-fundida] {
  background: rgba(251, 249, 245, 0.72);   /* marfil (#FBF9F5) translúcido */
}
.cabecera[data-fundida] .logo,
.cabecera[data-fundida] .nav__enlace,
.cabecera[data-fundida] .favs,
.cabecera[data-fundida] .bolsa { color: var(--tinta); }        /* vino */
.cabecera[data-fundida] .bolsa__icono,
.cabecera[data-fundida] .corazon__icono { stroke: var(--tinta); }
.cabecera[data-fundida] .nav__enlace[aria-current="true"] { border-bottom-color: var(--tinta); }

.cabecera__fila {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding: 1.1rem var(--margen) 0.9rem;
}

/* Wordmark: el serif es la voz de la casa (v4). Roman SIEMPRE — itálica en
   títulos es firma de IA (regla hallmark en design.md). El tracking baja de
   0.22em a 0.06em: un didone con tracking de rótulo se descompone. */
.logo {
  font-family: var(--serif);
  font-size: clamp(1.25rem, 2vw, 1.6rem);
  font-weight: 500;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  white-space: nowrap;
}

/* UNA fila que se DESLIZA (nunca dos líneas), en escritorio y móvil. `min-width:0`
   + `overflow-x` dejan que el menú se encoja y se deslice DENTRO de su espacio en
   vez de empujar los iconos (corazón/bolsa) fuera de la pantalla. */
.nav {
  display: flex;
  gap: 1.5rem;
  flex-wrap: nowrap;
  overflow-x: auto;
  min-width: 0;
  scrollbar-width: none;
}
.nav::-webkit-scrollbar { display: none; }

.nav__enlace {
  font-size: 11px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--tinta);
  padding-block: 0.3rem;
  border-bottom: 1px solid transparent;
  transition: border-color var(--rapido) ease;
  white-space: nowrap;   /* "Ropa de baño" SIEMPRE en una línea */
  flex: 0 0 auto;        /* no encoge: si no cabe, se desliza */
}
.nav__enlace[aria-current="true"] { border-bottom-color: var(--negro); }

@media (hover: hover) and (pointer: fine) {
  .nav__enlace:hover { border-bottom-color: var(--negro); }
}

.nav--movil {
  display: none;
  gap: 1.25rem;
  padding: 0 var(--margen) 0.85rem;
  overflow-x: auto;
  scrollbar-width: none;
  -webkit-mask-image: linear-gradient(to right, #000 90%, transparent 100%);
          mask-image: linear-gradient(to right, #000 90%, transparent 100%);
}
.nav--movil::-webkit-scrollbar { display: none; }

@media (max-width: 800px) {
  .cabecera .nav:not(.nav--movil) { display: none; }
  /* Cabecera compacta (el dueño: "un montón de espacio desperdiciado"). El
     menú de categorías era el que abultaba (55px): se le quita el aire de
     arriba/abajo y line-height apretado. */
  .nav--movil { display: flex; gap: 0.9rem; padding: 0 var(--margen) 0.3rem; align-items: center; }
  .cabecera__fila { padding: 0.35rem var(--margen) 0.25rem; }
  .logo { font-size: 0.95rem; letter-spacing: 0.03em; }
  .nav--movil .nav__enlace { font-size: 9px; padding-block: 0.1rem; line-height: 1.1; }
  .cabecera__acciones { gap: 0.6rem; }
  .anuncio { height: 20px; }
}

/* ── Portada: la foto ES la portada ───────────────────────────────────────────
   A sangre, altura de pantalla, sin panel de color al lado. El texto se posa
   ENCIMA, abajo, diminuto. En Zara la foto no comparte con nadie.

   `height` fijo, NO `min-height`: con min-height la foto estiraba la fila hasta
   su alto intrínseco y el botón caía fuera de pantalla. Un suelo no es un techo.
   -------------------------------------------------------------------------- */
/* El marco lleva la MISMA proporción que las fotos (3:4), no una altura suelta.
   Con altura libre, `contain` rellenaba con bandas grises arriba y abajo y el
   botón acababa flotando sobre una banda: parecía roto.

   Una portada a sangre de verdad (Zara) necesita una foto ANCHA; las de
   producto son verticales. Antes que recortar la prenda — cortar cabezas y
   dobladillos es peor que cualquier banda — el marco se adapta a la foto.
   Cuando haya una foto de portada apaisada de verdad, esto se replantea. */
/* En escritorio manda la ALTURA y el ancho sale de la proporción (width:auto).
   Al revés no funciona: con `max-height` peleando contra `aspect-ratio` ganaba
   el max-height y volvían las bandas — medidas, 53px a cada lado. */
.portada {
  position: relative;
  height: min(84vh, 820px);
  aspect-ratio: 3 / 4;
  width: auto;
  max-width: 100%;
  margin-inline: auto;
  background: var(--blanco);
  overflow: hidden;
}
.portada img { width: 100%; height: 100%; object-fit: contain; }

/* Velo solo en la franja del texto: sin él, texto blanco sobre una foto clara
   es ilegible — y no se sabe qué foto subirá el dueño. */
.portada__pie {
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  padding: 4rem var(--margen) clamp(1.25rem, 3vw, 2rem);
  background: linear-gradient(to top, rgba(0,0,0,0.6), transparent);
  color: var(--blanco);
}

/* El titular del hero: serif editorial a lo grande, caja normal. Es EL
   momento tipográfico de la página — si aquí no se nota el didone, no está. */
.portada__titulo {
  font-family: var(--serif);
  font-size: clamp(2rem, 4.5vw, 3.4rem);
  font-weight: 450;
  letter-spacing: 0.01em;
  line-height: 1.08;
  margin-bottom: 0.35rem;
}
.portada__precio { font-size: 13px; margin-bottom: 1.1rem; }

/* En móvil manda el ANCHO (la pantalla) y la proporción da el alto. Al revés
   que en escritorio: allí sobra ancho, aquí sobra alto. */
@media (max-width: 700px) {
  .portada { width: 100%; height: auto; }
}

/* La portada del CONSTRUCTOR (bloque hero del CMS): a lo ancho de verdad,
   no al 3:4 de la prenda destacada. El vídeo/imagen de campaña viene
   apaisado y aquí sí llena el marco (`cover`): es SU pieza de campaña,
   compuesta para esto — no una foto de producto que no se puede recortar. */
.portada--bloque {
  aspect-ratio: auto;
  width: 100%;
  height: min(78vh, 720px);
}
.portada--bloque video,
.portada--bloque img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
@media (max-width: 700px) {
  .portada--bloque { height: min(70vh, 560px); }
}

/* ── Banners del constructor ──────────────────────────────────────────────────
   Franjas de campaña a sangre después del catálogo. La imagen manda su
   propia altura (los banners reales vienen compuestos con su texto dentro);
   el pie solo aparece si el dueño escribió algo en el CMS. */
.banner-cms {
  position: relative;
  display: block;
  margin-top: clamp(3rem, 7vw, 6rem);
}
.banner-cms img { width: 100%; height: auto; display: block; }
/* El vídeo del banner: llena el ancho como la imagen. Con altura fijada por
   perilla (b-altura-*) se recorta a cover; sin ella, su proporción natural. */
.banner-cms video { width: 100%; height: auto; display: block; object-fit: cover; }

/* iOS esconde a veces un vídeo que queda detrás de un elemento con
   backdrop-filter (la cabecera translúcida): un bug de composición conocido.
   Forzar cada vídeo a su propia capa GPU (translateZ) lo evita. Barato y solo
   toca a los vídeos. */
.portada--bloque video,
.mosaico__celda video,
.banner-cms video { transform: translateZ(0); }
.banner-cms__pie {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  padding: 3.5rem var(--margen) clamp(1.25rem, 3vw, 2rem);
  background: linear-gradient(to top, rgba(20, 12, 10, 0.55), transparent);
  color: var(--blanco);
}
.banner-cms__titulo {
  font-family: var(--serif);
  font-size: clamp(1.6rem, 3.5vw, 2.6rem);
  font-weight: 450;
  line-height: 1.1;
  margin-bottom: 0.25rem;
}
.banner-cms__sub { font-size: 13px; margin-bottom: 1rem; }
.banner-cms .cta-hueco { color: var(--blanco); border-color: var(--blanco); }

/* ── Franja de texto (bloque `texto`) ─────────────────────────────────────────
   La campaña respira: serif grande centrado sobre banda rosa viejo — el único
   sitio donde el rosa trabaja, siempre de fondo, jamás de letra. */
.bloque-texto {
  margin-top: clamp(3rem, 7vw, 6rem);
  padding: clamp(3rem, 6vw, 5rem) var(--margen);
  background: var(--rosa);
  text-align: center;
}
.bloque-texto__titulo {
  font-family: var(--serif);
  font-size: clamp(1.7rem, 3.8vw, 2.8rem);
  font-weight: 450;
  line-height: 1.12;
  max-width: 26ch;
  margin-inline: auto;
}
.bloque-texto__sub {
  color: var(--gris);
  font-size: 14px;
  max-width: 52ch;
  margin: 0.75rem auto 1.5rem;
}

/* ── Mosaico editorial (bloque `mosaico`): dos imágenes, dos destinos ──────── */
.dupla {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--aire);
  margin-top: clamp(3rem, 7vw, 6rem);
  padding-inline: var(--margen);
}
.dupla__celda { position: relative; display: block; }
.dupla__celda img { width: 100%; height: auto; display: block; }
.dupla__titulo {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  padding: 2.5rem 1.25rem 1rem;
  background: linear-gradient(to top, rgba(20, 12, 10, 0.5), transparent);
  color: var(--blanco);
  font-family: var(--serif);
  font-size: clamp(1.1rem, 2vw, 1.6rem);
}
@media (max-width: 700px) { .dupla { grid-template-columns: 1fr; } }

/* ── LAS PERILLAS DE DISEÑO DE LOS BLOQUES (clases b-*) ───────────────────────
   Cada bloque del constructor elige su diseño en el CMS y llega con estas
   clases. SE COMBINAN: altura × alineación × velo × letra × disposición ×
   proporción × ancho × separación = miles de bloques distintos sin código.
   Sin clase = el default de siempre: los bloques viejos no cambian.        */

/* altura: cuánto manda el bloque en la pantalla */
.b-altura-baja img, .b-altura-baja video       { max-height: 32vh; object-fit: cover; width: 100%; }
.b-altura-media img, .b-altura-media video     { max-height: 55vh; object-fit: cover; width: 100%; }
.b-altura-alta img, .b-altura-alta video       { max-height: 78vh; object-fit: cover; width: 100%; }
.b-altura-completa img, .b-altura-completa video { height: 100vh; max-height: 100vh; object-fit: cover; width: 100%; }
.portada--bloque.b-altura-baja   { height: 32vh; }
.portada--bloque.b-altura-media  { height: 55vh; }
.portada--bloque.b-altura-alta   { height: 78vh; }
.portada--bloque.b-altura-completa { height: 100vh; }

/* ancho: a sangre (default) o con márgenes de revista */
.b-ancho-contenido { margin-inline: var(--margen); }

/* alinear: el texto encima de la foto */
.b-alinear-izquierda .banner-cms__pie, .b-alinear-izquierda .portada__pie { text-align: left; }
.b-alinear-centro .banner-cms__pie, .b-alinear-centro .portada__pie { text-align: center; }
.b-alinear-derecha .banner-cms__pie, .b-alinear-derecha .portada__pie { text-align: right; }

/* velo: el oscurecido que hace legible el texto sobre la foto */
.b-velo-no .banner-cms__pie, .b-velo-no .portada__pie { background: none; }
.b-velo-suave .banner-cms__pie, .b-velo-suave .portada__pie {
  background: linear-gradient(to top, rgba(20, 12, 10, 0.35), transparent); }
.b-velo-fuerte .banner-cms__pie, .b-velo-fuerte .portada__pie {
  background: linear-gradient(to top, rgba(20, 12, 10, 0.78), transparent); }
.b-velo-vino .banner-cms__pie, .b-velo-vino .portada__pie {
  background: linear-gradient(to top, rgba(94, 33, 41, 0.72), transparent); }

/* letra: el tamaño del título del bloque */
.b-letra-chica .banner-cms__titulo, .b-letra-chica .portada__titulo { font-size: clamp(1.1rem, 2vw, 1.6rem); }
.b-letra-media .banner-cms__titulo, .b-letra-media .portada__titulo { font-size: clamp(1.6rem, 3.5vw, 2.6rem); }
.b-letra-grande .banner-cms__titulo, .b-letra-grande .portada__titulo { font-size: clamp(2.2rem, 5.5vw, 4.2rem); }

/* separación: el aire con el bloque de arriba */
.b-separacion-pegado { margin-top: 4px !important; }
.b-separacion-amplio { margin-top: clamp(5rem, 11vw, 9rem) !important; }

/* botón del bloque */
.b-boton-solido .cta-hueco {
  border: 0; background: var(--negro); color: var(--blanco);
  padding: 0.8rem 1.8rem; }
.b-boton-fantasma .cta-hueco {
  border: 1px solid currentColor; padding: 0.7rem 1.6rem; }

/* proporción de las celdas (rejilla y mosaico) */
.b-proporcion-3-4 .casillas__celda img, .b-proporcion-3-4 .dupla__celda img { aspect-ratio: 3 / 4; object-fit: cover; }
.b-proporcion-1-1 .casillas__celda img, .b-proporcion-1-1 .dupla__celda img { aspect-ratio: 1 / 1; object-fit: cover; }
.b-proporcion-16-9 .casillas__celda img, .b-proporcion-16-9 .dupla__celda img { aspect-ratio: 16 / 9; object-fit: cover; }
.b-proporcion-natural .casillas__celda img, .b-proporcion-natural .dupla__celda img { aspect-ratio: auto; object-fit: contain; height: auto; }

/* disposición: cómo se arma la tira
   diagonal — las casillas pares bajan: el escalonado editorial
   vertical — una debajo de otra a lo ancho
   collage  — la primera manda al doble de tamaño */
.b-disposicion-diagonal .casillas__celda:nth-child(even),
.b-disposicion-diagonal .dupla__celda:nth-child(even) { transform: translateY(clamp(1.5rem, 4vw, 3.5rem)); }
.b-disposicion-diagonal .casillas__fila, .b-disposicion-diagonal.dupla { padding-bottom: clamp(1.5rem, 4vw, 3.5rem); }
.b-disposicion-vertical .casillas__fila { display: flex; flex-direction: column; }
.b-disposicion-vertical.dupla { grid-template-columns: 1fr; }
.b-disposicion-collage .casillas__fila { grid-auto-flow: dense; }
.b-disposicion-collage .casillas__celda:first-child { grid-column: span 2; grid-row: span 2; }

/* rótulo de las casillas: encima (default), debajo de la foto, u oculto */
.b-rotulo-debajo .casillas__rotulo, .b-rotulo-debajo .dupla__titulo {
  position: static; background: none; color: var(--tinta);
  padding: 0.6rem 0.25rem 0; }
.b-rotulo-oculto .casillas__rotulo, .b-rotulo-oculto .dupla__titulo { display: none; }

/* fondo de la franja de texto */
.b-fondo-marfil { background: var(--blanco) !important; }
.b-fondo-chocolate { background: var(--negro) !important; }
.b-fondo-chocolate .bloque-texto__titulo, .b-fondo-chocolate .cta-hueco { color: var(--blanco); }
.b-fondo-chocolate .bloque-texto__sub { color: #CBB9AC; }
.b-fondo-vino { background: var(--vino) !important; }
.b-fondo-vino .bloque-texto__titulo, .b-fondo-vino .cta-hueco { color: var(--blanco); }
.b-fondo-vino .bloque-texto__sub { color: #E5C6CB; }

/* ── Rejilla de categorías (bloque `rejilla`) ─────────────────────────────────
   LA firma de Bella Barnett: una tira de casillas foto+rótulo a sangre, cada
   una a su destino. El rótulo va ENCIMA de la foto, abajo y centrado, en
   mayúscula chica — como lo hacen ellos. En móvil la tira se desliza con el
   dedo (una rejilla de 6 columnas en 375px serían estampillas). */
.casillas { margin-top: clamp(3rem, 7vw, 6rem); }
.casillas__titulo { padding-inline: var(--margen); margin-bottom: 1rem; }
.casillas__fila {
  display: grid;
  grid-template-columns: repeat(var(--cols, 4), minmax(0, 1fr));
  gap: 4px;
}
.casillas__celda { position: relative; display: block; overflow: hidden; background: var(--lienzo); }
.casillas__celda img {
  width: 100%;
  height: 100%;
  aspect-ratio: 3 / 4;
  object-fit: cover;   /* casillas LLENAS: son piezas de campaña, no fichas */
  display: block;
  transition: transform var(--medio) var(--ease-out);
}
.casillas__rotulo {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  padding: 2.5rem 0.5rem 0.9rem;
  background: linear-gradient(to top, rgba(20, 12, 10, 0.55), transparent);
  color: var(--blanco);
  text-align: center;
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
}
@media (hover: hover) and (pointer: fine) {
  .casillas__celda:hover img { transform: scale(1.04); }
}
@media (max-width: 700px) {
  .casillas__fila {
    display: flex;
    overflow-x: auto;
    scroll-snap-type: x proximity;
    scrollbar-width: none;
  }
  .casillas__fila::-webkit-scrollbar { display: none; }
  .casillas__celda { flex: 0 0 44%; scroll-snap-align: start; }
}

/* ── Carrusel de prendas (bloque `carrusel`) ──────────────────────────────────
   Las mismas tarjetas del catálogo, en un riel que se desliza con el swipe
   nativo. Nada nuevo que aprender: la tarjeta ya se conoce. */
.fila-prendas { margin-top: clamp(3rem, 7vw, 6rem); }
.fila-prendas__riel {
  display: flex;
  gap: var(--aire);
  overflow-x: auto;
  padding: 1.25rem var(--margen) 0.5rem;
  scroll-snap-type: x proximity;
  scrollbar-width: none;
}
.fila-prendas__riel::-webkit-scrollbar { display: none; }
.fila-prendas__riel .prenda {
  flex: 0 0 clamp(200px, 22vw, 300px);
  scroll-snap-align: start;
}

/* ── Botón de línea ───────────────────────────────────────────────────────── */
.cta-hueco {
  display: inline-block;
  font-size: 11px;
  font-weight: 500;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  padding-bottom: 3px;
  border-bottom: 1px solid currentColor;
  transition: opacity var(--rapido) ease, transform var(--pulso) var(--ease-out);
}
.cta-hueco:active { transform: scale(0.97); }
@media (hover: hover) and (pointer: fine) { .cta-hueco:hover { opacity: 0.65; } }

/* ── Sección ──────────────────────────────────────────────────────────────── */
.seccion { padding-block: clamp(2rem, 4vw, 3.5rem) 0; }

.seccion__cabeza {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 1rem;
  padding-inline: var(--margen);
  margin-bottom: 1.25rem;
}

/* Título de sección (v4): serif grande en caja normal — titular de revista,
   no rótulo de pasillo. La mayúscula chiquita era la voz de Zara. */
.seccion__titulo {
  font-family: var(--serif);
  font-size: clamp(1.5rem, 3vw, 2.1rem);
  font-weight: 450;
  letter-spacing: 0.01em;
  line-height: 1.15;
}
.seccion__cuenta { font-size: 11px; color: var(--gris); }

/* ── Filtros ──────────────────────────────────────────────────────────────────
   Sin píldoras: solo texto con un filete debajo. Un botón dibujado pesaría más
   que el nombre de la prenda, y eso aquí no puede pasar.
   -------------------------------------------------------------------------- */
.filtros {
  margin-bottom: clamp(1.25rem, 2.5vw, 2rem);
}

/* Fila de VISTAS (Todo · Rebajas · Novedades): pastillas de texto. */
.filtros__vistas {
  display: flex;
  flex-wrap: wrap;
  gap: 1.25rem;
  padding-inline: var(--margen);
  margin-bottom: 0.9rem;
}
.filtro {
  font-size: 11px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--gris);
  padding-bottom: 3px;
  border-bottom: 1px solid transparent;
  transition: color var(--rapido) ease,
              border-color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
.filtro:active { transform: scale(0.97); }
.filtro[aria-pressed="true"] { color: var(--tinta); border-bottom-color: var(--negro); }
@media (hover: hover) and (pointer: fine) { .filtro:hover { color: var(--tinta); } }

/* CATEGORÍAS: tarjetas GRANDES tipo editorial (foto con el nombre en serif
   encima), como le gustaban al dueño "antes" — pero fusionadas (una sola cosa,
   sin doble) y filtran EN EL SITIO (data-cat, sin recargar). Rejilla que respira. */
.filtros__cats {
  display: flex;                       /* UNA FILA, una al lado de la otra (se desliza) */
  gap: var(--aire, 0.55rem);
  overflow-x: auto;
  scrollbar-width: none;
  padding-inline: var(--margen);
  scroll-snap-type: x proximity;
}
.filtros__cats::-webkit-scrollbar { display: none; }
.cat-card {
  position: relative;
  flex: 0 0 auto;
  width: clamp(116px, 34vw, 150px);    /* mediana: se ven ~3 y se deslizan las demás */
  aspect-ratio: 3 / 4;
  scroll-snap-align: start;
  overflow: hidden;
  display: block;
  background: #EDE4DB;                 /* relleno cálido mientras baja la foto */
  transition: transform var(--pulso) var(--ease-out);
}
.cat-card:active { transform: scale(0.985); }
.cat-card__foto {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;                   /* tile de navegación: lleno, uniforme */
  opacity: 0;                          /* aparece con FUNDIDO al cargar */
  transition: opacity 300ms var(--ease-out), transform 300ms var(--ease-out);
}
.cat-card__foto.cargada { opacity: 1; }
.cat-card__nombre {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  padding: 1.6rem 0.5rem 0.7rem;
  background: linear-gradient(transparent, rgba(43, 36, 29, 0.55));
  color: var(--blanco);
  font-family: var(--serif);
  font-size: clamp(0.82rem, 3.4vw, 1rem);
  letter-spacing: 0.04em;
  text-transform: uppercase;
  text-align: center;
  line-height: 1.1;
}
.cat-card[aria-pressed="true"] { outline: 1.5px solid var(--tinta); outline-offset: -1.5px; }
.cat-card[aria-pressed="true"] .cat-card__foto { transform: scale(1.04); }
@media (hover: hover) and (pointer: fine) {
  .cat-card:hover .cat-card__foto { transform: scale(1.05); }
}

/* ── Rejilla: LAS FOTOS RESPIRAN (v4) ─────────────────────────────────────────
   El muro `gap:0` era LA firma de Zara y murió con v3. Cult Gaia y House of CB
   —la referencia que eligió el dueño— separan las fotos con aire y márgenes de
   revista: cada prenda es una pieza, no un ladrillo. La foto sigue mandando;
   ahora además se la deja ser mirada.
   -------------------------------------------------------------------------- */
.rejilla {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: var(--aire);
}
@media (max-width: 1100px) { .rejilla { grid-template-columns: repeat(3, 1fr); } }
@media (max-width: 700px)  { .rejilla { grid-template-columns: repeat(2, 1fr); } }

/* ── Prenda ───────────────────────────────────────────────────────────────── */
.prenda { display: block; padding-bottom: 2.25rem; }

/* Marco 2:3 (la proporción de casi todas las fotos Oh Polly) y `cover`: así
   TODAS las tarjetas quedan del MISMO tamaño, una al lado de otra, sin las
   bandas disparejas que hacían ver los productos distintos (pedido del dueño).
   Como el marco YA es 2:3, la mayoría de fotos (2:3) llenan EXACTO sin recortar
   nada; solo las pocas 3:4 pierden un pelín de los lados (fondo/brazos, nunca
   cabeza ni pies) — se conserva el espíritu del "no recortar" de la marca. */
.prenda__marco {
  position: relative;
  aspect-ratio: 2 / 3;
  background: var(--lienzo);
  overflow: hidden;
}
/* Shimmer de carga: mientras la foto baja, la tarjeta se ve "cargando" (no
   vacía = "sin imagen"). La foto va encima (z-index) y lo tapa al aparecer;
   cuando ya cargó, se apaga la animación. */
.prenda__marco::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  background: linear-gradient(100deg, #EBE1D6 30%, #F5F0E8 50%, #EBE1D6 70%);
  background-size: 200% 100%;
  animation: brillo-carga 1.5s var(--ease-out) infinite;
}
@keyframes brillo-carga {
  0%   { background-position: 150% 0; }
  100% { background-position: -150% 0; }
}
.prenda__marco:has(.cargada)::after { animation: none; opacity: 0; }

/* Blur-up: la mini borrosa va ENTRE el shimmer (z0) y la foto (z2). Se ve la
   prenda intuida mientras baja la nítida; al cargar, la foto opaca la tapa y la
   borrosa se desvanece. `scale` esconde los bordes que el blur deja translúcidos. */
.prenda__blur {
  position: absolute;
  inset: 0;
  z-index: 1;
  background-size: cover;
  background-position: center;
  filter: blur(16px);
  transform: scale(1.12);
  transition: opacity var(--medio) var(--ease-out);
}
.prenda__marco:has(.prenda__foto--principal.cargada) .prenda__blur { opacity: 0; }

.prenda__foto { position: relative; z-index: 2; }

.prenda__foto {
  width: 100%;
  height: 100%;
  object-fit: cover;
  transition: opacity var(--medio) ease;
}
/* La foto principal aparece con FUNDIDO al cargar (no de golpe): así, al filtrar,
   no se ve el "parpadeo en blanco". La clase `cargada` la pone el JS al load. */
.prenda__foto--principal { opacity: 0; }
.prenda__foto--principal.cargada { opacity: 1; }
/* Segunda foto al pasar el mouse: enseña la prenda por detrás. Tiene función. */
.prenda__foto--alterna { position: absolute; inset: 0; opacity: 0; }

/* Al filtrar, el grid se ATENÚA suave mientras llegan las prendas nuevas —
   transición cara, no un salto en blanco. El JS pone/quita `rejilla--cargando`. */
.rejilla { transition: opacity 320ms var(--ease-out); }
.rejilla--cargando { opacity: 0.3; }

@media (hover: hover) and (pointer: fine) {
  .prenda:hover .prenda__foto--alterna  { opacity: 1; }
  .prenda:hover .prenda__foto--principal { opacity: 0; }
}
@media (hover: none) { .prenda__foto--alterna { display: none; } }

/* Sello sin fondo: tipografía pelada sobre la foto. Una cajita de color sería
   lo primero que se ve, y lo primero tiene que ser la prenda. */
.prenda__sello {
  position: absolute;
  top: 0.6rem;
  left: 0.6rem;
  z-index: 2;
  font-size: 10px;
  font-weight: 500;
  letter-spacing: 0.08em;
  text-transform: uppercase;
}
.prenda__sello--oferta  { color: var(--rebaja); }
.prenda__sello--agotado { color: var(--tinta); }

.prenda__datos { padding: 0.7rem 0.6rem 0; }

.prenda__nombre {
  font-size: 12px;
  letter-spacing: 0.02em;
  text-transform: uppercase;
  margin-bottom: 0.15rem;
  /* ESTÁNDAR MULTIMARCA: máximo 2 líneas con "…". Nombres de largo distinto
     (una marca vs otra) ya no descuadran la rejilla, y `min-height` reserva las
     dos líneas para que TODAS las tarjetas queden igual de altas. */
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
  min-height: 2.6em;
}

/* La marca SE VE. La escondí para el look Zara — pero Zara es de UNA marca.
   Esta tienda es multimarca (Revolve, ASOS): la clienta llega buscando "algo de
   Princess Polly", así que esconderle la marca es esconderle lo que busca. */
.prenda__marca {
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--gris);
  margin-bottom: 0.2rem;
}

.prenda__precio {
  color: var(--precio);   /* los precios NO van en vino: son la excepción */
  display: flex;
  align-items: baseline;
  gap: 0.45rem;
  font-size: 12px;
}
.precio--tachado { color: var(--gris); text-decoration: line-through; }

/* ── Marca (la puerta a cada proveedor) ───────────────────────────────────────
   Misma anatomía que .prenda a propósito: es el mismo muro de fotos. La rejilla
   lleva gap:0, así que el padding va SIEMPRE en __datos y NUNCA en la tarjeta —
   si se pone en la tarjeta, las fotos se separan y el muro se rompe.
   -------------------------------------------------------------------------- */
.marca-t { display: block; padding-bottom: 2.25rem; }

.marca-t__marco {
  position: relative;
  aspect-ratio: 3 / 4;
  background: var(--lienzo);
  overflow: hidden;
}

/* `contain` y nunca `cover`: las fotos vienen de proveedores distintos y con
   formatos mixtos. `cover` corta cabezas y dobladillos, y en ropa eso es peor
   que una banda de fondo. (Lección 8 del CLAUDE.md.) */
.marca-t__foto {
  width: 100%;
  height: 100%;
  object-fit: contain;
  transition: transform var(--medio) var(--ease-out);
}

/* El único movimiento: un acercamiento mínimo. Solo transform — va por GPU.
   Detrás de hover:hover porque en táctil se dispararía al tocar. */
@media (hover: hover) and (pointer: fine) {
  .marca-t:hover .marca-t__foto { transform: scale(1.03); }
}
/* Todo lo que se pulsa baja: sin acuse de recibo la interfaz parece rota. */
.marca-t:active { transform: scale(0.97); }
.marca-t { transition: transform var(--pulso) var(--ease-out); }

.marca-t__datos { padding: 0.7rem 0.6rem 0; }

.marca-t__nombre {
  font-size: 12px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--tinta);
  margin-bottom: 0.15rem;
}

.marca-t__n {
  font-size: 10px;
  letter-spacing: 0.04em;
  color: var(--gris);
}

@media (prefers-reduced-motion: reduce) {
  .marca-t, .marca-t__foto { transition: none; }
  .marca-t:hover .marca-t__foto { transform: none; }
}
.precio--oferta  { color: var(--precio); font-weight: 600; }   /* precio = chocolate SIEMPRE; la rebaja se nota por el tachado de al lado */

.puntos { display: flex; gap: 0.3rem; margin-top: 0.45rem; }
.punto {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  border: 1px solid var(--linea);
}

/* ── Ficha ────────────────────────────────────────────────────────────────── */
.ficha {
  display: grid;
  grid-template-columns: 1.45fr 1fr;
  gap: clamp(1.5rem, 3vw, 3rem);
  align-items: start;
}
/* `minmax(0, 1fr)` y no `1fr` pelado: un grid item no encoge por debajo de su
   min-content, y el min-content de una foto es su ancho INTRÍNSECO (900px).
   Con `1fr` la columna media 394px en una pantalla de 375 y toda la ficha se
   desbordaba de lado. Medido en Chrome a 375px, no supuesto. */
@media (max-width: 900px) { .ficha { grid-template-columns: minmax(0, 1fr); gap: 0; } }

/* ── El mosaico: la galería de House of CB (la pidió el dueño con su link) ───
   Las fotos COMPLETAS, de dos en dos, y se recorren BAJANDO por la página —
   no un carrusel de una en una. El vídeo es una celda más y anda solo.

   `contain`, NUNCA `cover`. Lo pedí al revés un día y el dueño lo devolvió en
   una frase: "las imagenes deben verse completas no picadas". Es además la
   regla 8 de la casa: si una foto no llena la celda, se arregla EL DATO
   (pedirla 3:4 al origen, como ya hace foto3x4), no se recorta a la clienta
   la mitad del vestido. Las importadas vienen 3:4 clavado, así que contain
   las pinta idénticas a llenas — sin recortar jamás a nadie.              */
.mosaico {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 4px;
  transition: opacity 200ms var(--ease-out);   /* cruza-fundido al cambiar de color */
}
.mosaico--cambiando { opacity: 0; }

/* La celda NO impone proporción: adopta la de la foto. El picoteo tenía DOS
   capas — el crop=center de la URL (arreglado en fotoCompleta) y este marco
   3:4 forzado sobre fotos 2:3. Con la celda a proporción natural la foto sale
   ENTERA, sin recorte y sin bandas: la fila la manda la foto, como en House
   of CB, donde todas las fotos de una prenda comparten proporción. */
/* La celda RESERVA espacio con una proporción fija (por defecto 2:3; el JS la
   ajusta a la proporción REAL de las fotos del producto en `--prop`). Sin esto
   la celda se colapsaba mientras la foto bajaba y luego crecía → todo saltaba
   al cargar y al cambiar de color. Con espacio reservado, entra suave. */
.mosaico__celda {
  aspect-ratio: var(--prop, 2 / 3);
  background: var(--lienzo);
  overflow: hidden;
}

.mosaico__celda img {
  width: 100%;
  height: 100%;
  object-fit: cover;             /* la celda YA es de la proporción de la foto: llena sin recortar */
  display: block;
  opacity: 0;                    /* aparece con FUNDIDO (clase `cargada` por JS) */
  /* El zoom de la celda: la escala SE transiciona, el ORIGEN no (--zx/--zy
     debe seguir al cursor al instante o la imagen se arrastra detrás). */
  transform-origin: var(--zx, 50%) var(--zy, 50%);
  transition: transform var(--medio) var(--ease-out), opacity 300ms var(--ease-out);
}
.mosaico__celda img.cargada { opacity: 1; }

/* Zoom al tocar la foto: acercarse a la tela es lo que decide la compra.
   En la celda con vídeo no existe (ahí el gesto es reproducir/pausar). */
@media (hover: hover) and (pointer: fine) {
  .mosaico__celda:not(.mosaico__celda--video) { cursor: zoom-in; }
}
.mosaico__celda.zoom { cursor: zoom-out; }
.mosaico__celda.zoom img { transform: scale(2.2); }

/* El vídeo declara su 2:3 (la proporción con la que Oh Polly los publica):
   sin ella, hasta que llegan los metadatos el <video> mide 150px de alto por
   defecto y la página pega un salto cuando arranca. */
.mosaico__celda video {
  width: 100%;
  height: auto;
  aspect-ratio: 2 / 3;
  object-fit: cover;
  display: block;
}

/* En el teléfono el mosaico se vuelve carrusel a pantalla completa con el
   swipe NATIVO (scroll-snap): cero JavaScript. Es lo que hace la propia
   House of CB en móvil. La sombra de scroll no hace falta: se ve el filo de
   la foto siguiente asomando (scroll-padding deja 8% del borde). */
@media (max-width: 900px) {
  .mosaico {
    display: flex;
    overflow-x: auto;
    scroll-snap-type: x mandatory;
    gap: 2px;
    scrollbar-width: none;
  }
  .mosaico::-webkit-scrollbar { display: none; }
  .mosaico__celda {
    flex: 0 0 92%;
    scroll-snap-align: center;
  }
}


/* ── Panel de compra ──────────────────────────────────────────────────────── */
.panel { position: sticky; top: 90px; padding-inline: var(--margen); }
@media (max-width: 900px) { .panel { position: static; padding-top: 1.5rem; } }

/* Pulsable: lleva a todo lo de esa marca. En un multimarca, "quiero más de
   esta marca" es el gesto más natural que hay después de que algo te guste. */
.panel__marca {
  display: inline-block;
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--gris);
  margin-bottom: 0.4rem;
  padding-bottom: 2px;
  border-bottom: 1px solid transparent;
  transition: color var(--rapido) ease, border-color var(--rapido) ease;
}
@media (hover: hover) and (pointer: fine) {
  a.panel__marca:hover { color: var(--tinta); border-color: var(--negro); }
}

/* ── Marcas ─────────────────────────────────────────────────────────────────
   Con cientos de marcas, una lista de casillas no sirve: hay que poder buscar.
   -------------------------------------------------------------------------- */
.buscar-marca {
  width: 100%;
  max-width: 200px;
  border: 0;
  border-bottom: 1px solid var(--linea);
  background: none;
  font: inherit;
  font-size: 12px;
  color: var(--tinta);
  padding: 0.3rem 0;
  margin-bottom: 0.6rem;
}
.buscar-marca:focus { outline: none; border-color: var(--negro); }
.buscar-marca::placeholder { color: var(--tenue); }

/* Alto tope + scroll: con 200 marcas el panel no puede medir 3 metros. */
.opciones--marcas {
  flex-direction: column;
  align-items: flex-start;
  gap: 0.45rem;
  max-height: 190px;
  overflow-y: auto;
  padding-right: 0.5rem;
}
.opcion-marca {
  display: flex;
  align-items: baseline;
  gap: 0.4rem;
  font-size: 12px;
  letter-spacing: 0.02em;
  color: var(--gris);
  text-align: left;
  transition: color var(--rapido) ease;
}
.opcion-marca[aria-pressed="true"] { color: var(--tinta); font-weight: 600; }
.opcion-marca__n { font-size: 10px; color: var(--tenue); }
@media (hover: hover) and (pointer: fine) {
  .opcion-marca:hover { color: var(--tinta); }
}

/* El nombre de la prenda en su ficha: serif, caja normal (v4). Es el titular
   de ESTA página — House of CB lo trata como el nombre de un vestido de
   revista, no como una referencia de almacén. */
.panel__titulo {
  font-family: var(--serif);
  font-size: clamp(1.5rem, 2.6vw, 2.1rem);
  font-weight: 450;
  letter-spacing: 0.01em;
  line-height: 1.12;
  margin-bottom: 0.5rem;
}

.panel__precio {
  color: var(--precio);
  display: flex;
  align-items: baseline;
  gap: 0.6rem;
  font-size: 15px;
  margin-bottom: 1.75rem;
}

.panel__descripcion {
  max-width: 62ch;
  font-size: 13px;
  line-height: 1.65;
  margin-bottom: 1.75rem;
}

.grupo { margin-bottom: 1.5rem; }

.grupo__cabeza {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 1rem;
  margin-bottom: 0.6rem;
}
.grupo__valor { font-size: 11px; letter-spacing: 0.04em; text-transform: uppercase; }

.ver-guia {
  font-size: 11px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--gris);
  border-bottom: 1px solid var(--linea);
  padding-bottom: 2px;
  transition: color var(--rapido) ease,
              border-color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
.ver-guia:active { transform: scale(0.97); }
@media (hover: hover) and (pointer: fine) {
  .ver-guia:hover { color: var(--tinta); border-color: var(--negro); }
}

/* ── Colores ──────────────────────────────────────────────────────────────── */
.colores { display: flex; flex-wrap: wrap; gap: 0.55rem; }

.color {
  position: relative;
  width: 26px;
  height: 26px;
  border-radius: 50%;
  border: 1px solid var(--linea);
  transition: transform var(--pulso) var(--ease-out);
}
/* El anillo va por fuera: la clienta tiene que ver el color limpio, no un
   borde comiéndoselo. */
.color::after {
  content: "";
  position: absolute;
  inset: -4px;
  border-radius: 50%;
  border: 1px solid transparent;
  transition: border-color var(--rapido) ease;
}
.color[aria-pressed="true"]::after { border-color: var(--negro); }
.color:active { transform: scale(0.94); }
@media (hover: hover) and (pointer: fine) {
  .color:hover { transform: scale(1.08); }
  .color:active { transform: scale(0.94); }
}

/* ── Tallas ───────────────────────────────────────────────────────────────────
   Las agotadas se TACHAN, no se ocultan: genera urgencia y evita que pregunten
   por WhatsApp algo que no hay.
   Sin recuadro, solo la letra: un borde por talla llenaría el panel de cajas, y
   aquí el panel tiene que desaparecer.
   -------------------------------------------------------------------------- */
.tallas { display: flex; flex-wrap: wrap; gap: 0.6rem; }

/* ⚠️ 44x44px mínimo. Antes la "S" medía 9x21px: el ancho de la letra.

   Un dedo cubre ~9mm; en un móvil eso son ~44px. Con 9px de ancho se falla el
   toque y se pide OTRA TALLA — y eso no se descubre hasta que llega la
   devolución. Es la guía de Apple y de Google, y aquí no es un detalle de
   manual: es un pedido equivocado.

   El área táctil crece con padding, pero la línea del subrayado se queda pegada
   a la letra con un ::after: si el filete midiera 44px, el diseño se llenaría
   de rayas gordas. Zona grande, marca fina. */
.talla {
  position: relative;
  min-width: 44px;
  min-height: 44px;
  padding: 0 0.4rem;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 12px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--tinta);
  transition: border-color var(--rapido) ease,
              color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
/* La marca: un filete fino bajo la letra, no bajo los 44px de zona táctil. */
.talla::after {
  content: "";
  position: absolute;
  left: 50%;
  bottom: 12px;
  width: 1.6em;
  height: 1px;
  background: transparent;
  transform: translateX(-50%);
  transition: background-color var(--rapido) ease;
}
.talla:active:not(:disabled) { transform: scale(0.94); }
.talla[aria-pressed="true"] { font-weight: 600; }
.talla[aria-pressed="true"]::after { background: var(--negro); }
.talla:disabled {
  color: var(--tenue);
  cursor: not-allowed;
  text-decoration: line-through;
  text-decoration-thickness: 1px;
}
@media (hover: hover) and (pointer: fine) {
  .talla:hover:not(:disabled)::after { background: var(--linea); }
}

.aviso-stock {
  font-size: 11px;
  color: var(--rebaja);
  letter-spacing: 0.04em;
  margin-top: 0.7rem;
  min-height: 1.2em;
}

/* ── Botón principal ──────────────────────────────────────────────────────────
   Negro macizo, esquinas vivas. La única mancha sólida de la página.
   -------------------------------------------------------------------------- */
.boton-wa {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 0.55rem;
  width: 100%;
  padding: 1rem;
  background: var(--negro);
  color: var(--blanco);
  border: 1px solid var(--negro);
  font-size: 12px;
  font-weight: 500;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  transition: background-color var(--rapido) ease,
              color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
.boton-wa:active { transform: scale(0.98); }
.boton-wa svg { width: 15px; height: 15px; fill: currentColor; }
.boton-wa[aria-disabled="true"] {
  background: var(--blanco);
  color: var(--tenue);
  border-color: var(--linea);
  cursor: not-allowed;
  pointer-events: none;
}
@media (hover: hover) and (pointer: fine) {
  .boton-wa:hover { background: var(--blanco); color: var(--negro); }
}

.nota-envio {
  font-size: 10px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--gris);
  text-align: center;
  margin-top: 0.7rem;
}

/* ── Confianza ────────────────────────────────────────────────────────────── */
.confianza {
  display: grid;
  gap: 0.75rem;
  margin-top: 1.5rem;
  padding-top: 1.25rem;
  border-top: 1px solid var(--linea);
}

/* Franja de confianza en la MAIN: a lo ancho, 3 columnas, aire alrededor.
   Anula el borde/margen del componente (aquí va en su propia franja). */
.confianza-franja {
  margin-top: clamp(2rem, 5vw, 4rem);
  padding: clamp(1.75rem, 4vw, 2.75rem) var(--margen);
  background: var(--rosa, #FBF6F0);
}
.confianza-franja .confianza {
  max-width: 1000px;
  margin: 0 auto;
  border-top: 0;
  padding-top: 0;
  grid-template-columns: repeat(3, 1fr);
  gap: clamp(1rem, 3vw, 2rem);
}
@media (max-width: 620px) {
  .confianza-franja .confianza { grid-template-columns: 1fr; gap: 1rem; }
}

/* Botón "volver arriba": flotante abajo-derecha, vino. */
.volver-arriba {
  position: fixed;
  right: clamp(0.9rem, 3vw, 1.75rem);
  bottom: clamp(0.9rem, 3vw, 1.75rem);
  z-index: var(--z-sticky);
  width: 42px;
  height: 42px;
  border-radius: 50%;
  background: var(--tinta);
  display: grid;
  place-items: center;
  box-shadow: 0 6px 18px rgba(43, 36, 29, 0.22);
  transition: transform var(--pulso) var(--ease-out);
}
.volver-arriba[hidden] { display: none; }
.volver-arriba svg {
  width: 17px; height: 17px;
  fill: none; stroke: var(--blanco);
  stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round;
}
.volver-arriba:active { transform: scale(0.9); }
@media (hover: hover) and (pointer: fine) {
  .volver-arriba:hover { transform: translateY(-2px); }
}

/* Migas de pan (ruta): Inicio › Categoría › Prenda. */
.migas {
  display: flex; flex-wrap: wrap; align-items: center; gap: 0.4rem;
  padding: var(--margen) var(--margen) 0;
  font-size: 11px; letter-spacing: 0.04em; text-transform: uppercase;
  color: var(--gris);
}
.migas a { color: var(--gris); transition: color var(--rapido) ease; }
.migas__actual { color: var(--tinta); }
@media (hover: hover) and (pointer: fine) { .migas a:hover { color: var(--tinta); } }

/* También te puede gustar: fila que se desliza, tarjetas como el catálogo. */
.relacionados {
  padding: clamp(2rem, 5vw, 3.5rem) var(--margen);
  border-top: 1px solid var(--linea);
  margin-top: clamp(2rem, 4vw, 3rem);
}
.relacionados__titulo {
  font-family: var(--serif);
  font-size: clamp(1.1rem, 3vw, 1.5rem);
  margin-bottom: 1.25rem;
}
.relacionados__fila {
  display: flex; gap: 0.7rem;
  overflow-x: auto; scrollbar-width: none;
  scroll-snap-type: x proximity;
}
.relacionados__fila::-webkit-scrollbar { display: none; }
.rel-card { flex: 0 0 auto; width: clamp(142px, 42vw, 185px); scroll-snap-align: start; }
.rel-card__marco {
  position: relative; aspect-ratio: 2 / 3;
  background: var(--lienzo); overflow: hidden;
  margin-bottom: 0.5rem;
}
.rel-card__nombre { font-size: 12px; line-height: 1.3; margin-bottom: 0.15rem; }
.rel-card__precio { font-size: 12px; color: var(--precio); }

.confianza__item { display: flex; gap: 0.6rem; align-items: flex-start; }
.confianza__icono {
  flex: none;
  width: 15px;
  height: 15px;
  margin-top: 2px;
  stroke: var(--tinta);
  stroke-width: 1.5;
  fill: none;
}
.confianza__titulo {
  font-size: 11px;
  font-weight: 500;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  margin-bottom: 0.1rem;
}
.confianza__texto { font-size: 11px; color: var(--gris); line-height: 1.5; }

/* ── Acordeón ─────────────────────────────────────────────────────────────── */
.acordeon { border-top: 1px solid var(--linea); margin-top: 1.5rem; }
.acordeon__item { border-bottom: 1px solid var(--linea); }

.acordeon__boton {
  display: flex;
  align-items: center;
  justify-content: space-between;
  width: 100%;
  padding: 0.95rem 0;
  text-align: left;
  font-size: 11px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
}

.acordeon__signo { position: relative; width: 9px; height: 9px; flex: none; }
.acordeon__signo::before,
.acordeon__signo::after {
  content: "";
  position: absolute;
  background: var(--tinta);
  transition: transform var(--medio) var(--ease-out);
}
.acordeon__signo::before { top: 4px; left: 0; width: 9px; height: 1px; }
.acordeon__signo::after  { left: 4px; top: 0; width: 1px; height: 9px; }
/* El "+" se vuelve "−" encogiendo la barra. Es transform: se puede interrumpir
   a mitad si la clienta cierra antes de que termine. */
.acordeon__boton[aria-expanded="true"] .acordeon__signo::after { transform: scaleY(0); }

.acordeon__cuerpo {
  display: grid;
  grid-template-rows: 0fr;
  transition: grid-template-rows var(--medio) var(--ease-out);
}
.acordeon__cuerpo > div { overflow: hidden; }
.acordeon__item.abierto .acordeon__cuerpo { grid-template-rows: 1fr; }

.acordeon__texto {
  color: var(--gris);
  padding-bottom: 1.1rem;
  white-space: pre-line;
  max-width: 62ch;
  font-size: 12px;
  line-height: 1.6;
}

/* ── Barra de compra pegada (móvil) ───────────────────────────────────────────
   El 73% del tráfico es móvil. Aparece solo cuando el botón de verdad ya salió
   de vista: sacarla antes le taparía la foto justo cuando la mira.
   -------------------------------------------------------------------------- */
.barra-compra {
  position: fixed;
  left: 0;
  right: 0;
  bottom: 0;
  z-index: var(--z-nota);
  display: none;
  align-items: center;
  gap: 0.75rem;
  padding: 0.6rem var(--margen);
  padding-bottom: max(0.6rem, env(safe-area-inset-bottom));
  background: var(--blanco);
  border-top: 1px solid var(--linea);
  transform: translateY(105%);
  transition: transform var(--medio) var(--ease-out);
}
.barra-compra.visible { transform: none; }

.barra-compra__info { flex: 1; min-width: 0; }
.barra-compra__nombre {
  font-size: 11px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.barra-compra__linea {
  font-size: 11px;
  color: var(--gris);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.barra-compra .boton-wa { width: auto; padding: 0.75rem 1.25rem; flex: none; }

@media (max-width: 900px) { .barra-compra { display: flex; } }

/* ── También te puede gustar ──────────────────────────────────────────────── */
.tambien { margin-top: clamp(2.5rem, 5vw, 4rem); }
.tambien__titulo {
  font-size: 13px;
  font-weight: 500;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  padding-inline: var(--margen);
  margin-bottom: 1.25rem;
}

/* ── Pie ──────────────────────────────────────────────────────────────────── */
.pie {
  margin-top: clamp(3rem, 6vw, 5rem);
  padding: clamp(2.5rem, 4vw, 3.5rem) 0;
  border-top: 1px solid var(--linea);
}

.pie__rejilla {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
  gap: 2rem;
}

.pie__titulo {
  font-size: 11px;
  font-weight: 500;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  margin-bottom: 0.5rem;
}
.pie__nota { font-size: 12px; color: var(--gris); }

.pie__legal {
  font-size: 10px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--tenue);
  margin-top: 2.5rem;
  padding-top: 1.25rem;
  border-top: 1px solid var(--linea);
}

@media (max-width: 900px) { .pie { padding-bottom: 5rem; } }

/* ── Paginación ───────────────────────────────────────────────────────────────
   Aire ARRIBA y nada más: el muro de fotos termina, respira, y aparece la
   salida. Sin caja, sin borde, sin fondo — el botón ya es `.cta-hueco` y esta
   tienda agrupa con aire, no con recuadros.
   -------------------------------------------------------------------------- */
.paginacion {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 0.85rem;
  padding-block: clamp(2rem, 5vw, 3.5rem) 0;
}
.paginacion:empty { display: none; }   /* sin nada que decir, no ocupa

   `:empty` y no `hidden`: la caja se pinta siempre (el JS le mete o le quita
   contenido), así que sin esto dejaría un hueco de padding cuando está vacía. */

.paginacion__cuenta {
  font-size: 11px;
  letter-spacing: 0.04em;
  color: var(--gris);
}

/* ── Vacío y carga ────────────────────────────────────────────────────────── */
.vacio {
  text-align: center;
  padding: clamp(3rem, 8vw, 6rem) var(--margen);
  color: var(--gris);
  font-size: 12px;
}
.vacio__titulo {
  font-size: 13px;
  font-weight: 500;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--tinta);
  margin-bottom: 0.5rem;
}
/* Un vacío SIN salida deja a la clienta encerrada mirando una página que no le
   dice qué hacer. El subrayado se queda: es un enlace dentro de un párrafo y
   sin él no se ve que se puede pulsar. */
.vacio__enlace {
  color: var(--tinta);
  text-decoration: underline;
  text-underline-offset: 3px;
}

.esqueleto {
  background: var(--lienzo);
  animation: respirar 2s linear infinite;
}
@keyframes respirar {
  0%, 100% { opacity: 1; }
  50%      { opacity: 0.5; }
}

/* ── Revelado ─────────────────────────────────────────────────────────────────
   ⚠️ NUNCA `opacity: 0` de base. Fue un bug real: la página salía EN BLANCO si
   la animación no llegaba a correr (pestaña en segundo plano, el móvil pausando
   al cambiar de app). `both` aplica el `from` durante el retardo y el `to` al
   terminar; si no corre nada, el elemento se queda VISIBLE.
   El contenido jamás depende de que una animación se ejecute.
   -------------------------------------------------------------------------- */
.revelar {
  animation: subir 300ms var(--ease-out) both;
  animation-delay: calc(var(--i, 0) * 40ms);
}
@keyframes subir {
  from { opacity: 0; transform: translateY(8px); }
  to   { opacity: 1; transform: none; }
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
  .color:hover, .color:active, .talla:active, .boton-wa:active,
  .filtro:active, .cta-hueco:active, .ver-guia:active { transform: none; }
}

/* ════════════════════════════════════════════════════════════════════════════
   EL PEDIDO
   ══════════════════════════════════════════════════════════════════════════ */

/* ── La bolsa en la cabecera ──────────────────────────────────────────────── */
/* `min-width:0` deja que las acciones (con el menú dentro) se encojan; los iconos
   van `flex:0 0 auto` para que NUNCA se corten ni se los empuje: el menú se
   desliza, los iconos se quedan fijos a la derecha. */
.cabecera__acciones { display: flex; align-items: center; gap: 1rem; min-width: 0; }
.cabecera .favs, .cabecera .bolsa { flex: 0 0 auto; }

.bolsa {
  position: relative;
  display: flex;
  align-items: center;
  transition: transform var(--pulso) var(--ease-out);
}
.bolsa:active { transform: scale(0.94); }
.bolsa__icono { width: 19px; height: 21px; fill: none; stroke: var(--tinta); stroke-width: 1.4; }

/* El contador: negro macizo, diminuto. Tiene que verse sin gritar. */
.bolsa__cuenta {
  position: absolute;
  top: -5px;
  right: -7px;
  min-width: 15px;
  height: 15px;
  padding: 0 3px;
  border-radius: 99px;
  background: var(--negro);
  color: var(--blanco);
  font-size: 9px;
  font-weight: 600;
  line-height: 15px;
  text-align: center;
}

/* ── Aviso al añadir ──────────────────────────────────────────────────────────
   Entra desde abajo y se va sola. Si no confirmara nada, la clienta pulsa dos
   veces "añadir" pensando que no funcionó — y pide dos.
   -------------------------------------------------------------------------- */
.avisado {
  position: fixed;
  left: 50%;
  bottom: 1.25rem;
  z-index: var(--z-nota);
  display: flex;
  align-items: center;
  gap: 0.85rem;
  max-width: calc(100vw - 1.5rem);
  padding: 0.7rem 0.7rem 0.7rem 1rem;
  background: var(--negro);
  color: var(--blanco);
  transform: translate(-50%, calc(100% + 2rem));
  opacity: 0;
  transition: transform var(--medio) var(--ease-out), opacity var(--medio) var(--ease-out);
}
.avisado.visible { transform: translate(-50%, 0); opacity: 1; }
.avisado__texto {
  font-size: 11px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.avisado__ir {
  flex: none;
  padding: 0.45rem 0.8rem;
  background: var(--blanco);
  color: var(--negro);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  transition: transform var(--pulso) var(--ease-out);
}
.avisado__ir:active { transform: scale(0.96); }

/* En móvil la barra de compra ya ocupa el borde inferior: el aviso sube. */
@media (max-width: 900px) { .avisado { bottom: 4.5rem; } }

/* ── Página del pedido ────────────────────────────────────────────────────── */
.pedido {
  display: grid;
  grid-template-columns: 1.6fr 1fr;
  gap: clamp(1.5rem, 4vw, 3.5rem);
  align-items: start;
  padding-block: clamp(1.5rem, 3vw, 2.5rem);
}
@media (max-width: 860px) { .pedido { grid-template-columns: 1fr; gap: 2rem; } }

.linea {
  display: grid;
  grid-template-columns: 72px 1fr auto;
  gap: 1rem;
  padding: 1.1rem 0;
  border-bottom: 1px solid var(--linea);
}
.linea:first-child { border-top: 1px solid var(--linea); }

.linea__foto {
  width: 72px;
  aspect-ratio: 3/4;
  object-fit: contain;
  background: var(--lienzo);
}
.linea__nombre {
  font-size: 12px;
  letter-spacing: 0.02em;
  text-transform: uppercase;
  margin-bottom: 0.2rem;
}
.linea__detalle { font-size: 11px; color: var(--gris); margin-bottom: 0.5rem; }
.linea__precio { font-size: 12px; color: var(--precio); }
.linea__lado { display: flex; flex-direction: column; align-items: flex-end; justify-content: space-between; gap: 0.5rem; }

/* Cantidad: sin caja, tres piezas de texto. Un stepper dibujado pesaría más
   que el nombre de la prenda. */
.cantidad { display: flex; align-items: center; gap: 0.35rem; }

/* 44x44 también. Y con esto, "+" y "Quitar" dejan de estar a 8px: tocar "+" y
   que desaparezca la prenda —sin deshacer— es de las peores cosas que le pueden
   pasar a una clienta a punto de comprar. */
.cantidad__btn {
  min-width: 44px;
  min-height: 44px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 14px;
  line-height: 1;
  color: var(--tinta);
  transition: opacity var(--rapido) ease, transform var(--pulso) var(--ease-out);
}
.cantidad__btn:active { transform: scale(0.9); }
.cantidad__btn:disabled { color: var(--tenue); cursor: not-allowed; }
.cantidad__n { font-size: 12px; min-width: 14px; text-align: center; }

.linea__quitar {
  font-size: 10px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--gris);
  border-bottom: 1px solid var(--linea);
  padding-bottom: 1px;
  transition: color var(--rapido) ease, border-color var(--rapido) ease;
}
@media (hover: hover) and (pointer: fine) {
  .linea__quitar:hover { color: var(--rebaja); border-color: var(--rebaja); }
}

/* ── Resumen ──────────────────────────────────────────────────────────────── */
.resumen { position: sticky; top: 90px; }
@media (max-width: 860px) { .resumen { position: static; } }

.resumen__caja { border: 1px solid var(--linea); padding: 1.25rem; }

.resumen__fila {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  font-size: 12px;
  padding-block: 0.35rem;
}
.resumen__total {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  font-size: 15px;
  font-weight: 600;
  padding-top: 0.85rem;
  margin-top: 0.6rem;
  border-top: 1px solid var(--linea);
}
.resumen__nota {
  font-size: 10px;
  letter-spacing: 0.03em;
  text-transform: uppercase;
  color: var(--gris);
  margin-top: 0.75rem;
  text-align: center;
}
.resumen .boton-wa { margin-top: 1.1rem; }

@media (prefers-reduced-motion: reduce) {
  .avisado { transition-duration: 0.01ms !important; }
  .bolsa:active, .avisado__ir:active, .cantidad__btn:active { transform: none; }
}

/* ════════════════════════════════════════════════════════════════════════════
   BUSCAR Y FILTRAR
   ════════════════════════════════════════════════════════════════════════════
   Con 6 prendas no hace falta. Con 60 —y la dueña llegará a 60— sin esto la
   clienta se pierde y se va. Se construye ahora para que exista cuando haga
   falta, no cuando ya duela.
   ══════════════════════════════════════════════════════════════════════════ */

.barra-buscar {
  display: flex;
  align-items: center;
  gap: 0.6rem;
  padding: 0.55rem 0;
  border-bottom: 1px solid var(--negro);
  margin-bottom: 1.5rem;
}
.barra-buscar__lupa { width: 15px; height: 15px; flex: none; stroke: var(--gris); stroke-width: 1.6; fill: none; }

/* Sin caja ni fondo: solo un filete. Una caja de búsqueda dibujada pesaría
   más que las prendas, y aquí manda la ropa. */
.buscar {
  flex: 1;
  min-width: 0;
  border: 0;
  background: none;
  font: inherit;
  /* 16px OBLIGATORIO. Con menos, Safari en iPhone hace zoom automático al
     tocar el campo y deja el catálogo descuadrado: la clienta escribe una letra
     y de repente está mirando la página al 150%, sin saber cómo volver.
     Es la regla de iOS y no hay forma de desactivarla sin romper el pellizco
     para hacer zoom, que sí hace falta para ver la tela de cerca. */
  font-size: 16px;
  color: var(--tinta);
  padding: 0.2rem 0;
}
.buscar::placeholder { color: var(--tenue); }
.buscar:focus { outline: none; }

.buscar__limpiar {
  flex: none;
  font-size: 16px;
  line-height: 1;
  color: var(--gris);
  padding: 0 0.2rem;
  transition: color var(--rapido) ease, transform var(--pulso) var(--ease-out);
}
.buscar__limpiar:active { transform: scale(0.9); }
@media (hover: hover) and (pointer: fine) { .buscar__limpiar:hover { color: var(--tinta); } }

/* ── Fila de controles ────────────────────────────────────────────────────── */
.controles {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  flex-wrap: wrap;
  margin-bottom: 1.25rem;
}

.afinar {
  display: flex;
  align-items: center;
  gap: 1.25rem;
  flex-wrap: wrap;
}

.afinar__btn {
  display: inline-flex;
  align-items: center;
  gap: 0.35rem;
  font-size: 11px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--tinta);
  padding-bottom: 3px;
  border-bottom: 1px solid transparent;
  transition: border-color var(--rapido) ease, transform var(--pulso) var(--ease-out);
}
.afinar__btn:active { transform: scale(0.97); }
.afinar__btn[aria-expanded="true"] { border-bottom-color: var(--negro); }
/* El puntito avisa de que hay filtros puestos aunque el panel esté cerrado.
   Sin él, la clienta ve "3 prendas" y cree que la tienda está vacía. */
.afinar__punto {
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--rebaja);
}

.orden {
  font: inherit;
  font-size: 11px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--tinta);
  background: none;
  border: 0;
  border-bottom: 1px solid var(--linea);
  padding: 0.2rem 0;
  cursor: pointer;
}
.orden:focus-visible { outline: 2px solid var(--negro); outline-offset: 2px; }

/* ── Panel de filtros ─────────────────────────────────────────────────────── */
.panel-filtros {
  display: grid;
  grid-template-rows: 0fr;
  transition: grid-template-rows var(--medio) var(--ease-out);
}
.panel-filtros > div { overflow: hidden; }
.panel-filtros.abierto { grid-template-rows: 1fr; }

.panel-filtros__caja {
  display: flex;
  flex-wrap: wrap;
  gap: 1.75rem;
  padding: 1.25rem 0 1.5rem;
  border-bottom: 1px solid var(--linea);
  margin-bottom: 1.5rem;
}

.grupo-filtro__titulo {
  font-size: 10px;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--gris);
  margin-bottom: 0.6rem;
}

.opciones { display: flex; flex-wrap: wrap; gap: 0.6rem; }

.opcion {
  font-size: 11px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--gris);
  padding-bottom: 2px;
  border-bottom: 1px solid transparent;
  transition: color var(--rapido) ease,
              border-color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
.opcion:active { transform: scale(0.95); }
.opcion[aria-pressed="true"] { color: var(--tinta); border-bottom-color: var(--negro); font-weight: 600; }
@media (hover: hover) and (pointer: fine) { .opcion:hover { color: var(--tinta); } }

/* Los colores se eligen por la muestra, no por el nombre: "Arena" no le dice
   nada a nadie hasta que lo ve. */
.opcion-color {
  position: relative;
  width: 22px;
  height: 22px;
  border-radius: 50%;
  border: 1px solid var(--linea);
  transition: transform var(--pulso) var(--ease-out);
}
.opcion-color::after {
  content: "";
  position: absolute;
  inset: -4px;
  border-radius: 50%;
  border: 1px solid transparent;
  transition: border-color var(--rapido) ease;
}
.opcion-color[aria-pressed="true"]::after { border-color: var(--negro); }
.opcion-color:active { transform: scale(0.92); }
@media (hover: hover) and (pointer: fine) { .opcion-color:hover { transform: scale(1.1); } }

/* Casilla sin caja: texto con un filete cuando está puesta */
.opcion-si {
  font-size: 11px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--gris);
  padding-bottom: 2px;
  border-bottom: 1px solid transparent;
  transition: color var(--rapido) ease, border-color var(--rapido) ease;
}
.opcion-si[aria-pressed="true"] { color: var(--tinta); border-bottom-color: var(--negro); }

.limpiar-todo {
  font-size: 10px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--rebaja);
  border-bottom: 1px solid currentColor;
  padding-bottom: 1px;
  align-self: flex-end;
}

@media (prefers-reduced-motion: reduce) {
  .opcion:active, .opcion-color:active, .opcion-color:hover,
  .afinar__btn:active, .buscar__limpiar:active { transform: none; }
}

/* ════════════════════════════════════════════════════════════════════════════
   PROMOCIONES
   ════════════════════════════════════════════════════════════════════════════
   El look es Zara; la maquinaria de ventas, de Shein. No se contradicen: Zara
   también pone -30% en rojo en rebajas. La regla se mantiene — el rojo es el
   ÚNICO color, y por eso cuando aparece, se ve.
   ══════════════════════════════════════════════════════════════════════════ */

/* ── Sellos ───────────────────────────────────────────────────────────────── */
/* El % es más fuerte que "Oferta": "-31%" es un número que se compara solo.
   "Oferta" no dice cuánto y no mueve a nadie. */
.prenda__sello--pct  { color: var(--rebaja); font-weight: 700; }
.prenda__sello--nuevo { color: var(--tinta); }

.panel__pct {
  font-size: 12px;
  font-weight: 700;
  letter-spacing: 0.04em;
  color: var(--rebaja);
}

/* ── Barra de envío gratis ────────────────────────────────────────────────────
   La palanca más barata para subir el ticket: "te faltan $12" hace que meta
   otra prenda. Solo sale si el dueño puso un mínimo en config.
   -------------------------------------------------------------------------- */
.envio-gratis {
  padding: 0.85rem 0;
  border-bottom: 1px solid var(--linea);
  margin-bottom: 1.25rem;
}
.envio-gratis__texto {
  font-size: 11px;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  margin-bottom: 0.5rem;
}
.envio-gratis__falta { color: var(--rebaja); font-weight: 600; }
.envio-gratis__logrado { font-weight: 600; }

.envio-gratis__pista {
  height: 2px;
  background: var(--linea);
  overflow: hidden;
}
.envio-gratis__avance {
  height: 100%;
  background: var(--negro);
  transform-origin: left;
  transform: scaleX(var(--avance, 0));
  transition: transform 250ms var(--ease-out);
}

/* ── Cupón ────────────────────────────────────────────────────────────────── */
.cupon { margin-top: 1rem; padding-top: 1rem; border-top: 1px solid var(--linea); }

.cupon__fila { display: flex; gap: 0.5rem; }

.cupon__campo {
  flex: 1;
  min-width: 0;
  border: 1px solid var(--linea);
  background: none;
  font: inherit;
  font-size: 12px;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--tinta);
  padding: 0.6rem 0.7rem;
}
.cupon__campo::placeholder { color: var(--tenue); letter-spacing: 0.04em; }
.cupon__campo:focus { outline: none; border-color: var(--negro); }

.cupon__btn {
  flex: none;
  padding: 0.6rem 0.9rem;
  border: 1px solid var(--negro);
  background: var(--blanco);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  transition: background-color var(--rapido) ease,
              color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
.cupon__btn:active { transform: scale(0.96); }
.cupon__btn:disabled { opacity: 0.4; cursor: not-allowed; }
@media (hover: hover) and (pointer: fine) {
  .cupon__btn:hover:not(:disabled) { background: var(--negro); color: var(--blanco); }
}

.cupon__mensaje { font-size: 11px; margin-top: 0.5rem; min-height: 1.2em; }
.cupon__mensaje--mal { color: var(--rebaja); }

.cupon__puesto {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 0.75rem;
  padding: 0.6rem 0.7rem;
  border: 1px solid var(--negro);
}
.cupon__codigo { font-size: 12px; font-weight: 600; letter-spacing: 0.08em; }
.cupon__quitar {
  font-size: 10px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--gris);
  border-bottom: 1px solid var(--linea);
}
@media (hover: hover) and (pointer: fine) {
  .cupon__quitar:hover { color: var(--rebaja); border-color: var(--rebaja); }
}

.resumen__fila--descuento { color: var(--rebaja); font-weight: 600; }

@media (prefers-reduced-motion: reduce) {
  .envio-gratis__avance { transition-duration: 0.01ms !important; }
  .cupon__btn:active { transform: none; }
}

/* ── Favoritos y compartir ───────────────────────────────────────────────── */

.corazon {
  display: flex;
  align-items: center;
  transition: transform var(--pulso) var(--ease-out);
}
.corazon:active { transform: scale(0.88); }
.corazon__icono {
  width: 19px;
  height: 18px;
  stroke: var(--tinta);
  stroke-width: 1.4;
  fill: none;
  transition: fill var(--rapido) ease, stroke var(--rapido) ease;
}
/* Relleno = guardado. El rojo aquí es el mismo de las rebajas: el ÚNICO color
   del sitio, y por eso los dos momentos en que aparece se sienten. */
.corazon__icono[data-lleno="true"] { fill: var(--rebaja); stroke: var(--rebaja); }

.favs__cuenta {
  position: absolute;
  top: -5px;
  right: -7px;
  min-width: 15px;
  height: 15px;
  padding: 0 3px;
  border-radius: 99px;
  background: var(--negro);
  color: var(--blanco);
  font-size: 9px;
  font-weight: 600;
  line-height: 15px;
  text-align: center;
}
.favs { position: relative; }

/* El corazón sobre la foto del catálogo. Sin fondo: una cajita blanca encima de
   la prenda sería lo primero que se ve, y lo primero tiene que ser la ropa. */
.prenda__corazon {
  position: absolute;
  top: 0.5rem;
  right: 0.5rem;
  z-index: 3;
  padding: 0.35rem;
  transition: transform var(--pulso) var(--ease-out);
}
.prenda__corazon:active { transform: scale(0.85); }
.prenda__corazon .corazon__icono {
  width: 17px;
  height: 16px;
  /* Sombra fina: la foto puede ser clara u oscura y no se sabe cuál subirá. */
  filter: drop-shadow(0 0 2px rgba(255,255,255,0.9));
}

/* Latido al guardar: confirma sin robar la atención. Corre una vez. */
@keyframes latir {
  0%, 100% { transform: scale(1); }
  35%      { transform: scale(1.28); }
  70%      { transform: scale(0.94); }
}
.corazon__icono.late { animation: latir 340ms var(--ease-out); }

/* ── Acciones de la ficha ─────────────────────────────────────────────────── */
.acciones-ficha {
  display: flex;
  gap: 1.5rem;
  margin-top: 0.9rem;
}

.accion {
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  font-size: 11px;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--gris);
  padding-bottom: 2px;
  border-bottom: 1px solid transparent;
  transition: color var(--rapido) ease,
              border-color var(--rapido) ease,
              transform var(--pulso) var(--ease-out);
}
.accion:active { transform: scale(0.97); }
.accion svg { width: 14px; height: 14px; stroke: currentColor; stroke-width: 1.5; fill: none; }
.accion .corazon__icono { stroke: currentColor; }
.accion .corazon__icono[data-lleno="true"] { fill: var(--rebaja); stroke: var(--rebaja); }
@media (hover: hover) and (pointer: fine) {
  .accion:hover { color: var(--tinta); border-color: var(--negro); }
}

@media (prefers-reduced-motion: reduce) {
  .corazon:active, .prenda__corazon:active, .accion:active { transform: none; }
  .corazon__icono.late { animation: none; }
}

/* ── Precio en Bolívares ──────────────────────────────────────────────────────
   Debajo del de $ y más discreto: el $ es el precio de referencia, el Bs es lo
   que va a pagar. Los dos hacen falta — uno para comparar, otro para decidir.
   -------------------------------------------------------------------------- */
.precio-bs {
  font-size: 11px;
  color: var(--gris);
  margin-top: 0.15rem;
}

.panel__bs {
  font-size: 13px;
  color: var(--gris);
  margin-top: -1.4rem;
  margin-bottom: 1.75rem;
}

.nota-tasa {
  font-size: 10px;
  letter-spacing: 0.03em;
  text-transform: uppercase;
  color: var(--tenue);
  margin-top: 0.2rem;
}

.resumen__bs {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  font-size: 12px;
  color: var(--gris);
  padding-top: 0.35rem;
}

/* ── Urgencia: el contador de SHEIN ──────────────────────────────────────────
   Fino, rojo, con el reloj en negrita. Es lo único que se mueve en la ficha —
   y por eso el ojo va ahí. El rojo es el mismo de las rebajas: coherente.
   -------------------------------------------------------------------------- */
.urgencia {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  margin: -0.75rem 0 1.75rem;
  padding: 0.5rem 0.7rem;
  background: #FBEEEC;
  color: var(--rebaja);
  font-size: 12px;
  letter-spacing: 0.02em;
}
.urgencia svg {
  width: 14px;
  height: 14px;
  flex: none;
  stroke: var(--rebaja);
  stroke-width: 1.4;
  fill: none;
}
.urgencia strong {
  font-weight: 700;
  font-variant-numeric: tabular-nums;   /* que no baile de ancho al contar */
  letter-spacing: 0.04em;
}
