/* ============================================================
   DUOWAVE · styles.css
   Plantilla de agencia recoloreada con la paleta DuoWave.
   SOLO cambian colores — layout y tipografía intactos.
   ============================================================ */

/* ---------- 1. TOKENS DE DISEÑO ---------- */
:root {
  /* ===== PALETA DUOWAVE — FUENTE DE VERDAD =====
     Estos valores mandan; CLAUDE.md solo los documenta. Si divergen,
     se corrige CLAUDE.md, no esto. */
  --deep:       #0A2540;   /* títulos y bloques de contraste */
  --signal:     #1FB6C1;   /* acento secundario */
  --signal-700: #157C84;
  --sun:        #FFA31F;   /* CTAs / highlights */
  --foam:       #F0EFEF;   /* fondo principal claro — gris cálido estable
                              en toda la web (tono editorial de referencia) */
  --ink:        #1A1F2B;   /* texto principal */
  --slate:      #6B7787;   /* texto secundario */
  --border:     #DDE4EB;   /* bordes de paneles */
  --surface:    #ffffff;   /* fondo de tarjetas */

  /* ===== Tokens de la plantilla, remapeados a DuoWave ===== */
  --bone: var(--foam);          /* fondo claro global */
  --white: var(--surface);
  --black: var(--deep);         /* nunca negro puro */
  --gray: var(--slate);         /* textos inactivos */

  /* Layout y tipografía: SIN CAMBIOS */
  --radius-pill: 999px;
  --radius-lg: 24px;
  --radius-xl: 44px;
  --pad-x: clamp(20px, 4vw, 76px);
  /* Padding vertical del header. Vive en :root (no en .site-header) porque el
     panel del menú también lo necesita para abrazar al botón, y no es hijo
     del header. Se reescribe en el bloque móvil de más abajo. */
  --header-pad-y: 1.4rem;
  --font: 'Manrope', system-ui, -apple-system, sans-serif;
}

/* ---------- 2. RESET ---------- */
*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
html { -webkit-font-smoothing: antialiased; }
html.lenis, html.lenis body { height: auto; }
.lenis.lenis-smooth { scroll-behavior: auto !important; }

body {
  font-family: var(--font);
  background: var(--bone);
  color: var(--ink);
  overflow-x: hidden;
  font-size: 17px;
  line-height: 1.45;
}

a { color: inherit; text-decoration: none; }
ul, ol { list-style: none; }
button { font: inherit; }
.arrow { display: inline-block; transition: transform .3s ease; }
a:hover .arrow { transform: translateX(4px); }

/* ---------- 3. HEADER + BOTONES FLOTANTES ---------- */
.site-header {
  position: fixed; inset: 0 0 auto 0; z-index: 60;
  display: flex; align-items: center; gap: 1.6rem;
  padding: var(--header-pad-y) var(--pad-x);
  mix-blend-mode: difference;      /* se invierte sobre fondos oscuros */
  color: #fff;
  /* La barra ocupa todo el ancho y va por encima (z-index 60). Sin esto,
     interceptaba el hover/click del botón flotante "Habla con nosotros" que
     queda debajo. La hacemos "click-through" y reactivamos solo sus hijos
     interactivos (logo, tag, burger). */
  pointer-events: none;
}
.site-header > * { pointer-events: auto; }
.logo__box {
  display: grid; grid-template-rows: 1fr 1fr;
  border: 2px solid currentColor; width: 56px; height: 56px;
  font-weight: 800; font-size: 14px; letter-spacing: 1px;
  place-items: center; line-height: 1;
}
/* Logo DuoWave (imagen). Misma altura visual que el monograma anterior. */
.logo__img { height: 44px; width: auto; display: block; }
/* Los footers y la marquesina usan la ONDA suelta (decisión de agosto
   2026: junto al correo del footer el lockup duplicaba el nombre); el
   lockup apilado vive solo en el header, que ajusta su alto abajo. */
/* En el header: la variante mono (marino) se invierte a claro para que el
   mix-blend-mode:difference del header la adapte a cada fondo, igual que
   hacía el texto blanco original. 3.8rem por el lockup apilado: con menos
   alto, el DUOWAVE de debajo no se lee. */
.site-header .logo__img { filter: invert(1); height: 3.8rem; }
/* Logo = enlace a inicio: puntero + foco visible por teclado (solo teclado,
   no altera el aspecto en reposo). Coherente con el anillo signal del sitio. */
.site-header .logo { cursor: pointer; }
.site-header .logo:focus-visible { outline: 3px solid var(--signal); outline-offset: 4px; border-radius: 6px; }
/* Como la referencia: pegado al logo a la izquierda, en caja alta,
   con tamaño legible en pantallas grandes */
.header__tag { font-size: 13px; letter-spacing: 2px; font-weight: 600; }
.burger {
  /* Medidas del icono en variables: el giro a vertical calcula con ellas el
     centro del bloque, y el override móvil (≤600px) solo las reescribe. */
  --burger-bar: 2px;               /* grosor de cada raya */
  --burger-gap: 0.5rem;            /* separación entre las dos rayas */
  margin-left: auto; width: 3.9rem; height: 3.9rem; border-radius: 50%;
  border: 1.5px solid currentColor; background: transparent; cursor: pointer;
  display: grid; place-content: center; gap: var(--burger-gap); color: inherit;
}
.burger span { display: block; width: 1.5rem; height: var(--burger-bar); background: currentColor; }

/* Menú abierto: las dos rayas giran 90° y quedan VERTICALES y PARALELAS
   (nada de aspa). Para que giren como un bloque único, cada raya rota sobre
   el CENTRO COMÚN del icono, no sobre el suyo: así conservan el grosor y la
   misma separación (--burger-gap) y no se cruzan.
     · raya 1: su centro está --burger-gap/2 + --burger-bar/2 por encima del
       centro del icono → origen a  bar + gap/2  de su borde superior.
     · raya 2: mismo desplazamiento hacia el otro lado → origen a −gap/2.
   El botón NO se mueve al abrir (mismo top/right y mismo tamaño): solo giran
   las rayas. Enganchado a aria-expanded (lo togglea el JS). */
.burger span { transition: transform .3s cubic-bezier(0.4, 0, 0.2, 1); }
.burger span:nth-child(1) { transform-origin: 50% calc(var(--burger-bar) + var(--burger-gap) / 2); }
.burger span:nth-child(2) { transform-origin: 50% calc(-0.5 * var(--burger-gap)); }
.burger[aria-expanded="true"] span { transform: rotate(90deg); }
/* El color NO se toca al abrir: lo sigue resolviendo el mix-blend-mode del
   header (contorno y rayas van con currentColor). Sobre el panel blanco se
   pinta oscuro, y sobre las secciones marino de la portada se aclara solo,
   que es lo que lo mantiene legible con el menú cerrado. */

@media (prefers-reduced-motion: reduce) { .burger, .burger span { transition: none; } }

/* ------------------------------------------------------------
   CTAs flotantes — JERARQUÍA FIJA (no cambian de color al scroll;
   se retiró la lógica is-light del JS bloque 6).
   · Primario = --project: naranja (--sun), estrella, shine en bucle.
   · Secundario = --hire: outline blanco con borde, discreto, solo hover.
     Blanco sólido → legible sobre secciones claras Y oscuras (no
     necesita variante adaptativa, así que queda 100% fijo).
   ------------------------------------------------------------ */
.floating-btn {
  position: fixed; z-index: 55;
  padding: 1rem 1.75rem; border-radius: var(--radius-pill);
  font-weight: 600; font-size: 1.05rem;
  display: inline-flex; align-items: center; gap: 0.7rem;
  border: 1.5px solid transparent;
  transition: transform .25s cubic-bezier(.22,1,.36,1), box-shadow .25s ease,
              background .25s ease, color .25s ease, border-color .25s ease;
}
.floating-btn .arrow { transition: transform .25s cubic-bezier(.22,1,.36,1); }

/* PRIMARIO (naranja) — fijo + shine en bucle + hover (eleva, sombra, flecha) */
.floating-btn--project {
  bottom: 1.6rem; right: var(--pad-x);
  background: var(--sun); color: var(--deep); overflow: hidden;
  box-shadow: 0 10px 26px -10px rgba(255,163,31,.55);
}
.floating-btn--project::before {
  content: ""; position: absolute; top: 0; left: 0; width: 55%; height: 100%;
  background: linear-gradient(100deg, transparent 0%, rgba(255,255,255,.5) 50%, transparent 100%);
  transform: translateX(-170%) skewX(-18deg);
  animation: ctaShine 3s ease-in-out infinite; pointer-events: none;
}
.floating-btn--project:hover { transform: translateY(-3px); box-shadow: 0 16px 36px -10px rgba(255,163,31,.72); }
.floating-btn--project:hover .arrow { transform: translateX(4px); }
@keyframes ctaShine {
  0%        { transform: translateX(-170%) skewX(-18deg); }
  38%, 100% { transform: translateX(330%)  skewX(-18deg); }
}

/* SECUNDARIO (outline) — fijo, legible sobre claro y oscuro, discreto */
.floating-btn--hire {
  top: 1.6rem; right: calc(var(--pad-x) + 5rem);
  color: var(--deep);
  /* HITBOX de tamaño FIJO (el pill completo): NUNCA se encoge, así el cursor no
     "pierde" el hover ni entra en bucle de parpadeo, esté sobre el texto o la
     flecha. Es TRANSPARENTE: la forma visible (pill → círculo) la pinta ::before. */
  --hire-w: 15.6rem; --hire-h: 3.65rem;
  width: var(--hire-w); height: var(--hire-h); padding: 0;
  background: transparent; border: none; box-shadow: none;
  overflow: visible; contain: layout;
}
.floating-btn--hire:focus-visible { outline: 3px solid var(--deep); outline-offset: 3px; border-radius: var(--radius-pill); }

/* PARTE VISUAL: pill en reposo → círculo en hover. Anclada a la derecha; SOLO se
   anima su width (aislado: es absoluta, no refluye nada). El texto y la flecha van
   ENCIMA (z-index) y no se mueven; el texto NO desaparece: al encogerse la forma
   queda visible a su izquierda, fuera del círculo. Blanco+navy. */
.floating-btn--hire::before {
  content: ""; position: absolute; top: 0; bottom: 0; right: 0; z-index: 0;
  width: var(--hire-w); box-sizing: border-box;
  background: var(--surface); border: 1.5px solid var(--deep);
  border-radius: var(--radius-pill);
  box-shadow: 0 8px 20px -10px rgba(10,37,64,.30);
}
.floating-btn--hire .fb-label {
  position: absolute; left: 1.4rem; top: 0; bottom: 0; z-index: 1;
  display: flex; align-items: center; white-space: nowrap;
}
.floating-btn--hire .arrow {
  position: absolute; right: 0; top: 0; bottom: 0; width: var(--hire-h); z-index: 1;
  display: flex; align-items: center; justify-content: center;
  /* Posición natural (translateX 0) = right:0/width:--hire-h = centro exacto del
     círculo. En reposo la retranqueamos a la izquierda para que quede junto al
     texto (final de línea); en hover vuelve a 0 → aterriza en el centro. */
  transform: translateX(-1.35rem);
}

/* --- Color adaptativo sobre secciones oscuras (JS añade .on-dark, sincronizado
   con logo/texto/menú que usan mix-blend-mode) ---
   Sobre claro: pastilla BLANCA + navy (por defecto). Sobre oscuro: contorno +
   texto + flecha DORADOS y relleno transparente. El dorado = difference(#fff,
   --deep) = rgb(245,218,191), el mismo tono que produce el mix-blend del navbar
   sobre las secciones navy. Transición suave para que acompañe al scroll. */
.floating-btn--hire { transition: color .35s ease; }
.floating-btn--hire::before { transition: border-color .35s ease, background-color .35s ease; }
.floating-btn--hire.on-dark { color: rgb(245, 218, 191); }
.floating-btn--hire.on-dark::before { background-color: transparent; border-color: rgb(245, 218, 191); }

@media (hover: hover) and (pointer: fine) {
  /* La forma (::before) se recoge a círculo Y la flecha VIAJA a su centro,
     sincronizadas (misma curva/duración). El destino de la flecha (translateX 0)
     ES su posición natural right:0/width:--hire-h = el centro exacto del círculo
     (mismo anclaje) → aterriza perfectamente centrada. El texto NO se mueve. */
  .floating-btn--hire::before { transition: width .4s cubic-bezier(.22,1,.36,1), box-shadow .3s ease, border-color .35s ease, background-color .35s ease; }
  .floating-btn--hire .arrow { transition: transform .4s cubic-bezier(.22,1,.36,1); }
  .floating-btn--hire:hover::before {
    width: var(--hire-h);
    box-shadow: 0 14px 30px -12px rgba(10,37,64,.42);
    will-change: width, transform;
  }
  .floating-btn--hire:hover .arrow { transform: translateX(0); }   /* viaja al centro del círculo */
}

/* reduced-motion: sin morph ni viaje de flecha; se mantiene como pill. */
@media (prefers-reduced-motion: reduce) {
  .floating-btn--hire::before { transition: box-shadow .2s ease; }
  .floating-btn--hire:hover::before { width: var(--hire-w); }
  .floating-btn--hire .arrow { transition: none; }
  .floating-btn--hire:hover .arrow { transform: translateX(-1.35rem); }
}

/* reduced-motion: sin bucle (shine off); el hover sí (lo inicia el usuario) */
@media (prefers-reduced-motion: reduce) { .floating-btn--project::before { animation: none; } }

/* Móvil (≤600px): el navbar ya es táctil y el ancho está al límite (logo +
   "Habla con nosotros" + hamburguesa llenan la fila). Se mantiene una escala
   compacta para que quepan sin solaparse; el CTA flotante inferior sí crece
   un poco porque tiene sitio libre en su esquina. */
@media (max-width: 600px) {
  /* En :root, no en .site-header: el panel del menú lee esta misma variable
     para seguir abrazando al botón con el header compacto. */
  :root { --header-pad-y: 1.25rem; }
  .site-header { gap: 0.9rem; }
  .site-header .logo__img { height: 2.7rem; }
  /* --burger-gap (no gap a pelo): el giro a vertical calcula el centro del
     bloque con esa variable y así sigue cuadrando en móvil. */
  .burger { width: 3.3rem; height: 3.3rem; --burger-gap: 0.375rem; }
  .burger span { width: 1.25rem; }
  /* Móvil: cápsula flex normal (sin morph; en táctil no hay hover). La forma
     vuelve al <a> (::before oculto), texto y flecha al flujo → cabe en la fila. */
  /* El botón es fixed y NADIE le reserva sitio: con width:auto su ancho lo
     fija el texto (184px), así que al estrecharse la pantalla su borde
     izquierdo avanzaba hasta meterse debajo del logo (23px de solape a 360px,
     63px a 320px). El tope lo ata al espacio que queda de verdad: ancho de
     ventana menos lo que ocupa a su derecha (--pad-x + el burger), menos el
     borde derecho del logo (120px), menos 12px de aire mínimo. */
  .floating-btn--hire { top: 1.5rem; right: calc(var(--pad-x) + 3.7rem);
    max-width: min(184px, calc(100vw - var(--pad-x) - 3.7rem - 132px));
    width: auto; height: auto; padding: 0.72rem 1.05rem; contain: none; font-size: 0.85rem;
    background: var(--surface); border: 1.5px solid var(--deep); box-shadow: 0 8px 20px -10px rgba(10,37,64,.30);
    transition: color .35s ease, background-color .35s ease, border-color .35s ease; }
  /* en móvil el visual va en el propio <a> (::before oculto): adaptamos su borde
     y relleno directamente sobre oscuro */
  .floating-btn--hire.on-dark { background-color: transparent; border-color: rgb(245, 218, 191); }
  .floating-btn--hire::before { display: none; }
  .floating-btn--hire .fb-label { position: static; }
  .floating-btn--hire .arrow { position: static; width: auto; transform: none; }
  .floating-btn--project { bottom: 1.35rem; font-size: 0.95rem; padding: 0.85rem 1.35rem; }
}

/* Pantallas muy estrechas: el botón pierde el texto y se queda en la flecha.
   El tope de arriba (max-width con min()) evita el solape, pero por debajo de
   cierto ancho lo consigue estrujando el botón por debajo de su contenido: el
   texto se sale de la cápsula en vez de envolverse, que es peor que el solape
   que veníamos a arreglar.

   El umbral no es redondo por gusto, sale de la cuenta: el botón mide 184,25px
   con el texto, a su derecha se van 79,2px (--pad-x + el burger), el logo
   acaba en 120px y queremos 12px de aire → hacen falta 395,45px de ventana.
   400px es el primer número redondo por encima, con algo de margen para
   diferencias de renderizado de la fuente.

   Va JUSTO AQUÍ, pegado al bloque de 600px, y no al final de la hoja: es la
   continuación del mismo componente y además tiene que ganarle en la cascada.

   Accesible: el nombre del botón lo da el aria-label del <a>, presente en las
   23 páginas, así que ocultar .fb-label no deja al lector de pantalla sin
   texto. 2,9rem = 46px de lado, por encima del mínimo táctil de 44px. */
@media (max-width: 400px) {
  .floating-btn--hire {
    max-width: none; width: 2.9rem; height: 2.9rem;
    padding: 0; justify-content: center;
  }
  .floating-btn--hire .fb-label { display: none; }
}

/* Menú: panel compacto blanco anclado a la esquina superior derecha
   (estilo de la referencia), en vez del telón a pantalla completa.
   POSICIÓN: el panel no se ancla al viewport, se ancla AL BOTÓN — abraza su
   esquina dejando el mismo hueco (--menu-hug) por arriba y por la derecha.
   Por eso el desplazamiento se calcula desde los mismos valores que colocan
   al botón (--header-pad-y arriba, --pad-x a la derecha): si cambia el
   padding del header, el abrazo sigue cuadrado y el botón NO se mueve.
   Nota: el margen exterior del panel es forzosamente MENOR que el del header
   —el panel tiene que empezar por encima del botón, que está justo a esa
   distancia del borde—, así que se queda a --menu-hug de la línea del
   header, lo más cerca posible sin pegarse al viewport. */
.overlay-menu {
  --menu-hug: 10px;                /* hueco entre el borde del panel y el botón */
  position: fixed; left: auto; bottom: auto; z-index: 58;
  top: calc(var(--header-pad-y) - var(--menu-hug));
  right: calc(var(--pad-x) - var(--menu-hug));
  width: min(400px, calc(100vw - 2 * (var(--pad-x) - var(--menu-hug))));
  background: var(--surface); color: var(--deep);
  border-radius: 28px; box-shadow: 0 30px 80px -20px rgba(10, 37, 64, .35);
  padding: clamp(112px, 14vh, 130px) clamp(34px, 3.5vw, 52px) clamp(30px, 4vh, 44px);
  opacity: 0; visibility: hidden; transform: scale(.92); transform-origin: top right;
  transition: opacity .35s ease, transform .35s cubic-bezier(.22, 1, .36, 1),
              visibility 0s linear .35s;
}
.overlay-menu.open {
  opacity: 1; visibility: visible; transform: scale(1);
  transition: opacity .35s ease, transform .35s cubic-bezier(.22, 1, .36, 1);
}
.overlay-menu ul { text-align: left; display: grid; gap: 8px; }
.overlay-menu a {
  font-size: clamp(24px, 2.2vw, 32px); font-weight: 600; line-height: 1.25;
  color: var(--deep); transition: color .25s;
}
/* Hover y página actual comparten el naranja de marca: el hover "adelanta"
   el estado current.
   AVISO de contraste: --sun sobre el panel blanco da 2.0:1, por debajo del
   3:1 que pide WCAG AA para texto grande (sobre el panel marino daba 7.8:1).
   El enlace activo se distingue igualmente por ser el único en naranja, pero
   si hace falta cumplir AA haría falta un --sun oscurecido para texto sobre
   claro (p. ej. #A85F00 → 4.9:1), como ya existe --signal-700 para --signal. */
.overlay-menu a:hover { color: var(--sun); }
.overlay-menu a[aria-current="page"] { color: var(--sun); }
/* CTA al pie del panel (píldora con contorno, como la referencia) */
.overlay-menu .menu-cta { margin-top: 28px; }
.overlay-menu .menu-cta a {
  display: inline-flex; align-items: center; gap: 10px;
  border: 1.5px solid var(--deep); border-radius: 999px;
  padding: 14px 24px; font-size: 16px; font-weight: 600; color: var(--deep);
  transition: background .25s, color .25s;
}
.overlay-menu .menu-cta a:hover { background: var(--deep); color: var(--foam); }
@media (prefers-reduced-motion: reduce) { .overlay-menu { transition: none; } }

/* ---------- 4. AURORA (colores de marca DuoWave) ---------- */
.aurora { position: absolute; inset: 0; overflow: hidden; z-index: 0; pointer-events: none; }
.aurora__blob {
  position: absolute; border-radius: 50%;
  filter: blur(85px); opacity: .9; will-change: transform;
}
.aurora__blob--1 { width: 52vw; height: 52vw; right: -6vw; top: 0;
  background: radial-gradient(circle at 40% 40%, var(--sun) 0%, transparent 62%);
  animation: float1 20s ease-in-out infinite; }
.aurora__blob--2 { width: 44vw; height: 44vw; right: 6vw; top: 22vh;
  background: radial-gradient(circle at 55% 45%, var(--signal) 0%, transparent 60%);
  animation: float2 24s ease-in-out infinite; }
.aurora--soft .aurora__blob { opacity: .55; filter: blur(115px); }

@keyframes float1 { 0%,100%{transform:translate(0,0) scale(1)} 50%{transform:translate(-6%,4%) scale(1.14)} }
@keyframes float2 { 0%,100%{transform:translate(0,0) scale(1.08)} 50%{transform:translate(5%,-6%) scale(.92)} }

/* ---------- 5. HERO ---------- */
.hero { position: relative; min-height: 100vh; padding: 0 var(--pad-x); display: flex; flex-direction: column; justify-content: center; }
.hero__inner { position: relative; z-index: 2; }
.hero__title {
  /* Tamaño grande restaurado (como antes). Las 3 líneas van
     alineadas a la izquierda, sin sangrías. */
  font-size: clamp(72px, 12.5vw, 240px); font-weight: 800;
  line-height: .84; letter-spacing: -0.035em;
  color: var(--deep);                          /* títulos → deep */
}
.hero__title .line { display: block; }
/* "tu negocio responde" no cabe físicamente a 12.5vw (mediría ~2170px):
   esta línea se autoajusta al ancho disponible con calc, quedando lo
   más grande posible en cualquier pantalla sin desbordar */
.hero__title .line--fit {
  font-size: clamp(58px, calc((100vw - 190px) / 9.3), 200px);
  /* aire extra sobre esta línea: el descendente de la "y" de "tuyo."
     (línea grande) invadía las letras de "responde" con el interlineado
     ceñido y los tamaños mixtos (.34em ≈ separación garantizada entre
     cajas de glifos, verificada por medición) */
  margin-top: .34em;
}
/* Aire entre "tu negocio responde" y "solo" (la línea que sigue a la
   línea ajustada) */
.hero__title .line--fit + .line { margin-top: .14em; }
.line--indent-lg { margin-left: 16%; }
.line--indent-sm { margin-left: 5%; }
.line--indent-md { margin-left: 11%; }
.hero__media {
  /* Sustituye a la "o" de "solo". Contiene una "o" REAL pero TRANSPARENTE
     como elemento de medida: ocupa EXACTAMENTE el avance horizontal de la
     letra (sin número mágico y sobrevive a cualquier cambio de fuente), así
     que NO empuja a "s" ni a "lo". El círculo del vídeo va aparte (absoluto)
     y desborda sin afectar al flujo. */
  position: relative;
  display: inline-block;
  color: transparent;
}
.hero__disc {
  /* Círculo visible del vídeo. position:absolute → desborda visualmente SIN
     afectar al flujo del texto. Reconstruye la caja de TINTA exacta de la "o":
     empieza donde empezaría su trazo (left = side bearing) y mide lo que mide
     el trazo (width), así el aire a izquierda y derecha es idéntico al de una
     "o" real en ese hueco — sin centrar (centrar falla por el letter-spacing)
     y sin compensar a mano. Vertical: centrado sobre la x-height. Todo en em →
     escala igual en todos los breakpoints. El degradado es el respaldo mientras
     carga el vídeo. Medido con canvas @180px: avance 0.627em, trazo 0.547em,
     side bearing 0.040em. */
  position: absolute;
  left: 0.04em;
  top: 50%;
  width: .547em; height: .547em;
  /* translateX(0.02em): micro-ajuste óptico a la derecha para que el aire
     s→○ y ○→l sea visualmente igual (offset = (B−A)/2 medido). Va en el
     disco, no en el padre: "s" y "l" no se mueven. */
  transform: translateX(0.02em) translateY(-50%) translateY(0.11em);
  border-radius: 50%;
  overflow: hidden;
  background: linear-gradient(135deg, var(--signal), var(--sun));
}
.hero__media-video {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; display: block;
}
@media (prefers-reduced-motion: reduce) {
  .hero__media-video { display: none; }   /* queda el círculo con degradado */
}
/* Subtítulo: vive DENTRO de .hero__inner (position:relative), anclado
   abajo-derecha del BLOQUE DEL TITULAR → queda a la derecha de la línea
   corta "solo", alineado con su base a cualquier tamaño de pantalla,
   sin poder pisar ninguna letra */
.hero__desc {
  /* bottom negativo: baja el subtítulo un poco por debajo de la base
     del titular para que no quede pegado a él */
  position: absolute; right: 0; bottom: -1.4em; max-width: 540px;
  font-size: clamp(17px,1.4vw,22px); line-height: 1.4; z-index: 2;
}
/* Tablet y pantallas medias: el subtítulo pasa DEBAJO del titular a
   ancho completo. Umbral 1200px: por encima, la banda de la línea
   "solo" (0.84 × fuente) siempre es más alta que el subtítulo, así que
   el solape es geométricamente imposible. */
@media (max-width: 1200px) {
  .hero__desc { position: static; margin-top: 36px; max-width: 100%; }
}
.hero__desc strong { font-weight: 800; }
/* Marquesina de sectores: vive en el apartado SECTORES, en bucle
   infinito con fundido en los bordes (máscara, sin tocar colores). */
.awards {
  position: relative; overflow: hidden; white-space: nowrap;
  font-size: clamp(17px, 1.6vw, 26px); font-weight: 700; letter-spacing: 1px;
  color: var(--ink); text-align: left;
  -webkit-mask-image: linear-gradient(90deg, transparent, #000 6%, #000 94%, transparent);
  mask-image: linear-gradient(90deg, transparent, #000 6%, #000 94%, transparent);
}
.awards__track { display: inline-flex; will-change: transform; }
.awards__seq { display: inline-flex; align-items: center; gap: 34px; padding-right: 34px; }
.awards__sep { opacity: .45; }

/* La marquesina vive ahora al final de «Analiza tu negocio gratis»
   (sección oscura): texto claro, aire superior y por encima de los glows */
.chat-sec .awards {
  color: var(--foam); z-index: 1;
  margin-top: clamp(46px, 8vh, 90px);
  padding: 0 var(--pad-x);
}

/* Tarjetas del blog de la portada: ahora son enlaces (vista previa
   sincronizada con blog.html) */
a.post { display: block; color: inherit; text-decoration: none; }
a.post:hover .post__title { color: var(--signal-700); }
.post__media img { width: 100%; height: 100%; object-fit: cover; display: block; }

/* Flecha de scroll: rebote muy sutil; clic → siguiente sección */
.hero__scroll {
  position: absolute; left: 50%; bottom: 78px; z-index: 2;
  transform: translateX(-50%);
  background: none; border: 0; padding: 8px; cursor: pointer;
  color: var(--deep);
  animation: scrollNudge 2.2s ease-in-out infinite;
}
@keyframes scrollNudge {
  0%, 100% { transform: translate(-50%, 0); }
  50%      { transform: translate(-50%, 7px); }
}

/* Accesibilidad: sin movimiento → tira estática y flecha quieta
   (la entrada del titular y el marquee se omiten desde main.js) */
@media (prefers-reduced-motion: reduce) {
  .hero__scroll { animation: none; }
}

/* ---------- 6. OUR SERVICES ---------- */
/* Fondo transparente: deja ver el vídeo fijo del hero */
.services-zone { position: relative; background: transparent; overflow: clip; padding-bottom: 16vh; }
.zone-heading {
  /* z-index 1 (por debajo del stack, z2): al hacer scroll, la primera
     tarjeta pasa POR ENCIMA del titular y lo va tapando */
  position: relative; z-index: 1;
  display: flex; align-items: flex-end; justify-content: space-between;
  padding: 16vh var(--pad-x) 8vh;
}
.zone-heading__title {
  font-size: clamp(70px, 11vw, 210px); font-weight: 500;
  line-height: .95; letter-spacing: -0.02em; text-transform: uppercase;
  color: var(--deep);
}
.zone-heading__title span { display: block; }
.zone-heading__indent { margin-left: 14%; }
.zone-heading__arrow { width: clamp(90px, 12vw, 220px); color: var(--deep); flex-shrink: 0; }

/* ---------- 7. STICKY STACK ---------- */
.stack { position: relative; z-index: 2; padding: 0 var(--pad-x); }
.stack__card {
  position: sticky; top: 9vh;
  display: grid; grid-template-columns: 1fr 1.05fr; gap: 50px;
  min-height: 82vh; margin-top: 7vh;
  background-color: var(--foam);   /* dot-grid n8n-canvas, unifica las 3 tarjetas */
  background-image: radial-gradient(rgba(10,37,64,.08) 1.2px, transparent 1.3px);
  background-size: 22px 22px;
  border: 1px solid var(--border);
  border-radius: var(--radius-xl);
  padding: clamp(30px,4vw,64px); overflow: hidden;
  box-shadow: 0 -12px 60px rgba(10,37,64,.07);
}
/* (Se retiró .stack__card--frost: el cristal translúcido rgba(.55) + backdrop-filter:blur
   dejaban ver borroso el hero de detrás. La tarjeta "Presencia digital" usa ahora el
   MISMO fondo sólido opaco que las otras 2: var(--foam) + dot-grid, heredado de .stack__card.) */
.stack__text { display: flex; flex-direction: column; justify-content: center; align-items: flex-start; }
.stack__title { font-size: clamp(44px,5.4vw,104px); font-weight: 600; line-height: .98; letter-spacing: -0.03em; color: var(--deep); }
.tags { display: flex; flex-wrap: wrap; gap: 10px; margin: 34px 0 26px; }
.tags li, .tags span {
  border: 1.2px solid var(--border); border-radius: var(--radius-pill);
  padding: 10px 20px; font-size: 15px; font-weight: 500; color: var(--ink);
}
.stack__desc { max-width: 470px; font-size: 19px; margin-bottom: 32px; }
.btn-outline {
  display: inline-flex; align-items: center; gap: 12px;
  border: 1.4px solid var(--deep); border-radius: var(--radius-pill);
  padding: 14px 26px; font-weight: 600; font-size: 16px;
  background: transparent; cursor: pointer; color: var(--deep);
  transition: background .3s, color .3s;
}
.btn-outline:hover { background: var(--deep); color: var(--foam); }
.stack__media { border-radius: var(--radius-lg) 160px var(--radius-lg) var(--radius-lg); min-height: 320px; overflow: hidden; }

/* ---------- Imagen de fondo de las tarjetas de servicio ----------
   Fondo claro (fondotarjetas) que cubre la tarjeta (cover, centrado, recortado
   a las esquinas por el overflow:hidden) + velo foam MUY leve para homogeneizar
   sin oscurecer. Borde marino grueso. El texto navy y las escenas quedan por
   encima (el fondo es del elemento, siempre detrás del contenido). Fondo claro
   → el navbar (mix-blend-difference) se mantiene navy, no dorado. */
.stack__card.has-bgimg {
  /* mismo contorno fino que el resto de tarjetas del sitio */
  border: 1px solid var(--border);
  background:
    linear-gradient(color-mix(in srgb, var(--foam) 22%, transparent),
                    color-mix(in srgb, var(--foam) 22%, transparent)),
    url("../assets/img/fondotarjetas.png") center / cover no-repeat;
}

/* Placeholders de media (fotos pendientes de blog y tarjetas de valor).
   Solo se conservan las variantes en uso; se retiraron 12 gradientes de
   la plantilla que no se usaban en ninguna parte. */
.media-placeholder {
  width: 100%; height: 100%; display: grid; place-content: center;
  color: rgba(0,0,0,.4); font-weight: 700; letter-spacing: .5px; text-align: center; padding: 20px;
}
.media-placeholder--lovie    { background: linear-gradient(135deg, var(--foam), var(--border)); color: var(--slate); }
.media-placeholder--limeblack{ background: radial-gradient(circle at 70% 40%, var(--signal-700) 0%, var(--deep) 72%); color: var(--foam); }
.media-placeholder--navy     { background: linear-gradient(135deg, var(--deep), var(--ink)); color: var(--foam); }

/* ---------- 8. PROCESO ---------- */
/* Fondo transparente: el vídeo fijo del hero sigue visible hasta la
   primera sección oscura (NUESTROS CASOS) */
.process { position: relative; padding: clamp(90px,16vh,200px) var(--pad-x); background: transparent; overflow: hidden; }
.process__heading {
  position: relative; z-index: 2; text-align: center;
  font-size: clamp(42px,5.8vw,110px); font-weight: 600; line-height: 1.02;
  letter-spacing: -0.03em; margin-bottom: 10vh;
  color: var(--deep);
}
.steps { position: relative; z-index: 2; }
.step { padding: 44px 0; border-bottom: 1px solid var(--border); }
.step__num { display: block; font-size: clamp(17px,1.3vw,22px); opacity: .55; margin-bottom: 8px; }
.step__row { display: grid; grid-template-columns: 1.15fr .55fr .8fr; gap: 36px; align-items: center; }
.step__title {
  font-size: clamp(44px,6.8vw,132px); font-weight: 600; line-height: .95;
  letter-spacing: -0.03em; color: var(--gray); transition: color .5s ease;
}
.step.is-active .step__title { color: var(--deep); }
.step.is-active .step__num { opacity: 1; }
.step__media {
  aspect-ratio: 4/3; width: 100%; max-width: 260px; justify-self: center;
  border-radius: 14px; transform: rotate(-4deg); overflow: hidden;
  opacity: 0; transition: opacity .5s, transform .6s;
  box-shadow: 0 20px 50px rgba(10,37,64,.18);
}
.step.is-active .step__media { opacity: 1; transform: rotate(-2deg); }
/* La primera y la última foto van un poco más grandes */
.step:nth-child(1) .step__media,
.step:nth-child(3) .step__media { max-width: 330px; }
.step__desc {
  font-size: clamp(17px,1.5vw,22px); line-height: 1.4;
  opacity: 0; transform: translateY(18px); transition: opacity .5s, transform .5s;
}
.step.is-active .step__desc { opacity: 1; transform: translateY(0); }

/* ---------- 9. OUR WORK — bloque de contraste (deep) ---------- */
.work {
  position: relative; background: var(--deep); color: var(--foam);
  padding: clamp(80px,12vh,160px) var(--pad-x);
  /* sin esquinas superiores: ANALIZA va ahora primero y es quien abre la
     zona oscura (si .work las mantuviera, asomarían cuñas claras entre
     las dos secciones oscuras) */
  overflow: hidden;
}
.starfield { position: absolute; inset: 0; width: 100%; height: 100%; z-index: 0; opacity: .8; }
.work__intro {
  position: relative; z-index: 2;
  margin-bottom: clamp(18px, 3vh, 40px);   /* REDUCIDO (antes 10vh): carrusel más cerca del título */
}
.work__heading {
  /* Una sola línea a TODO ancho: el tamaño se calcula para llenar el
     contenedor (ancho = 100vw − 2·--pad-x). Multiplicador medido con canvas
     (R = 8.57 px/px de "NUESTROS CASOS") → 10.7vw llena la línea sin
     desbordar de 601px a 1920px+. El resto (color/peso/tracking) intacto. */
  font-size: clamp(64px, 10.7vw, 400px); font-weight: 500;
  line-height: .92; letter-spacing: -0.01em; text-transform: uppercase;
  white-space: nowrap;
}
.work__heading span { display: block; }
.work__tagline {
  /* Línea de apoyo pequeña, alineada al margen derecho (termina donde termina
     el titular). --foam a 0.72 sobre --deep ≈ 7:1 de contraste (> 4.5:1). */
  margin-top: clamp(10px, 1.4vh, 22px);
  text-align: right; font-size: clamp(15px, 1.15vw, 18px); font-weight: 500;
  line-height: 1.4; color: var(--foam); opacity: .72;
}
/* Móvil (≤600px): a una línea sería demasiado pequeño → parte en dos líneas
   y la frase de apoyo pasa a alineación izquierda. */
@media (max-width: 600px) {
  .work__heading { white-space: normal; font-size: clamp(48px, 13vw, 78px); }
  .work__tagline { text-align: left; }
}

/* Tarjetas de proyecto → surface con borde (paneles claros) */
.project {
  position: relative; z-index: 2;
  border: 1px solid var(--border); border-radius: var(--radius-lg);
  overflow: hidden; background: var(--surface); color: var(--ink);
}
.project__head {
  display: flex; justify-content: space-between; align-items: center;
  padding: 16px 22px; font-size: 19px; font-weight: 600;
}
.project__arrow { color: var(--signal); font-weight: 700; margin-right: 6px; }
.project__year { font-weight: 400; }
.project__media { aspect-ratio: 16/11; border-radius: 0; }
.project--featured { margin-bottom: 24px; }
.project--featured .project__media { aspect-ratio: 21/10; }
.project__caption { font-size: clamp(22px,2.4vw,40px); font-weight: 500; max-width: 85%; margin-bottom: 20px; }
.tags--dark { margin: 0; gap: 10px; }
.tags--dark span { border-color: rgba(255,255,255,.5); color: #fff; padding: 9px 16px; font-size: 13px; }
.work__grid { position: relative; z-index: 2; display: grid; grid-template-columns: 1fr 1fr; gap: 24px; }

/* ---------- 10. CASE STUDIES — fondo claro, paneles surface ---------- */
/* Fondo transparente: el vídeo fijo del hero sigue de fondo */
.cases { position: relative; background: transparent; padding: clamp(60px,10vh,140px) var(--pad-x); }
.cases-swiper { overflow: visible; }
.case-card__brand { font-weight: 700; letter-spacing: 2px; font-size: 15px; margin-bottom: 30px; color: var(--slate); }
.case-card__stat {
  font-size: clamp(70px,9vw,170px); font-weight: 600; letter-spacing: -0.03em; line-height: 1;
  background: linear-gradient(90deg, var(--signal), var(--sun));
  -webkit-background-clip: text; background-clip: text; color: transparent;
}
.case-card__label { font-size: clamp(18px,1.6vw,24px); margin: 18px 0 34px; max-width: 380px; }
.case-card__media { border-radius: 18px; min-height: 380px; }
/* Flecha "siguiente" de las barajas: vive DENTRO del contenedor Swiper,
   anclada a la esquina inferior derecha de la tarjeta activa */
.deck-next {
  position: absolute; right: 18px; bottom: 18px; z-index: 20;
  width: 56px; height: 56px; border-radius: 50%;
  border: 1.5px solid currentColor; background: transparent; cursor: pointer;
  font-size: 26px; line-height: 1; display: grid; place-content: center;
  transition: transform .3s ease;
}
.deck-next:hover { transform: scale(1.1); }
.deck-next--cases { color: var(--deep); }

/* ---------- 11. TESTIMONIOS — fondo claro ---------- */
.testimonials {
  background: transparent; color: var(--ink); padding: clamp(80px,12vh,160px) var(--pad-x);
  display: grid; grid-template-columns: 1fr 1.1fr; gap: 40px; align-items: center; min-height: 100vh;
}
.testimonials__heading { font-size: clamp(50px,6.5vw,120px); font-weight: 600; line-height: .98; letter-spacing: -0.02em; color: var(--deep); }
.testi-wrap { position: relative; }
.testi-swiper { width: 100%; max-width: 640px; overflow: visible; }
.testi-card {
  background: var(--t-bg, var(--surface)); color: var(--ink);
  border: 1px solid var(--border);
  border-radius: 14px 150px 26px 26px;
  padding: clamp(32px,3.6vw,54px); min-height: 560px; display: flex; flex-direction: column;
}
.testi-card__brand { font-size: 22px; font-weight: 800; letter-spacing: 1px; margin-bottom: 26px; color: var(--deep); }
.testi-card__quote { font-size: clamp(17px,1.5vw,21px); line-height: 1.5; }
.testi-card__author { margin-top: auto; padding-top: 28px; font-size: 16px; color: var(--slate); }
.testi-card__author p:first-child { font-weight: 700; color: var(--ink); }
.btn-outline--dark { border-color: var(--deep); margin-top: 22px; align-self: flex-start; }
.deck-next--testi { color: var(--deep); }

/* ---------- 12. PARTNERS — fondo claro ---------- */
.partners { background: transparent; color: var(--deep); padding: clamp(80px,12vh,160px) var(--pad-x); text-align: center; }
.partners__heading {
  font-size: clamp(64px,11vw,210px); font-weight: 500; letter-spacing: -0.01em;
  margin-bottom: 9vh;
}
.partners__grid {
  display: grid; grid-template-columns: repeat(5,1fr); gap: 60px 30px;
  align-items: center; justify-items: center; max-width: 1400px; margin: 0 auto;
  color: var(--ink);
}
.partners__grid li { font-size: clamp(15px,1.4vw,22px); line-height: 1.15; opacity: .95; }
.partners__grid small { font-size: .7em; letter-spacing: 2px; }

/* ---------- 13. BLOG — fondo claro ---------- */
/* padding-bottom reforzado: las tarjetas entran con un desplazamiento
   de 40px (animación reveal) y sin este colchón podían pisar el titular
   de la sección FAQ en pantallas panorámicas */
.blog { background: transparent; color: var(--ink); padding: clamp(80px,12vh,160px) var(--pad-x) clamp(70px,9vh,110px); }
/* Carrusel horizontal de posts. En escritorio, .blog-wrap es alto (100vh +
   recorrido, lo fija main.js) y la sección queda PEGADA con position:sticky
   — el enganche lo hace el navegador en el sitio exacto, sin saltos — y el
   scroll sobrante desplaza la vía. En móvil, deslizamiento lateral nativo. */
.blog-wrap { position: relative; }
/* Mientras está anclada, la sección se COMPACTA (rellenos y márgenes más
   cortos y tarjetas capadas por alto de viewport) para que titular,
   tarjetas y títulos quepan SIEMPRE enteros en pantalla. */
.blog-wrap.is-sticky .blog {
  position: sticky; top: 0; min-height: 100vh; box-sizing: border-box;
  display: flex; flex-direction: column; justify-content: center;
  padding-top: clamp(50px, 7vh, 90px);
  padding-bottom: clamp(22px, 3.5vh, 50px);
}
.blog-wrap.is-sticky .blog__head { margin-bottom: clamp(16px, 2.5vh, 34px); }
.blog-wrap.is-sticky .blog-rail__track .post {
  flex-basis: min(clamp(280px, 30vw, 420px), 51vh);
}
.blog-rail { overflow: hidden; }
.blog-rail__track {
  display: flex; gap: clamp(18px, 2vw, 32px); align-items: stretch;
  will-change: transform;
}
.blog-rail__track .post { flex: 0 0 clamp(280px, 30vw, 420px); min-width: 0; }
@media (max-width: 900px) {
  .blog-rail { overflow-x: auto; -webkit-overflow-scrolling: touch; scrollbar-width: none; }
  .blog-rail::-webkit-scrollbar { display: none; }
  .blog-rail__track { width: max-content; padding-right: var(--pad-x); }
  .blog-rail__track .post { flex-basis: 78vw; }
}
.blog__head { display: flex; align-items: center; justify-content: space-between; gap: 30px; flex-wrap: wrap; margin-bottom: 6vh; }
.blog__heading { font-size: clamp(50px,7vw,130px); font-weight: 600; letter-spacing: -0.02em; color: var(--deep); }
.blog__head .btn-outline--light { border-color: var(--deep); color: var(--deep); }
.blog__head .btn-outline--light:hover { background: var(--deep); color: var(--foam); }
/* minmax(0,1fr): columnas SIEMPRE iguales — evita que el tamaño
   mínimo de una tarjeta (p. ej. un placeholder con height:100%)
   desequilibre el grid */
.blog__grid { display: grid; grid-template-columns: repeat(3, minmax(0,1fr)); gap: 24px; }
.post__media { aspect-ratio: 4/3; border-radius: var(--radius-lg) 100px var(--radius-lg) 4px; overflow: hidden; }
/* El alto lo dicta el aspect-ratio a partir del ANCHO (anula el
   height:100% heredado de .media-placeholder) */
.post__media.media-placeholder { height: auto; }
/* Fotos reales de los pasos: llenan la tarjeta flotante (que conserva
   su giro, sombra y aparición al activarse el paso) */
.step__media img { width: 100%; height: 100%; object-fit: cover; display: block; }
/* Vídeos de los pasos: mismo encuadre que la foto (recorta el 16:9 dentro
   del 4:3 de la tarjeta, conservando giro, sombra y aparición al activarse) */
.step__media video { width: 100%; height: 100%; object-fit: cover; display: block; }
.post__cat { margin: 22px 0 10px; font-size: 12px; letter-spacing: 1px; font-weight: 700; color: var(--slate); }
.post__title { font-size: clamp(20px,1.7vw,26px); font-weight: 500; line-height: 1.25; }

/* ---------- 14. FAQ's — fondo claro ---------- */
/* separación moderada respecto al blog (el colchón para el reveal de las
   tarjetas lo pone el padding-bottom de .blog) */
.faq { background: transparent; color: var(--ink); padding: clamp(70px,10vh,130px) var(--pad-x) clamp(120px,18vh,220px); }
.faq__heading { font-size: clamp(50px,7vw,130px); font-weight: 600; letter-spacing: -0.02em; margin-bottom: 7vh; color: var(--deep); }
.faq__item { opacity: .3; transition: opacity .45s ease; }
.faq__item.is-near { opacity: 1; }
.faq__q {
  width: 100%; background: none; border: 0; color: var(--ink); cursor: pointer;
  display: flex; align-items: flex-start; gap: 22px; text-align: left;
  padding: 20px 0; font-size: clamp(18px,1.6vw,24px); font-weight: 500;
}
.faq__icon { font-size: 26px; line-height: 1.2; transition: transform .35s ease; flex-shrink: 0; color: var(--signal); }
.faq__item.open .faq__icon { transform: rotate(45deg); }
.faq__a { overflow: hidden; height: 0; opacity: 0; transition: height .4s ease, opacity .4s ease; }
.faq__a p { padding: 0 0 26px 48px; max-width: 720px; color: var(--slate); font-size: 17px; }

/* ---------- 15. KOTAVERSE — bloque de contraste (deep) ---------- */
.kotaverse {
  /* Altura = proporción del CONTENIDO del vídeo (1920x820, sin las barras de
     letterbox). Así el vídeo (object-fit:cover, sin ampliar) recorta las barras
     exactamente y la sección termina justo donde termina el vídeo: sin franja
     azul entre el header y el vídeo, ni entre el vídeo y el footer. */
  position: relative; background: var(--deep); color: var(--foam);
  aspect-ratio: 1920 / 820;
  display: flex; flex-direction: column; align-items: center;
  /* center: sin el CTA, el tag y el marquee quedan agrupados y centrados
     sobre el vídeo (se retiró el botón "Pide tu diagnóstico gratis"). */
  justify-content: center; gap: 40px;
  padding: 7vh 0;
  overflow: hidden;
}
/* Tag y marquee por encima del blob (cada uno con su z-index:2). */
.kotaverse__blob {
  position: absolute; width: 46vh; height: 46vh; border-radius: 50%;
  background: conic-gradient(from 0deg, var(--signal-700), var(--signal), var(--sun), var(--signal), var(--signal-700));
  filter: blur(6px) saturate(1.4); animation: spinBlob 14s linear infinite;
  box-shadow: 0 0 120px 30px rgba(31,182,193,.45);
}
@keyframes spinBlob { to { transform: rotate(360deg); } }
/* Tag del cierre: grande y visual, legible sobre el vídeo del blob
   gracias a la sombra suave (no depende de lo que haya detrás) */
.kotaverse__tag {
  position: relative; z-index: 2;
  font-size: clamp(26px, 3.4vw, 58px); font-weight: 800;
  letter-spacing: .06em; text-transform: uppercase;
  text-align: center;
  text-shadow: 0 2px 10px rgba(4, 12, 24, .55), 0 8px 40px rgba(4, 12, 24, .45);
}
.marquee { position: relative; z-index: 2; width: 100%; overflow: hidden; white-space: nowrap; }
/* En el cierre: la marquesina DUOWAVE clavada en el CENTRO exacto de la
   figura del vídeo, y el tag flotando por encima (antes se centraban
   como grupo y las letras caían por debajo del centro). */
.kotaverse .marquee {
  position: absolute; left: 0; top: 50%; transform: translateY(-50%);
}
.kotaverse__tag {
  position: absolute; left: 0; right: 0;
  bottom: calc(50% + clamp(92px, 8.2vw, 165px));
}
.marquee__track { display: inline-flex; gap: 40px; font-size: clamp(60px,10vw,180px); font-weight: 800; letter-spacing: -0.02em; will-change: transform; }
.marquee__track span { padding-right: 40px; }
/* Logo DuoWave entre las palabras del marquee (sustituye al ▪),
   como el logo del header: escala con el tamaño de letra del track */
.marquee__logo {
  height: .48em; width: auto;
  display: inline-block; vertical-align: middle;
  margin: 0 .12em; position: relative; top: -.04em;
}
.btn-outline--light { border-color: var(--foam); color: var(--foam); }
.btn-outline--light:hover { background: var(--foam); color: var(--deep); }

/* ---------- 16. FOOTER — bloque de contraste (deep) ---------- */
.site-footer { background: var(--deep); color: var(--foam); padding: clamp(60px,9vh,120px) var(--pad-x) 40px; }
.footer__top { display: flex; align-items: center; gap: 40px; flex-wrap: wrap; margin-bottom: 8vh; }
.footer__email {
  font-size: clamp(34px,5.5vw,100px); font-weight: 500; letter-spacing: -0.02em;
  background: linear-gradient(90deg, var(--signal), var(--sun));
  -webkit-background-clip: text; background-clip: text; color: transparent;
}
.footer__mid { display: flex; justify-content: space-between; gap: 40px; flex-wrap: wrap; padding-bottom: 8vh; }
.footer__social, .footer__links { display: flex; gap: 28px; flex-wrap: wrap; }
.footer__social { margin-bottom: 26px; }
.footer__social a:hover, .footer__links a:hover { opacity: .6; }
.footer__links a { color: rgba(255,255,255,.7); }
.footer__col--right { display: flex; flex-direction: column; align-items: flex-end; justify-content: center; gap: 26px; }
.footer__awards { display: flex; gap: 26px; flex-wrap: wrap; font-size: 12px; font-weight: 700; letter-spacing: .5px; opacity: .8; }
.footer__sectors { display: flex; align-items: center; gap: 14px; flex-wrap: wrap; padding-top: 40px; border-top: 1px solid rgba(255,255,255,.15); }
.footer__sectors-label { font-size: 14px; opacity: .7; }
.footer__sectors .tags--dark { margin: 0; }
.footer__copy { margin-left: auto; font-size: 14px; opacity: .7; }
.footer__note { margin-top: 40px; font-size: 13px; color: rgba(255,255,255,.4); }
.site-footer .logo__box { color: var(--foam); }

/* ---------- 17. UTILIDAD REVEAL ----------
   El estado oculto SOLO aplica si main.js llegó a arrancar (añade
   html.anim). Si GSAP no carga o el motor no arranca, la página se ve
   completa en estático — nada puede quedarse invisible. */
html.anim .reveal { opacity: 0; transform: translateY(40px); }

/* Máscara por línea para titulares grandes: cada línea vive dentro de
   un contenedor con overflow hidden y sube desde abajo (main.js los
   envuelve automáticamente en los <h2 data-mask-lines>). */
/* Recorte SOLO vertical: la letra final con tracking negativo
   (p. ej. la S de SERVICIOS) ya no se corta por el lado derecho.
   El padding inferior (compensado con margen negativo) da sitio a los
   descendentes ("j" de trabajos, "q" de qué) sin alterar el layout. */
.line-mask {
  display: block; overflow-x: visible; overflow-y: clip;
  padding-bottom: .14em; margin-bottom: -.14em;
}
.line-mask > * { display: block; }

/* ---------- 17b. VÍDEOS (hero, tarjetas de servicio, blob CTA) ---------- */
/* Hero: vídeo FIJO que hace de fondo de toda la parte clara de la web
   (hero + servicios + beneficios). Las secciones oscuras que vienen
   después tienen fondo sólido y lo tapan de forma natural. */
.hero__video {
  position: fixed; inset: 0; width: 100%; height: 100%;
  object-fit: cover; z-index: -2;
}
/* Póster estático del hero: solo se muestra si el vídeo está oculto
   (prefers-reduced-motion). Mismo comportamiento de fondo fijo. */
.hero__poster {
  display: none; position: fixed; inset: 0; width: 100%; height: 100%;
  object-fit: cover; z-index: -2;
}
/* Overlay foam semitransparente fijo: garantiza legibilidad del texto
   en todas las secciones claras que dejan ver el vídeo */
.hero__overlay {
  position: fixed; inset: 0; z-index: -1; pointer-events: none;
  background: color-mix(in srgb, var(--foam) 55%, transparent);
}

/* Tarjetas de servicio: vídeo dentro del contenedor existente */
.stack__media--video { position: relative; }
.stack__video { width: 100%; height: 100%; object-fit: cover; display: block; }
.stack__poster {
  display: none; width: 100%; height: 100%; object-fit: cover;
}

/* Blob del CTA final en vídeo: más grande que el gradiente original y
   "sin fondo" — mix-blend-mode:lighten funde el fondo oscuro del vídeo
   con el fondo deep de la sección (solo queda visible el blob brillante),
   como en la referencia. Sin máscara circular ni glow. */
.kotaverse__blob--video {
  /* Full-bleed: cubre TODA la sección de borde a borde. inset:0 + width/height
     100% + object-fit:cover. El vídeo NO se amplía (sin transform, nítido): es
     la SECCIÓN la que adopta la proporción del CONTENIDO del vídeo (1920x820,
     ver .kotaverse), de modo que el cover recorta justo las barras negras
     incrustadas (~130px arriba/abajo) sin sobrar franjas ni ampliar el vídeo. */
  inset: 0; width: 100%; height: 100%;
  object-fit: cover; object-position: center;
  background: none; filter: none; animation: none;
  border-radius: 0; box-shadow: none;
  mix-blend-mode: lighten;
  /* Máscara de difuminado en los bordes (NO cambia tamaño/posición/nitidez):
     el vídeo se desvanece a transparente y deja ver el fondo --deep (#0A2540)
     de la sección — el mismo del footer — así no se ve la línea donde el fondo
     del vídeo no casa exacto con el azul. Arriba ~10% (suaviza el header),
     abajo se desvanece desde el 75% hasta el 100% (funde con el footer). */
  -webkit-mask-image: linear-gradient(to bottom, transparent 0%, #000 10%, #000 75%, transparent 100%);
          mask-image: linear-gradient(to bottom, transparent 0%, #000 10%, #000 75%, transparent 100%);
}
/* Póster del blob: solo visible con prefers-reduced-motion */
.kotaverse__blob--poster {
  display: none; inset: 0; width: 100%; height: 100%;
  object-fit: cover; object-position: center;
  background: none; filter: none; animation: none;
  border-radius: 0; box-shadow: none;
  mix-blend-mode: lighten;
  -webkit-mask-image: linear-gradient(to bottom, transparent 0%, #000 10%, #000 75%, transparent 100%);
          mask-image: linear-gradient(to bottom, transparent 0%, #000 10%, #000 75%, transparent 100%);
}
/* Móvil: en vertical la proporción 1920/820 dejaría la sección demasiado baja
   para el tag y el marquee. Volvemos a alto completo (como antes); el vídeo del
   cierre se reproduce igual y el texto tiene sitio. */
@media (max-width: 900px) {
  .kotaverse { aspect-ratio: auto; min-height: 100vh; }
}

/* Móvil: las tarjetas de servicio muestran solo el póster;
   el vídeo se mantiene únicamente en el hero */
@media (max-width: 768px) {
  .stack__video { display: none; }
  .stack__poster { display: block; }
}

/* Accesibilidad: sin movimiento → nada de vídeo, solo pósters */
@media (prefers-reduced-motion: reduce) {
  .hero__video, .stack__video, .kotaverse__blob--video { display: none; }
  .hero__poster, .stack__poster { display: block; }
  .kotaverse__blob--poster { display: block; }
}
/* Móvil: el vídeo de fondo (que carga en todas las páginas) se sustituye
   por su póster estático → menos datos y batería. */
@media (max-width: 900px) {
  .hero__video { display: none; }
  .hero__poster { display: block; }
}

/* ---------- 18. RESPONSIVE (sin cambios) ---------- */
@media (max-width: 900px) {
  .header__tag { display: none; }

  .line--indent-lg, .line--indent-sm, .line--indent-md { margin-left: 0; }
  .hero__desc { position: static; margin-top: 40px; max-width: 100%; }
  .hero__scroll { bottom: 14px; }
  .hero { padding-top: 120px; padding-bottom: 60px; }

  .zone-heading { flex-direction: column; align-items: flex-start; gap: 20px; }
  .zone-heading__indent { margin-left: 0; }

  .stack__card { grid-template-columns: 1fr; min-height: auto; top: 8vh; }
  .stack__media { min-height: 240px; }

  .step__row { grid-template-columns: 1fr; }
  .step__media { display: none; }

  .work__grid { grid-template-columns: 1fr; }
  .case-card__media { min-height: 240px; }

  .testimonials { grid-template-columns: 1fr; }
  /* Colapsar la columna NO basta. Un ítem de grid arranca con min-width:auto,
     así que no puede encogerse por debajo de su ancho de contenido mínimo — y
     Swiper le fija a la baraja un ancho por estilo inline. Resultado: la
     columna 1fr se estiraba a 640px y el documento cogía scroll horizontal
     (435px a 360px de viewport). Con min-width:0 el ítem ya puede encoger y
     Swiper recalcula sobre el ancho real. Se arregla aquí, en el ítem, y no
     con overflow-x:hidden en body: eso taparía el síntoma dejando el
     contenido cortado. */
  .testi-wrap { min-width: 0; overflow-x: clip; }
  /* El min-width se lleva la mayor parte (435px → 67px a 360), pero no todo:
     el efecto swiper-cards ladea las slides con matrix3d y sobresalen ~30px
     por la derecha, y .testi-swiper las deja asomar a propósito
     (overflow: visible, más arriba) para que se vea la baraja girada.

     Lo que decide recortar NO es el scroll lateral en sí, es su efecto
     secundario: el desborde estira los elementos position:fixed al ancho del
     documento, y con eso el burger sale cortado y el CTA "Pide tu diagnóstico
     gratis" se queda fuera de pantalla. Recortar ~30px de una tarjeta que ya
     estaba medio fuera cuesta menos que esconder el CTA principal.

     clip y no hidden: hidden forzaría el eje vertical a auto y crearía un
     contenedor de scroll. Y va aquí, en el contenedor de la baraja, no en
     body: mismo patrón que .work, .process, .chat-sec o .kotaverse. Solo
     móvil — en escritorio el giro se mantiene intacto. */
  .partners__grid { grid-template-columns: repeat(2,1fr); gap: 40px 20px; }
  .blog__grid { grid-template-columns: 1fr; }
  .footer__mid { flex-direction: column; }
  .footer__col--right { align-items: flex-start; }
  .footer__copy { margin-left: 0; }
}

/* ============================================================
   19. ANALIZA TU NEGOCIO — chat de diagnóstico conversacional
   Widget portado del proyecto anterior, reescrito sobre la
   paleta y la tipografía de web2 (Manrope). Es una sección
   OSCURA (como NUESTROS CASOS y el cierre DUOWAVE): tapa el
   vídeo fijo del hero. Los tintes que no están en :root se
   definen como tokens locales scoped en .chat-sec.
   JS: bloque 13 de main.js (initChat).
   ============================================================ */
.chat-sec {
  /* Tokens locales (tintes que no existen en la paleta global) */
  --c-teal-soft: #E4F6F8;   /* burbuja del bot / superficies suaves de signal */
  --c-online:    #2FBF71;   /* punto "En línea" */
  --c-danger:    #E5484D;   /* validación de error */
  --c-deep-2:    #12466E;   /* navy más claro para degradados */
  --c-deep-0:    #071A30;   /* navy más oscuro para el fondo */
  --c-field-r:   14px;      /* radio de inputs/botones del chat */

  position: relative;
  z-index: 1;
  overflow: hidden;
  color: #fff;
  padding: clamp(72px, 12vh, 150px) var(--pad-x);
  /* MISMO fondo que NUESTROS CASOS: navy plano + starfield en canvas
     (se retiraron el degradado y la textura de puntos propios) */
  background-color: var(--deep);
  /* ANALIZA abre ahora la zona oscura (va antes que CASOS): hereda las
     esquinas superiores redondeadas que tenía .work */
  border-radius: var(--radius-xl) var(--radius-xl) 0 0;
}

/* Resplandores retirados: rompían la igualdad con el fondo estrellado
   de NUESTROS CASOS (se conserva el markup por si se recuperan) */
.chat-sec__glow { display: none; }
.chat-sec__glow-old {
  position: absolute;
  z-index: 0;
  width: clamp(320px, 42vw, 560px);
  height: clamp(320px, 42vw, 560px);
  border-radius: 50%;
  filter: blur(90px);
  opacity: .55;
  pointer-events: none;
}
.chat-sec__glow--teal { background: radial-gradient(circle, rgba(31,182,193,.55), transparent 70%); top: -170px; right: -130px; }
.chat-sec__glow--sun  { background: radial-gradient(circle, rgba(255,163,31,.40), transparent 70%); bottom: -190px; left: -150px; }

.chat-sec__wrap { position: relative; z-index: 1; max-width: 1120px; margin: 0 auto; }

/* Rejilla: panel de apoyo (izq) + chat (der) */
.analiza-grid {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 6fr);
  gap: clamp(32px, 5vw, 72px);
  align-items: center;
}

/* ── Panel de apoyo ── */
.analiza-aside { max-width: 480px; }
.analiza-badge__dot { width: 7px; height: 7px; border-radius: 50%; background: var(--sun); box-shadow: 0 0 0 4px rgba(255,163,31,.18); }

.analiza-title {
  font-family: var(--font);
  font-weight: 800;
  text-transform: uppercase;
  font-size: clamp(30px, 4vw, 52px);
  line-height: 1.02;
  letter-spacing: -.02em;
  color: #fff;
  margin-top: 20px;
}
.analiza-title .hl-sun { color: var(--sun); }

.analiza-sub {
  margin-top: 16px;
  max-width: 42ch;
  color: rgba(255,255,255,.72);
  font: 400 clamp(15px, 1.3vw, 18px)/1.65 var(--font);
}

.analiza-benefits { list-style: none; margin-top: 28px; display: flex; flex-direction: column; gap: 14px; }
.analiza-benefits li {
  display: flex; align-items: center; gap: 13px;
  font: 500 clamp(15px, 1.2vw, 16.5px)/1.3 var(--font);
  color: rgba(255,255,255,.92);
}
.analiza-benefit__ic {
  width: 28px; height: 28px; border-radius: 50%;
  flex-shrink: 0;
  display: flex; align-items: center; justify-content: center;
  color: var(--signal);
  background: rgba(31,182,193,.16);
  border: 1px solid rgba(31,182,193,.32);
}

/* ── Tarjeta del chat (clara, flotando sobre navy) ── */
.chat {
  width: 100%;
  background: #fff;
  border: 1px solid rgba(255,255,255,.65);
  border-radius: clamp(18px, 1.8vw, 26px);
  box-shadow: 0 40px 80px -22px rgba(0,0,0,.55), 0 8px 24px rgba(0,0,0,.20);
  overflow: hidden;
  display: flex;
  flex-direction: column;
}

/* Cabecera */
.chat__head {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 15px 18px;
  border-bottom: 1px solid var(--border);
  background: linear-gradient(180deg, #ffffff, #f6f9fc);
}
.chat__head-avatar {
  width: 42px; height: 42px;
  border-radius: 50%;
  background: linear-gradient(135deg, var(--deep) 8%, var(--signal));
  color: #fff;
  display: flex; align-items: center; justify-content: center;
  font: 800 17px/1 var(--font);
  flex-shrink: 0;
  box-shadow: 0 6px 16px rgba(31,182,193,.40);
}
.chat__head-info { display: flex; flex-direction: column; gap: 3px; margin-right: auto; }
.chat__head-name { font: 700 14px/1 var(--font); color: var(--deep); }
.chat__head-status { display: inline-flex; align-items: center; gap: 6px; font: 400 12px/1 var(--font); color: var(--slate); }
.chat__dot-online { width: 8px; height: 8px; border-radius: 50%; background: var(--c-online); box-shadow: 0 0 0 3px rgba(47,191,113,.18); animation: chatPulse 2.2s infinite ease-in-out; }
@keyframes chatPulse { 0%, 100% { box-shadow: 0 0 0 3px rgba(47,191,113,.18); } 50% { box-shadow: 0 0 0 6px rgba(47,191,113,.04); } }

.chat__progress { text-align: right; flex-shrink: 0; }
.chat__progress-label { display: block; font: 600 11px/1 var(--font); color: var(--slate); margin-bottom: 6px; }
.chat__progress-track { display: block; width: clamp(84px, 20vw, 132px); height: 5px; border-radius: var(--radius-pill); background: var(--border); overflow: hidden; }
.chat__progress-fill { display: block; height: 100%; width: 12.5%; border-radius: var(--radius-pill); background: linear-gradient(90deg, var(--signal), var(--sun)); transition: width .45s cubic-bezier(.22,.61,.36,1); }

/* Registro de conversación */
.chat__log {
  display: flex;
  flex-direction: column;
  gap: 14px;
  padding: 24px 20px;
  min-height: clamp(320px, 42vh, 420px);
  max-height: 460px;
  overflow-y: auto;
  scroll-behavior: smooth;
  background:
    radial-gradient(rgba(10,37,64,0.032) 1px, transparent 1.4px) 0 0 / 18px 18px,
    #fff;
  scrollbar-width: thin;
  scrollbar-color: var(--border) transparent;
}
.chat__log::-webkit-scrollbar { width: 8px; }
.chat__log::-webkit-scrollbar-thumb { background: var(--border); border-radius: 99px; }

.chat__row { display: flex; align-items: flex-end; gap: 9px; max-width: 100%; animation: chatIn .4s cubic-bezier(.22,.61,.36,1) both; }
.chat__row--user { flex-direction: row-reverse; }
@keyframes chatIn { from { opacity: 0; transform: translateY(12px) scale(.98); } to { opacity: 1; transform: none; } }

.chat__avatar {
  width: 30px; height: 30px;
  border-radius: 50%;
  background: linear-gradient(135deg, var(--deep), var(--signal));
  color: #fff;
  display: flex; align-items: center; justify-content: center;
  font: 800 12px/1 var(--font);
  flex-shrink: 0;
}
.chat__bubble {
  max-width: 82%;
  padding: 12px 16px;
  border-radius: 18px;
  font: 400 15px/1.5 var(--font);
  word-wrap: break-word;
  overflow-wrap: anywhere;
  box-shadow: 0 2px 8px rgba(10,37,64,.06);
}
.chat__row--bot  .chat__bubble { background: var(--c-teal-soft); color: var(--deep); border-bottom-left-radius: 6px; }
.chat__row--user .chat__bubble { background: linear-gradient(135deg, var(--deep), var(--c-deep-2)); color: #fff; border-bottom-right-radius: 6px; box-shadow: 0 8px 18px rgba(10,37,64,.24); }

/* Indicador "escribiendo…" */
.chat__typing { display: inline-flex; align-items: center; gap: 5px; padding: 15px 17px; background: var(--c-teal-soft); border-radius: 18px; border-bottom-left-radius: 6px; }
.chat__typing span { width: 7px; height: 7px; border-radius: 50%; background: var(--signal); opacity: .5; animation: chatDot 1.2s infinite ease-in-out; }
.chat__typing span:nth-child(2) { animation-delay: .18s; }
.chat__typing span:nth-child(3) { animation-delay: .36s; }
@keyframes chatDot { 0%, 60%, 100% { transform: translateY(0); opacity: .45; } 30% { transform: translateY(-5px); opacity: 1; } }

/* Zona de entrada */
.chat__input { padding: 16px 20px; border-top: 1px solid var(--border); background: linear-gradient(180deg, #f6f9fc, #ffffff); min-height: 78px; }
.chat__input:empty { display: none; }

.chat__options { display: flex; flex-wrap: wrap; gap: 9px; }
.chat__opt {
  padding: 11px 17px;
  border: 1.5px solid rgba(31,182,193,.45);
  color: var(--signal-700);
  background: rgba(31,182,193,.06);
  border-radius: var(--radius-pill);
  font: 600 14px/1 var(--font);
  cursor: pointer;
  transition: background .18s, color .18s, border-color .18s, transform .18s, box-shadow .18s;
}
.chat__opt:hover { background: var(--signal); color: #fff; border-color: var(--signal); transform: translateY(-2px); box-shadow: 0 8px 18px rgba(31,182,193,.32); }
.chat__opt.is-sel { background: var(--deep); border-color: var(--deep); color: #fff; box-shadow: 0 6px 16px rgba(10,37,64,.25); }
.chat__opt.is-sel::after { content: " ✓"; font-weight: 700; }

.chat__multi-actions { margin-top: 14px; }

.chat__field { display: flex; gap: 10px; align-items: stretch; }
.chat__field input {
  flex: 1; min-width: 0;
  height: 52px;
  border: 1.5px solid var(--border);
  border-radius: var(--c-field-r);
  padding: 0 16px;
  font: 400 15px/1 var(--font);
  color: var(--deep);
  background: #fff;
  transition: border-color .18s, box-shadow .18s;
}
.chat__field input::placeholder { color: var(--slate); }
.chat__field input:focus { outline: none; border-color: var(--signal); box-shadow: 0 0 0 4px rgba(31,182,193,.16); }
.chat__field input.is-error { border-color: var(--c-danger); box-shadow: 0 0 0 4px rgba(229,72,77,.14); }

.chat__send {
  flex-shrink: 0;
  height: 52px;
  padding: 0 22px;
  background: var(--deep);
  color: #fff;
  border: 0;
  border-radius: var(--c-field-r);
  font: 600 14px/1 var(--font);
  cursor: pointer;
  display: inline-flex; align-items: center; gap: 7px;
  transition: background .18s, color .18s, transform .18s, box-shadow .18s;
}
.chat__send:hover { background: var(--sun); color: var(--deep); transform: translateY(-2px); box-shadow: 0 8px 20px rgba(255,163,31,.34); }
.chat__send svg { flex-shrink: 0; }

.chat__hint { margin-top: 9px; font: 400 12px/1.4 var(--font); color: var(--slate); }
.chat__hint--error { color: var(--c-danger); }

.chat__retry {
  margin-top: 4px;
  padding: 12px 20px;
  background: var(--deep); color: #fff;
  border: 0; border-radius: var(--radius-pill);
  font: 600 14px/1 var(--font); cursor: pointer;
  transition: background .18s, color .18s;
}
.chat__retry:hover { background: var(--sun); color: var(--deep); }

/* ── Responsive del chat ── */
@media (max-width: 900px) {
  .analiza-grid { grid-template-columns: 1fr; gap: clamp(28px, 5vw, 40px); max-width: 620px; margin: 0 auto; }
  .analiza-aside { max-width: none; }
}
@media (max-width: 560px) {
  .chat__head { flex-wrap: wrap; }
  .chat__progress { width: 100%; text-align: left; margin-top: 6px; }
  .chat__progress-track { width: 100%; }
  .chat__log { max-height: 62vh; padding: 20px 15px; }
  .chat__input { padding: 15px; }
  .chat__bubble { max-width: 86%; }
  .chat__field { flex-direction: column; }
  .chat__field input, .chat__send { width: 100%; }
  .chat__send { justify-content: center; }
}

/* Accesibilidad: sin movimiento → sin animaciones del chat */
@media (prefers-reduced-motion: reduce) {
  .chat__row { animation: none !important; }
  .chat__typing span { animation: none !important; opacity: .6 !important; }
  .chat__dot-online { animation: none !important; }
  .chat__log { scroll-behavior: auto !important; }
}

/* ============================================================
   20. CASOS — botón CTA sólido, carrusel de la home (scroll-snap
   vanilla, variante B: profundidad por escala/opacidad/blur) y
   páginas de casos (listado + caso individual). Solo Manrope.
   Anima únicamente transform / opacity / filter. Curva
   cubic-bezier(0.22,1,0.36,1). El detalle del movimiento vive
   en main.js (bloque 14).
   ============================================================ */

/* ---- CTA sólido primario (no existía uno relleno) ---- */
.btn-cta {
  display: inline-flex; align-items: center; gap: 10px;
  background: var(--sun); color: var(--deep);
  border: 0; border-radius: var(--radius-pill);
  padding: 15px 26px; font: 700 15px/1 var(--font); cursor: pointer;
  transition: transform .3s cubic-bezier(.22,1,.36,1), box-shadow .3s cubic-bezier(.22,1,.36,1);
}
.btn-cta:hover { transform: translateY(-2px); box-shadow: 0 12px 26px rgba(255,163,31,.34); }
.btn-cta .arrow { transition: transform .3s cubic-bezier(.22,1,.36,1); }
.btn-cta:hover .arrow { transform: translateX(4px); }

/* ---- Carrusel de la home ---- */
.cases-carousel {
  --cc-w: clamp(280px, 56vw, 780px);   /* tarjetas más pequeñas (antes 64vw/900) */
  --cc-gap: clamp(16px, 2.4vw, 36px);
  position: relative; z-index: 1; text-align: center;
  margin-top: clamp(6px, 1.2vw, 16px);   /* REDUCIDO (antes 36-72px): más pegado al título */
  /* Full-bleed: de filo a filo del viewport (escapa del padding de .work) para
     que el viewport recorte las vecinas contra el BORDE REAL de la pantalla, sin
     hueco navy. El viewport (100%) y .cases-carousel comparten el mismo borde
     izquierdo (=0), así el JS (card.offsetLeft vs vp.scrollLeft) sigue correcto. */
  width: 100vw; max-width: 100vw; margin-left: calc(50% - 50vw);
}
.cc-viewport {
  display: flex; overflow-x: auto; scroll-snap-type: x mandatory;
  scroll-behavior: smooth; scrollbar-width: none; -ms-overflow-style: none;
  padding-block: clamp(14px, 2vw, 28px) clamp(24px, 4vw, 52px); outline: none;   /* top reducido; bottom igual (hueco de las tarjetas retrocedidas) */
}
.cc-viewport::-webkit-scrollbar { display: none; }
.cc-viewport:focus-visible { box-shadow: 0 0 0 3px rgba(31,182,193,.5); border-radius: 30px; }
.cc-track {
  display: flex; gap: var(--cc-gap); margin: 0 auto;
  padding-inline: max(var(--pad-x), calc((100% - var(--cc-w)) / 2));
}
.cc-card {
  scroll-snap-align: center; flex: 0 0 var(--cc-w);
  display: grid; grid-template-columns: 1fr 1fr;
  min-height: clamp(320px, 38vw, 440px);   /* más bajas (antes 44vw/500) */
  background: var(--surface); border: 1px solid var(--border);
  border-radius: 26px; overflow: hidden; text-align: left;
  box-shadow: 0 20px 50px -30px rgba(10,37,64,.30);
  /* estado por defecto = adyacente (retrocedido en el arco) */
  transform: scale(.88) translateY(22px); opacity: .5; filter: blur(2px);
  transition: transform .5s cubic-bezier(.22,1,.36,1),
              opacity   .5s cubic-bezier(.22,1,.36,1),
              filter    .5s cubic-bezier(.22,1,.36,1),
              box-shadow .5s cubic-bezier(.22,1,.36,1);
}
.cc-card.is-active {
  transform: none; opacity: 1; filter: none;
  box-shadow: 0 44px 80px -40px rgba(10,37,64,.45);
}
.cc-card.is-active:hover { transform: translateY(-6px); box-shadow: 0 54px 90px -42px rgba(10,37,64,.5); }
/* will-change solo mientras el carrusel se mueve (main.js lo activa) */
.cases-carousel.is-scrolling .cc-card { will-change: transform, opacity, filter; }

.cc-card__media { position: relative; overflow: hidden; background: var(--deep); }
.cc-card__img {
  width: 100%; height: 100%; object-fit: cover; display: block;
  transform: scale(1.08);   /* la tarjeta entrante hace zoom-out a 1.0 al activarse */
  transition: transform .6s cubic-bezier(.22,1,.36,1);
}
.cc-card.is-active .cc-card__img { transform: scale(1); }
.cc-card.is-active:hover .cc-card__img { transform: scale(1.03); }
.cc-card__media--ph { display: grid; place-content: center;
  background: linear-gradient(135deg, var(--deep), var(--ink)); }
.cc-card__ph-label { font: 600 13px/1 var(--font); letter-spacing: .18em; color: var(--foam); opacity: .65; }

.cc-card__body { padding: clamp(24px, 2.6vw, 44px); display: flex; flex-direction: column; }
.cc-card__sector { font: 700 12px/1 var(--font); letter-spacing: .16em; text-transform: uppercase; color: var(--signal); margin-bottom: 16px; }
.cc-card__name { font: 800 clamp(28px, 3.2vw, 46px)/1 var(--font); letter-spacing: -0.02em; color: var(--deep); }
.cc-card__summary { margin: 16px 0 20px; color: var(--slate); font-size: clamp(15px, 1.2vw, 18px); line-height: 1.55; }
.cc-card__bullets { list-style: none; display: flex; flex-direction: column; gap: 10px; margin-bottom: 28px; }
.cc-card__bullets li { position: relative; padding-left: 22px; color: var(--ink); font-size: 15px; line-height: 1.4; }
.cc-card__bullets li::before { content: ""; position: absolute; left: 0; top: .45em; width: 8px; height: 8px; border-radius: 2px; background: var(--sun); }
.cc-card .btn-cta { margin-top: auto; align-self: flex-start; }

/* Flechas */
.cc-arrow {
  position: absolute; top: 50%; transform: translateY(-50%); z-index: 3;
  width: 52px; height: 52px; border-radius: 50%; border: 1px solid var(--border);
  background: var(--surface); color: var(--deep); font-size: 26px; line-height: 1; cursor: pointer;
  display: grid; place-content: center; box-shadow: 0 10px 30px -12px rgba(10,37,64,.4);
  transition: transform .3s cubic-bezier(.22,1,.36,1), background .3s, color .3s, opacity .3s;
}
.cc-arrow:hover { transform: translateY(-50%) scale(1.08); background: var(--deep); color: var(--foam); }
.cc-arrow--prev { left: clamp(6px, 2vw, 24px); }
.cc-arrow--next { right: clamp(6px, 2vw, 24px); }
.cc-arrow:disabled { opacity: .3; pointer-events: none; }

/* Dots */
.cc-dots { display: flex; justify-content: center; gap: 10px; margin-top: 26px; }
.cc-dot { width: 9px; height: 9px; border-radius: 50%; border: 0; padding: 0; cursor: pointer;
  background: rgba(255,255,255,.35); transition: transform .3s cubic-bezier(.22,1,.36,1), background .3s; }
.cc-dot.is-active { background: var(--sun); transform: scale(1.4); }

/* "Ver todos los casos": más grande y más separado de los dots */
.cc-all { display: inline-flex; align-items: center; gap: 11px; margin-top: clamp(34px, 5vh, 52px);
  color: var(--foam); font-weight: 600; font-size: clamp(17px, 1.5vw, 21px); opacity: .82;
  padding: 10px 16px; transition: opacity .3s, transform .3s cubic-bezier(.22,1,.36,1); }
.cc-all:hover { opacity: 1; }
.cc-all .arrow { transition: transform .3s cubic-bezier(.22,1,.36,1); }
.cc-all:hover .arrow { transform: translateX(4px); }

/* Tablet: tarjeta algo más ancha, mismo 50/50, efectos on */
@media (max-width: 900px) {
  .cases-carousel { --cc-w: min(80vw, 560px); }
}
/* Móvil: apila (imagen arriba, contenido debajo), SIN blur ni escalado */
@media (max-width: 600px) {
  .cases-carousel { --cc-w: 86vw; }
  .cc-card { grid-template-columns: 1fr; grid-template-rows: auto auto; min-height: 0; }
  .cc-card__media { aspect-ratio: 16 / 10; }
  .cc-card, .cc-card.is-active, .cc-card.is-active:hover { transform: none; opacity: 1; filter: none; }
  .cc-card__img, .cc-card.is-active .cc-card__img, .cc-card.is-active:hover .cc-card__img { transform: none; }
  .cc-arrow { display: none; }
}
/* Reduced-motion: sin efectos, el carrusel solo cambia de tarjeta */
@media (prefers-reduced-motion: reduce) {
  .cc-card, .cc-card__img, .cc-arrow, .cc-dot, .btn-cta, .btn-cta .arrow { transition: none !important; }
  .cc-card, .cc-card.is-active { transform: none !important; opacity: 1 !important; filter: none !important; }
  .cc-card__img { transform: none !important; }
  .cc-viewport { scroll-behavior: auto !important; }
}

/* ---- Subpáginas (casos.html, caso-enza.html): fondo claro ---- */
.subpage { background: var(--foam); }
.subpage main { padding-top: 120px; }
.casos-page__head { text-align: center; margin-bottom: clamp(36px, 6vw, 72px); }
.casos-page__title { font: 800 clamp(40px, 7vw, 92px)/0.98 var(--font); letter-spacing: -0.03em; color: var(--deep); }
.casos-page__sub { margin-top: 16px; color: var(--slate); font-size: clamp(16px, 1.5vw, 20px); }
.caso-card__media { display: block; aspect-ratio: 16 / 10; overflow: hidden; background: var(--deep); }
.caso-card__media img { width: 100%; height: 100%; object-fit: cover; display: block;
  transition: transform .5s cubic-bezier(.22,1,.36,1); }
.caso-card__media--ph { display: grid; place-content: center; background: linear-gradient(135deg, var(--deep), var(--ink)); }
.caso-card__body { padding: clamp(22px, 2.2vw, 34px); display: flex; flex-direction: column; flex: 1; }
.caso-card__sector { font: 700 12px/1 var(--font); letter-spacing: .16em; text-transform: uppercase; color: var(--signal); margin-bottom: 12px; }
.caso-card__name { font: 800 clamp(24px, 2.4vw, 34px)/1.05 var(--font); letter-spacing: -0.02em; color: var(--deep); }
.caso-card__summary { margin: 14px 0 18px; color: var(--slate); font-size: 16px; line-height: 1.55; }
.caso-card__bullets { list-style: none; display: flex; flex-direction: column; gap: 9px; margin-bottom: 24px; }
.caso-card__bullets li { position: relative; padding-left: 20px; color: var(--ink); font-size: 15px; }
.caso-card__bullets li::before { content: ""; position: absolute; left: 0; top: .45em; width: 7px; height: 7px; border-radius: 2px; background: var(--sun); }
@media (max-width: 900px) { }

/* Caso individual (caso-enza.html) */
.caso-hero { max-width: 1240px; margin: 0 auto; padding: clamp(10px, 3vh, 40px) var(--pad-x) clamp(40px, 6vh, 80px);
  display: grid; grid-template-columns: 1fr 1.05fr; gap: clamp(32px, 5vw, 72px); align-items: center; }
.caso-hero__eyebrow { font: 700 13px/1 var(--font); letter-spacing: .18em; text-transform: uppercase; color: var(--signal); margin-bottom: 20px; }
.caso-hero__name { font: 800 clamp(56px, 10vw, 150px)/0.92 var(--font); letter-spacing: -0.04em; color: var(--deep); }
.caso-hero__sub { margin: 22px 0 34px; color: var(--slate); font-size: clamp(17px, 1.6vw, 22px); line-height: 1.5; max-width: 46ch; }
.caso-hero__media { border-radius: 26px; overflow: hidden; aspect-ratio: 16 / 10; background: var(--deep); box-shadow: 0 40px 80px -40px rgba(10,37,64,.5); }
.caso-hero__media img { width: 100%; height: 100%; object-fit: cover; display: block; }
.caso-body { max-width: 900px; margin: 0 auto; padding: clamp(20px, 4vh, 50px) var(--pad-x);
  display: flex; flex-direction: column; gap: clamp(28px, 4vh, 56px); }
.caso-block { border-top: 1px solid var(--border); padding-top: clamp(20px, 3vh, 36px); }
.caso-block h2 { font: 800 clamp(24px, 3vw, 40px)/1.05 var(--font); letter-spacing: -0.02em; color: var(--deep); margin-bottom: 14px; }
.caso-block p { color: var(--slate); font-size: clamp(16px, 1.4vw, 19px); line-height: 1.65; }
.caso-cta { text-align: center; padding: clamp(50px, 9vh, 120px) var(--pad-x); }
.caso-cta h2 { font: 800 clamp(28px, 4vw, 56px)/1.05 var(--font); letter-spacing: -0.02em; color: var(--deep); margin-bottom: 26px; }
@media (max-width: 900px) {
  .caso-hero { grid-template-columns: 1fr; gap: clamp(24px, 5vw, 40px); }
  .caso-hero__media { order: -1; }
}

/* ------------------------------------------------------------
   Páginas internas (servicios, precios, blog, nosotros,
   contacto): cabecera simple + cuerpo con placeholder. Usa los
   mismos tokens y tipografía; nada de copy inventado.
   ------------------------------------------------------------ */
.page-hero { max-width: 1240px; margin: 0 auto; padding: clamp(20px, 5vh, 60px) var(--pad-x) clamp(24px, 3vh, 40px); }
.page-hero__eyebrow { font: 700 13px/1 var(--font); letter-spacing: .18em; text-transform: uppercase; color: var(--signal); margin-bottom: 18px; }
.page-hero__title { font: 800 clamp(44px, 8vw, 110px)/0.95 var(--font); letter-spacing: -0.03em; color: var(--deep); }
.page-hero__sub { margin-top: 18px; color: var(--slate); font-size: clamp(16px, 1.6vw, 21px); line-height: 1.5; max-width: 52ch; }
.page-cta { display: flex; justify-content: center; padding: 0 var(--pad-x) clamp(60px, 10vh, 120px); }

/* ------------------------------------------------------------
   Parrilla de servicios (servicios.html): 3 bloques, 3 tarjetas
   por fila en desktop. Tarjeta = foto (tercio superior) + cuerpo
   (dos tercios: título + texto). Ratio 1:2 exacto con flex-basis 0.
   Alturas iguales por fila (grid stretch). Solo se anima
   transform / box-shadow / border-color. Mismos tokens del sitio.
   ------------------------------------------------------------ */
.serv-page { max-width: 1240px; margin: 0 auto;
  padding: clamp(8px, 2vh, 24px) var(--pad-x) clamp(70px, 11vh, 150px);
  display: flex; flex-direction: column; gap: clamp(44px, 6vh, 82px); }
.serv-block__title { font: 800 clamp(26px, 3.4vw, 44px)/1.02 var(--font);
  letter-spacing: -0.02em; color: var(--deep); margin-bottom: clamp(20px, 2.4vw, 32px); }
.serv-grid { display: grid; grid-template-columns: repeat(3, 1fr);
  gap: clamp(18px, 2vw, 30px); align-items: stretch; }
/* Foco de teclado: outline --deep (alto contraste ~14:1, WCAG 1.4.11) */
.serv-card:focus-visible { outline: 3px solid var(--deep); outline-offset: 3px; }

/* Foto: tercio superior (fila 1fr) */
.serv-card__media { position: relative; min-height: 0;
  overflow: hidden; background: var(--foam); }
.serv-card__media img { position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; display: block;
  transition: transform .5s cubic-bezier(.22,1,.36,1); }
.serv-card__ph { position: absolute; inset: 0; display: grid; place-content: center;
  background: var(--foam); color: var(--slate);
  font: 700 12px/1 var(--font); letter-spacing: .18em; opacity: .5; }

/* Cuerpo: dos tercios inferiores (fila 2fr) */
.serv-card__body { min-height: 0; padding: clamp(20px, 2vw, 28px);
  display: flex; flex-direction: column; }
.serv-card__title { font: 800 clamp(19px, 1.5vw, 23px)/1.15 var(--font);
  letter-spacing: -0.01em; color: var(--deep); }
.serv-card__text { margin-top: 10px; color: var(--slate); font-size: 15px; line-height: 1.55;
  display: -webkit-box; -webkit-line-clamp: 4; -webkit-box-orient: vertical; overflow: hidden; }
.serv-card__arrow { margin-top: auto; align-self: flex-start; font-size: 20px;
  color: var(--signal); transition: transform .25s cubic-bezier(.22,1,.36,1); }

/* Responsive: tablet 2 por fila, móvil 1 */
@media (max-width: 900px) { .serv-grid { grid-template-columns: repeat(2, 1fr); } }
@media (max-width: 620px) {
  .serv-grid { grid-template-columns: 1fr; max-width: 440px; margin-inline: auto; }
}
@media (prefers-reduced-motion: reduce) {
  .serv-card__media img, .serv-card__arrow { transition: none; }
}

/* ------------------------------------------------------------
   Página de detalle de servicio (servicios/*.html, en subcarpeta).
   Reutiliza navbar/footer/tokens del sitio; layout propio scopeado
   a .sdetail. Solo variables de paleta, tipografía var(--font).
   ------------------------------------------------------------ */
.sdetail { max-width: 1100px; margin: 0 auto;
  padding: clamp(8px, 2vh, 20px) var(--pad-x) clamp(60px, 9vh, 110px); }

/* Botón "volver" sin contorno (estilo texto/link) */
.sdetail__back { display: inline-flex; align-items: center; gap: 8px;
  margin-bottom: clamp(22px, 4vh, 40px);
  font: 700 15px/1 var(--font); color: var(--deep); text-decoration: none;
  background: none; border: 0; cursor: pointer; transition: color .2s ease; }
.sdetail__back .arrow { transition: transform .25s cubic-bezier(.22,1,.36,1); }
.sdetail__back:hover { color: var(--signal); }
.sdetail__back:hover .arrow { transform: translateX(-4px); }
.sdetail__back:focus-visible { outline: 3px solid var(--deep); outline-offset: 3px; border-radius: 6px; }

/* Hero: título + imagen (misma foto que la tarjeta) */
.sdetail__hero { display: grid; grid-template-columns: 1fr 1fr; gap: clamp(28px, 4vw, 60px);
  align-items: center; margin-bottom: clamp(40px, 7vh, 84px); }
.sdetail__eyebrow { font: 700 13px/1 var(--font); letter-spacing: .18em; text-transform: uppercase;
  color: var(--signal); margin-bottom: 18px; }
.sdetail__title { font: 800 clamp(34px, 5vw, 64px)/1.02 var(--font); letter-spacing: -.02em; color: var(--deep); }
.sdetail__sub { margin-top: 20px; color: var(--slate); font-size: clamp(16px, 1.5vw, 20px);
  line-height: 1.55; max-width: 46ch; }
.sdetail__media { position: relative; aspect-ratio: 16 / 11; border-radius: var(--radius-lg);
  overflow: hidden; background: var(--foam); border: 1px solid var(--border);
  box-shadow: 0 30px 60px -40px rgba(10,37,64,.4); }
.sdetail__media img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; display: block; }
.sdetail__ph { position: absolute; inset: 0; display: grid; place-content: center; background: var(--foam);
  color: var(--slate); font: 700 13px/1 var(--font); letter-spacing: .18em; opacity: .5; }

/* Cuerpo: secciones con placeholders marcados */
.sdetail__body { display: flex; flex-direction: column; gap: clamp(22px, 4vh, 40px); max-width: 820px; }
.sdetail__sec { border-top: 1px solid var(--border); padding-top: clamp(18px, 3vh, 30px); }
.sdetail__sec h2 { font: 800 clamp(20px, 2.4vw, 30px)/1.1 var(--font); letter-spacing: -.01em;
  color: var(--deep); margin-bottom: 12px; }
.sdetail__sec p { color: var(--slate); font-size: clamp(15px, 1.4vw, 18px); line-height: 1.65; }

@media (max-width: 860px) {
  .sdetail__hero { grid-template-columns: 1fr; gap: clamp(22px, 4vw, 34px); }
  .sdetail__media { order: -1; }
}
@media (prefers-reduced-motion: reduce) {
  .sdetail__back .arrow { transition: none; }
  .sdetail__back:hover .arrow { transform: none; }
}

/* Filtro de categorías (burbujas). En móvil hacen wrap a varias líneas. */
.blog-filter { display: flex; flex-wrap: wrap; gap: 10px; margin-bottom: clamp(26px, 4vw, 44px); }
.blog-pill { font: 600 14px/1 var(--font); color: var(--deep); background: transparent;
  border: 1px solid var(--border); border-radius: var(--radius-pill);
  padding: 10px 18px; cursor: pointer;
  transition: background .2s ease, color .2s ease, border-color .2s ease,
              transform .2s cubic-bezier(.22,1,.36,1); }
.blog-pill:hover { border-color: var(--signal); transform: translateY(-1px); }
.blog-pill__count { opacity: .6; font-weight: 500; margin-left: 2px; }
.blog-pill.is-active { background: var(--sun); border-color: var(--sun); color: var(--deep); }
.blog-pill.is-active .blog-pill__count { opacity: .75; }
.blog-pill:focus-visible { outline: 3px solid var(--deep); outline-offset: 3px; }

/* Parrilla 3 por fila */
.blog-grid { display: grid; grid-template-columns: repeat(3, 1fr);
  gap: clamp(20px, 2.4vw, 32px); align-items: stretch; }

/* Tarjeta de artículo — estilo KOTA blog: SIN caja (fondo transparente,
   sin borde ni sombra); solo imagen redondeada + categoría + título.
   El hover vive en la imagen (zoom) y el título (color), no en la caja. */
.blog-card { position: relative; min-width: 0; display: flex; flex-direction: column;
  text-decoration: none; cursor: pointer;
  background: transparent; border: 0; border-radius: 0; overflow: visible;
  box-shadow: none;
  transition: opacity .25s ease, transform .25s ease; }
.blog-card:focus-visible { outline: 3px solid var(--deep); outline-offset: 3px; }
.blog-card[hidden] { display: none; }
.blog-card.is-out { opacity: 0; transform: scale(.96); pointer-events: none; }

/* Imagen arriba con placeholder [FOTO] */
.blog-card__media { position: relative; aspect-ratio: 16 / 10; overflow: hidden;
  background: var(--foam); border-radius: 14px; }
.blog-card__media img { position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; display: block; transition: transform .5s cubic-bezier(.22,1,.36,1); }
.blog-card:hover .blog-card__media img { transform: scale(1.05); }
.blog-card:hover .blog-card__title { color: var(--signal-700); }
.blog-card__ph { position: absolute; inset: 0; display: grid; place-content: center;
  background: var(--foam); color: var(--slate); font: 700 12px/1 var(--font);
  letter-spacing: .18em; opacity: .5; }

/* Cuerpo: categoría + título + meta (sobre el fondo de la página) */
.blog-card__body { display: flex; flex-direction: column; flex: 1; padding: 16px 2px 0; }
.blog-card__cat { font: 700 11px/1 var(--font); letter-spacing: .16em; text-transform: uppercase;
  color: var(--signal); margin-bottom: 10px; }
.blog-card__title { font: 800 clamp(18px, 1.5vw, 22px)/1.2 var(--font); letter-spacing: -0.01em; color: var(--deep); transition: color .25s; }
/* Extracto opcional de la tarjeta (2-3 líneas de la entradilla, recortado). */
.blog-card__excerpt { margin-top: 10px; color: var(--slate); font: 400 14px/1.5 var(--font);
  display: -webkit-box; -webkit-line-clamp: 3; line-clamp: 3; -webkit-box-orient: vertical; overflow: hidden; }
.blog-card__meta { margin-top: auto; padding-top: 14px; color: var(--slate); font-size: 13px; }

/* Cabecera editorial del blog (estilo KOTA: titular grande a la izquierda,
   sobre el mismo fondo de vídeo de la landing) */
/* Compacta: al entrar se ven el titular Y la imagen destacada entera */
.blog-hero { padding: clamp(16px, 3vh, 40px) var(--pad-x) clamp(18px, 3.5vh, 40px); }
.blog-hero__kicker {
  font-size: 13px; letter-spacing: 3px; font-weight: 700;
  color: var(--slate); text-transform: uppercase; margin-bottom: 18px;
}
.blog-hero__title {
  font-size: clamp(36px, 5vw, 78px); font-weight: 800; line-height: .98;
  letter-spacing: -.03em; color: var(--deep);
}
.blog-hero__title span { display: block; }

/* Artículo DESTACADO (estilo KOTA: imagen con arco arriba-derecha,
   etiquetas y titular grande debajo, sin caja) */
.blog-feat {
  display: block; max-width: 720px;
  margin: 0 0 clamp(44px, 7vh, 76px);
  text-decoration: none; color: inherit;
}
.blog-feat__media {
  display: block; overflow: hidden; aspect-ratio: 16 / 9;
  /* capada por el espacio que queda bajo el titular: la imagen entra
     ENTERA en el primer pantallazo (el recorte lo absorbe object-fit) */
  max-height: clamp(220px, calc(100vh - 440px), 42vh);
  max-height: clamp(220px, calc(100svh - 440px), 42vh);
  border-radius: 0 clamp(48px, 6vw, 90px) 0 0; background: var(--foam);
}
.blog-feat__media img { width: 100%; height: 100%; object-fit: cover; display: block;
  transition: transform .5s cubic-bezier(.22,1,.36,1); }
.blog-feat:hover .blog-feat__media img { transform: scale(1.04); }
.blog-feat__tags { display: flex; flex-wrap: wrap; gap: 16px; margin: 18px 0 10px; }
.blog-feat__tag { font: 700 12px/1 var(--font); letter-spacing: .16em;
  text-transform: uppercase; color: var(--signal); }
.blog-feat__tag--dest { color: var(--sun); }
.blog-feat__title {
  display: block; font: 800 clamp(24px, 2.8vw, 42px)/1.1 var(--font);
  letter-spacing: -.02em; color: var(--deep); transition: color .25s;
}
.blog-feat:hover .blog-feat__title { color: var(--signal-700); }
.blog-feat__meta { display: block; margin-top: 12px; color: var(--slate); font-size: 13px; }

/* Estado vacío (categorías a 0) */
.blog-empty { color: var(--slate); text-align: center; font-size: clamp(15px, 1.4vw, 18px);
  padding: clamp(30px, 5vw, 64px) 0; }
.blog-empty[hidden] { display: none; }

/* Tarjeta "Próximamente" del blog: mismo lenguaje que la del carrusel de
   casos (onda del logo flotando + puntos "escribiendo…"), adaptada a la
   parrilla. NO lleva .blog-card ni data-category: queda fuera del filtro
   (siempre visible) y no cuenta en los contadores. */
.blog-soon {
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  gap: 14px; text-align: center; padding: 34px 24px; min-height: 320px;
  border: 2px dashed var(--border); border-radius: 14px;
  /* translúcida: deja intuir el fondo de vídeo de la página */
  background:
    radial-gradient(340px 240px at 85% 10%, rgba(31, 182, 193, .10), transparent 70%),
    radial-gradient(300px 220px at 12% 90%, rgba(255, 163, 31, .10), transparent 70%),
    color-mix(in srgb, var(--surface) 62%, transparent);
}
.blog-soon__mark {
  width: clamp(60px, 6vw, 88px); height: auto; opacity: .85;
  animation: ccSoonFloat 4.5s ease-in-out infinite;
}
.blog-soon__name { font: 800 clamp(22px, 2vw, 30px)/1.1 var(--font); letter-spacing: -.01em; color: var(--deep); }
.blog-soon__text { color: var(--slate); font: 400 14px/1.55 var(--font); max-width: 30ch; }
.blog-soon__dots { display: flex; gap: 8px; }
.blog-soon__dots i {
  width: 8px; height: 8px; border-radius: 50%; background: var(--sun);
  animation: ccSoonPulse 1.6s ease-in-out infinite;
}
.blog-soon__dots i:nth-child(2) { animation-delay: .25s; background: var(--signal); }
.blog-soon__dots i:nth-child(3) { animation-delay: .5s; }
@media (prefers-reduced-motion: reduce) {
  .blog-soon__mark, .blog-soon__dots i { animation: none; }
}

/* Responsive: tablet 2 por fila, móvil 1 */
@media (max-width: 900px) { .blog-grid { grid-template-columns: repeat(2, 1fr); } }
@media (max-width: 600px) {
  .blog-grid { grid-template-columns: 1fr; max-width: 440px; margin-inline: auto; }
}
@media (prefers-reduced-motion: reduce) {
  .blog-card, .blog-card__media img, .blog-pill { transition: none; }
  .blog-card:hover { transform: none; }
  .blog-card:hover .blog-card__media img { transform: none; }
}

/* ============================================================
   21. DIAGRAMA DE FLUJO (tarjeta "Automatización operativa").
   Sustituye a la media DENTRO de .stack__media, heredando su
   tamaño/forma (no se toca). HTML+CSS+SVG puro, sin librerías.
   Etiquetas en Manrope (var(--font), la que ya carga el sitio).
   Solo se anima transform/opacity/stroke-dashoffset (el bloque
   de animación se añade aparte, tras validar el estático).
   ============================================================ */
.stack__media--flow {
  position: relative;
  background: transparent;   /* el dot-grid ahora es continuo desde .stack__card (sin costura) */
}
.flow { position: absolute; inset: 0; }

/* Conectores (curvas bézier estilo n8n). preserveAspectRatio=none
   estira el viewBox 0-100 al contenedor; non-scaling-stroke mantiene
   el grosor en 2px pase lo que pase con la forma. */
.flow__wires { position: absolute; inset: 0; width: 100%; height: 100%; z-index: 1; overflow: visible; }
.flow__wire { fill: none; stroke: var(--signal); stroke-width: 2; stroke-linecap: round; }

/* Nodos: posición relativa al contenedor (%), no px fijos */
.flow__node {
  position: absolute; left: var(--x); top: var(--y);
  z-index: 2; display: flex; flex-direction: column; align-items: center; gap: 11px;
  width: clamp(84px, 20%, 150px);
  /* Estado inicial de la animación de entrada (.is-in lo revela) */
  opacity: 0; transform: translate(-50%, calc(-50% + 14px));
  transition: opacity .55s cubic-bezier(.22,1,.36,1), transform .55s cubic-bezier(.22,1,.36,1);
  transition-delay: calc(var(--i, 0) * .12s);
}
.is-in .flow__node { opacity: 1; transform: translate(-50%, -50%); }
.flow__chip {
  width: clamp(62px, 6.6vw, 100px); aspect-ratio: 1; border-radius: 15px;
  background: var(--surface); border: 1px solid var(--border);
  box-shadow: 0 10px 24px -12px rgba(10,37,64,.30);
  display: grid; place-items: center; color: var(--deep);   /* place-items (no place-content): que el width:% del svg se resuelva contra la caja */
}
.flow__chip svg { width: 62%; height: 62%; display: block; }   /* con place-items, la tinta visible queda ~50% de la caja */
.flow__chip svg path, .flow__chip svg rect, .flow__chip svg circle, .flow__chip svg line, .flow__chip svg polyline {
  fill: none; stroke: currentColor; stroke-width: 2; stroke-linecap: round; stroke-linejoin: round;
}
.flow__chip svg text { fill: currentColor; stroke: none; font: 800 8px/1 var(--font); }
.flow__node--ia   .flow__chip { color: var(--signal); border-color: rgba(31,182,193,.45); box-shadow: 0 12px 26px -12px rgba(31,182,193,.4); }
.flow__node--bell .flow__chip { color: var(--sun);    border-color: rgba(255,163,31,.45); box-shadow: 0 12px 26px -12px rgba(255,163,31,.4); }
.flow__label {
  font: 600 clamp(10px, 1vw, 12.5px)/1.25 var(--font);
  color: var(--deep); text-align: center; max-width: 100%;
}

/* Tablet: chips algo menores, siguen en fila */
@media (max-width: 900px) {
  .flow__chip { width: clamp(50px, 6.4vw, 76px); }
  .flow__label { font-size: clamp(9px, 1.6vw, 12px); }
}
/* Móvil: el flujo pasa a VERTICAL en el mismo hueco. Nodos en columna
   central (top = --my); el JS recalcula las conexiones como verticales
   (borde inferior → borde superior). */
@media (max-width: 768px) {
  /* Solo la tarjeta del flujo: más alto para el flujo vertical + franja
     inferior reservada al botón (no pisa el nodo 5). No afecta a las otras 2. */
  .stack__media--flow { min-height: 600px; }
  .flow { bottom: 96px; }
  .flow__run { bottom: 16px; }
  .flow__node { left: 50% !important; top: var(--my); width: clamp(130px, 66%, 280px); }
  .flow__chip { width: clamp(44px, 11vw, 62px); }
  .flow__label { font-size: clamp(9px, 2.6vw, 12px); }
}

/* ---- Animación de entrada (IntersectionObserver añade .is-in) ---- */
/* Wires: se "dibujan" con stroke-dashoffset (pathLength=1). */
.flow__wire { stroke-dasharray: 1; stroke-dashoffset: 1; }
.is-in .flow__wire {
  stroke-dashoffset: 0;
  transition: stroke-dashoffset .6s cubic-bezier(.22,1,.36,1);
  transition-delay: calc(var(--wi, 0) * .12s + .2s);
}
/* Pulso de luz --sun recorriendo cada wire en bucle (solo stroke-dashoffset) */
.flow__pulse {
  fill: none; stroke: var(--sun); stroke-width: 2.6; stroke-linecap: round;
  stroke-dasharray: 0.14 0.86; stroke-dashoffset: 1; opacity: 0;
}
.is-in .flow__pulse {
  opacity: .9; animation: flowPulse 1.2s linear infinite;   /* ~1s por nodo (antes 2.6s) */
  animation-delay: calc(.9s + var(--wi, 0) * .16s);
}
@keyframes flowPulse { from { stroke-dashoffset: 1; } to { stroke-dashoffset: 0; } }

/* ---- Simulación "Ejecutar" el workflow (JS bloque 16b, WAAPI) ---- */
/* Relleno naranja de las líneas conectoras (superpuesto a la base --signal).
   dasharray/dashoffset los fija el JS con la longitud REAL (getTotalLength). */
.flow__fill { fill: none; stroke: var(--sun); stroke-width: 2.6; stroke-linecap: round; }
/* Contornos naranja de cada nodo: overlay POR ENCIMA de las cajas (z-index 3).
   Son <path> (perímetro redondeado) que arrancan en el punto de conexión; el
   dibujo se controla por JS con longitud real → oculto (offset=L) hasta su turno. */
.flow__rings { position: absolute; inset: 0; width: 100%; height: 100%; z-index: 3; overflow: visible; pointer-events: none; }
.flow__ring { fill: none; stroke: var(--sun); stroke-width: 3; stroke-linecap: round; stroke-linejoin: round; }
/* Durante la ejecución, se pausa el pulso ambiental para que no compita */
.flow--running .flow__pulse { opacity: 0 !important; animation: none !important; }

/* Botón "Ejecutar": outline discreto (el naranja se reserva al flujo) */
.flow__run {
  position: absolute; left: 50%; bottom: 4%; transform: translateX(-50%); z-index: 4;
  display: inline-flex; align-items: center; gap: 8px;
  padding: 9px 16px; border-radius: var(--radius-pill);
  background: var(--surface); color: var(--deep); border: 1.5px solid var(--deep);
  font: 600 13px/1 var(--font); cursor: pointer;
  box-shadow: 0 8px 20px -10px rgba(10,37,64,.30);
  transition: transform .25s cubic-bezier(.22,1,.36,1), box-shadow .25s ease, border-color .25s ease;
}
.flow__run:hover { transform: translateX(-50%) translateY(-2px); box-shadow: 0 13px 26px -10px rgba(10,37,64,.4); border-color: var(--signal); }
.flow__run:disabled { cursor: default; }
.flow__run:disabled:hover { transform: translateX(-50%); box-shadow: 0 8px 20px -10px rgba(10,37,64,.30); border-color: var(--deep); }
.flow__run-ic { width: 14px; height: 14px; fill: currentColor; flex: none; }
.flow__run .ic-pause { display: none; }
.flow__run.is-running .ic-play { display: none; }
.flow__run.is-running .ic-pause { display: block; }

/* Medición: neutraliza el translateY de entrada para leer la posición
   asentada de los chips al calcular los conectores (JS, bloque 16). */
.flow--measure .flow__node { transform: translate(-50%, -50%) !important; transition: none !important; }

/* Sin movimiento: todo estático, sin dibujo ni pulso */
@media (prefers-reduced-motion: reduce) {
  .flow__node { opacity: 1 !important; transform: translate(-50%, -50%) !important; transition: none !important; }
  .flow__wire { stroke-dashoffset: 0 !important; transition: none !important; }
  .flow__pulse { display: none !important; }
}

/* ============================================================
   22. ESCENA "PRESENCIA DIGITAL" (tarjeta 2 de servicios).
   Sustituye a la media DENTRO de .stack__media (hereda su
   tamaño/forma). SVG+CSS puro. Iconos inline desde
   assets/img/social/ para poder colorearlos con la paleta.
   De abajo a arriba: local + "TU NEGOCIO" · ondas wifi ·
   iconos flotando en burbujas. (Animación: bloque 23.)
   ============================================================ */
.pd-scene { position: relative; container-type: size; display: grid; place-items: center; }   /* hereda radios/overflow/min-height de .stack__media */
/* Escenario de proporción fija: se escala como una unidad y se centra en la
   media, así las posiciones en % valen igual en desktop/tablet/móvil. */
.pd-stage { position: relative; width: min(100%, 100cqh); aspect-ratio: 1 / 1; }

/* --- Local + etiqueta (abajo, centrado) --- */
.pd-shop { position: absolute; left: 50%; bottom: 6%; transform: translateX(-50%); width: 43%; text-align: center; z-index: 1; }
.pd-shop__svg { width: 100%; height: auto; display: block; stroke-linejoin: round; }
.pd-shop__label { display: block; margin-top: 8%; font: 800 clamp(9px, 1.15vw, 12px)/1 var(--font);
  letter-spacing: .2em; color: var(--deep); }
.pd-ln     { stroke: var(--deep); stroke-width: 2; stroke-linecap: round; }
.pd-ground { stroke: var(--deep); stroke-width: 2.6; stroke-linecap: round; }
.pd-fill   { fill: var(--surface); stroke: var(--deep); stroke-width: 2; }
.pd-door   { fill: var(--foam); stroke: var(--deep); stroke-width: 2; }
.pd-win    { fill: var(--signal); fill-opacity: .18; stroke: var(--deep); stroke-width: 2; }
.pd-aw     { stroke: var(--deep); stroke-width: 1.5; }
.pd-aw--a  { fill: var(--sun); }
.pd-aw--b  { fill: var(--surface); }
.pd-acc-sig { fill: var(--signal); }

/* --- Ondas wifi (suben del local) --- */
.pd-waves { position: absolute; left: 50%; bottom: 42%; transform: translateX(-50%); width: 52%; height: auto; z-index: 1;
  animation: pdBreathe 4s ease-in-out infinite; }   /* onda de fondo (z1) con respiración suave de opacidad */
.pd-wave  { stroke: var(--signal); stroke-width: 2; stroke-linecap: round; }
@keyframes pdBreathe { 0%, 100% { opacity: 1; } 50% { opacity: .72; } }

/* --- Iconos flotantes en burbujas --- */
/* Ancla: posición + centrado (translate) + proximidad (transform, vía JS).
   Van en propiedades distintas para que compongan sin pisarse. */
.pd-icon { position: absolute; left: var(--x); top: var(--y); z-index: 3;
  translate: -50% -50%;
  transform: translate(var(--px, 0px), var(--py, 0px));   /* repulsión (JS) — se compone con la flotación */
  transition: transform .5s cubic-bezier(.22, 1, .36, 1);   /* retorno lento y amortiguado (muelle suave), y salida "perezosa" */
  width: clamp(56px, 7.8vw, 86px); aspect-ratio: 26 / 18; color: var(--deep); }
/* Nube (contenedor): silueta de nube en SVG (fill --surface, borde suave
   --border) como background; la sombra la da filter:drop-shadow para que siga
   la forma de la nube (no un rectángulo). SOLO flotación en bucle (translate
   animado); la repulsión por proximidad vive en el ancla .pd-icon (transform). */
.pd-box { width: 100%; height: 100%; display: grid; place-items: center;
  background: center / 100% 100% no-repeat
    url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' viewBox='-1 3 26 18'><path fill='%23ffffff' stroke='%23dde4eb' stroke-width='.5' d='M19.35 10.04A7.49 7.49 0 0 0 12 4C9.11 4 6.6 5.64 5.35 8.04A5.994 5.994 0 0 0 0 14c0 3.31 2.69 6 6 6h13c2.76 0 5-2.24 5-5 0-2.64-2.05-4.78-4.65-4.96z'/></svg>");
  filter: drop-shadow(0 4px 7px rgba(10,37,64,.20)) drop-shadow(0 1px 1px rgba(10,37,64,.10));
  animation: pdFloat var(--fd, 4.6s) ease-in-out var(--dl, 0s) infinite;
  will-change: translate; }
/* Icono centrado en el cuerpo de la nube (se escala por altura para no
   deformarse y se baja un pelín para caer en la masa de la nube). */
.pd-box .pd-g { height: 44%; width: auto; display: block; transform: translateY(4%); }
.pd-g--fill path  { fill: currentColor; }
.pd-g--stroke     { fill: none; stroke: currentColor; stroke-width: 1.9; stroke-linecap: round; stroke-linejoin: round; }
.pd-meg-sound     { stroke: var(--sun); }
@keyframes pdFloat { 0%, 100% { translate: 0 0; } 50% { translate: 0 calc(-1 * var(--fa, 6px)); } }

/* Sin movimiento: sin flotación ni repulsión; escena estática. */
@media (prefers-reduced-motion: reduce) {
  .pd-box { animation: none; }
  .pd-icon { transition: none; }
  .pd-waves { animation: none; }
}

/* ============================================================
   24. ARTÍCULO DEL BLOG — cabecera editorial (PATRÓN para todos los artículos)
   Disposición (referencia KOTA, adaptada a DuoWave): TODO alineado a la
   izquierda compartiendo el MISMO borde → pills (mismo estilo que el filtro
   del blog, .blog-pill) → título grande → fecha "hace X" → imagen destacada →
   cuerpo. Pills, título, fecha, imagen y cuerpo comparten el MISMO ancho (el de
   la columna .article) y el mismo borde izquierdo. Solo tokens de
   la paleta; medidas en em. Sin animaciones propias (nada que desactivar en
   reduced-motion; los hovers los heredan .btn-cta y .blog-pill, ya cubiertos).

   PATRÓN: un solo <article class="article"> con .article__head (pills+título+
   meta), .article__hero (portada) y .article__body (cuerpo). Un artículo nuevo
   solo cambia el contenido: pills, título, fecha, imágenes y texto.
   ============================================================ */

/* Columna de la página: centrada en pantalla; los hijos se alinean a la
   izquierda (sin auto-márgenes) para compartir el mismo borde izquierdo. */
.article { max-width: 56em; margin: 0 auto;
  padding: clamp(1.25em, 5vh, 3.25em) clamp(1.25em, 5vw, 2.5em) clamp(4.5em, 11vh, 9em); }

/* Cabecera: pills + título + meta. Llena el ancho de la columna (= imagen)
   y se alinea a la izquierda, igual que la portada y el cuerpo. */
.article__head { max-width: none; }
/* Pills de categoría: reutilizan .blog-pill (estilo del filtro del blog). */
.article__pills { display: flex; flex-wrap: wrap; gap: 0.625em; margin: 0 0 1.25em; }
.article__title { font: 800 clamp(1.9em, 4.6vw, 3.25em)/1.08 var(--font); letter-spacing: -0.02em; color: var(--deep); margin: 0; }
.article__meta { margin: 1.15em 0 0; color: var(--slate); font: 500 0.875em/1.5 var(--font); }
.article__meta time { color: var(--slate); }
.article__dot { margin: 0 0.2em; opacity: .55; }

/* Imagen destacada: todo el ancho de la columna (más ancha que el texto) →
   presencia. Mismo borde izquierdo que las pills y el título. */
.article__hero { margin: clamp(1.6em, 4vh, 2.75em) 0 0; }
.article__hero img { display: block; width: 100%; height: auto; border-radius: var(--radius-lg);
  background: var(--foam); box-shadow: 0 1.5em 3.75em -1.875em rgba(10, 37, 64, .45); }

/* Cuerpo: MISMO ancho que la imagen destacada (llena la columna .article, que
   está capada a 62em ≈ 969px de contenido), alineado a la izquierda. Para que
   ese ancho no dé líneas incómodas, la fuente sube a ~21px en desktop → ~88
   caracteres por línea (parte alta del rango cómodo). Los párrafos y H2 son
   hijos directos de .article__body; las excepciones (lead, fuentes) aparte. */
.article__body { max-width: none; margin: clamp(1.75em, 4.5vh, 3em) 0 0; }
/* Texto justificado: ambos márgenes de la columna quedan alineados.
   hyphens evita ríos de espacios partiendo palabras largas (lang="es"). */
.article__body > p {
  font: 400 clamp(1.0625em, 2vw, 1.25em)/1.75 var(--font); color: var(--ink);
  margin: 0 0 1.15em; text-align: justify; hyphens: auto;
}
.article__body > p.article__lead { font: 500 clamp(1.2em, 2.1vw, 1.4375em)/1.55 var(--font); color: var(--ink); margin: 0 0 0.9em; }
.article__body > h2 { font: 800 clamp(1.45em, 3vw, 1.9em)/1.2 var(--font); letter-spacing: -0.015em; color: var(--deep);
  margin: clamp(2.2em, 5vh, 3.4em) 0 0.6em; }
.article__body strong { font-weight: 700; color: var(--deep); }

/* Imagen interior: márgenes que dan respiro (no pegada al texto). */
.article__figure { margin: clamp(1.9em, 5vh, 3em) 0; }
.article__figure img { display: block; width: 100%; height: auto; border-radius: var(--radius-lg); background: var(--foam); }

/* Huecos de imagen de artículos aún sin foto (mismo lenguaje visual que
   los huecos de Servicios: borde punteado + etiqueta "TU IMAGEN"). */
.article__hero--ph, .article__figure--ph {
  aspect-ratio: 16 / 9; border: 2px dashed var(--border);
  border-radius: var(--radius-lg);
  background: linear-gradient(135deg, var(--foam), var(--border));
  display: grid; place-content: center; text-align: center;
}

/* CTA de cierre (reutiliza .btn-cta dorado; mismo destino que el resto). */
.article__body .btn-cta { margin: 0.75em 0 0.25em; }

/* Fuentes: diferenciadas, más pequeñas, sobre fondo --foam para no competir. */
.article__sources { margin-top: clamp(2.9em, 7vh, 4.5em); padding: clamp(1.4em, 3vw, 2em);
  background: var(--foam); border: 1px solid var(--border); border-radius: var(--radius-lg); }
.article__sources-title { font: 800 0.9375em/1.2 var(--font); letter-spacing: .04em; text-transform: uppercase; color: var(--deep); margin: 0 0 0.9em; }
.article__sources ul { list-style: none; margin: 0; padding: 0; display: grid; gap: 0.7em; }
.article__sources li { position: relative; padding-left: 1.15em; font: 400 0.84375em/1.55 var(--font); color: var(--slate); }
.article__sources li::before { content: ""; position: absolute; left: 0; top: 0.55em; width: 0.375em; height: 0.375em; border-radius: 50%; background: var(--signal); }
.article__sources strong { color: var(--deep); font-weight: 700; }

/* «Sigue leyendo»: los otros artículos al final de cada post (reutiliza
   las tarjetas sin caja .blog-card del listado del blog). */
.article__related { margin-top: clamp(2.9em, 7vh, 4.5em); }
.article__related-title { font: 800 clamp(1.3em, 2.4vw, 1.7em)/1.1 var(--font);
  letter-spacing: -.01em; color: var(--deep); margin: 0 0 1em; }
.article__related-grid { display: grid; grid-template-columns: 1fr 1fr;
  gap: clamp(16px, 2.5vw, 28px); }
@media (max-width: 700px) { .article__related-grid { grid-template-columns: 1fr; } }

/* «Volver al blog» repetido al final: misma clase .sdetail__back que arriba,
   solo se le añade separación superior respecto al bloque de fuentes (aplica
   únicamente a la instancia dentro del cuerpo, no a la de la cabecera). */
.article__body .sdetail__back { margin-top: clamp(2em, 5vh, 3.5em); }

@media (max-width: 900px) {
  .article__title { font-size: clamp(1.75em, 8vw, 2.5em); }
}

/* ============================================================
   Páginas de servicio (plantilla: servicios/chatbot-whatsapp.html)
   ============================================================ */

/* Pills como ENLACE a páginas de servicio: mismo look que .tags li (borde,
   radio, padding, tipografía) con acento teal en hover/focus. Solo .tags--nav
   (las pills decorativas del resto siguen igual). El <li> es solo contenedor. */
.tags--nav li { border: 0; padding: 0; }
.tags--nav a {
  display: inline-block; text-decoration: none; color: var(--ink);
  border: 1.2px solid var(--border); border-radius: var(--radius-pill);
  padding: 10px 20px; font-size: 15px; font-weight: 500;
  transition: border-color .2s ease, color .2s ease, background .2s ease;
}
.tags--nav a:hover { border-color: var(--signal); color: var(--signal-700); background: rgba(31,182,193,.06); }
.tags--nav a:focus-visible { outline: 3px solid var(--signal); outline-offset: 3px; border-radius: var(--radius-pill); }

/* Frase resumen bajo el h1 (subtítulo del servicio, dentro de .page-hero).
   Mayor que el body y menor que el h1; gris slate con peso ligero → se lee
   como subtítulo, no como un párrafo más. Clase reutilizable por otros
   servicios (chatbot-whatsapp.html no la usa todavía, y no debe). */
.servicio-resumen {
  margin: clamp(16px, 2.4vh, 26px) 0 0; max-width: 42ch;
  font: 500 clamp(19px, 2.2vw, 26px)/1.45 var(--font);
  letter-spacing: -0.01em; color: var(--slate);
}

/* Cuerpo de la página de servicio: columna de lectura cómoda (~46em). */
.service { max-width: 46em; margin: 0 auto;
  padding: clamp(1.4em, 3.5vh, 2.8em) var(--pad-x) clamp(4em, 10vh, 8em); }
.service > .sdetail__back { margin-bottom: clamp(1.4em, 3vh, 2.2em); }
.service section { margin: 0; }
.service h2 { font: 800 clamp(1.5em, 3vw, 2em)/1.2 var(--font); letter-spacing: -0.015em; color: var(--deep);
  margin: clamp(2.2em, 5vh, 3.4em) 0 0.6em; }
.service section:first-of-type h2 { margin-top: 0; }
.service p { font: 400 clamp(1.0625em, 1.4vw, 1.1875em)/1.75 var(--font); color: var(--ink); margin: 0 0 1.1em; }

/* Placeholder de imagen (mismo estilo [FOTO] del blog: caja foam + etiqueta). */
.service__figure { margin: clamp(1.6em, 4vh, 2.6em) 0; aspect-ratio: 16 / 10;
  background: var(--foam); border: 1px solid var(--border); border-radius: var(--radius-lg);
  display: grid; place-content: center; overflow: hidden; }
.service__ph-label { font: 600 13px/1.4 var(--font); letter-spacing: .04em; color: var(--slate);
  text-align: center; padding: 0 20px; }

/* Bloques de beneficio (titular en negrita + párrafo debajo). */
.service__benefit { margin: 0 0 1.6em; }
.service__benefit h3 { font: 800 clamp(1.1em, 1.8vw, 1.3em)/1.3 var(--font); color: var(--deep); margin: 0 0 0.3em; }
.service__benefit p { margin: 0; }

/* CTA de cierre. */
.service__cta { margin-top: clamp(2.2em, 5vh, 3.4em); }
.service__cta .btn-cta { text-decoration: none; }

/* ---------- Tarjeta "Próximamente" del carrusel de casos ----------
   Hueco reservado en visual: onda del logo flotando, puntos tipo
   "escribiendo…" en colores de marca y borde discontinuo. */
.cc-card--soon {
  display: flex; align-items: center; justify-content: center;
  border: 2px dashed var(--border);
  background: linear-gradient(180deg, var(--surface), var(--foam));
  box-shadow: none;
}
.cc-soon {
  display: flex; flex-direction: column; align-items: center;
  gap: 18px; padding: 30px; text-align: center;
}
.cc-soon__mark {
  width: clamp(72px, 8vw, 110px); height: auto; opacity: .85;
  animation: ccSoonFloat 4.5s ease-in-out infinite;
}
.cc-soon__name { font-size: clamp(26px, 2.4vw, 38px); color: var(--deep); }
.cc-soon__dots { display: flex; gap: 8px; }
.cc-soon__dots i {
  width: 8px; height: 8px; border-radius: 50%; background: var(--sun);
  animation: ccSoonPulse 1.6s ease-in-out infinite;
}
.cc-soon__dots i:nth-child(2) { animation-delay: .25s; background: var(--signal); }
.cc-soon__dots i:nth-child(3) { animation-delay: .5s; }
@keyframes ccSoonFloat { 0%,100%{transform:translateY(0)} 50%{transform:translateY(-9px)} }
@keyframes ccSoonPulse { 0%,100%{opacity:.35;transform:scale(.85)} 50%{opacity:1;transform:scale(1)} }
@media (prefers-reduced-motion: reduce) {
  .cc-soon__mark, .cc-soon__dots i { animation: none; }
}

/* ---------- Página SERVICIOS — rediseño por bloques numerados ----------
   Cabecera con kicker + titular grande + píldoras-ancla; 3 bloques con
   filas de servicio (hover: título teal + flecha que avanza); banda oscura
   del analizador; proceso en 4 pasos; CTA final. */
/* (antes heredaba el relleno de .page-hero, ya retirada) */
.sv-hero { padding: clamp(20px, 4vh, 44px) var(--pad-x) clamp(30px, 5vh, 60px); }
.sv-kicker {
  font-size: 13px; letter-spacing: 3px; font-weight: 700;
  color: var(--slate); text-transform: uppercase; margin-bottom: 18px;
}
.sv-title {
  /* 6vw/100px: la línea más larga ("puede hacer solo.") cabe entera
     en su columna sin partirse */
  font-size: clamp(40px, 6vw, 100px); font-weight: 800; line-height: .95;
  letter-spacing: -.03em; color: var(--deep); margin: 0 0 22px;
}
.sv-sub { max-width: 620px; font-size: clamp(17px, 1.5vw, 22px); color: var(--ink); margin-bottom: 30px; }
.sv-pills { display: flex; flex-wrap: wrap; gap: 12px; }
.sv-pills a {
  border: 1.4px solid var(--deep); color: var(--deep); border-radius: 999px;
  padding: 12px 22px; font-weight: 600; font-size: 15px; text-decoration: none;
  transition: background .25s, color .25s;
}
.sv-pills a:hover { background: var(--deep); color: var(--foam); }

/* Tamaños compactos: cada bloque debe caber entero en un viewport
   (título + 3 servicios + imagen, sin scroll), como en KOTA. */
/* Separación generosa y UNIFORME entre bloques de servicio (los tres
   huecos iguales; cada bloque sigue cabiendo en un pantallazo) */
.sv-block { padding: clamp(100px, 15vh, 180px) var(--pad-x) 0; }
.sv-block__head {
  display: grid; grid-template-columns: auto 1fr; gap: 6px 20px;
  align-items: end; margin-bottom: clamp(18px, 3vh, 30px);
}
.sv-block__num { font-size: clamp(14px, 1vw, 17px); font-weight: 700; color: var(--signal-700); }
/* Escala KOTA: titulares y filas contenidos, con mucho aire — la columna
   de texto debe respirar como en kota.co.uk/service/... */
.sv-block__title {
  font-size: clamp(27px, 2.9vw, 44px); font-weight: 800;
  letter-spacing: -.02em; color: var(--deep); line-height: 1;
}
.sv-block__intro { grid-column: 2; max-width: 560px; color: var(--slate); font-size: clamp(14px, 1vw, 16px); }

.sv-rows { border-top: 1px solid var(--border); }
.sv-row {
  display: grid; grid-template-columns: minmax(0, .95fr) minmax(0, 1.05fr) auto;
  gap: 14px 30px; align-items: center;
  padding: clamp(15px, 2.4vh, 24px) 0; border-bottom: 1px solid var(--border);
  text-decoration: none; color: inherit;
}
.sv-row__title {
  font-size: clamp(17px, 1.4vw, 21px); font-weight: 700;
  color: var(--deep); letter-spacing: -.01em; transition: color .25s;
}
.sv-row__desc { color: var(--slate); font-size: clamp(13px, .95vw, 15px); }
.sv-row__arrow { font-size: clamp(16px, 1.3vw, 20px); color: var(--sun); transition: transform .25s; }
.sv-row:hover .sv-row__title { color: var(--signal-700); }
.sv-row:hover .sv-row__arrow { transform: translateX(8px); }

.sv-band {
  position: relative; overflow: hidden;
  margin: clamp(80px, 12vh, 150px) var(--pad-x) 0;
  padding: clamp(44px, 7vh, 80px) clamp(24px, 4vw, 64px);
  background: var(--deep); color: var(--foam); border-radius: 28px;
}
.sv-band__glow { position: absolute; border-radius: 50%; filter: blur(70px); pointer-events: none; }
.sv-band__glow--teal { width: 420px; height: 420px; right: -90px; top: -120px; background: var(--signal); opacity: .5; }
.sv-band__glow--sun { width: 340px; height: 340px; left: -70px; bottom: -140px; background: var(--sun); opacity: .35; }
.sv-band__title { position: relative; font-size: clamp(30px, 3.6vw, 56px); font-weight: 800; letter-spacing: -.02em; margin-bottom: 14px; }
.sv-band__text { position: relative; max-width: 560px; color: rgba(244,247,250,.82); margin-bottom: 26px; font-size: clamp(16px, 1.35vw, 20px); }
.sv-band .btn-cta { position: relative; }
/* Cuando la banda es la ÚLTIMA sección antes del footer (p.ej. blog):
   aire debajo para no quedar pegada, y algo más de respiro en el botón */
.sv-band--last { margin-bottom: clamp(70px, 10vh, 130px); }
.sv-band--last .sv-band__text { margin-bottom: 36px; }

.sv-process { padding: clamp(80px, 12vh, 150px) var(--pad-x) 0; }
.sv-process__title {
  font-size: clamp(34px, 4.6vw, 76px); font-weight: 800; color: var(--deep);
  letter-spacing: -.02em; margin-bottom: clamp(26px, 4vh, 44px);
}
.sv-steps { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 22px; }
.sv-step { background: var(--surface); border: 1px solid var(--border); border-radius: 20px; padding: 26px 24px; }
.sv-step__num { font-weight: 800; color: var(--sun); font-size: 14px; letter-spacing: 1px; }
.sv-step__title { font-size: clamp(19px, 1.6vw, 24px); font-weight: 700; color: var(--deep); margin: 10px 0 8px; }
.sv-step__desc { color: var(--slate); font-size: 15.5px; line-height: 1.5; }
.sv-cta__title { font-size: clamp(38px, 5.4vw, 92px); font-weight: 800; color: var(--deep); letter-spacing: -.02em; margin-bottom: 14px; }
.sv-cta__text { color: var(--slate); font-size: clamp(16px, 1.4vw, 21px); margin-bottom: 30px; }
.sv-cta__actions { display: flex; gap: 14px; justify-content: center; flex-wrap: wrap; align-items: center; }
/* Dentro de la banda oscura, los botones van alineados a la izquierda
   como el resto del contenido de la banda */
.sv-band .sv-cta__actions { position: relative; justify-content: flex-start; }

@media (max-width: 900px) {
  .sv-block__head { grid-template-columns: 1fr; align-items: start; }
  .sv-block__intro { grid-column: 1; }
  .sv-row { grid-template-columns: 1fr auto; }
  .sv-row__desc { grid-column: 1 / -1; }
  .sv-steps { grid-template-columns: 1fr 1fr; }
}
@media (max-width: 560px) {
  .sv-steps { grid-template-columns: 1fr; }
}

/* ---------- Servicios: animaciones y huecos de imagen ----------
   Los estados ocultos SOLO se aplican con html.sv-anim (lo pone
   subpage-anims.js): sin JS o con reduced-motion, todo visible. */
html.sv-anim .sv-reveal { opacity: 0; transform: translateY(36px); }

.sv-title span { display: block; }
/* "solo.": naranja de marca, alineada a la izquierda como las demás */
.sv-title__indent { margin-left: 0; color: var(--sun); }

/* Hueco de imagen por bloque: sustituir el div por <img>/<video>.
   Esquina superior derecha en arco, como las medias de la portada. */
.sv-media {
  position: relative; margin: 0 0 clamp(26px, 4vh, 44px);
  aspect-ratio: 21 / 8;
  border-radius: var(--radius-lg) 140px var(--radius-lg) var(--radius-lg);
  overflow: hidden;
  background: linear-gradient(135deg, var(--foam), var(--border));
  border: 2px dashed var(--border);
  display: grid; place-content: center; text-align: center;
}
.sv-media__label { color: var(--slate); font-weight: 700; letter-spacing: .5px; padding: 14px; }
.sv-media__label small { display: block; font-weight: 500; margin-top: 6px; opacity: .8; }

/* Deriva sutil de los resplandores de la banda */
@keyframes svGlowDrift {
  0%, 100% { transform: translate(0, 0); }
  50%      { transform: translate(-24px, 18px); }
}
.sv-band__glow { animation: svGlowDrift 14s ease-in-out infinite; }

@media (max-width: 900px) {
  .sv-title__indent { margin-left: 0; }
  .sv-media { aspect-ratio: 16 / 9; }
}
@media (prefers-reduced-motion: reduce) {
  .sv-band__glow { animation: none; }
}

/* ---------- Servicios: estructura fiel a la referencia editorial ----------
   Hero partido (titular · círculo + intro), mosaico de medias,
   declaración a dos columnas y bloques con media lateral sticky. */
.sv-hero__grid {
  display: grid; grid-template-columns: 1.25fr .75fr;
  gap: clamp(30px, 4vw, 70px); align-items: start;
}
.sv-hero__right { display: flex; flex-direction: column; gap: 26px; align-items: flex-end; }
/* Círculo del hero: marco 1:1 que hace de RECORTE REAL del carrusel. Las
   tarjetas de media profundidad se salen del disco y las corta el
   border-radius + overflow; por eso el contenedor es position:relative y los
   envoltorios absolutos. */
.sv-hero__circle {
  /* Fondo que asoma entre tarjetas. NO es color de marca —por eso vive aquí
     y no en :root—: es el navy de las propias ilustraciones de fondo oscuro,
     muestreado de assets/img/ilus-orbita.webp. */
  --sv-hero-navy: #0E2840;
  /* ════════════════════════════════════════════════════════════════
     DIÁMETRO DEL DISCO. Ajustable a mano; lo demás se acomoda solo.
        380px  actual · 460px era el anterior, empujaba el texto
     ════════════════════════════════════════════════════════════════ */
  --sv-disco: 380px;
  width: min(100%, var(--sv-disco));
  aspect-ratio: 1 / 1; border-radius: 50%;
  background: var(--sv-hero-navy); overflow: hidden;
  position: relative; isolation: isolate;
}

/* Tope por ALTURA DE VENTANA — arreglo de raíz del solape con el CTA flotante.
   .floating-btn--project es position:fixed en la banda inferior del viewport y
   NADIE le reserva sitio, así que lo que caiga ahí queda tapado. En vez de
   compensar con márgenes —que solo funcionaría a un alto concreto— se impide
   que el disco crezca lo bastante como para empujar el párrafo a esa banda.

   Los 376px son lo que la columna necesita por debajo del disco: ~150 de
   cabecera y padding del hero + 26 de hueco + ~95 del párrafo + ~90 de banda
   del botón. Si cambia el alto del párrafo o del CTA, ajustar ESTE número y
   no el diámetro.

   ⚠ SOLO a partir de 901px, es decir solo en la maquetación a dos columnas.
   Por debajo el hero se apila, el párrafo cae POR DEBAJO del botón y no hay
   solape que evitar; aplicar el tope allí encogía el disco sin motivo (a
   500x580 lo dejaba en 204px teniendo --sv-disco en 300). */
@media (min-width: 901px) {
  .sv-hero__circle { width: min(100%, var(--sv-disco), calc(100svh - 376px)); }
}

/* Vídeo de la baraja de tarjetas dentro del disco (sustituye al collage
   de ilustraciones). Cubre el círculo entero; con prefers-reduced-motion
   se oculta y en su lugar se muestra el póster estático. */
.sv-hero__video,
.sv-hero__poster {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; display: block;
}
.sv-hero__poster { display: none; }
@media (prefers-reduced-motion: reduce) {
  .sv-hero__video { display: none; }
  .sv-hero__poster { display: block; }
}

/* ---- CARRUSEL EN PROFUNDIDAD, CONTINUO ----
   Las 12 tarjetas recorren SIN PARAR una elipse cerrada vista en escorzo:
   vienen del fondo pequeñas y desvaídas, crecen hasta el primer plano
   cruzando por delante de las demás y vuelven a alejarse. Los 12 llevan el
   mismo recorrido con un desfase negativo, así que se reparten por la
   trayectoria y el conjunto se lee como un giro continuo. Al ser keyframes
   periódicos el bucle cierra solo: no hay corte que disimular.

   PROFUNDIDAD IDÉNTICA a la versión de pasos: los keyframes están muestreados
   cada 15° y uno de cada dos cae exactamente sobre los 12 puestos de
   entonces, con su misma escala y opacidad. El contraste entre la frontal
   nítida y grande (escala 1, opacidad 1) y las del fondo pequeñas y desvaídas
   (0,40 y 0,40) se conserva punto por punto.

   La posición va en el ENVOLTORIO, no en la tarjeta: el envoltorio mide lo
   que el disco (inset:0), así que el % de su translate() se resuelve contra
   el disco. ⚠ Si se pusiera en la tarjeta, el % se mediría contra la propia
   tarjeta y todo saldría amontonado en el centro. Y NO usar unidades de
   contenedor (cqw): dentro de transform se resuelven en una pasada de layout
   posterior y dejan el transform en identidad de forma intermitente.

   Solo se anima transform y opacity. El z-index es entero y no interpola: lo
   reordena js/subpage-anims.js leyendo el reloj real de la animación. */
.collage {
  /* ════════════════════════════════════════════════════════════════
     DURACIÓN DE UNA VUELTA COMPLETA. Único número para el ritmo; los
     desfases se derivan (--collage-paso = vuelta / 12).
        40s  actual → cada tarjeta pasa por delante cada 40 s y el
                      frente cambia cada 3,3 s
        30s  más vivo; a partir de aquí empieza a competir con el titular
        60s  contemplativo, pero un minuto entre pasadas es mucho
     ════════════════════════════════════════════════════════════════ */
  --collage-vuelta: 40s;
  /* En móvil se recalcula sobre 8 (bloque de 560px) para que las que quedan
     sigan repartidas por igual en la trayectoria. */
  --collage-paso: calc(var(--collage-vuelta) / 12);
  position: absolute; inset: 0;
}

/* Envoltorio: lleva la POSICIÓN sobre la elipse. */
.collage__orbita {
  position: absolute; inset: 0;
  animation: collage-orbita var(--collage-vuelta) linear infinite;
  animation-delay: calc(var(--i) * var(--collage-paso) * -1);
}
/* Tarjeta: lleva la PROFUNDIDAD (escala + opacidad) y su ladeo, que crece
   hacia los laterales y es 0 en el frente. Como el envoltorio solo traslada
   y no gira, la tarjeta no necesita contrarrotación. */
.collage__card {
  position: absolute; left: 50%; top: 50%;
  width: var(--card, 26%); height: auto;
  transform-origin: 50% 50%;
  border-radius: 10px;
  box-shadow: 0 10px 30px rgba(0, 0, 0, .28);
  animation: collage-carta var(--collage-vuelta) linear infinite;
  animation-delay: calc(var(--i) * var(--collage-paso) * -1);
}

@keyframes collage-orbita {
  0%      { transform: translate(0.00%, 14.00%); }
  4.167%  { transform: translate(9.84%, 13.49%); }
  8.333%  { transform: translate(19.00%, 11.99%); }
  12.5%   { transform: translate(26.87%, 9.61%); }
  16.67%  { transform: translate(32.91%, 6.50%); }
  20.83%  { transform: translate(36.71%, 2.88%); }
  25%     { transform: translate(38.00%, -1.00%); }
  29.17%  { transform: translate(36.71%, -4.88%); }
  33.33%  { transform: translate(32.91%, -8.50%); }
  37.5%   { transform: translate(26.87%, -11.61%); }
  41.67%  { transform: translate(19.00%, -13.99%); }
  45.83%  { transform: translate(9.84%, -15.49%); }
  50%     { transform: translate(0.00%, -16.00%); }
  54.17%  { transform: translate(-9.84%, -15.49%); }
  58.33%  { transform: translate(-19.00%, -13.99%); }
  62.5%   { transform: translate(-26.87%, -11.61%); }
  66.67%  { transform: translate(-32.91%, -8.50%); }
  70.83%  { transform: translate(-36.71%, -4.88%); }
  75%     { transform: translate(-38.00%, -1.00%); }
  79.17%  { transform: translate(-36.71%, 2.88%); }
  83.33%  { transform: translate(-32.91%, 6.50%); }
  87.5%   { transform: translate(-26.87%, 9.61%); }
  91.67%  { transform: translate(-19.00%, 11.99%); }
  95.83%  { transform: translate(-9.84%, 13.49%); }
  100%    { transform: translate(-0.00%, 14.00%); }
}

@keyframes collage-carta {
  0%      { transform: translate(-50%, -50%) rotate(0.00deg) scale(1.000); opacity: 1.000; }
  4.167%  { transform: translate(-50%, -50%) rotate(1.55deg) scale(0.990); opacity: 0.990; }
  8.333%  { transform: translate(-50%, -50%) rotate(3.00deg) scale(0.960); opacity: 0.960; }
  12.5%   { transform: translate(-50%, -50%) rotate(4.24deg) scale(0.912); opacity: 0.912; }
  16.67%  { transform: translate(-50%, -50%) rotate(5.20deg) scale(0.850); opacity: 0.850; }
  20.83%  { transform: translate(-50%, -50%) rotate(5.80deg) scale(0.778); opacity: 0.778; }
  25%     { transform: translate(-50%, -50%) rotate(6.00deg) scale(0.700); opacity: 0.700; }
  29.17%  { transform: translate(-50%, -50%) rotate(5.80deg) scale(0.622); opacity: 0.622; }
  33.33%  { transform: translate(-50%, -50%) rotate(5.20deg) scale(0.550); opacity: 0.550; }
  37.5%   { transform: translate(-50%, -50%) rotate(4.24deg) scale(0.488); opacity: 0.488; }
  41.67%  { transform: translate(-50%, -50%) rotate(3.00deg) scale(0.440); opacity: 0.440; }
  45.83%  { transform: translate(-50%, -50%) rotate(1.55deg) scale(0.410); opacity: 0.410; }
  50%     { transform: translate(-50%, -50%) rotate(0.00deg) scale(0.400); opacity: 0.400; }
  54.17%  { transform: translate(-50%, -50%) rotate(-1.55deg) scale(0.410); opacity: 0.410; }
  58.33%  { transform: translate(-50%, -50%) rotate(-3.00deg) scale(0.440); opacity: 0.440; }
  62.5%   { transform: translate(-50%, -50%) rotate(-4.24deg) scale(0.488); opacity: 0.488; }
  66.67%  { transform: translate(-50%, -50%) rotate(-5.20deg) scale(0.550); opacity: 0.550; }
  70.83%  { transform: translate(-50%, -50%) rotate(-5.80deg) scale(0.622); opacity: 0.622; }
  75%     { transform: translate(-50%, -50%) rotate(-6.00deg) scale(0.700); opacity: 0.700; }
  79.17%  { transform: translate(-50%, -50%) rotate(-5.80deg) scale(0.778); opacity: 0.778; }
  83.33%  { transform: translate(-50%, -50%) rotate(-5.20deg) scale(0.850); opacity: 0.850; }
  87.5%   { transform: translate(-50%, -50%) rotate(-4.24deg) scale(0.912); opacity: 0.912; }
  91.67%  { transform: translate(-50%, -50%) rotate(-3.00deg) scale(0.960); opacity: 0.960; }
  95.83%  { transform: translate(-50%, -50%) rotate(-1.55deg) scale(0.990); opacity: 0.990; }
  100%    { transform: translate(-50%, -50%) rotate(-0.00deg) scale(1.000); opacity: 1.000; }
}

/* Desfase de cada tarjeta: las reparte por el recorrido. El z-index de
   arranque va por profundidad; en cuanto la animación corre lo reordena el
   JS. Los valores son escala*1000, monótonos con la cercanía. */
.collage__orbita:nth-child(1)  { --i:  0; z-index: 1000; }
.collage__orbita:nth-child(2)  { --i:  1; z-index:  960; }
.collage__orbita:nth-child(3)  { --i:  2; z-index:  850; }
.collage__orbita:nth-child(4)  { --i:  3; z-index:  700; }
.collage__orbita:nth-child(5)  { --i:  4; z-index:  550; }
.collage__orbita:nth-child(6)  { --i:  5; z-index:  440; }
.collage__orbita:nth-child(7)  { --i:  6; z-index:  400; }
.collage__orbita:nth-child(8)  { --i:  7; z-index:  440; }
.collage__orbita:nth-child(9)  { --i:  8; z-index:  550; }
.collage__orbita:nth-child(10) { --i:  9; z-index:  700; }
.collage__orbita:nth-child(11) { --i: 10; z-index:  850; }
.collage__orbita:nth-child(12) { --i: 11; z-index:  960; }

/* Sin movimiento: se PAUSAN las animaciones en vez de anularlas. Como el
   desfase negativo ya está aplicado, cada tarjeta se congela en su punto de
   la trayectoria y el conjunto queda repartido y quieto — no hace falta una
   disposición estática aparte. */
@media (prefers-reduced-motion: reduce) {
  .collage__orbita, .collage__card { animation-play-state: paused; }
}
.sv-hero__right .sv-sub { max-width: 460px; margin-bottom: 0; }
.sv-hero__foot {
  display: flex; justify-content: space-between; align-items: flex-end;
  gap: 30px; margin-top: clamp(30px, 5vh, 60px);
}
.sv-discover-label { color: var(--slate); font-size: 15px; margin-bottom: 12px; }
.sv-pills a.is-active { background: var(--deep); color: var(--foam); }

/* Hueco de imagen genérico (sustituir por <img>/<video>) */
.sv-media-slot {
  position: relative; overflow: hidden; border-radius: var(--radius-lg);
  border: 2px dashed var(--border);
  background: linear-gradient(135deg, var(--foam), var(--border));
  display: grid; place-content: center; text-align: center;
}
.sv-media-slot--arch { border-radius: var(--radius-lg) 140px var(--radius-lg) var(--radius-lg); }
/* Hueco ya relleno con imagen o vídeo real: fuera borde punteado y fondo */
.sv-media-slot--filled { border: 0; background: none; display: block; }
.sv-media-slot--filled img,
.sv-media-slot--filled video {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; display: block;
}

/* Declaración */
.sv-statement {
  display: grid; grid-template-columns: 1.15fr .85fr;
  gap: clamp(30px, 4vw, 70px); align-items: start;
  padding: clamp(80px, 12vh, 150px) var(--pad-x) 0;
}
.sv-statement__title {
  font-size: clamp(34px, 4.6vw, 80px); font-weight: 800;
  color: var(--deep); letter-spacing: -.02em; line-height: 1.02;
}
.sv-statement__title span { display: block; }
.sv-statement__text { color: var(--ink); font-size: clamp(17px, 1.5vw, 23px); max-width: 520px; }

/* Bloques a dos columnas al estilo KOTA: imagen grande pegada al margen
   de página (alterna izquierda/derecha por bloque), arco solo en la
   esquina superior exterior y texto centrado en vertical respecto a ella. */
.sv-block__grid {
  display: grid;
  grid-template-columns: minmax(0, .94fr) minmax(0, 1.06fr);
  gap: clamp(34px, 5.5vw, 100px); align-items: center;
}
.sv-block__grid--flip { grid-template-columns: minmax(0, 1.06fr) minmax(0, .94fr); }
.sv-block__grid--flip .sv-block__content { order: 2; }
.sv-block__grid--flip .sv-block__media { order: 1; }
.sv-block__media {
  /* Como las piezas de KOTA: tarjeta esbelta que FLOTA dentro del padding
     de página (ya no sangra hasta el borde). El ancho va atado a la altura
     (74vh × .92) para que la proporción vertical se mantenga igual en
     cualquier pantalla; los vídeos vienen preparados en ese mismo 0.92. */
  height: min(74vh, 680px);
  width: min(100%, calc(74vh * .92), 640px); max-width: none;
  align-self: center;
  /* sin --flip: imagen a la derecha → pegada al lado exterior de su
     columna, arco arriba-derecha y el resto de esquinas suaves */
  justify-self: end;
  border-radius: var(--radius-lg) clamp(120px, 10vw, 200px) var(--radius-lg) var(--radius-lg);
}
.sv-block__grid--flip .sv-block__media {
  /* imagen a la izquierda → lado exterior izquierdo, arco arriba-izquierda */
  justify-self: start;
  border-radius: clamp(120px, 10vw, 200px) var(--radius-lg) var(--radius-lg) var(--radius-lg);
}

@media (max-width: 900px) {
  .sv-hero__grid, .sv-statement, .sv-block__grid { grid-template-columns: 1fr; }
  .sv-hero__right { align-items: flex-start; }
  .sv-hero__circle { --sv-disco: 340px; }
  .collage__card { --card: 27%; box-shadow: 0 8px 22px rgba(0, 0, 0, .26); }
  .sv-block__media {
    position: static; aspect-ratio: 16 / 10; width: 100%;
    height: auto; max-height: none; margin: 0;
    border-radius: clamp(70px, 16vw, 120px) 0 0 0;
  }
  .sv-block__grid--flip .sv-block__content,
  .sv-block__grid--flip .sv-block__media { order: 0; }
}
/* Móvil estrecho: el disco baja a 300px, las tarjetas suben un punto en
   proporción y el carrusel se queda en 8 (el porqué, junto a su regla).
   ⚠ ESTE BLOQUE VA DESPUÉS DEL DE 900px A PROPÓSITO: por debajo de 560
   casan los dos, misma especificidad, y gana el último de la hoja. Si se
   sube por encima, el de 900 le pisa el width y el --card. */
@media (max-width: 560px) {
  .sv-hero__circle { --sv-disco: 300px; }
  /* SOLO 8 TARJETAS EN MÓVIL, por dos motivos que se suman. Con 12 son 24
     animaciones infinitas y en un móvil modesto no es gratis, aunque sean
     transform puro; y en un disco de 300px el recorte se comía casi enteras
     las que rozan el borde. Se ocultan las cuatro últimas —que alternan
     claro/oscuro, así que el equilibrio se mantiene en 4 y 4— y el paso se
     recalcula sobre 8 para que las que quedan sigan repartidas por igual en
     la trayectoria. */
  .collage { --collage-paso: calc(var(--collage-vuelta) / 8); }
  .collage__orbita:nth-child(n+9) { display: none; }
  /* 28% es el techo que aguanta el triángulo frontal con las tres tarjetas
     enteras; se deja en 27% para no ir al límite. Los keyframes NO se tocan:
     sus % se miden contra el disco, así que escalan solos al bajar el
     diámetro. */
  .collage__card { --card: 27%; box-shadow: 0 6px 18px rgba(0, 0, 0, .26); }
}


/* ---------- "Cómo trabajamos" por etapas (filas editoriales) ----------
   Título de etapa a la izquierda; descripción + "Qué incluye" en
   píldoras a la derecha. Sustituye a la parrilla de tarjetas. */
.sv-stages { border-top: 1px solid var(--border); }
.sv-stage__meta {
  display: block; color: var(--sun); font-weight: 800;
  font-size: 14px; letter-spacing: 1.5px; margin-bottom: 10px;
}
.sv-stage__title {
  font-size: clamp(26px, 3vw, 52px); font-weight: 800;
  color: var(--deep); letter-spacing: -.01em; line-height: 1.05;
}
.sv-stage__desc { color: var(--ink); font-size: clamp(16px, 1.4vw, 20px); margin-bottom: 18px; }
.sv-stage__inc-label {
  font-size: 12px; letter-spacing: 2px; font-weight: 700;
  color: var(--slate); text-transform: uppercase; margin-bottom: 10px;
}
.sv-stage__inc { display: flex; flex-wrap: wrap; gap: 10px; padding: 0; }
.sv-stage__inc li {
  list-style: none; border: 1.2px solid var(--border); border-radius: 999px;
  padding: 9px 16px; font-size: 14.5px; color: var(--ink); background: var(--surface);
}
@media (max-width: 900px) {
}

/* ============================================================
   Página CONTACTO — estilo KOTA /contact adaptado a DuoWave
   (titular grande + pills de interés + formulario de líneas +
   bloque oscuro de datos con tarjeta en arco + banda de vídeo).
   El formulario NO tiene backend: compone un mensaje de WhatsApp
   con lo rellenado (patrón de CTAs de la casa).
   ============================================================ */
.ct-hero { padding: clamp(30px, 6vh, 70px) var(--pad-x) clamp(20px, 4vh, 44px); }
.ct-hero__title {
  font-size: clamp(40px, 5.6vw, 92px); font-weight: 800; line-height: .98;
  letter-spacing: -.03em; color: var(--deep);
}
.ct-hero__title span { display: block; }

/* --- Formulario --- */
.ct-form { padding: clamp(10px, 3vh, 30px) var(--pad-x) clamp(60px, 9vh, 110px); }
.ct-form__label { font-size: clamp(22px, 2.2vw, 34px); font-weight: 800; color: var(--deep); margin-bottom: 22px; }
.ct-pills { display: flex; flex-wrap: wrap; gap: 12px; margin-bottom: clamp(36px, 6vh, 60px); }
.ct-pill {
  border: 1.4px solid var(--deep); color: var(--deep); background: transparent;
  border-radius: 999px; padding: 12px 22px; font: 600 15px/1 var(--font);
  cursor: pointer; transition: background .25s, color .25s;
}
.ct-pill:hover { background: color-mix(in srgb, var(--deep) 8%, transparent); }
.ct-pill.is-active { background: var(--deep); color: var(--foam); }

.ct-grid { display: grid; grid-template-columns: 1fr 1fr 1.4fr; gap: 34px 44px; margin-bottom: 34px; }
.ct-grid--b { grid-template-columns: 1fr 1.4fr; }
.ct-field { min-width: 0; }
.ct-field input, .ct-field textarea {
  width: 100%; border: 0; border-bottom: 1.5px solid color-mix(in srgb, var(--deep) 45%, transparent);
  background: transparent; padding: 12px 2px; font: 500 clamp(17px, 1.4vw, 21px)/1.4 var(--font);
  color: var(--ink); border-radius: 0; outline: none; resize: vertical;
}
.ct-field input::placeholder, .ct-field textarea::placeholder { color: var(--deep); opacity: .9; }
.ct-field input:focus, .ct-field textarea:focus { border-bottom-color: var(--signal); }
.ct-field--full { grid-column: 1 / -1; }
.ct-note { color: var(--slate); font-size: 14px; margin: 10px 0 0; }

.ct-foot { display: flex; flex-wrap: wrap; align-items: flex-end; justify-content: space-between; gap: 24px; margin-top: 26px; }
.ct-check { display: flex; align-items: flex-start; gap: 12px; max-width: 560px; cursor: pointer; }
.ct-check input { width: 20px; height: 20px; margin-top: 2px; accent-color: var(--signal-700); cursor: pointer; }
.ct-check span { color: var(--ink); font-size: 15px; line-height: 1.5; }
.ct-submit[disabled] { opacity: .45; cursor: not-allowed; }
.ct-status { margin-top: 20px; font: 600 16px/1.5 var(--font); color: var(--signal-700); }
.ct-status--error { color: #b3541e; }
.ct-alt { color: var(--slate); font-size: 15px; margin-top: 18px; }
.ct-alt a { color: var(--signal-700); font-weight: 600; text-decoration: none; }
.ct-alt a:hover { text-decoration: underline; }

/* --- Bloque oscuro de datos (tarjeta blanca en arco + emails) --- */
.ct-info { background: var(--deep); color: var(--foam); padding: clamp(60px, 10vh, 120px) var(--pad-x); }
.ct-info__grid { display: grid; grid-template-columns: 1.1fr .9fr; gap: clamp(36px, 5vw, 90px); align-items: center; }
.ct-card {
  background: var(--surface); color: var(--ink);
  border-radius: 24px clamp(80px, 9vw, 150px) 24px 24px;
  padding: clamp(30px, 4vw, 60px);
}
.ct-card__city { font-size: clamp(26px, 2.6vw, 40px); font-weight: 800; color: var(--deep); margin-bottom: 12px; }
.ct-card__addr { color: var(--slate); line-height: 1.6; margin-bottom: 26px; }
.ct-card__tel { display: inline-block; font-size: clamp(22px, 2.2vw, 34px); font-weight: 800; color: var(--deep); text-decoration: none; margin-bottom: 22px; }
.ct-card__tel:hover { color: var(--signal-700); }
.ct-card__faq { color: var(--slate); font-size: 15px; line-height: 1.6; }
.ct-card__faq a { color: var(--signal-700); font-weight: 600; text-decoration: none; }
.ct-card__faq a:hover { text-decoration: underline; }
.ct-mails__tag { color: color-mix(in srgb, var(--foam) 55%, transparent); font-size: 15px; margin-bottom: 4px; }
.ct-mails__mail {
  display: inline-block; color: var(--foam); font-size: clamp(26px, 3vw, 46px);
  font-weight: 800; letter-spacing: -.01em; text-decoration: none; margin-bottom: 26px;
}
.ct-mails__mail:hover { color: var(--signal); }
.ct-mails__follow { font-size: clamp(20px, 1.8vw, 28px); font-weight: 800; margin: 10px 0 12px; }
.ct-mails__links { display: flex; flex-direction: column; gap: 8px; }
.ct-mails__links a { color: var(--foam); text-decoration: none; font-size: 17px; }
.ct-mails__links a:hover { color: var(--signal); }

/* --- Banda de vídeo tipo showreel (enlaza a casos) ---
   A sangre completa: ocupa todo el ancho y va pegada al bloque oscuro
   de datos (arriba) y al footer (abajo), sin huecos de fondo claro. */
.ct-reel { position: relative; padding: 0; overflow: hidden; display: block; }
.ct-reel__pill {
  display: block; /* es un <span>: sin esto, aspect-ratio no aplica */
  position: relative; width: 100%; aspect-ratio: 21 / 9; max-height: 82vh;
  margin: 0; border-radius: 0; overflow: hidden; background: var(--deep);
}
/* El navy del vídeo no es exactamente --deep: se funden los bordes
   superior e inferior con un degradado del color de la web para que
   no se vea el corte contra el bloque de datos ni contra el footer. */
.ct-reel__pill::before, .ct-reel__pill::after {
  content: ""; position: absolute; left: 0; right: 0; z-index: 1;
  height: clamp(70px, 14vh, 150px); pointer-events: none;
}
.ct-reel__pill::before { top: 0; background: linear-gradient(to bottom, var(--deep), transparent); }
.ct-reel__pill::after { bottom: 0; background: linear-gradient(to top, var(--deep), transparent); }
.ct-reel__pill video, .ct-reel__poster { width: 100%; height: 100%; object-fit: cover; display: block; }
.ct-reel__poster { display: none; }
.ct-reel__marquee {
  position: absolute; top: 50%; left: 0; transform: translateY(-50%);
  white-space: nowrap; pointer-events: none; z-index: 2;
  color: #fff; mix-blend-mode: difference;
  font-size: clamp(60px, 9vw, 150px); font-weight: 800; letter-spacing: -.02em;
}
.ct-reel__marquee > span { display: inline-block; padding-right: .6em; animation: ctMarquee 16s linear infinite; }
@keyframes ctMarquee { to { transform: translateX(-100%); } }
.ct-reel__btn {
  position: absolute; left: 50%; bottom: 14%; transform: translateX(-50%); z-index: 3;
  border: 1.4px solid rgba(255,255,255,.85); color: #fff; border-radius: 999px;
  padding: 14px 26px; font: 600 16px/1 var(--font); background: rgba(10,37,64,.25);
  backdrop-filter: blur(4px); transition: background .25s;
}
.ct-reel:hover .ct-reel__btn { background: rgba(10,37,64,.55); }

@media (max-width: 900px) {
  .ct-grid, .ct-grid--b { grid-template-columns: 1fr; gap: 26px; }
  .ct-info__grid { grid-template-columns: 1fr; }
  .ct-reel__pill { aspect-ratio: 16 / 10; }
}
@media (prefers-reduced-motion: reduce) {
  .ct-reel__pill video { display: none; }
  .ct-reel__poster { display: block; }
  .ct-reel__marquee > span { animation: none; }
}

/* ============================================================
   Página SOBRE NOSOTROS — estilo KOTA /agency adaptado
   (hero editorial + secciones con kicker lateral + declaración +
   equipo con fichas + CTA final). Sin premios ni datos inventados.
   ============================================================ */
/* El hero llena el primer pantallazo (solo kicker + titular, centrados);
   la siguiente sección queda bajo el pliegue y nada asoma tapado. */
.ab-hero {
  min-height: calc(100vh - 110px);
  min-height: calc(100svh - 110px);
  display: flex; flex-direction: column; justify-content: center;
  padding: clamp(30px, 6vh, 70px) var(--pad-x) clamp(80px, 14vh, 150px);
}
@media (max-width: 900px) { .ab-hero { min-height: auto; padding-bottom: clamp(26px, 5vh, 56px); } }
.ab-kicker {
  font-size: 13px; letter-spacing: 3px; font-weight: 700;
  color: var(--slate); text-transform: uppercase; margin-bottom: 18px;
}
.ab-hero__title {
  font-size: clamp(40px, 6vw, 96px); font-weight: 800; line-height: .98;
  letter-spacing: -.03em; color: var(--deep);
}
.ab-hero__title span { display: block; }

/* Sección con kicker lateral (OUR MISSION / OUR APPROACH de KOTA) */
.ab-sec {
  display: grid; grid-template-columns: minmax(0, .3fr) minmax(0, .7fr);
  gap: clamp(24px, 4vw, 70px); align-items: start;
  padding: clamp(50px, 8vh, 100px) var(--pad-x) 0;
}
.ab-sec__kicker {
  font-size: clamp(14px, 1.1vw, 17px); font-weight: 800; letter-spacing: .18em;
  text-transform: uppercase; color: var(--signal-700); line-height: 1.5;
}
.ab-sec__title {
  font-size: clamp(26px, 3.2vw, 52px); font-weight: 800; line-height: 1.08;
  letter-spacing: -.02em; color: var(--deep); margin-bottom: 22px;
}
.ab-sec__body > p {
  max-width: 62ch; color: var(--ink); font-size: clamp(16px, 1.35vw, 20px);
  line-height: 1.7; margin-bottom: 1em;
}
.ab-sec__body > p strong { color: var(--deep); }

/* Media panorámica (hueco marcado) */
.ab-media { margin: clamp(50px, 8vh, 100px) var(--pad-x) 0; aspect-ratio: 21 / 9; }
/* Ficha con vídeo recortado (sin el marco blanco del original): el hueco
   adopta la proporción exacta del archivo para que no reaparezcan franjas
   ni se pierdan los laterales. Va en clase y NO inline porque GSAP limpia
   los estilos inline de los .sv-reveal al acabar la animación. */
.ab-media--panoramico { aspect-ratio: 1284 / 456; }

/* Declaración grande intermedia */
.ab-quote { padding: clamp(60px, 10vh, 130px) var(--pad-x) 0; }
.ab-quote__title {
  font-size: clamp(32px, 4.4vw, 74px); font-weight: 800; line-height: 1.02;
  letter-spacing: -.02em; color: var(--deep); margin-bottom: 22px;
}
.ab-quote__title span { display: block; }
.ab-quote__text { max-width: 640px; color: var(--slate); font-size: clamp(16px, 1.4vw, 21px); line-height: 1.65; }

/* Equipo: fichas (foto + nombre + rol) */
.ab-team {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: clamp(20px, 3vw, 44px); max-width: 860px;
}
.ab-card { min-width: 0; }
/* 2:3 y no 4:5: los retratos van a plano completo con su fondo original
   (decisión de agosto 2026) y este hueco calca su proporción para no
   recortarles nada */
.ab-card__photo { aspect-ratio: 2 / 3; border-radius: var(--radius-lg) 90px var(--radius-lg) var(--radius-lg); }
.ab-card__name { font-size: clamp(20px, 1.9vw, 28px); font-weight: 800; color: var(--deep); margin: 14px 0 2px; }
.ab-card__role { color: var(--slate); font-size: clamp(14px, 1.1vw, 16px); }

@media (max-width: 900px) {
  .ab-sec { grid-template-columns: 1fr; gap: 14px; }
  .ab-media { aspect-ratio: 16 / 10; }
  .ab-team { grid-template-columns: 1fr; }
}

/* ============================================================
   Página CASOS — estilo KOTA /work: hero editorial con círculo,
   parrilla de tarjetas con cabecera (↘ nombre · año) y hover que
   muestra el resumen + servicios sobre fondo oscuro.
   ============================================================ */
/* Proporciones de la referencia: sección casi a pantalla completa;
   título arriba-izquierda, etiqueta "Casos" abajo-izquierda, círculo
   arriba-derecha e intro abajo-derecha. */
/* MISMAS proporciones que el hero de Servicios (sv-hero): grid 1.25/.75,
   titular a 6vw (máx. 100px) y círculo de 460px. */
.cs-hero {
  display: grid; grid-template-columns: minmax(0, 1.15fr) minmax(0, .85fr);
  gap: clamp(30px, 4vw, 70px); align-items: stretch;
  /* La COMPOSICIÓN ENTERA (título + círculo + intro + etiqueta) cabe en
     el primer pantallazo, como la referencia: la altura descuenta el
     padding-top global de .subpage main (120px) y el margen inferior. */
  /* pantalla EXACTA: el hero llena el primer pantallazo y la parrilla
     no asoma por abajo al entrar */
  min-height: calc(100vh - 120px);
  min-height: calc(100svh - 120px);
  padding: clamp(20px, 4vh, 44px) var(--pad-x) clamp(30px, 5vh, 56px);
}
.cs-hero__left {
  display: flex; flex-direction: column; justify-content: space-between;
  gap: clamp(40px, 8vh, 90px);
}
.cs-hero__title {
  font-size: clamp(40px, 6vw, 100px); font-weight: 800; line-height: .95;
  letter-spacing: -.03em; color: var(--deep);
}
.cs-hero__title span { display: block; }
.cs-label {
  border-left: 3px solid var(--deep); padding-left: 16px;
  font-size: clamp(22px, 2.1vw, 34px); font-weight: 700; color: var(--deep);
}
/* Como la referencia: el círculo pegado a la derecha y el párrafo
   debajo, alineado al inicio de la columna (se extiende por la
   izquierda del círculo, no escondido en la esquina). */
.cs-hero__right {
  display: flex; flex-direction: column; align-items: flex-start;
  justify-content: space-between; gap: clamp(24px, 4vh, 44px);
  /* el subtítulo termina por ENCIMA de la zona del botón flotante
     naranja: nunca queda texto tapado al entrar */
  padding-bottom: clamp(100px, 12vh, 130px);
}
/* El círculo no toca el borde: se acerca al centro, como la referencia */
.cs-hero__circle { align-self: flex-end; margin-right: clamp(24px, 5vw, 100px); }
.cs-hero__circle {
  /* 460px como en Servicios, pero capado por alto de viewport para que
     círculo + intro + etiqueta sigan cabiendo en el primer pantallazo
     en portátiles con poco alto útil */
  width: min(100%, 460px, calc(100vh - 420px));
  width: min(100%, 460px, calc(100svh - 420px));
  aspect-ratio: 1; border-radius: 50%;
  overflow: hidden; background: var(--deep);
}
.cs-hero__circle img { width: 100%; height: 100%; object-fit: cover; display: block; }
.cs-hero__intro {
  max-width: 44ch; color: var(--ink); font-size: clamp(16px, 1.35vw, 20px);
  line-height: 1.65;
  /* arranca cerca del centro de la página, como el párrafo de la referencia */
  margin-left: clamp(-120px, -6vw, 0px);
}

.cs-grid {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: clamp(18px, 2.2vw, 34px);
  padding: 0 var(--pad-x) clamp(70px, 11vh, 140px);
}
.cs-card {
  display: block; text-decoration: none; color: inherit; min-width: 0;
  border: 1px solid var(--border); border-radius: var(--radius-lg);
  background: color-mix(in srgb, var(--surface) 55%, transparent);
  padding: clamp(10px, 1.2vw, 16px);
}
.cs-card__head {
  display: flex; align-items: center; justify-content: space-between; gap: 16px;
  padding: 6px 8px 14px;
}
.cs-card__name { font-size: clamp(17px, 1.4vw, 21px); font-weight: 700; color: var(--deep); }
.cs-card__name .arrow { color: var(--sun); margin-right: 8px; }
.cs-card__year { color: var(--slate); font-size: clamp(15px, 1.2vw, 18px); }
.cs-card__media {
  display: block; position: relative; aspect-ratio: 16 / 10; border-radius: 14px;
  overflow: hidden; background: var(--deep);
}
/* Solo la imagen directa del caso llena la caja (el logo de la tarjeta
   "Próximamente" conserva su tamaño propio) */
.cs-card__media > img { width: 100%; height: 100%; object-fit: cover; display: block;
  transition: transform .5s cubic-bezier(.22,1,.36,1); }
a.cs-card:hover .cs-card__media > img { transform: scale(1.04); }
/* Cubierta al pasar el ratón: resumen + servicios sobre navy */
.cs-card__cover {
  position: absolute; inset: 0; z-index: 1; opacity: 0; transition: opacity .35s ease;
  display: flex; flex-direction: column; justify-content: space-between;
  padding: clamp(20px, 2.4vw, 40px);
  background: color-mix(in srgb, var(--deep) 90%, transparent); color: var(--foam);
}
a.cs-card:hover .cs-card__cover, a.cs-card:focus-visible .cs-card__cover { opacity: 1; }
.cs-card__cover-title {
  font-size: clamp(19px, 1.8vw, 30px); font-weight: 700; line-height: 1.25;
  max-width: 24ch;
}
.cs-tags { display: flex; flex-wrap: wrap; gap: 8px; }
.cs-tags span {
  border: 1.2px solid rgba(244,247,250,.65); border-radius: 999px;
  padding: 9px 16px; font-size: 14px; font-weight: 600;
}
/* Tarjeta "Próximamente" de la parrilla (no enlaza) */
.cs-card--soon .cs-card__media { background: none; }
.cs-card--soon .blog-soon { height: 100%; min-height: 0; border: 0; border-radius: 0; }

@media (max-width: 900px) {
  .cs-hero { grid-template-columns: 1fr; min-height: auto; }
  .cs-hero__right { align-items: flex-start; padding-bottom: 0; }
  .cs-hero__circle { margin-right: 0; }
  .cs-hero__intro { margin-left: 0; }
  .cs-grid { grid-template-columns: 1fr; }
}

/* ---------- Detalle de caso — estilo KOTA /work/upp ----------
   Titular-declaración + etiqueta de servicio; introducción con
   kicker lateral (reutiliza .ab-sec) + ficha de datos; imagen
   grande; secciones editoriales. ---------- */
.cd-hero { padding: clamp(30px, 6vh, 70px) var(--pad-x) 0; }
.cd-hero__title {
  font-size: clamp(34px, 4.4vw, 76px); font-weight: 800; line-height: 1.04;
  letter-spacing: -.03em; color: var(--deep); max-width: 22ch; margin-bottom: 26px;
}
.cd-hero__title span { display: block; }
.cd-hero__pill {
  display: inline-block; border: 1.4px solid var(--deep); color: var(--deep);
  border-radius: 999px; padding: 12px 22px; font: 600 15px/1 var(--font);
}
.cd-meta { display: grid; gap: 18px; align-content: start; }
.cd-meta__tag { color: var(--slate); font-size: 14px; margin-bottom: 2px; }
.cd-meta__val { color: var(--deep); font-weight: 700; font-size: clamp(16px, 1.3vw, 19px); }
.cd-media { margin: clamp(50px, 8vh, 100px) var(--pad-x) 0; }
.cd-media img { width: 100%; height: auto; display: block; border-radius: var(--radius-lg);
  box-shadow: 0 30px 70px -40px rgba(10,37,64,.5); }

/* ---------- Servicios: aire tras ocultar el mosaico de medias ----------
   Con el mosaico visible, .sv-statement era una sección aparte que llegaba
   después de una galería a pantalla casi completa, y por eso arrancaba con
   clamp(80px, 12vh, 150px) de aire. Comentado el mosaico, ese mismo aire
   deja el titular flotando lejos de las píldoras y se lee como un bloque
   suelto en vez de como continuación de ellas.

   Se ajusta por selector de HERMANO ADYACENTE y no con una clase
   modificadora ni tocando las reglas base, por dos motivos:

     · .sv-statement se usa en 10 páginas (esta y las 9 de servicios/) y
       .sv-block tiene tres instancias en esta misma página. Bajar el
       padding en la regla base apretaría todo eso de rebote. Los hermanos
       adyacentes solo casan aquí: .sv-hero existe únicamente en
       servicios.html, y .sv-block no existe en las 9 páginas de servicio.
     · La condición que justifica el ajuste ES la posición. Si el titular
       dejara de ir pegado al hero —por ejemplo al descomentar el mosaico y
       devolverlo a su sitio— el selector deja de casar solo y vuelve el
       espaciado original, sin tener que acordarse de revertir nada.

   Los valores mantienen clamp() con el mismo tramo vh que los originales,
   solo con topes más bajos; medidos en el DOM a 390/768/1440 quedan en
   ~80-100px y ~100-120px. */
/* Hueco píldoras → titular: sin padding propio. El aire que queda ya lo pone
   el padding-bottom del hero —clamp(30px, 5vh, 60px)— y basta: en reposo deja
   45px a 1440, 51px a 768 y 42px a 390, que es el rango que buscábamos. Poner
   padding aquí encima lo duplicaba y la sección se leía como un bloque aparte.

   ⚠ Ese 45px es el SUELO por esta vía: para bajar más habría que recortar el
   padding-bottom del propio .sv-hero, que también gobierna el aire bajo la
   flecha del hero.

   ⚠ Al medir este hueco, hacerlo en REPOSO y no a scrollY=0: .sv-hero__discover
   es un .sv-reveal, así que mientras no se ha revelado arrastra un
   translateY(36px) que desplaza las píldoras y falsea la medida. */
.sv-hero + .sv-statement { padding-top: 0; }
.sv-statement + .sv-block { padding-top: clamp(88px, 12.5vh, 120px); }

/* ==== 25. INTRO — apertura de la portada con el logo en vídeo ====
   A pantalla COMPLETA, sin márgenes: el blob del logo a sangre ocupa
   todo el primer viewport, con el titular gigante (misma voz que el
   .kotaverse__tag del cierre, aquí aún más grande) y el CTA encima. El
   header se lee igual gracias a su mix-blend-mode: difference.
   En móvil y con prefers-reduced-motion no se descarga vídeo: póster.
   El borde INFERIOR va redondeado: al hacer scroll, la cola oscura del
   héroe cruzaba el viewport como una franja recta que parecía una
   sombra o un corte suelto; con los radios se lee como el remate del
   panel que se va. */
.intro {
  position: relative; overflow: hidden;
  height: 100svh; min-height: 520px;
  background: var(--deep);
  display: grid; place-items: center;
  border-radius: 0 0 var(--radius-xl) var(--radius-xl);
}
.intro__video,
.intro__poster {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; display: block;
}
.intro__poster { display: none; }
.intro__contenido {
  position: relative; z-index: 1; text-align: center;
  display: grid; justify-items: center; gap: clamp(20px, 4vh, 36px);
  padding: 0 24px;
}
/* Titular estilo cierre kotaverse (mismas negritas, mayúsculas y sombra
   de legibilidad sobre el vídeo), a tamaño de apertura */
.intro__titulo {
  color: var(--foam); font-weight: 800; text-transform: uppercase;
  font-size: clamp(40px, 6.5vw, 112px); line-height: 1.04;
  letter-spacing: .04em;
  /* SIN text-shadow a propósito: con letras tan gordas las capas de
     sombra se acumulan y parecen un fondo negro difuminado. */
}
.intro__titulo span { display: block; }
.intro__flecha {
  position: absolute; bottom: clamp(16px, 3vh, 30px); left: 50%;
  z-index: 1; color: var(--foam); font-size: 26px; line-height: 1;
  animation: intro-bote 2.2s ease-in-out infinite;
}
@keyframes intro-bote {
  0%, 100% { transform: translate(-50%, 0); }
  50%      { transform: translate(-50%, 9px); }
}
@media (prefers-reduced-motion: reduce) {
  .intro__video  { display: none; }
  .intro__poster { display: block; }
  .intro__flecha { animation: none; }
}
@media (max-width: 768px) {
  /* línea "sin vídeo en móvil" del proyecto: solo póster */
  .intro__video  { display: none; }
  .intro__poster { display: block; }
}

/* ==== 26. ANALIZA — kicker del panel de apoyo ====
   Texto plano en mayúsculas espaciadas (la píldora con borde y punto
   naranja se retiró a petición). La doble llamada que había debajo
   (botón al chat + formulario clásico) se retiró en agosto 2026: el
   chat vive al lado y era puerta duplicada. */
.analiza-oferta {
  margin-bottom: 18px;
  color: var(--foam); font-weight: 700;
  font-size: clamp(11px, .9vw, 13px); letter-spacing: .14em;
  text-transform: uppercase;
}

/* Variante ROBOT de la intro (vídeo hero-robot.*: el robot sube desde la
   repisa, saluda y se queda congelado — sin loop). La composición es
   completa (robot centrado + iconos a todo lo ancho arriba), así que el
   mensaje y el CTA van a la zona inferior IZQUIERDA, la única despejada
   del plano, en columna compacta. */
.intro--robot .intro__contenido {
  justify-self: start; align-self: end;
  justify-items: start; text-align: left;
  max-width: min(38vw, 520px);
  margin: 0 0 clamp(52px, 11vh, 100px) clamp(20px, 4vw, 80px);
}
/* Tope de tamaño MEDIDO contra la silueta real del robot en la franja del
   titular (borde en x=602 del archivo): con 3.2vw la cola de "AUTOMATIZA"
   conserva holgura en cualquier ancho de ventana — crema sobre crema
   sería ilegible */
.intro--robot .intro__titulo { font-size: clamp(26px, 3.2vw, 60px); }
@media (max-width: 768px) {
  /* en móvil el póster enseña al robot centrado; el mensaje vuelve al
     centro, por encima del borde inferior */
  .intro--robot .intro__contenido {
    justify-self: center; justify-items: center; text-align: center;
    max-width: none; margin: 0 0 clamp(40px, 9vh, 70px);
  }
}



/* ==== 27. INTRO — titular enriquecido (amplía la sección 25) ====
   El "AUTOMATIZA TU NEGOCIO" plano se quedaba sobrio: ahora contraste
   editorial de pesos Manrope (ligera 300 + negra 800, sin salir de la
   tipografía de marca), "negocio" en el naranja de la casa, la onda del
   logo como subrayado, y micro-argumento + línea de confianza bajo el
   CTA para empujar la conversión. Sombra heredada del titular para
   legibilidad sobre vídeo. */
.intro__kicker {
  color: rgba(240, 239, 239, .85); font-weight: 700;
  letter-spacing: .22em; text-transform: uppercase;
  font-size: clamp(11px, .95vw, 14px);
  text-shadow: 0 2px 10px rgba(4, 12, 24, .55);
  margin-bottom: clamp(10px, 1.8vh, 18px);
}
.intro__titulo { text-transform: none; }
.intro__titulo-fina {
  display: block; font-weight: 300; letter-spacing: .01em;
}
.intro__titulo-fuerte { display: block; font-weight: 800; }
.intro__titulo-fuerte em { font-style: normal; color: var(--sun); }
.intro__onda {
  width: clamp(110px, 11vw, 190px); height: auto;
  color: var(--sun); margin: clamp(8px, 1.4vh, 14px) 0 0;
  filter: drop-shadow(0 2px 8px rgba(4, 12, 24, .5));
}
.intro__apoyo {
  color: rgba(240, 239, 239, .88);
  font-size: clamp(15px, 1.25vw, 19px); line-height: 1.55;
  max-width: 34ch;
  text-shadow: 0 2px 10px rgba(4, 12, 24, .55);
  margin-top: clamp(10px, 1.8vh, 16px);
}
.intro__confianza {
  color: rgba(240, 239, 239, .6); font-weight: 600;
  font-size: clamp(11px, .9vw, 13px); letter-spacing: .12em;
  text-transform: uppercase;
  text-shadow: 0 2px 10px rgba(4, 12, 24, .55);
  margin-top: clamp(8px, 1.4vh, 12px);
}
/* En la variante robot el bloque va abajo-izquierda: la onda y los
   textos ya heredan esa alineación del contenedor. En la centrada
   (index-olas) todo se centra solo por justify-items. */

/* ==== 28. INTRO — titular "Di hola." (sustituye al de la sección 27) ====
   Dos palabras a lo grande, patrón de los sitios premiados: el visual
   (robot saludando) lleva el mensaje y el titular le responde. "Di" en
   ligera, "hola" en negra y el punto en el naranja de marca. En línea,
   no apilado: menos altura = menos interferencia con el vídeo. */
.intro__titulo--hola .intro__titulo-fina,
.intro__titulo--hola .intro__titulo-fuerte { display: inline; }
.intro__titulo--hola { font-size: clamp(52px, 7vw, 128px); line-height: 1; }
/* La variante robot capa el titular genérico a 3.2vw (holgura con el
   brazo); "Di hola." es corto y puede ir mucho más grande sin tocarlo:
   medido contra la silueta (borde x=602 del archivo). */
.intro--robot .intro__titulo--hola { font-size: clamp(46px, 6vw, 110px); }

/* ==== 29. INTRO — titular "AUTOMATIZA TU NEGOCIO" estilo cierre ====
   El titular replica el lettering del rótulo del cierre sobre el vídeo
   (.kotaverse__tag): Manrope negra 800, mayúsculas y tracking .06em,
   pero SIN su sombra (ver regla). Dos líneas del mismo
   cuerpo (antes iban en pesos contrastados y no convencía), cada una
   subiendo desde su máscara (entrada del bloque 2a de main.js vía
   data-hero-line) y la onda del logo dibujándose al aterrizar. El trazo
   animado va GATED bajo html.anim: sin JS o con el motor parado, la
   onda se ve completa y estática. */
.intro__titulo--dual .intro__linea { display: block; overflow: hidden; }
.intro__titulo--dual .intro__titulo-fina,
.intro__titulo--dual .intro__titulo-fuerte {
  display: inline-block;
  font-size: clamp(24px, 3.1vw, 54px); font-weight: 800;
  letter-spacing: .06em; text-transform: uppercase; line-height: 1.12;
  color: var(--foam);
  /* Sin sombra: acumulada en negrita tan grande parecía un fondo
     negro difuminado tras las letras (quitada a petición). */
  text-shadow: none;
}
.intro__onda path {
  stroke-dasharray: 165; stroke-dashoffset: 0;   /* estático: completa */
}
html.anim .intro__onda path {
  stroke-dashoffset: 165;
  animation: intro-onda-dibujo .9s ease-out 1s forwards;
}
@keyframes intro-onda-dibujo { to { stroke-dashoffset: 0; } }
@media (prefers-reduced-motion: reduce) {
  html.anim .intro__onda path { stroke-dashoffset: 0; animation: none; }
}

/* ==== 30. HEADER — lema solo en el hero de la portada; intro compacta ====
   El "MARKETING Y AUTOMATIZACIÓN CON IA" junto al logo solo se ve
   mientras el hero de la landing está bajo el header: al bajar se funde
   (clase que pone main.js bloque 0) y en las subpáginas ni aparece.
   Además la intro del robot se compacta: el bloque de texto empezaba tan
   arriba que tapaba el panel de burbujas del vídeo. */
.subpage .header__tag { display: none; }
.header__tag { transition: opacity .35s ease; }
.header__tag--oculta { opacity: 0; pointer-events: none; }

.intro--robot .intro__contenido { gap: clamp(10px, 1.8vh, 18px); }
.intro--robot .intro__onda {
  width: clamp(80px, 7.5vw, 140px); margin-top: clamp(4px, .8vh, 8px);
}
.intro--robot .intro__apoyo { margin-top: clamp(4px, .8vh, 8px); }

