/* ============================================================
   ENSO MEDIA — Home horizontal
   Recorrido lateral: la página avanza de izquierda a derecha.
   Hoja independiente: no depende de base.css ni de style.css,
   porque aquí el color es dual (oscuro / claro).
   ============================================================ */

@font-face {
  font-family: "Oceania";
  src: url("../assets/fonts/Oceania-Regular.woff2") format("woff2");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: "Ubuntu Titling";
  src: url("../assets/fonts/Ubuntu-Bold.woff2") format("woff2");
  font-weight: 700;
  font-style: normal;
  font-display: swap;
}

/* ------------------------------------------------------------
   Tokens
   Los nombres son semánticos (fondo / tinta / marca) justo para
   que el tema claro sea un solo bloque de sobrescritura y no una
   cacería de #000 por toda la hoja.
   ------------------------------------------------------------ */
:root {
  color-scheme: dark;

  --marca: #ebdb00;         /* Amarillo Enso */
  --naranja: #f3b000;
  --marca-tinta: #ebdb00;   /* el amarillo cuando hace de TEXTO */
  --blanco: #ffffff;
  --negro: #000000;
  --wa: #25d366;            /* verde de WhatsApp: marca ajena, no nuestra */

  --fondo: #050505;
  --fondo-2: #0d0d0c;
  --fondo-3: #161614;
  /* Base opaca de los paneles oscuros: no cambia con el tema, por eso
     vive fuera de los pares claro/oscuro. Estaba escrito a mano en
     cuatro hojas distintas. */
  --negro-panel: #050505;
  --error: #ff9a8b;
  --sobre-marca: #0b0b0a;
  --wa-tinta: #05300f;
  --velo: 0 0 0;            /* rgb del velo sobre fotografía */

  --tinta: #ffffff;
  --tinta-suave: rgba(255, 255, 255, 0.68);
  --tinta-tenue: rgba(255, 255, 255, 0.55);
  --linea: rgba(255, 255, 255, 0.14);
  --linea-fuerte: rgba(255, 255, 255, 0.3);

  --vidrio: rgba(10, 10, 9, 0.72);
  --foto-brillo: 1;

  --display: "Ubuntu Titling", "Ubuntu", system-ui, sans-serif;
  --texto-font: "Oceania", "Ubuntu", system-ui, sans-serif;

  /* Tipografía: la misma escala que el home vertical, para que las
     dos versiones se lean como el mismo sitio. */
  --fs-hero: clamp(2.4rem, 5vw, 5.6rem);
  --fs-h2: clamp(1.8rem, 3.2vw, 3.3rem);
  --fs-h3: clamp(1.2rem, 1.7vw, 1.85rem);
  --fs-lead: clamp(1rem, 1.25vw, 1.28rem);
  --fs-body: clamp(0.95rem, 1vw, 1.05rem);
  --fs-micro: clamp(0.66rem, 0.74vw, 0.76rem);

  --space-2xs: 0.5rem;
  --space-xs: 0.75rem;
  --space-sm: 1rem;
  --space-md: 1.5rem;
  --space-lg: 2rem;
  --space-2xl: 4rem;

  --flow-sm: clamp(1rem, 1.6vw, 1.5rem);
  --flow-md: clamp(1.5rem, 2.4vw, 2rem);
  --flow-lg: clamp(2rem, 3.6vw, 3rem);
  --flow-xl: clamp(3rem, 5vw, 4rem);

  /* Multiplicador de los desfases verticales del recorrido lateral.
     Cada margen o relleno escalonado se escribe contra esta variable, así
     que apagarlos en una pantalla nueva es cambiar UN número. Antes cada
     desfase había que acordarse de resetearlo abajo, y tres se quedaron
     encendidos en móvil. */
  --desfase: 1;

  --gutter: clamp(1.25rem, 4.5vw, 5rem);
  --radio-sm: 8px;
  --radio: 16px;

  --z-elevado: 10;
  --z-flotante: 30;
  --z-menu: 40;
  --z-header: 50;
  --z-preloader: 80;

  --ease: cubic-bezier(0.22, 1, 0.36, 1);
}

[data-tema="claro"] {
  color-scheme: light;

  /* Sobre papel el amarillo de marca es ilegible como texto (1.3:1).
     Se conserva como RELLENO y baja a una versión tostada como TINTA. */
  --marca-tinta: #6b5c00;
  --blanco: #ffffff;

  --fondo: #f3f2ee;
  --fondo-2: #e8e6df;
  --fondo-3: #dedbd1;
  --velo: 243 242 238;

  --tinta: #0b0b0a;
  --tinta-suave: rgba(11, 11, 10, 0.74);
  --tinta-tenue: rgba(11, 11, 10, 0.62);
  --linea: rgba(11, 11, 10, 0.16);
  --linea-fuerte: rgba(11, 11, 10, 0.34);

  --vidrio: rgba(243, 242, 238, 0.78);
  --foto-brillo: 0.96;
}

*,
*::before,
*::after { box-sizing: border-box; }
* { margin: 0; padding: 0; }

html {
  -webkit-text-size-adjust: 100%;
  scroll-behavior: auto;
}

body {
  background: var(--fondo);
  color: var(--tinta);
  font-family: var(--texto-font);
  font-size: var(--fs-body);
  line-height: 1.62;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  overflow-x: hidden;
  transition: background-color 0.5s var(--ease), color 0.5s var(--ease);
}

img, video, svg { display: block; max-width: 100%; }
img, video { height: auto; }
a { color: inherit; text-decoration: none; }
p { text-wrap: pretty; }
button { font: inherit; color: inherit; background: none; border: 0; cursor: pointer; }

.sprite { position: absolute; width: 0; height: 0; overflow: hidden; }

::selection { background: rgba(235, 219, 0, 0.3); color: var(--tinta); }

:focus-visible {
  outline: 2px solid var(--marca);
  outline-offset: 3px;
  border-radius: var(--radio-sm);
  box-shadow: 0 0 0 5px rgba(0, 0, 0, 0.6);
}

[data-tema="claro"] :focus-visible { box-shadow: 0 0 0 5px rgba(255, 255, 255, 0.85); }

.salto {
  position: fixed;
  top: var(--space-sm);
  left: var(--space-sm);
  z-index: var(--z-preloader);
  padding: var(--space-xs) var(--space-md);
  border-radius: 100px;
  background: var(--marca);
  color: var(--negro);
  font-family: var(--display);
  font-size: 0.82rem;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  transform: translateY(-200%);
  transition: transform 0.3s var(--ease);
}

.salto:focus-visible { transform: translateY(0); }

/* Sólo para lectores de pantalla: fuera de la vista, dentro del árbol
   de accesibilidad. Sin width/height en cero, que algunos lectores saltan. */
.solo-lector {
  position: absolute;
  width: 1px;
  height: 1px;
  margin: -1px;
  padding: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
  border: 0;
}

/* ============================================================
   Tipografía de marca
   ============================================================ */

.display {
  font-family: var(--display);
  font-weight: 700;
  line-height: 0.94;
  letter-spacing: -0.025em;
  text-wrap: balance;
  -webkit-user-select: none;
  user-select: none;
}

.eyebrow {
  font-family: var(--display);
  font-weight: 700;
  font-size: var(--fs-micro);
  letter-spacing: 0.28em;
  text-transform: uppercase;
  color: var(--marca-tinta);
  display: inline-flex;
  align-items: center;
  gap: var(--space-xs);
}

.eyebrow::before {
  content: "";
  width: var(--space-md);
  height: 2px;
  background: currentColor;
  flex: none;
}

.lead {
  font-size: var(--fs-lead);
  line-height: 1.58;
  color: var(--tinta-suave);
  max-width: 54ch;
}

/* ============================================================
   Botones
   ============================================================ */

.btn {
  --bg: var(--marca);
  --fg: var(--negro);
  position: relative;
  display: inline-flex;
  align-items: center;
  gap: var(--space-2xs);
  padding: var(--space-sm) var(--space-md);
  min-height: 46px;
  border-radius: 100px;
  font-family: var(--display);
  font-weight: 700;
  font-size: clamp(0.78rem, 0.9vw, 0.9rem);
  letter-spacing: 0.06em;
  text-transform: uppercase;
  background: var(--bg);
  color: var(--fg);
  overflow: hidden;
  isolation: isolate;
  transition: color 0.4s var(--ease), border-color 0.4s var(--ease);
}

.btn span { position: relative; z-index: var(--z-elevado); }

.btn svg {
  position: relative;
  z-index: var(--z-elevado);
  width: 15px;
  height: 15px;
  flex: none;
  transition: transform 0.5s var(--ease);
}

.btn::after {
  content: "";
  position: absolute;
  inset: 0;
  background: var(--tinta);
  border-radius: inherit;
  transform: translateY(101%);
  transition: transform 0.55s var(--ease);
}

.btn:hover::after { transform: translateY(0); }
.btn:hover { color: var(--fondo); }
.btn:hover svg { transform: translate(3px, -3px); }

.btn--fantasma {
  --bg: transparent;
  --fg: var(--tinta);
  border: 1px solid var(--linea-fuerte);
}

.btn--fantasma::after { background: var(--marca); }
.btn--fantasma:hover { color: var(--negro); border-color: var(--marca); }

.btn--wa { --bg: transparent; --fg: var(--tinta); border: 1px solid var(--linea-fuerte); }
.btn--wa::after { background: var(--wa); }
.btn--wa:hover { color: var(--negro); border-color: var(--wa); }

.link-flecha {
  display: inline-flex;
  align-items: center;
  min-height: 48px;
  gap: var(--space-2xs);
  font-family: var(--display);
  font-weight: 700;
  font-size: 0.78rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--tinta);
  padding-bottom: var(--space-xs);
  border-bottom: 1px solid var(--linea-fuerte);
  transition: color 0.35s var(--ease), border-color 0.35s var(--ease);
}

.link-flecha svg { transition: transform 0.35s var(--ease); }
.link-flecha:hover { color: var(--marca-tinta); border-color: var(--marca-tinta); }
.link-flecha:hover svg { transform: translateX(4px); }

/* ============================================================
   Preloader
   ============================================================ */

/* La pantalla de carga sólo existe si hay guion que la retire. Sin él
   no se dibuja: era la razón de que la página se quedara en negro. */
.preloader { display: none; }

.js .preloader {
  position: fixed;
  inset: 0;
  z-index: var(--z-preloader);
  display: grid;
  place-content: center;
  justify-items: center;
  gap: var(--space-md);
  background: var(--fondo);
}

.preloader__mark { width: 88px; height: 84px; fill: var(--marca); opacity: 0.92; }
.preloader__frase {
  font-family: var(--display);
  font-size: var(--fs-micro);
  letter-spacing: 0.34em;
  text-transform: uppercase;
  color: var(--tinta-tenue);
}
.preloader__barra { width: min(240px, 46vw); height: 2px; background: var(--linea); overflow: hidden; }
.preloader__barra i { display: block; height: 100%; width: 0; background: var(--marca); }

/* Header y navegador flotan por encima del contenido: sobre el hero
   y el cierre —que siempre son fotografía en penumbra— se invierten,
   aunque el resto del sitio esté en tema claro. */
/* Un solo bloque define "claro sobre fotografía en penumbra". Antes
   estos seis valores estaban escritos tres veces; cambiar el gris del
   texto obligaba a cazarlos por toda la hoja. */
.hero,
.cierre,
.sobre-oscuro .header,
.sobre-oscuro .puntos,
.sobre-oscuro .cue--fija,
.con-video .video-btn {
  --tinta: var(--blanco);
  --tinta-suave: rgba(255, 255, 255, 0.72);
  --tinta-tenue: rgba(255, 255, 255, 0.6);
  --linea: rgba(255, 255, 255, 0.16);
  --linea-fuerte: rgba(255, 255, 255, 0.32);
  --marca-tinta: var(--marca);
  --vidrio: rgba(10, 10, 9, 0.72);
  --fondo: #050505;
}

/* Y al revés: sobre un panel claro dentro de una página oscura, el
   header y los puntos tienen que pasar a tinta negra o desaparecen. */
.sobre-claro .header,
.sobre-claro .puntos,
.sobre-claro .cue--fija {
  --tinta: #0b0b0a;
  --tinta-suave: rgba(11, 11, 10, 0.74);
  --tinta-tenue: rgba(11, 11, 10, 0.62);
  --linea: rgba(11, 11, 10, 0.16);
  --linea-fuerte: rgba(11, 11, 10, 0.34);
  --marca-tinta: #6b5c00;
  --vidrio: rgba(243, 242, 238, 0.78);
  --fondo: #f3f2ee;
  color: var(--tinta);
}

[data-tema="claro"].sobre-claro .header,
[data-tema="claro"].sobre-claro .puntos,
[data-tema="claro"].sobre-claro .cue--fija {
  --tinta: #ffffff;
  --tinta-suave: rgba(255, 255, 255, 0.72);
  --tinta-tenue: rgba(255, 255, 255, 0.6);
  --linea: rgba(255, 255, 255, 0.16);
  --linea-fuerte: rgba(255, 255, 255, 0.32);
  --marca-tinta: #ebdb00;
  --vidrio: rgba(10, 10, 9, 0.72);
  --fondo: var(--negro-panel);
  color: var(--tinta);
}

.sobre-claro .header__anillo { fill: #6b5c00; }
[data-tema="claro"].sobre-claro .header__anillo { fill: #ebdb00; }
.sobre-claro .punto::before { filter: brightness(0.62) saturate(1.3); }
[data-tema="claro"].sobre-claro .punto::before { filter: none; }

/* En tema claro los aros amarillos se pierden sobre el papel:
   se oscurecen sin salirse de la gama de marca. */
[data-tema="claro"] .punto::before { filter: brightness(0.62) saturate(1.3); }
[data-tema="claro"].sobre-oscuro .punto::before { filter: none; }

/* ============================================================
   Header
   ============================================================ */

.header {
  position: fixed;
  inset: 0 0 auto;
  z-index: var(--z-header);
  padding: var(--space-md) var(--gutter);
  display: flex;
  align-items: center;
  /* Envuelve. Con el texto al 200 % —lo que hace cualquiera con la
     vista cansada— las piezas crecen y en una fila rígida el botón
     «Menú» se salía por la derecha, fuera de alcance. */
  flex-wrap: wrap;
  row-gap: var(--space-2xs);
  gap: var(--flow-md);
  pointer-events: none;
}

.header > * { pointer-events: auto; }

.header__logo {
  display: inline-flex;
  align-items: center;
  gap: 0.55rem;
  min-height: 44px;
  flex: none;
}

/* Imagotipo conmemorativo "+15 años". Va en una sola tinta, como en el
   manual, así que hereda el color del tema: blanco sobre los paneles
   oscuros, negro sobre los claros. Sin ancho fijo —la proporción del
   bloque es 2.55:1— para que no se deforme si cambia el alto. */
.header__quince {
  /* En `em` y no en px: con el texto ampliado el logotipo crece con el
     resto del encabezado en vez de quedarse pequeño al lado. El tope
     evita que se coma la fila entera. */
  height: min(2.6em, 40px);
  width: auto;
  color: var(--tinta);
  transition: color 0.5s var(--ease);
}

/* Las dos piezas sueltas del logotipo anterior. No las usa ninguna
   página publicada; se conservan porque las archivadas sí. */
.header__anillo { width: 30px; height: 28px; fill: var(--marca); }
.header__palabra { width: 74px; height: 40px; fill: var(--tinta); transition: fill 0.5s var(--ease); }

/* La etiqueta de sección: cambia sola conforme avanza el recorrido */
/* La etiqueta de sección que iba junto al logotipo se retiró: el cliente
   pidió el logotipo solo. El aviso para lector de pantalla (#aviso) sigue
   anunciando el cambio de sección, y los puntos de abajo siguen diciendo
   por dónde vas. Las reglas de .header__seccion se conservan sólo para la
   página archivada, que todavía la lleva. */
.header__seccion { display: none; }

.header__nav {
  margin-inline-start: auto;
  display: none;
  gap: var(--flow-sm);
  font-family: var(--display);
  font-size: 0.74rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
}

/* 44px de alto de caja aunque el texto mida 12: el subrayado se pinta
   con un pseudo, no con el borde, para que no se despegue del texto. */
.header__nav a {
  position: relative;
  display: inline-flex;
  align-items: center;
  min-height: 44px;
  color: var(--tinta-suave);
  transition: color 0.3s var(--ease);
}

.header__nav a::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  bottom: 12px;
  height: 1px;
  background: var(--marca);
  transform: scaleX(0);
  transform-origin: left center;
  transition: transform 0.3s var(--ease);
}

.header__nav a:hover,
.header__nav a.is-activo { color: var(--tinta); }
.header__nav a:hover::after,
.header__nav a.is-activo::after { transform: scaleX(1); }

/* ------------------------------------------------------------
   Servicios: siete líneas que no caben en la barra, así que van en
   un desplegable. Botón real, no un :hover: con hover puro el
   submenú es inalcanzable con teclado y en pantalla táctil.
   ------------------------------------------------------------ */
.nav-grupo { position: relative; }

.nav-grupo__btn {
  position: relative;
  display: inline-flex;
  align-items: center;
  gap: 0.3rem;
  min-height: 44px;
  font-family: var(--display);
  font-size: 0.74rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--tinta-suave);
  transition: color 0.3s var(--ease);
}

/* La página en la que estás, marcada de verdad: el aria-current ya
   estaba puesto para el lector de pantalla, pero a la vista no se
   notaba nada. */
.header__nav a[aria-current="page"] { color: var(--tinta); }
.header__nav a[aria-current="page"]::after { transform: scaleX(1); }

.nav-grupo__btn[aria-current="page"] { color: var(--tinta); }

.nav-grupo__btn[aria-current="page"]::after {
  content: "";
  position: absolute;
  left: 0;
  right: 17px;
  bottom: 12px;
  height: 1px;
  background: var(--marca);
}

.nav-grupo__btn svg { width: 13px; height: 13px; transition: transform 0.3s var(--ease); }
.nav-grupo__btn:hover,
.nav-grupo__btn[aria-expanded="true"] { color: var(--tinta); }
.nav-grupo__btn[aria-expanded="true"] svg { transform: rotate(180deg); }

.submenu {
  position: absolute;
  top: calc(100% + var(--space-2xs));
  left: 50%;
  translate: -50% 0;
  z-index: var(--z-header);
  display: grid;
  min-width: 232px;
  padding: var(--space-2xs);
  border-radius: var(--radio);
  border: 1px solid var(--linea);
  background: var(--vidrio);
  backdrop-filter: blur(20px) saturate(150%);
  box-shadow: 0 16px 40px rgba(0, 0, 0, 0.4);
}

.submenu[hidden] { display: none; }

/* El botón "Servicios" abre el desplegable pero no lleva a ningún
   lado. Sin esta primera línea no había forma de llegar a la página
   madre desde la barra. */
.submenu .submenu__madre {
  border-bottom: 1px solid var(--linea);
  border-radius: var(--radio-sm) var(--radio-sm) 0 0;
  margin-bottom: var(--space-2xs);
  color: var(--marca-tinta);
}

.submenu a {
  display: flex;
  align-items: center;
  min-height: 44px;
  padding: 0 var(--space-sm);
  border-radius: var(--radio-sm);
  font-family: var(--display);
  font-size: 0.72rem;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--tinta-suave);
  white-space: nowrap;
  transition: color 0.25s var(--ease), background-color 0.25s var(--ease);
}

.submenu a:hover { color: var(--tinta); background: var(--linea); }

.header__acciones {
  margin-inline-start: auto;
  display: flex;
  align-items: center;
  gap: var(--space-2xs);
}

.header__nav + .header__acciones { margin-inline-start: var(--flow-sm); }

/* Interruptor de tema */
.tema {
  width: 44px;
  height: 44px;
  display: grid;
  place-items: center;
  border-radius: 100px;
  border: 1px solid var(--linea);
  background: var(--vidrio);
  backdrop-filter: blur(14px);
  color: var(--tinta);
  transition: border-color 0.3s var(--ease), color 0.3s var(--ease);
}

.tema:hover { border-color: var(--marca); color: var(--marca-tinta); }
.tema svg { width: 19px; height: 19px; }
.tema .luna { display: none; }
[data-tema="claro"] .tema .sol { display: none; }
[data-tema="claro"] .tema .luna { display: block; }

.header__cta { display: none; }
.header__cta span { white-space: nowrap; }

.menu-btn {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2xs);
  min-height: 44px;
  padding: 0 var(--space-md);
  border-radius: 100px;
  border: 1px solid var(--linea);
  background: var(--vidrio);
  backdrop-filter: blur(14px);
  font-family: var(--display);
  font-size: 0.74rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
}

.burger { display: grid; gap: 4px; width: 16px; }
.burger i { display: block; height: 2px; background: currentColor; transition: transform 0.35s var(--ease); }

@media (min-width: 1120px) {
  .header__nav { display: flex; }
  .header__cta { display: inline-flex; }
  .menu-btn { display: none; }
}

/* ============================================================
   Menú (solo abajo de 1120px)
   ============================================================ */

.menu {
  position: fixed;
  inset: 0;
  z-index: var(--z-menu);
  display: grid;
  /* Con trece enlaces ya no se puede centrar: el primero quedaba debajo
     del header. Empieza abajo del header y, si hiciera falta, rueda. */
  align-content: start;
  gap: var(--space-lg);
  padding: calc(var(--gutter) + 4.5rem) var(--gutter) var(--gutter);
  overflow-y: auto;
  overscroll-behavior: contain;
  background: var(--fondo-2);
  visibility: hidden;
  opacity: 0;
  transition: opacity 0.4s var(--ease), visibility 0.4s;
}

.menu.is-abierto { visibility: visible; opacity: 1; }

.menu__lista { display: grid; gap: var(--space-2xs); }

.menu__lista a {
  font-family: var(--display);
  font-size: clamp(1.35rem, 5.2vw, 2.2rem);
  line-height: 1.1;
  letter-spacing: -0.02em;
  /* Al bajar el cuerpo para que cupieran trece enlaces, la caja táctil
     cayó a 40 px. El mínimo se fija aparte del tamaño de letra. */
  min-height: 48px;
  display: flex;
  align-items: center;
  padding: var(--space-2xs) 0;
  color: var(--tinta);
  transition: color 0.3s var(--ease);
}

.menu__lista a:hover { color: var(--marca-tinta); }

/* En el overlay los siete servicios van sangrados bajo su título:
   sin la sangría se leían como siete secciones más del mismo nivel. */
.menu__grupo { display: grid; gap: var(--space-2xs); }

.menu__sub {
  display: grid;
  gap: 0;
  padding-left: var(--space-md);
  border-left: 1px solid var(--linea);
}

.menu__sub a {
  font-family: var(--texto-font);
  font-size: clamp(0.95rem, 3.6vw, 1.05rem);
  letter-spacing: 0.02em;
  line-height: 1.3;
  padding: var(--space-2xs) 0;
  min-height: 44px;
  display: flex;
  align-items: center;
  color: var(--tinta-suave);
}
.menu__pie { color: var(--tinta-tenue); font-size: 0.9rem; }

/* ============================================================
   El escenario y la pista
   ============================================================ */

.escenario {
  position: relative;
  height: 100svh;
  overflow: hidden;
}

.pista {
  display: flex;
  align-items: stretch;
  height: 100svh;
  will-change: transform;
}

/* El ancho lo dicta el contenido, no un número inventado: así ningún
   panel corta una tarjeta por la mitad ni deja un hueco muerto. */
.panel {
  position: relative;
  flex: none;
  width: max-content;
  min-width: 100vw;
  height: 100svh;
  display: flex;
  align-items: center;
  /* Arriba deja pasar el header; abajo, la píldora de puntos.
     El relleno inferior usa max(), no clamp(): con clamp se encogía con
     la altura justo cuando la píldora seguía midiendo lo mismo, y a
     720 px la píldora acababa encima del texto.

     --util es el alto que de verdad queda para el contenido. Todo lo que
     antes se medía en vh sueltos ahora se mide contra esto, que es lo
     único que no miente cuando la pantalla es baja. */
  /* El mayor de los dos: el de siempre, y el alto real del encabezado
     más aire. Con el texto al 200 % el encabezado envuelve a dos filas
     y sin esto los botones caían encima del titular. `--alto-cab` lo
     publica el guion; si no llega, manda el valor de siempre. */
  --pad-t: max(clamp(5.5rem, 10vh, 7.5rem), calc(var(--alto-cab, 0px) + 1.4rem));
  --pad-b: max(7rem, 10vh);
  --util: calc(100svh - var(--pad-t) - var(--pad-b));
  padding: var(--pad-t) var(--gutter) var(--pad-b);
  overflow: hidden;
}

/* ------------------------------------------------------------
   La costura entre paneles
   La pista se desplaza en posiciones fraccionarias y cada panel
   redondea su rectángulo por separado: el píxel que cae a medias entre
   dos paneles se compone con los colores de ambos, y entre uno claro y
   uno oscuro eso se lee como una línea clara de altura completa. Medido:
   luminancia 109 en esa columna con las vecinas en 7.

   Cada panel monta un píxel sobre el anterior. Son opacos, así que no
   se ve nada distinto salvo que la línea desaparece.
   ------------------------------------------------------------ */
/* ------------------------------------------------------------
   Etiqueta de sección
   El documento la señala diez veces como el formato de subtítulo del
   sitio entero. Vivía en la hoja de Nosotros, así que en el Home salía
   como texto suelto: se muda aquí, que es lo que carga todo el sitio.

   Píldora con borde, no bloque sólido: el amarillo pesa demasiado
   repetido seis veces en la misma página.
   ------------------------------------------------------------ */
.pill {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2xs);
  padding: 0.4rem var(--space-md);
  border: 1px solid var(--marca-tinta);
  border-radius: 100px;
  font-family: var(--display);
  font-size: var(--fs-micro);
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: var(--marca-tinta);
}

.pill::before {
  content: "";
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: currentColor;
}

/* En una rejilla o una columna flex la píldora se estiraría a todo el
   ancho: es una etiqueta, no una barra. */
.panel .pill { align-self: start; justify-self: start; width: fit-content; }

.panel + .panel { margin-left: -1px; }

.panel--alterno { background: var(--fondo-2); }

/* Número de panel al fondo: da sensación de recorrido, como los
   kilómetros de una carretera. */
.panel__folio {
  position: absolute;
  right: var(--gutter);
  bottom: calc(var(--space-2xl) + 0.5rem);
  font-family: var(--display);
  font-size: clamp(3rem, 5.5vw, 5.5rem);
  line-height: 1;
  color: var(--tinta);
  opacity: 0.045;
  pointer-events: none;
  user-select: none;
}

/* ============================================================
   1 · Hero
   ============================================================ */

/* El hero y el cierre se quedan en oscuro aunque el sitio esté en
   claro: son fotografía de espectáculo, luz de escenario sobre
   negro. Aclararlos los vuelve una postal lavada. */
.hero,
.cierre { --velo: 0 0 0; }

.hero,
.cierre,
.sobre-oscuro .header,
.sobre-oscuro .puntos { color: var(--blanco); }

/* --- El velo del encabezado ---------------------------------------
   El menú va sobre lo que haya: en el panel de servicios del Home eso
   es una rejilla de fotografías a sangre, y en tema claro suben de
   brillo hasta dejar el enlace activo en 3,45:1. Existía este velo pero
   sólo en teléfono; aquí vale para todos los tamaños.

   Muy suave a propósito: sobre un panel oscuro no se distingue del
   fondo —no aparece una barra— y sobre uno claro es lo único que
   sostiene el texto. */
/* El velo va contra la tinta del propio encabezado, no contra el tema de
   la página: sobre un panel oscuro el menú es blanco y el velo negro;
   sobre uno claro, al revés. Usar el `--velo` general lo pintaba blanco
   bajo texto blanco y el contraste caía a 1,8:1. */
.header { --velo-cab: 0 0 0; }
.sobre-claro .header { --velo-cab: 243 242 238; }
[data-tema="claro"].sobre-claro .header { --velo-cab: 0 0 0; }
[data-tema="claro"].sobre-oscuro .header { --velo-cab: 0 0 0; }

.header::before {
  content: "";
  position: absolute;
  inset: -1px 0 auto;
  height: 190%;
  background: linear-gradient(180deg,
    rgb(var(--velo-cab) / 0.62) 0%,
    rgb(var(--velo-cab) / 0.38) 46%,
    rgb(var(--velo-cab) / 0) 100%);
  pointer-events: none;
  z-index: -1;
}

.hero {
  padding-block: clamp(6rem, 11vh, 8rem) clamp(7rem, 13vh, 9rem);
  align-items: center;
}

/* Todo panel con fotografía o vídeo de fondo pinta una base opaca. El
   vídeo carga en diferido y la foto es lazy: mientras no están, el panel
   era transparente y por debajo del velo semitransparente se colaba el
   fondo de la página. En la transición se veía como una franja clara —el
   "espacio" que parecía un bug. */
.panel[data-oscuro] { background: var(--negro-panel); }

/* Más ancha que el panel: el desplazamiento la mueve sin dejar
   franjas negras en los bordes. */
/* La caja mide el panel y recorta ella misma; el desbordamiento de
   paralaje vive en la foto de dentro. Cuando era la caja la que se
   salía del panel, su recorte y el del velo se redondeaban distinto en
   las posiciones fraccionarias del recorrido y asomaba una columna de
   foto sin velar: la línea blanca vertical que reportó el cliente. */
.hero__media {
  position: absolute;
  inset: 0;
  overflow: hidden;
  z-index: 0;
}

/* Con `.hero__media > img` perdía contra `.hero__media img { width:100% }`
   —misma especificidad y esa va después—, y la foto se quedaba corta por
   la derecha. Se cuenta el .panel para ganar sin `!important`. */
.panel .hero__media > img,
.panel .hero__media > video {
  position: absolute;
  top: 0;
  left: -14%;
  /* `img, video, svg { max-width: 100% }` de la base recorta el 128 % y
     deja una franja negra a la derecha. La misma trampa que ya estaba
     anotada para .medios__media img. */
  max-width: none;
  width: 128%;
  height: 100%;
}

/* El <img> es la red de seguridad: si el vídeo no puede cargarse
   —o el empaquetado lo sustituye por su póster— la imagen tiene que
   cubrir igual, no salir a tamaño natural encima del titular. */
.hero__media video,
.hero__media img,
.cierre__media video,
.cierre__media img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  filter: brightness(var(--foto-brillo));
}

.hero__velo {
  position: absolute;
  /* 2 px de sangrado, no 0: con `inset: 0` el borde del velo y el
     recorte de la foto caen en píxeles distintos al estar el panel
     en una posición fraccionaria, y asoma una línea de foto sin
     velo. El panel recorta, así que el sangrado no se ve. */
  inset: -2px;
  z-index: 1;
  background:
    linear-gradient(90deg, rgb(var(--velo) / 0.92) 0%, rgb(var(--velo) / 0.72) 42%, rgb(var(--velo) / 0.35) 100%),
    linear-gradient(0deg, rgb(var(--velo) / 0.85) 0%, rgb(var(--velo) / 0) 55%);
}

.hero__inner {
  position: relative;
  z-index: 2;
  width: min(58ch, 52vw);
}

.hero__titulo {
  font-size: var(--fs-hero);
  margin: var(--flow-sm) 0 var(--flow-md);
  max-width: 15ch;
}

.hero__titulo em { font-style: normal; color: var(--marca); }

.hero__sub {
  color: var(--tinta-suave);
  font-size: var(--fs-lead);
  max-width: 46ch;
  margin-bottom: var(--flow-md);
}

.hero__acciones { display: flex; flex-wrap: wrap; gap: var(--space-sm); }

/* Antes había aquí una tira de tres métricas con número grande y
   etiqueta chica: la plantilla de "hero metrics" que sale en cualquier
   sitio generado. Los nombres propios prueban lo mismo y no se parecen
   a nada. */
.hero__prueba {
  position: relative;
  z-index: 2;
  margin-top: var(--flow-lg);
  padding-top: var(--space-md);
  border-top: 1px solid var(--linea);
  font-family: var(--display);
  font-size: clamp(0.82rem, 1.05vw, 1rem);
  letter-spacing: 0.04em;
  color: var(--tinta-suave);
  max-width: 44ch;
}

.hero__prueba span {
  display: block;
  margin-top: 0.35rem;
  font-family: var(--texto-font);
  font-size: 0.82rem;
  letter-spacing: 0.06em;
  color: var(--tinta-tenue);
}

/* Pista de "desliza" horizontal */
.cue {
  position: absolute;
  right: var(--gutter);
  bottom: calc(var(--space-2xl) + 1.4rem);
  z-index: 2;
  display: inline-flex;
  align-items: center;
  gap: var(--space-xs);
  font-family: var(--display);
  font-size: var(--fs-micro);
  letter-spacing: 0.26em;
  text-transform: uppercase;
  color: var(--tinta-tenue);
}

/* --- Indicador de scroll del Home ----------------------------
   Dice lo que hay que hacer y lo que va a pasar: una rueda de ratón
   con el punto bajando, y una flecha que apunta a la derecha. El
   cliente reportó la contradicción entre el gesto y el movimiento;
   esto no la elimina —es el recorrido— pero deja de ser una sorpresa. */
.cue--scroll {
  gap: var(--space-sm);
  letter-spacing: 0.12em;
  color: var(--tinta-suave);
}

/* --- La copia que inyecta el motor en las páginas sin portada ---
   Va fija a la ventana, no al panel: el panel de apertura de esas
   páginas es más ancho que la pantalla y una posición absoluta la
   dejaría fuera de cuadro. Se aparta sola al primer scroll. */
.cue--scroll.cue--fija {
  /* Los bloques de inversión de arriba fijan `color` con dos clases;
     este lo devuelve al tono discreto sin tocar los tokens. */
  color: var(--tinta-suave);
}

.cue--fija {
  position: fixed;
  right: var(--gutter);
  bottom: calc(var(--space-2xl) + 1.4rem);
  z-index: 40;
  pointer-events: none;
  transition: opacity 0.45s var(--ease), transform 0.45s var(--ease);
}

.cue--fija.se-fue {
  opacity: 0;
  transform: translateX(1.2rem);
}

/* Una ficha de proyecto de una sola fotografía cabe entera en la
   pantalla. Ahí la indicación pediría un scroll que no lleva a ninguna
   parte, así que no se dibuja. */
.cue--sin-recorrido { display: none; }

.panel__folio { transition: opacity 0.45s var(--ease); }
.con-indicacion .panel__folio { opacity: 0; }

.cue__rueda {
  position: relative;
  width: 20px;
  height: 32px;
  border: 1.5px solid var(--linea-fuerte);
  border-radius: 100px;
  flex: none;
}

.cue__rueda i {
  position: absolute;
  left: 50%;
  top: 7px;
  width: 3px;
  height: 6px;
  margin-left: -1.5px;
  border-radius: 100px;
  background: var(--marca);
  animation: cueRueda 1.9s var(--ease) infinite;
}

@keyframes cueRueda {
  0%, 12%   { transform: translateY(0); opacity: 0; }
  25%       { opacity: 1; }
  70%, 100% { transform: translateY(11px); opacity: 0; }
}

.cue__texto { display: grid; gap: 2px; text-align: right; }
.cue__texto b {
  font-family: var(--texto-font);
  font-weight: 400;
  font-size: 0.72rem;
  letter-spacing: 0.01em;
  text-transform: none;
  color: var(--tinta-tenue);
}

.cue__flecha { width: 20px; height: 20px; color: var(--marca); flex: none; }

@media (prefers-reduced-motion: reduce) {
  .cue__rueda i { animation: none; opacity: 1; transform: translateY(5px); }
}

.cue i {
  width: 54px;
  height: 1px;
  background: var(--linea-fuerte);
  position: relative;
  overflow: hidden;
}

.cue i::after {
  content: "";
  position: absolute;
  inset: 0;
  background: var(--marca);
  transform: translateX(-100%);
  animation: cue 2.1s var(--ease) infinite;
}

@keyframes cue {
  0% { transform: translateX(-100%); }
  60%, 100% { transform: translateX(100%); }
}

/* ============================================================
   2 · Esencia
   ============================================================ */

.esencia { gap: var(--flow-xl); align-items: center; }

.esencia__texto { max-width: 44ch; flex: none; width: min(44ch, 40vw); }
.esencia__texto p + p { margin-top: var(--space-sm); }
.esencia__texto p { color: var(--tinta-suave); }
.esencia__texto .link-flecha { margin-top: var(--flow-md); }

/* Tres placas fotográficas a distintas alturas y velocidades: la
   profundidad se lee sola cuando cada una se mueve a su ritmo. */
.placas { display: flex; align-items: center; gap: var(--flow-md); }

.placa {
  position: relative;
  flex: none;
  overflow: hidden;
  border-radius: var(--radio);
  background: var(--fondo-3);
}

.placa img { width: 100%; height: 100%; object-fit: cover; filter: brightness(var(--foto-brillo)); }

.placa--a { width: min(30vw, 420px); aspect-ratio: 4 / 5; }
.placa--b { width: min(26vw, 360px); aspect-ratio: 1 / 1; margin-top: calc(-14vh * var(--desfase)); }
.placa--c { width: min(22vw, 300px); aspect-ratio: 4 / 5; margin-top: calc(12vh * var(--desfase)); }

/* Una sola fotografía, la de grupo: es panorámica, así que ocupa ancho
   en vez de altura y se lee de un vistazo.

   La proporción es la de la fotografía misma —1800 × 669, o sea 2.69:1—
   y no un 16/9 redondeado. Con 16/9 el `object-fit: cover` se comía un
   tercio del ancho y la gente de los extremos quedaba fuera de cuadro:
   es una foto de grupo, así que recortarla por los lados es recortar
   personas. */
.placa--grupo { width: min(46vw, 660px); aspect-ratio: 1800 / 669; }

.placa__pie {
  position: absolute;
  left: var(--space-sm);
  bottom: var(--space-sm);
  padding: 0.35rem 0.7rem;
  border-radius: 100px;
  background: rgba(0, 0, 0, 0.78);
  color: var(--blanco);
  font-family: var(--display);
  font-size: 0.62rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
}

/* ============================================================
   3 · Servicios
   ============================================================ */

.servicios { gap: var(--flow-lg); align-items: center; }

.servicios__intro { flex: none; width: min(34ch, 30vw); }

.mosaico {
  display: grid;
  grid-template-rows: repeat(2, minmax(0, 1fr));
  grid-auto-flow: column;
  grid-auto-columns: minmax(330px, 30vw);
  gap: var(--space-md);
  height: min(var(--util), 500px);
}

.servicio {
  position: relative;
  overflow: hidden;
  border-radius: var(--radio);
  background: var(--fondo-3);
  isolation: isolate;
}

.servicio img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  filter: brightness(calc(var(--foto-brillo) * 0.7)) saturate(0.9);
  transition: transform 0.7s var(--ease), filter 0.5s var(--ease);
}

.servicio::after {
  content: "";
  position: absolute;
  inset: 0;
  background: linear-gradient(0deg, rgba(0, 0, 0, 0.94) 0%, rgba(0, 0, 0, 0.72) 34%,
                              rgba(0, 0, 0, 0.42) 62%, rgba(0, 0, 0, 0.24) 100%);
}

.servicio:hover img { transform: scale(1.06); filter: brightness(calc(var(--foto-brillo) * 0.95)) saturate(1.05); }

/* El enlace cubre la tarjeta entera. Antes sólo respondía el renglón de
   "Conocer más" y, con la tarjeta inclinada por su animación de entrada,
   el punto de clic no coincidía con lo que se veía: el cliente reportó
   que los enlaces "no funcionan hasta que están casi fuera de pantalla". */
.servicio__ir {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin-top: var(--space-xs);
  font-family: var(--display);
  font-size: var(--fs-micro);
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--blanco);
  transition: color 0.3s var(--ease);
}

.servicio__manta {
  position: absolute;
  inset: 0;
  z-index: 4;
}

.servicio:hover .servicio__ir { color: var(--marca); }
.servicio__ir:focus-visible { outline: 2px solid var(--marca); outline-offset: 4px; }

.servicio__cuerpo {
  position: relative;
  z-index: 2;
  height: 100%;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  padding: var(--space-md);
  color: var(--blanco);
}

.servicio__num {
  font-family: var(--display);
  font-size: 0.72rem;
  letter-spacing: 0.2em;
  color: var(--marca);
}

.servicio h3 { font-family: var(--display); font-size: var(--fs-h3); line-height: 1.05; letter-spacing: -0.02em; }
.servicio p { font-size: 0.92rem; color: rgba(255, 255, 255, 0.76); margin-top: var(--space-2xs); }
.servicio .link-flecha { color: var(--blanco); margin-top: var(--space-xs); }

/* La tarjeta alta rompe la retícula de seis iguales */
.servicio--alto { grid-row: span 2; }

/* ============================================================
   4 · Por qué Enso
   ============================================================ */

.porque { gap: var(--flow-xl); align-items: center; }
.porque__intro { flex: none; width: min(30ch, 26vw); }

/* La foto ancla: una sola imagen grande sostiene las cinco razones.
   Antes eran cinco miniaturas dentro de cinco tarjetas iguales —la
   rejilla de tarjetas idénticas que este proyecto tiene prohibida. */
.ancla {
  position: relative;
  flex: none;
  width: min(32vw, 430px);
  height: min(calc(var(--util) * 0.72), 480px);
  overflow: hidden;
  border-radius: var(--radio);
  background: var(--fondo-3);
}

.ancla img { width: 100%; height: 100%; object-fit: cover; filter: brightness(var(--foto-brillo)); }

.ancla figcaption {
  position: absolute;
  left: var(--space-sm);
  bottom: var(--space-sm);
  padding: 0.35rem 0.7rem;
  border-radius: 100px;
  background: rgba(0, 0, 0, 0.78);
  color: var(--blanco);
  font-family: var(--display);
  font-size: 0.62rem;
  letter-spacing: 0.2em;
  text-transform: uppercase;
}

/* Cinco entradas de texto separadas por un filete, no por un contenedor.
   La regla vertical es de 1px: un filete editorial, no una franja de color. */
.razones { display: flex; align-items: stretch; list-style: none; }

.razon {
  flex: none;
  width: min(300px, 23vw);
  padding: 0 var(--flow-md);
  border-left: 1px solid var(--linea);
  display: flex;
  flex-direction: column;
}

.razon:first-child { border-left: 0; padding-left: 0; }

/* Alturas alternas: la fila deja de leerse como una tabla */
.razon:nth-child(even) { padding-top: calc(14vh * var(--desfase)); }
.razon:nth-child(3n) { padding-top: calc(4vh * var(--desfase)); }

.razon__indice {
  font-family: var(--display);
  font-size: clamp(2.2rem, 3.4vw, 3.4rem);
  line-height: 1;
  color: var(--marca-tinta);
  opacity: 0.9;
  margin-bottom: var(--flow-sm);
}

.razon h3 {
  font-family: var(--display);
  font-size: 1.16rem;
  line-height: 1.16;
  letter-spacing: -0.01em;
  margin-bottom: var(--space-2xs);
}

.razon p { font-size: 0.94rem; color: var(--tinta-suave); }

/* La fotografía de cada razón, debajo de su texto. El documento cuelga
   una de cada una de las cinco; sin ellas la fila eran cinco columnas
   de texto y poco más. `margin-top: auto` las alinea por abajo aunque
   los textos midan distinto. */
.razon__foto {
  margin-top: auto;
  padding-top: var(--flow-sm);
  /* Grandes: a 0.24 del alto útil la fotografía era una tira de 168 px
     debajo de un texto de 350 y no se veía qué había en ella. El panel
     tenía 178 px libres por debajo; se los queda la foto. */
  height: clamp(180px, calc(var(--util) * 0.40), 340px);
  border-radius: var(--radio-sm);
  overflow: hidden;
}

.razon__foto img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  border-radius: inherit;
  filter: brightness(calc(var(--foto-brillo) * 0.92)) saturate(0.96);
}

/* ============================================================
   5 · Proyectos
   ============================================================ */

.proyectos { gap: var(--flow-lg); align-items: center; }
.proyectos__intro { flex: none; width: min(30ch, 26vw); }

.galeria { display: flex; align-items: center; gap: var(--flow-md); }

.proyecto { position: relative; flex: none; width: min(38vw, 560px); display: grid; gap: var(--space-md); }

/* Cada proyecto lleva al caso dentro de su página de servicio. El enlace
   cubre la ficha entera —igual que en las tarjetas de servicio— para que
   el clic funcione donde se ve, no sólo sobre el renglón de texto. */
.proyecto__ir {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin-top: var(--space-2xs);
  font-family: var(--display);
  font-size: var(--fs-micro);
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--tinta);
  transition: color 0.3s var(--ease);
}

.proyecto__manta { position: absolute; inset: 0; z-index: 8; border-radius: var(--radio); }
.proyecto:hover .proyecto__ir { color: var(--marca-tinta); }
.proyecto__ir:focus-visible { outline: 2px solid var(--marca); outline-offset: 4px; }
.proyecto__marco img,
.proyecto__marco video { transition: filter 0.5s var(--ease); }
.proyecto:hover .proyecto__marco img,
.proyecto:hover .proyecto__marco video { filter: brightness(calc(var(--foto-brillo) * 1.12)); }
.proyecto--chico { width: min(26vw, 380px); margin-top: calc(6vh * var(--desfase)); }
.proyecto--medio { width: min(31vw, 460px); margin-top: calc(-6vh * var(--desfase)); }

.proyecto__marco {
  position: relative;
  /* El marco es decoración: la foto se agranda al centrarse y el efecto
     le sube el z-index a 6 desde el guion, así que se pintaba por encima
     del enlace que cubre la ficha y el clic caía en la imagen. No se pelea
     por el apilamiento —el enlace va aún más arriba— y además se le quita
     el puntero para que ningún clic muera en la foto. */
  pointer-events: none;
  overflow: hidden;
  border-radius: var(--radio);
  aspect-ratio: 4 / 3;
  /* Sin fondo propio: la foto va a 124 % y con paralaje, y cualquier
     franja que quedara al descubierto se veía como un bloque claro
     pegado al borde de la ficha. */
  background: transparent;
}

.proyecto--chico .proyecto__marco { aspect-ratio: 4 / 5; }

/* La imagen es más ancha que el marco: al desplazarse en sentido
   contrario a la pista, la foto respira dentro de su ventana. */
.proyecto__marco img,
.proyecto__marco video {
  position: absolute;
  top: 0;
  left: -12%;
  width: 124%;
  height: 100%;
  object-fit: cover;
  filter: brightness(var(--foto-brillo));
}

.proyecto__meta {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2xs);
  font-family: var(--display);
  font-size: 0.62rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
}

.proyecto__meta span {
  padding: 0.3rem 0.65rem;
  border-radius: 100px;
  border: 1px solid var(--linea);
  color: var(--tinta-tenue);
}

.proyecto__meta .es-premio { border-color: var(--marca); color: var(--marca-tinta); }

.proyecto h3 { font-family: var(--display); font-size: var(--fs-h3); line-height: 1.1; letter-spacing: -0.02em; margin-top: var(--space-2xs); }
.proyecto p { font-size: 0.94rem; color: var(--tinta-suave); margin-top: var(--space-2xs); }

/* Los dos enlaces del cierre, del mismo tamaño: `justify-items: stretch`
   los estira a la columna, así que no miden lo que mide su texto. */
.proyectos__cierre { flex: none; width: min(26ch, 22vw); display: grid; gap: var(--space-sm); align-content: center; justify-items: stretch; }
.proyectos__cierre .btn { justify-content: space-between; width: 100%; }

/* ============================================================
   6 · Marcas
   ============================================================ */

.marcas { gap: var(--flow-lg); align-items: center; }
.marcas__intro { flex: none; width: min(32ch, 28vw); }
.marcas__intro .btn { margin-top: var(--flow-md); }

/* Tres columnas que se desplazan en sentidos alternos */
.rejilla-logos { display: flex; gap: var(--flow-sm); height: min(var(--util), 640px); overflow: hidden; }
.rejilla-logos__col { display: grid; gap: var(--space-md); align-content: start; }

/* Sin caja: 34 rectángulos redondeados no aportaban nada que el aire
   no resuelva, y sumaban al cuarto panel consecutivo con la misma forma. */
/* Bloque con alto definido, no celda de rejilla: dentro de una celda el
   navegador trata la altura como indefinida y el `max-height: 100%` de la
   imagen no resuelve —el mismo tropiezo que ya hubo en la reja de
   Clientes—. Con alto fijo el `object-fit` sí encaja cada marca. */
.marca-logo {
  display: block;
  width: clamp(130px, 12vw, 178px);
  height: clamp(65px, 6vw, 89px);
  padding: var(--space-sm);
}

/* Contenido, no anchura: con `width: 100%` un logotipo cuadrado —Huawei,
   BMW, 3M— salía al doble de alto que uno apaisado y la reja parecía
   hecha de piezas de tamaños distintos. Encajado dentro de la caja 2:1
   todos ocupan lo mismo a ojo, que es el «mismo tratamiento» que pedía
   el documento. */
.marca-logo img {
  width: 100%;
  height: 100%;
  object-fit: contain;
  opacity: 0.72;
  transition: opacity 0.35s var(--ease), filter 0.35s var(--ease);
}

/* Los logos vienen en blanco: sobre papel hay que invertirlos */
[data-tema="claro"] .marca-logo img { filter: invert(1); opacity: 0.66; }

.marca-logo:hover img { opacity: 1; }

.testimonios { flex: none; width: min(34ch, 28vw); display: grid; gap: var(--flow-md); }

.testimonio p { font-size: 1.05rem; line-height: 1.5; color: var(--tinta); }
.testimonio footer {
  margin-top: var(--space-xs);
  display: flex;
  align-items: center;
  gap: var(--space-2xs);
  font-size: 0.78rem;
  letter-spacing: 0.06em;
  color: var(--tinta-tenue);
}
.testimonio footer i { width: 22px; height: 1px; background: var(--marca); flex: none; }

/* ============================================================
   7 · Proceso
   ============================================================ */

.proceso { gap: var(--flow-lg); align-items: center; }
.proceso__intro { flex: none; width: min(30ch, 26vw); }

/* Geometría del riel.
   Las seis tarjetas miden lo mismo a propósito: con altura fija, el
   punto de conexión cae SIEMPRE sobre el hilo. Con altura libre cada
   tarjeta lo dejaba en un sitio distinto. */
.ruta {
  /* Dos filas de tarjetas más el aire de cada lado tienen que caber en
     --util; si no caben, la altura de la tarjeta cede primero. */
  --paso-aire: 30px;
  --paso-h: min(226px, calc((var(--util) - var(--paso-aire) * 2) / 2));
  position: relative;
  display: flex;
  align-items: center;
  gap: var(--flow-md);
  /* Sin relleno propio: el aire de los puntos ya separa el hilo del
     borde, y sumar padding aquí rompía la cuenta de --util. */
  padding-block: 0;
}

/* El hilo que une los seis pasos, dibujado con el scroll */
.ruta__hilo {
  position: absolute;
  left: 0;
  right: 0;
  top: 50%;
  height: 2px;
  margin-top: -1px;
  background: var(--linea);
}

.ruta__hilo i {
  position: absolute;
  inset: 0;
  background: linear-gradient(90deg, var(--marca), var(--naranja));
  transform-origin: left center;
  transform: scaleX(0);
}

/* Sin caja: el hilo es la estructura. Seis tarjetas de la misma altura
   con el mismo borde eran el cuarto panel seguido con forma de
   rectángulo redondeado; la altura fija se queda porque de ella depende
   que el punto caiga exactamente sobre el hilo, pero ya no se ve. */
.paso {
  position: relative;
  flex: none;
  width: min(268px, 21vw);
  height: var(--paso-h);
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  gap: var(--space-md);
  padding-inline: 0 var(--flow-md);
}

/* El texto se recuesta contra el hilo y el numeral se va al extremo
   opuesto: arriba del hilo, texto abajo; debajo del hilo, texto arriba. */
.paso:nth-of-type(even) { flex-direction: column-reverse; }

/* of-type, no child: el hilo es el primer hijo de .ruta y correría
   la cuenta un lugar, dejando los seis pasos del mismo lado. */
.paso:nth-of-type(odd) { margin-bottom: calc(var(--paso-h) + var(--paso-aire) * 2); }
.paso:nth-of-type(even) { margin-top: calc(var(--paso-h) + var(--paso-aire) * 2); }

/* El punto sobre el hilo y la patita que lo une con la tarjeta */
.paso::before {
  content: "";
  position: absolute;
  left: 50%;
  width: 11px;
  height: 11px;
  margin-left: -5.5px;
  border-radius: 50%;
  background: var(--fondo);
  border: 2px solid var(--marca);
  z-index: 2;
}

.panel--alterno .paso::before { background: var(--fondo-2); }

.paso::after {
  content: "";
  position: absolute;
  left: 50%;
  width: 1px;
  height: var(--paso-aire);
  background: var(--linea-fuerte);
}

.paso:nth-of-type(odd)::before { bottom: calc(var(--paso-aire) * -1); transform: translateY(50%); }
.paso:nth-of-type(even)::before { top: calc(var(--paso-aire) * -1); transform: translateY(-50%); }
.paso:nth-of-type(odd)::after { bottom: calc(var(--paso-aire) * -1); }
.paso:nth-of-type(even)::after { top: calc(var(--paso-aire) * -1); }

/* Cada paso llevaba su mitad de pista en blanco: el numeral arriba y
   media pantalla de papel abajo. La fotografía ocupa ese hueco —del
   tamaño de la propia tarjeta, no una miniatura— y va absoluta para no
   tocar la cuenta de --paso-h de la que depende que el punto caiga
   sobre el hilo. */
.paso__foto {
  position: absolute;
  left: 0;
  right: var(--flow-md);
  height: var(--paso-h);
  margin: 0;
  border-radius: var(--radio);
  overflow: hidden;
  background: var(--fondo-3);
}

.paso:nth-of-type(odd) .paso__foto  { top: calc(100% + var(--paso-aire) * 2); }
.paso:nth-of-type(even) .paso__foto { bottom: calc(100% + var(--paso-aire) * 2); }

.paso__foto img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  filter: brightness(var(--foto-brillo)) saturate(0.94);
}

/* Un filete de marca en la esquina que mira al hilo, igual que en las
   fichas de proyecto: hilvana la fotografía con la línea del tiempo. */
.paso__foto::after {
  content: "";
  position: absolute;
  left: 0;
  width: 34%;
  height: 3px;
  background: var(--marca);
}

.paso:nth-of-type(odd) .paso__foto::after  { top: 0; }
.paso:nth-of-type(even) .paso__foto::after { bottom: 0; }

.paso__num {
  font-family: var(--display);
  font-size: clamp(2.2rem, 3.4vw, 3.4rem);
  line-height: 1;
  letter-spacing: 0.02em;
  color: var(--marca-tinta);
  opacity: 0.85;
}
.paso h3 { font-family: var(--display); font-size: 1.12rem; line-height: 1.15; margin-bottom: var(--space-2xs); }
.paso p { font-size: 0.9rem; color: var(--tinta-suave); }

/* ============================================================
   8 · Presencia
   ============================================================ */

.presencia { gap: var(--space-lg); align-items: center; }
.presencia__intro { flex: none; width: min(27ch, 19.5vw); }
.presencia__intro h2 {
  /* Más contenido: el titular ocupaba seis renglones y la columna
     entera medía 728 px contra 698 disponibles. */
  font-size: clamp(1.4rem, 2.2vw, 2.3rem);
  margin: var(--space-md) 0 var(--space-md);
}

.presencia__intro .lead { font-size: 0.95rem; }

/* La ficha de dirección, compacta */
.presencia .matriz { margin-top: var(--space-md); padding: var(--space-2xs) var(--space-sm); }
.presencia .matriz__pin { width: 34px; height: 34px; }
.presencia .matriz__pin svg { width: 16px; height: 16px; }
.presencia .matriz__dir { font-size: 0.82rem; line-height: 1.4; }

.mapa { flex: none; width: min(36.5vw, 580px); position: relative; }

/* Por encima de 1700 px sobra sitio de sobra: el mapa crece y con él
   el grosor real de rutas y contorno, que a 580 px quedaban en un hilo. */
@media (min-width: 1700px) {
  .mapa { width: min(34vw, 720px); }
}
.mapa svg { width: 100%; height: auto; overflow: visible; }

/* El contorno tiene que LEERSE: con 0.055 de relleno la silueta
   desaparecía y sólo quedaba la luz, que era justo el problema. */
.mapa__pais {
  fill: var(--tinta);
  fill-opacity: 0.09;
  stroke: var(--linea-fuerte);
  stroke-width: 2;
  stroke-linejoin: round;
}

/* La trama de puntos, recortada al país (ver mapaBase) */
.mapa__trama { fill: var(--marca); opacity: 0.2; }

/* El halo se queda cerca de su punto: con r=26 el de Mérida se salía
   de la península y volvía a leerse como mancha sobre el mar. */
.pin__halo { fill: var(--marca); opacity: 0.11; r: 17; }
.pin__punto { fill: var(--marca); }

.pin__label {
  font-family: var(--display);
  font-size: 20px;
  letter-spacing: 0.06em;
  fill: var(--tinta);
}

.pin__sub {
  font-family: var(--texto-font);
  font-size: 13px;
  letter-spacing: 0.16em;
  fill: var(--tinta-tenue);
}

/* La luz y la trama del mapa ya no viven aquí: se dibujan dentro del
   SVG recortadas al contorno de México (ver mapaBase en horizontal.js).
   Como rectángulos de CSS se veían como una mancha amarilla que se
   salía por la costa. */
.mapa--casa svg { position: relative; z-index: 1; }

/* Las rutas de la matriz a cada bodega */
.mapa__ruta {
  fill: none;
  stroke: var(--marca);
  stroke-width: 3.2;
  stroke-linecap: round;
  opacity: 0.95;
}

/* El trazo oscuro que va debajo: separa la ruta del país iluminado */
.mapa__ruta-base {
  fill: none;
  stroke: var(--negro-panel);
  stroke-width: 6.4;
  stroke-linecap: round;
  opacity: 0.3;
}

[data-tema="claro"] .mapa__ruta-base { stroke: var(--blanco); opacity: 0.55; }

[data-tema="claro"] .mapa__ruta { stroke: var(--marca-tinta); opacity: 0.85; }
[data-tema="claro"] .mapa__brillo { opacity: 0.6; }
[data-tema="claro"] .mapa__trama { opacity: 0.3; }

.ciudades { flex: none; width: min(22ch, 17vw); list-style: none; display: grid; gap: var(--space-2xs); }

/* La matriz se distingue del resto: es la única oficina */
.ciudades__matriz { border-bottom-color: var(--marca-tinta) !important; }
.ciudades__matriz em { color: var(--marca-tinta) !important; }

/* --- La dirección, como ficha ------------------------------- */
.matriz {
  margin-top: var(--flow-md);
  display: flex;
  align-items: center;
  gap: var(--space-md);
  padding: var(--space-sm) var(--space-md);
  border-radius: var(--radio);
  border: 1px solid var(--linea);
  background: var(--fondo-3);
  transition: border-color 0.3s var(--ease), transform 0.3s var(--ease);
}

.matriz:hover { border-color: var(--marca); transform: translateX(3px); }

.matriz__pin {
  flex: none;
  width: 40px;
  height: 40px;
  display: grid;
  place-items: center;
  border-radius: 50%;
  border: 1px solid var(--marca-tinta);
  color: var(--marca-tinta);
}

.matriz__pin svg { width: 19px; height: 19px; }

.matriz__cuerpo { display: grid; gap: 2px; }

/* `> b` y no `b`: dentro de la ficha hay más negritas —los metros
   cuadrados— y con el selector suelto salían en versalitas amarillas
   como si fueran otro rótulo. */
.matriz__cuerpo > b {
  font-family: var(--display);
  font-size: var(--fs-micro);
  letter-spacing: 0.22em;
  text-transform: uppercase;
  color: var(--marca-tinta);
}

/* La ficha absorbió la fila de Ciudad de México, que decía lo mismo
   justo debajo. Con ella entran la ciudad, el detalle de las oficinas y
   la superficie de bodega: cada dato una sola vez, en un solo sitio. */
.matriz__ciudad {
  font-family: var(--display);
  font-size: 1.02rem;
  line-height: 1.2;
  color: var(--tinta);
}

.matriz__dir { font-size: 0.86rem; line-height: 1.35; color: var(--tinta-suave); }
.matriz__detalle { font-size: 0.86rem; line-height: 1.35; color: var(--tinta-suave); }
.matriz__area { font-size: 0.86rem; color: var(--tinta-tenue); }
.matriz__area em {
  font-family: var(--display);
  font-style: normal;
  color: var(--tinta);
  margin-right: 0.4em;
}

/* Con seis renglones dentro, el alfiler centrado quedaba a media
   dirección: se alinea con el rótulo, que es donde empieza la ficha. */
.matriz { align-items: flex-start; }
.matriz__pin { margin-top: 2px; }

/* La ficha manda sobre el punto de Ciudad de México en el mapa, igual
   que las filas mandan sobre el suyo. */
.matriz.is-activa { border-color: var(--marca); }
.matriz.is-activa .matriz__ciudad { color: var(--marca-tinta); }

.matriz__ir {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  font-size: 0.76rem;
  letter-spacing: 0.06em;
  color: var(--tinta-tenue);
}

.matriz:hover .matriz__ir { color: var(--marca-tinta); }

.ciudades li {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: var(--space-sm);
  padding-block: var(--space-2xs);
  border-bottom: 1px solid var(--linea);
  font-family: var(--display);
  font-size: 0.98rem;
  letter-spacing: 0.02em;
}

.ciudades em { font-family: var(--texto-font); font-style: normal; font-size: 0.76rem; color: var(--tinta-tenue); letter-spacing: 0.08em; text-transform: uppercase; }

.cifra { margin-top: var(--flow-md); }
.cifra b { display: block; font-family: var(--display); font-size: clamp(1.8rem, 3vw, 2.8rem); line-height: 1; color: var(--marca-tinta); }
.cifra span { font-size: 0.84rem; color: var(--tinta-tenue); }

/* ============================================================
   9 · Cierre
   ============================================================ */

.cierre { padding-block: 0; }

/* Misma razón que en .hero__media: la caja recorta, la foto desborda. */
/* Fondo negro debajo del vídeo: si alguna vez se cuela medio píxel por
   el redondeo del recorte, lo que asoma es negro y no una imagen. */
.cierre__media { position: absolute; inset: 0; overflow: hidden; z-index: 0; background: var(--negro-panel); }

/* El vídeo mide EXACTAMENTE su caja. Antes sobresalía un 12 % por cada
   lado —hueco para un parallax que se retiró— y, al llevar `filter`, el
   navegador lo pinta en su propia capa: el recorte de esa capa se
   redondea a píxeles enteros por su cuenta y el velo, que medía otra
   cosa, redondeaba distinto. Entre los dos bordes quedaba la columna de
   vídeo sin velar que reportó el cliente. */
.panel .cierre__media > img,
.panel .cierre__media > video { position: absolute; top: 0; left: 0; max-width: none; width: 100%; height: 100%; }
.cierre__media video,
.cierre__media img { width: 100%; height: 100%; object-fit: cover; filter: brightness(calc(var(--foto-brillo) * 0.5)); }

.cierre__velo {
  position: absolute;
  /* 2 px de sangrado, no 0: con `inset: 0` el borde del velo y el
     recorte de la foto caen en píxeles distintos al estar el panel
     en una posición fraccionaria, y asoma una línea de foto sin
     velo. El panel recorta, así que el sangrado no se ve. */
  inset: -2px;
  z-index: 1;
  background: linear-gradient(90deg, rgb(var(--velo) / 0.94) 0%, rgb(var(--velo) / 0.7) 55%, rgb(var(--velo) / 0.5) 100%);
}

/* El trazo iba a `right: -6vw`, o sea 6 vw FUERA del panel, y el panel
   recorta: el logotipo aparecia cortado al final de todas las secciones.
   El cliente lo reporto dos veces. Ahora entra entero; es una marca de
   agua al 10 % detras del contenido, asi que solaparse con la columna
   de datos no estorba. */
.cierre__anillo {
  position: absolute;
  right: clamp(1.5rem, 3vw, 4rem);
  top: 50%;
  z-index: 1;
  width: min(52vh, 460px);
  height: auto;
  translate: 0 -50%;
  fill: var(--marca);
  opacity: 0.1;
}

.cierre__inner { position: relative; z-index: 2; width: min(56ch, 46vw); }
.cierre__inner h2 { font-size: clamp(2rem, 3.8vw, 3.8rem); margin: var(--flow-sm) 0 var(--flow-md); }
.cierre__acciones { display: flex; flex-wrap: wrap; gap: var(--space-sm); margin-top: var(--flow-md); }

.cierre__datos {
  position: relative;
  z-index: 2;
  flex: none;
  width: min(30ch, 24vw);
  display: grid;
  gap: var(--flow-md);
  align-self: center;
  margin-inline-start: var(--flow-xl);
  /* Sitio reservado para el WhatsApp flotante y la fila de redes: se
     ponían encima de la última línea de datos. */
  padding-bottom: 3.5rem;
}

.cierre__bloque h3 {
  font-family: var(--display);
  font-size: 0.72rem;
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: var(--marca-tinta);
  margin-bottom: var(--space-2xs);
}

.cierre__bloque p { color: var(--tinta-suave); font-size: 0.94rem; }
.cierre__bloque a {
  display: flex;
  align-items: center;
  min-height: 44px;
  color: var(--tinta-suave);
  font-size: 0.94rem;
}
.cierre__bloque a:hover { color: var(--tinta); }

.cierre__legal { font-size: 0.78rem; color: var(--tinta-tenue); border-top: 1px solid var(--linea); padding-top: var(--space-sm); }

/* ============================================================
   Navegador de puntos
   ============================================================ */

.puntos {
  position: fixed;
  left: 50%;
  bottom: var(--space-md);
  z-index: var(--z-flotante);
  translate: -50% 0;
  display: flex;
  align-items: center;
  gap: var(--space-2xs);
  padding: 0.4rem;
  border-radius: 100px;
  border: 1px solid var(--linea);
  background: var(--vidrio);
  backdrop-filter: blur(18px) saturate(150%);
  box-shadow: 0 10px 34px rgba(0, 0, 0, 0.35);
}

.puntos__flecha {
  width: 38px;
  height: 38px;
  display: grid;
  place-items: center;
  border-radius: 100px;
  color: var(--tinta-suave);
  transition: color 0.3s var(--ease), background-color 0.3s var(--ease);
}

.puntos__flecha:hover:not(:disabled) { color: var(--tinta); background: var(--linea); }
.puntos__flecha:disabled { opacity: 0.3; cursor: default; }
.puntos__flecha svg { width: 15px; height: 15px; }

.puntos__lista { display: flex; align-items: center; gap: 2px; }

/* El punto: 34px de caja táctil, 12px de círculo visible.
   La caja grande es lo que hace que se pueda picar en un teléfono. */
.punto {
  position: relative;
  width: 38px;
  height: 38px;
  display: grid;
  place-items: center;
  border-radius: 100px;
}

.punto::before {
  content: "";
  width: 13px;
  height: 13px;
  border-radius: 50%;
  border: 1.5px solid var(--tono);
  background: transparent;
  transition: background-color 0.4s var(--ease), transform 0.4s var(--ease);
}

.punto:hover::before { background: var(--tono); transform: scale(1.15); }
.punto.is-activo::before { background: var(--tono); transform: scale(1.25); }

/* La etiqueta del punto aparece al pasar encima: sin ella, ocho
   círculos de colores no le dicen nada a nadie. */
.punto__nombre {
  position: absolute;
  bottom: calc(100% + 10px);
  left: 50%;
  translate: -50% 0;
  padding: 0.3rem 0.6rem;
  border-radius: 100px;
  background: var(--tinta);
  color: var(--fondo);
  font-family: var(--display);
  font-size: 0.6rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  white-space: nowrap;
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.25s var(--ease), translate 0.25s var(--ease);
}

.punto:hover .punto__nombre,
.punto:focus-visible .punto__nombre { opacity: 1; translate: -50% -3px; }

/* ============================================================
   Control del video de fondo
   WCAG 2.2.2: movimiento automático de más de cinco segundos necesita
   un mecanismo para detenerlo. Sólo aparece cuando hay video debajo.
   ============================================================ */

.video-btn[hidden] { display: none; }

.video-btn {
  position: fixed;
  left: var(--space-md);
  bottom: var(--space-md);
  z-index: var(--z-flotante);
  display: inline-flex;
  align-items: center;
  gap: var(--space-2xs);
  min-height: 44px;
  padding: 0 var(--space-md) 0 var(--space-sm);
  border-radius: 100px;
  border: 1px solid rgba(255, 255, 255, 0.22);
  background: rgba(10, 10, 9, 0.72);
  backdrop-filter: blur(14px);
  color: var(--blanco);
  font-family: var(--display);
  font-size: 0.68rem;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  opacity: 0;
  visibility: hidden;
  transform: translateY(8px);
  transition: opacity 0.35s var(--ease), transform 0.35s var(--ease), visibility 0.35s;
}

/* Sólo en los paneles que de verdad llevan video: en los demás el
   botón prometía pausar algo que no se estaba moviendo. */
.con-video .video-btn { opacity: 1; visibility: visible; transform: translateY(0); }

.video-btn svg { width: 15px; height: 15px; flex: none; }
.video-btn .play { display: none; }
.video-btn.is-pausado .pausa { display: none; }
.video-btn.is-pausado .play { display: block; }
.video-btn:hover { border-color: var(--marca); color: var(--marca); }

/* ============================================================
   WhatsApp flotante
   ============================================================ */

.wa-flotante {
  position: fixed;
  right: var(--space-md);
  bottom: var(--space-md);
  z-index: var(--z-flotante);
  width: 52px;
  height: 52px;
  display: grid;
  place-items: center;
  border-radius: 100px;
  background: var(--wa);
  color: var(--wa-tinta);
  box-shadow: 0 10px 28px rgba(0, 0, 0, 0.4);
  transition: transform 0.35s var(--ease);
}

.wa-flotante:hover { transform: scale(1.08); }
.wa-flotante svg { width: 26px; height: 26px; }

/* ============================================================
   Estados iniciales de animación
   ============================================================ */

.js [data-fade] { opacity: 0; transform: translateY(26px); }

/* --- El panel de apertura no espera al guion ---------------------
   Es el único que ya está en pantalla al abrir, así que ocultarlo no
   escalona nada: retrasa. Las fotografías se ven desde el primer
   fotograma —son las que mide el navegador como elemento mayor— y el
   resto se enciende solo a los dos segundos por si el guion tarda.
   Medido en 3G: el elemento mayor de Nosotros pasa de 6,1 s a 3,2. */
.js .panel:first-of-type figure[data-fade],
.js .panel:first-of-type [data-fade] > img,
.js .hero figure[data-fade] { opacity: 1; transform: none; }

.js .panel:first-of-type [data-fade],
.js .hero [data-fade] { animation: enciende-solo 1ms linear 2s forwards; }

@keyframes enciende-solo { to { opacity: 1; transform: none; } }
.js [data-anim] .linea-inner,
.js [data-anim] .palabra-inner { display: inline-block; }

/* El recorte que esconde la palabra mientras sube le comería la cola a
   la «g» y a la «j»: se le da aire abajo y se descuenta con un margen
   negativo, así que la línea base no se mueve. */
.js [data-anim] .linea { padding-bottom: 0.14em; margin-bottom: -0.14em; }

/* ============================================================
   Pantallas bajas (portátiles de 1366×768 y similares)
   Todas las medidas verticales del recorrido salen de vh, así que se
   encogen a la vez. Abajo de 820 px de alto se apagan los desfases y el
   riel del proceso pasa a una sola fila.
   ============================================================ */

@media (min-width: 900px) and (max-height: 820px) {
  /* La mitad del desfase: se nota el escalonado, no empuja nada fuera */
  :root { --desfase: 0.3; }

  /* Los proyectos encogen y el marco deja de mandar: su alto sale de
     --util para que el texto de abajo siempre quepa. */
  .proyecto { width: min(30vw, 430px); }
  .proyecto--chico { width: min(21vw, 300px); }
  .proyecto--medio { width: min(25vw, 360px); }

  .proyecto__marco,
  .proyecto--chico .proyecto__marco {
    aspect-ratio: auto;
    height: calc(var(--util) * 0.48);
  }

  .hero__titulo { font-size: clamp(2.2rem, 4.2vw, 4.2rem); }

  .hero { padding-block: clamp(5rem, 9vh, 7rem) clamp(5.5rem, 10vh, 8rem); }
  .hero__prueba { margin-top: var(--flow-md); }
}

/* ============================================================
   Móvil y tablet: el recorrido se endereza
   Abajo de 900px el scroll horizontal pelea con el gesto natural
   del pulgar. La misma historia, apilada.
   ============================================================ */

@media (max-width: 899px) {
  /* Un solo interruptor apaga todos los escalonados del recorrido */
  :root { --desfase: 0; }

  .escenario, .pista, .panel { height: auto; }
  .escenario { overflow: visible; }
  .pista { display: block; }

  /* El carril de redes y el WhatsApp flotan sobre la esquina inferior:
     el último panel reserva su sitio para no acabar debajo de ellos. */
  .pista > .panel:last-child { padding-bottom: calc(var(--pad-b) + 3.5rem); }

  .panel {
    width: 100%;
    min-width: 0;
    min-height: auto;
    display: block;
    padding: var(--flow-xl) var(--gutter);
    /* Al saltar a una sección, el rótulo no se esconde bajo el header */
    scroll-margin-top: 6rem;
  }

  /* El primero empieza por debajo del encabezado, que en teléfono flota
     encima. Con el texto ampliado el encabezado envuelve a dos filas y
     `--alto-cab` —que lo mide el guion— es lo único que lo sabe. */
  .pista > .panel:first-child,
  .pista > .hero:first-child {
    padding-top: max(var(--flow-xl), calc(var(--alto-cab, 5rem) + 1.4rem));
  }

  .hero, .cierre {
    min-height: 100svh;
    display: flex;
    flex-direction: column;
    justify-content: center;
    align-items: stretch;
    gap: var(--flow-lg);
    padding-block: clamp(6.5rem, 15vh, 9rem) var(--flow-xl);
  }

  /* Todo lo que en el recorrido lateral tiene ancho de columna, aquí
     ocupa el renglón completo. */
  .esencia__texto,
  .servicios__intro,
  .porque__intro,
  .proyectos__intro,
  .marcas__intro,
  .proceso__intro,
  .presencia__intro,
  .proyectos__cierre,
  .testimonios,
  .ciudades,
  .mapa,
  .ancla,
  .cierre__inner,
  .cierre__datos { width: 100%; max-width: none; margin-inline-start: 0; }

  .hero__inner, .cierre__inner { width: 100%; }
  .hero__inner { max-width: none; }
  .cue { display: none; }
  .panel__folio { display: none; }
  .cierre__datos { gap: var(--flow-md); }

  /* En teléfono el velo del encabezado es un poco más denso: el menú
     comparte franja con el logotipo y el botón. */
  .header::before { height: 150%; background: linear-gradient(180deg, var(--fondo) 12%, transparent 100%); opacity: 0.92; }

  /* --- Esencia --- */
  .placas { flex-wrap: wrap; margin-top: var(--flow-lg); gap: var(--space-sm); }
  .placa { width: calc(50% - var(--space-sm)); }
  .placa--a { width: 100%; aspect-ratio: 4 / 3; }
  .placa--grupo { width: 100%; aspect-ratio: 1800 / 669; }

  /* --- Por qué Enso: la foto ancla recupera su ancho --- */
  .ancla { height: min(58vh, 420px); margin-top: var(--flow-lg); }
  .razones { display: block; margin-top: var(--flow-lg); }

  /* Los tres selectores repetidos no son adorno: :nth-child(even) y
     :nth-child(3n) pesan más que .razon y se comían el relleno. */
  .razon,
  .razon:nth-child(even),
  .razon:nth-child(3n) {
    width: 100%;
    padding: var(--flow-md) 0 0;
    border-left: 0;
    border-top: 1px solid var(--linea);
  }

  .razon:first-child { border-top: 0; padding-top: 0; }
  .razon__indice { margin-bottom: var(--space-2xs); }

  /* --- Servicios --- */
  .mosaico {
    grid-auto-flow: row;
    grid-template-rows: none;
    grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
    grid-auto-columns: auto;
    height: auto;
    margin-top: var(--flow-lg);
  }

  .servicio { min-height: 300px; }
  .servicio--alto { grid-row: auto; }

  /* --- Proyectos --- */
  .galeria { flex-wrap: wrap; margin-top: var(--flow-lg); }
  .proyecto { width: 100%; }
  .proyecto__marco,
  .proyecto--chico .proyecto__marco { aspect-ratio: 4 / 3; height: auto; }

  /* Sin recorrido lateral no hay parallaje: la foto vuelve a su marco */
  .proyecto__marco img,
  .proyecto__marco video { left: 0; width: 100%; }
  .panel .hero__media > img, .panel .hero__media > video,
  /* Ya no hace falta devolverlo al 100 %: no sobresale en ningún tamaño. */

  /* --- Clientes --- */
  .rejilla-logos {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(120px, 1fr));
    height: auto;
    margin-block: var(--flow-lg);
  }
  .rejilla-logos__col { display: contents; }
  .marca-logo { width: 100%; }

  /* --- Proceso: sin riel, los seis pasos son una lista ---
     La altura fija y la dirección invertida existen para que el punto
     caiga sobre el hilo; sin hilo sólo dejaban el numeral a 300 px de su
     propio texto y, en los pares, debajo de él. */
  .ruta { display: block; margin-top: var(--flow-lg); }
  .ruta__hilo { display: none; }

  .paso__foto {
    position: static;
    height: clamp(150px, 34vw, 240px);
    margin-top: var(--space-md);
  }

  /* Los tres selectores otra vez: :nth-of-type pesa más que .paso y
     dejaba el margen de 286 px que separa las tarjetas del riel. */
  .paso,
  .paso:nth-of-type(odd),
  .paso:nth-of-type(even) {
    width: 100%;
    height: auto;
    flex-direction: column;
    gap: var(--space-2xs);
    margin: 0 0 var(--flow-lg);
    padding: var(--flow-md) 0 0;
    border-top: 1px solid var(--linea);
  }

  .paso:first-of-type { border-top: 0; padding-top: 0; }
  .paso::before, .paso::after { display: none; }

  /* --- Cierre --- */
  /* En vertical se centra en lugar de salirse: cortado se veia igual de
     mal que en escritorio. */
  .cierre__anillo { opacity: 0.06; right: auto; left: 50%; translate: -50% -50%; }

  .puntos { display: none; }

  /* ============================================================
     Segunda pasada de móvil: que se vea diseñado, no apilado
     ============================================================ */

  /* --- Tipografía. En una columna de 350 px, el titular del recorrido
     lateral se vuelve un muro de cuatro renglones gigantes. --- */
  :root {
    --fs-hero: clamp(2.2rem, 11vw, 3.1rem);
    --fs-h2: clamp(1.65rem, 7.6vw, 2.2rem);
    --fs-lead: 1.02rem;
  }

  /* balance reparte las líneas para que midan lo mismo; en una columna
     angosta eso abre huecos entre palabras. pretty sólo evita la palabra
     huérfana, que es lo único que hace falta aquí. */
  .display { text-wrap: pretty; }

  .eyebrow { letter-spacing: 0.2em; }
  .eyebrow::before { width: var(--space-sm); }

  /* --- Ritmo entre secciones: sin el fondo alterno del escritorio, los
     nueve paneles se leían como un solo bloque interminable. --- */
  .panel { padding-block: var(--flow-2xl); }
  .panel + .panel { border-top: 1px solid var(--linea); }
  .panel--alterno { background: var(--fondo-2); }

  /* --- Hero y cierre: el velo del recorrido lateral corre de izquierda
     a derecha. En vertical hay que taparlo de arriba abajo. --- */
  .hero__velo {
    background:
      linear-gradient(180deg, rgb(var(--velo) / 0.86) 0%, rgb(var(--velo) / 0.68) 32%,
                      rgb(var(--velo) / 0.8) 66%, rgb(var(--velo) / 0.95) 100%);
  }

  .cierre__velo {
    background: linear-gradient(180deg, rgb(var(--velo) / 0.8) 0%, rgb(var(--velo) / 0.9) 45%,
                                rgb(var(--velo) / 0.97) 100%);
  }

  .hero__acciones,
  .cierre__acciones { display: grid; gap: var(--space-sm); }
  .hero__acciones .btn,
  .cierre__acciones .btn { justify-content: center; }

  .hero__prueba { margin-top: var(--flow-md); }

  /* --- Servicios: la foto arriba, el texto abajo sobre fondo sólido.
     Con el texto encima de la fotografía cada tarjeta dependía de que el
     degradado tapara justo la zona correcta, y en formato ancho no lo
     hacía: el texto caía sobre las luces del escenario. --- */
  .mosaico { grid-template-columns: 1fr; gap: var(--flow-md); }

  .servicio {
    min-height: 0;
    display: grid;
    grid-template-rows: auto 1fr;
    background: var(--fondo-2);
    border: 1px solid var(--linea);
  }

  .panel--alterno .servicio { background: var(--fondo-3); }

  .servicio img {
    position: relative;
    inset: auto;
    width: 100%;
    height: auto;
    aspect-ratio: 16 / 10;
    filter: brightness(var(--foto-brillo)) saturate(1);
  }

  .servicio::after { display: none; }

  .servicio__cuerpo {
    display: grid;
    gap: var(--space-2xs);
    align-content: start;
    padding: var(--space-md);
    color: var(--tinta);
  }

  .servicio p { color: var(--tinta-suave); }
  .servicio .link-flecha { color: var(--tinta); justify-self: start; }

  /* --- Clientes: tres columnas y caja de alto fijo. Con dos columnas y
     alto libre, un logo cuadrado como BMW medía el triple que uno
     apaisado y la reja se veía descuadrada. --- */
  /* minmax(0, 1fr), no 1fr: una columna 1fr no baja del ancho mínimo de
     su contenido, y las tres sumaban 430 px en una pantalla de 350. */
  .rejilla-logos {
    grid-template-columns: repeat(3, minmax(0, 1fr));
    gap: var(--space-md) var(--space-sm);
  }

  /* Alto fijo, no aspect-ratio: con aspect-ratio la caja se dimensiona
     por el contenido y una imagen alta (BMW, Huawei, W Hotels) crecía
     al triple que una apaisada. */
  .marca-logo {
    height: 84px;
    padding: var(--space-2xs);
    display: grid;
    place-items: center;
  }

  .marca-logo img {
    width: auto;
    height: auto;
    max-width: 100%;
    max-height: 100%;
    object-fit: contain;
  }

  .proyectos__cierre {
    margin-top: var(--flow-lg);
    padding-top: var(--flow-md);
    border-top: 1px solid var(--linea);
    gap: var(--flow-md);
  }

  .proyectos__cierre .btn { justify-self: start; }

  .testimonios { margin-top: var(--flow-lg); gap: var(--flow-lg); }
  .testimonio p { font-size: 1rem; }

  .mapa { margin-block: var(--flow-md); }
  .ciudades li { padding-block: var(--space-xs); }
  .cifra { margin-top: var(--flow-lg); }

  .cierre__datos { padding-top: var(--flow-md); border-top: 1px solid var(--linea); }
  .cierre__bloque a { min-height: 48px; }

  /* --- Controles flotantes --- */
  .wa-flotante { width: 56px; height: 56px; right: var(--space-sm); bottom: var(--space-sm); }
  .video-btn { display: none; }
}

@media (prefers-reduced-motion: reduce) {
  .js [data-fade] { opacity: 1 !important; transform: none !important; }
  * { animation-duration: 0.001ms !important; transition-duration: 0.001ms !important; }
  .cue i::after { display: none; }
}


/* ------------------------------------------------------------
   Teselas del revelado de fichas (recurso 53 adaptado). Nueve
   tapas del color del panel que se retiran en orden aleatorio.
   Se destruyen al terminar: no dejan nodos vivos.
   ------------------------------------------------------------ */
.teselas {
  position: absolute;
  inset: 0;
  z-index: 4;
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-template-rows: repeat(3, 1fr);
  pointer-events: none;
}

.teselas b { display: block; background: var(--fondo); }

.panel--alterno .teselas b { background: var(--fondo-2); }
.panel--claro .teselas b { background: var(--fondo); }


/* --- Fondo de marca: resplandor y trama --------------------------
   El panel era una plancha lisa. Mismo recurso del mapa y de Nosotros.
   El contenido sube a z-index 2 para quedar por encima. --- */
.proceso::before,
.proceso::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
}

.proceso::before { background: radial-gradient(52% 60% at 60% 50%, rgb(235 219 0 / 0.10) 0%, rgb(235 219 0 / 0) 66%); }

.proceso::after {
  background-image: radial-gradient(currentColor 1px, transparent 1px);
  background-size: 30px 30px;
  color: var(--marca);
  opacity: 0.11;
  mask-image: radial-gradient(58% 62% at 60% 50%, #000 0%, transparent 74%);
  -webkit-mask-image: radial-gradient(58% 62% at 60% 50%, #000 0%, transparent 74%);
}

.proceso > *:not(.panel__folio, .deco) { position: relative; z-index: 2; }

@media (max-width: 899px) {
  .proceso::before, .proceso::after { display: none; }
}


/* ------------------------------------------------------------
   Persianas: siete lamas que descubren el metraje de portada y
   de cierre (efecto 05 del Vol.03). Se destruyen al terminar.
   ------------------------------------------------------------ */
.persianas {
  position: absolute;
  inset: 0;
  z-index: 3;
  display: grid;
  grid-template-columns: repeat(7, 1fr);
  pointer-events: none;
}

.persianas b { display: block; background: #050505; }

[data-tema="claro"] .persianas b { background: #f3f2ee; }

/* Las letras del remate llegan dispersas y se arman */
.caracter { display: inline-block; will-change: transform, filter; }

/* ============================================================
   Titulares de sección — un solo sistema
   ------------------------------------------------------------
   El cliente lo pidió con estas palabras: "homologar el diseño de
   títulos y subtítulos, en cada lado es diferente". Y tenía razón:
   cada panel traía su propio clamp —nueve tamaños distintos para el
   mismo nivel de jerarquía— porque cada uno se escribió el día que
   se armó ese panel. Aquí queda uno.

   Las excepciones son deliberadas y siguen abajo, con su nombre:
   la portada del Home, las declaraciones del credo y el remate.
   ============================================================ */
.panel :is(h1, h2).display {
  font-size: var(--fs-h2);
  margin: var(--flow-sm) 0 var(--flow-md);
}


/* Excepciones con nombre.

   Ojo con el peso: la regla de arriba usa `:is(h1, h2)`, que NO baja la
   especificidad de sus argumentos, así que vale (0,2,1). Una excepción
   de dos clases pierde. De ahí que estas lleven la clase del panel
   delante: hacen (0,3,0) y (0,3,1).

   Y declaran su tamaño, no lo heredan: `font-size: inherit` toma el del
   padre —que aquí es el texto corriente—, no el que la hoja define para
   el componente. */
.panel.hero .hero__titulo {
  font-size: var(--fs-hero);
  margin: var(--flow-sm) 0 var(--flow-md);
}

.panel.cierre .cierre__inner h2 {
  font-size: clamp(2rem, 3.8vw, 3.8rem);
  margin: var(--flow-sm) 0 var(--flow-md);
}

/* ------------------------------------------------------------
   Redes sociales · fila a la izquierda del WhatsApp flotante
   No van encima ni debajo: arriba está la indicación de scroll y
   debajo el borde de la pantalla. A la izquierda hay sitio libre en
   todas las páginas.
   ------------------------------------------------------------ */
.social {
  position: fixed;
  right: calc(var(--gutter) + 68px);
  bottom: calc(var(--gutter) - 4px);
  z-index: 45;
  display: flex;
  align-items: center;
  gap: var(--space-2xs);
}

/* 44 px, no 38: la norma AA pide 24 y ya se cumplía, pero el nivel
   recomendado son 44 y aquí sobra sitio. */
.social__ir {
  display: grid;
  place-items: center;
  width: 44px;
  height: 44px;
  border-radius: 50%;
  border: 1px solid var(--linea-fuerte);
  background: var(--vidrio);
  backdrop-filter: blur(10px);
  color: var(--tinta);
  transition: border-color 0.25s var(--ease), color 0.25s var(--ease),
              transform 0.25s var(--ease);
}

.social__ir svg { width: 17px; height: 17px; }

.social__ir[href]:hover {
  border-color: var(--marca);
  color: var(--marca-tinta);
  transform: translateY(-2px);
}

.social__ir[href]:focus-visible { outline: 2px solid var(--marca); outline-offset: 3px; }

@media (max-width: 899px) {
  .social {
    right: auto;
    left: var(--gutter);
    bottom: calc(var(--gutter) - 4px);
    gap: 6px;
  }
  .social__ir { width: 44px; height: 44px; }
  .social__ir svg { width: 16px; height: 16px; }
}

/* La fila de redes ocupa la esquina inferior derecha, justo donde estaba
   la indicación de scroll. Subirla dejaba de solaparse con las redes
   pero caía sobre la última tarjeta de las galerías de casos —medido en
   seis páginas—. Ahora comparte franja con ellas, a su izquierda: es la
   única banda que está libre en todas las páginas.

   El ancho de la fila de redes se declara una vez; son tres botones de
   44 con dos huecos entre medias. */
:root { --fila-social: calc(3 * 44px + 2 * var(--space-2xs)); }

.cue {
  bottom: calc(var(--gutter) - 4px);
  right: calc(var(--gutter) + 68px + var(--fila-social) + var(--space-md));
}

@media (max-width: 899px) {
  .cue { bottom: calc(var(--space-2xl) + 1.4rem); }
}

/* ------------------------------------------------------------
   El velo del cierre pasa a ser hijo de la caja de la foto
   ------------------------------------------------------------
   Era hermano: la foto la recortaba su caja y el velo lo recortaba el
   panel. Dos recortes distintos sobre la misma junta y, en las
   posiciones fraccionarias del recorrido, una columna de foto sin
   velar: la línea clara de altura completa que reportó el cliente.

   Como pseudo-elemento de la caja, velo y foto se componen DENTRO del
   mismo recorte y el panel corta algo ya mezclado. La regla: dentro de una caja que recorta, el velo tiene que medir
   exactamente lo que la foto —ni un píxel de sangrado—.
   ------------------------------------------------------------ */
.cierre__velo { display: none; }

.cierre__media::after {
  content: "";
  position: absolute;
  /* Un píxel de sangrado: la caja recorta, así que no se ve, pero
     asegura que el velo cubre el rectángulo redondeado ENTERO. Con
     `inset: 0` el velo y el vídeo redondean por separado y podía
     asomar una hebra de vídeo sin velar. */
  inset: -1px;
  z-index: 1;
  background: linear-gradient(90deg, rgb(var(--velo) / 0.94) 0%, rgb(var(--velo) / 0.7) 55%, rgb(var(--velo) / 0.5) 100%);
}

@media (max-width: 899px) {
  .cierre__media::after {
    background: linear-gradient(180deg, rgb(var(--velo) / 0.8) 0%, rgb(var(--velo) / 0.9) 45%, rgb(var(--velo) / 0.97) 100%);
  }
}

/* ------------------------------------------------------------
   Fuera la barra de puntos
   El cliente: «la barra de abajo estorba mucho, la podemos quitar».
   Se oculta en lugar de borrarla del HTML porque su código es también
   quien invierte el header sobre paneles claros u oscuros y quien
   anuncia la sección al lector de pantalla. Oculta con `display: none`
   sale del orden de tabulación, y el teclado sigue teniendo las
   flechas izquierda/derecha para recorrer los paneles.
   ------------------------------------------------------------ */
.puntos { display: none; }

/* Sin la barra, el resto de flotantes puede bajar a su sitio natural. */
.video-btn { bottom: calc(var(--gutter) - 4px); }

/* La indicación va fija a la ventana, así que puede caer sobre lo que
   sea: en las páginas de servicio aterriza encima de una tarjeta de
   proyecto oscura y, con la tinta del panel claro, desaparecía. Lleva
   su propio fondo, como el botón de WhatsApp o los iconos de redes. */
.cue--fija {
  padding: 0.55rem var(--space-sm);
  border-radius: 100px;
  border: 1px solid var(--linea);
  background: var(--vidrio);
  backdrop-filter: blur(10px);
}

/* La indicación se queda en dos palabras y una flecha: fuera la rueda
   de ratón y la coletilla, como pidió el cliente. */
.cue__rueda { display: none; }
.cue__texto { display: block; text-align: right; }
.cue__texto b { display: none; }
.cue--scroll { gap: var(--space-xs); letter-spacing: 0.2em; }


/* ============================================================
   Elementos de identidad en los fondos
   ------------------------------------------------------------
   Recursos de marca —líneas, galones, tramas de puntos, medias lunas—
   en las orillas de los paneles oscuros que no llevan fotografía. Muy
   tenues y DETRÁS del contenido: el panel se aísla para que el
   `z-index: -1` caiga sobre su propio fondo y no lo atraviese.
   ============================================================ */

.con-deco { isolation: isolate; }

/* Los paneles que sacan a sus hijos del fondo con
   `> *:not(.panel__folio)` ponían el elemento de marca en `relative`:
   volvía al flujo, sumaba una columna al panel y `left/top` pasaban a
   contarse desde su sitio en la fila. Aquí se asegura, con más peso que
   esas reglas, que siempre está fuera del flujo. */
.panel > .deco { position: absolute; }

/* Sobre fotografía: por delante del velo, por detrás del contenido.
   Con `.deco--encima` a secas perdía contra el `z-index: -1` de `.deco`,
   que va después en la hoja: misma especificidad, gana el último. */
.panel > .deco--encima { z-index: 1; }

.deco {
  position: absolute;
  z-index: -1;
  pointer-events: none;
  /* El tamaño lo pone `decorado()` en línea: depende de la proporción
     real de cada dibujo, y en un cuadrado las cruces y los galones
     salían diminutos. Esto es sólo el respaldo si el JS no corre. */
  width: clamp(104px, 13vw, 215px);
  height: auto;
  aspect-ratio: 1;
  /* Máscara, no imagen: el color sale de la tinta del propio panel, así
     que el mismo archivo vale en oscuro y en claro. Y al ser vector no
     hay tamaño al que se vea pixelado. */
  background-color: currentColor;
  -webkit-mask-image: var(--deco);
  mask-image: var(--deco);
  -webkit-mask-size: contain;
  mask-size: contain;
  -webkit-mask-repeat: no-repeat;
  mask-repeat: no-repeat;
  -webkit-mask-position: center;
  mask-position: center;
  /* Base: paneles claros. Ahí el elemento es textura de fondo —a plena
     tinta un contorno negro sobre papel compite con el texto y no es lo
     que muestra la referencia, que va toda sobre negro—. */
  opacity: 0.3;
  transform: rotate(var(--giro, 0deg));
  animation: decoDeriva 26s var(--ease) infinite alternate;
  animation-delay: var(--tardanza, 0s);
}

/* En los paneles claros el amarillo a plena tinta compite con el
   texto: el encargo habla de las zonas oscuras, así que aquí el
   elemento se queda como presencia, no como protagonista. */
.deco--marca { color: var(--marca); opacity: 0.5; }

/* Los paneles oscuros son de los que habla el encargo: «el fondo negro
   se siente demasiado plano». Ahí van a tinta plena, como en la
   referencia que mandó el cliente. */
.panel[data-oscuro] .deco,
.panel > .deco--encima { opacity: 0.92; }

.panel[data-oscuro] .deco--marca,
.panel > .deco--encima.deco--marca { opacity: 1; }

/* Sobre fotografía el blanco a tinta plena se come la imagen: se le
   quita un punto, el amarillo aguanta entero. */
.panel > .deco--encima:not(.deco--marca) { opacity: 0.7; }

/* Las tramas densas —puntos, círculo rayado— pesan más que un contorno
   a igualdad de tamaño: un punto menos en todos los casos. */
.deco--trama { opacity: 0.24; }
.deco--trama.deco--marca { opacity: 0.42; }
.panel[data-oscuro] .deco--trama,
.panel > .deco--encima.deco--trama { opacity: 0.8; }
.panel[data-oscuro] .deco--trama.deco--marca,
.panel > .deco--encima.deco--trama.deco--marca { opacity: 0.95; }


/* La posición ya no es una esquina fija: la calcula `huecos()` en
   horizontal.js midiendo el sitio libre real de cada panel, y llega
   como left/top en línea. Las esquinas fijas metían el triángulo
   encima del titular de «Por qué elegir Enso Media». */

@keyframes decoDeriva {
  from { transform: rotate(var(--giro, 0deg)) translate3d(0, 0, 0); }
  to   { transform: rotate(calc(var(--giro, 0deg) * -0.6)) translate3d(0, -22px, 0); }
}

@media (prefers-reduced-motion: reduce) {
  .deco { animation: none; }
}

/* En móvil el espacio es el que es: sobra decoración. */
@media (max-width: 899px) {
  .deco { display: none; }
}



/* --- El mosaico de la portada en ventanas bajas ----------------------
   Las tarjetas del mosaico tienen alto fijo (dos filas dentro del
   panel) y las descripciones completas de enso.com.mx ocupan hasta tres
   párrafos. Por debajo de 780 px de alto el texto se mide contra la
   ventana, igual que en las fichas de servicios.html. */
@media (min-width: 900px) and (max-height: 780px) {
  .servicio p { font-size: clamp(0.76rem, 2.05svh, 0.92rem); line-height: 1.4; }
  .servicio__cuerpo { padding: var(--space-sm) var(--space-md); }
}
