/* Noreve Hotel Management — NOR-3
   macroestructura: 10 Specimen
   lock: Liron Moran (primaria) · Sequel (retratos) · Aspelin Reitan (disciplina del dorado)
   La identidad es del cliente (deck): manda sobre el research. Ver REFERENCE-LOCK.md
   Ningún #hex ni font-family fuera de :root. */

:root {
  /* ── Tier 1 — crudo ──────────────────────────────────────────────── */
  --raw-negro:    #0d0b0a;   /* [deck p1] NO es negro puro: tira a marrón */
  --raw-negro-2:  #141110;   /* [inferido] segunda superficie oscura */
  --raw-crema:    #f7ece8;   /* [deck p2] es ROSADO, no gris */
  --raw-crema-2:  #efe1dc;   /* [inferido] segunda superficie clara */
  --raw-dorado:   #c2a878;   /* [deck p2] ACENTO ÚNICO */
  --raw-dorado-2: #a98d5e;   /* [inferido] hover sobre crema */
  --raw-dorado-3: #7a6539;   /* [inferido] el dorado LEGIBLE sobre crema: 4,83 */
  --raw-gris:     #6f6660;   /* [inferido] terciario sobre crema */
  --raw-gris-inv: #9a908a;   /* [inferido] terciario sobre negro */

  --raw-serif: "Playfair Display", Georgia, serif;
  --raw-sans:  "Poppins", ui-sans-serif, system-ui, sans-serif;

  --raw-ease-out: cubic-bezier(0.16, 1, 0.3, 1);
  --raw-dur-short: 220ms;
  --raw-dur-long:  520ms;

  /* ── Tier 2 — roles ──────────────────────────────────────────────── */
  --oscuro:       var(--raw-negro);
  --oscuro-2:     var(--raw-negro-2);
  --claro:        var(--raw-crema);
  --claro-2:      var(--raw-crema-2);
  --acento:       var(--raw-dorado);
  --acento-hover: var(--raw-dorado-2);
  /* El dorado de la marca sobre crema da 3,89 y no llega al umbral. Este token se
     venía usando con `var(--acento-oscuro, #8a7444)` en cuatro lugares SIN estar
     declarado, así que ganaba siempre el fallback: el rótulo de los socios, su
     contador, el numeral de cada ficha y el cargo estaban todos por debajo.
     Declararlo acá los corrige a los cuatro de una vez. */
  --acento-oscuro: var(--raw-dorado-3);
  --tinta:        var(--raw-negro);
  --tinta-2:      var(--raw-gris);
  --tinta-inv:    var(--raw-crema);
  --tinta-inv-2:  var(--raw-gris-inv);
  --hairline:     color-mix(in srgb, var(--raw-dorado) 34%, transparent);
  --hairline-claro: color-mix(in srgb, var(--raw-dorado-3) 28%, transparent);

  --f-serif: var(--raw-serif);
  --f-sans:  var(--raw-sans);

  --margen:  clamp(20px, 4vw, 64px);
  --ancho:   1320px;
  --seccion: clamp(96px, 12vw, 190px);
  --r-card:  0px;   /* [research: Liron] zero-radius; la única curva es la muesca del deck */
}

/* ─────────────────────────  base  ───────────────────────── */

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

html, body {
  /* clip, NO hidden: hidden rompe position:sticky en descendientes */
  overflow-x: clip;
  margin: 0;
  background: var(--oscuro);
}
/* SIN scroll-behavior: smooth. Lenis anima el scroll por su cuenta y los dos a la vez
   se pelean — ésa es la sensación de trabado. Los anchors van por lenis.scrollTo(). */

body {
  font-family: var(--f-sans);
  font-weight: 400;
  font-size: 16px;
  line-height: 1.7;
  color: var(--tinta-inv);
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}

img { display: block; max-width: 100%; height: auto; }
ul, ol { margin: 0; padding: 0; list-style: none; }
h1, h2, h3, p, figure { margin: 0; }
a { color: inherit; text-decoration: none; }

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

.solo-lectores {
  position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px;
  overflow: hidden; clip-path: inset(50%); white-space: nowrap; border: 0;
}

.saltar {
  position: fixed; top: 8px; left: 8px; z-index: 95;
  transform: translateY(-200%);
  min-height: 44px; padding: 10px 18px;
  display: inline-flex; align-items: center;
  background: var(--claro); color: var(--tinta);
  font-size: 13px; font-weight: 500;
}
.saltar:focus-visible { transform: translateY(0); }

/* Cada sección es su propio frame de 1440: un píxel de diseño es (v/1440*100)cqw */
section, footer { container-type: inline-size; }
@media (max-width: 1023px) { section, footer { --type-min: 13px; } }

.claro  { background: var(--claro);  color: var(--tinta); }
.oscuro { background: var(--oscuro); color: var(--tinta-inv); }

/* ─────────────────────────  piezas compartidas  ───────────────────────── */

/* La serif itálica dorada es SIEMPRE etiqueta, nunca titular. [deck] */
.etiqueta {
  font-family: var(--f-serif);
  font-style: italic;
  font-size: clamp(19px, 1.9vw, 26px);
  line-height: 1.2;
  color: var(--acento);
}
/* Sobre crema el dorado da 2,1:1 — sólo pasa a ≥24px. Por eso la etiqueta nunca
   baja de ahí sobre claro, y las etiquetas chicas van en --tinta-2. */
.etiqueta--inv { color: var(--acento); }

.titulo {
  font-family: var(--f-sans);
  font-weight: 400;
  font-size: clamp(32px, 4.4vw, 60px);
  line-height: 1.04;
  letter-spacing: -0.02em;
  margin-top: clamp(10px, 1.2vw, 16px);
  text-wrap: balance;
}
.titulo--inv { color: var(--tinta-inv); }

.punto {
  font-size: 20px; line-height: 1;
  color: var(--tinta-inv-2);
  margin-block: clamp(20px, 2.6vw, 34px);
}

strong { font-weight: 600; color: inherit; }   /* contraste por peso, nunca por color */

/* ─────────────────────────  header  ───────────────────────── */

.marca {
  position: fixed; inset: 0 0 auto; z-index: 80;
  /* Grid de tres y no flex+space-between: con flex el menú se centra entre los dos
     extremos, no en la PÁGINA, así que se corre cada vez que el wordmark o la
     acción cambian de ancho. Con 1fr auto 1fr queda clavado al centro real. */
  display: grid; grid-template-columns: minmax(0, 1fr) auto minmax(0, 1fr);
  align-items: center; gap: 16px;
  padding: clamp(18px, 2.4vw, 28px) var(--margen);
  /* opacity NO va acá: la escribe el resorte inline cuadro a cuadro y una
     transición encima le agrega su propio retardo contra el que pelea. */
  transition: transform var(--raw-dur-long) var(--raw-ease-out),
              color var(--raw-dur-long) var(--raw-ease-out);
  color: var(--tinta-inv);
}
/* La barra necesita superficie propia fuera del hero.

   Era enteramente transparente y lo único que la separaba del contenido era el
   scrim: un degradé al 58%. Alcanza sobre metraje, pero no cuando lo que pasa por
   debajo es texto claro sobre fondo oscuro, del mismo tono que la barra: los dos
   textos quedaban legibles y se pisaban.

   Translúcida con desenfoque y no opaca, porque en "Quiénes somos" el metraje pasa
   por debajo a propósito: un fondo sólido cortaría ese plano en seco. El `data-fondo`
   lo escribe §header sólo después del hero, donde la toma sí tiene que mandar. */
.marca[data-fondo] {
  background: color-mix(in srgb, var(--oscuro) 74%, transparent);
  -webkit-backdrop-filter: blur(16px) saturate(118%);
  backdrop-filter: blur(16px) saturate(118%);
}
.marca[data-fondo][data-sobre="claro"] {
  background: color-mix(in srgb, var(--claro) 74%, transparent);
}
/* con superficie propia el degradé sobra y sólo ensucia el borde */
.marca[data-fondo] { --scrim: 0; }

/* Sin esto el wordmark crema desaparece sobre el crema de "Quiénes somos" */
.marca[data-sobre="claro"] { color: var(--tinta); }
/* El scrim existe para leer la nav sobre metraje oscuro. Sobre superficie clara
   no hace nada salvo dejar una mancha gris de 190px, muy visible en el borde del
   barrido de los socios. `--scrim` estaba declarada pero nadie la escribía. */
.marca[data-sobre="claro"] { --scrim: 0; }

.marca__wordmark {
  font-family: var(--f-serif); font-style: italic;
  font-size: 19px; line-height: 1;
  white-space: nowrap;
}
/* columna 3 explícita: en mobile el menú se oculta y sin esto la acción cae en
   la columna del medio */
.marca__accion { grid-column: 3; justify-self: end;
  font-size: 12px; font-weight: 500;
  letter-spacing: 0.18em; text-transform: uppercase;
  white-space: nowrap;      /* un link de nav que wrapea se lee como error de estilo */
  opacity: 0.72;
  transition: color var(--raw-dur-short) var(--raw-ease-out),
              opacity var(--raw-dur-short) var(--raw-ease-out);
}
.marca__accion:hover { color: var(--acento); opacity: 1; }

/* ─────────────────────────  1 · hero specimen  ───────────────────────── */

/* El retrato es absolute; sin reservar su alto, se come la bajada que va debajo.
   alto = ancho / (3/4). */

/* La palabra: el specimen. Serif itálica, recortada por el marco. [deck p1 + Liron] */

/* El retrato: tapa las letras del medio. Ése es el movimiento entero. */

/* Etiquetas de esquina [research: Liron] */
.esq {
  position: absolute;
  font-size: clamp(9.5px, 0.75vw, 10.5px);
  font-weight: 400;
  letter-spacing: 0.2em; text-transform: uppercase;
  color: var(--tinta-inv-2);
  white-space: nowrap;
}
/* Debajo de la franja del header fijo, que ocupa los primeros ~68px */
.esq--ai { top: calc(var(--margen) + clamp(46px, 5vw, 62px)); left: var(--margen); }
.esq--ad { top: calc(var(--margen) + clamp(46px, 5vw, 62px)); right: var(--margen); }
.esq--bi { bottom: var(--margen); left: var(--margen); }
.esq--bd { bottom: var(--margen); right: var(--margen); }
@media (max-width: 1023px) { .esq--ai, .esq--ad, .esq--bd { display: none; } }

/* ─────────────────────────  2 · quiénes somos  ───────────────────────── */

.quienes { position: relative; overflow: clip; padding: var(--seccion) var(--margen); }

/* El círculo que sangra del borde izquierdo [deck p2] */
.circulo {
  position: absolute; left: 0; top: clamp(60px, 9vw, 130px);
  width: clamp(56px, 7vw, 92px); aspect-ratio: 1;
  border-radius: 50%;
  background: var(--oscuro);
  transform: translateX(-42%);
}

/* Quiénes somos — el plano se parte

   Tres intentos de poner este texto ENCIMA del metraje terminaron en lo mismo: un
   scrim cada vez más opaco para poder leer, o sea tapar el video para usarlo de
   fondo. El deck no hace eso: alterna páginas con imagen y páginas con contenido.
   Acá el plano se abre en dos —el metraje sangra una mitad, el texto vive en la
   otra sobre superficie sólida— y nadie pelea con nadie.

   Se queda OSCURA aunque el deck use crema para las páginas de contenido, porque
   la que sigue (los socios) es clara: dos claras seguidas matan ese corte. */
/* La sección es el riel: mide más de una pantalla y su contenido se fija. Así el
   scroll no la pasa de largo —deja de ser un bloque más— sino que avanza el
   metraje mientras el texto se sostiene. */
.quienes {
  position: relative;
  min-height: 210svh;
  padding: 0;
  background: var(--oscuro);
}
.quienes__pin {
  position: sticky; top: 0;
  /* dvh y no svh: un pin que mide menos que la ventana deja una franja de la
     sección de fondo abajo, sólo visible bajo el metraje porque el resto es del
     mismo negro. Abajo de 900 este pin es estático, así que la barra dinámica del
     browser no puede hacerlo saltar. */
  /* min-height y no height: con 100dvh fijo y overflow clip, en una notebook de
     768 de alto el panel mide ~990 y el último párrafo quedaba cortado contra la
     sección siguiente (lo marcó el cliente). Si el panel es más alto que la
     ventana, el pin crece y el sticky igual lo sostiene mientras dura el riel. */
  min-height: 100dvh;
  display: grid;
  grid-template-columns: minmax(0, 0.94fr) minmax(0, 1.06fr);
  align-items: stretch;
  overflow: clip;
}
.quienes__panel { transform: translateY(var(--qy, 0)); }

/* La n del wordmark como RELIEVE, no como figura.

   En el hero "noreve." es el logo: grande, crema, centrado. Repetir eso acá sería
   repetirse. Sangrando por el borde y apenas separada del fondo deja de leerse
   como marca y pasa a ser textura — que es lo que el círculo del deck intentaba
   hacer, pero con algo que sí es de ellos. La referencia primaria del lock es
   exactamente esto: una letra en serif recortada por el marco. */
.quienes__n {
  position: absolute;
  z-index: 0;
  left: 0; bottom: clamp(-30px, -2vw, -10px);
  transform: translateX(-34%);
  font-family: var(--f-serif);
  font-style: italic;
  font-size: clamp(300px, 36vw, 560px);
  line-height: 0.78;
  color: rgb(247 236 232 / 0.075);
  pointer-events: none; user-select: none;
}
.quienes__panel > :not(.quienes__n) { position: relative; z-index: 1; }
@media (max-width: 900px) {
  .quienes__n { font-size: clamp(240px, 58vw, 380px); }
}

/* El panel lleva su propia superficie: es una hoja del telón y tiene que viajar
   con su fondo. Con el negro puesto en la sección, al abrirse quedaba el texto
   flotando sobre el crema. */
.quienes__panel {
  position: relative;
  align-self: stretch;
  display: flex;
  flex-direction: column;
  justify-content: center;
  background: var(--oscuro);
  /* Más aire abajo que arriba: el cierre del texto necesita separarse del corte
     a la sección siguiente, si no se lee como cortado. */
  padding: clamp(48px, 6vw, 84px) clamp(40px, 5vw, 86px) clamp(80px, 9vw, 140px)
           clamp(56px, 7.5vw, 130px);
}
/* El panel llena su columna y es el CONTENIDO el que tiene ancho de lectura. Con
   un max-width en el panel quedaba un hueco a su izquierda, invisible mientras el
   fondo era oscuro y evidente apenas dejó de serlo. */
.quienes__panel > * { max-width: 560px; margin-right: auto; }
.quienes__frase {
  font-family: var(--f-sans);
  font-weight: 300;
  font-size: clamp(28px, 3.1vw, 46px);
  line-height: 1.12;
  letter-spacing: -0.02em;
  max-width: 15ch;
  margin-top: clamp(12px, 1.2vw, 18px);
  text-wrap: balance;
  color: var(--tinta-inv);
}
/* La separación que ocupaba el punto ahora la lleva el aire: sin ella el cuerpo
   queda pegado al titular y los dos bloques se leen como uno. */
.quienes__copy {
  display: grid;
  gap: clamp(16px, 1.8vw, 24px);
  margin-top: clamp(30px, 3.4vw, 52px);
}
.quienes__copy p {
  font-size: clamp(14.5px, 1.1vw, 16.5px);
  line-height: 1.8;
  max-width: 44ch;
  text-wrap: pretty;
  color: var(--tinta-inv-2);
}

/* El metraje ocupa su mitad a sangre. Se neutraliza el sticky del `.fondo`
   general: acá no es un fondo que pasa por detrás, es una de las dos mitades. */
/* Selector con la sección adelante: `.fondo` global fija `height: 100svh` y con
   la misma especificidad ganaba por orden. Quedaban 58px de franja negra bajo el
   metraje cuando el panel de texto es más alto que el viewport. */
.quienes__pin > .quienes__media {
  position: relative;
  height: 100%;
  margin: 0;
  align-self: stretch;
  overflow: clip;
}
.quienes__media .toma__video,
.quienes__media .fondo__poster { position: absolute; inset: 0; }

@media (max-width: 900px) {
  .quienes { min-height: 0; }
  .quienes__pin {
    position: static;
    height: auto;
    grid-template-columns: minmax(0, 1fr);
  }
  .quienes__panel { max-width: none; margin-left: 0; }
  .quienes__media { min-height: 56svh; order: -1; }
  .quienes__frase { max-width: 18ch; }
}

/* ─────────────────────────  1b · nuestros servicios  ───────────────────────── */

/* Dos unidades lado a lado, partidas por una hairline dorada. Sin card y sin
   relleno: la separación la dan la regla y el aire (Mews / Aspelin Reitan). */
.unidades { padding: var(--seccion) var(--margen); }
.unidades__cabeza, .unidades__par, .unidades__remate {
  max-width: var(--ancho); margin-inline: auto;
}
.unidades__par {
  margin-top: clamp(52px, 6vw, 96px);
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  border-top: 1px solid var(--hairline);
  border-bottom: 1px solid var(--hairline);
}
.unidad {
  padding: clamp(36px, 4.4vw, 64px) clamp(28px, 4vw, 64px) clamp(40px, 4.8vw, 70px) 0;
}
.unidad + .unidad {
  border-left: 1px solid var(--hairline);
  padding-left: clamp(28px, 4vw, 64px);
  padding-right: 0;
}

/* El lockup de sub-marca: el mismo gesto que el del hero (wordmark + regla +
   bajada espaciada en dorado), a escala de sección. */
.unidad__lockup { margin: 0; font-weight: 400; }
.unidad__marca {
  display: block;
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(56px, 6.6vw, 104px);
  line-height: 0.92;
  letter-spacing: -0.02em;
  color: var(--tinta-inv);
  padding-bottom: 0.08em;
}
.unidad__linea {
  display: grid; grid-template-columns: minmax(0, 1fr) auto;
  align-items: center; gap: clamp(14px, 1.6vw, 22px);
  margin-top: clamp(10px, 1.2vw, 16px);
  font-family: var(--f-sans);
  font-size: clamp(11px, 0.9vw, 13px);
  letter-spacing: 0.3em; text-transform: uppercase;
  color: var(--acento);
}
.unidad__regla {
  display: block; height: 1px; background: var(--acento); opacity: 0.42;
  transform-origin: left;
  transform: scaleX(var(--regla, 1));
}
.unidad__bajada {
  margin-top: clamp(28px, 3.2vw, 46px);
  font-size: clamp(19px, 1.7vw, 24px);
  font-weight: 500;
  line-height: 1.3;
  letter-spacing: -0.01em;
  max-width: 26ch;
  text-wrap: balance;
  color: var(--tinta-inv);
}
.unidad__copy {
  margin-top: clamp(16px, 1.6vw, 22px);
  font-size: clamp(14.5px, 1.1vw, 16px);
  line-height: 1.75;
  max-width: 48ch;
  text-wrap: pretty;
  color: var(--tinta-inv-2);
}
.unidad__copy strong { color: var(--tinta-inv); font-weight: 500; }

.unidades__remate {
  margin-top: clamp(36px, 4vw, 60px);
  font-weight: 300;
  font-size: clamp(22px, 2.3vw, 34px);
  line-height: 1.22;
  letter-spacing: -0.015em;
  max-width: min(var(--ancho), 30ch);
  margin-left: max(0px, calc((100% - var(--ancho)) / 2));
  text-wrap: balance;
  color: var(--tinta-inv);
}

@media (max-width: 900px) {
  .unidades__par { grid-template-columns: minmax(0, 1fr); }
  .unidad { padding-right: 0; }
  .unidad + .unidad {
    border-left: 0; border-top: 1px solid var(--hairline);
    padding-left: 0;
  }
}

/* ─────────────────────────  1c · cómo trabajamos  ───────────────────────── */

.metodo { padding: var(--seccion) var(--margen); }
.metodo .etiqueta { color: var(--acento-oscuro); }
.metodo__cabeza, .ciclo, .metodo__puente, .modalidades {
  max-width: var(--ancho); margin-inline: auto;
}
.metodo__cabeza > * { max-width: 62ch; }
.metodo__copy {
  margin-top: clamp(22px, 2.6vw, 34px);
  font-size: clamp(14.5px, 1.15vw, 16.5px);
  line-height: 1.75;
  max-width: 58ch;
  text-wrap: pretty;
  color: var(--tinta-2);
}
.metodo__copy strong { color: var(--tinta); font-weight: 500; }

/* El ciclo: cuatro verbos sobre un riel que se dibuja con el scroll y remata en
   la vuelta. El riel pasa por el centro de los puntos. */
.ciclo {
  position: relative;
  margin-top: clamp(64px, 7vw, 112px);
  --punto: 11px;
}
.ciclo__riel {
  position: absolute; left: 0; right: 34px;
  top: calc(var(--punto) / 2); height: 1px;
  background: var(--hairline-claro);
}
.ciclo__relleno {
  position: absolute; inset: 0;
  background: var(--acento-oscuro);
  transform-origin: left;
  transform: scaleX(var(--avance, 1));
}
.ciclo__pasos {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: clamp(20px, 2.6vw, 40px);
  padding-right: 34px;
}
.paso__punto {
  display: block; position: relative;
  width: var(--punto); aspect-ratio: 1; border-radius: 50%;
  background: var(--claro);
  border: 1px solid var(--acento-oscuro);
  transition: background var(--raw-dur-long) var(--raw-ease-out);
}
.paso.encendido .paso__punto { background: var(--acento-oscuro); }
.paso__verbo {
  margin-top: clamp(22px, 2.4vw, 34px);
  font-size: clamp(21px, 2vw, 28px);
  font-weight: 500;
  line-height: 1.15;
  letter-spacing: -0.02em;
  color: var(--tinta);
}
.paso__desc {
  margin-top: 12px;
  font-size: clamp(14px, 1.05vw, 15px);
  line-height: 1.7;
  max-width: 30ch;
  text-wrap: pretty;
  color: var(--tinta-2);
}
.ciclo__vuelta {
  position: absolute; right: 0; top: calc(var(--punto) / 2 - 11px);
  color: var(--acento-oscuro);
}

.metodo__puente {
  margin-top: clamp(72px, 8vw, 128px);
  padding-top: clamp(36px, 4vw, 56px);
  border-top: 1px solid var(--hairline-claro);
  font-weight: 300;
  font-size: clamp(20px, 2vw, 29px);
  line-height: 1.35;
  letter-spacing: -0.01em;
  text-wrap: pretty;
  color: var(--tinta);
}
.metodo__puente { max-width: var(--ancho); }
.metodo__puente strong { font-weight: 500; }

/* Las modalidades: filas de ledger. La cabeza queda fija mientras pasa la lista,
   el mismo recurso que las demostraciones del sistema. */
.modalidades { margin-top: clamp(48px, 5.4vw, 84px); }
.modalidad {
  display: grid;
  grid-template-columns: minmax(0, 0.8fr) minmax(0, 1.2fr);
  gap: clamp(28px, 5vw, 86px);
  padding-block: clamp(40px, 4.6vw, 72px);
  border-top: 1px solid var(--hairline-claro);
  align-items: start;
}
.modalidad:last-child { border-bottom: 1px solid var(--hairline-claro); }
.modalidad__cabeza { position: sticky; top: clamp(110px, 14vh, 150px); }
.modalidad__n {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(24px, 2.4vw, 34px);
  line-height: 1;
  color: var(--acento-oscuro);
}
.modalidad__nombre {
  margin-top: clamp(14px, 1.4vw, 20px);
  font-size: clamp(30px, 3.4vw, 48px);
  font-weight: 500;
  line-height: 1.02;
  letter-spacing: -0.025em;
  text-wrap: balance;
  color: var(--tinta);
}
.modalidad__lema {
  margin-top: 12px;
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(19px, 1.7vw, 24px);
  line-height: 1.25;
  color: var(--acento-oscuro);
}
.modalidad__para {
  margin-top: clamp(16px, 1.6vw, 22px);
  font-size: clamp(14.5px, 1.1vw, 16px);
  line-height: 1.7;
  max-width: 40ch;
  text-wrap: pretty;
  color: var(--tinta-2);
}
.modalidad__rotulo {
  font-size: 12px;
  letter-spacing: 0.2em; text-transform: uppercase;
  color: var(--tinta-2);
}
.modalidad__rotulo em { font-style: normal; color: var(--tinta); font-weight: 500; }
.modalidad__lista {
  margin-top: clamp(14px, 1.4vw, 20px);
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  column-gap: clamp(20px, 2.8vw, 44px);
}
.modalidad__lista li {
  display: grid; grid-template-columns: 14px minmax(0, 1fr); gap: 10px;
  padding-block: 13px;
  border-bottom: 1px solid var(--hairline-claro);
  font-size: clamp(14.5px, 1.1vw, 16px);
  line-height: 1.45;
  color: var(--tinta);
}
/* un guion dorado en vez del bullet: marca sin inventar un ícono */
.modalidad__lista li::before {
  content: ""; height: 1px; margin-top: 0.72em;
  background: var(--acento-oscuro);
}
.modalidad__cierre {
  margin-top: clamp(24px, 2.6vw, 36px);
  font-size: clamp(14.5px, 1.1vw, 16px);
  line-height: 1.75;
  max-width: 62ch;
  text-wrap: pretty;
  color: var(--tinta-2);
}
.modalidad__cierre strong { color: var(--tinta); font-weight: 500; }

@media (max-width: 900px) {
  .ciclo__pasos { grid-template-columns: repeat(2, minmax(0, 1fr)); row-gap: 44px; padding-right: 0; }
  .ciclo__riel, .ciclo__vuelta { display: none; }
  .modalidad { grid-template-columns: minmax(0, 1fr); }
  .modalidad__cabeza { position: static; }
}
@media (max-width: 560px) {
  .ciclo__pasos { grid-template-columns: minmax(0, 1fr); }
  .modalidad__lista { grid-template-columns: minmax(0, 1fr); }
}

/* ─────────────────────────  3a · el numeral  ───────────────────────── */

.numeral {
  min-height: 74svh;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  padding: var(--seccion) var(--margen);
  text-align: center;
}
/* No itálica: en el deck el 4 es recto [deck p3] */
.numeral__cifra {
  font-family: var(--f-serif); font-style: normal; font-weight: 400;
  font-size: clamp(200px, 38vw, 560px);
  line-height: 0.8;
  color: var(--tinta-inv);
  user-select: none;
}
.numeral__copy {
  max-width: 46ch;
  margin-top: clamp(14px, 1.8vw, 22px);
  font-size: clamp(14.5px, 1.15vw, 16.5px);
  line-height: 1.72;
  color: var(--tinta-inv-2);
  text-wrap: pretty;
}
.numeral__copy strong { color: var(--tinta-inv); }

/* ─────────────────────────  3 · el reparto  ─────────────────────────

   Pedido del cliente: la foto de los cuatro juntos y abajo las fichas. Antes era
   un carril fijado de un retrato por socio. Ahora es una sección estática: el
   encabezado y la foto en split (el mismo que "Quiénes somos"), y las cuatro
   fichas en fila debajo. */
.reparto {
  position: relative; z-index: 2;
  padding: var(--seccion) var(--margen);
}
.reparto__cabeza,
.reparto__fichas {
  max-width: var(--ancho);
  margin-inline: auto;
}
.reparto__cabeza {
  display: grid;
  grid-template-columns: minmax(0, 0.9fr) minmax(0, 1.1fr);
  gap: clamp(32px, 6vw, 110px);
  align-items: end;
}

/* Los dígitos itálicos de Playfair tienen descendente largo: con line-height
   menor a 1 la caja los recortaba y el rótulo quedaba pisado. */
.reparto__cifra {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(110px, 13vw, 210px);
  line-height: 1; padding-bottom: 0.1em;
  margin-left: -0.05em;
  letter-spacing: -0.04em;
  color: var(--tinta);
}
.reparto__rotulo {
  margin-top: clamp(6px, 1vw, 14px);
  font-size: clamp(11px, 0.9vw, 13px); font-weight: 500;
  letter-spacing: 0.34em; text-transform: uppercase;
  color: var(--acento-oscuro);
}
.reparto__intro {
  margin-top: clamp(22px, 3vw, 40px);
  max-width: 46ch;
  font-size: clamp(14px, 1.05vw, 15.5px); line-height: 1.7;
  color: var(--tinta-2);
  text-wrap: pretty;
}
.reparto__intro strong { color: var(--tinta); font-weight: 500; }

/* La foto es vertical (3:4) y la gente ocupa los tres cuartos de abajo: el
   recorte cuadrado se queda con las caras y el sillón y deja afuera el techo. */
.reparto__foto {
  position: relative; overflow: clip;
  margin: 0;
  aspect-ratio: 1;
  border-radius: 4px;
  background: var(--claro-2);
}
.reparto__foto img {
  display: block;
  width: 100%; height: 100%; object-fit: cover;
  object-position: 50% 92%;
  filter: grayscale(0.18) contrast(1.06) saturate(0.9);
}
.reparto__foto[data-fallo] img { display: none; }

.reparto__fichas {
  list-style: none; padding: 0;
  margin-top: clamp(48px, 6vw, 96px);
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: clamp(28px, 3vw, 48px);
}
.reparto__ficha {
  display: grid; align-content: start;
  padding-top: clamp(16px, 1.6vw, 22px);
  border-top: 1px solid var(--hairline);
}
.reparto__n {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(20px, 1.8vw, 26px); line-height: 1;
  color: var(--acento-oscuro); opacity: 0.6;
}
.reparto__nombre {
  margin-top: 10px;
  font-family: var(--f-serif); font-style: italic; font-weight: 400;
  font-size: clamp(22px, 1.9vw, 30px); line-height: 1.1;
  letter-spacing: -0.02em;
  color: var(--tinta);
  text-wrap: balance;
}
.reparto__cargo {
  margin-top: 10px;
  font-size: 11px; font-weight: 500;
  letter-spacing: 0.16em; text-transform: uppercase; line-height: 1.6;
  color: var(--acento-oscuro);
}
.reparto__bio {
  margin-top: 12px;
  font-size: clamp(13.5px, 0.95vw, 14.5px); line-height: 1.62;
  color: var(--tinta-2);
  text-wrap: pretty;
}

@media (max-width: 1100px) {
  .reparto__fichas { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 900px) {
  .reparto__cabeza { grid-template-columns: minmax(0, 1fr); }
}
@media (max-width: 540px) {
  .reparto__foto { aspect-ratio: 4 / 5; }
  .reparto__foto img { object-position: 50% 80%; }
  .reparto__fichas { grid-template-columns: minmax(0, 1fr); }
}

@media (prefers-reduced-motion: reduce) {
  .quienes { min-height: 0; }
  .quienes__pin { position: static; height: auto; }
}

/* ─────────────────────────  WhatsApp flotante  ───────────────────────── */
.wa {
  position: fixed; z-index: 90;
  right: max(18px, env(safe-area-inset-right));
  bottom: max(18px, env(safe-area-inset-bottom));
  width: 56px; height: 56px;
  display: grid; place-items: center;
  border-radius: 50%;
  color: #fff; background: #25d366;
  box-shadow: 0 1px 2px rgb(0 0 0 / .18), 0 8px 24px rgb(0 0 0 / .32);
  transition: transform var(--raw-dur-short) var(--raw-ease-out),
              box-shadow var(--raw-dur-short) var(--raw-ease-out);
}
.wa:hover { transform: translateY(-2px) scale(1.05);
  box-shadow: 0 2px 4px rgb(0 0 0 / .2), 0 14px 32px rgb(0 0 0 / .36); }
.wa:active { transform: scale(0.96); }
.wa:focus-visible { outline: 2px solid var(--acento); outline-offset: 4px; }
@media (max-width: 540px) { .wa { width: 52px; height: 52px; } }
@media (prefers-reduced-motion: reduce) { .wa { transition: none; } }

/* ─────────────────────────  4 · el sistema  ───────────────────────── */

.sistema { padding: var(--seccion) var(--margen); }
.sistema__cabeza, .modulos { max-width: var(--ancho); margin-inline: auto; }
.sistema__cabeza { max-width: min(var(--ancho), 62ch); }
.sistema__copy {
  margin-top: clamp(22px, 2.6vw, 34px);
  font-size: clamp(14.5px, 1.15vw, 16.5px);
  line-height: 1.72;
  color: var(--tinta-inv-2);
  max-width: 54ch;
  text-wrap: pretty;
}
.sistema__copy strong { color: var(--tinta-inv); }

/* El índice del sistema.

   Lock de esta sección (research: Cloudbeds y Mews, del rubro exacto; Dovetail por
   el canvas oscuro):
     · Cloudbeds no enumera capacidades con ícono, lleva a la evidencia de cada una.
     · Mews sostiene el bloque con hairlines y cero relleno ("digital ledger").
     · Dovetail, sobre oscuro: la profundidad la dan superficie y borde, nunca sombra.
   Paleta y tipografía NO se importan: las manda el deck del cliente.

   Lo que se rechaza: el ícono circular de cada fila (el tell de "grid de features"),
   la paridad 2x2 y cualquier card. */

.modulos { margin-top: clamp(44px, 5vw, 76px); }
.modulo {
  position: relative;
  display: grid;
  /* Cuatro columnas: numeral, nombre, descripción y bajada.

     Antes el nombre y la descripción iban APILADOS en una sola columna de 1fr, y
     como la descripción corta en 52ch sobraban 727 de los 1320 de cada fila: más de
     la mitad vacía, y en las tres filas sin bajada el vacío llegaba hasta el borde.
     En columnas, la fila se llena a lo ancho y baja de alto. Es el patrón que la
     sección de servicios ya usaba en este mismo sitio, y el "digital ledger" con
     que Mews sostiene este tipo de lista.

     Tres columnas y no cuatro: la cuarta era la bajada a las demostraciones, que se
     sacó. Sin ella la descripción se queda con todo el ancho restante. */
  grid-template-columns:
    minmax(0, 68px) minmax(0, 18.5rem) minmax(0, 1fr);
  gap: clamp(18px, 2.4vw, 32px);
  padding-block: clamp(24px, 2.7vw, 36px);
  border-top: 1px solid var(--hairline);
  align-items: baseline;
}
.modulo:last-child { border-bottom: 1px solid var(--hairline); }

/* El numeral, en lugar del ícono. Es el mismo recurso que el 4 de los socios y su
   contador: el sitio ya cuenta con serif itálica dorada, no hacía falta inventar
   una familia de íconos para decir "son cinco". */
.modulo__n {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(20px, 2vw, 28px);
  line-height: 1;
  color: var(--acento);
  /* 0.72 y no 0.55: a 0.55 el numeral quedaba en 3,28 de contraste sobre el negro
     del deck. Pasa el umbral de texto grande por poco, pero es el elemento que
     dice cuántos módulos son y a esa opacidad casi no se lee. */
  opacity: 0.72;
}

/* Sans en crema, no serif itálica dorada.

   Venían a 26px, el mismo tamaño y el mismo tratamiento que `.etiqueta`, o sea el
   eyebrow de la sección: cinco nombres de módulo vestidos de rótulo. Con eso la
   sección acumulaba once elementos en serif itálica dorada contra uno del
   calendario, y la jerarquía del resto del sitio (rótulo serif dorado chico →
   contenido sans) quedaba invertida justo acá.

   El dorado se reserva para el numeral y la bajada, que sí son señalética. */
.modulo__nombre {
  text-wrap: balance;   /* si igual parte en dos, que las dos líneas queden parejas */
  font-family: var(--f-sans);
  font-weight: 500;
  font-size: clamp(17.5px, 1.65vw, 21px);
  line-height: 1.3;
  letter-spacing: -0.01em;
  color: var(--tinta-inv);
}
.modulo__desc {
  font-size: clamp(14px, 1.05vw, 15px);
  line-height: 1.7;
  color: var(--tinta-inv-2);
  text-wrap: pretty;
}

/* Abajo de 1100 la descripción no entra al lado del nombre sin quedar en una
   medida ilegible, así que vuelve a apilarse debajo. */
@media (max-width: 1100px) {
  .modulo { grid-template-columns: minmax(0, 68px) minmax(0, 1fr); }
  .modulo__nombre { grid-column: 2; }
  .modulo__desc { grid-column: 2; margin-top: 8px; max-width: 52ch; }
}

@media (max-width: 720px) {
  .modulo { grid-template-columns: minmax(0, 44px) minmax(0, 1fr); align-items: start; }
}

/* ─────────────────────────  5 · revenue  ───────────────────────── */

.revenue { padding: var(--seccion) var(--margen); }
.revenue__grid {
  max-width: var(--ancho); margin-inline: auto;
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1.05fr);
  gap: clamp(32px, 5vw, 90px);
}
.revenue__copy {
  font-size: clamp(15px, 1.25vw, 17.5px);
  line-height: 1.72;
  max-width: 48ch;
  text-wrap: pretty;
}

/* El conector vertical de los cuatro insumos [deck p8] */
.insumos {
  position: relative;
  margin-top: clamp(28px, 3.2vw, 42px);
  display: grid; gap: clamp(16px, 1.8vw, 24px);
}
.insumos::before {
  content: ""; position: absolute;
  left: 3px; top: 0.85em; bottom: 0.85em;
  width: 1px; background: var(--hairline);
}
/* 24 y no 34: con la sangría larga el texto se despegaba tanto del copy que la
   lista se leía suelta en vez de subordinada. */
.insumos li {
  position: relative;
  padding-left: 24px;
  font-size: clamp(14.5px, 1.15vw, 16px);
  line-height: 1.7;
}
/* El punto era `var(--tinta)`, o sea el negro para fondo claro, y esta sección es
   oscura: quedaba en rgb(13,11,10) sobre rgb(13,11,10), contraste 1,0, invisible.
   `.sobre-metraje` corrige el `color` del texto pero no el `background` de un
   pseudo-elemento, así que el bug sobrevivía a la inversión de la sección. */
.insumos li::before {
  content: ""; position: absolute;
  left: 0; top: 0.62em;
  width: 7px; height: 7px; border-radius: 50%;
  background: var(--acento);
}

/* el remate 24/7 [deck p9] */
.remate {
  min-height: 62svh;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  padding: var(--seccion) var(--margen);
  text-align: center;
}
.remate__cifra {
  font-family: var(--f-serif); font-style: normal;
  font-size: clamp(88px, 15vw, 210px);
  line-height: 0.9;
  color: var(--tinta-inv);
}
.remate__nombre {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(28px, 4vw, 56px);
  line-height: 1.1;
  color: var(--acento);
  margin-top: clamp(6px, 0.8vw, 12px);
}
.remate__copy {
  max-width: 42ch;
  margin-top: clamp(18px, 2.2vw, 28px);
  font-size: clamp(14px, 1.1vw, 15.5px);
  line-height: 1.7;
  color: var(--tinta-inv-2);
  text-wrap: pretty;
}

/* ─────────────────────────  6 · servicios  ───────────────────────── */

.servicios { padding: var(--seccion) var(--margen); }
.servicios__cabeza, .servicios__lista { max-width: var(--ancho); margin-inline: auto; }
.servicios__lista { margin-top: clamp(44px, 5vw, 76px); }

/* Índice numerado, no grilla de cards: son ocho y cada uno tiene copy propia */
.servicio {
  display: grid;
  grid-template-columns: minmax(0, 58px) minmax(0, 300px) minmax(0, 1fr);
  gap: clamp(16px, 2.6vw, 48px);
  padding-block: clamp(24px, 2.8vw, 38px);
  border-top: 1px solid var(--hairline);
  align-items: start;
}
.servicio:last-child { border-bottom: 1px solid var(--hairline); }
.servicio__n {
  font-size: 12px; letter-spacing: 0.18em;
  color: var(--tinta-2);
  padding-top: 0.5em;
}
.servicio__nombre {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(19px, 2vw, 27px);
  line-height: 1.2;
  color: var(--acento);
}
.servicio__desc {
  font-size: clamp(14.5px, 1.1vw, 15.5px);
  line-height: 1.7;
  max-width: 52ch;
  text-wrap: pretty;
}

/* ─────────────────────────  7 · panel de socios  ─────────────────────────

   Tercera demostración, con la gramática de las otras dos: sección crema, split, y
   la pieza como placa oscura. Antes era una sección oscura con foto de fondo al 22%
   y cuatro cards crema en grilla; ni la foto decía nada (una persona de espaldas
   detrás de indicadores financieros) ni las cards mostraban un dato. */

.panel { position: relative; overflow: clip; }
/* No tenía estilo propio: el párrafo quedaba pegado al titular. Mismo trato que
   `.sistema__copy`, en tinta de fondo claro. */
.panel__copy {
  margin-top: clamp(22px, 2.6vw, 34px);
  font-size: clamp(14.5px, 1.15vw, 16.5px);
  line-height: 1.72;
  color: var(--tinta-2);
  max-width: 54ch;
  text-wrap: pretty;
}
.panel__copy strong { color: var(--tinta); font-weight: 500; }

/* El tablero. Un solo plano, sin cards: los cuatro indicadores comparten superficie
   y se separan por hairline, igual que el panel del motor. */
.tablero {
  position: relative;
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  background: var(--oscuro-2);
  border: 1px solid var(--hairline);
  color: var(--tinta-inv);
}
/* La muesca del deck, una vez. Es el crema de la sección mordiendo el tablero, así
   que de verdad descubre la superficie de atrás; las cuatro de antes eran negras
   sobre card crema y no revelaban nada. */
.tablero::before {
  content: ""; position: absolute; z-index: 2;
  top: -1px; left: 50%; transform: translateX(-50%);
  width: clamp(64px, 7vw, 96px); aspect-ratio: 2 / 1;
  background: var(--claro);
  border-radius: 0 0 999px 999px;
}
.indicador {
  padding: clamp(26px, 3.2vw, 44px) clamp(22px, 2.6vw, 34px);
  border-right: 1px solid var(--hairline);
  border-bottom: 1px solid var(--hairline);
}
.indicador:nth-child(2n) { border-right: 0; }
.indicador:nth-child(n + 3) { border-bottom: 0; }
/* los dos de arriba despejan la muesca */
.indicador:nth-child(-n + 2) { padding-top: clamp(44px, 4.6vw, 64px); }

.indicador__label {
  font-size: clamp(11px, 0.9vw, 12.5px);
  letter-spacing: 0.16em; text-transform: uppercase;
  color: var(--tinta-inv-2);
}
/* El dato manda: serif itálica grande en dorado, el mismo tratamiento que la tarifa
   del motor, para que las tres demostraciones se lean como el mismo sistema. */
.indicador__valor {
  margin-top: clamp(10px, 1.2vw, 16px);
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(30px, 3.4vw, 46px);
  line-height: 1;
  color: var(--acento);
  font-variant-numeric: tabular-nums;
}
.indicador__valor i { font-style: normal; font-size: 0.52em; opacity: 0.72; }
.indicador__pie {
  margin-top: clamp(8px, 1vw, 12px);
  font-size: clamp(12px, 0.95vw, 13.5px);
  line-height: 1.6;
  color: var(--tinta-inv-2);
}

@media (max-width: 640px) {
  .tablero { grid-template-columns: minmax(0, 1fr); }
  .indicador { border-right: 0; border-bottom: 1px solid var(--hairline); }
  .indicador:last-child { border-bottom: 0; }
  .indicador:nth-child(2) { padding-top: clamp(26px, 3.2vw, 44px); }
}

.cierre {
  padding: var(--seccion) var(--margen) clamp(32px, 4vw, 52px);
  display: flex; flex-direction: column; align-items: center;
  text-align: center;
}
/* El lema sangra a los dos bordes del cierre y come su padding superior, para que
   el plano toque el borde de la sección anterior en vez de flotar en un marco. */
.lema {
  position: relative; isolation: isolate; overflow: clip;
  align-self: stretch;
  margin: calc(-1 * var(--seccion)) calc(-1 * var(--margen)) 0;
  /* El texto vive en el TERCIO INFERIOR, no centrado.

     El viñedo tiene su punto de fuga luminoso justo en el medio del cuadro, que es
     donde caía el texto: el lema dorado desaparecía contra el cielo. Un velo parejo
     lo hubiera arreglado tapando lo mejor del plano, que es el error que "Quiénes
     somos" documenta. Abajo la tierra ya es oscura, así que alcanza con un degradé
     que sube desde el borde inferior: el texto se lee y el cielo queda entero. */
  min-height: clamp(560px, 82svh, 860px);
  padding: clamp(110px, 15vh, 190px) var(--margen) clamp(56px, 7vh, 96px);
  display: grid; align-items: end; justify-items: center;
}
/* Sube desde el piso del cuadro y se agota antes del horizonte. El tramo del 30 al
   58 se sostiene alto a propósito: ahí vive el rótulo, que es el texto más chico y
   el que primero se pierde cuando el scrub trae un cuadro claro. */
.lema .fondo__scrim {
  background: linear-gradient(to top,
    color-mix(in srgb, var(--oscuro) 95%, transparent) 0%,
    color-mix(in srgb, var(--oscuro) 90%, transparent) 34%,
    color-mix(in srgb, var(--oscuro) 78%, transparent) 58%,
    color-mix(in srgb, var(--oscuro) 34%, transparent) 78%,
    transparent 100%);
}
/* Crema pleno y no el terciario: es el texto más chico del bloque y vive sobre
   metraje en movimiento. La jerarquía se la da el cuerpo de 11px, no el color. */
.lema .cierre__lema-label { color: var(--tinta-inv); }
/* `.fondo` global es sticky a 100svh con margen negativo, porque en otras secciones
   pasa POR DETRÁS mientras la sección scrollea. Acá es una capa contenida: si no se
   neutraliza, se despega del bloque y el plano aparece corrido. */
.lema > .fondo {
  position: absolute; inset: 0;
  height: auto; margin: 0;
}
.lema__texto {
  position: relative; z-index: 1;
  display: grid; justify-items: center;
  max-width: var(--ancho);
}

.cierre__lema-label {
  font-size: 11px; letter-spacing: 0.28em; text-transform: uppercase;
  color: var(--tinta-inv-2);
}
.cierre__lema {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(28px, 4.6vw, 64px);
  line-height: 1.12;
  color: var(--acento);
  margin-top: clamp(12px, 1.4vw, 18px);
  text-wrap: balance;
}
.cierre__copy {
  max-width: 52ch;
  font-size: clamp(14.5px, 1.15vw, 16.5px);
  line-height: 1.72;
  color: var(--tinta-inv-2);
  text-wrap: pretty;
}
/* El pedido: la única acción del sitio.

   Lock (research: Mews, del rubro; Pipe y Spellbook por el canvas oscuro):
     · Mews cierra con una pregunta y UNA acción, no con links parejos.
     · Sobre canvas oscuro, el acento único va SÓLO al CTA primario y todo lo demás
       queda monocromo. Acá eso le da por fin rol de acción al dorado, que en todo
       el sitio venía siendo decorativo.

   Partido y no centrado: el bloque centrado medía 450px dentro de una línea de
   1320, tres veces más angosto que su propio marco, y eso es lo que se leía como
   desalineado aunque estuviera centrado al píxel. Ocupando el mismo ancho que la
   línea del pie, el problema desaparece sin mover nada de lugar. */
.pedido {
  width: 100%; max-width: var(--ancho);
  margin-top: clamp(72px, 9vw, 130px);
  display: grid;
  grid-template-columns: minmax(0, 1.1fr) minmax(0, 0.9fr);
  gap: clamp(30px, 5vw, 80px);
  align-items: end;
  text-align: left;
}
.pedido__copy {
  margin-top: clamp(18px, 2.2vw, 28px);
  max-width: 46ch;
  font-size: clamp(14.5px, 1.15vw, 16.5px);
  line-height: 1.72;
  color: var(--tinta-inv-2);
  text-wrap: pretty;
}
/* Pegado al borde derecho, no flotando en el medio de su columna: así el botón
   arma una vertical con "Rosario, Argentina" del pie y con el borde de la línea. */
.pedido__via { display: grid; justify-items: end; }
.pedido__via .contactos { justify-content: flex-end; }

/* El primer botón del sitio. Relleno dorado sobre el negro del deck: es el único
   elemento de la página que pide algo, así que es el único que se llena. */
.boton {
  display: inline-flex; align-items: center; gap: 0.7em;
  padding: clamp(15px, 1.6vw, 20px) clamp(26px, 2.8vw, 38px);
  background: var(--acento);
  color: var(--oscuro);
  border-radius: var(--r-card);
  font-size: clamp(13px, 1.05vw, 14.5px);
  font-weight: 500;
  letter-spacing: 0.14em; text-transform: uppercase;
  text-decoration: none;
  white-space: nowrap;
  transition: background var(--raw-dur-short) var(--raw-ease-out),
              transform var(--raw-dur-short) var(--raw-ease-out);
}
/* La flecha, al sesgo.

   Era una línea al ras, prestada de las filas del índice del sistema. Ahí funciona
   porque rima con las hairlines de cada fila; dentro de un botón relleno no tiene
   con qué rimar y se lee como un guion colgado.

   Con punta, para que se lea como dirección y no como guion. Sigue siendo una línea
   de 1px, así que no rompe el lenguaje de hairlines del sitio. */
.boton__flecha {
  position: relative;
  width: 1.6em; height: 1px;
  background: currentColor;
  transition: width var(--raw-dur-short) var(--raw-ease-out);
}
.boton__flecha::after {
  content: ""; position: absolute; right: 0; top: 50%;
  width: 0.42em; height: 0.42em;
  border-top: 1px solid currentColor;
  border-right: 1px solid currentColor;
  transform: translateY(-50%) rotate(45deg);
}
.boton:hover { background: var(--tinta-inv); transform: translateY(-2px); }
.boton:hover .boton__flecha { width: 2em; }
.boton:focus-visible { outline: 2px solid var(--tinta-inv); outline-offset: 4px; }

@media (max-width: 860px) {
  .pedido { grid-template-columns: minmax(0, 1fr); align-items: start; }
  .pedido__via { justify-items: stretch; }
  .pedido__via .contactos { justify-content: flex-start; }
  .boton { width: 100%; justify-content: center; }
}

@media (prefers-reduced-motion: reduce) {
  .boton, .boton__flecha { transition: none; }
  .boton:hover { transform: none; }
}

.cierre__wordmark {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(46px, 7vw, 96px);
  line-height: 1;
  color: var(--tinta-inv);
  /* firma, no titular: va después del pedido y con menos aire que antes */
  margin-top: clamp(76px, 9vw, 128px);
}
.cierre__bajada {
  margin-top: clamp(8px, 1vw, 14px);
  font-size: clamp(10.5px, 0.85vw, 12px);
  letter-spacing: 0.34em; text-transform: uppercase;
  color: var(--acento);
}
/* Secundarios respecto del botón: quedan debajo, alineados a la izquierda y un
   punto más chicos. Antes eran tres links del mismo peso y no había un cuarto que
   los ordenara, así que el lector tenía que elegir sin ninguna pista. */
.contactos {
  display: flex; flex-wrap: wrap; justify-content: flex-start;
  gap: 8px clamp(16px, 2.4vw, 32px);
  margin-top: clamp(20px, 2.4vw, 30px);
  font-size: clamp(13px, 1vw, 14px);
  color: var(--tinta-inv-2);
}
.contactos a {
  white-space: nowrap;
  transition: color var(--raw-dur-short) var(--raw-ease-out);
}
.contactos a:hover { color: var(--acento); }
.cierre__pie {
  width: 100%; max-width: var(--ancho);
  margin-top: clamp(56px, 7vw, 96px);
  padding-top: clamp(22px, 2.6vw, 32px);
  border-top: 1px solid var(--hairline);
  display: flex; flex-wrap: wrap; justify-content: space-between; gap: 8px 20px;
  font-size: 11.5px;
  color: var(--tinta-inv-2);
}

/* ─────────────────────────  revelado  ───────────────────────── */

/* El estado inicial lo escribe el motor (`cascada` / `palabras`) en el primer cuadro.
   NO va un `opacity: 0` acá: la clase .rev sobrevivió a la función que la encendía y
   dejó secciones enteras invisibles con su contenido animado correctamente adentro.
   Una regla que apaga algo tiene que vivir al lado de la que lo enciende. */
.js [data-partido] { opacity: 1; }

/* ─────────────────────────  responsive  ───────────────────────── */

@media (max-width: 1023px) {
  .quienes__grid, .revenue__grid { grid-template-columns: minmax(0, 1fr); }
  .socio {
    grid-template-columns: minmax(0, 46px) minmax(0, 1fr);
    row-gap: clamp(16px, 2.4vw, 24px);
  }
  .socio__foto { grid-column: 2; max-width: 240px; }
  .socio__texto { grid-column: 2; }
  .servicio {
    grid-template-columns: minmax(0, 46px) minmax(0, 1fr);
    row-gap: 10px;
  }
  .servicio__desc { grid-column: 2; }
}

@media (max-width: 639px) {
  .socio__foto { max-width: 62%; }
  /* A 390 la foto tapaba el 76% de la palabra y se leía "N...e.". El gesto necesita
     oclusión, no borrado: se agranda la palabra y se achica la foto. */
  .hero__palabra { font-size: clamp(104px, 27vw, 320px); }
  .hero__retrato { width: 42vw; }
  .hero__centro { min-height: calc(42vw / 0.75); }
  .cierre__pie { justify-content: flex-start; }
  /* aire para el WhatsApp flotante: sin esto tapa el pie */
  .cierre { padding-bottom: 96px; }
}

/* Los !important viven todos acá: es el único bloque que tiene que ganarle a un
   estilo inline escrito por el motor. */
@media (prefers-reduced-motion: reduce) {
  .js .rev { opacity: 1 !important; transform: none !important; }
  .js .hero__palabra, .js .hero__retrato, .js .hero__marca-bajada,
  .js .hero__bajada, .js .esq { opacity: 1 !important; transform: none !important; }
  .js .hero__retrato { transform: translate(-50%, -50%) !important; }
}

/* ─────────────────────────  5b · el motor, vivo  ─────────────────────────
   Noreve vende que construyó su propio sistema. Una empresa cuyo argumento es
   el software tiene que MOSTRAR el software: esto es la interfaz de verdad,
   viva, no una captura ni un chrome de navegador dibujado (que los gates
   prohíben justamente por eso). */

.motor { padding: var(--seccion) var(--margen); }
.motor__cabeza { max-width: var(--ancho); margin-inline: auto; }
.motor__nota {
  margin-top: clamp(14px, 1.6vw, 20px);
  font-size: clamp(12.5px, 1vw, 13.5px);
  letter-spacing: 0.04em;
  color: var(--tinta-inv-2);
}

.motor__cuerpo { max-width: var(--ancho); margin-inline: auto; }
.panel-motor {
  margin-top: clamp(40px, 5vw, 72px);
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1.06fr);
  gap: 0;
  border: 1px solid var(--hairline);
  background: var(--oscuro-2);
}

/* ── los insumos ── */
.panel-motor__insumos { border-right: 1px solid var(--hairline); }
.insumo {
  padding: clamp(22px, 2.6vw, 34px) clamp(22px, 2.8vw, 38px);
  border-bottom: 1px solid var(--hairline);
  display: grid;
  grid-template-columns: minmax(0, 1fr) auto;
  align-items: baseline;
  column-gap: 16px;
}
.insumo:last-child { border-bottom: 0; }
.insumo__label {
  font-size: clamp(11.5px, 0.95vw, 13px);
  letter-spacing: 0.06em;
  color: var(--tinta-inv-2);
}
.insumo__valor {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(22px, 2.3vw, 32px);
  line-height: 1;
  color: var(--tinta-inv);
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}
.insumo__valor i { font-style: italic; opacity: 0.55; font-size: 0.6em; }
.insumo__barra {
  grid-column: 1 / -1;
  margin-top: clamp(12px, 1.4vw, 18px);
  display: block; height: 1px;
  background: color-mix(in srgb, var(--raw-crema) 12%, transparent);
}
.insumo__barra i { display: block; height: 100%; width: 0%; background: var(--acento); }

/* ── la salida ── */
.panel-motor__salida {
  padding: clamp(22px, 2.8vw, 38px);
  display: grid; align-content: start;
}
.salida__label {
  font-size: clamp(11.5px, 0.95vw, 13px);
  letter-spacing: 0.06em;
  color: var(--tinta-inv-2);
}
.salida__tarifa {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(52px, 7.4vw, 104px);
  line-height: 1;
  letter-spacing: -0.02em;
  color: var(--acento);
  font-variant-numeric: tabular-nums;
  margin-top: clamp(8px, 1vw, 14px);
  white-space: nowrap;
}
.salida__tarifa i { font-size: 0.42em; opacity: 0.6; vertical-align: 0.5em; }
.salida__delta {
  margin-top: clamp(8px, 1vw, 12px);
  font-size: clamp(12.5px, 1.05vw, 14px);
  color: var(--tinta-inv-2);
  font-variant-numeric: tabular-nums;
  min-height: 1lh;              /* reservado: el delta no empuja la curva */
}
.salida__curva {
  width: 100%; height: clamp(90px, 11vw, 150px);
  display: block;
  margin-top: clamp(20px, 2.4vw, 32px);
}
.salida__pie {
  display: flex; justify-content: space-between; gap: 16px;
  margin-top: clamp(10px, 1.2vw, 14px);
  font-size: clamp(10.5px, 0.85vw, 11.5px);
  letter-spacing: 0.14em; text-transform: uppercase;
  color: var(--tinta-inv-2);
}
#pulso { transition: opacity var(--raw-dur-short) var(--raw-ease-out); opacity: 0; }
#pulso[data-activo] { opacity: 1; color: var(--acento); }

@media (max-width: 1023px) {
  .panel-motor { grid-template-columns: minmax(0, 1fr); }
  .panel-motor__insumos { border-right: 0; border-bottom: 1px solid var(--hairline); }
}

/* ─────────────────────────  4b · el PMS, vivo  ───────────────────────── */

/* Las dos demostraciones (ésta y el motor) comparten tratamiento a propósito.

   DOS cambios que resuelven lo mismo. El primero: la sección va sobre crema y la
   pieza queda como una placa oscura encima. Desde el índice del sistema hasta el
   cierre había SEIS secciones oscuras seguidas, y el propio proyecto tiene la regla
   escrita en "Quiénes somos" ("dos claras seguidas matan ese corte"), sólo que se
   abandonaba después de los socios. Invertir la pieza en sí no era opción: el
   calendario y el panel del motor están construidos con los tokens de fondo oscuro.
   Como placa sobre crema no hay que tocarles un color y encima ganan presencia, que
   es lo que hace Ghost con su dashboard.

   El segundo: la composición pasa a partida, texto a la izquierda y pieza a la
   derecha. Antes el índice, el calendario y el motor eran las tres "cabeza arriba,
   cuerpo abajo", tres secciones seguidas con el mismo esqueleto. Partidas, las dos
   demos se emparentan entre sí, se separan del índice que las precede, y reusan el
   split que ya usan "Quiénes somos" y los socios: continuidad interna, no un patrón
   nuevo. */
.demo {
  padding: var(--seccion) var(--margen);
  background: var(--claro);
  color: var(--tinta);
}
.demo__grid {
  max-width: var(--ancho); margin-inline: auto;
  display: grid;
  grid-template-columns: minmax(0, 0.72fr) minmax(0, 1.28fr);
  gap: clamp(32px, 5vw, 86px);
  align-items: start;
}
/* La cabeza se queda arriba mientras la pieza pasa: en una columna de texto corta
   junto a una pieza alta, pegarla al borde superior deja un hueco enorme debajo. */
.demo__grid > :first-child { position: sticky; top: clamp(110px, 14vh, 150px); }
.demo .etiqueta { color: var(--acento-oscuro); }
.demo .titulo { color: var(--tinta); }
.demo .motor__nota { color: var(--tinta-2); }
/* La leyenda vive FUERA de la placa oscura, así que al pasar la sección a crema
   quedó en crema apagado sobre crema: 2,69 de contraste, prácticamente invisible. */
.demo .leyenda, .demo .leyenda li { color: var(--tinta-2); }

/* Los cuerpos traían `max-width` y `margin-inline: auto` de cuando eran bloques a
   ancho de página. Dentro del grid ese `auto` a los dos lados los encoge a su
   contenido en vez de estirarlos, así que el calendario quedaba en 540px centrado
   dentro de una columna de 790 y con las celdas más chicas de lo necesario. */
.demo .pms__cuerpo, .demo .motor__cuerpo {
  max-width: none; margin-inline: 0; margin-top: 0;
}

@media (max-width: 900px) {
  .demo__grid { grid-template-columns: minmax(0, 1fr); }
  .demo__grid > :first-child { position: static; }
}

.pms { padding: var(--seccion) var(--margen); }
.pms__cabeza, .pms__cuerpo { max-width: var(--ancho); margin-inline: auto; }
.pms__cuerpo { margin-top: clamp(40px, 5vw, 72px); }

.calendario {
  border: 1px solid var(--hairline);
  background: var(--oscuro-2);
  padding: clamp(16px, 2vw, 26px);
  overflow: clip;
}
.calendario__dias {
  display: grid;
  grid-template-columns: minmax(0, 96px) repeat(14, minmax(0, 1fr));
  gap: 3px;
  margin-bottom: 10px;
}
.calendario__dias span {
  font-size: clamp(9px, 0.72vw, 10.5px);
  letter-spacing: 0.1em; text-transform: uppercase;
  color: var(--tinta-inv-2);
  text-align: center;
}
.calendario__dias span:first-child { text-align: left; }
.calendario__filas { display: grid; gap: 3px; }

.cal-fila {
  display: grid;
  grid-template-columns: minmax(0, 96px) repeat(14, minmax(0, 1fr));
  gap: 3px;
  align-items: stretch;
}
.cal-fila__hab {
  font-size: clamp(10.5px, 0.85vw, 12px);
  color: var(--tinta-inv-2);
  display: flex; align-items: center;
  white-space: nowrap;
}
.cal-celda {
  height: clamp(26px, 2.6vw, 34px);
  background: color-mix(in srgb, var(--raw-crema) 5%, transparent);
  position: relative;
}
.cal-bloque {
  position: absolute; inset: 0;
  display: flex; align-items: center;
  padding-inline: clamp(5px, 0.6vw, 9px);
  font-size: clamp(8.5px, 0.7vw, 10px);
  letter-spacing: 0.04em;
  white-space: nowrap; overflow: clip;
  transform-origin: left center;
  transform: scaleX(0);
}
.cal-bloque[data-e="confirmada"] { background: color-mix(in srgb, var(--raw-dorado) 34%, transparent); color: var(--tinta-inv); }
.cal-bloque[data-e="encasa"]     { background: var(--raw-dorado); color: var(--raw-negro); }
.cal-bloque[data-e="limpieza"]   { background: color-mix(in srgb, var(--raw-crema) 16%, transparent); color: var(--tinta-inv-2); }

.leyenda {
  display: flex; flex-wrap: wrap; gap: 10px clamp(18px, 2.4vw, 30px);
  margin-top: clamp(16px, 2vw, 24px);
  font-size: clamp(10.5px, 0.85vw, 11.5px);
  color: var(--tinta-inv-2);
}
.leyenda li { display: flex; align-items: center; gap: 8px; }
.leyenda i { width: 16px; height: 8px; display: block; }
.leyenda i[data-e="confirmada"] { background: color-mix(in srgb, var(--raw-dorado) 34%, transparent); }
.leyenda i[data-e="encasa"]     { background: var(--raw-dorado); }
.leyenda i[data-e="limpieza"]   { background: color-mix(in srgb, var(--raw-crema) 16%, transparent); }
.leyenda i[data-e="libre"]      { background: color-mix(in srgb, var(--raw-crema) 5%, transparent); }

@media (max-width: 767px) {
  /* A 390 catorce noches dan columnas de 14px: ilegible. Se muestran siete. */
  .calendario__dias, .cal-fila { grid-template-columns: minmax(0, 62px) repeat(7, minmax(0, 1fr)); }
  .calendario__dias span:nth-child(n+9), .cal-fila .cal-celda:nth-child(n+9) { display: none; }
}

/* ─────────────────────────  el velo  ───────────────────────── */

.velo {
  position: fixed; inset: 0; z-index: 100;
  display: grid; place-items: center;
  background: var(--oscuro);
}
.velo[data-listo] { pointer-events: none; }
.velo__centro { display: grid; justify-items: center; gap: clamp(22px, 2.6vw, 32px); }
.velo__marca {
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(32px, 4vw, 52px);
  line-height: 1;
  color: var(--tinta-inv);
}
.velo__medidor {
  display: block; width: min(220px, 40vw); height: 1px;
  background: color-mix(in srgb, var(--raw-crema) 18%, transparent);
  overflow: clip;
}
.velo__medidor i {
  display: block; height: 100%; width: 100%;
  background: var(--acento);
  transform-origin: left; transform: scaleX(0);
}

/* ─────────────────────────  1 · el viaje  ─────────────────────────
   Tres pantallas de scroll sobre una sola toma. El video se scrubbea con
   currentTime, no se reproduce: la cámara avanza con el dedo del lector. */

.viaje { position: relative; height: 320svh; background: var(--oscuro); }
.viaje__pin {
  position: sticky; top: 0;
  height: 100svh;
  overflow: clip;
  isolation: isolate;
}
.viaje__video {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  object-fit: cover;
  z-index: -2;
}
.viaje__velo {
  position: absolute; inset: 0; z-index: -1;
  background:
    radial-gradient(86% 66% at 46% 44%, rgb(13 11 10 / 0.06) 0%, rgb(13 11 10 / 0.34) 62%, rgb(13 11 10 / 0.66) 100%),
    linear-gradient(to bottom, rgb(13 11 10 / 0.46) 0%, rgb(13 11 10 / 0) 22%, rgb(13 11 10 / 0) 66%, var(--oscuro) 100%);
}

/* los capítulos: absolutos y superpuestos, cruzan por opacidad */
/* Scrim DIRECCIONAL: nace del borde donde está el texto y muere al tercio.
   Un velo global aplana toda la toma; éste sólo apoya la columna que hay que leer,
   y deja el resto del plano con su contraste original. */
.cap::before {
  content: ""; position: absolute; inset: 0; z-index: -1; pointer-events: none;
}
.cap--izq::before {
  background: linear-gradient(to right, rgb(13 11 10 / 0.82) 0%, rgb(13 11 10 / 0.52) 26%, rgb(13 11 10 / 0) 58%);
}
.cap--der::before {
  background: linear-gradient(to left, rgb(13 11 10 / 0.82) 0%, rgb(13 11 10 / 0.52) 26%, rgb(13 11 10 / 0) 58%);
}
.cap--centro::before {
  background: radial-gradient(62% 42% at 50% 52%, rgb(13 11 10 / 0.56) 0%, rgb(13 11 10 / 0.28) 56%, rgb(13 11 10 / 0) 100%);
}

.cap {
  position: absolute;
  inset: 0;
  isolation: isolate;
  display: grid; align-content: center;
  padding: clamp(96px, 14vh, 150px) var(--margen) clamp(72px, 11vh, 120px);
  opacity: 0;
  pointer-events: none;
  will-change: opacity, transform;
}
/* El capítulo del título NO se centra como una pila: se compone como specimen.
   La palabra sangra el marco (que es el rasgo de Liron Moran que estamos
   preservando) y la bajada se ancla a SU borde izquierdo, no al centro del
   viewport. Centrada bajo el medio de la palabra flotaba en un hueco muerto. */
.cap--centro { justify-items: stretch; text-align: center; }
.cap--izq    { justify-items: start;  text-align: left;  }
.cap--der    { justify-items: end;    text-align: right; }

.cap__palabra {
  font-family: var(--f-serif); font-style: italic; font-weight: 400;
  /* Pedido del cliente: mas chica y centrada sobre la regla del lockup, en vez
     del recorte por el marco que traia de Liron Moran. */
  font-size: clamp(76px, 18vw, 290px);
  margin-inline: auto;
  line-height: 0.92;
  letter-spacing: -0.02em;
  color: var(--tinta-inv);
  white-space: nowrap;
  user-select: none;
}
/* La itálica de Playfair desborda su caja por abajo (line-height .82 + descendentes),
   así que el margen normal dejaba la bajada ENCIMA de la palabra. El padding
   reserva el alto real del glifo; el margen ya no pelea contra el desborde. */
.cap__palabra { padding-bottom: 0.14em; }
/* La bajada, la regla y el lugar en UNA línea: el lockup cierra la palabra por
   abajo en vez de colgar de ella. La regla se come todo el sobrante, así que el
   bloque llega siempre al margen derecho sea cual sea el ancho. */
.lockup {
  display: grid; grid-template-columns: auto 1fr auto;
  align-items: center; gap: clamp(14px, 1.6vw, 24px);
  margin-top: clamp(14px, 1.6vw, 22px);
  width: 100%;
}
.lockup__regla { height: 1px; background: var(--acento); opacity: 0.42; }
.cap__marca, .cap__lugar {
  font-size: clamp(10.5px, 0.86vw, 12.5px);
  letter-spacing: 0.3em; text-transform: uppercase;
  white-space: nowrap;
}
.cap__marca { color: var(--acento); }
.cap__lugar { color: var(--tinta-inv-2); letter-spacing: 0.22em; }
.cap__etiqueta {
  font-size: clamp(10.5px, 0.85vw, 12px);
  letter-spacing: 0.24em; text-transform: uppercase;
  color: var(--acento);
}
.cap__frase {
  margin-top: clamp(14px, 1.8vw, 24px);
  font-family: var(--f-serif); font-style: italic;
  font-size: clamp(38px, 5.6vw, 88px);
  line-height: 1.04;
  letter-spacing: -0.02em;
  color: var(--tinta-inv);
}
.cap__frase, .cap__pie, .cap__etiqueta { max-width: min(46ch, 52vw); }
.cap__pie {
  margin-top: clamp(16px, 2vw, 26px);
  font-size: clamp(13.5px, 1.05vw, 15.5px);
  line-height: 1.7;
  color: var(--tinta-inv-2);
}

@media (max-width: 639px) {
  .cap--der, .cap--izq { justify-items: start; text-align: left; }
  .cap__palabra { font-size: clamp(104px, 28vw, 340px); }
}

/* el poster manda hasta que el blob está montado; después manda el metraje */
.viaje__video { opacity: 0; transition: opacity 600ms cubic-bezier(.22,.61,.36,1); }
.viaje__video.esta { opacity: 1; }
.viaje__pin::before {          /* el poster, siempre debajo: si el mp4 falla, esto queda */
  content: ""; position: absolute; inset: 0; z-index: -3;
  background: url("img/recepcion-still.jpg") center / cover no-repeat;
}
@media (prefers-reduced-motion: reduce) { .viaje { height: 100svh; } .viaje__video { display: none; } }

/* ─────────────────────────  vocabulario de motion  ───────────────────────── */

/* Las palabras partidas: inline-block para que acepten translate, y sin cambiar
   el ritmo de la línea. El .js- evita que un lector sin JS vea el texto en cero. */
.js .pal { display: inline-block; opacity: 0; will-change: transform, opacity; }
.pal { display: inline-block; }

/* Las capas con paralaje se componen aparte o el navegador repinta la sección entera */
.js .socio__foto, .js .quienes .circulo { will-change: transform; }


/* Con movimiento reducido nada queda en cero: el contenido se ve entero y quieto. */
@media (prefers-reduced-motion: reduce) {
  .js .pal { opacity: 1 !important; transform: none !important; }
  .js .socio__foto, .js .quienes .circulo { transform: none !important; }
}

/* ── traspaso entre secciones ──
   clip-path no participa del layout: si la aritmética se va de rango, la sección se
   recorta fea pero NUNCA empuja a la de al lado ni abre un hueco. Por eso no es
   transform: un transform acá sacaría del marco del viewport a cualquier sticky. */
/* Sin recorte. La placa entrante dejaba ver por su borde superior el fondo de la
   página: entre dos secciones del mismo tono no se nota, pero cuando la que entra
   es crema y lo de atrás es negro queda una franja oscura de unos 13px que se lee
   como un error de maquetado. Queda la sombra, que es lo que daba la profundidad;
   el recorte sólo aportaba el problema. */
.js .traspaso { will-change: auto; }
/* la placa proyecta sombra sobre lo que queda arriba mientras sube */
.js .traspaso::before {
  content: ""; position: absolute; left: 0; right: 0; top: 0;
  height: 120px; pointer-events: none; z-index: 3;
  opacity: calc(1 - var(--entra, 1));
  background: linear-gradient(to bottom, rgb(0 0 0 / 0.38), rgb(0 0 0 / 0));
}
.js .traspaso { position: relative; }

/* ── traspaso por fundido: sólo para la sección que sigue al hero ──
   El hero cierra a negro, así que la que entra tiene que NACER de ese negro. Con
   el recorte de la placa, en cambio, su metraje entraba cortado y arriba quedaba
   una banda de fondo plano: se leía como un hueco entre dos secciones, no como un
   corte de cámara. Acá no se recorta nada: la sección está entera desde el primer
   cuadro y lo que se abre es el negro que tiene encima. */
.js .traspaso--fundido { clip-path: none; }
.js .traspaso--fundido::before {
  content: ""; position: absolute; inset: 0; z-index: 5;
  pointer-events: none;
  background: var(--oscuro);
  opacity: calc(1 - var(--entra, 1));
  height: auto;
}
@media (prefers-reduced-motion: reduce) {
  .js .traspaso--fundido::before { display: none; }
}

@media (prefers-reduced-motion: reduce) {
  .js .traspaso { clip-path: none; }
  .js .traspaso::before { display: none; }
}

/* ─────────────────────  el hero, tratamiento de cine  ─────────────────────

   Cuatro capas que separan "un video de fondo" de una toma. Ninguna es decorado:
   cada una imita una propiedad física de una cámara real.

   1 · BARRAS ANAMÓRFICAS. La toma abre en 2.39:1 y las barras se retiran en la
       entrada. Es la señal de "esto es una película" más barata y más legible que
       existe, y además encuadra el wordmark antes de que el lector vea nada más.
   2 · GRANO. Una emulsión real tiene ruido. Sin grano, una imagen generada se lee
       como render; con grano, se lee como material filmado. Se anima por pasos
       (steps) y no de forma continua: el grano de película salta cuadro a cuadro,
       no se desliza.
   3 · VIÑETA Y BLOOM. La luz del LED sangra hacia la sombra como en una lente real.
   4 · RESPIRACIÓN. Un escalado lentísimo permanente: aunque el lector no scrollee,
       la toma nunca queda congelada. Una imagen quieta delata que es una foto. */

.viaje__barra {
  position: absolute; left: 0; right: 0; z-index: 4;
  height: var(--barra, 10.5vh);
  background: var(--oscuro);
  pointer-events: none;
}
.viaje__barra--arriba { top: 0; }
.viaje__barra--abajo  { bottom: 0; }

/* grano: ruido fractal en un SVG inline, sin pedir un archivo más */
/* inset -20% y no -120%: la animación sólo traslada ±3%, pero a -120% la capa
   medía 3,4× el viewport de lado — once veces el área — y todo eso se compone con
   mix-blend-mode encima del video en cada cuadro. */
.viaje__grano {
  position: absolute; inset: -20%;
  z-index: 3; pointer-events: none;
  opacity: 0.16; mix-blend-mode: overlay;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='180' height='180'%3E%3Cfilter id='r'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.82' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='180' height='180' filter='url(%23r)'/%3E%3C/svg%3E");
  animation: granea 0.6s steps(6) infinite;
}
@keyframes granea {
  0%   { transform: translate3d(0, 0, 0); }
  16%  { transform: translate3d(-3%, 2%, 0); }
  33%  { transform: translate3d(2%, -3%, 0); }
  50%  { transform: translate3d(-2%, -2%, 0); }
  66%  { transform: translate3d(3%, 1%, 0); }
  83%  { transform: translate3d(-1%, 3%, 0); }
  100% { transform: translate3d(0, 0, 0); }
}

/* viñeta + bloom cálido saliendo de la línea de LED */
.viaje__pin::after {
  content: ""; position: absolute; inset: 0; z-index: 2; pointer-events: none;
  background:
    radial-gradient(38% 30% at 28% 26%, rgb(214 178 110 / 0.16) 0%, rgb(214 178 110 / 0) 70%),
    radial-gradient(120% 90% at 50% 50%, rgb(0 0 0 / 0) 52%, rgb(0 0 0 / 0.46) 100%);
}

/* respiración: el motor escribe --resp; el escalado nunca vuelve a 1 exacto */
.viaje__video {
  transform: scale(calc(1.04 + var(--resp, 0) * 0.05));
  transform-origin: 52% 46%;
}
/* el poster NO respira: es la red de seguridad, y escalando dos capas del tamaño
   del viewport en cada cuadro se paga el doble por un efecto que sólo se ve en una */
.viaje__pin::before { transform: scale(1.04); transform-origin: 52% 46%; }

/* el wordmark se atraviesa: al avanzar el viaje escala y se desenfoca, como si la
   cámara pasara POR la palabra en vez de que la palabra se apague */
.cap--centro { transform-origin: 50% 46%; }

@media (prefers-reduced-motion: reduce) {
  .viaje__grano { animation: none; opacity: 0.08; }
  .viaje__barra { display: none; }
  .viaje__video, .viaje__pin::before { transform: none; }
}

/* ── el menú ──
   Sobre la toma el header necesita su propio apoyo: un scrim de 1 sola dirección
   arriba de todo, no un fondo sólido que cortaría el plano en dos. */
.marca { opacity: 0; }
.marca::before {
  content: ""; position: absolute; inset: -1px 0 auto 0; height: 190px; z-index: -1;
  pointer-events: none;
  background: linear-gradient(to bottom, rgb(13 11 10 / 0.58) 0%, rgb(13 11 10 / 0) 100%);
  opacity: var(--scrim, 1);
  transition: opacity 320ms var(--raw-ease-out);
}
.marca[data-sobre="claro"]::before { opacity: 0; }

.menu {
  display: flex; gap: clamp(20px, 2.4vw, 38px);
  justify-self: center;
}
.menu a {
  font-size: 12px; letter-spacing: 0.16em; text-transform: uppercase;
  color: rgb(247 236 232 / 0.72); text-decoration: none;
  position: relative; padding-block: 4px;
  transition: color 260ms var(--raw-ease-out);
}
/* El ítem sin destino no promete interacción: ni cursor de mano ni el subrayado
   que se dibuja al pasar. Se ve igual que los otros, pero no responde. */
.menu a:not([href]) { cursor: default; }
.menu a:not([href])::after { content: none; }

.menu a::after {
  content: ""; position: absolute; left: 0; right: 0; bottom: 0; height: 1px;
  background: currentColor; transform: scaleX(0); transform-origin: right;
  transition: transform 320ms var(--raw-ease-out);
}
.menu a:hover { color: var(--tinta-inv); }
.menu a:hover::after { transform: scaleX(1); transform-origin: left; }
.marca[data-sobre="claro"] .menu a { color: rgb(13 11 10 / 0.66); }
.marca[data-sobre="claro"] .menu a:hover { color: var(--tinta); }

@media (max-width: 899px) { .menu { display: none; } }

/* ─────────────────  secciones sobre metraje  ─────────────────

   El fondo se FIJA mientras la sección pasa por encima. El truco es
   `position: sticky` + `margin-bottom: -100svh`: la caja se pega al viewport pero
   no ocupa lugar en el flujo, así que el contenido de la sección arranca arriba de
   todo como si el fondo no existiera.

   Por qué sticky y no fixed: un `fixed` se escaparía de la sección y seguiría
   visible en las de al lado; sticky nace y muere con su contenedor. Y por qué no
   `background-attachment: fixed`: no acepta video y en móvil está roto. */

/* min-height 100svh: el fondo es una caja sticky de una pantalla de alto. Si la
   sección mide menos, la caja se va con ella antes de terminar de mostrarse y la
   sección se ve en negro plano — que es lo que pasaba con el remate del 24/7. */
/* min-height 100svh: el fondo es una caja sticky de una pantalla de alto. Si la
   sección mide menos, la caja se va con ella antes de terminar de mostrarse y la
   sección se ve en negro plano — que es lo que pasaba con el remate del 24/7.
   Y NO lleva `display: grid`: el fondo pasa a ser ítem de grilla y se encajona en
   la columna del contenido en vez de sangrar la pantalla. El centrado vertical,
   donde hace falta, se resuelve en la sección y no acá. */
.sobre-metraje {
  position: relative; isolation: isolate;
  min-height: 100svh;
}
/* el remate es una sola cifra: va centrado en su pantalla */
.remate.sobre-metraje { display: flex; flex-direction: column; justify-content: center; }
.remate.sobre-metraje > .fondo { position: sticky; flex: 0 0 auto; align-self: stretch; }
/* z-index 0 y NO -1: un hijo con z-index negativo se pinta DETRÁS del fondo de su
   propio padre, y `.oscuro` le pone un background sólido a la sección. El metraje
   quedaba tapado por el color de la sección que tenía que estar abajo. */
.fondo {
  position: sticky; top: 0;
  height: 100svh;
  margin-bottom: -100svh;
  z-index: 0;
  overflow: clip;
  pointer-events: none;
}
.fondo .toma__video {
  position: absolute; inset: 0; z-index: 1;
  width: 100%; height: 100%; object-fit: cover;
  opacity: 0; transition: opacity 700ms var(--raw-ease-out);
}
.fondo .toma__video.esta { opacity: 1; }
.fondo__poster {
  position: absolute; inset: 0; z-index: 0;
  background-size: cover; background-position: center;
}

/* El scrim nace del lado donde está el texto y muere al 62%. Nunca un velo parejo:
   aplana la toma y tira a la basura el trabajo del metraje. */
.fondo__scrim { position: absolute; inset: 0; z-index: 3; }
/* Medido sobre la fachada al atardecer: con 0.62 al 30% el cuerpo de texto quedaba
   en 2,4:1 sobre las ventanas iluminadas. El scrim tiene que resolverse contra la
   zona MÁS clara de la toma, no contra su promedio. */
[data-lado="izq"] .fondo__scrim {
  background: linear-gradient(to right, rgb(13 11 10 / 0.95) 0%, rgb(13 11 10 / 0.88) 34%, rgb(13 11 10 / 0.42) 62%, rgb(13 11 10 / 0.24) 100%);
}
[data-lado="der"] .fondo__scrim {
  background: linear-gradient(to left, rgb(13 11 10 / 0.95) 0%, rgb(13 11 10 / 0.88) 34%, rgb(13 11 10 / 0.42) 62%, rgb(13 11 10 / 0.24) 100%);
}
/* `pleno` lleva listas largas encima (8 servicios, 6 módulos), así que el scrim
   tiene que ser una base y no un tinte: con 0.38 en el medio los nombres en serif
   caían a 2,8:1 contra el reflejo de la pileta. La toma se sigue leyendo, pero el
   texto gana siempre. */
/* `centro` es para bloques de poco texto: un radial suave que apoya el centro y
   deja los bordes con el contraste de la toma. El `pleno` sobre una toma ya oscura
   —la grúa termina en el techo al anochecer— la convierte en barro. */
[data-lado="centro"] .fondo__scrim {
  background: radial-gradient(58% 40% at 50% 46%, rgb(13 11 10 / 0.72) 0%, rgb(13 11 10 / 0.42) 54%, rgb(13 11 10 / 0.1) 100%);
}
[data-lado="pleno"] .fondo__scrim {
  background:
    linear-gradient(to bottom, rgb(13 11 10 / 0.9) 0%, rgb(13 11 10 / 0.78) 36%, rgb(13 11 10 / 0.72) 64%, rgb(13 11 10 / 0.92) 100%);
}

/* grano y viñeta, las mismas dos capas del hero: sin ellas el fondo se lee como
   render y no como material filmado */
.fondo__grano {
  position: absolute; inset: -20%; z-index: 2;
  opacity: 0.13; mix-blend-mode: overlay;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='180' height='180'%3E%3Cfilter id='r'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.82' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='180' height='180' filter='url(%23r)'/%3E%3C/svg%3E");
  animation: granea 0.6s steps(6) infinite;
}
.fondo::after {
  content: ""; position: absolute; inset: 0; z-index: 4;
  background: radial-gradient(120% 90% at 50% 50%, rgb(0 0 0 / 0) 54%, rgb(0 0 0 / 0.5) 100%);
}

/* el contenido de una sección sobre metraje se acota al lado del scrim */
.sobre-metraje > :not(.fondo) { position: relative; z-index: 1; }
/* `.columna` acota el bloque al lado del scrim. Si el bloque YA era una grilla de
   dos columnas, se pasa a una sola: meter dos columnas en 46vw da renglones de
   veinte caracteres, que es lo que pasaba en quiénes somos. */
.columna { display: block !important; max-width: min(54ch, 48vw); }
/* los !important pisan el `margin-inline: auto` que centra estos bloques cuando la
   sección era clara y de ancho acotado; acá tienen que pegarse a su lado */
[data-lado="izq"] .columna { margin-left: 0 !important; margin-right: auto !important; }
[data-lado="der"] .columna { margin-right: 0 !important; margin-left: auto !important; text-align: right; }
.columna > * + * { margin-top: clamp(26px, 3.4vw, 46px); }

@media (max-width: 899px) {
  [data-lado="izq"] .columna, [data-lado="der"] .columna { max-width: none; text-align: left; }
  [data-lado="der"] .fondo__scrim, [data-lado="izq"] .fondo__scrim {
    background: linear-gradient(to bottom, rgb(13 11 10 / 0.72) 0%, rgb(13 11 10 / 0.5) 45%, rgb(13 11 10 / 0.82) 100%);
  }
}
@media (prefers-reduced-motion: reduce) { .fondo__grano { animation: none; opacity: 0.07; } }

/* ── inversión de tinta en las secciones que pasaron a estar sobre metraje ──
   Eran claras y su texto está escrito con los tokens de tinta oscura. En vez de
   cambiar clase por clase en el HTML (que deja el marcado mintiendo sobre qué es
   cada cosa), se invierte por contenedor: la sección ES oscura ahora. */

.sobre-metraje { color: var(--tinta-inv); }
.sobre-metraje .titulo,
.sobre-metraje .numeral__cifra,
.sobre-metraje h2, .sobre-metraje h3 { color: var(--tinta-inv); }
.sobre-metraje .etiqueta { color: var(--acento); }
.sobre-metraje p, .sobre-metraje li { color: var(--tinta-inv-2); }
.sobre-metraje strong { color: var(--tinta-inv); font-weight: 500; }
.sobre-metraje .punto { color: var(--acento); }

/* hairlines y bordes: los de las secciones claras son negros al 10% y sobre
   metraje desaparecen */
.sobre-metraje .servicio,
.sobre-metraje .modulo,
.sobre-metraje .insumos li { border-color: rgb(247 236 232 / 0.16); }

/* El padding lateral se le saca a la SECCIÓN y se le da al contenido: si queda en
   la sección, el fondo fijado lo hereda y la toma aparece con márgenes blancos a
   los costados en vez de sangrar la pantalla. */
/* El aire vertical va en el CONTENIDO y no en la sección: si lo lleva la sección,
   el metraje arranca después de ese aire y, mientras la sección entra, queda una
   banda de fondo plano entre el plano que se va y el que llega — se lee como un
   hueco. Con el padding acá, el fondo sangra de borde a borde y el texto conserva
   su respiro. */
.sobre-metraje { padding: 0 0 var(--seccion); }
.sobre-metraje > :not(.fondo) { padding-inline: var(--margen); }
/* El aire de arriba lo lleva el primer bloque de contenido, no la sección: así el
   metraje sangra desde el borde exacto y no queda banda mientras la sección entra.
   Se usa `.fondo + *` y no :first-of-type porque el fondo también es un div. */
.sobre-metraje > .fondo + * { padding-block-start: var(--seccion); }

/* ─────────────────────  la toma: respiro a sangre  ─────────────────────

   Un plano suelto entre dos bloques de contenido, sin titular. Es el respiro del
   montaje: si todas las secciones argumentan, ninguna respira, y la página se lee
   como un folleto. El único texto es un rótulo de esquina.

   Nunca lleva headline: repetir el lema o una frase del deck acá sería la
   frase-plantilla que delata una página generada. */

.toma { position: relative; height: 210svh; background: var(--oscuro); }
.toma__pin {
  position: sticky; top: 0;
  height: 100svh;
  overflow: clip;
  isolation: isolate;
}
.toma__pin > .toma__video {
  position: absolute; inset: 0; z-index: 0;
  width: 100%; height: 100%; object-fit: cover;
  opacity: 0; transition: opacity 700ms var(--raw-ease-out);
}
.toma__pin > .toma__video.esta { opacity: 1; }

.toma__grano {
  position: absolute; inset: -20%; z-index: 2;
  opacity: 0.13; mix-blend-mode: overlay; pointer-events: none;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='180' height='180'%3E%3Cfilter id='r'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.82' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='180' height='180' filter='url(%23r)'/%3E%3C/svg%3E");
  animation: granea 0.6s steps(6) infinite;
}
/* viñeta + fundido al color de la página arriba y abajo, para que el plano no corte
   con un filo contra la sección de al lado */
.toma__pin::after {
  content: ""; position: absolute; inset: 0; z-index: 3; pointer-events: none;
  background:
    radial-gradient(120% 92% at 50% 50%, rgb(0 0 0 / 0) 52%, rgb(0 0 0 / 0.5) 100%),
    linear-gradient(to bottom, var(--oscuro) 0%, rgb(13 11 10 / 0) 16%, rgb(13 11 10 / 0) 82%, var(--oscuro) 100%);
}

.toma__pie {
  position: absolute; z-index: 4;
  left: var(--margen); bottom: clamp(28px, 6vh, 58px);
  font-size: 12px; letter-spacing: 0.22em; text-transform: uppercase;
  color: rgb(247 236 232 / 0.62);
}

@media (max-width: 899px) { .toma { height: 150svh; } }
@media (prefers-reduced-motion: reduce) {
  .toma { height: 100svh; }
  .toma__grano { animation: none; opacity: 0.07; }
}


/* ═════════  salida del hero: la transición no puede parecer scroll  ═════════

   Las tres variantes comparten el truco: se congela el último cuadro del plano en
   una capa fija que tapa el viewport, el scroll salta DETRÁS de ella, y recién
   entonces se anima. El desplazamiento —lo único que delata que esto es una
   página y no una película— nunca llega a verse. */
.salida {
  position: fixed; inset: 0; z-index: 91;
  pointer-events: none;
  will-change: transform, opacity;
}
/* Sin fondo propio: debajo está el hero fijado y todavía en movimiento. Un
   background acá lo taparía y volveríamos a la sensación de imagen congelada. */
.salida--sobre { background: none; }
.salida__negro {
  position: absolute; inset: 0; background: var(--oscuro);
  opacity: 0;
}
@media (prefers-reduced-motion: reduce) { .salida { display: none; } }
