/* =========================================================
   SECCIONES.CSS — Capa base COMPARTIDA de secciones aditivas + saludo.
   SPEC 0006. Transversal (como motor.js): NO se versiona.

   Qué estiliza:
     (a) Las fichas de sección DINÁMICA `.ti-sec` (las genera el motor desde el
         manifiesto), dirigidas por tokens `--sec-*` que cada plantilla define en
         su :root, CON fallbacks AA por si una plantilla aún no los define.
     (b) El `.saludo` del invitado — SOLO como FALLBACK: las 7 plantillas con
         `.saludo` nativo (editorial, botanico, acuarela, mariposas, luz-celestial,
         logro, liga-heroes) GANAN por cascada porque su hoja se enlaza DESPUÉS de
         esta (ver class-ti-render: secciones.css va ANTES de la hoja de plantilla).
         Las 8 sin `.saludo` propio toman este estilo, legible por --sec-acento-*.
     (c) El pulso `.musica--invita` "toca para sonar" (guard prefers-reduced-motion).

   Contrato de tokens (§4.3), consumidos SIEMPRE con fallback var(--sec-x, <AA>):
     --sec-bg            fondo del recuadro de ficha
     --sec-borde         borde/hairline de la ficha
     --sec-radio         radio de esquinas
     --sec-titulo-font   tipografía del título de sección/saludo
     --sec-titulo-color  color del título (AA sobre --sec-bg)
     --sec-texto-color   color del cuerpo (AA sobre --sec-bg)
     --sec-acento        acento (enlaces, filetes)
     --sec-acento-bg     fondo del recuadro de saludo
     --sec-acento-tinta  texto sobre --sec-acento-bg (AA)
     --sec-acento-boton-bg / --sec-acento-boton-tinta  botón "Ver mi pase"

   Esta hoja NO declara --sec-* en :root: solo los consume (los declara la
   plantilla; el último :root gana por var(), independiente del orden de hojas).
   ========================================================= */

[hidden] { display: none !important; }

/* =========================================================
   Sección dinámica estándar (.ti-sec) — mobile-first, BEM
   ========================================================= */
.ti-sec {
  max-width: var(--ancho, 620px);
  margin: 40px auto;
  padding: 40px 24px;
  background: var(--sec-bg, #f7f5f2);
  color: var(--sec-texto-color, #2a2a2a);
  border: 1px solid var(--sec-borde, rgba(0, 0, 0, .14));
  border-radius: var(--sec-radio, 14px);
  text-align: center;
}

.ti-sec__titulo {
  margin: 0 0 14px;
  font-family: var(--sec-titulo-font, inherit);
  font-size: clamp(1.4rem, 5vw, 2rem);
  line-height: 1.15;
  color: var(--sec-titulo-color, #1a1a1a);
}

.ti-sec__cuerpo { color: var(--sec-texto-color, #2a2a2a); }

.ti-sec__texto {
  margin: 0 auto;
  max-width: 46ch;
  font-size: 1.02rem;
  line-height: 1.7;
}

/* Sub-elementos para renderers futuros (lista/enlaces/colores — roadmap 0006 §6) */
.ti-sec__lista {
  list-style: none;
  margin: 0;
  padding: 0;
}
.ti-sec__lista li { padding: 6px 0; }

.ti-sec__enlaces {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  justify-content: center;
}
.ti-sec__enlaces a {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: 44px;
  padding: 10px 18px;
  border-radius: 999px;
  font-weight: 600;
  text-decoration: none;
  background: var(--sec-acento, #333);
  color: var(--sec-acento-boton-tinta, #fff);
}

.ti-sec__colores {
  display: flex;
  flex-wrap: wrap;
  gap: 10px;
  justify-content: center;
}
.ti-sec__color {
  width: 34px;
  height: 34px;
  border-radius: 50%;
  border: 1px solid rgba(0, 0, 0, .18);
}

/* =========================================================
   Saludo del invitado — SOLO FALLBACK
   Las 7 plantillas con .saludo nativo prevalecen (cargan después).
   ========================================================= */
.saludo {
  text-align: center;
  padding: 40px 24px;
  background: var(--sec-acento-bg, #2b2b2b);
  color: var(--sec-acento-tinta, #ffffff);
}
.saludo__hola {
  font-family: var(--sec-titulo-font, inherit);
  font-size: clamp(1.6rem, 6vw, 2.3rem);
  line-height: 1.15;
  color: var(--sec-acento-tinta, #ffffff);
}
.saludo__pases {
  margin-top: 6px;
  letter-spacing: .04em;
  opacity: .92;
}

/* =========================================================
   Foto del festejado DENTRO del sello/medallón del hero (capa compartida)
   ---------------------------------------------------------
   El motor inyecta <img class="hero__sello-foto"> dentro de cualquier sello
   ([data-rol="hero-sello"]) cuando hay CFG.fotos.hero. La foto se RECORTA a la
   forma del sello (círculo/cuadro) heredando su radio, sin importar la plantilla.
   Cada plantilla ya da tamaño y forma a su sello; el bloque :has() de abajo es
   solo una red de seguridad por si alguno no trajera dimensiones.
   ========================================================= */
.hero__sello-foto {
  width: 100%;
  height: 100%;
  object-fit: cover;
  border-radius: inherit;
  display: block;
}
/* Salvaguarda: si algún sello no define tamaño propio, la foto no colapsa. */
[data-rol="hero-sello"]:has(.hero__sello-foto) {
  min-width: 64px;
  min-height: 64px;
}

/* =========================================================
   Pulso "toca para sonar" del botón de música (SPEC 0007 pendiente)
   El motor añade .musica--invita a #musica cuando autoGesto está activo.
   Especificidad .musica.musica--invita para ganar sin depender del orden.
   ========================================================= */
@media (prefers-reduced-motion: no-preference) {
  .musica.musica--invita {
    animation: ti-musica-pulso 2.4s ease-in-out infinite;
  }
  @keyframes ti-musica-pulso {
    0%, 100% { box-shadow: 0 0 0 0 rgba(0, 0, 0, .30); }
    50%      { box-shadow: 0 0 0 12px rgba(0, 0, 0, 0); }
  }
}

/* =========================================================
   PORTADA DE APERTURA "toca para abrir" (SPEC 0008)
   ---------------------------------------------------------
   Capa a pantalla completa que CUBRE la invitación al cargar y se ABRE al tocar
   (arranca la música y revela). La CREA motor.js (initPortada); aquí va el
   ANDAMIAJE compartido (estructura + animación por defecto + fallbacks AA),
   dirigido por tokens --portada-* que cada plantilla define en su :root. Cada
   plantilla puede SOBRESCRIBIR .ti-portada/.ti-portada__lienzo en su hoja (que
   carga DESPUÉS de esta → gana por cascada, sin !important). Transversal, NO
   versionada (como .ti-sec* y el pulso .musica--invita).

   Contrato de tokens (§4.3), consumidos con fallback var(--portada-x, <AA>):
     --portada-bg          fondo de la capa de apertura
     --portada-tinta       color de nombres/fecha/mensaje (AA sobre --portada-bg)
     --portada-acento      acento (filetes, sello)
     --portada-titulo-font tipografía de nombres/título
     --portada-radio       radio del panel/sobre
     --portada-cta-bg      fondo del botón "abrir"
     --portada-cta-tinta   texto del botón (AA sobre --portada-cta-bg)
   ========================================================= */
.ti-portada {
  position: fixed;
  inset: 0;
  z-index: 9999;                 /* por encima de música (40) y lightbox (50). */
  display: flex;
  align-items: center;
  justify-content: center;
  min-height: 100svh;            /* svh: sin saltos por las barras del móvil. */
  padding: 32px 22px;
  text-align: center;
  background: var(--portada-bg, #1a1a2e);
  color: var(--portada-tinta, #ffffff);
  overflow: hidden;
  transition: opacity .5s ease;
  -webkit-tap-highlight-color: transparent;
  cursor: pointer;
}
/* [hidden] ya lo cubre la regla global de arriba (display:none !important). */

.ti-portada__lienzo {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 14px;
  max-width: 560px;
  width: 100%;
  min-width: 0;                  /* flex item: permite encoger bajo su contenido para
                                    que el título envuelva en vez de expandir la capa. */
  box-sizing: border-box;
  will-change: transform, opacity;
  transition: transform .55s ease, opacity .55s ease;
}

/* Decorativos (masthead "edición especial", emblema): solo los muestra/coloca la
   plantilla (p. ej. con ::before). En el fallback base no se ven. */
.ti-portada__masthead,
.ti-portada__emblema {
  display: none;
}

/* Título de ESTADO ("¡Estás invitado!" / "¡Tienes una invitación!"): secundario. */
.ti-portada__titulo {
  margin: 0;
  /* Límite ABSOLUTO al viewport (no depende del flex, que no encogía en móvil):
     garantiza que el texto largo ENVUELVA en vez de cortarse por el borde. */
  width: 100%;
  max-width: min(calc(100vw - 2.75rem), 18ch);   /* el tope en ch fuerza el salto
                                    de línea del texto largo de forma robusta,
                                    independiente del viewport/flex. */
  overflow-wrap: break-word;
  font-family: var(--portada-titulo-font, inherit);
  font-size: clamp(1.4rem, 6vw, 2.1rem);
  line-height: 1.1;
  text-wrap: balance;
  color: var(--portada-tinta, #ffffff);
}

/* Destinatario "PARA: <nombre>" — el nombre es el PROTAGONISTA de la portada.
   Llega async (initInvitado): el <p> arranca [hidden]; al resolver, motor.js lo
   muestra y añade .ti-portada--personalizada para el fade-in. */
.ti-portada__invitado {
  margin: 0;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 4px;
  opacity: 0;
  transition: opacity .45s ease;
}
.ti-portada--personalizada .ti-portada__invitado { opacity: 1; }
.ti-portada__para {
  font-size: clamp(.78rem, 3.2vw, .98rem);
  letter-spacing: .18em;
  text-transform: uppercase;
  opacity: .85;
}
.ti-portada__nombre {
  font-family: var(--portada-titulo-font, inherit);
  font-size: clamp(2.3rem, 12vw, 4.2rem);
  line-height: 1.02;
  color: var(--portada-tinta, #ffffff);
}

.ti-portada__mensaje {
  margin: 0;
  max-width: 40ch;
  font-size: 1.02rem;
  line-height: 1.55;
  color: var(--portada-tinta, #ffffff);
  opacity: .9;
}

.ti-portada__cta {
  margin-top: 10px;
  min-height: 44px;
  min-width: 44px;
  padding: 12px 30px;
  font: inherit;
  font-weight: 700;
  font-size: 1.1rem;
  letter-spacing: .02em;
  color: var(--portada-cta-tinta, #1a1a2e);
  background: var(--portada-cta-bg, #ffffff);
  border: 0;
  border-radius: var(--portada-radio, 999px);
  cursor: pointer;
}
.ti-portada__cta:focus-visible {
  outline: 3px solid var(--portada-cta-tinta, #1a1a2e);
  outline-offset: 3px;
}

/* Estado de apertura (lo añade motor.js): la capa se desvanece y el lienzo sube
   ligeramente. SOLO opacity/transform en la PROPIA capa (nunca sobre el hero). */
.ti-portada--abriendo { opacity: 0; }
.ti-portada--abriendo .ti-portada__lienzo {
  transform: translateY(-18px) scale(1.03);
  opacity: 0;
}

/* Pulso invitador del CTA — mismo lenguaje que .musica--invita. El anillo usa
   --portada-acento (on-brand y visible sobre fondos claros U oscuros); fallback a
   un gris translúcido. Las plantillas con box-shadow de marca en el CTA (pop/glow)
   sustituyen este pulso por uno de solo `transform` en su hoja (para no pisar la
   sombra). */
@media (prefers-reduced-motion: no-preference) {
  .ti-portada:not(.ti-portada--abriendo) .ti-portada__cta {
    animation: ti-portada-pulso 2.2s ease-in-out infinite;
  }
  @keyframes ti-portada-pulso {
    0%, 100% { box-shadow: 0 0 0 0 var(--portada-acento, rgba(0, 0, 0, .28)); }
    50%      { box-shadow: 0 0 0 14px rgba(0, 0, 0, 0); }
  }
}

/* Reduced-motion: sin desplazamientos/escala. Fundido corto (para que
   transitionend dispare la revelación rápido) en vez de un cambio brusco.
   `!important` con especificidad 0,1,0 (> `*` del reset global de cada plantilla,
   que usa `* { transition:none !important }`): así la revelación NO cae al timeout
   de respaldo (1.4 s) en ninguna plantilla — vale para las 15 sin repetir por hoja. */
@media (prefers-reduced-motion: reduce) {
  .ti-portada { transition: opacity .2s linear !important; }
  .ti-portada__lienzo { transition: opacity .2s linear !important; will-change: opacity; }
  .ti-portada--abriendo .ti-portada__lienzo { transform: none !important; opacity: 0; }
}
