/* =========================================================================
   NOVOTERRA — Regeneramos el bioma del suelo
   Sistema visual: "El descenso" — el scroll baja por el perfil del suelo.
   ========================================================================= */

/* ---------- 1. Tipografías autoalojadas (latin + latin-ext) ---------- */
@font-face{font-family:'Space Grotesk';font-style:normal;font-weight:500;font-display:swap;src:url('../fonts/SpaceGrotesk-500-normal-latin-ext.woff2') format('woff2');unicode-range:U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;}
@font-face{font-family:'Space Grotesk';font-style:normal;font-weight:500;font-display:swap;src:url('../fonts/SpaceGrotesk-500-normal-latin.woff2') format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;}
@font-face{font-family:'Space Grotesk';font-style:normal;font-weight:700;font-display:swap;src:url('../fonts/SpaceGrotesk-700-normal-latin-ext.woff2') format('woff2');unicode-range:U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;}
@font-face{font-family:'Space Grotesk';font-style:normal;font-weight:700;font-display:swap;src:url('../fonts/SpaceGrotesk-700-normal-latin.woff2') format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;}
@font-face{font-family:'Manrope';font-style:normal;font-weight:400;font-display:swap;src:url('../fonts/Manrope-400-normal-latin-ext.woff2') format('woff2');unicode-range:U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;}
@font-face{font-family:'Manrope';font-style:normal;font-weight:400;font-display:swap;src:url('../fonts/Manrope-400-normal-latin.woff2') format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;}
@font-face{font-family:'Manrope';font-style:normal;font-weight:500;font-display:swap;src:url('../fonts/Manrope-500-normal-latin-ext.woff2') format('woff2');unicode-range:U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;}
@font-face{font-family:'Manrope';font-style:normal;font-weight:500;font-display:swap;src:url('../fonts/Manrope-500-normal-latin.woff2') format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;}
@font-face{font-family:'Manrope';font-style:normal;font-weight:700;font-display:swap;src:url('../fonts/Manrope-700-normal-latin-ext.woff2') format('woff2');unicode-range:U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;}
@font-face{font-family:'Manrope';font-style:normal;font-weight:700;font-display:swap;src:url('../fonts/Manrope-700-normal-latin.woff2') format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;}
@font-face{font-family:'JetBrains Mono';font-style:normal;font-weight:500;font-display:swap;src:url('../fonts/JetBrainsMono-500-normal-latin-ext.woff2') format('woff2');unicode-range:U+0100-02BA,U+02BD-02C5,U+02C7-02CC,U+02CE-02D7,U+02DD-02FF,U+0304,U+0308,U+0329,U+1D00-1DBF,U+1E00-1E9F,U+1EF2-1EFF,U+2020,U+20A0-20AB,U+20AD-20C0,U+2113,U+2C60-2C7F,U+A720-A7FF;}
@font-face{font-family:'JetBrains Mono';font-style:normal;font-weight:500;font-display:swap;src:url('../fonts/JetBrainsMono-500-normal-latin.woff2') format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02BB-02BC,U+02C6,U+02DA,U+02DC,U+0304,U+0308,U+0329,U+2000-206F,U+20AC,U+2122,U+2191,U+2193,U+2212,U+2215,U+FEFF,U+FFFD;}

/* ---------- 2. Tokens ---------- */
:root{
  /* profundidad: cada paso baja por el perfil del suelo */
  --ink:#04120C;
  --soil-950:#050F0A;
  --soil-900:#06170F;
  --soil-850:#081C13;
  --soil-800:#0A1F16;
  --soil-700:#0E2C20;
  --soil-600:#123A2A;

  /* superficie árida (capítulo del desafío) */
  --arid-950:#0E0C09;
  --arid-900:#17130D;
  --arid-800:#221B12;
  --clay:#8A5A2B;

  /* vida */
  --teal-700:#0F5D52;
  --teal-500:#17B58F;
  --green-600:#3E8E41;
  --lime-600:#8FBB2E;
  --lime-500:#A8D33A;
  --lime-400:#C6E85A;

  /* señal (la cadena molecular ámbar del logo) */
  --yellow:#F2C230;
  --amber:#F5A623;
  --amber-600:#F08C1E;

  /* luz */
  --bone:#F4F7F1;
  --bone-2:#E4EDDF;
  --mute:#9FB3A4;
  --mute-2:#7A9080;
  --hair:rgba(200,226,200,.14);
  --hair-2:rgba(200,226,200,.07);

  /* fondo activo — lo cambia el JS al pasar de capítulo */
  --bg:var(--soil-900);
  --fg:var(--bone);

  --wrap:1280px;
  --gut:clamp(1.25rem, 4vw, 4.5rem);

  --ff-display:'Space Grotesk', ui-sans-serif, system-ui, sans-serif;
  --ff-body:'Manrope', ui-sans-serif, system-ui, -apple-system, sans-serif;
  --ff-mono:'JetBrains Mono', ui-monospace, SFMono-Regular, Menlo, monospace;

  /* escala tipográfica fluida — los topes importan en 1920+:
     sin ellos los títulos devoran la pantalla y se pierde lo premium */
  /* titular del hero: contenido en 2 líneas limpias; el máximo anterior
     (5.9rem con tracking -.042em) apelmazaba las letras en pantallas anchas */
  --t-hero:clamp(2.4rem, 4.7vw, 5.15rem);
  --t-h2:clamp(1.95rem, 4.4vw, 3.9rem);
  --t-h2-xl:clamp(2.2rem, 5.3vw, 4.9rem);
  --t-h3:clamp(1.05rem, 1.5vw, 1.3rem);
  --t-body:clamp(1rem, 1.12vw, 1.125rem);
  --t-lead:clamp(1.08rem, 1.55vw, 1.4rem);
  --t-mono:clamp(.66rem, .82vw, .76rem);

  --ease:cubic-bezier(.22,1,.36,1);
  --ease-io:cubic-bezier(.6,0,.2,1);

  --shadow-card:0 2px 4px rgba(0,0,0,.28), 0 12px 28px rgba(0,0,0,.34), 0 42px 80px rgba(0,0,0,.36);
  --radius:18px;
}

/* ---------- 3. Base ---------- */
*,*::before,*::after{box-sizing:border-box}
html{
  -webkit-text-size-adjust:100%;
  scroll-behavior:smooth;
  scroll-padding-top:96px;
}
/* Con el relato WebGL, el suavizado CSS cede el paso: ScrollTrigger asigna
   posiciones de scroll durante refresh() y el suavizado CSS las convierte en
   animaciones que desincronizan las anclas (conflicto conocido de GSAP).
   Los enlaces internos siguen siendo suaves vía scrollIntoView en JS. */
html.has-webgl{scroll-behavior:auto}
body{
  margin:0;
  background:var(--bg);
  color:var(--fg);
  font-family:var(--ff-body);
  font-size:var(--t-body);
  line-height:1.65;
  font-weight:400;
  -webkit-font-smoothing:antialiased;
  -moz-osx-font-smoothing:grayscale;
  overflow-x:hidden;
  transition:background-color 900ms var(--ease-io), color 900ms var(--ease-io);
}
img,picture,svg,canvas{display:block;max-width:100%}
img{height:auto}
[hidden]{display:none !important}
h1,h2,h3,h4,p,ul,ol,figure,blockquote{margin:0}
ul,ol{list-style:none;padding:0}
a{color:inherit;text-decoration:none}
button{font:inherit;color:inherit;background:none;border:0;cursor:pointer}
input,textarea{font:inherit;color:inherit}
::selection{background:var(--lime-500);color:var(--ink)}

:focus-visible{
  outline:2px solid var(--lime-400);
  outline-offset:3px;
  border-radius:4px;
}

.skip-link{
  position:fixed;top:.5rem;left:.5rem;z-index:200;
  padding:.7rem 1.1rem;border-radius:10px;
  background:var(--lime-500);color:var(--ink);
  font-family:var(--ff-mono);font-size:.75rem;font-weight:500;
  transform:translateY(-160%);
  transition:transform .3s var(--ease);
}
.skip-link:focus{transform:translateY(0)}

.wrap{
  width:100%;
  max-width:var(--wrap);
  margin-inline:auto;
  padding-inline:var(--gut);
  position:relative;
  z-index:2;
}

/* ---------- 4. Tipografía ---------- */
.label{
  display:flex;align-items:center;gap:.85rem;
  font-family:var(--ff-mono);
  font-size:var(--t-mono);
  font-weight:500;
  letter-spacing:.22em;
  text-transform:uppercase;
  color:var(--lime-500);
  margin-bottom:clamp(1.4rem,3vw,2.4rem);
}
/* los capítulos ya no van numerados: donde estaba el círculo con el número va
   un filete ámbar, que conserva el acento de color y le da un punto de apoyo
   a la línea en lugar de dejarla suelta contra el margen */
.label::before{
  content:"";flex:none;
  width:clamp(1.5rem,2.6vw,2.4rem);height:1px;
  background:var(--amber);
}
.label--dark{color:var(--green-600)}
.label--dark::before{background:var(--amber-600)}

.eyebrow{
  display:inline-flex;align-items:center;gap:.65rem;
  font-family:var(--ff-mono);font-size:var(--t-mono);font-weight:500;
  letter-spacing:.24em;text-transform:uppercase;color:var(--mute);
}
.eyebrow__dot{
  width:7px;height:7px;border-radius:50%;background:var(--amber);
  box-shadow:0 0 0 4px rgba(245,166,35,.16);
  animation:pip 2.8s var(--ease-io) infinite;
}
@keyframes pip{0%,100%{box-shadow:0 0 0 4px rgba(245,166,35,.16)}50%{box-shadow:0 0 0 9px rgba(245,166,35,0)}}

.h2{
  font-family:var(--ff-display);
  font-weight:700;
  font-size:var(--t-h2);
  line-height:1.02;
  letter-spacing:-.032em;
  text-wrap:balance;
}
.h2--xl{font-size:var(--t-h2-xl)}
.h2--dark{color:var(--green-600)}
.reg{font-size:.42em;vertical-align:.9em;letter-spacing:0;font-weight:500;color:var(--lime-500)}

.h3{
  font-family:var(--ff-display);
  font-weight:700;font-size:var(--t-h3);
  letter-spacing:-.012em;line-height:1.25;
  margin-bottom:.85rem;
}
.h3--spaced{margin-top:2.2rem}

.body{color:var(--mute);max-width:56ch}
.body + .body{margin-top:1rem}
.body strong{color:var(--bone);font-weight:700}
.body em{color:var(--lime-400);font-style:normal}
.body--lead{
  font-size:var(--t-lead);
  line-height:1.5;
  color:var(--bone-2);
  letter-spacing:-.011em;
}

/* Destaca una frase dentro de un párrafo con el naranja del logo (lo pidió la
   clienta para el lead de #soluciones). Solo cambia el color: mantiene peso y
   tamaño para no romper el ritmo de la línea. Sobre los fondos oscuros del
   sitio da ~7.6:1 de contraste, así que cumple AA también como texto normal. */
.accent-amber{color:var(--amber-600)}

.placeholder{
  display:inline-block;
  margin-top:.85rem;
  padding:.4rem .65rem;
  border:1px dashed rgba(242,194,48,.3);
  border-radius:8px;
  background:rgba(242,194,48,.04);
  color:rgba(242,194,48,.75);
  font-family:var(--ff-mono);
  font-size:.6rem;
  line-height:1.55;
  letter-spacing:.03em;
}

/* ---------- 5. Header ---------- */
.site-header{
  position:fixed;inset:0 0 auto 0;z-index:90;
  transition:background-color .5s var(--ease-io), backdrop-filter .5s var(--ease-io), border-color .5s var(--ease-io);
  border-bottom:1px solid transparent;
}
.site-header.is-stuck{
  background:rgba(5,15,10,.72);
  -webkit-backdrop-filter:blur(18px) saturate(1.3);
  backdrop-filter:blur(18px) saturate(1.3);
  border-bottom-color:var(--hair-2);
}
.site-header.is-hidden{transform:translateY(-102%)}
.site-header{transition:transform .45s var(--ease-io), background-color .5s var(--ease-io), backdrop-filter .5s var(--ease-io), border-color .5s var(--ease-io)}

.site-header__inner{
  max-width:var(--wrap);margin-inline:auto;
  padding:clamp(.9rem,1.6vw,1.35rem) var(--gut);
  display:flex;align-items:center;gap:1.5rem;
  justify-content:space-between;
}
.brand{display:block;flex:none}
/* el eslogan es parte del logo: por debajo de ~150px deja de leerse */
.brand__logo{
  width:clamp(150px,13vw,190px);height:auto;
  transition:width .45s var(--ease-io);
}
.is-stuck .brand__logo{width:clamp(132px,11vw,162px)}

.nav{display:flex;align-items:center;gap:clamp(1rem,2.4vw,2.4rem)}
.nav__list{display:flex;align-items:center;gap:clamp(.5rem,1.5vw,1.5rem)}
.nav__link{
  position:relative;
  padding:.4rem 0;
  white-space:nowrap;
  font-size:.84rem;font-weight:500;
  letter-spacing:-.005em;
  color:var(--bone-2);
  opacity:.82;
  transition:opacity .3s var(--ease), color .3s var(--ease);
}
.nav__link::after{
  content:"";position:absolute;left:0;bottom:-1px;
  width:100%;height:1px;background:var(--lime-500);
  transform:scaleX(0);transform-origin:100% 50%;
  transition:transform .45s var(--ease);
}
.nav__link:hover,.nav__link.is-active{opacity:1;color:var(--bone)}
.nav__link:hover::after,.nav__link.is-active::after{transform:scaleX(1);transform-origin:0 50%}
.nav__link.is-active{color:var(--lime-400)}

.nav__tail{display:flex;align-items:center;gap:1rem}
.icon-link{
  display:grid;place-items:center;
  width:38px;height:38px;border-radius:50%;
  border:1px solid var(--hair);
  color:var(--bone-2);
  transition:border-color .35s var(--ease), color .35s var(--ease), transform .35s var(--ease), background-color .35s var(--ease);
}
.icon-link svg{width:17px;height:17px;fill:currentColor}
.icon-link:hover{border-color:var(--lime-500);color:var(--lime-400);transform:translateY(-2px);background:rgba(168,211,58,.07)}

.nav-toggle{
  display:none;
  width:44px;height:44px;
  border:1px solid var(--hair);border-radius:12px;
  position:relative;flex:none;
}
.nav-toggle__bar{
  position:absolute;left:50%;width:19px;height:1.5px;
  background:var(--bone);border-radius:2px;
  transform:translateX(-50%);
  transition:transform .4s var(--ease), opacity .25s var(--ease);
}
.nav-toggle__bar:nth-child(1){top:17px}
.nav-toggle__bar:nth-child(2){top:25px}
.nav-toggle[aria-expanded="true"] .nav-toggle__bar:nth-child(1){transform:translateX(-50%) translateY(4px) rotate(45deg)}
.nav-toggle[aria-expanded="true"] .nav-toggle__bar:nth-child(2){transform:translateX(-50%) translateY(-4px) rotate(-45deg)}

/* ---------- 6. Botones ---------- */
.btn{
  --btn-bg:transparent;
  --btn-fg:var(--bone);
  --btn-bd:var(--hair);
  position:relative;
  display:inline-flex;align-items:center;justify-content:center;gap:.6rem;
  padding:.92em 1.5em;
  border-radius:100px;
  border:1px solid var(--btn-bd);
  background:var(--btn-bg);
  color:var(--btn-fg);
  font-family:var(--ff-body);
  font-size:.9rem;font-weight:700;
  letter-spacing:-.006em;
  line-height:1.15;
  text-align:center;
  overflow:hidden;
  isolation:isolate;
  transition:transform .4s var(--ease), border-color .4s var(--ease), color .35s var(--ease), box-shadow .4s var(--ease);
  will-change:transform;
}
.btn > span{position:relative;z-index:2}
.btn::before{
  content:"";position:absolute;inset:0;z-index:1;
  background:radial-gradient(120% 140% at 20% 110%, var(--lime-400) 0%, var(--lime-500) 42%, var(--green-600) 100%);
  transform:translateY(101%);
  transition:transform .55s var(--ease);
}
.btn:hover{transform:translateY(-2px)}
.btn:hover::before{transform:translateY(0)}
.btn:active{transform:translateY(0)}

.btn__ico,.btn__wa{width:17px;height:17px;flex:none;position:relative;z-index:2;transition:transform .45s var(--ease)}
.btn__wa{fill:currentColor}
.btn:hover .btn__ico{transform:translateX(4px)}

.btn--primary{
  --btn-bg:var(--lime-500);
  --btn-fg:var(--ink);
  --btn-bd:var(--lime-500);
  box-shadow:0 6px 22px rgba(168,211,58,.18);
}
.btn--primary::before{background:radial-gradient(120% 140% at 20% 110%, #FFF 0%, var(--lime-400) 55%, var(--lime-500) 100%)}
.btn--primary:hover{box-shadow:0 10px 34px rgba(168,211,58,.3)}

.btn--ghost{--btn-bd:var(--hair);--btn-fg:var(--bone)}
.btn--ghost:hover{--btn-fg:var(--ink);--btn-bd:var(--lime-400)}

.btn--dark{--btn-bg:var(--ink);--btn-fg:var(--bone);--btn-bd:var(--ink)}
.btn--dark:hover{--btn-fg:var(--ink);--btn-bd:var(--lime-500)}

.btn--sm{padding:.72em 1.15em;font-size:.8rem}
.btn--full{width:100%}

/* ---------- 7. Rail de profundidad ---------- */
.rail{
  position:fixed;z-index:60;
  right:clamp(.9rem,1.7vw,1.6rem);
  top:50%;transform:translateY(-50%);
  display:flex;flex-direction:column;align-items:center;gap:.85rem;
  opacity:0;transition:opacity .6s var(--ease);
  pointer-events:none;
}
.rail.is-on{opacity:1}
.rail__label{
  font-family:var(--ff-mono);font-size:.58rem;font-weight:500;
  letter-spacing:.3em;text-transform:uppercase;color:var(--mute-2);
  writing-mode:vertical-rl;
}
.rail__track{
  width:1px;height:clamp(90px,16vh,150px);
  background:var(--hair);position:relative;overflow:hidden;
}
.rail__fill{
  position:absolute;inset:0 0 auto 0;
  height:0%;
  background:linear-gradient(180deg,var(--lime-400),var(--amber));
}
.rail__fill::after{
  content:"";position:absolute;left:50%;bottom:0;
  width:5px;height:5px;margin-left:-2.5px;margin-bottom:-2.5px;
  border-radius:50%;background:var(--amber);
  box-shadow:0 0 8px 2px rgba(245,166,35,.55);
}
.rail__chapter{
  font-family:var(--ff-mono);font-size:.68rem;font-weight:500;
  color:var(--amber);letter-spacing:.06em;
}

/* ---------- 8. Capítulos ---------- */
.chapter{
  position:relative;
  padding-block:clamp(6rem,15vh,11rem);
  overflow:clip;
}
.chapter__head{margin-bottom:clamp(3rem,7vw,5.5rem)}
.chapter__head--split{
  display:grid;
  grid-template-columns:minmax(0,1.15fr) minmax(0,1fr);
  gap:clamp(1.75rem,4vw,4rem);
  align-items:end;
}

/* separador hairline entre capítulos, con nodo ámbar */
.chapter::before{
  content:"";position:absolute;top:0;left:var(--gut);right:var(--gut);
  height:1px;background:var(--hair-2);
  z-index:1;
}

/* ---------- 8b. Escenas ancladas ----------
   #desafio y #sistema animan con el scroll (el barrido de suelo vivo y el
   círculo de los 5 pilares). Sin anclaje el efecto terminaba cuando el bloque
   ya había salido de la pantalla: se veía medio círculo y medio barrido.
   Aquí el bloque se queda fijo mientras se consume su PISTA y se suelta justo
   antes de lo que viene después, así nunca lo tapa (el capítulo siguiente).

   La pista es un ::after real dentro de .scrolly y NO un padding: el bloque
   contenedor de un hijo de bloque es la caja de CONTENIDO del padre, de modo
   que un padding-bottom no le daría ningún recorrido al sticky.

   Invariante que asume novoterra.js: el elemento pegado es siempre el PRIMER
   hijo en flujo de su pista y la pista no tiene padding ni borde superior.
   Con eso el avance es (tope - rect.top) / (altoPista - altoBloque). */
:root{ --anclaje:calc(var(--header-h, 158px) + .85rem); }
.scrolly{position:relative}
.scrolly::after{content:"";display:block;height:var(--pista,0px)}

/* ---------- 9. HERO ---------- */
/* Composición "bajo nuestros pies": el contenido vive en la mitad superior,
   ordenado y limpio; una línea de superficie hace de horizonte y las raíces
   solo existen debajo de ella. Nada cruza el titular. */
.hero{
  position:relative;
  min-height:100svh;
  display:flex;flex-direction:column;justify-content:center;
  /* proporción: el bloque respira centrado y la banda de suelo inferior
     queda compacta y CON contenido visual (línea viva, destellos, terreno).
     El max() con --header-h es el suelo mínimo: el header es position:fixed,
     no reserva sitio en el flujo, así que en pantallas BAJAS (portátil 1366×620,
     móvil apaisado) el contenido centrado subía hasta meterse debajo de él.
     En pantallas normales gana el clamp y la proporción no cambia. */
  padding-block:max(clamp(7rem,13vh,9.5rem), calc(var(--header-h, 158px) + 1.4rem)) 13svh;
  background:
    radial-gradient(120% 78% at 74% 6%, rgba(23,181,143,.16) 0%, rgba(15,93,82,.05) 42%, transparent 72%),
    linear-gradient(180deg, #071A11 0%, #06170F 46%, #08200f00 100%),
    var(--soil-900);
  overflow:clip;
}
/* fundido suave hacia el capítulo siguiente */
.hero::after{
  content:"";position:absolute;left:0;right:0;bottom:0;height:16%;
  z-index:3;pointer-events:none;
  background:linear-gradient(180deg, rgba(6,23,15,0) 0%, rgba(14,12,9,.55) 100%);
}
/* la superficie del suelo: hairline con un pulso ámbar al centro */
.hero__surface{
  position:absolute;left:0;right:0;top:78%;
  z-index:3;pointer-events:none;
}
.hero__surface::before{
  content:"";position:absolute;left:0;right:0;top:0;height:1px;
  /* la línea del horizonte lleva un destello ámbar que la recorre:
     primera capa animada (barrido) + capa base estática */
  background:
    linear-gradient(90deg, transparent, rgba(255,214,120,.95) 45%, rgba(245,166,35,.9) 55%, transparent) no-repeat,
    linear-gradient(90deg,
      transparent 0%, rgba(200,226,200,.16) 16%,
      rgba(245,166,35,.42) 50%,
      rgba(200,226,200,.16) 84%, transparent 100%);
  background-size:230px 1px, 100% 1px;
  background-position:-260px 0, 0 0;
  animation:surface-sweep 7.5s var(--ease-io) infinite;
}
@keyframes surface-sweep{
  0%, 18%{background-position:-260px 0, 0 0}
  70%, 100%{background-position:calc(100% + 260px) 0, 0 0}
}
.hero__surface::after{
  content:"";position:absolute;left:50%;top:0;
  width:min(58vw,780px);height:130px;
  transform:translate(-50%,-50%);
  background:radial-gradient(50% 100% at 50% 50%, rgba(245,166,35,.11), transparent 70%);
}
.hero__canvas{
  position:absolute;inset:0;width:100%;height:100%;
  z-index:0;pointer-events:none;
}
.hero__grain{
  position:absolute;inset:0;z-index:1;pointer-events:none;
  opacity:.5;mix-blend-mode:overlay;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='140' height='140'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='3'/%3E%3C/filter%3E%3Crect width='140' height='140' filter='url(%23n)' opacity='.42'/%3E%3C/svg%3E");
}
.hero__inner{
  position:relative;z-index:4;
  width:100%;max-width:var(--wrap);
  margin-inline:auto;padding-inline:var(--gut);
  display:flex;flex-direction:column;
  gap:clamp(1.4rem,2.6vw,2.1rem);
}
.hero__title{
  font-family:var(--ff-display);
  font-weight:700;
  font-size:var(--t-hero);
  /* respiración tipográfica: leading > 1 y tracking moderado; el ajuste
     anterior (-.042em / .97) juntaba letras y descolgaba las líneas */
  line-height:1.04;
  letter-spacing:-.024em;
  margin:0;
  max-width:24ch;
  text-wrap:balance;
}
.hero__title em{
  font-style:normal;
  /* inline-block a propósito: siendo inline, al partirse en dos líneas el
     navegador da a CADA fragmento su propia caja de fondo y el degradado se
     reinicia — se veía un corte de color a mitad del titular en móvil.
     Como bloque en línea la caja es una sola y el degradado corre entero. */
  display:inline-block;
  /* degradado con brillo itinerante: el tramo claro recorre las palabras
     lentamente — el toque premium sin mover una sola letra */
  background:linear-gradient(96deg,
    var(--lime-400) 0%, var(--lime-500) 26%,
    #F8E28A 42%,
    var(--yellow) 58%, var(--amber) 86%, var(--amber-600) 100%);
  background-size:230% 100%;
  background-position:0% 0;
  -webkit-background-clip:text;background-clip:text;
  -webkit-text-fill-color:transparent;color:transparent;
  animation:title-sheen 9s var(--ease-io) infinite;
}
@keyframes title-sheen{
  0%, 24%{background-position:0% 0}
  62%{background-position:82% 0}
  100%{background-position:0% 0}
}
.hero__title .line{display:block;overflow:hidden;padding-bottom:.06em}

.hero__foot{
  display:grid;
  grid-template-columns:minmax(0,1fr) auto;
  gap:clamp(1.5rem,4vw,3.5rem);
  align-items:center;
  padding-top:clamp(1rem,2vw,1.5rem);
  border-top:1px solid var(--hair-2);
}
.hero__lead{
  color:var(--mute);max-width:44ch;
  font-size:clamp(1rem,1.22vw,1.15rem);
  line-height:1.6;
}
.hero__actions{display:flex;flex-wrap:wrap;gap:.8rem}

/* franja de datos reales bajo el bloque principal: ancla el hero a la
   oferta (líneas de solución) y elimina la sensación de vacío */
.hero__meta{
  display:flex;align-items:center;flex-wrap:wrap;
  gap:.9rem clamp(1.1rem,2.4vw,2rem);
  padding-top:clamp(.9rem,1.8vw,1.3rem);
  border-top:1px solid var(--hair-2);
  font-family:var(--ff-mono);
  font-size:var(--t-mono);
  letter-spacing:.2em;
  text-transform:uppercase;
  color:var(--mute-2);
}
.hero__meta-k{color:var(--lime-500)}
.hero__meta-list{
  display:flex;align-items:center;flex-wrap:wrap;
  gap:.9rem clamp(1.1rem,2.2vw,1.8rem);
}
.hero__meta-list li{position:relative;white-space:nowrap}
.hero__meta-list li + li::before{
  content:"";position:absolute;left:calc(-.55rem - 1vw);top:50%;
  width:4px;height:4px;border-radius:50%;
  background:var(--amber);opacity:.55;transform:translateY(-50%);
}
.hero__meta-tag{margin-left:auto;color:var(--mute);white-space:nowrap}

/* no puede pisar el rail de profundidad, que vive pegado al borde derecho */
.hero__cue{
  position:absolute;right:calc(var(--gut) + 2.6rem);bottom:clamp(1.5rem,4vh,2.75rem);
  display:flex;flex-direction:column;align-items:center;gap:.7rem;
  z-index:5;
}
.hero__cue-text{
  font-family:var(--ff-mono);font-size:.6rem;font-weight:500;
  letter-spacing:.32em;text-transform:uppercase;color:var(--mute-2);
  writing-mode:vertical-rl;
  line-height:1;
}
.hero__cue-line{
  width:1px;height:56px;background:var(--hair);position:relative;overflow:hidden;
}
.hero__cue-line::after{
  content:"";position:absolute;left:0;top:0;width:1px;height:40%;
  background:linear-gradient(180deg,transparent,var(--lime-400));
  animation:cue 2.4s var(--ease-io) infinite;
}
@keyframes cue{0%{transform:translateY(-100%)}60%,100%{transform:translateY(250%)}}

/* Raíz procedural: SOLO debajo de la superficie. Arranca exactamente en la
   línea del horizonte y desciende — nunca cruza el contenido. */
.rootfield{
  position:absolute;z-index:2;pointer-events:none;
  left:0;right:0;top:78%;bottom:-60%;
  opacity:.5;
  -webkit-mask-image:linear-gradient(180deg,#000 0%,#000 46%,transparent 92%);
  mask-image:linear-gradient(180deg,#000 0%,#000 46%,transparent 92%);
}
.rootfield__svg{width:100%;height:100%}

/* ---------- 10. Cap. 01 — El desafío ---------- */
.chapter--arid{
  background:
    radial-gradient(90% 60% at 50% 0%, rgba(138,90,43,.14) 0%, transparent 62%),
    linear-gradient(180deg, var(--arid-950) 0%, var(--arid-900) 55%, var(--soil-950) 100%);
}
.chapter--arid .label{color:var(--clay)}
.chapter--arid .label::before{background:var(--yellow)}

.challenge{
  display:grid;
  grid-template-columns:minmax(0,.9fr) minmax(0,1.1fr);
  gap:clamp(2.5rem,6vw,5rem);
  align-items:center;
}
.challenge__list{display:flex;flex-direction:column}
.challenge__item{
  display:flex;align-items:baseline;gap:1.1rem;
  padding:clamp(.85rem,1.7vw,1.35rem) 0;
  border-bottom:1px solid rgba(200,180,140,.13);
  position:relative;
}
.challenge__item:first-child{border-top:1px solid rgba(200,180,140,.13)}
.challenge__i{
  font-family:var(--ff-mono);font-size:.68rem;font-weight:500;
  letter-spacing:.1em;color:var(--clay);flex:none;
}
.challenge__t{
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.15rem,2.5vw,2rem);
  letter-spacing:-.028em;line-height:1.1;
  color:#C9BCA6;
  transition:color .5s var(--ease), transform .5s var(--ease);
}
.challenge__item::after{
  content:"";position:absolute;left:0;bottom:-1px;height:1px;width:0;
  background:linear-gradient(90deg,var(--yellow),transparent);
  transition:width .8s var(--ease);
}
.challenge__item.is-in::after{width:100%}
.challenge__item:hover .challenge__t{color:var(--bone);transform:translateX(6px)}

.soilcompare{margin:0}
.soilcompare__stage{
  position:relative;
  aspect-ratio:4/3.1;
  border-radius:var(--radius);
  overflow:hidden;
  border:1px solid rgba(200,180,140,.14);
  background:#0B0906;
  box-shadow:var(--shadow-card);
}
.soilcompare__canvas{position:absolute;inset:0;width:100%;height:100%}
.soilcompare__legend{
  position:absolute;inset:auto 0 0 0;
  display:flex;justify-content:space-between;
  padding:.9rem 1.1rem;
  font-family:var(--ff-mono);font-size:.6rem;font-weight:500;
  letter-spacing:.18em;text-transform:uppercase;
  background:linear-gradient(180deg,transparent,rgba(0,0,0,.72));
}
.soilcompare__tag{display:flex;align-items:center;gap:.45rem}
.soilcompare__tag::before{content:"";width:6px;height:6px;border-radius:50%}
.soilcompare__tag--dead{color:#9A8A6E}
.soilcompare__tag--dead::before{background:#9A8A6E}
.soilcompare__tag--alive{color:var(--lime-400)}
.soilcompare__tag--alive::before{background:var(--lime-400);box-shadow:0 0 8px 1px rgba(198,232,90,.6)}
.soilcompare__cap{
  margin-top:1rem;color:var(--mute-2);
  font-size:.85rem;line-height:1.6;max-width:52ch;
}

/* ---------- 11. Manifiesto ---------- */
.chapter--manifesto{
  background:linear-gradient(180deg, var(--soil-950) 0%, var(--soil-850) 50%, var(--soil-900) 100%);
}
.manifesto{
  margin:0 0 clamp(4rem,9vw,7rem);
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.75rem,4.6vw,4.1rem);
  line-height:1.02;letter-spacing:-.038em;
  text-wrap:balance;
}
.manifesto__line{display:block;overflow:hidden;padding-bottom:.05em}
.manifesto__line--accent{
  background:linear-gradient(96deg,var(--lime-400) 0%,var(--yellow) 58%,var(--amber) 100%);
  -webkit-background-clip:text;background-clip:text;
  -webkit-text-fill-color:transparent;color:transparent;
}
.manifesto__line--sm{
  font-family:var(--ff-body);font-weight:400;
  font-size:clamp(.98rem,1.55vw,1.32rem);
  line-height:1.5;letter-spacing:-.008em;
  color:var(--mute);
  margin-top:clamp(1.4rem,3vw,2.2rem);
  max-width:44ch;
}

.history{
  display:grid;
  grid-template-columns:repeat(2,minmax(0,1fr));
  gap:clamp(2rem,5vw,4.5rem);
  padding-top:clamp(2.2rem,5vw,3.5rem);
  border-top:1px solid var(--hair-2);
}
.history .h3{color:var(--amber-600)}

/* ---------- 12. Bioma ---------- */
.chapter--bioma{
  background:var(--ink);
  min-height:100svh;
  display:flex;align-items:center;
}
.bioma__canvas{
  position:absolute;inset:0;width:100%;height:100%;
  z-index:0;
  -webkit-mask-image:radial-gradient(120% 88% at 50% 50%, #000 40%, transparent 88%);
  mask-image:radial-gradient(120% 88% at 50% 50%, #000 40%, transparent 88%);
}
/* dos preguntas compactas: el protagonista de esta sección es el campo de
   microorganismos del fondo, no dos paneles gigantes de vidrio */
.bioma__grid{
  display:grid;grid-template-columns:repeat(2,minmax(0,1fr));
  gap:clamp(1.25rem,2.6vw,2rem);
  max-width:1020px;
}
.bioma__q .h2{
  font-size:clamp(1.5rem,2.6vw,2.3rem);
  line-height:1.06;
  margin-bottom:1rem;
}
.bioma__q .body--lead{max-width:44ch;font-size:clamp(1rem,1.3vw,1.15rem)}
.bioma__q{
  position:relative;
  padding:clamp(1.5rem,2.6vw,2.1rem);
  border-radius:var(--radius);
  border:1px solid var(--hair-2);
  background:linear-gradient(155deg, rgba(10,31,22,.72) 0%, rgba(4,18,12,.55) 100%);
  -webkit-backdrop-filter:blur(9px);backdrop-filter:blur(9px);
  transition:border-color .6s var(--ease), transform .6s var(--ease);
}
.bioma__q::before{
  content:"";position:absolute;top:-1px;left:clamp(1.5rem,2.6vw,2.1rem);
  width:52px;height:1px;
  background:linear-gradient(90deg,var(--lime-400),transparent);
}
.bioma__q:hover{border-color:rgba(168,211,58,.3);transform:translateY(-4px)}
.bioma__cta{margin-top:clamp(2.5rem,5vw,3.75rem)}

/* ---------- 13. Sistema — 5 pilares ---------- */
.chapter--sistema{
  background:linear-gradient(180deg, var(--soil-900) 0%, var(--soil-800) 100%);
}
.chapter--sistema::after{
  content:"";position:absolute;inset:0;z-index:0;pointer-events:none;opacity:.55;
  background-image:linear-gradient(var(--hair-2) 1px, transparent 1px),linear-gradient(90deg, var(--hair-2) 1px, transparent 1px);
  background-size:clamp(48px,6vw,88px) clamp(48px,6vw,88px);
  -webkit-mask-image:radial-gradient(100% 70% at 50% 40%, #000 0%, transparent 78%);
  mask-image:radial-gradient(100% 70% at 50% 40%, #000 0%, transparent 78%);
}
.pillars{
  display:grid;
  grid-template-columns:minmax(0,1fr) minmax(0,1fr);
  gap:clamp(2.5rem,5vw,4.5rem);
  align-items:center;
}
.pillars__diagram{position:relative;display:flex;justify-content:center}
.pillars__svg{
  width:100%;height:auto;overflow:visible;
  max-width:clamp(320px,36vw,500px);
}
.pillars__panel{display:flex;flex-direction:column;gap:clamp(1.5rem,3vw,2.25rem)}
.pillars__tabs{display:flex;flex-direction:column}

.pillar{
  position:relative;
  display:flex;align-items:baseline;gap:1rem;
  width:100%;text-align:left;
  padding:clamp(.7rem,1.5vw,1.05rem) 0;
  border-bottom:1px solid var(--hair-2);
  transition:padding-left .45s var(--ease);
}
.pillar__num{
  font-family:var(--ff-mono);font-size:.66rem;font-weight:500;
  letter-spacing:.1em;color:var(--mute-2);flex:none;
  transition:color .4s var(--ease);
}
.pillar__name{
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.25rem,2.9vw,2.35rem);
  line-height:1.05;letter-spacing:-.032em;
  color:var(--mute);
  transition:color .4s var(--ease);
}
.pillar__bar{
  position:absolute;left:0;bottom:-1px;height:1px;width:0;
  background:linear-gradient(90deg,var(--lime-400),var(--amber));
  transition:width .6s var(--ease);
}
.pillar:hover .pillar__name{color:var(--bone-2)}
.pillar[aria-selected="true"]{padding-left:.9rem}
.pillar[aria-selected="true"] .pillar__name{color:var(--bone)}
.pillar[aria-selected="true"] .pillar__num{color:var(--amber)}
.pillar[aria-selected="true"] .pillar__bar{width:100%}

.pillars__body{
  display:flex;flex-direction:column;align-items:flex-start;gap:1.75rem;
  min-height:8.5rem;
}
.pillar-panel{display:none}
.pillar-panel.is-active{display:block}
.pillar-panel__text{
  font-size:var(--t-lead);line-height:1.5;
  color:var(--bone-2);max-width:48ch;letter-spacing:-.011em;
}

/* ---------- 14. Soluciones ---------- */
.chapter--soluciones{
  background:linear-gradient(180deg, var(--soil-800) 0%, var(--soil-850) 100%);
}
.solutions{
  display:grid;
  grid-template-columns:repeat(4,minmax(0,1fr));
  gap:clamp(.85rem,1.4vw,1.25rem);
}
.solution{
  position:relative;isolation:isolate;
  display:flex;flex-direction:column;
  padding:clamp(1.6rem,2.6vw,2.15rem) clamp(1.35rem,2vw,1.75rem) clamp(1.4rem,2.2vw,1.8rem);
  border-radius:20px;
  border:1px solid var(--hair-2);
  background:
    radial-gradient(120% 90% at 50% -10%, rgba(168,211,58,.09) 0%, transparent 62%),
    linear-gradient(168deg, #0D2418 0%, #081C13 58%, #061710 100%);
  box-shadow:0 1px 0 rgba(230,245,210,.05) inset, 0 18px 40px -32px rgba(0,0,0,.9);
  overflow:hidden;
  transition:transform .55s var(--ease), border-color .55s var(--ease), box-shadow .55s var(--ease);
}
/* halo de luz que sube al pasar el mouse: la tarjeta “se enciende” */
.solution::before{
  content:"";position:absolute;inset:auto -20% -55% -20%;height:75%;z-index:-1;
  background:radial-gradient(60% 100% at 50% 100%, rgba(23,181,143,.3) 0%, transparent 70%);
  opacity:0;transition:opacity .6s var(--ease);
}
.solution::after{
  content:"";position:absolute;inset:auto 0 0 0;height:2px;
  background:linear-gradient(90deg,var(--lime-500),var(--amber));
  transform:scaleX(0);transform-origin:0 50%;
  transition:transform .6s var(--ease);
}
.solution:hover,.solution:focus-within{
  transform:translateY(-6px);
  border-color:rgba(168,211,58,.3);
  box-shadow:0 1px 0 rgba(230,245,210,.07) inset, 0 34px 60px -34px rgba(0,0,0,.95);
}
.solution:hover::after,.solution:focus-within::after{transform:scaleX(1)}
.solution:hover::before,.solution:focus-within::before{opacity:1}
.solution__ix{
  font-family:var(--ff-mono);font-size:.64rem;font-weight:500;
  letter-spacing:.16em;color:var(--mute-2);
}
/* plato de cultivo: el ícono no flota suelto, se apoya en un disco */
.solution__ico{
  position:relative;
  margin:clamp(1.15rem,2.2vw,1.7rem) 0 clamp(1.15rem,2vw,1.5rem);
  width:clamp(74px,7.4vw,92px);height:clamp(74px,7.4vw,92px);
  display:grid;place-items:center;
  border-radius:50%;
  border:1px solid var(--hair);
  background:radial-gradient(70% 70% at 50% 34%, rgba(23,181,143,.16) 0%, rgba(6,23,15,0) 72%);
  transition:border-color .55s var(--ease), transform .55s var(--ease);
}
.solution:hover .solution__ico{border-color:rgba(245,166,35,.34);transform:scale(1.05)}
.solution__ico svg{width:64%;height:64%;overflow:visible}
.solution__name{
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.15rem,1.85vw,1.5rem);
  letter-spacing:-.026em;line-height:1.15;
  margin-bottom:.7rem;
}
.solution__text{color:var(--mute);font-size:.9rem;line-height:1.6}
.solution__link{
  margin-top:auto;padding-top:clamp(1.2rem,2.2vw,1.7rem);
  display:inline-flex;align-items:center;gap:.5rem;
  font-family:var(--ff-mono);font-size:.68rem;font-weight:500;
  letter-spacing:.11em;text-transform:uppercase;
  color:var(--lime-400);
  transition:color .4s var(--ease);
}
.solution__link svg{width:15px;height:15px;transition:transform .45s var(--ease)}
.solution__link:hover{color:var(--yellow)}
.solution__link:hover svg{transform:translateX(5px)}
.soluciones__cta{margin-top:clamp(2.25rem,4.5vw,3.25rem)}

/* ---------- 15. Productos ---------- */
.chapter--productos{
  background:
    radial-gradient(90% 55% at 50% 0%, rgba(23,181,143,.09), transparent 60%),
    linear-gradient(180deg, var(--soil-950) 0%, #030B07 60%, var(--soil-950) 100%);
}
/* tres columnas es el valor de partida; el bloque responsive lo reescribe como
   seis columnas con span 2 (mismo ancho) para poder centrar la fila huérfana */
.products{
  display:grid;
  grid-template-columns:repeat(3,minmax(0,1fr));
  gap:clamp(1.25rem,2.4vw,2rem);
}
.product{
  position:relative;
  display:flex;flex-direction:column;
  border-radius:var(--radius);
  border:1px solid var(--hair-2);
  background:linear-gradient(168deg, rgba(14,44,32,.6) 0%, rgba(5,15,10,.9) 58%, rgba(3,11,7,.96) 100%);
  overflow:hidden;
  box-shadow:var(--shadow-card);
  transition:transform .65s var(--ease), border-color .65s var(--ease), box-shadow .65s var(--ease);
  will-change:transform;
}
.product::before{
  content:"";position:absolute;inset:0;z-index:3;pointer-events:none;
  border-radius:inherit;
  background:linear-gradient(158deg, rgba(255,255,255,.09) 0%, transparent 34%);
  opacity:.7;
}
.product:hover{
  transform:translateY(-8px);
  border-color:rgba(168,211,58,.28);
  box-shadow:0 4px 8px rgba(0,0,0,.3), 0 22px 44px rgba(0,0,0,.42), 0 60px 110px rgba(0,0,0,.4), 0 0 0 1px rgba(168,211,58,.06);
}
/* el envase es el protagonista y las fotos se ven COMPLETAS:
   1/1 es la proporción real de las fotos entregadas (1000×1000) y contain
   garantiza que nada del packaging quede recortado. contain y no cover aunque
   hoy den lo mismo: el día que llegue una foto que no sea cuadrada, cover le
   comería la tapa y el pie de etiqueta; contain la apoya sobre el degradado
   teal de la propia caja, que lee como fondo de estudio. */
.product__media{
  position:relative;
  aspect-ratio:1/1;
  overflow:hidden;
  background:
    radial-gradient(110% 80% at 50% 96%, rgba(23,181,143,.10), transparent 62%),
    #050D08;
  flex:none;
}
.product__img{
  width:100%;height:100%;object-fit:contain;
  transition:transform 1.1s var(--ease), filter .8s var(--ease);
  filter:saturate(1.02) contrast(1.03);
}
.product:hover .product__img{transform:scale(1.045)}
.product__media::after{
  content:"";position:absolute;inset:0;
  background:linear-gradient(180deg, transparent 86%, rgba(3,11,7,.5) 100%);
}
/* el 86% y el -26% están recalibrados sobre la caja cuadrada: con la 4/5 de
   antes eran 82% y -32% */
.product__glow{
  position:absolute;z-index:1;
  left:50%;bottom:-26%;
  width:78%;aspect-ratio:1;
  transform:translateX(-50%);
  border-radius:50%;
  background:radial-gradient(circle, rgba(168,211,58,.34) 0%, rgba(23,181,143,.12) 42%, transparent 68%);
  filter:blur(26px);
  opacity:0;
  transition:opacity .8s var(--ease);
}
.product:hover .product__glow{opacity:1}

.product__body{
  position:relative;z-index:2;
  display:flex;flex-direction:column;flex:1;
  padding:clamp(1.4rem,2.4vw,1.9rem);
  margin-top:-1px;
}
.product__cat{
  font-family:var(--ff-mono);font-size:.62rem;font-weight:500;
  letter-spacing:.19em;text-transform:uppercase;
  color:var(--lime-500);margin-bottom:.6rem;
}
.product__name{
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.3rem,2.2vw,1.75rem);
  letter-spacing:-.03em;line-height:1.08;
  margin-bottom:.85rem;
}
/* el margen de abajo es el hueco mínimo garantizado hasta la tabla de specs:
   el margin:auto de la tabla se come todo el espacio libre, pero cuando no
   sobra nada vale 0 y sin esto el filete quedaría pegado al texto */
.product__desc{color:var(--mute);font-size:.88rem;line-height:1.62;margin-bottom:1.25rem}
.product__desc strong{color:var(--lime-400);font-weight:700}

/* el margin-top:auto está aquí y no en .product__actions (donde estaba) porque
   las descripciones de una misma fila no tienen el mismo número de líneas: con
   el auto en los botones, la tabla de specs arrancaba y terminaba a tres
   alturas distintas dentro de la fila. Con el auto aquí, specs y botones bajan
   juntos y el filete que cierra la tabla queda a la misma altura en las tres
   tarjetas (medido a 1440: desalineación del cierre 38px -> 0px). Lo único que
   sigue variando es dónde empieza la tabla, y eso es información real: esa
   ficha tiene una fila más porque lleva microorganismo. */
.product__specs{
  margin:auto 0 0;
  border-top:1px solid var(--hair-2);
}
.product__specs li{
  display:flex;justify-content:space-between;gap:1rem;
  padding:.6rem 0;
  border-bottom:1px solid var(--hair-2);
  font-family:var(--ff-mono);font-size:.68rem;letter-spacing:.04em;
}
.product__specs li span:first-child{color:var(--mute-2);text-transform:uppercase;letter-spacing:.14em;font-size:.6rem}
.product__specs li span:last-child{color:var(--bone-2)}
/* "Ficha técnica — Pendiente": una fila que reserva el sitio de la ficha hasta
   que el cliente mande la oficial. El valor baja al mismo gris de la etiqueta
   en vez del hueso resaltado, así la fila entera se lee como anotación tranquila
   y el ojo no la confunde con un dato real (la presentación, el microorganismo).
   Medido sobre el parche más claro del fondo da 5.01:1: atenuado, no invisible.

   Cuando llegue la ficha, esta fila se sustituye por las filas reales
   (composición, dosis, cultivos, registro…) ya sin la clase.

   Ojo con el selector: hace falta arrastrar `.product__specs li` aunque
   parezca redundante. `.product__spec--pendiente span:last-child` por sí solo
   es (0,2,1) y pierde contra la regla de arriba, que es (0,2,2) — la clase se
   aplicaría en el HTML sin que cambiara nada en pantalla.

   Si se prefiere publicar sin la fila hasta tener las fichas, basta con
   descomentar la regla de abajo — no hace falta tocar el HTML. */
.product__specs li.product__spec--pendiente span:last-child{color:var(--mute-2)}
/* .product__specs li.product__spec--pendiente{display:none} */

.product__actions{
  display:flex;flex-direction:column;gap:.6rem;
  padding-top:1.4rem;
}

/* ---------- 16. Propósito / valores ---------- */
.chapter--proposito{
  background:linear-gradient(180deg, var(--soil-950) 0%, var(--soil-700) 62%, var(--soil-600) 100%);
}
.pmv{
  display:grid;grid-template-columns:repeat(3,minmax(0,1fr));
  gap:clamp(1rem,2vw,1.75rem);
  margin-bottom:clamp(4rem,9vw,7rem);
}
.pmv__card{
  position:relative;
  padding:clamp(1.6rem,3vw,2.4rem);
  border-radius:var(--radius);
  border:1px solid var(--hair-2);
  background:linear-gradient(160deg, rgba(255,255,255,.055) 0%, rgba(255,255,255,.012) 100%);
  transition:transform .6s var(--ease), border-color .6s var(--ease), background-color .6s var(--ease);
  overflow:hidden;
}
.pmv__card::after{
  content:"";position:absolute;top:0;left:0;height:2px;width:100%;
  background:linear-gradient(90deg,var(--lime-500),var(--amber));
  transform:scaleX(0);transform-origin:0 50%;
  transition:transform .7s var(--ease);
}
.pmv__card:hover{transform:translateY(-5px);border-color:rgba(168,211,58,.28)}
.pmv__card:hover::after{transform:scaleX(1)}
.pmv__t{
  font-family:var(--ff-mono);font-size:.66rem;font-weight:500;
  letter-spacing:.24em;text-transform:uppercase;
  color:var(--lime-500);margin-bottom:1.1rem;
}
.pmv__x{
  font-family:var(--ff-display);font-weight:500;
  font-size:clamp(1rem,1.5vw,1.22rem);
  line-height:1.38;letter-spacing:-.018em;color:var(--bone-2);
}
/* propósito / misión / visión viven en #nosotros y cierran la sección: sin
   margen inferior, y con el mismo filete y aire que separa la historia para
   que manifiesto → historia → p/m/v lleven un único ritmo */
.pmv--nosotros{
  margin-top:clamp(2.6rem,6vw,4.5rem);
  margin-bottom:0;
  padding-top:clamp(2.2rem,5vw,3.5rem);
  border-top:1px solid var(--hair-2);
}
/* pedido de la clienta: cada tarjeta lleva su propia foto de fondo (estilo
   ficha editorial premium). El velo va en ::before con z-index negativo
   -pinta encima de la foto pero debajo del texto, que sigue en flujo
   normal- así el texto nunca pierde contraste, sea cual sea la foto.
   Revisión: el velo vuelve a OSCURO y el texto a claro, por pedido explícito.
   Con eso el bloque deja de ser una isla clara dentro de una sección oscura y
   los overrides de color que necesitaba la versión blanca ya no hacen falta:
   la base de .pmv__card (rótulo lime-500, cuerpo bone-2, filete --hair-2,
   regla lime→amber) ya es la variante oscura, así que se hereda tal cual.
   Se mantiene el eje 195deg: casi vertical, con la pizca de diagonal que
   evita que el degradado se lea mecánico. */
.pmv--nosotros .pmv__card{
  position:relative;
  isolation:isolate;
  /* reserva oscura: si una foto no carga, la tarjeta sigue siendo oscura y
     el texto claro se sigue leyendo. Un escalón por encima del fondo de la
     sección para que la tarjeta no se funda con él */
  background-color:var(--soil-850);
  background-size:cover;
  background-position:center;
  /* la foto asomando aclara los bordes; la sombra los vuelve a despegar */
  box-shadow:var(--shadow-card);
}
/* misma arquitectura de dos capas que la versión clara, invertida. La de
   abajo es un plano oscuro que fija el piso de legibilidad en TODA la
   tarjeta (.55); encima, el degradado que refuerza donde vive el texto.
   Compuesto deja pasar ~10% de la foto arriba (rótulo y primeras líneas) y
   ~27% en el borde inferior, donde la imagen respira.
   Las opacidades suben respecto del velo blanco -que podía desvanecerse a 0-
   porque aquí el riesgo se invierte: las tres fotos son CLARAS (follaje a
   contraluz, manos con sol, trigal) y son ellas las que atentan contra el
   texto claro. Un velo oscuro que se apague abajo dejaría la última línea
   sobre trigo iluminado. Por eso el degradado cierra en .40, no en 0.
   Contrastes calculados contra el peor caso absoluto -un píxel blanco puro
   (255,255,255) en la zona de menor velo-: cuerpo bone-2 6.9:1 y rótulo
   lime-500 8.8:1, ambos sobre el 4.5:1 que pide AA. Sobre los altos reales
   de las fotos el margen es mayor. */
.pmv--nosotros .pmv__card::before{
  content:"";position:absolute;inset:0;z-index:-1;
  background:
    linear-gradient(195deg,
      rgba(5,15,10,.78) 0%,
      rgba(5,15,10,.72) 38%,
      rgba(5,15,10,.54) 76%,
      rgba(5,15,10,.40) 100%),
    linear-gradient(0deg, rgba(5,15,10,.55), rgba(5,15,10,.55));
}
.pmv--nosotros .pmv__card--proposito{background-image:url('../pmv-proposito.webp');background-position:center 44%}
.pmv--nosotros .pmv__card--mision{background-image:url('../pmv-mision.webp');background-position:60% 46%}
.pmv--nosotros .pmv__card--vision{background-image:url('../pmv-vision.webp');background-position:center 62%}

.values{margin-bottom:clamp(3.5rem,8vw,6rem)}
/* .h2 aporta la tipografía; aquí solo el aire hasta la lista */
.values__h{margin-bottom:clamp(1.6rem,3.2vw,2.4rem)}
.values__list{border-top:1px solid var(--hair-2)}
.value{
  display:grid;
  grid-template-columns:auto minmax(0,1fr) minmax(0,.85fr);
  align-items:baseline;gap:1.25rem;
  padding:clamp(.75rem,1.7vw,1.25rem) 0;
  border-bottom:1px solid var(--hair-2);
  transition:transform .5s var(--ease);
}
.value__k{
  font-family:var(--ff-mono);font-size:.66rem;font-weight:500;
  letter-spacing:.1em;color:var(--amber);
}
.value__n{
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.35rem,4.2vw,3.25rem);
  line-height:1.04;letter-spacing:-.034em;
  color:var(--bone);
  transition:color .5s var(--ease);
}
.value__d{
  color:var(--mute);font-size:clamp(.86rem,1.05vw,1rem);
  line-height:1.55;max-width:34ch;
  transition:color .5s var(--ease);
}
.value:hover{transform:translateX(10px)}
.value:hover .value__n{color:var(--lime-400)}
.value:hover .value__d{color:var(--bone-2)}

.tone{
  display:flex;flex-wrap:wrap;justify-content:space-between;gap:clamp(1rem,3vw,3rem);
  padding-top:clamp(2rem,4vw,3rem);
  border-top:1px solid var(--hair-2);
}
.tone__i{
  position:relative;padding-left:1.15rem;
  font-size:clamp(1.05rem,1.7vw,1.3rem);color:var(--bone-2);
}
.tone__i::before{
  content:"";position:absolute;left:0;top:.62em;
  width:6px;height:6px;border-radius:50%;background:var(--amber);
}

/* ---------- 17. Compromiso (emergencia a la luz) ---------- */
/* Texto a la izquierda, foto enmarcada COMPLETA a la derecha.
   Nada de foto a sangre con velos ni recortes: los ocho envases se ven.
   La foto es 2:1, más baja que la columna de texto: align-items:center la
   centra en vertical, así que no hace falta forzarle proporción. */
.chapter--compromiso{
  background:var(--bone);
  color:var(--ink);
}
.chapter--compromiso::before{display:none}
.compromiso__grid{
  display:grid;
  grid-template-columns:minmax(0,.95fr) minmax(0,1.05fr);
  gap:clamp(2.5rem,5vw,4.5rem);
  align-items:center;
}
.compromiso__media{
  margin:0;position:relative;
  border-radius:calc(var(--radius) + 6px);
  overflow:hidden;
  box-shadow:0 2px 4px rgba(10,26,16,.08), 0 18px 44px rgba(10,26,16,.16), 0 52px 96px rgba(10,26,16,.13);
}
.compromiso__img{display:block;width:100%;height:auto}
.chapter--compromiso .h2{font-size:clamp(1.8rem,3vw,2.7rem)}
.finalquote{
  margin:clamp(2.5rem,5vw,4rem) 0 clamp(2.25rem,4.5vw,3.25rem);
  padding-left:clamp(1rem,2.2vw,1.75rem);
  border-left:2px solid var(--amber-600);
  max-width:48ch;
}
.finalquote p{
  font-family:var(--ff-display);font-weight:500;
  font-size:clamp(1.05rem,1.8vw,1.5rem);
  line-height:1.34;letter-spacing:-.022em;
  color:#254032;
}
.finalquote em{font-style:normal;font-weight:700;color:var(--ink)}

/* ---------- 18. Contacto ---------- */
.chapter--contacto{
  background:
    radial-gradient(80% 60% at 82% 12%, rgba(23,181,143,.14), transparent 62%),
    linear-gradient(180deg, var(--soil-900) 0%, var(--soil-950) 100%);
}
.chapter--contacto .h2{margin-bottom:1.1rem}
/* eco de la lámina 2 del brand book: la frase que abre la marca cierra la página */
.contacto__echo{
  font-family:var(--ff-display);font-weight:500;
  font-size:clamp(1rem,1.5vw,1.3rem);
  letter-spacing:-.014em;
  color:var(--mute);
  margin-bottom:clamp(3rem,7vw,5rem);
}
.contact{
  display:grid;
  grid-template-columns:minmax(0,1.2fr) minmax(0,.8fr);
  gap:clamp(2.5rem,5vw,5rem);
  align-items:start;
}
.contact__hint{
  color:var(--mute-2);font-size:.82rem;line-height:1.6;
  margin-bottom:2rem;max-width:44ch;
}
.field{margin-bottom:1.25rem}
.field label{
  display:block;margin-bottom:.5rem;
  font-family:var(--ff-mono);font-size:.62rem;font-weight:500;
  letter-spacing:.18em;text-transform:uppercase;color:var(--mute-2);
}
.field input,.field textarea{
  width:100%;
  padding:.9rem 1.05rem;
  border-radius:12px;
  border:1px solid var(--hair);
  background:rgba(255,255,255,.035);
  color:var(--bone);
  font-size:.95rem;
  transition:border-color .35s var(--ease), background-color .35s var(--ease);
  resize:vertical;
}
.field input::placeholder,.field textarea::placeholder{color:var(--mute-2)}
.field input:focus,.field textarea:focus{
  outline:none;border-color:var(--lime-500);
  background:rgba(168,211,58,.05);
}
.field__err{
  display:block;margin-top:.45rem;
  font-family:var(--ff-mono);font-size:.63rem;color:#F2846A;letter-spacing:.04em;
}
.field.has-err input,.field.has-err textarea{border-color:#C2604C}
.contact__status{
  margin-top:.9rem;
  font-family:var(--ff-mono);font-size:.66rem;letter-spacing:.05em;
  color:var(--lime-400);min-height:1.2em;
}

.contact__side{display:flex;flex-direction:column;gap:1.6rem}
.contact__block{padding-bottom:1.4rem;border-bottom:1px solid var(--hair-2)}
.contact__k{
  font-family:var(--ff-mono);font-size:.62rem;font-weight:500;
  letter-spacing:.2em;text-transform:uppercase;color:var(--mute-2);
  margin-bottom:.5rem;
}
.contact__v{
  font-family:var(--ff-display);font-weight:700;
  font-size:clamp(1.05rem,1.7vw,1.35rem);letter-spacing:-.022em;
  color:var(--bone);
  transition:color .35s var(--ease);
}
a.contact__v:hover{color:var(--lime-400)}

.iglink{
  display:inline-flex;align-items:center;gap:.7rem;
  padding:.85rem 1.3rem;border-radius:100px;
  border:1px solid var(--hair);
  font-size:.86rem;font-weight:700;
  align-self:flex-start;
  transition:border-color .4s var(--ease), color .4s var(--ease), transform .4s var(--ease), background-color .4s var(--ease);
}
.iglink svg{width:17px;height:17px;fill:currentColor;flex:none}
.iglink:hover{
  transform:translateY(-2px);
  border-color:transparent;color:#fff;
  background:linear-gradient(72deg,#F5A623,#D6336C 46%,#7B3FE4);
}

/* ---------- 19. Footer ---------- */
.site-footer{
  background:var(--ink);
  padding-block:clamp(3.5rem,8vw,5.5rem) clamp(1.75rem,3vw,2.5rem);
  border-top:1px solid var(--hair-2);
}
.site-footer__top{
  display:grid;
  grid-template-columns:minmax(0,1.5fr) minmax(0,1fr) minmax(0,1fr);
  gap:clamp(2rem,4vw,3.5rem);
  padding-bottom:clamp(2.5rem,5vw,3.5rem);
  border-bottom:1px solid var(--hair-2);
}
.site-footer__logo{width:clamp(160px,17vw,215px);margin-bottom:1.4rem}
.site-footer__claim{color:var(--mute-2);font-size:.86rem;line-height:1.65;max-width:38ch}
.social{display:flex;gap:.7rem;margin-top:1.6rem}
.social__a{
  display:grid;place-items:center;
  width:44px;height:44px;border-radius:50%;
  border:1px solid var(--hair);color:var(--mute);
  transition:color .4s var(--ease), border-color .4s var(--ease), transform .4s var(--ease), background-color .4s var(--ease);
}
.social__a svg{width:19px;height:19px;fill:currentColor}
.social__a:hover{
  color:var(--ink);background:var(--lime-400);
  border-color:var(--lime-400);transform:translateY(-3px);
}
.site-footer__k{
  font-family:var(--ff-mono);font-size:.62rem;font-weight:500;
  letter-spacing:.2em;text-transform:uppercase;color:var(--mute-2);
  margin-bottom:1.1rem;
}
.site-footer__nav li,.site-footer__contact li{margin-bottom:.6rem}
.site-footer__nav a,.site-footer__contact a{
  font-size:.88rem;color:var(--bone-2);opacity:.78;
  transition:opacity .3s var(--ease), color .3s var(--ease);
}
.site-footer__nav a:hover,.site-footer__contact a:hover{opacity:1;color:var(--lime-400)}
.site-footer__bottom{
  display:flex;flex-wrap:wrap;gap:1rem 2rem;justify-content:space-between;
  padding-top:clamp(1.5rem,3vw,2.25rem);
  font-family:var(--ff-mono);font-size:.64rem;letter-spacing:.06em;color:var(--mute-2);
}
.site-footer__legal .placeholder{margin-top:0}

/* ---------- 20. WhatsApp flotante ---------- */
.wa-float{
  position:fixed;z-index:95;
  right:clamp(1rem,2vw,1.75rem);
  bottom:clamp(1rem,2vw,1.75rem);
  display:inline-flex;align-items:center;gap:0;
  height:56px;padding:0 16px;
  border-radius:100px;
  background:#1FAD54;
  color:#fff;
  box-shadow:0 6px 18px rgba(0,0,0,.34), 0 0 0 5px rgba(31,173,84,.14);
  overflow:hidden;
  transition:opacity .5s var(--ease), transform .5s var(--ease), gap .45s var(--ease), padding .45s var(--ease), box-shadow .45s var(--ease);
}
/* el estado oculto SOLO existe con JS activo (patrón .js-anim): sin JS el
   botón queda visible desde el arranque en vez de no aparecer nunca */
.js-anim .wa-float{opacity:0;transform:translateY(18px) scale(.9);pointer-events:none}
.js-anim .wa-float.is-on{opacity:1;transform:none;pointer-events:auto}
.wa-float svg{width:26px;height:26px;fill:currentColor;flex:none}
.wa-float__txt{
  max-width:0;opacity:0;white-space:nowrap;
  font-size:.88rem;font-weight:700;
  transition:max-width .45s var(--ease), opacity .35s var(--ease);
}
.wa-float:hover{gap:.6rem;box-shadow:0 10px 26px rgba(0,0,0,.4), 0 0 0 7px rgba(31,173,84,.2)}
.wa-float:hover .wa-float__txt{max-width:8rem;opacity:1}

/* ---------- 21. Sistema de revelado (solo con JS activo) ---------- */
.js-anim [data-reveal]{
  opacity:0;
  transform:translateY(26px);
  transition:opacity .95s var(--ease), transform .95s var(--ease);
  transition-delay:var(--d,0ms);
}
.js-anim [data-reveal].is-in{opacity:1;transform:none}

.js-anim .line__i,
.js-anim .manifesto__line .line__i{
  display:block;
  transform:translateY(105%) rotate(2.2deg);
  transition:transform 1.05s var(--ease);
  transition-delay:var(--d,0ms);
}
.js-anim [data-reveal-line].is-in .line__i{transform:none}
.js-anim .manifesto__line{overflow:hidden}
.js-anim .manifesto__line--sm .line__i{transform:translateY(60%);opacity:0;transition:transform 1s var(--ease),opacity 1s var(--ease)}
.js-anim .manifesto__line--sm.is-in .line__i{transform:none;opacity:1}

/* raíces: se dibujan al entrar */
.js-anim .rootfield{opacity:0;transition:opacity 1.4s var(--ease)}
/* misma opacidad que el estado base: si esta regla sube el valor, las raíces
   terminan dominando el hero (ya pasó) */
.js-anim .rootfield.is-in{opacity:.5}

/* ---------- 22. Responsive ---------- */

/* Ocho fichas en tres columnas dejan la última fila a medias (3+3+2) y esas dos
   quedaban abandonadas contra el margen izquierdo. La rejilla pasa a seis
   columnas con tarjetas de span 2 —el ancho resulta idéntico al de tres
   columnas, medido: 411/367/372px a 1920/1440/1280— y a la séptima se le da
   inicio en la columna 2, así el par sobrante se centra con medio hueco a cada
   lado. Cuatro columnas no valen: a 1920 el botón "Comprar NOVOCONTROL TR" ya
   rompe en dos líneas y por debajo de 1600 rompe también el nombre.

   La condición :nth-child(7):nth-last-child(2) solo se cumple con exactamente
   ocho fichas, así que el día que la clienta añada o quite un producto la regla
   se desactiva sola en vez de descolocar la rejilla. Va en su propio
   min-width:1181px para no pisar las dos columnas de abajo. */
@media (min-width:1181px){
  .products{grid-template-columns:repeat(6,minmax(0,1fr))}
  .products > .product{grid-column:span 2}
  .products > .product:nth-child(7):nth-last-child(2){grid-column:2 / span 2}
}

@media (max-width:1180px){
  .nav__list{gap:.85rem}
  .nav__link{font-size:.8rem}
  .brand__logo{width:clamp(140px,14vw,178px)}

  /* Con 8 productos la pista de 3 columnas se estrecha demasiado antes de
     llegar al apilado de 1000: a 1001px la tarjeta baja a ~291px y la fila de
     .product__specs (flex sin wrap) pide más de lo que hay. Dos columnas dan
     además 4 filas exactas, sin tarjeta huérfana. */
  .products{grid-template-columns:repeat(2,minmax(0,1fr))}
}

@media (max-width:1000px){
  .nav-toggle{display:block;order:3}
  .nav{
    position:fixed;inset:0;
    flex-direction:column;justify-content:center;align-items:flex-start;
    gap:2.5rem;
    padding:6rem var(--gut) 3rem;
    background:linear-gradient(165deg, #071A11 0%, #04120C 100%);
    -webkit-backdrop-filter:blur(20px);backdrop-filter:blur(20px);
    clip-path:circle(0% at calc(100% - 44px) 44px);
    /* visibility con retardo: clip-path solo oculta visualmente y los enlaces
       del menú cerrado seguían recibiendo Tab y foco de lectores de pantalla */
    visibility:hidden;
    transition:clip-path .7s var(--ease), visibility 0s linear .7s;
    overflow-y:auto;
    z-index:-1;
  }
  .nav.is-open{
    clip-path:circle(160% at calc(100% - 44px) 44px);z-index:1;
    visibility:visible;
    transition:clip-path .7s var(--ease), visibility 0s;
  }
  .nav__list{
    flex-direction:column;align-items:flex-start;gap:.35rem;width:100%;
  }
  .nav__list li{width:100%;border-bottom:1px solid var(--hair-2)}
  .nav__link{
    display:block;width:100%;padding:.85rem 0;
    font-family:var(--ff-display);font-weight:700;
    font-size:clamp(1.35rem,6vw,2rem);letter-spacing:-.03em;
    opacity:0;transform:translateY(14px);
    transition:opacity .5s var(--ease),transform .5s var(--ease),color .3s var(--ease);
  }
  .nav.is-open .nav__link{opacity:1;transform:none;transition-delay:calc(var(--i,0) * 55ms + 180ms)}
  .nav__link::after{display:none}
  .nav__tail{
    width:100%;flex-direction:column-reverse;align-items:stretch;gap:.9rem;
  }
  .nav__tail .btn{width:100%}
  .icon-link{align-self:flex-start}

  .chapter__head--split{grid-template-columns:1fr;align-items:start}
  .history{grid-template-columns:1fr;gap:2.5rem}
  .bioma__grid{grid-template-columns:1fr;gap:1.25rem}

  /* Entre 720 y 1000 la fila de dos columnas dejaba el lead del hero en unos
     30ch (266px a 820 de ancho): ilegible. Apila igual que .chapter__head--split
     y le devuelve su medida. Los botones NO pasan a ancho completo aquí: eso
     sigue siendo tratamiento de móvil (por debajo de 720). */
  .hero__foot{grid-template-columns:1fr;gap:1.25rem;align-items:start}

  /* Apilado no cabe el bloque entero bajo el header, así que se ancla SOLO la
     pieza que anima y el resto queda debajo, sin solaparse nunca: la lista/el
     panel pasan antes o después, nunca por detrás.
     display:block (en vez de grid con order) porque el elemento pegado tiene
     que ser el primer hijo en flujo de su pista —invariante del cálculo de
     avance en novoterra.js— y el orden del DOM ya es el correcto. */
  .scrolly--challenge,.scrolly--pillars{--pista:0px}

  .challenge{display:block}
  .challenge__list{margin-bottom:clamp(1.75rem,5vw,2.5rem)}
  .challenge__aside{position:relative}
  .challenge__aside::after{content:"";display:block;height:clamp(340px,52vh,520px)}
  .soilcompare{position:sticky;top:var(--anclaje)}

  .pillars{display:block}
  .pillars__aside{position:relative}
  /* cinco pasos necesitan recorrido: con menos, un solo gesto los atraviesa
     todos y el arco vuelve a parecer que no cierra */
  .pillars__aside::after{content:"";display:block;height:clamp(460px,72vh,620px)}
  .pillars__diagram{position:sticky;top:var(--anclaje);max-width:clamp(240px,72vw,320px);margin-inline:auto}
  .pillars__panel{margin-top:clamp(2rem,6vw,3rem)}
  .solutions{grid-template-columns:repeat(2,minmax(0,1fr))}
  .products{grid-template-columns:1fr;gap:1.5rem}
  .product{
    display:grid;
    grid-template-columns:minmax(0,.82fr) minmax(0,1.18fr);
  }
  /* aquí la ficha es horizontal y la caja de la foto estira al alto de la
     tarjeta, que lo marca el texto: sale más alta que ancha (medido 0.84 a
     820px y 0.67 a 721px). Con el contain de arriba eso dejaba hasta 68px de
     degradado vacío arriba y abajo, que se lee como error de carga. cover en
     una caja ALTA recorta por los lados, no por arriba: comprobado con las ocho
     fotos a 0.67 y los ocho envases siguen enteros, solo se pierde campo. */
  .product__media{aspect-ratio:auto;height:100%;min-height:260px}
  .product__img{object-fit:cover;object-position:center}
  /* En una columna cada ficha entra sola en pantalla, así que el escalonado de
     initReveal deja de leerse como cascada: las tarjetas 7 y 8 heredan el tope
     de 420ms y se ven en blanco casi medio segundo. El --d lo pone el JS como
     estilo inline, y un !important de hoja de estilos sí lo gana. En escritorio
     no se toca: allí la fila entra junta y la cascada sí tiene sentido. */
  .products > .product{--d:0ms !important}
  .pmv{grid-template-columns:1fr}
  .contact{grid-template-columns:1fr;gap:3rem}

  /* compromiso apila: texto arriba, foto completa debajo */
  .compromiso__grid{grid-template-columns:1fr;gap:2.5rem}

  .site-footer__top{grid-template-columns:1fr 1fr;gap:2.5rem}
  .site-footer__brand{grid-column:1/-1}
  .rail{display:none}
}

@media (max-width:720px){
  html{scroll-padding-top:78px}
  /* el header es fixed y NO reserva sitio: en pantalla corta el hero no tiene
     holgura para centrar y su contenido arranca justo en el padding, así que
     este tiene que superar el alto real del header (--header-h, publicado por
     novoterra.js). Con 5.75rem fijos el eyebrow quedaba bajo el logo. */
  .hero{min-height:100svh;padding-block:calc(var(--header-h, 115px) + 1.4rem) 10svh}
  .hero__title{max-width:100%;line-height:1.07;letter-spacing:-.02em}
  /* el barrido del degradado repinta texto recortado en cada cuadro: en móvil
     no compensa (batería) y el degradado luce igual en su posición de reposo */
  .hero__title em{animation:none;background-position:14% 0}
  .hero__foot{grid-template-columns:1fr;gap:1.5rem;align-items:start}
  .hero__actions{width:100%}
  .hero__actions .btn{flex:1 1 100%}
  .hero__cue{display:none}
  .hero__surface{top:86%}
  .rootfield{top:86%;bottom:-46%;opacity:.55}
  .hero__meta{gap:.7rem 1.2rem;letter-spacing:.16em}
  .hero__meta-tag{margin-left:0;width:100%}
  .hero__meta-list li + li::before{left:-.8rem}

  .solutions{grid-template-columns:1fr}
  .value{
    grid-template-columns:auto minmax(0,1fr);
    row-gap:.15rem;
  }
  .value__d{grid-column:2}
  .product{grid-template-columns:1fr}
  /* la caja vuelve a ser cuadrada, así que vuelve el contain: la regla es
     contain siempre que la caja sea 1/1 y cover solo cuando el alto lo manda
     el texto (banda de 1000 a 721px) */
  .product__media{aspect-ratio:1/1;min-height:0}
  .product__img{object-fit:contain}
  .site-footer__top{grid-template-columns:1fr}
  .site-footer__bottom{flex-direction:column;gap:.75rem}
  .wa-float{height:52px;padding:0 14px}
  .wa-float svg{width:24px;height:24px}
}

@media (max-width:420px){
  .challenge__item{gap:.75rem}
  .value{gap:.35rem .85rem}
}

/* pantallas muy anchas: no dejar que el texto se estire */
@media (min-width:1700px){
  :root{--wrap:1440px}
}

/* ---------- 23. Relato inmersivo — canvas WebGL persistente ----------
   Un solo canvas sticky respalda el tramo #inicio → #sistema. El HTML de
   cada capítulo sigue en flujo normal por encima (sin pinning): las anclas
   del menú y la posición de scroll no se alteran. La clase .story-on la
   pone soil-story.js SOLO cuando la escena 3D quedó lista; hasta entonces
   (y siempre que no haya WebGL) rigen los fondos y visuales 2D originales. */
.soil-story{position:relative}
.soil-story__stage{
  position:sticky;top:0;height:100svh;
  margin-bottom:-100svh;               /* el contenido se superpone al escenario */
  z-index:0;pointer-events:none;
  opacity:0;visibility:hidden;
}
.story-on .soil-story__stage{
  opacity:1;visibility:visible;
  transition:opacity 1.2s var(--ease-io);
}
#soil-story-canvas{width:100%;height:100%}

/* grano de película sobre TODO el relato (el del hero queda de fallback) */
.soil-story__stage::after{
  content:"";position:absolute;inset:0;pointer-events:none;
  opacity:.42;mix-blend-mode:overlay;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='140' height='140'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='3'/%3E%3C/filter%3E%3Crect width='140' height='140' filter='url(%23n)' opacity='.42'/%3E%3C/svg%3E");
}

/* velo de tierra: se enciende un instante al atravesar la superficie */
.soil-story__wipe{
  position:absolute;inset:0;pointer-events:none;
  opacity:0;
  background:
    radial-gradient(120% 90% at 50% 50%, rgba(34,27,18,.92) 0%, rgba(14,12,9,.97) 70%),
    url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='220' height='220'%3E%3Cfilter id='s'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.14' numOctaves='4'/%3E%3CfeColorMatrix values='0 0 0 0 .32 0 0 0 0 .23 0 0 0 0 .12 0 0 0 .9 0'/%3E%3C/filter%3E%3Crect width='220' height='220' filter='url(%23s)'/%3E%3C/svg%3E");
  background-blend-mode:multiply;
}

/* Con la escena activa, los capítulos del tramo ceden su fondo al canvas.
   (El color base del documento sigue transicionando por capítulo vía --bg,
   así el 3D y el resto de la página comparten la misma atmósfera.) */
.story-on .soil-story .hero,
.story-on .soil-story .chapter{background:transparent}
/* el hero conserva su aurora (capas translúcidas sobre el canvas):
   la atmósfera teal arriba-derecha y un rescoldo ámbar abajo-izquierda */
.story-on .soil-story .hero{
  background:
    radial-gradient(120% 78% at 74% 6%, rgba(23,181,143,.18) 0%, rgba(15,93,82,.05) 42%, transparent 72%),
    radial-gradient(56% 42% at 10% 88%, rgba(245,166,35,.055) 0%, transparent 70%);
}
.story-on .soil-story .hero::after{display:none}
.story-on .soil-story .chapter--sistema::after{display:none}
.story-on #hero-canvas,
.story-on .hero__grain,
.story-on .rootfield,
.story-on .bioma__canvas{display:none}

/* pasos con aire extra en escritorio: le dan recorrido a cada escena
   (descenso, despertar, red, regeneración, división en pilares).
   Va sobre .has-webgl —puesta en <head> ANTES del primer render— y no
   sobre .story-on: si el layout creciera después de que el navegador
   ancló un #hash, el destino quedaría desplazado. */
@media (min-width:1001px){
  .has-webgl #desafio{padding-block:clamp(8rem,20svh,14rem) clamp(9rem,24svh,16rem)}
  .has-webgl #nosotros{padding-block:clamp(8rem,20svh,14rem) clamp(9rem,22svh,15rem)}
  .has-webgl #bioma{padding-block:clamp(9rem,24svh,16rem) clamp(14rem,42svh,26rem)}
  .has-webgl #sistema{padding-block:clamp(8rem,20svh,14rem) clamp(10rem,26svh,17rem)}

  /* en dos columnas el bloque entero cabe bajo el header: se ancla completo,
     con su lista/panel al lado, y el efecto se completa sin que nada salga */
  .scrolly--challenge{--pista:clamp(340px,50vh,560px)}
  .scrolly--pillars{--pista:clamp(400px,58vh,640px)}
  .scrolly--challenge > .challenge,
  .scrolly--pillars > .pillars{position:sticky;top:var(--anclaje)}
}

@media print{
  .soil-story__stage{display:none !important}
}

/* ---------- 24. Movimiento reducido ---------- */
@media (prefers-reduced-motion:reduce){
  html{scroll-behavior:auto}
  *,*::before,*::after{
    animation-duration:.001ms !important;
    animation-iteration-count:1 !important;
    transition-duration:.001ms !important;
    scroll-behavior:auto !important;
  }
  .js-anim [data-reveal],
  .js-anim [data-reveal].is-in{opacity:1;transform:none}
  .js-anim .line__i{transform:none;opacity:1}
  .js-anim .rootfield{opacity:.5}
  .hero__cue-line::after{display:none}
  .eyebrow__dot{animation:none}
  .wa-float{opacity:1;transform:none;pointer-events:auto}
  /* el relato 3D nunca se activa con movimiento reducido (también se
     bloquea desde JS); las secciones quedan en flujo normal con los
     visuales estáticos originales */
  .soil-story__stage{display:none !important}
  /* sin anclaje: las pistas sólo añadirían scroll vacío, y los efectos ya
     arrancan en su estado final desde JS */
  .scrolly{--pista:0px}
  .scrolly > .challenge,.scrolly > .pillars,
  .soilcompare,.pillars__diagram{position:static}
  .challenge__aside::after,.pillars__aside::after{display:none}
}

/* ---------- 25. Impresión ---------- */
@media print{
  .site-header,.rail,.wa-float,.hero__canvas,.bioma__canvas,.rootfield,.hero__grain{display:none !important}
  body{background:#fff;color:#000}
}
