/* ==========================================================================
   ENNAT PROTECTION, deck (presentación con slides)
   Se monta sobre los tokens de theme.css: acá NO se define ni un color nuevo,
   solo la mecánica de diapositivas. Lo carga únicamente la página why-ennat.

   Estructura:
     .deck > .deck-track > .deck-slide          (todas en el DOM, se desplazan)
              .deck-arrow (izq/der)             (los botones laterales)
              .deck-bar   (contador + puntos)

   Las slides viven TODAS en el DOM a propósito: así el texto es rastreable por
   buscadores y localize.mjs puede traducirlo, en vez de inyectarlas por JS.
   ========================================================================== */

/* El deck ocupa la ventana completa y arranca en y=0: la nav del sitio es
   position:fixed (no ocupa layout), así la portada sangra por debajo de ella.
   El contenido de las demás slides se despeja con padding-top, no moviendo el
   deck, para no dejar una franja muerta arriba de la foto de portada.
   dvh sigue la barra del navegador en móvil; vh queda de respaldo. */
.deck{
  position:relative;
  height:100vh;
  height:100dvh;
  overflow:hidden;
  background:var(--bg);
  /* El viewport meta ya permite zoom (sin user-scalable=no ni maximum-scale):
     esto solo asegura que ningún elemento del deck le gane el gesto de pellizco
     al navegador. touch-action NO se toca en ningún selector de este archivo. */
  touch-action:pan-y;
  /* Radio de las fotos. Más chico que el --r-md del sitio (18px): a tamaño de
     slide ese redondeo se lee como una tarjeta, no como una foto. */
  --deck-r:10px;
}
/* La nav sólo se pinta un fondo con .scrolled, y esa clase la agrega js/site.js
   mirando window.scrollY. Acá el documento NUNCA scrollea (el scroll vive dentro
   de cada slide), así que la nav se quedaría transparente para siempre, con sus
   enlaces sobre la foto de portada. En esta página se le da el scrim desde el
   principio: es lo que el resto del sitio muestra apenas bajás un poco. */
/* :is() agrupa esta página con client-deck.html (el deck de cliente generado desde
   el Layout Tool): mismo mecanismo de nav sin scroll propio, incluida acá y no
   duplicada porque las dos comparten exactamente este problema y esta solución -
   a diferencia de las reglas [aria-label="N"] más abajo, que son contenido FIJO de
   esta página y no deben aplicar a client-deck.html (ver el comentario ahí). */
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .nav{
  background:var(--scrim-nav);
  -webkit-backdrop-filter:blur(16px);backdrop-filter:blur(16px);
  border-bottom:1px solid var(--line);
}
.deck-track{
  display:flex;
  height:100%;
  transition:transform .5s var(--ease);
  will-change:transform;
}
.deck-slide{
  flex:0 0 100%;
  width:100%;
  height:100%;
  overflow-y:auto;
  overflow-x:hidden;
  /* Sin esto, al llegar al final del scroll de una slide el gesto se encadena
     al scroller de arriba y en móvil dispara el "volver atrás" del navegador. */
  overscroll-behavior:contain;
  -webkit-overflow-scrolling:touch;
  display:flex;
  flex-direction:column;
  /* Centrado vertical: pedido explícito (se probó anclado arriba para que el
     título quedara a la misma altura en todas las slides, pero el resultado
     gustó menos que el centrado de antes). Solo la 15 (.deck-fill) no
     depende de esto: su .deck-inner ya ocupa el alto completo por su cuenta,
     así que sigue anclada arriba y con el botón pegado abajo. El resto,
     cierre incluido, se centra como grupo; donde el pedido es que el botón
     quede a la altura de la foto/badge, eso se resuelve con align-items en
     esa fila puntual (ver casos, TCO, garantía y cierre más abajo), no
     estirando la slide entera. */
  justify-content:center;
  padding:calc(var(--nav-h) + 26px) 76px 46px;
  position:relative;
}
/* El contenido nunca se pega a los botones laterales. */
.deck-inner{width:100%;max-width:var(--maxw);margin:0 auto}

/* Una slide fuera de vista no debe ser tabulable ni leída por lectores de
   pantalla: el JS le pone [inert]. No se oculta con visibility ni display
   porque las slides tienen que seguir pintadas MIENTRAS dura el desplazamiento
   (si no, se ve el salto) y su texto tiene que quedar en el DOM para los
   buscadores. [inert] hace exactamente eso: saca del foco sin sacar de la vista. */
.deck-slide[inert]{user-select:none}

/* ---- Tipografía de slide ---- */
.deck-eyebrow{
  display:inline-flex;align-items:center;gap:10px;
  font-size:12.5px;font-weight:600;letter-spacing:.18em;text-transform:uppercase;
  color:var(--text-3);margin-bottom:16px;
}
.deck-eyebrow::before{content:"";width:22px;height:2px;background:var(--spark);flex:none}
.deck-slide h2{
  font-family:var(--ff-display);font-weight:600;letter-spacing:-.02em;line-height:1.05;
  font-size:clamp(27px,3.6vw,46px);margin:0 0 16px;
}
.deck-slide h3{font-size:19px;margin:0 0 8px;font-weight:600}
.deck-lead{font-size:clamp(16px,1.5vw,19px);color:var(--text-2);line-height:1.6;margin:0 0 14px;max-width:62ch}
.deck-slide p{color:var(--text-2);line-height:1.6;margin:0 0 12px}
.deck-note{font-size:13.5px;color:var(--text-3);margin-top:14px}

/* ---- Plantillas de slide ---- */
.deck-split{display:grid;grid-template-columns:1fr 1fr;gap:52px;align-items:center}
/* El texto ocupa lo justo y la imagen se queda con el resto: para un esquema con
   cotas, 50/50 lo deja tan chico que hay que acercarlo para leerlo. */
.deck-split.split-media{grid-template-columns:minmax(0,.72fr) minmax(0,1.28fr);gap:36px}
.deck-split.rev .deck-figure{order:-1}
.deck-duo{display:grid;grid-template-columns:1fr 1fr;gap:32px;align-items:stretch}
.deck-trio{display:grid;grid-template-columns:repeat(3,1fr);gap:22px}
.deck-quad{display:grid;grid-template-columns:repeat(4,1fr);gap:18px}
.deck-center{text-align:center;display:flex;flex-direction:column;align-items:center}
.deck-center .deck-eyebrow{justify-content:center}
.deck-center .deck-lead{margin-left:auto;margin-right:auto}

/* ---- Media ----
   La altura de una imagen se ata al viewport, no solo a su proporción: en un
   deck la slide TIENE que entrar en pantalla, y una caja con aspect-ratio fijo
   crece con el ancho hasta desbordar en pantallas bajas (1280x720 era el caso).
   El descuento reserva el alto de la nav, el título y la barra inferior.
   El max() evita que en una ventana muy baja (móvil apaisado, por debajo de
   ~364px de alto) el calc dé negativo: CSS lo clampea a 0 y la imagen
   desaparecería. El piso de 120px la mantiene visible.
   Por debajo de 820px este límite se reemplaza por el modelo flex de más
   abajo, que no depende de adivinar un porcentaje de la pantalla. */
.deck-figure{margin:0;min-width:0}
.deck-media{
  border-radius:var(--deck-r);overflow:hidden;border:1px solid var(--line);
  background:var(--surface);display:block;
  max-height:max(120px,calc(100vh - var(--nav-h) - 290px));
  max-height:max(120px,calc(100dvh - var(--nav-h) - 290px));
}
/* La comparación a dos columnas lleva encabezado propio y pie en cada mitad. */
.deck-duo .deck-media{
  max-height:max(120px,calc(100vh - var(--nav-h) - 340px));
  max-height:max(120px,calc(100dvh - var(--nav-h) - 340px));
}
.deck-media img{width:100%;height:100%;object-fit:cover;display:block}
/* Los diagramas y renders del deck vienen sobre blanco: necesitan lienzo claro
   y encuadre completo (contain), no recortado. */
.deck-media.paper{background:#fff;border-color:rgba(255,255,255,.14)}
/* Sobre el tema claro el lienzo blanco se funde con la página: necesita un
   borde real que lo separe, no el blanco translúcido que sirve sobre oscuro. */
[data-theme="light"] .deck-media.paper{border-color:var(--line-strong)}
.deck-media.paper img{object-fit:contain;padding:14px}
/* Los diagramas recortados aprovechan la caja entera: el margen blanco ya se
   fue en el recorte y volver a meterle padding los achica de nuevo. */
.deck-media.paper.dg-stage img{padding:4px}
.deck-media.plain{background:none;border:none;border-radius:0}
.deck-media.plain img{object-fit:contain}
.deck-media.tall{aspect-ratio:4/5}
.deck-media.wide{aspect-ratio:16/9}
.deck-media.square{aspect-ratio:1/1}
/* Las 4 fotos de daño comparten grilla con miniaturas chicas: en cuadrado no
   entraban en un portátil, y recortadas a 4/3 se sigue leyendo el destrozo. */
.deck-quad .deck-media.square{aspect-ratio:4/3}
/* En la grilla de instalaciones el pie iba en gris a 12.5px y se perdía contra
   el fondo de la slide: en blanco y con peso funciona como etiqueta. */
.deck-quad .deck-cap{color:var(--text);font-weight:700;letter-spacing:.02em}
[data-theme="dark"] .deck-quad .deck-cap,
:root:not([data-theme="light"]) .deck-quad .deck-cap{color:#F4F2F7}
.deck-cap{font-size:12.5px;color:var(--text-3);margin-top:10px;letter-spacing:.04em;overflow-wrap:break-word}

/* ---- Pie de foto SOBRE la imagen ----
   Debajo, en la grilla de miniaturas, el pie caía a 10.5px gris sobre el fondo
   de la slide y en un teléfono no se leía. Encima de la foto puede ir bastante
   más grande y con peso, y el degradado le garantiza el contraste sea cual sea
   la parte de la foto que le toque debajo. */
.deck-cap-over .deck-media{position:relative}
/* Arriba, no abajo: en estas fotos lo que importa (la base rota, el anclaje
   arrancado) está en la parte BAJA del encuadre y el pie la tapaba. */
.deck-cap-over .deck-cap{
  position:absolute;left:0;right:0;top:0;bottom:auto;margin:0;
  padding:10px 12px 26px;
  font-size:14px;font-weight:700;line-height:1.2;letter-spacing:.01em;
  color:#F4F2F7;text-shadow:0 1px 4px rgba(0,0,0,.75);
  background:linear-gradient(180deg,rgba(8,8,10,.92) 0%,rgba(8,8,10,.82) 38%,rgba(8,8,10,0) 100%);
}
/* Texto 100% más grande en escritorio (pedido explícito). El degradado de
   arriba ya está en % sobre la propia caja del pie, así que al crecer el
   padding/line-height la sigue cubriendo entera sin tocarle los stops. */
@media(min-width:821px){
  .deck-cap-over .deck-cap{font-size:28px;padding:18px 18px 46px}
}

/* ---- Slide de portada (imagen a sangre) ---- */
.deck-slide.cover{padding:0;justify-content:flex-end}
.cover-bg{position:absolute;inset:0;z-index:0}
.cover-bg img{width:100%;height:100%;object-fit:cover;display:block}
.cover-bg::after{
  content:"";position:absolute;inset:0;
  background:linear-gradient(180deg,rgba(10,10,12,.30) 0%,rgba(10,10,12,.08) 30%,rgba(10,10,12,.58) 62%,rgba(10,10,12,.95) 100%);
}
.cover-body{position:relative;z-index:1;padding:56px 76px 92px;width:100%;max-width:var(--maxw);margin:0 auto}
.deck-slide.cover h1{
  font-family:var(--ff-display);font-weight:600;letter-spacing:-.02em;line-height:1.03;
  font-size:clamp(34px,5.4vw,68px);margin:0 0 18px;max-width:19ch;
}
/* La portada va SIEMPRE en texto claro, en los dos temas: el fondo no es la
   página sino una foto oscurecida por el degradado de arriba. Heredar --text
   dejaba el título en gris oscuro sobre negro con el tema claro activo. */
.deck-slide.cover h1,
.cover-body .deck-lead{color:#F4F2F7}
.cover-body .deck-eyebrow,
.cover-body .deck-note{color:#C9C6D2}
.deck-slide.cover .deck-lead{max-width:56ch}

/* ---- Slide con imagen de fondo a sangre (mapa, etc.) ----
   Mismo mecanismo que la portada (foto + velo + texto encima) pero reutilizable
   en cualquier slide, no solo la primera. El texto va SIEMPRE en claro, sea cual
   sea el tema activo: el fondo acá nunca es la superficie de la página, es una
   foto oscurecida por el velo, igual que en la portada. */
.deck-slide.has-bg{padding-left:0;padding-right:0}
.slide-bg{position:absolute;inset:0;z-index:0}
.slide-bg img{width:100%;height:100%;object-fit:cover;display:block}
/* El mapa de América es angosto y alto: con "cover" se recortaba casi todo
   el continente para llenar una slide ancha. "contain" lo deja completo,
   ocupando el alto entero (pedido explícito), con la franja oscura del velo
   de sobra a los costados en vez de tapar Canadá/Chile. */
/* object-position a la derecha (pedido explícito), no centrado: deja el mapa
   pegado al borde derecho de la slide en vez de flotando en el medio. */
.slide-bg.contain img{object-fit:contain;object-position:100% 50%}
.slide-bg::after{content:"";position:absolute;inset:0;background:rgba(8,8,10,.66)}
.has-bg .deck-inner{position:relative;z-index:1;padding:0 76px}
.has-bg .deck-eyebrow{color:#C9C6D2}
.has-bg h2,.has-bg .deck-lead{color:#F4F2F7}
/* Translúcidos a propósito: el mapa tiene que seguir viéndose por detrás de las
   cifras (pedido explícito). El desenfoque mantiene el contraste del texto sin
   necesidad de subir la opacidad del fondo. */
.has-bg .deck-stat{background:rgba(16,15,20,.42);border-color:rgba(255,255,255,.16);-webkit-backdrop-filter:blur(9px);backdrop-filter:blur(9px)}
.has-bg .deck-stat .l{color:#D8D5DF}
/* El degradado ámbar sobre blanco (ver más abajo, tema claro) no aplica acá:
   el fondo de esta slide es siempre la foto oscura, nunca la superficie clara. */
.has-bg .deck-stat .v{background:var(--spark)!important;-webkit-background-clip:text!important;background-clip:text!important}

/* ---- Tarjetas dentro de slides ---- */
.deck-card{
  background:var(--surface);border:1px solid var(--line);border-radius:var(--r-md);
  padding:22px;min-width:0;
}
/* overflow-wrap: en la grilla de 4 columnas del proceso, una palabra sin
   espacios ("Assessment") no tiene dónde partir y por default se desborda en
   vez de bajar de línea, silenciosa (sin scroll ni indicio visual, se pierde
   el final). Esto le da un punto de corte cuando no entra. */
.deck-card h3{color:var(--text);overflow-wrap:break-word}
.deck-card p{font-size:14.5px;margin:0}
.deck-card .ic{
  width:42px;height:42px;border-radius:12px;background:var(--spark-soft);
  border:1px solid rgba(255,201,40,.22);display:flex;align-items:center;justify-content:center;
  margin-bottom:14px;color:var(--amber-ink);
}
.deck-card .ic svg{width:21px;height:21px}
.deck-card .num{
  font-family:var(--ff-display);font-weight:700;font-size:15px;color:var(--amber-ink);
  width:42px;height:42px;border-radius:12px;background:var(--spark-soft);
  border:1px solid rgba(255,201,40,.22);display:flex;align-items:center;justify-content:center;
  margin-bottom:12px;
}

/* ---- Cifras ---- */
.deck-stats{display:grid;grid-template-columns:repeat(4,1fr);gap:18px}
.deck-stats.three{grid-template-columns:repeat(3,1fr)}
.deck-stat{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-md);padding:22px}
.deck-stat .v{
  font-family:var(--ff-display);font-weight:700;line-height:1;letter-spacing:-.03em;
  font-size:clamp(26px,3vw,40px);
  background:var(--spark);-webkit-background-clip:text;background-clip:text;color:transparent;
}
.deck-stat .l{
  font-size:11.5px;color:var(--text-3);letter-spacing:.08em;text-transform:uppercase;
  margin-top:10px;font-weight:600;line-height:1.35;
}
/* El gradiente spark sobre blanco da 1.63:1 (docs/design-system.json lo marca
   como "no usar" en texto). Con el tema claro las cifras pasan al ámbar oscuro
   aprobado para texto grande (#B07A00, 3.73:1), que a >=26px cumple AA. */
[data-theme="light"] .deck-stat .v,
[data-theme="light"] .deck-quote .mark,
/* Mismo motivo en los títulos con palabra destacada: sobre la portada el
   degradado va sobre una foto oscura y se lee, pero en una slide normal con
   tema claro quedaría ámbar sobre blanco. La portada queda fuera. */
[data-theme="light"] .deck-slide:not(.cover) .grad-text{
  background:linear-gradient(115deg,#B07A00 0%,#8A6103 100%);
  -webkit-background-clip:text;background-clip:text;
}

/* ---- Cita ---- */
.deck-quote{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-md);padding:24px}
.deck-quote .mark{
  font-family:var(--ff-display);font-size:44px;line-height:.6;margin-bottom:10px;
  background:var(--spark);-webkit-background-clip:text;background-clip:text;color:transparent;
}
.deck-quote p{font-size:15px;color:var(--text)}
.deck-quote .who{font-weight:600;color:var(--text);font-size:14.5px;margin-top:14px}
.deck-quote .role{font-size:13px;color:var(--text-3)}

/* ---- Logos de clientes ---- */
/* 40 marcas: a 5 columnas serían 8 filas y no entran, así que la grilla se
   abre a 8. Un solo archivo por logo, siempre el arte para fondo blanco
   (pedido explícito: se ven mejor que el ajustado a fondo oscuro). Cada
   archivo viene en un lienzo 3:1 uniforme con el logo escalado adentro a la
   MISMA área visual (ver el horneado en scripts/): sin eso, fijar solo la
   altura hacía que un logo ancho como Walmart ocupara 5 veces más tinta que
   uno cuadrado como Tesla. */
.deck-logos{display:grid;grid-template-columns:repeat(8,1fr);gap:16px 14px;align-items:center}
/* El arte asume fondo blanco: en tema claro la propia página YA es blanca
   (--bg:#FFFFFF) y el logo flota libre, pero en oscuro necesita su recuadro
   propio o no se lee. box-sizing:border-box para que el padding entre DENTRO
   del height y las celdas de la grilla salgan todas iguales. */
.deck-logos img{
  width:100%;height:78px;object-fit:contain;box-sizing:border-box;
  /* Gris muy claro en vez de blanco puro (pedido explícito: el contraste
     contra el fondo casi negro de la slide era demasiado fuerte con blanco
     puro). Mismo tono que usa el muro de logos de la web (src/clients.html,
     .sc-has-logo) -- las dos superficies muestran las mismas 40 marcas y se
     ajustaron juntas para que coincidan. */
  background:#E7E7EA;border-radius:var(--deck-r);padding:8px 14px;
  transition:transform .2s;
}
.deck-logos img:hover{transform:scale(1.05)}
/* En claro, el recuadro sobra (blanco sobre blanco): se apaga a los mismos
   valores que tenía cuando no existía el pack a color. */
[data-theme="light"] .deck-logos img{background:none;padding:0;border-radius:0}

/* ---- Botones de navegación ----
   A media altura perdían contraste sobre fotos claras (pedido explícito de
   bajarlos): ahora viven abajo, sobre el mismo degradado oscuro que ya
   garantiza legibilidad al contador y los puntos. */
.deck-arrow{
  position:absolute;bottom:17px;z-index:6;
  width:46px;height:46px;border-radius:var(--r-pill);
  background:var(--veil-2);border:1px solid var(--line-strong);color:var(--text);
  display:flex;align-items:center;justify-content:center;cursor:pointer;
  transition:background .24s,border-color .24s,transform .24s var(--ease);
  -webkit-backdrop-filter:blur(8px);backdrop-filter:blur(8px);
}
.deck-arrow:hover:not(:disabled){background:var(--veil-3);border-color:var(--amber);transform:scale(1.06)}
.deck-arrow:disabled{opacity:.28;cursor:default}
.deck-arrow svg{width:20px;height:20px}
.deck-prev{left:16px}
.deck-next{right:16px}
.deck-arrow:focus-visible{outline:2px solid var(--amber);outline-offset:3px}

/* ---- Barra inferior: contador + puntos ----
   min-height (en vez de dejar que el padding solo determine el alto): las
   flechas de 46px paradas en bottom:17px llegan a los 63px, y el degradado
   tiene que cubrirlas enteras o vuelven a perder contraste arriba. */
.deck-bar{
  position:absolute;left:0;right:0;bottom:0;z-index:5;
  display:flex;align-items:center;justify-content:center;gap:16px;
  padding:12px 76px;min-height:80px;pointer-events:none;
  background:linear-gradient(180deg,transparent,rgba(10,10,12,.55));
}
[data-theme="light"] .deck-bar{background:linear-gradient(180deg,transparent,rgba(255,255,255,.65))}
.deck-dots{display:flex;gap:7px;flex-wrap:wrap;justify-content:center;pointer-events:auto}
.deck-dot{
  width:7px;height:7px;border-radius:var(--r-pill);border:none;padding:0;cursor:pointer;
  background:var(--veil-4);transition:background .24s,width .24s var(--ease);
}
.deck-dot[aria-current="true"]{background:var(--amber);width:20px}
.deck-dot:focus-visible{outline:2px solid var(--amber);outline-offset:3px}
.deck-count{
  font-size:12px;color:var(--text-3);letter-spacing:.1em;font-weight:600;
  font-variant-numeric:tabular-nums;pointer-events:auto;
}

/* ---- Botones (reusa el look de theme.css sin depender de .btn) ---- */
.deck-cta{display:flex;flex-wrap:wrap;gap:12px;margin-top:22px}
.deck-center .deck-cta{justify-content:center}
.deck-cta.cta-end{justify-content:flex-end}
.deck-cta.cta-center{justify-content:center}
.btn-sm{padding:8px 16px;font-size:13.5px}

/* ==========================================================================
   Lupa de foto: tocar una miniatura la abre grande sobre la slide. Se usa en
   las grillas marcadas con [data-lightbox]; el <dialog> lo crea js/deck.js.
   ========================================================================== */
[data-lightbox] .deck-media{cursor:zoom-in}
.lb{
  position:fixed;inset:0;z-index:120;
  display:flex;align-items:center;justify-content:center;
  padding:clamp(16px,4vw,48px);
  background:rgba(6,6,8,.94);-webkit-backdrop-filter:blur(6px);backdrop-filter:blur(6px);
}
.lb[hidden]{display:none}
.lb img{max-width:100%;max-height:100%;object-fit:contain;border-radius:var(--deck-r);display:block}
.lb-cap{
  position:absolute;left:0;right:0;bottom:16px;text-align:center;
  color:#F4F2F7;font-size:14px;font-weight:600;letter-spacing:.04em;
  text-shadow:0 1px 4px rgba(0,0,0,.7);padding:0 20px;
}
.lb-close{
  position:absolute;top:14px;right:14px;
  width:40px;height:40px;border-radius:var(--r-pill);
  background:rgba(255,255,255,.12);border:1px solid rgba(255,255,255,.22);
  color:#F4F2F7;display:flex;align-items:center;justify-content:center;cursor:pointer;
}
.lb-close:hover{background:rgba(255,255,255,.2)}
.lb-close svg{width:18px;height:18px}
.lb-close:focus-visible{outline:2px solid var(--amber);outline-offset:3px}

/* ==========================================================================
   Chrome del sitio en esta página. Es una presentación, no una página del
   sitio: el header se reduce a marca + selectores, sin menú hamburguesa.
   El drawer que abría ese botón era el ÚNICO lugar donde el visitante móvil
   podía cambiar idioma y país (theme.css los oculta del header a 820px), así
   que al sacarlo hay que devolverlos al header o se pierden.
   ========================================================================== */
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .burger,
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .mobile-menu,
/* El selector de idioma sale del header y su lugar lo ocupan compartir y
   descargar (pedido explícito). El idioma sigue resolviéndose solo por
   navegador y la URL de mercado sigue siendo la que decide el país. */
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .nav-inner > .lang-toggle,
/* Con compartir y PDF adentro, el header ya no entra en 1200px (pedía 1237) y
   se recortaba en silencio. El CTA de contacto sale: la última slide del deck
   es exactamente ese botón. */
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .nav-cta,
/* Pedido explícito: sin los links del sitio (Solutions, Technology, etc.) en
   esta página. Es una presentación, no una página para seguir navegando. */
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .nav-links{display:none!important}
:is(body[data-page="why-ennat"], body[data-page="client-deck"]) .nav-inner{gap:22px}

/* ==========================================================================
   Barra de acciones del deck: compartir + PDF. js/deck.js la reubica dentro
   de .nav-inner; la posición absoluta es el respaldo si el JS no corre.
   ========================================================================== */
.deck-tools{
  position:absolute;z-index:7;
  top:calc(var(--nav-h) + 10px);right:16px;
  display:flex;gap:8px;
}
.nav-inner .deck-tools{position:static;top:auto;right:auto;flex:none}
.deck-tool{
  display:inline-flex;align-items:center;gap:7px;
  height:34px;padding:0 13px;border-radius:var(--r-pill);
  background:var(--veil-2);border:1px solid var(--line-strong);color:var(--text);
  font-family:inherit;font-size:12.5px;font-weight:600;cursor:pointer;
  -webkit-backdrop-filter:blur(8px);backdrop-filter:blur(8px);
  transition:background .2s,border-color .2s;
}
.deck-tool:hover{background:var(--veil-3);border-color:var(--amber)}
.deck-tool:focus-visible{outline:2px solid var(--amber);outline-offset:3px}
.deck-tool svg{width:15px;height:15px;flex:none}
.deck-share{position:relative}
.deck-share-menu{
  position:absolute;right:0;top:calc(100% + 8px);min-width:172px;
  background:var(--surface);border:1px solid var(--line-strong);border-radius:var(--r-md);
  padding:6px;display:flex;flex-direction:column;
  box-shadow:0 18px 44px rgba(0,0,0,.42);
}
/* display:flex de arriba le gana al [hidden] de la hoja del navegador (una
   clase pesa más que el selector de atributo del UA), así que el menú hay que
   volver a apagarlo explícitamente. */
.deck-share-menu[hidden]{display:none}
.deck-share-menu a,.deck-share-menu button{
  padding:9px 12px;border-radius:9px;font-size:13.5px;font-family:inherit;
  color:var(--text);background:none;border:none;text-align:left;cursor:pointer;
}
.deck-share-menu a:hover,.deck-share-menu button:hover{background:var(--veil-2)}

/* ==========================================================================
   Esquemas comparables: dos versiones del mismo dibujo y una lupa sobre la
   zona central. Las dos versiones se apilan en la misma caja (position
   absolute) para que cambiar de una a otra no mueva el layout de la slide.
   ========================================================================== */
.dg-stage{
  position:relative;--zx:50%;--zy:50%;--px:0px;--py:0px;
  /* Estas slides llevan poco texto, así que el esquema puede reservar menos
     alto que una foto con pie y quedarse con el resto de la pantalla. */
  max-height:max(160px,calc(100vh - var(--nav-h) - 210px));
  max-height:max(160px,calc(100dvh - var(--nav-h) - 210px));
}
.dg-stage .dg-view{
  position:absolute;inset:0;width:100%;height:100%;
  transform-origin:var(--zx) var(--zy);
  transition:transform .32s var(--ease);
}
.deck-diagram.zoomed .dg-stage{cursor:grab;touch-action:none}
.deck-diagram .dg-stage{cursor:zoom-in}
/* --px/--py los mueve js/deck.js mientras se arrastra; sin transición para que
   el dibujo siga al dedo en vez de ir detrás. */
.deck-diagram.zoomed .dg-view{transform:translate(var(--px),var(--py)) scale(2.15);transition:none}
.dg-tools{display:flex;align-items:center;justify-content:flex-end;gap:10px;margin-top:10px}
.dg-zoom{
  display:inline-flex;align-items:center;gap:6px;
  background:none;border:1px solid var(--line);border-radius:var(--r-pill);
  color:var(--text-3);font-family:inherit;font-size:12px;font-weight:600;
  padding:6px 12px;cursor:pointer;
}
.dg-zoom svg{width:14px;height:14px}
.dg-zoom:focus-visible{outline:2px solid var(--amber);outline-offset:2px}
.dg-zoom[aria-pressed="true"]{border-color:var(--amber);color:var(--amber-ink)}

/* ==========================================================================
   Video (slide de acero + caucho). El archivo lo elige js/deck.js.
   ========================================================================== */
.deck-videobox{aspect-ratio:16/9;background:#000}
.deck-video{width:100%;height:100%;object-fit:cover;display:block}

/* Simulador de impacto PB100 (slides 6a y 6b). En la misma caja conviven dos
   piezas y sólo se ve una por medio: en PANTALLA el iframe con el visor 3D en
   vivo, en PAPEL la foto multiexposición. El intercambio está en @media print,
   al final del archivo.
   Por qué no alcanza con el iframe: el PDF lo imprime Chromium headless con
   1500 ms de espera (scripts/deck-pdf.mjs) y el visor tiene que bajar three.js,
   el .glb y el HDR — no llega ni cerca. Y una animación en una hoja necesita
   un cuadro elegido, no el que toque. Ver el comentario de esas dos slides en
   src/why-ennat.html. */
.deck-sim{aspect-ratio:16/9;background:#000}
.deck-sim .deck-sim-live{width:100%;height:100%;border:0;display:block}
.deck-sim .deck-sim-print{display:none}

/* ==========================================================================
   Casos de éxito: encabezado con logo del cliente, foto y columna de cifras.
   ========================================================================== */
.case-head{display:flex;align-items:flex-start;justify-content:space-between;gap:22px}
/* Las marcas de cliente vienen en archivos monocromos de densidad muy distinta
   (el wordmark de Tesla es finito, el de CAT macizo). brightness(0)+invert las
   lleva a todas a un blanco parejo en vez de dejar que cada una salga con su
   propio gris. */
.case-logo{
  height:58px;width:auto;max-width:300px;object-fit:contain;flex:none;margin-top:0;
  filter:brightness(0) invert(1);opacity:.92;
}
[data-theme="light"] .case-logo{filter:brightness(0);opacity:.78}
.case-body{display:grid;grid-template-columns:1fr 1fr;gap:28px;align-items:start;margin-top:8px}
.case-side{display:flex;flex-direction:column;gap:12px;min-width:0}
.case-quote{padding:16px}
.case-quote p{font-size:14px;line-height:1.5;margin:0}
.case-lead{font-size:14.5px;margin:0}
/* Pedido explícito: el botón alineado con el pie de la FOTO, no flotando
   donde termine el texto. stretch (no "end") mantiene el arranque en común
   de foto y case-side pegado arriba (sin este cambio "end" corriría todo el
   bloque de texto hacia abajo dejando un hueco arriba) y solo reparte el
   sobrante de alto en la fila; .case-side ya es flex column, así que el
   margin-top:auto de .cta-bottom (en el HTML) hace el resto. La foto no
   necesita ayuda: su img ya cubre el 100% de su caja (object-fit:cover), así
   que estirarla no deja letterbox, solo recorta un poco distinto. */
@media(min-width:821px){
  .case-body{align-items:stretch}
}

/* ==========================================================================
   Extracto del ROI: costo total a 5 años, metal contra ENNAT.
   Las dos barras comparten escala (metal = 100%), así el largo ES el dato.
   ========================================================================== */
.tco{display:grid;grid-template-columns:minmax(0,.95fr) minmax(0,2fr);gap:26px;align-items:center;margin-top:14px}
/* Foto del producto exacto del que salen las cifras: sin esto, "$155,750" se
   lee como el costo de un proyecto entero y no de UNA barrera. */
.tco-shot{margin:0;text-align:center}
/* 170px la dejaba mucho más chica que cualquier otra foto única del deck
   (la de orden de sitio, el sello de garantía, el cierre): pedido explícito
   de consistencia de tamaño entre slides con una sola foto protagonista. */
.tco-shot img{width:100%;height:auto;max-height:300px;object-fit:contain;display:block}
.tco-shot figcaption{font-size:12px;color:var(--text-3);margin-top:8px;letter-spacing:.04em}
/* Mismo formato "tarjeta" que las fotos de los success case (bordes
   redondeados, marco, cover) en vez del recorte suelto de antes. En
   escritorio además se estira al alto de .tco-bars (ver [aria-label="14"]
   .tco más abajo) para que el CTA de fuera del grid quede a la altura de
   la foto, no de donde termine el texto. */
@media(min-width:821px){
  .tco-shot-media{
    flex:1 1 auto;min-height:0;border-radius:var(--deck-r);
    overflow:hidden;border:1px solid var(--line);
  }
  .tco-shot-media img{width:100%;height:100%;object-fit:cover;max-height:none;display:block}
  body[data-page="why-ennat"] [aria-label="14"] .tco{align-items:stretch}
  body[data-page="why-ennat"] [aria-label="14"] .tco-shot{display:flex;flex-direction:column;height:100%}
}
.tco-row{display:grid;grid-template-columns:118px 1fr;gap:12px;align-items:center;margin-bottom:10px}
.tco-k{font-size:11.5px;letter-spacing:.06em;text-transform:uppercase;color:var(--text-2);font-weight:600;line-height:1.25}
.tco-track{
  position:relative;height:46px;border-radius:var(--r-sm);
  background:var(--veil-2);border:1px solid var(--line);overflow:hidden;
}
.tco-fill{height:100%}
/* Relleno sólido, no un gris apenas más claro que la pista: la barra del metal
   está al 100% y con el gris anterior se leía como una pista VACÍA al lado de
   la de ENNAT, que sí se veía llena de ámbar. */
.tco-fill.metal{background:linear-gradient(90deg,#8E8A98 0%,#6A6675 100%)}
[data-theme="light"] .tco-fill.metal{background:linear-gradient(90deg,#9E9AA8 0%,#7C7887 100%)}
.tco-fill.ennat{background:var(--spark)}
.tco-v{
  position:absolute;right:14px;top:50%;transform:translateY(-50%);
  font-family:var(--ff-display);font-weight:700;font-size:18px;color:var(--text);
  font-variant-numeric:tabular-nums;
}
/* Sobre el relleno oscuro del metal el texto va claro sí o sí, también en tema
   claro, donde --text es casi negro. */
.tco-row:first-child .tco-v{color:#F4F2F7}
.tco-legend{font-size:12.5px;color:var(--text-3);margin-top:8px;line-height:1.5;max-width:64ch}
.tco-kpis{grid-template-columns:repeat(2,1fr);margin-top:12px;max-width:380px}

/* ==========================================================================
   Catálogo: grilla de fichas. Las filas se reparten el alto disponible
   (grid-auto-rows:1fr + object-fit:contain), así la grilla llena la slide
   en vez de dejar media pantalla vacía.
   ========================================================================== */
.cat-head{display:flex;align-items:flex-end;justify-content:space-between;gap:22px;margin-bottom:14px;flex:0 0 auto}
.cat-grid{display:grid;grid-template-columns:repeat(6,1fr);gap:10px;grid-auto-rows:1fr;min-height:0;flex:1 1 auto}
.cat-grid img{width:100%;height:100%;object-fit:contain;min-height:0;display:block}
/* .deck-fill: la slide deja de centrar su contenido y se lo entrega entero, para
   que una grilla pueda repartirse el alto real (grid-auto-rows:1fr necesita que
   la caja TENGA un alto; sin esto crecía con el contenido y se salía). */
.deck-fill{display:flex;flex-direction:column;min-height:0;flex:1 1 auto}

/* ==========================================================================
   Sello de la promesa de confiabilidad (arte original de marca).
   ========================================================================== */
.promise-wrap{display:flex;align-items:center;justify-content:center}
/* +15% (pedido explícito): 300px×58vw -> 345px×66.7vw. */
.promise-img{width:min(345px,66.7vw);aspect-ratio:1;flex:none}
.promise-img img{width:100%;height:100%;object-fit:contain;display:block}

/* ==========================================================================
   Firma de marca sobre la foto de cierre: logo + lema centrados, con el mismo
   velo degradado que la portada para que se lean sea cual sea la parte de la
   foto que quede detrás. Texto siempre claro: el fondo es una foto oscurecida,
   nunca la superficie de la página (igual criterio que .cover-body/.has-bg).
   ========================================================================== */
.deck-signoff{position:relative}
.deck-signoff::after{
  content:"";position:absolute;left:0;right:0;bottom:0;height:58%;z-index:1;
  border-radius:0 0 var(--deck-r) var(--deck-r);pointer-events:none;
  background:linear-gradient(180deg,rgba(8,8,10,0) 0%,rgba(8,8,10,.82) 100%);
}
.signoff-mark{
  position:absolute;left:0;right:0;bottom:22px;z-index:2;
  display:flex;flex-direction:column;align-items:center;gap:9px;padding:0 20px;
}
.signoff-logo{height:26px;width:auto;display:block}
.signoff-tag{
  font-size:11.5px;font-weight:600;letter-spacing:.16em;text-transform:uppercase;
  color:#F4F2F7;text-shadow:0 1px 4px rgba(0,0,0,.6);
}

/* ==========================================================================
   Ajustes puntuales de tamaño en un par de slides (pedido explícito: las
   fotos de daños y el diagrama de bases expuestas se veían chicas). Ambas
   llevan poco texto arriba, así que pueden darse un presupuesto de alto más
   generoso que el genérico de .deck-media/.dg-stage.
   ========================================================================== */
/* La fila de 4 anchas quedaba chica porque el ancho de columna (no el alto)
   era lo que la limitaba: a 4-por-fila, el 4:3 de cada una da una caja baja
   aunque sobre media slide de alto libre debajo. 2x2 en vez de 4x1 en
   escritorio también (mobile ya lo hace) reparte ese ancho extra en alto.
   El max-height va en la GRILLA entera (grid-auto-rows:1fr reparte ese
   presupuesto entre las dos filas) y no en cada foto: puesto en cada .deck-media
   por separado no se entera de que hay una segunda fila debajo y las dos
   juntas se salían de la slide en portátiles comunes (1366x768, 1440x900). */
/* minmax(0,1fr), no 1fr a secas: una fila de grid sin ese piso en 0 no encoge
   por debajo del contenido (la foto "empuja" su fila alta), la misma trampa
   que min-height:0 en flexbox documentada arriba para el rewrite de mobile. */
/* Ancho/alto en @media(min-width:821px): "25% más chico" es un pedido de la
   versión de escritorio en particular; mobile ya tiene su propio rewrite de
   .deck-quad-2x2 (gap, columnas, flex) y no toca max-width/margin, así que
   dejarlo suelto se le hubiera colado también achicándole la grilla. */
@media(min-width:821px){
  body[data-page="why-ennat"] [aria-label="4"] .deck-quad{
    grid-template-columns:repeat(2,1fr);grid-auto-rows:minmax(0,1fr);
    max-width:75%;margin:0 auto;
    max-height:calc(max(240px,(100vh - var(--nav-h) - 210px)) * .75);
    max-height:calc(max(240px,(100dvh - var(--nav-h) - 210px)) * .75);
  }
}
body[data-page="why-ennat"] [aria-label="4"] .deck-figure{min-height:0}
/* aspect-ratio:auto pisa el 4:3 de .deck-quad .deck-media.square: con alto
   fijo Y una proporción fija a la vez, el ancho salía de la proporción, no de
   la columna, y cada foto quedaba angosta con un hueco al lado. object-fit
   sigue recortando parejo sea cual sea la forma final de la celda. */
body[data-page="why-ennat"] [aria-label="4"] .deck-media{width:100%;height:100%;aspect-ratio:auto;min-height:0;max-height:none}
/* El esquema se lleva más ancho que el split-media genérico (.72/1.28) y un
   presupuesto de alto igual de generoso que el de la slide 7 (mismo dg-stage),
   así el dibujo crece en las dos direcciones en vez de solo estirarse angosto.
   .rev reordena con order:-1 (la figura pasa a ubicarse primera), así que acá
   la columna ANCHA tiene que ir PRIMERO en la lista o termina siendo el texto
   el que se lleva el ancho y el dibujo el que se achica — pasó, se vio en capturas. */
body[data-page="why-ennat"] [aria-label="8"] .deck-split{grid-template-columns:minmax(0,1.3fr) minmax(0,.7fr)}
body[data-page="why-ennat"] [aria-label="8"] .dg-stage{max-height:max(160px,calc(100vh - var(--nav-h) - 170px));max-height:max(160px,calc(100dvh - var(--nav-h) - 170px))}

@media(min-width:821px){
  /* Vertical en vez de 16:9 (pedido explícito): mismo criterio que en móvil,
     donde este video ya se sirve en 9:16 (ver js/deck.js). width:fit-content
     porque un div de bloque con aspect-ratio, sin esto, igual se estira al
     ancho completo de la columna y da un rectángulo horizontal enorme en vez
     de vertical; con fit-content el ancho sale del alto vía la proporción. */
  body[data-page="why-ennat"] [aria-label="6"] .deck-videobox{
    aspect-ratio:9/16;width:fit-content;margin:0 auto;
    height:min(560px,calc(100vh - var(--nav-h) - 160px));
    height:min(560px,calc(100dvh - var(--nav-h) - 160px));
  }

  /* Mismo mecanismo que en casos/TCO: stretch mantiene texto y sello
     arrancando juntos arriba y el CTA (cta-bottom en el HTML) se pega al pie
     de esa fila, que ahora coincide con el pie del badge. align-items:end en
     vez de stretch en .promise-wrap porque el sello es de tamaño fijo (no
     cubre su caja como una foto): sin este flex-end quedaría centrado
     verticalmente en la columna estirada, con un hueco debajo antes del CTA. */
  body[data-page="why-ennat"] [aria-label="17"] .deck-split{align-items:stretch}
  body[data-page="why-ennat"] [aria-label="17"] .deck-split>div:first-child{display:flex;flex-direction:column;height:100%}
  body[data-page="why-ennat"] [aria-label="17"] .promise-wrap{align-items:flex-end}

  /* La 18 pasa de dos columnas a una pila centrada (pedido explícito): foto
     arriba, título abajo, y el botón cerca del texto en vez de pegado al pie
     de la slide como antes. */
  body[data-page="why-ennat"] [aria-label="18"] .deck-split{
    display:flex;flex-direction:column;gap:26px;max-width:640px;margin:0 auto;
    height:auto;text-align:center;
  }
  /* En laptops bajos (720p/768p) la pila completa (foto 16:9 a 640px de ancho
     + título + bajada + botón) no entraba por unos px: el ancho se mantiene
     (lo fija el flex column de arriba) y el sobrante de alto se recorta con
     cover, sin dejar la foto angosta. Ojo al tocar el copy: el título está
     medido para entrar en DOS líneas en los dos idiomas a 46px sobre 640px
     de ancho; una tercera línea son ~48px que a 720p ya no hay de dónde
     sacar (la foto acá ya está en su mínimo). */
  body[data-page="why-ennat"] [aria-label="18"] .deck-media{
    max-height:min(360px,calc(100vh - var(--nav-h) - 390px));
    max-height:min(360px,calc(100dvh - var(--nav-h) - 390px));
  }
  body[data-page="why-ennat"] [aria-label="18"] .deck-eyebrow{justify-content:center}
  body[data-page="why-ennat"] [aria-label="18"] .deck-cta{margin-top:0}
}

/* ==========================================================================
   Utilidades de composición usadas por varias slides.
   ========================================================================== */
/* Fuerza las cifras a UNA fila, también en móvil (donde .deck-stats cae a 2
   columnas por defecto). Pedido explícito para los KPI de experiencia, casos
   y garantía. Se hace pasando la caja a flex: así el grid-template-columns de
   los breakpoints queda inerte sin tener que pelearlo con !important, y el
   gap que ya define .deck-stats se sigue aplicando igual. */
.deck-stats-row{display:flex}
.deck-stats-row>*{flex:1 1 0;min-width:0}
/* Dentro de una slide centrada la fila se encoge al contenido y las cajas
   quedan más angostas que la slide (en 320px daban 56px y "PROYECTOS" pedía
   64): ocupa todo el ancho disponible. */
.deck-center .deck-stats-row{width:100%}
/* Red de seguridad: una etiqueta de una sola palabra más ancha que su caja se
   desbordaba en silencio, sin scroll ni indicio visual. */
.deck-stat .l,.deck-stat .v{overflow-wrap:break-word}
/* Tres cifras compartiendo un ancho parten de cajas mucho más angostas que la
   grilla de cuatro para la que se calibró .deck-stat .v: con el tamaño de allá,
   "+416%" se salía de su caja. Acá se escala con el ancho de la caja. */
.deck-stats-row .deck-stat{padding:16px 12px;text-align:center}
.deck-stats-row .deck-stat .v{font-size:clamp(21px,2.1vw,30px)}
.deck-stats-row .deck-stat .l{font-size:10.5px;letter-spacing:.06em}

/* Las slides marcadas para un solo ancho: la comparación metal/caucho va junta
   en escritorio y separada en dos slides en móvil, donde lado a lado no se lee.
   El deck se cuenta y se navega SOLO sobre las visibles (ver js/deck.js). */
@media(max-width:820px){.deck-slide[data-viewport="wide"]{display:none}}
@media(min-width:821px){.deck-slide[data-viewport="narrow"]{display:none}}

/* ==========================================================================
   Responsive. 820px es el corte del sitio: abajo de ahí el deck cambia de
   comportamiento (una columna, flechas compactas), no solo de tamaño.
   ========================================================================== */
@media(max-width:1100px){
  .deck-slide{padding:calc(var(--nav-h) + 22px) 62px 42px}
  .cover-body{padding:44px 62px 84px}
  .deck-bar{padding:12px 62px}
  .deck-split{gap:36px}
  .deck-quad{grid-template-columns:repeat(2,1fr)}
  .deck-logos{grid-template-columns:repeat(6,1fr);gap:10px 8px}
  .case-body{gap:20px}
  .tco{gap:18px}
  .cat-grid{gap:8px}
}

/* ==========================================================================
   MÓVIL: cada slide tiene que entrar completa, sin scroll (pedido explícito:
   se navega con flechas o deslizando, no leyendo hacia abajo). La técnica es
   flex, no un porcentaje de pantalla fijo: el bloque de texto mide lo que
   necesita (flex:0 0 auto) y la imagen se queda con TODO lo que sobra
   (flex:1 1 auto), así se adapta sola a cuánto texto tenga cada slide.
   min-height:0 en cada nivel es obligatorio: sin eso flexbox no deja encoger
   por debajo del contenido intrínseco y la imagen fuerza el alto de todo lo
   demás (el clásico "flexbox no encoge").
   ========================================================================== */
@media(max-width:820px){
  /* El header de esta página se encoge: marca chica, sin bajada, sin
     hamburguesa. Los 18px que libera se los queda el contenido de cada slide,
     que es lo escaso en un teléfono. */
  :is(body[data-page="why-ennat"], body[data-page="client-deck"]){--nav-h:56px}
  :is(body[data-page="why-ennat"], body[data-page="client-deck"]) .nav-inner{gap:10px;padding:0 14px}
  :is(body[data-page="why-ennat"], body[data-page="client-deck"]) .brand img{height:17px}
  :is(body[data-page="why-ennat"], body[data-page="client-deck"]) .brand .tag{display:none}
  :is(body[data-page="why-ennat"], body[data-page="client-deck"]) .theme-toggle{width:30px;height:30px}

  .deck-tools{top:calc(var(--nav-h) + 6px);right:10px;gap:6px}
  .deck-tool{height:29px;padding:0 10px;font-size:11.5px;gap:5px}
  .deck-tool svg{width:13px;height:13px}

  /* Ya no hay barra flotante bajo la nav (las acciones viven dentro de ella),
     así que el contenido puede arrancar justo debajo del header. */
  .deck-slide{
    padding:calc(var(--nav-h) + 10px) 16px 60px;
    overflow:hidden;                 /* pedido explícito: nada de scroll */
    justify-content:flex-start;
  }
  .deck-slide.cover{padding-top:0}
  .deck-inner{height:100%;display:flex;flex-direction:column;min-height:0}
  /* Las slides centradas (logos, mapa) no llenan el alto: sin esto el contenido
     se apilaba arriba y dejaba media pantalla vacía debajo. */
  .deck-inner.deck-center{justify-content:center}
  .has-bg .deck-inner{height:auto;justify-content:center;flex:1 1 auto;padding:0 16px}

  /* Texto+imagen: se apilan, la imagen se lleva el espacio que el texto deja
     libre. La imagen SIEMPRE primero: es lo que ancla la slide de un vistazo. */
  .deck-split,.deck-split.rev{
    display:flex;flex-direction:column;gap:12px;align-items:stretch;
    flex:1 1 auto;min-height:0;
  }
  .deck-split.split-media{gap:12px}
  .deck-split>div:first-child{flex:0 0 auto}
  .deck-split .deck-figure{order:-1;flex:1 1 auto;min-height:0;display:flex;flex-direction:column}
  .deck-split .deck-media{flex:1 1 auto;min-height:0;height:auto;max-height:none}
  .deck-split .deck-cap{flex:0 0 auto}

  /* Dos imágenes lado a lado (nunca apiladas: sería el doble de alto) reciben
     el mismo tratamiento: una fila que se lleva el espacio libre. */
  .deck-duo{
    grid-template-columns:1fr 1fr;gap:12px;
    flex:1 1 auto;min-height:0;
  }
  .deck-duo .deck-figure{min-height:0;display:flex;flex-direction:column}
  .deck-duo .deck-media{flex:1 1 auto;min-height:0;height:auto;max-height:none}
  .deck-duo .deck-cap{flex:0 0 auto;font-size:11px}

  /* Grillas de tarjetas chicas (proceso) o de miniaturas (costos, instalaciones):
     no compiten por el espacio sobrante, se dimensionan solas y compactas. */
  .deck-trio{grid-template-columns:repeat(3,1fr);gap:10px}
  .deck-quad{grid-template-columns:repeat(4,1fr);gap:8px}
  /* Cuatro fotos en 2x2 en vez de una fila de cuatro: en un teléfono, cuatro
     miniaturas en fila quedan del ancho de un dedo y no se ve el daño. */
  .deck-quad-2x2{grid-template-columns:repeat(2,1fr);grid-auto-rows:1fr;flex:1 1 auto;min-height:0;gap:10px}
  .deck-quad-2x2 .deck-figure{display:flex;flex-direction:column;min-height:0}
  .deck-quad-2x2 .deck-media{flex:1 1 auto;min-height:0;height:auto;max-height:none;aspect-ratio:auto}
  .deck-quad .deck-cap{font-size:10.5px;margin-top:5px;line-height:1.25}

  .deck-stats,.deck-stats.three{grid-template-columns:repeat(2,1fr);gap:10px}
  .deck-stats-row{gap:8px}
  .deck-stat{padding:12px}
  .deck-stat .v{font-size:clamp(20px,5.5vw,28px)}
  .deck-stat .l{font-size:10px;margin-top:5px}
  .deck-stats-row .deck-stat{padding:9px 6px;text-align:center}
  .deck-stats-row .deck-stat .v{font-size:clamp(17px,4.8vw,23px)}
  .deck-stats-row .deck-stat .l{font-size:9px;margin-top:4px;letter-spacing:.05em}
  /* 20 -> 30 (+50%) -> 38 (+25%) -> 46 (+20%): pedidos explícitos sucesivos. */
  /* 40 logos en un teléfono: a 5 columnas son 8 filas. Se achican y se aprieta
     el gap para que el muro entre completo sin scroll. */
  .deck-logos{grid-template-columns:repeat(5,1fr);gap:4px 4px}
  .deck-logos img{height:48px;padding:4px 6px;border-radius:6px}
  .deck-card{padding:12px}
  .deck-card h3{font-size:14.5px}
  .deck-card p{font-size:12.5px}
  .deck-card .num{width:30px;height:30px;font-size:13px;margin-bottom:8px}

  .deck-eyebrow{font-size:11px;margin-bottom:8px}
  .deck-slide h2{font-size:clamp(20px,5.6vw,26px);margin-bottom:8px;line-height:1.1}
  .deck-lead{font-size:13.5px;margin-bottom:8px;line-height:1.4}
  .deck-slide p{font-size:13px;margin-bottom:6px;line-height:1.4}
  .deck-note{font-size:11px;margin-top:8px}
  .deck-quote{padding:16px}
  .deck-quote p{font-size:13px;line-height:1.45}
  .deck-quote .mark{font-size:32px;margin-bottom:4px}
  /* Pedido explícito: en el teléfono todos los botones van a la derecha,
     donde cae el pulgar. Incluye los de las slides centradas. */
  .deck-cta,.deck-center .deck-cta{margin-top:12px;gap:8px;justify-content:flex-end}

  /* ---- Esquemas: la barra de herramientas no compite por el alto ---- */
  .dg-tools{margin-top:8px;flex:0 0 auto}
  .dg-zoom{font-size:11px;padding:5px 10px}
  .deck-diagram{display:flex;flex-direction:column;min-height:0;justify-content:center}
  /* El dibujo es apaisado y el hueco que le queda en un teléfono es vertical:
     si el lienzo se lleva TODO el alto libre, el esquema queda chico en medio de
     una plancha blanca. Se le fija una proporción cercana a la del dibujo y el
     resto del espacio se reparte arriba y abajo. */
  .deck-diagram .dg-stage{flex:0 1 auto;min-height:0;aspect-ratio:16/11;max-height:100%}

  /* ---- Casos de éxito: foto arriba, cifras y cita debajo ---- */
  .case-head{gap:12px;flex:0 0 auto;align-items:center}
  /* 22px -> 44px: pedido explícito de duplicar el logo del cliente. */
  .case-logo{height:34px;max-width:150px;margin-top:0}
  .case-body{
    display:flex;flex-direction:column;gap:10px;margin-top:6px;
    flex:1 1 auto;min-height:0;
  }
  .case-body .deck-figure{flex:1 1 auto;min-height:0;display:flex;flex-direction:column}
  .case-body .deck-media{flex:1 1 auto;min-height:0;height:auto;max-height:none;aspect-ratio:auto}
  .case-side{flex:0 0 auto;gap:8px;height:auto}
  .case-quote{padding:10px 12px}
  .case-quote p{font-size:11.5px;line-height:1.4}
  .case-quote .who{font-size:12px;margin-top:6px}
  .case-quote .role{font-size:10.5px}
  .case-lead{font-size:12px}
  .case-side .deck-cta{margin-top:0}

  /* ---- Costo total: foto chica arriba, barras debajo ---- */
  .tco{display:flex;flex-direction:column;gap:10px;margin-top:8px}
  .tco-shot img{max-height:78px}
  .tco-shot figcaption{font-size:10.5px;margin-top:4px}
  .tco-row{grid-template-columns:86px 1fr;gap:9px;margin-bottom:8px}
  .tco-k{font-size:10px;letter-spacing:.03em}
  .tco-track{height:36px}
  .tco-v{font-size:15px;right:10px}
  .tco-legend{font-size:10.5px;line-height:1.4;margin-top:4px}
  .tco-kpis{margin-top:8px;max-width:none}

  /* ---- Pie sobre foto ---- */
  /* margin:0 otra vez: la regla de .deck-quad .deck-cap de más arriba le
     mete margin-top y a un pie absoluto eso lo baja, dejando ver una
     franja de foto por encima del degradado. */
  .deck-cap-over .deck-cap{font-size:12.5px;padding:8px 9px 20px;margin:0}

  /* ---- Sello ---- */
  .promise-img{width:min(200px,54vw)}

  /* ---- Catálogo: 5 por fila (4 filas). Pedido explícito: en vertical entran
     mejor 5 columnas que 6, y las fichas se ven más grandes. ---- */
  .cat-head{gap:12px;margin-bottom:10px;flex:0 0 auto}
  .cat-grid{grid-template-columns:repeat(5,1fr);gap:6px;flex:1 1 auto}


  .deck-slide.cover{justify-content:flex-end;overflow:hidden}
  .cover-body{padding:20px 16px 68px}
  .deck-slide.cover h1{font-size:clamp(24px,7vw,32px);margin-bottom:8px}
  .deck-slide.cover .deck-lead{font-size:14px}

  /* Las flechas son absolutas y se superponían al texto: con 16px de padding
     lateral, una flecha de 38px en left:8px invade la columna de contenido.
     Bajan al pie, en fila con el contador, donde además caen bajo el pulgar. */
  .deck-arrow{
    width:36px;height:36px;
    top:auto;bottom:10px;transform:none;
  }
  .deck-arrow:hover:not(:disabled){transform:none}
  .deck-arrow svg{width:16px;height:16px}
  .deck-prev{left:12px}
  .deck-next{right:12px}
  /* Deja libres los 48px que ocupa cada flecha ahora que viven en esta fila. */
  .deck-bar{padding:8px 58px;gap:10px;min-height:56px}
  .deck-dot{width:5px;height:5px}
  .deck-dot[aria-current="true"]{width:14px}
}
@media(max-width:520px){
  .deck-lead{font-size:13px}
  /* Con muchas slides los puntos no entran: se deja solo el contador. */
  .deck-dots{display:none}
}
@media(max-width:360px){
  .deck-quad{gap:6px}
  .deck-eyebrow{margin-bottom:6px}
  .deck-slide h2{font-size:clamp(18px,6vw,23px)}
  /* Tres cifras en fila dejan cajas de ~77px: el espaciado entre letras que
     hace legible la etiqueta en grande acá es justo lo que la desborda
     ("INSTALACIONES" pedía 86px). Se saca el tracking, no la mayúscula. */
  .deck-stats-row .deck-stat .l{font-size:8.5px;letter-spacing:0}
}

/* Altura chica (móvil apaisado): el ancho sobra pero el alto no. Acá el
   ancho SÍ alcanza para más columnas, así que las grillas se abren en vez de
   apilarse, y las cifras/tarjetas se achican en vez de crecer con el texto. */
@media(max-height:480px){
  /* En apaisado el alto es lo único escaso: la barra de acciones se encoge a
     iconos chicos y el contenido arranca 20px antes. */
  .deck-tools{top:calc(var(--nav-h) + 3px);right:8px;gap:5px}
  .deck-tool{height:24px;padding:0 9px;font-size:10.5px;gap:4px}
  .deck-tool svg{width:11px;height:11px}
  .deck-slide{padding-top:calc(var(--nav-h) + 28px);padding-bottom:42px}
  .deck-eyebrow{margin-bottom:5px}
  .deck-slide h2{font-size:clamp(17px,4vw,22px);margin-bottom:5px}
  .deck-lead,.deck-slide p{margin-bottom:4px}
  .deck-bar{min-height:46px;padding:6px 52px}
  .deck-arrow{width:30px;height:30px;bottom:8px}
  /* Mismo criterio para el muro de 40 marcas: en apaisado el ancho sobra, así
     que se abre a 10 columnas (4 filas en vez de 8) y entra en los 375px de
     alto, que a 5 columnas desbordaba por 35px. */
  .deck-logos{grid-template-columns:repeat(10,1fr);gap:4px 5px}
  .deck-logos img{height:34px;padding:2px 4px;border-radius:4px}
  /* Ocho miniaturas todavía apiladas de a 4 no entraban por poco: con este
     ancho de sobra, pasan a 8 en una sola fila. */
  .deck-quad{grid-template-columns:repeat(8,1fr);gap:6px}
  /* En apaisado el ancho sobra: las cuatro fotos vuelven a una sola fila y
     recuperan el alto que la segunda fila les quitaba. */
  .deck-quad-2x2{grid-template-columns:repeat(4,1fr);gap:8px}
  .deck-quad .deck-cap{font-size:9px;margin-top:3px}
  .deck-stat{padding:8px}
  .deck-stat .v{font-size:clamp(16px,4vw,22px)}
  .deck-stat .l{font-size:9px;margin-top:3px}
  .deck-stats,.deck-stats.three{gap:8px}
  .deck-stats-row .deck-stat{padding:6px 4px}
  .deck-stats-row .deck-stat .v{font-size:clamp(14px,3.4vw,19px)}
  .deck-stats-row .deck-stat .l{font-size:8px;margin-top:2px}
  /* Con 375px de alto, el caso vuelve a dos columnas (foto | cifras) y la cita
     se retira: no hay alto para un párrafo y las cifras dicen lo mismo. */
  .case-head{gap:10px}
  .case-body{display:grid;grid-template-columns:1.05fr 1fr;gap:12px;margin-top:2px;flex:1 1 auto;min-height:0}
  .case-body .deck-figure{min-height:0}
  /* Proporción fija: las fotos de los tres casos vienen en formatos distintos
     (16:9, 4:3, 21:9) y con alto libre la de 4:3 estiraba la slide 77px de más.
     El recorte lo hace object-fit, no el alto de la slide. */
  .case-body .deck-media{aspect-ratio:16/9;flex:0 0 auto;height:auto;max-height:none}
  .case-quote{display:none}
  .case-logo{height:24px;max-width:110px}
  .cat-grid{grid-template-columns:repeat(9,1fr);gap:5px}
  /* Vuelve a dos columnas: apilado no entra, y acá el ancho sobra. */
  .tco{display:grid;grid-template-columns:.7fr 1.6fr 1fr;gap:12px;margin-top:4px}
  .tco-legend{font-size:9.5px;margin-top:4px}
  .tco-kpis{margin-top:6px}
  .tco-track{height:30px}
  .tco-v{font-size:13px}
  .tco-row{margin-bottom:6px}
  .promise-img{width:min(140px,28vw)}
  .dg-tools{margin-top:5px}
}

/* ==========================================================================
   CTA pegado abajo del todo (pedido explícito: todos los botones de cierre de
   slide, a la altura más baja posible). Clase aparte en vez de calzarlo en
   .deck-cta a secas, y declarada acá, después de TODOS los @media de arriba:
   así, ante un empate de especificidad (una sola clase de cada lado), esta
   gana siempre por orden de aparición — incluido sobre el margin-top:12px
   fijo que .deck-cta ya trae en el bloque mobile de más arriba. Requiere que
   el contenedor ya ocupe el alto completo de su columna: hoy en escritorio
   solo la 18 cumple eso (ver su regla más abajo); el resto de las slides que
   todavía llevan esta clase volvieron a centrado vertical y la dejan
   inerte a propósito.

   El padding-top es el PISO de esa separación, y va aparte del margin porque
   margin-top:auto no puede ser las dos cosas: cuando la columna no tiene
   espacio libre —el caso de la 17 en un teléfono— el auto resuelve a 0 y el
   botón quedaba pegado a la fila de cifras, sin ningún aire (medido: 0 px). */
.cta-bottom{margin-top:auto;padding-top:14px}

@media(prefers-reduced-motion:reduce){
  .deck-track{transition:none}
  .deck-arrow,.deck-dot{transition:none}
}

/* ==========================================================================
   Impresión / "Descargar PDF". El botón de la barra de acciones llama a
   window.print(): no hay un PDF guardado que mantener sincronizado, lo que
   se baja es SIEMPRE la presentación tal como está publicada.
   El carrusel se desarma: las slides dejan de ser una fila desplazada y
   pasan a ser una por página.
   ========================================================================== */
@media print{
  /* Sin margen de página: cada slide ocupa la hoja entera y trae su propio
     padding, igual que en pantalla. */
  @page{size:A4 landscape;margin:0}
  /* La presentación se imprime OSCURA, como se ve. Sin esto el navegador
     descarta los fondos y quedaba texto claro sobre papel blanco (ilegible). */
  /* El velo de la portada y el de la slide con mapa son ::after con un
     degradado: sin esta regla el navegador los descarta al imprimir y el título
     blanco quedaba sobre la parte clara de la foto, ilegible. El selector
     universal es a propósito, para no ir enumerando pseudo-elementos. */
  *,*::before,*::after{
    -webkit-print-color-adjust:exact!important;print-color-adjust:exact!important;
  }
  .nav,.mobile-menu,.footer,.deck-arrow,.deck-bar,.deck-tools,.dg-tools,
  .swap-hint,.swap-toast,.swap-tip{display:none!important}
  /* Slides 6a/6b: el visor 3D en vivo se cambia por la foto multiexposición
     (ver .deck-sim más arriba). La caja suelta el 16/9 y el recorte de
     .deck-media img: la foto es casi cuadrada y con object-fit:cover saldría
     recortada, y encerrada en la franja 16/9 quedaría chica en vez de usar el
     alto de la hoja. */
  .deck-sim{
    aspect-ratio:auto!important;background:none!important;border:none!important;
    display:flex!important;align-items:center;justify-content:center;
    max-height:none!important;
  }
  .deck-sim .deck-sim-live{display:none!important}
  .deck-sim .deck-sim-print{
    display:block!important;width:auto!important;height:auto!important;
    max-width:100%!important;max-height:100%!important;object-fit:contain!important;
  }
  html,body{height:auto!important;overflow:visible!important;background:var(--bg)!important}
  .deck{height:auto!important;overflow:visible!important;background:var(--bg)!important}
  .deck-track{display:block!important;transform:none!important;height:auto!important}
  .deck-slide{
    display:flex!important;width:100%!important;
    height:100vh!important;min-height:0!important;
    justify-content:center!important;overflow:hidden!important;
    padding:12mm 14mm!important;
    break-after:page;page-break-after:always;break-inside:avoid;page-break-inside:avoid;
  }
  .deck-slide:last-child{break-after:auto;page-break-after:auto}
  /* En papel no hay "versión móvil": va la comparación completa, no las dos
     slides sueltas que la reemplazan en pantalla chica. */
  .deck-slide[data-viewport="narrow"]{display:none!important}
  .deck-slide[data-viewport="wide"]{display:flex!important}
  /* El justify-content:center de arriba también alcanzaba a la portada y le
     subía el título al medio de la foto, justo donde el velo es más claro. */
  .deck-slide.cover{padding:0!important;justify-content:flex-end!important}
  .cover-bg,.slide-bg{position:absolute!important}
  /* En papel el velo de la portada va más cargado abajo que en pantalla: sin
     retroiluminación, el blanco del título sobre la foto pierde contraste. */
  /* En pantalla la portada es alta y el texto cae en la franja más oscura del
     velo; en A4 apaisado la proporción cambia y quedaba sobre el piso claro.
     En vez de adivinar porcentajes, el bloque de texto lleva su propio fondo:
     el contraste deja de depender de qué parte de la foto le toque debajo. */
  /* Color PLANO, no degradado: al exportar a PDF, Chrome descarta los
     linear-gradient de fondo (comprobado: un rojo sólido en la misma regla sí
     se imprime, el mismo degradado no) y el título quedaba sobre el piso claro
     de la foto. En papel se lee como una banda de pie, que es exactamente lo
     que una portada de deck impresa suele llevar. */
  .deck-slide.cover .cover-body{
    background:rgba(9,9,11,.92);
    padding-top:40px!important;padding-bottom:40px!important;
  }
  .deck-media{max-height:none!important}
  .deck-slide[inert]{opacity:1!important}
  .dg-view{position:absolute!important;transform:none!important}
  .dg-view[hidden]{display:none!important}
  /* El video no se imprime: queda su fotograma de portada. */
  .deck-videobox{background:#000!important}
}

/* ==========================================================================
   client-deck.html (WHY ENNAT de cliente, generado desde el Layout Tool):
   estado de carga/error antes de que existan slides, y el [hidden] que las
   oculta mientras tanto. .deck-track/.deck-arrow/.deck-bar normalmente no
   llevan el atributo hidden -why-ennat.html pinta sus slides directo en el
   HTML-, así que esto es aditivo: no cambia nada en el deck genérico.
   El atributo [hidden] del navegador pesa menos que la regla de clase
   .deck-track{display:flex} de más arriba, así que sin este override
   quedaría con display:flex aunque tenga hidden puesto (mismo problema ya
   resuelto para .roi-state en css/roi.css). */
.deck-track[hidden],.deck-arrow[hidden],.deck-bar[hidden]{display:none}
.deck-state{display:flex;align-items:center;gap:12px;height:100%;padding:0 24px;
  color:var(--text-2);font-size:15px;justify-content:center}
.deck-state[hidden]{display:none}
.deck-state.err{color:var(--text-2);max-width:62ch;margin:0 auto;line-height:1.6;text-align:center}
.deck-state.err .deck-spin{display:none}
.deck-spin{width:16px;height:16px;border-radius:50%;flex:0 0 auto;
  border:2px solid var(--line-strong);border-top-color:var(--amber);
  animation:deck-spin .8s linear infinite}
@keyframes deck-spin{to{transform:rotate(360deg)}}

/* pair-wide slides (client-deck.html, js/why-ennat-deck.js): dos filas completas
   (forma+producto) apiladas -- una forma ancha-y-baja se lee mejor apilada que
   forzada al lado de otra en la misma fila. */
.deck-stack{display:flex;flex-direction:column;gap:24px;width:100%}
.deck-stack .deck-duo{width:100%}

/* Vista de "corte convencional": el mismo glifo en zigzag de breakLineSvg(),
   una vez por cada lado del hueco (nunca una sola línea fingiendo representar
   todo el tramo omitido) -- ver el comentario largo en why-ennat-deck.js. */
.deck-break{flex-shrink:0;background:var(--surface-2)}
.deck-break-wrap-x .deck-break{width:22px}
.deck-break-wrap-y .deck-break{height:22px}
.deck-break-wrap .deck-media{border-radius:0}
/* Redondeo en las puntas EXTERNAS de cada fragmento nada más -- el borde que
   queda pegado al corte se deja recto, para que el zigzag lea como una
   continuación real de la forma y no como dos fotos con marco separadas. */
.deck-break-wrap-x .deck-media:first-child{border-top-left-radius:var(--deck-r);border-bottom-left-radius:var(--deck-r)}
.deck-break-wrap-x .deck-media:last-child{border-top-right-radius:var(--deck-r);border-bottom-right-radius:var(--deck-r)}
.deck-break-wrap-y .deck-media:first-child{border-top-left-radius:var(--deck-r);border-top-right-radius:var(--deck-r)}
.deck-break-wrap-y .deck-media:last-child{border-bottom-left-radius:var(--deck-r);border-bottom-right-radius:var(--deck-r)}
