/* ---------- Satoshi, alojada por nosotros ---------- */
  @font-face{font-family:Satoshi;src:url('fuentes/satoshi-400.woff2') format('woff2');
    font-weight:400;font-style:normal;font-display:swap}
  @font-face{font-family:Satoshi;src:url('fuentes/satoshi-500.woff2') format('woff2');
    font-weight:500;font-style:normal;font-display:swap}
  @font-face{font-family:Satoshi;src:url('fuentes/satoshi-700.woff2') format('woff2');
    font-weight:700;font-style:normal;font-display:swap}
  @font-face{font-family:Satoshi;src:url('fuentes/satoshi-900.woff2') format('woff2');
    font-weight:900;font-style:normal;font-display:swap}

  /* PALETA INVERTIDA (Diego, 17-ago-2026): papel blanco, tinta negra y CERO
     grises — la jerarquía la hacen el tamaño y los filos, no medias tintas. */
  :root{
    --bg:#fff;
    --raise:#fafafa;
    --tx:#000;
    --tx2:#000;
    --tx3:#000;
    --line:#000;
    --line-soft:#000;
    --ease:cubic-bezier(.16,.84,.44,1);
    /* margen lateral MEDIDO contra la referencia (17-ago): basement deja
       16px a 1440 y nosotros teníamos 35 — el contenido va casi al filo. */
    --gutter:clamp(14px,1.15vw,22px);
    /* la mono de los acentos se declara en la RAÍZ: vivía dentro de `.bstm` y
       las piezas de fuera —la terminal de contacto— no la veían */
    --mono:GeistMonoVar,ui-monospace,'SF Mono',Menlo,monospace;
    --ancho:2100px;
  }
  *{margin:0;padding:0;box-sizing:border-box}
  html{scroll-behavior:smooth;-webkit-text-size-adjust:100%}
  body{
    background:var(--bg);color:var(--tx);overflow-x:clip;
    font-family:Satoshi,system-ui,-apple-system,sans-serif;font-weight:500;
    font-size:17px;line-height:1.6;-webkit-font-smoothing:antialiased;
  }
  ::selection{background:var(--tx);color:var(--bg)}
  a{color:inherit;text-decoration:none}
  img,video{display:block;max-width:100%}
  :focus-visible{outline:2px solid var(--tx);outline-offset:3px;border-radius:4px}

  .wrap{width:100%;max-width:var(--ancho);margin:0 auto;padding-inline:var(--gutter)}
  /* el nav es fijo: sin esto, un ancla deja el título debajo de la barra */
  section[id]{scroll-margin-top:68px}
  .disp{font-weight:900;letter-spacing:-.042em;line-height:.98;text-wrap:balance}
  .lede{font-size:clamp(1.06rem,1.55vw,1.32rem);line-height:1.55;color:var(--tx2);font-weight:500;
    max-width:34em}
  .label{font-size:14px;font-weight:700;color:var(--tx3);letter-spacing:-.01em}

  /* ---------- nav ---------- */
  header{position:fixed;top:0;inset-inline:0;z-index:80;
    border-bottom:1px solid transparent;
    transition:background-color .45s var(--ease),border-color .45s var(--ease)}
  header.solid{background:var(--bg);border-bottom-color:var(--tx);
    backdrop-filter:blur(18px);-webkit-backdrop-filter:blur(18px)}
  /* grid de tres columnas: con space-between el centro sale desviado, porque
     el logo y el botón no miden lo mismo y el "centro" acaba siendo el del hueco */
  .bar{width:100%;max-width:var(--ancho);margin:0 auto;padding-inline:var(--gutter);
    height:52px;display:grid;grid-template-columns:1fr auto 1fr;
    align-items:center;gap:20px}
  .bar > .brand{grid-column:1;justify-self:start}
  .bar > nav.links{grid-column:2;justify-self:center}
  /* columna 3 fija: en móvil nav.links no genera caja y sin esto el botón
     de menú se subiría a la columna del centro */
  .bar > .demo-btn,.bar > .burger{grid-column:3;justify-self:end}
  /* el logotipo es un PNG de tinta clara: sobre papel se invierte */
  .brand img{height:16px;width:auto;filter:invert(1)}
  nav.links{display:none;gap:26px}
  nav.links a{font-size:14px;font-weight:600;color:var(--tx2);
    letter-spacing:-.01em;
    display:inline-grid;overflow:hidden;line-height:1.25;height:1.25em}
  nav.links a span{grid-area:1/1;transition:transform .42s var(--ease),color .42s var(--ease)}
  nav.links a span:last-child{transform:translateY(100%);color:var(--tx)}
  nav.links a:hover span:first-child{transform:translateY(-100%)}
  nav.links a:hover span:last-child{transform:translateY(0)}
  nav.links a.activa span:first-child{color:var(--tx)}
  @media(prefers-reduced-motion:reduce){
    nav.links a span{transition:none}
    nav.links a:hover span:first-child{color:var(--tx)}
    nav.links a:hover span:last-child{transform:translateY(100%)}
  }
  @media(min-width:900px){nav.links{display:flex}}

  /* ---------- menú móvil ---------- */
  .burger{display:flex;flex-direction:column;justify-content:center;gap:5px;
    width:44px;height:44px;padding:0;background:none;border:0;cursor:pointer;
    margin-right:-8px}
  .burger b{display:block;height:2px;width:22px;background:var(--tx);
    margin-inline:auto;border-radius:2px;
    transition:transform .4s var(--ease),opacity .3s var(--ease)}
  body.menu .burger b:nth-child(1){transform:translateY(7px) rotate(45deg)}
  body.menu .burger b:nth-child(2){opacity:0}
  body.menu .burger b:nth-child(3){transform:translateY(-7px) rotate(-45deg)}
  @media(min-width:900px){.burger{display:none}}

  .sheet{position:fixed;inset:0;z-index:70;background:var(--bg);
    display:flex;flex-direction:column;justify-content:center;gap:8px;
    padding:0 var(--gutter);
    opacity:0;visibility:hidden;transform:translateY(-8px);
    transition:opacity .38s var(--ease),transform .38s var(--ease),visibility .38s}
  body.menu .sheet{opacity:1;visibility:visible;transform:none}
  .sheet a{font-size:clamp(1.7rem,7.5vw,2.4rem);font-weight:900;
    text-transform:uppercase;letter-spacing:-.01em;padding:10px 0}
  @media(min-width:900px){.sheet{display:none}}

  .btn{display:inline-flex;align-items:center;justify-content:center;
    height:46px;padding:0 26px;border-radius:999px;font-weight:700;font-size:13px;
    text-transform:uppercase;letter-spacing:.07em;
    white-space:nowrap;cursor:pointer;border:1px solid transparent;
    font-family:inherit;
    transition:transform .3s var(--ease),background-color .3s var(--ease),color .3s var(--ease)}
  .btn:active{transform:scale(.97)}
  .btn-solid{background:var(--tx);color:var(--bg)}
  .btn-solid:hover{transform:translateY(-2px)}
  .btn-ghost{border-color:var(--line);color:var(--tx)}
  .btn-ghost:hover{background:rgba(255,255,255,.07);transform:translateY(-2px)}
  /* en móvil el CTA vive dentro del menú: en la barra competiría con el botón de menú */
  .demo-btn{display:none;height:32px;padding:0 16px;font-size:11px}
  @media(min-width:900px){.demo-btn{display:inline-flex}}

  /* ---------- hero a pantalla completa ---------- */
  .hero{position:relative;min-height:100svh;display:flex;align-items:flex-end;
    padding:calc(52px + clamp(50px,10vh,110px)) 0 clamp(56px,9vh,110px);
    overflow:hidden}
  .hero-fondo{position:absolute;inset:0;z-index:0}
  /* la ficha se va arriba: al centro chocaba con el titular y no se leía ninguna */
  .hero-fondo .hueco{width:100%;height:100%;border-radius:0;border:0;
    align-items:flex-start;justify-content:center;padding-top:110px}
  @media(min-width:900px){
    .hero-fondo .hueco{justify-content:flex-end;padding-right:var(--gutter)}
  }
  /* el velo es obligatorio, no decorativo: sin él, un material claro se come
     la tipografía blanca — es lo que tumbó la dirección editorial */
  .hero-velo{position:absolute;inset:0;z-index:1;pointer-events:none;
    background:
      linear-gradient(180deg,rgba(0,0,0,.72) 0%,rgba(0,0,0,.28) 30%,
                             rgba(0,0,0,.5) 62%, rgba(0,0,0,.88) 88%, #000 100%)}
  .hero > .wrap{position:relative;z-index:2;width:100%}
  .hero h1{font-size:clamp(2.55rem,7.6vw,6.6rem);max-width:15ch}
  .hero h1 .q{color:var(--tx3)}
  .hero .lede{margin-top:clamp(24px,3.4vh,34px);max-width:32em;color:var(--tx)}
  .cta{display:flex;gap:12px;margin-top:clamp(30px,4.5vh,42px);flex-wrap:wrap}


  /* ---------- huecos reservados para imagen o video ----------
     Cada uno lleva su proporción real y la ficha de qué va dentro.
     Para llenarlo: se sustituye el div entero por una etiqueta de imagen o de
     video con las mismas clases. Nada de esto se queda en producción.
     Son divs a propósito, no etiquetas vacías: una etiqueta sin origen se
     publica como caja rota. */
  .hueco{
    position:relative;border:1px dashed var(--tx);border-radius:12px;
    background:
      repeating-linear-gradient(135deg,
        rgba(0,0,0,.06) 0 12px, transparent 12px 24px),
      var(--bg);
    display:flex;align-items:center;justify-content:center;
    padding:22px;overflow:hidden;text-align:center}
  .hueco .ficha{display:flex;flex-direction:column;gap:5px;max-width:34ch}
  .hueco .qué{font-size:15px;font-weight:700;letter-spacing:-.018em;color:var(--tx)}
  .hueco .cómo{font-size:13px;line-height:1.45;color:var(--tx3)}
  .hueco .medida{font-size:12px;color:var(--tx3);
    border:1px solid var(--line);border-radius:5px;padding:3px 8px;align-self:center;
    font-variant-numeric:tabular-nums}


  /* (el bloque de .level vive más abajo, junto a su sección: si se declara
     aquí, la regla posterior de dos columnas lo pisa y el hueco cae de fila) */


  /* franja panorámica, a todo el ancho de la ventana */
  .franja{margin-top:clamp(70px,11vh,140px)}
  .franja .hueco{aspect-ratio:21/9;border-radius:0;border-inline:0}
  @media(max-width:700px){.franja .hueco{aspect-ratio:4/3}}

  /* ---------- bloques ---------- */
  .blk{padding:clamp(80px,12vh,160px) 0}
  .blk h2{font-size:clamp(2rem,5.4vw,4.2rem);max-width:16ch}
  .blk .lede{margin-top:22px;max-width:34em}

  /* niveles */
  .levels{margin-top:clamp(64px,10vh,130px);display:flex;flex-direction:column;
    gap:clamp(38px,6vh,72px)}
  /* separador SOLO entre filas: ni antes de la primera ni después de la última.
     No es la raya de sección que se retiró —esa cruzaba la ventana y encajonaba—:
     esta vive dentro de la lista y es lo que le da estructura a la escalera. */
  .level + .level{padding-top:clamp(38px,6vh,72px);
    border-top:1px solid var(--line-soft)}
  .level{display:grid;grid-template-columns:1fr;gap:10px;
    position:relative;align-items:start}
    /* La fila usa el ancho COMPLETO: nombre ancho a la izquierda y la descripción
     ocupando lo que queda. Antes el nombre medía 320 px y el párrafo llevaba un
     tope de 35em, así que el texto moría a dos tercios y sobraban ~350 px a la
     derecha — el filo entre filas sí cruzaba entero y delataba el hueco. */
  @media(min-width:900px){
    .level{grid-template-columns:minmax(0,480px) minmax(0,1fr);gap:100px}
    /* recorte del colchón de cada texto — ver el comentario de arriba */
    .level h3{margin-top:-.181em}
    .level p{margin-top:-.446em}
  }
  /* sin line-height propio heredaba el 1.6 del cuerpo, que en un titular deja
     20 px de aire muerto encima y descuadra la fila entera */
  .level h3{font-size:clamp(1.6rem,3vw,2.4rem);font-weight:900;letter-spacing:-.035em;
    line-height:1.06;transition:transform .5s var(--ease)}
  @media(hover:hover){.level:hover h3{transform:translateX(8px)}}
    /* Al llegar al borde derecho la línea se alargó a ~101 caracteres, que es
     ilegible. La medida no se arregla estrechando la caja —eso devuelve el
     hueco— sino AGRANDANDO la letra: mismo ancho, menos caracteres por línea. */
  .level p{color:var(--tx2);font-size:clamp(1rem,1.5vw,1.35rem);line-height:1.55}


  /* método */
  .method{display:grid;gap:clamp(28px,4vw,56px);margin-top:clamp(44px,6.5vh,80px);
    grid-template-columns:1fr}
  @media(min-width:860px){.method{grid-template-columns:repeat(3,1fr)}}
  .step{display:flex;flex-direction:column;gap:12px}
  .step h3{font-size:1.3rem;font-weight:700;letter-spacing:-.024em}
  .step p{color:var(--tx2);font-size:15.5px;line-height:1.6;max-width:32em}

  /* capacidades */
  .caps{display:grid;gap:clamp(30px,4vw,52px);
    margin-top:clamp(64px,10vh,130px);grid-template-columns:1fr}
  @media(min-width:720px){.caps{grid-template-columns:repeat(2,1fr)}}
  @media(min-width:1080px){.caps{grid-template-columns:repeat(3,1fr)}}
  /* Cuatro piezas cortas: una sola fila que ocupa el ancho completo. En tres
     columnas la cuarta se queda huérfana abajo, y en una sola el bloque se
     descuelga a un lado del título centrado, que es como se veía mal.
     Va pegada a su base y con dos clases, para ganarle a la de 1080 sin
     depender del orden del archivo. */
  @media(min-width:1160px){.caps.caps-4{grid-template-columns:repeat(4,1fr)}}
  .cap{display:flex;flex-direction:column;gap:10px}

  .cap h3{font-size:1.12rem;font-weight:700;letter-spacing:-.022em}
  .cap p{color:var(--tx2);font-size:15px;line-height:1.58;max-width:32em}


  /* cierre */
  .close{padding:clamp(88px,13vh,170px) 0 0}
  .close-grid{display:grid;gap:clamp(38px,5vw,80px);grid-template-columns:1fr;align-items:start}
  @media(min-width:940px){.close-grid{grid-template-columns:1fr 1fr}}
  .close h2{font-size:clamp(2.4rem,6.6vw,5rem);max-width:12ch}
  .close .lede{margin-top:22px;max-width:30em}
  .direct{margin-top:32px;display:flex;flex-direction:column;gap:6px}
  .direct a{font-size:clamp(1.05rem,1.5vw,1.2rem);font-weight:700;letter-spacing:-.018em;
    transition:opacity .25s}
  .direct a:hover{opacity:.65}
  .direct span{font-size:14px;color:var(--tx3)}

  form{display:flex;flex-direction:column;gap:12px}
  .field{display:flex;flex-direction:column;gap:7px}
  .field label{font-size:14px;font-weight:700;color:var(--tx2)}
  .field input,.field textarea{
    width:100%;background:transparent;border:1px solid var(--line);border-radius:10px;
    padding:15px 16px;color:var(--tx);font-family:inherit;font-size:16px;font-weight:500;
    transition:border-color .3s var(--ease),background-color .3s var(--ease)}
  .field input::placeholder,.field textarea::placeholder{color:var(--tx3);font-weight:500}
  .field input:focus,.field textarea:focus{outline:none;border-color:var(--tx);
    background:rgba(255,255,255,.04)}
  .field textarea{resize:vertical;min-height:110px}
  form button{margin-top:6px;height:52px;border-radius:999px;border:0;cursor:pointer;
    background:var(--tx);color:var(--bg);font-family:inherit;font-weight:700;font-size:13.5px;
    text-transform:uppercase;letter-spacing:.07em;
    transition:transform .3s var(--ease),opacity .3s}
  form button:hover{transform:translateY(-2px)}
  form button:disabled{opacity:.5;transform:none;cursor:default}
  .msg{min-height:20px;font-size:14px;color:var(--tx3)}

  footer{margin-top:clamp(70px,11vh,130px);
    padding:26px 0 32px}
  .foot{display:flex;flex-direction:column;gap:14px;align-items:center;
    justify-content:space-between;color:var(--tx3);font-size:14px;text-align:center}
  .foot img{height:16px;width:auto;flex:none;opacity:.72}
  /* los datos se separan por espacio, no por signos entre palabras */
  .foot-mid{display:flex;flex-direction:column;gap:6px;align-items:center}
  @media(min-width:760px){
    .foot{flex-direction:row;text-align:left}
    .foot-mid{flex-direction:row;gap:30px}
  }

  /* ---------- movimiento ---------- */
  .anima .rv{opacity:0;transform:translateY(26px);
    transition:opacity 1.15s var(--ease),transform 1.15s var(--ease)}
  .anima .rv.in{opacity:1;transform:none}
  .h1-line{display:block;overflow:hidden}
  .anima .h1-line > span{display:block;transform:translateY(104%);
    transition:transform 1.1s var(--ease)}
  .anima body.ready .h1-line > span,
  body.ready .h1-line > span{transform:none}
  body.ready .h1-line:nth-child(2) > span{transition-delay:.09s}
  body.ready .h1-line:nth-child(3) > span{transition-delay:.18s}
  @media(prefers-reduced-motion:reduce){
    html{scroll-behavior:auto}
    .rv,.h1-line > span{opacity:1!important;transform:none!important;transition:none}
  }

  /* ---------- enlace activo del menú ---------- */
  nav.links a.activa{color:var(--tx)}
  .sheet a.activa{opacity:.5}

  /* ---------- hero de página interior ---------- */
  .hero-int{position:relative;min-height:74svh;display:flex;align-items:flex-end;
    padding:calc(52px + clamp(50px,9vh,100px)) 0 clamp(48px,7vh,86px);overflow:hidden}
  .hero-int .hero-fondo{position:absolute;inset:0;z-index:0}
  .hero-int .hero-fondo .hueco{width:100%;height:100%;border-radius:0;border:0;
    align-items:flex-start;justify-content:center;padding-top:110px}
  @media(min-width:900px){
    .hero-int .hero-fondo .hueco{justify-content:flex-end;padding-right:var(--gutter)}
  }
  .hero-int > .wrap{position:relative;z-index:2;width:100%}
  .hero-int h1{font-size:clamp(2.3rem,6.4vw,5rem);max-width:16ch}
  .hero-int .lede{margin-top:clamp(20px,3vh,30px);max-width:32em;color:var(--tx)}

  /* ---------- bloque de detalle (páginas interiores) ---------- */
  .detalle{display:grid;gap:clamp(26px,4vw,64px);grid-template-columns:1fr;
    padding:clamp(66px,10vh,130px) 0}
  @media(min-width:940px){.detalle{grid-template-columns:minmax(0,1fr) minmax(0,1.15fr)}}
  .detalle h2{font-size:clamp(1.9rem,4.4vw,3.4rem)}
  .detalle .cuerpo{display:flex;flex-direction:column;gap:20px}
  .detalle .cuerpo p{color:var(--tx2);font-size:clamp(1rem,1.35vw,1.15rem);line-height:1.65;
    max-width:36em}
  .detalle .cuerpo strong{color:var(--tx);font-weight:700}

  /* lista de puntos, sin viñetas de recuadro */
  .puntos{display:flex;flex-direction:column;gap:clamp(18px,2.6vh,26px);
    margin-top:6px;list-style:none}
  .puntos li{display:flex;flex-direction:column;gap:3px;max-width:42em}
  .puntos b{color:var(--tx);font-weight:700;font-size:16.5px;letter-spacing:-.012em}
  .puntos span{color:var(--tx2);font-size:16px;line-height:1.55}


  /* ---------- llamada final compartida ---------- */
  .remate{padding:clamp(88px,13vh,160px) 0;text-align:center}
  .remate h2{font-size:clamp(2.2rem,6vw,4.4rem);max-width:16ch;margin-inline:auto}
  .remate .lede{margin:22px auto 0;max-width:30em}
  .remate .cta{justify-content:center}




  /* ---------- sección con video de fondo y texto encima ---------- */
  .cine{position:relative;min-height:86svh;display:flex;align-items:center;
    overflow:hidden;
    padding:clamp(70px,10vh,120px) 0}
  .cine-fondo{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;
    z-index:0;background:#000}
  /* el velo NO es decorativo: las líneas del video son brillantes y el texto
     vive sobre ellas. Oscurece más la mitad donde va la tipografía. */
  /* Dos velos con oficios distintos:
     - el lateral protege la legibilidad del texto,
     - el vertical FUNDE la pieza con el negro en bandas altas (28% arriba y
       abajo), que es lo que quita el canto y da el corte limpio. */
  .cine-velo{position:absolute;inset:0;z-index:1;pointer-events:none;
    background:
      linear-gradient(90deg,rgba(0,0,0,.92) 0%,rgba(0,0,0,.82) 34%,
                            rgba(0,0,0,.42) 62%,rgba(0,0,0,.35) 100%),
      linear-gradient(180deg,
        #000 0%, rgba(0,0,0,.86) 9%, rgba(0,0,0,.45) 20%, transparent 30%,
        transparent 68%, rgba(0,0,0,.45) 80%, rgba(0,0,0,.86) 91%, #000 100%)}
  .cine > .wrap{position:relative;z-index:2;width:100%}
  .cine h2{font-size:clamp(2rem,5.4vw,4.2rem);max-width:16ch}
  .cine .lede{margin-top:22px;max-width:34em;color:var(--tx)}
  .cine .cta{margin-top:clamp(30px,4.5vh,42px)}

  /* Toda pieza a sangre se funde con el fondo por arriba y por abajo,
     en vez de terminar en un canto. Es lo que da el corte limpio. */
  .franja{position:relative}
  .franja::before,.franja::after{content:"";position:absolute;inset-inline:0;
    height:clamp(90px,14vh,190px);pointer-events:none;z-index:1}
  .franja::before{top:0;background:linear-gradient(180deg,#000,transparent)}
  .franja::after{bottom:0;background:linear-gradient(0deg,#000,transparent)}

  /* ---------- pie de una sola fila ----------
     La navegación ya vive arriba; repetirla aquí es ruido. Aquí solo va lo
     que NO está en el menú: cómo escribirnos, y la línea legal. */
  .pie{padding:clamp(34px,5vh,52px) 0}
  .pie-fila{display:grid;grid-template-columns:1fr;gap:18px;align-items:center;
    text-align:center}
  @media(min-width:820px){
    .pie-fila{grid-template-columns:1fr auto 1fr;text-align:left}
    .pie-lado:last-child{justify-self:end;text-align:right}
  }
  .pie-lado{color:var(--tx3);font-size:12px;
    text-transform:uppercase;letter-spacing:.09em}
  .pie-enlaces{display:flex;gap:clamp(20px,3vw,40px);justify-content:center;
    flex-wrap:wrap}
  .pie-enlaces a{color:var(--tx2);font-size:12px;font-weight:600;
    text-transform:uppercase;letter-spacing:.09em;transition:color .25s}
  .pie-enlaces a:hover{color:var(--tx)}

  /* ---------- sección de dos columnas: imagen y texto ----------
     El bloque desplazado a la derecha solo se sostiene si algo ocupa el otro
     lado; si no, no es composición, es texto empujado. La imagen se queda
     pegada mientras se recorren las tres filas, así no hace falta una pieza
     altísima ni queda hueco al final. */
  .par{display:grid;grid-template-columns:1fr;gap:clamp(34px,5vw,72px)}
  @media(min-width:960px){
    .par{grid-template-columns:minmax(0,.62fr) minmax(0,1fr);
      gap:clamp(48px,5vw,96px);align-items:start}
    .par-medio{position:sticky;top:calc(52px + 28px)}
    /* la rejilla de las filas vive en dos variables: el botón usa las mismas,
       así no pueden desalinearse al retocar una sola */
    .blk.der{--col-nombre:200px;--col-hueco:60px}
    .blk.der .level{grid-template-columns:minmax(0,var(--col-nombre)) minmax(0,1fr);
      column-gap:var(--col-hueco)}
    /* el botón cierra la sección: se alinea con la columna del TEXTO, que es
       donde el ojo viene leyendo, no con la de los nombres. Usa la misma
       definición de rejilla que las filas, así no puede desalinearse. */
    .blk.der .cta{display:grid;
      grid-template-columns:minmax(0,var(--col-nombre)) minmax(0,1fr);
      column-gap:var(--col-hueco)}
    .blk.der .cta > *{grid-column:2;justify-self:start}
  }
  .par-medio .hueco{aspect-ratio:3/4}
  @media(max-width:959px){.par-medio .hueco{aspect-ratio:16/10}}

  /* ---------- cortina de entrada ----------
     Las cuatro rejas que ya nos costaron una pantalla en negro (cerebro-interfaces
     §7-bis.3-bis), aplicadas aquí:
       1. La retirada es CSS con `both`, así que se va sola aunque el JS no corra
          nunca. Ningún guion es requisito para que la página sea usable.
       2. El fotograma final lleva `visibility:hidden`, y el contenedor
          `pointer-events:none` desde el principio: ni intercepta clics ni cuenta.
       3. NO se bloquea el scroll. La receta del cerebro dice que lo ponga el mismo
          guion que lo quita; aquí se elimina el riesgo de raíz no bloqueándolo —
          la capa cubre la ventana durante 1.8s y el scroll detrás no molesta.
       4. `prefers-reduced-motion` la apaga entera, no la enseña a medias.

     Reparto del tiempo (§7-bis.3-ter): movimiento → PAUSA DE LECTURA → salida.
     El logo entra en .5s, se lee 0.55s, sale en .35s y el telón se va en .5s.
     Si se toca un número hay que tocar los tres retardos: están encadenados. */
  .cortina{display:none}
  /* SIN logo (Diego, 17-ago): la cortina es solo el blanco que los cuadritos
     deshacen en cuanto la página carga. El fade de abajo es la red sin JS. */
  .anima .cortina{position:fixed;inset:0;z-index:300;background:#000;
    pointer-events:none;
    animation:cortina-sale .6s var(--ease) .9s both}
  @keyframes logo-entra{from{opacity:0;transform:scale(.94)}to{opacity:1;transform:none}}
  @keyframes logo-sale{to{opacity:0}}
  @keyframes cortina-sale{to{opacity:0;visibility:hidden}}

  /* segunda visita de la sesión: ni se pinta */
  .anima.sin-cortina .cortina{display:none}

  /* Va al final y con la misma especificidad que la regla que enciende la
     cortina: si se declara antes, `.anima .cortina` lo pisa y la intro sale
     igual a quien pidió que no se moviera nada. */
  @media(prefers-reduced-motion:reduce){
    .anima .cortina{display:none}
  }

  /* ---------- entrada escalonada del hero ----------
     No usa observador: el hero está bajo la cortina desde el primer instante y
     un observador solo sabe de intersección con la ventana, no de OCLUSIÓN —
     el revelado se gastaba a puerta cerrada y al abrirse el telón ya estaba
     todo puesto. Aquí entra por animación con retardo, encadenada al telón.
     Los retardos suman: telón fuera a 2.8s, y el hero empieza a asomar antes
     de que termine de irse, que es lo que hace el relevo suave. */
  .anima .hero .wrap > *,
  .anima .hero-int .wrap > *{animation:asoma 1.15s var(--ease) both}
  .anima .hero .wrap > h1,
  .anima .hero-int .wrap > h1{animation-delay:1s}
  .anima .hero .wrap > .lede,
  .anima .hero-int .wrap > .lede{animation-delay:1.25s}
  .anima .hero .wrap > .cta{animation-delay:1.45s}
  /* segunda visita: no hay telón que esperar */
  .anima.sin-cortina .hero .wrap > h1,
  .anima.sin-cortina .hero-int .wrap > h1{animation-delay:.05s}
  .anima.sin-cortina .hero .wrap > .lede,
  .anima.sin-cortina .hero-int .wrap > .lede{animation-delay:.3s}
  .anima.sin-cortina .hero .wrap > .cta{animation-delay:.5s}
  @keyframes asoma{from{opacity:0;transform:translateY(30px)}to{opacity:1;transform:none}}

  /* el titular ya no necesita el relevo por clase de JS */
  .anima .h1-line > span{transform:none}

  @media(prefers-reduced-motion:reduce){
    .anima .hero .wrap > *,
    .anima .hero-int .wrap > *{animation:none}
  }

  /* el cuerpo de la tesis: dos párrafos de lectura, no una rejilla de tarjetas */
  .tesis{display:flex;flex-direction:column;gap:22px;margin-top:clamp(34px,5vh,56px)}
  .tesis p{color:var(--tx2);font-size:clamp(1.02rem,1.4vw,1.2rem);line-height:1.65;
    max-width:38em}
  .tesis strong{color:var(--tx);font-weight:700}

  /* ---------- página de contacto ----------
     UNA columna centrada, y en este orden: primero qué va a pasar si escribes,
     después por dónde más se nos encuentra, y hasta abajo el formulario. En dos
     columnas la secuencia numerada quedaba de barra lateral al formulario, o
     sea leyéndose de arriba abajo mientras el ojo iba de izquierda a derecha.

     La ley de centrado de esta casa tiene dos mitades y aquí se usan las dos:
     lo que es TEXTO se centra estrechando (el hero, los rótulos, el
     formulario); lo que es REJILLA se centra LLENANDO el ancho (los pasos),
     porque encogerla al texto más largo la vuelve a descolgar. */
  .contacto-hero{min-height:auto;padding-bottom:clamp(20px,3vh,40px);text-align:center}
  .contacto-hero h1,.contacto-hero .lede{margin-inline:auto}
  .contacto{display:flex;flex-direction:column;gap:clamp(52px,7vh,92px);
    padding-bottom:clamp(80px,12vh,150px)}
  .contacto-lado{display:flex;flex-direction:column;gap:clamp(44px,6vh,72px)}
  .bloque{display:flex;flex-direction:column;align-items:center;gap:20px}
  .bloque h2{font-size:15px;font-weight:700;color:var(--tx3);
    text-transform:uppercase;letter-spacing:.08em;text-align:center}

  /* los pasos SÍ son una secuencia, así que van numerados de verdad — y en una
     sola fila, que es como se lee una secuencia: de izquierda a derecha. */
  .pasos{list-style:none;display:grid;grid-template-columns:1fr;width:100%;
    gap:26px clamp(30px,4vw,52px);counter-reset:paso}
  @media(min-width:660px){.pasos{grid-template-columns:repeat(2,1fr);gap:34px clamp(30px,4vw,52px)}}
  @media(min-width:1080px){.pasos{grid-template-columns:repeat(4,1fr)}}
  .pasos li{display:grid;grid-template-columns:26px 1fr;gap:4px 14px;
    counter-increment:paso;align-content:start}
  .pasos li::before{content:counter(paso);grid-row:1/3;
    font-size:13px;font-weight:700;color:var(--tx3);
    font-variant-numeric:tabular-nums;padding-top:2px}
  .pasos b{font-size:16.5px;font-weight:700;letter-spacing:-.012em}
  .pasos span{color:var(--tx2);font-size:15.5px;line-height:1.55;max-width:34em}

  /* los canales sí son tres cosas equivalentes: en fila, y se parten solos */
  .canales{display:flex;flex-wrap:wrap;justify-content:center;
    gap:12px clamp(26px,3.5vw,48px)}
  .canales a{font-size:clamp(1.05rem,1.5vw,1.22rem);font-weight:700;
    letter-spacing:-.02em;transition:opacity .25s}
  .canales a:hover{opacity:.6}
  .bloque .nota{color:var(--tx3);font-size:14.5px;text-align:center}

  /* el formulario, centrado y estrecho: es texto que se escribe, no una
     rejilla que llenar. Los rótulos siguen a bandera izquierda dentro de él,
     porque un `label` centrado sobre su campo se lee como decoración. */
  #lead{width:100%;max-width:620px;margin-inline:auto}


  /* ---------- ESCENA: imagen a pantalla completa con el texto encima ----------
     La pieza que sustituye a los bloques de texto largo. La imagen ocupa toda
     la sección; el velo oscurece SOLO el lado donde vive la tipografía, para
     que el otro lado siga viéndose. Alterna de lado con .escena-der.
     El velo no es decoración: sin él el texto compite con la foto. */
  .escena{position:relative;min-height:92svh;display:flex;align-items:center;
    overflow:hidden;padding:clamp(70px,10vh,120px) 0}
  .escena-fondo{position:absolute;inset:0;z-index:0}
  .escena-fondo .hueco{width:100%;height:100%;border:0;border-radius:0}
  .escena-fondo img,.escena-fondo video{width:100%;height:100%;object-fit:cover}
  .escena-velo{position:absolute;inset:0;z-index:1;pointer-events:none;
    background:
      linear-gradient(90deg,rgba(0,0,0,.93) 0%,rgba(0,0,0,.84) 38%,
                            rgba(0,0,0,.34) 68%,rgba(0,0,0,.22) 100%),
      linear-gradient(180deg,#000 0%,rgba(0,0,0,.4) 14%,transparent 26%,
                             transparent 74%,rgba(0,0,0,.4) 86%,#000 100%)}
  .escena-der .escena-velo{background:
      linear-gradient(270deg,rgba(0,0,0,.93) 0%,rgba(0,0,0,.84) 38%,
                             rgba(0,0,0,.34) 68%,rgba(0,0,0,.22) 100%),
      linear-gradient(180deg,#000 0%,rgba(0,0,0,.4) 14%,transparent 26%,
                             transparent 74%,rgba(0,0,0,.4) 86%,#000 100%)}
  .escena > .wrap{position:relative;z-index:2;width:100%}
  .escena-texto{max-width:min(46%,620px)}
  @media(max-width:900px){.escena-texto{max-width:100%}}
  .escena-der .escena-texto{margin-left:auto}
  .escena h2{font-size:clamp(2.1rem,5.4vw,4rem);max-width:15ch}
  .escena .lede{margin-top:20px;max-width:30em;color:var(--tx)}
  .escena .cta{margin-top:clamp(28px,4vh,40px)}
  /* el número del paso, cuando la escena es parte de una secuencia */
  .escena .paso{display:block;font-size:14px;font-weight:700;color:var(--tx);
    letter-spacing:.1em;margin-bottom:18px}

  /* lista de pasos a tamaño de sección, cuando la secuencia es el contenido */
  .pasos-grandes{list-style:none;counter-reset:pg;display:flex;flex-direction:column;
    gap:clamp(34px,5vh,58px);margin-top:clamp(64px,10vh,130px)}
  .pasos-grandes li{counter-increment:pg;display:grid;grid-template-columns:1fr;gap:6px}
  @media(min-width:900px){
    .pasos-grandes li{grid-template-columns:minmax(0,480px) minmax(0,1fr);
      gap:10px 100px;align-items:start}
    .pasos-grandes li b{margin-top:-.191em}
    .pasos-grandes li span{margin-top:-.454em}
    .pasos-grandes li::before{grid-column:1;grid-row:1}
    .pasos-grandes li b{grid-column:1;grid-row:2}
    .pasos-grandes li span{grid-column:2;grid-row:2}
  }
  .pasos-grandes b{font-size:clamp(1.35rem,2.6vw,1.95rem);font-weight:900;
    letter-spacing:-.035em;line-height:1.06}
  /* El número cuelga del `li`, no del `b`: dentro del `b` empujaba el nombre
     hacia abajo y la descripción se alineaba con el NÚMERO en vez de con el
     título. Fuera, ocupa su propia fila y no arrastra a nadie. */
  .pasos-grandes li::before{content:counter(pg);font-size:13px;
    font-weight:700;color:var(--tx3);letter-spacing:.1em;
    font-variant-numeric:tabular-nums}
  .pasos-grandes span{color:var(--tx2);font-size:clamp(1rem,1.55vw,1.4rem);
    line-height:1.55}

  /* ---------- SLIDES DE PURO TEXTO: dos formas, y las dos LLENAN el ancho -------
     Decisión de Diego, 13-ago-2026, tomada sobre una página de variantes
     numeradas. Se descartaron las dos maneras de NO llenar: la columna
     estrecha centrada (usaba 730 de 1399 px y dejaba 740 muertos) y el bloque
     desplazado a un lado. Lo que queda son dos maneras de ocupar la página:

       DECLARACIÓN  la sección ES una frase. Tipografía grande de borde a
                    borde y el remate en tinta apagada. ~50 caracteres por
                    línea. Se usa cuando la idea cabe en dos frases.
       COLUMNAS     titular ancho y el cuerpo en dos columnas justificadas.
                    ~73 caracteres por línea. Se usa cuando hay prosa de veras.

     Y lo que NO se hace, porque fue el error de fondo: estrechar la caja y
     centrarla. Centrar una columna angosta no la ensancha, y justificar
     tampoco — justificar solo empareja el borde derecho del ancho que YA
     tienes. Lo que ocupa la página es la ESTRUCTURA, no la alineación. */
  @media(min-width:900px){
    /* Un titular de bloque tampoco se estrecha: sin tope usa el ancho y el
       `text-wrap:balance` de `.disp` reparte los renglones. */
    .blk > .wrap > h2{max-width:none}
    /* El botón sí va centrado: suelto a la izquierda bajo un bloque que ocupa
       todo el ancho se lee inclinado (corrección de Diego, 12-ago-2026). */
    .blk > .wrap > .cta{justify-content:center}
    /* Ninguna pieza de un bloque de texto se estrecha ni se centra: todas
       ocupan el ancho de la zona de contenido. Un `fit-content` aquí encoge
       las rejillas al texto más largo y las vuelve a descolgar. */
    .blk > .wrap > .cols,
    .blk > .wrap > .levels,
    .blk > .wrap > .caps,
    .blk > .wrap > .pasos-grandes,
    .blk > .wrap > .puntos{width:100%}
  }

  /* DECLARACIÓN. Hereda de `.disp` el peso y el interletraje; lo suyo es el
     tamaño contenido —para que quepan ~50 caracteres a todo lo ancho— y el
     remate apagado, que es lo que antes vivía suelto como entradilla. */
  .decl{font-size:clamp(1.9rem,4.2vw,3.4rem);letter-spacing:-.03em;
    line-height:1.12;max-width:none}
  @media(min-width:900px){.blk > .wrap > h2{margin-left:-.03em}}
  .decl .sigue{color:var(--tx3)}

  /* ---------- ÍNDICE DE PIEZAS: catálogo numerado a dos columnas ----------
     Nace de la queja de que tres páginas cerraban con la MISMA rejilla de
     tarjetas (.caps). Este es el cierre de Servicios: mismas piezas, pero
     leídas como inventario — filo entre filas y numeración tabular. */
  .piezas{list-style:none;counter-reset:pz;margin-top:clamp(56px,9vh,110px);
    display:grid;grid-template-columns:1fr;column-gap:clamp(44px,5vw,96px)}
  @media(min-width:860px){.piezas{grid-template-columns:repeat(2,1fr)}}
  .piezas li{counter-increment:pz;border-top:1px solid var(--line-soft);
    padding:clamp(22px,3.4vh,34px) 0;display:grid;grid-template-columns:auto 1fr;
    gap:4px 18px;align-content:start}
  .piezas li::before{content:counter(pz,decimal-leading-zero);grid-row:1/3;
    font-size:13px;font-weight:700;color:var(--tx3);
    font-variant-numeric:tabular-nums;padding-top:6px}
  .piezas b{font-size:clamp(1.2rem,1.9vw,1.6rem);font-weight:900;
    letter-spacing:-.03em;line-height:1.12}
  .piezas span{grid-column:2;color:var(--tx2);font-size:15.5px;line-height:1.55;
    max-width:36em}

  /* ---------- LO QUE NO SE HACE: la palabra tachada ----------
     El cierre de Proceso. La raya no es adorno: el layout dice lo mismo que el
     copy — esto está descartado. Una sola columna que llena por tamaño de
     letra, no por rejilla. */
  .no-lista{list-style:none;margin-top:clamp(56px,9vh,110px);
    display:flex;flex-direction:column;gap:clamp(34px,5.5vh,58px)}
  .no-lista del{font-size:clamp(1.9rem,4.2vw,3.4rem);font-weight:900;
    letter-spacing:-.035em;line-height:1.08;
    /* La tinta de la raya es GRIS OPACO a propósito: blanca con alfa se vuelve
       invisible justo encima de los glifos blancos —se veía solo en los huecos
       entre palabras— y el tachón es el mensaje del bloque. */
    text-decoration:line-through;text-decoration-thickness:.09em;
    text-decoration-color:#555}
  .no-lista span{display:block;margin-top:10px;color:var(--tx2);
    font-size:clamp(1rem,1.45vw,1.3rem);line-height:1.55;max-width:44em}

  /* ---------- CREDO: los principios como un solo texto corrido ----------
     El cierre de Nosotros. Sin titular .decl y sin rejilla: un rótulo chico y
     un solo bloque grande a dos tintas, donde el principio va en blanco y su
     porqué en tinta apagada. Es la anatomía del hero aplicada al cuerpo. */
  .credo{margin-top:clamp(36px,5.5vh,60px);
    font-size:clamp(1.5rem,3.1vw,2.7rem);font-weight:900;
    letter-spacing:-.033em;line-height:1.3;text-wrap:pretty;max-width:none}
  .credo b{color:var(--tx)}
  .credo span{color:var(--tx3)}

  /* ---------- variante DERECHA del ledger ----------
     Pedida por Diego (17-ago-2026) para "Página, panel, asistente." de
     Servicios: el mismo ledger de filas, espejeado — titular y nombres al filo
     derecho, la descripción a su izquierda. Completa el repertorio de ejes
     (izquierda / centro / derecha) sin estrechar nada. */
  .blk-d .wrap{text-align:right}
  /* bajo 900px el h2 conserva su tope de 16ch: sin el margen auto se queda
     pegado a la izquierda con el texto en bandera derecha — lo peor de ambos */
  .blk-d .wrap > h2{margin-left:auto}
  @media(min-width:900px){
    .blk-d .level{grid-template-columns:minmax(0,1fr) minmax(0,480px)}
    .blk-d .level h3{grid-column:2;grid-row:1}
    .blk-d .level p{grid-column:1;grid-row:1}
  }
  @media(hover:hover){.blk-d .level:hover h3{transform:translateX(-8px)}}

  /* ---------- variante CENTRADA de un bloque de texto ----------
     Corrección de Diego (16-ago-2026): con todo anclado a los costados, las
     páginas se leían "cuadradas" — cada slide pegada a un borde. Esta clase
     centra el CONTENIDO sin estrechar la caja (la ley del 13-ago sigue: no se
     encoge la columna, se reparte el texto simétrico en el ancho completo).
     Se alterna con las anclas de borde, no las sustituye. */
  .blk-c .wrap{text-align:center}
  .blk-c .wrap > h2{margin-inline:auto}
  .blk-c .lede{margin-inline:auto}
  .blk-c .no-lista span{margin-inline:auto}
  .blk-c .caps .cap{align-items:center;text-align:center}
  .blk-c .caps .cap p{margin-inline:auto}

  /* ================= NOSOTROS · lenguaje basement =================
     Pedido literal de Diego (17-ago-2026) sobre basement.studio: grotesca
     pesada tipo Helvetica, texto en GRIS en vez de blanco, tamaños más
     contenidos que los nuestros, etiqueta de sección + línea de filo, bloques
     de texto bold, recuadros de etiqueta, imágenes CONTENIDAS en marco (no
     full-bleed) y nada de heros enormes. Escopado a .bstm: vive solo en
     nosotros.html; si convence, se extiende página por página. */
  /* Geist: la fuente REAL de la referencia (medida con getComputedStyle el
     17-ago: Geist, peso 600 en todo, tracking −4%, line-height 0.9). Archivo
     fue la primera aproximación; se retiró al medir. */
  @font-face{font-family:GeistVar;
    src:url('fuentes/geist-var.woff2') format('woff2');
    font-weight:100 900;font-style:normal;font-display:swap}
  @font-face{font-family:GeistMonoVar;
    src:url('fuentes/geist-mono.woff2') format('woff2');
    font-weight:400 600;font-style:normal;font-display:swap}
  /* Texto BLANCO, no cremita — corrección literal de Diego. El gris queda
     solo en la estructura: títulos de sección y etiquetas, como allá. */
  .bstm{font-family:GeistVar,Satoshi,system-ui,sans-serif;
    --gris:#000;--gris2:#000;--gristit:#000;--filo:#000}

  /* título de sección GRANDE en gris — el nivel "Featured Projects":
     uno por página, con su línea de filo debajo cruzando el ancho */
  .tit-b{font-size:clamp(2.6rem,5.3vw,4.75rem);font-weight:600;
    color:var(--gristit);letter-spacing:-.04em;line-height:.9;
    padding-bottom:clamp(16px,2.2vh,26px);border-bottom:1px solid var(--filo);
    margin-bottom:clamp(20px,2.8vh,34px)}

  /* cabecera = réplica de la página People de la referencia: UNA palabra
     enorme a la izquierda y DOS columnas de texto grande bold a la derecha,
     las tres arrancando en la misma línea superior. Sin imagen aquí. */
  .cab-b{padding:calc(52px + clamp(36px,6vh,64px)) 0 clamp(48px,7vh,84px)}
  /* "Nosotros" tiene 8 letras contra las 6 de "People": a 8vw se encimaba con
     la primera columna de texto. El tope está medido para que quepa entero. */
  .cab-b h1{font-size:clamp(2.7rem,4.7vw,4.5rem);font-weight:600;color:var(--gris);
    letter-spacing:-.04em;line-height:.9}
  .cab-b-grid{display:grid;grid-template-columns:1fr;gap:clamp(30px,4.5vw,60px);
    align-items:start}
  @media(min-width:1000px){
    .cab-b-grid{grid-template-columns:minmax(0,.92fr) minmax(0,1.18fr) minmax(0,1fr);
      column-gap:clamp(44px,4.5vw,84px)}
  }
  .col-grande{font-size:clamp(1.35rem,2.4vw,2.25rem);font-weight:600;
    line-height:1.1;letter-spacing:-.028em;color:var(--gris)}
  /* compensación óptica: las columnas nacen alineadas al TOPE del titular */
  @media(min-width:1000px){.col-grande{margin-top:.35em}}

  /* sección con etiqueta y línea de filo — la retícula de la referencia */
  /* Sin rayas divisorias, el ESPACIO es lo único que separa una sección de
     otra: se duplica el aire (Diego, 17-ago). Va en dos mitades — arriba y
     abajo — para que el hueco entre secciones sea la suma de las dos. */
  .sec-b{padding:clamp(52px,7.5vh,104px) 0}
  /* Las secciones NO se abren con una raya: en la referencia el filo solo
     aparece bajo el TÍTULO GRANDE y entre filas de una lista (Diego, 17-ago:
     "hay exceso de líneas"). La separación la hace el espacio. */
  .sec-b .wrap > :first-child{padding-top:clamp(12px,1.8vh,20px)}
  /* etiqueta de sección chica — 24px gris #757575 en la referencia */
  .etq-b{font-size:clamp(17px,1.55vw,22px);font-weight:600;color:var(--gris2);
    letter-spacing:-.03em;margin-bottom:clamp(18px,2.6vh,30px)}

  /* dos columnas: rótulo chico gris + párrafo grande bold gris */
  .dos-b{display:grid;grid-template-columns:1fr;gap:clamp(32px,4.5vw,64px)}
  @media(min-width:900px){.dos-b{grid-template-columns:repeat(2,1fr)}}
  /* anatomía de la retícula Services de la referencia: rótulo gris con LÍNEA
     de filo debajo cruzando su columna, y el párrafo en texto GRANDE */
  .dos-b h3{font-size:clamp(17px,1.55vw,22px);font-weight:600;color:var(--gris2);
    letter-spacing:-.03em;padding-bottom:12px;margin-bottom:18px;
    border-bottom:1px solid var(--filo)}
  .dos-b p{font-size:clamp(1.5rem,2.7vw,2.5rem);font-weight:600;line-height:1.08;
    letter-spacing:-.032em;color:var(--gris)}

  /* declaración grande junto a imagen GRANDE — la imagen manda en la fila */
  .giro-b{display:grid;grid-template-columns:1fr;gap:clamp(28px,4vw,72px);
    align-items:center}
  @media(min-width:960px){.giro-b{grid-template-columns:minmax(0,1.45fr) minmax(0,1fr)}}
  .paisaje-b{aspect-ratio:4/3;border-radius:0}

  /* banda de imagen a TODO el ancho del contenido — el plano gigante que la
     referencia mete en Services; una por página como mucho */
  .banda-b{margin-top:clamp(30px,4.5vh,52px)}
  .banda-b .hueco,.banda-b.hueco{aspect-ratio:21/10;border-radius:0}

  /* ---------- EMPALME al hacer scroll ----------
     La sección marcada se queda FIJA al llegar arriba y la siguiente se le
     monta encima (referencia en video, 17-ago). Pura posición sticky: cero
     JS, cero costo. Exige que toda sección tenga fondo opaco. */
  .bstm section{background:var(--bg)}
  .apila{position:sticky;top:0;z-index:0}
  .apila ~ section{position:relative;z-index:1}
  .mega-b{font-size:clamp(1.7rem,3.2vw,2.9rem);font-weight:600;line-height:1.08;
    letter-spacing:-.03em;color:var(--gris)}

  /* cuatro capacidades con recuadros de etiqueta — el patrón Capabilities */
  .cuatro-b{display:grid;grid-template-columns:1fr;gap:clamp(30px,4vw,52px)}
  @media(min-width:720px){.cuatro-b{grid-template-columns:repeat(2,1fr)}}
  @media(min-width:1160px){.cuatro-b{grid-template-columns:repeat(4,1fr)}}
  .cuatro-b h3{font-size:clamp(1.1rem,1.4vw,1.25rem);font-weight:600;letter-spacing:-.02em;color:var(--tx)}
  .cuatro-b p{margin-top:12px;font-size:clamp(15.5px,1.4vw,20px);font-weight:600;
    line-height:1.28;letter-spacing:-.02em;color:var(--tx);max-width:30em}
  .tags-b{display:flex;flex-wrap:wrap;gap:6px;margin-top:16px}
  /* chip: caja de tinta con letra en papel — el negativo del bloque */
  .tags-b span{font-size:12px;font-family:var(--mono);font-weight:500;
    text-transform:uppercase;letter-spacing:.02em;color:var(--bg);
    background:var(--tx);padding:4px 9px;border-radius:3px}

  /* dentro del lenguaje basement el texto va blanco y el peso es 600, también
     en las piezas que nacieron fuera de él (ledgers .piezas y .levels) */
  .bstm .no-lista span{color:var(--tx)}
  .bstm .piezas b,.bstm .levels h3{font-weight:600;letter-spacing:-.025em}
  .bstm .piezas span,.bstm .levels p{color:var(--tx);font-weight:600}
  .bstm .no-lista del{font-weight:600;letter-spacing:-.035em}

  /* fila de medio contenido + texto al lado — patrón Featured Projects:
     la pieza va en marco dentro de la retícula, nunca a sangre */
  /* la pieza de media DOMINA la fila — en la referencia la imagen come más de
     media pantalla; una imagen tímida no es el lenguaje (Diego, 17-ago) */
  .media-b{display:grid;grid-template-columns:1fr;gap:clamp(26px,3.5vw,64px);
    align-items:start}
  @media(min-width:960px){
    .media-b{grid-template-columns:minmax(0,1.6fr) minmax(0,1fr)}
  }
  .media-b .hueco{aspect-ratio:16/10;border-radius:0}
  /* foto real dentro de la fila de media: mismo tamaño que el hueco que
     sustituye, recortada a la proporción y en blanco y negro por diseño */
  .marco-foto{position:relative;aspect-ratio:16/10;overflow:hidden;
    border:1px solid var(--tx);background:var(--bg)}
  /* Las fotos van A COLOR (Diego, 18-ago: "tampoco quiero todo en blanco y
     negro"). La interfaz sigue monocroma y el color entra SOLO por el
     contenido: es lo que evita que el sitio se lea como collage. El leve
     realce de contraste se queda para que la foto no compita en flojera con
     la tipografía negra. */
  .marco-foto img{width:100%;height:100%;object-fit:cover;filter:contrast(1.04)}
  .media-b .marco-video{position:relative;aspect-ratio:16/10;overflow:hidden;
    border:1px solid var(--tx);background:#000}
  .media-b .marco-video video{position:absolute;inset:0;width:100%;height:100%;
    object-fit:cover}

  /* (la malla de recuadros con filo se retiró el 17-ago: Diego la leyó como
     "recuadros flotantes" — las piezas van en columnas limpias, sin caja) */

  /* ---------- sección MANIFIESTO — la anatomía Capabilities calcada ----------
     Tres piezas con dos márgenes distintos, y ahí está el truco que rompe la
     monotonía: la etiqueta y las columnas van INDENTADAS (~11% del ancho), la
     declaración gigante gris corre desde el borde del contenido. Las columnas
     usan letra más chica: es donde SÍ cabe el texto largo sin saturar. */
  .capa-etq{font-size:clamp(17px,1.55vw,22px);font-weight:600;color:var(--gris2);
    letter-spacing:-.03em;margin-bottom:clamp(20px,3vh,34px);
    margin-inline-start:clamp(0px,11vw,160px)}
  .capa-decl{font-size:clamp(2.1rem,5.3vw,4.75rem);font-weight:600;
    color:var(--gristit);letter-spacing:-.04em;line-height:.96;
    margin-bottom:clamp(48px,8vh,110px)}
  .capa-cols{display:grid;grid-template-columns:1fr;gap:clamp(32px,4vw,56px);
    margin-inline-start:clamp(0px,11vw,160px)}
  @media(min-width:720px){.capa-cols{grid-template-columns:repeat(2,1fr)}}
  @media(min-width:1160px){.capa-cols{grid-template-columns:repeat(4,1fr)}}
  .capa-cols h3{font-size:clamp(1.15rem,1.6vw,1.5rem);font-weight:600;
    letter-spacing:-.02em;color:var(--tx)}
  .capa-cols p{margin-top:16px;font-size:clamp(1rem,1.35vw,1.25rem);
    font-weight:600;line-height:1.3;letter-spacing:-.02em;color:var(--tx);
    max-width:24em}
  /* chips RELLENOS, como los de la referencia: tinta clara sobre gris, sin borde */
  .capa-cols .tags-b{margin-top:18px}
  .capa-cols .tags-b span{border:0;background:var(--tx);
    color:var(--bg);border-radius:2px}

  /* pasos numerados en columnas — el número chico gris arriba, como etiqueta */
  .pasos-b{list-style:none;counter-reset:pb;display:grid;grid-template-columns:1fr;
    gap:clamp(30px,4vw,52px)}
  @media(min-width:760px){.pasos-b{grid-template-columns:repeat(2,1fr)}}
  @media(min-width:1160px){.pasos-b.p4{grid-template-columns:repeat(4,1fr)}
    .pasos-b.p3{grid-template-columns:repeat(3,1fr)}}
  .pasos-b li{counter-increment:pb}
  .pasos-b li::before{content:"0" counter(pb);display:block;font-size:13px;
    font-family:var(--mono);font-weight:500;color:var(--gris2);
    font-variant-numeric:tabular-nums;margin-bottom:10px}
  .pasos-b b{display:block;font-size:clamp(1.1rem,1.4vw,1.25rem);font-weight:600;
    letter-spacing:-.02em;color:var(--tx)}
  .pasos-b span{display:block;margin-top:10px;font-size:clamp(15px,1.3vw,18px);
    font-weight:600;line-height:1.3;letter-spacing:-.015em;color:var(--tx);max-width:30em}

  /* variante de 3 columnas del patrón Capabilities */
  @media(min-width:1160px){.cuatro-b.n3{grid-template-columns:repeat(3,1fr)}}
  /* texto de apoyo de las columnas Capabilities cuando lleva más prosa */
  .cuatro-b.n3 p{font-size:clamp(1rem,1.25vw,1.15rem)}

  /* cabecera del inicio — la home de la referencia: titular GIGANTE de borde a
     borde, bajada bold abajo a la izquierda y un vacío negro enorme antes de
     la siguiente sección (pedido de Diego: "pon un espacio enorme para hero").
     Es tipografía, no foto: el vacío es parte de la composición. */
  /* La portada ya NO reserva pantalla completa: con la banda dentro, el 92svh
     dejaba la imagen cortada por el borde inferior (Diego, 17-ago). Ahora el
     conjunto titular + bajada + botón + banda se compone para caber. */
  /* la portada es la pieza sola: casi sin aire arriba, para que la imagen
     empiece pegada a la barra como la escena de la referencia */
  .port-b{padding:calc(52px + 10px) 0 clamp(20px,3vh,36px)}
  .port-b h1{font-size:clamp(2.6rem,6.4vw,5.6rem)}
  /* la banda de portada se limita por ALTO: manda la ventana, no la proporción */
  .port-b .banda-b{margin-top:0}
  @media(min-width:960px){
    /* el alto sale de lo que SOBRA de ventana bajo el titular (~32rem de
       nav + titular + bajada + botón), no de una fracción fija: así la banda
       cabe entera también en pantallas chaparras de portátil */
    /* sin titular encima, la imagen se lleva casi toda la ventana */
    .port-b .banda-b.hueco{min-height:0;aspect-ratio:auto;
      height:calc(100svh - 52px - 34px)}
  }
  .port-b h1{font-size:clamp(2.9rem,7.6vw,7rem);font-weight:600;color:var(--tx);
    letter-spacing:-.04em;line-height:.9;text-wrap:balance}
  /* Medida MEDIDA contra la referencia (17-ago): su bajada ocupa el 54% del
     ancho de ventana y ~59 caracteres por línea; la nuestra iba al 69% y
     cruzaba media página. 36em a 21.6px ≈ 780px ≈ 54% en 1440. */
  .baja-b{margin-top:clamp(20px,3.2vh,34px);max-width:36em;
    font-size:clamp(1.05rem,1.5vw,1.35rem);font-weight:600;line-height:1.3;
    letter-spacing:-.02em;color:var(--tx)}
  .port-b .cta{margin-top:clamp(26px,4vh,40px)}

  /* fila de PROYECTO — el patrón Featured Projects medido en la referencia:
     media contenida a la izquierda (~58%), y a la derecha el párrafo arriba,
     el nombre del proyecto GRANDE al filo derecho y las categorías al fondo */
  .proy-b{display:grid;grid-template-columns:1fr;gap:clamp(22px,3vw,48px);
    padding:clamp(26px,4vh,44px) 0;border-top:1px solid var(--filo)}
  .proy-b:first-of-type{border-top:0;padding-top:0}
  @media(min-width:960px){.proy-b{grid-template-columns:minmax(0,1.35fr) minmax(0,1fr)}}
  .proy-b .hueco{aspect-ratio:16/10}
  .proy-info{display:flex;flex-direction:column;gap:clamp(20px,3vh,34px)}
  .proy-info .arriba{display:flex;flex-direction:column;gap:18px}
  @media(min-width:1200px){
    .proy-info .arriba{flex-direction:row;justify-content:space-between;gap:32px}
  }
  .proy-info p{font-size:clamp(1rem,1.4vw,1.25rem);font-weight:600;line-height:1.28;
    letter-spacing:-.02em;color:var(--tx);max-width:24em}
  .proy-info .nombre{font-size:clamp(1.7rem,2.6vw,2.4rem);font-weight:600;
    letter-spacing:-.035em;line-height:1;color:var(--tx);white-space:nowrap}
  .proy-info .cats{margin-top:auto;display:flex;flex-direction:column;gap:4px}
  .proy-info .cats span{font-size:clamp(1rem,1.3vw,1.2rem);font-weight:600;
    letter-spacing:-.02em;color:var(--tx)}

  /* cierre de contacto — puro texto grande, SIN caja ni fondo. La versión con
     rayado diagonal se retiró (Diego, 17-ago): usaba el mismo patrón que los
     huecos de imagen pendiente y se leía como una imagen que no cargó. */
  .caja-b{display:block;transition:opacity .3s var(--ease)}
  .caja-b:hover{opacity:.72}
  .caja-b span{display:block;font-size:clamp(1.9rem,4.4vw,3.6rem);font-weight:600;
    letter-spacing:-.035em;line-height:1.02;color:var(--gris)}
  .caja-b .correo-b{color:var(--tx);margin-top:.15em}

  /* ---------- transición de página en CUADRITOS (referencia basement) ----------
     Al navegar entre páginas internas: una retícula de celdas negras cubre la
     pantalla en orden aleatorio, se navega, y en la página nueva se disuelve
     al revés. Solo anima OPACIDAD con steps(1) — composición pura, cero
     repintado (§7-bis). El orden aleatorio vive en el animation-delay inline
     de cada celda. Si el JS no corre, no existe: los enlaces navegan normal. */
  .trans-b{position:fixed;inset:0;z-index:200;pointer-events:none;display:grid}
  .trans-b div{background:#000;opacity:0}
  .trans-b.cubre div{animation:tb-in .01s steps(1) forwards}
  /* la disolución NO arranca al montar: el guion agrega .va cuando la página
     ya terminó de cargar. Medido (17-ago): si arranca durante la carga, el
     hilo se congela ~300ms a media disolución y los cuadritos que faltaban se
     quedan pegados en pantalla — ese era el "bug" del final del efecto. */
  .trans-b.revela div{opacity:1}
  .trans-b.revela.va div{animation:tb-out .01s steps(1) forwards}
  /* (la variante .blanca ya no hace falta: todos los cuadritos son blancos) */
  @keyframes tb-in{to{opacity:1}}
  @keyframes tb-out{to{opacity:0}}
  /* pre-telón: pinta negro ANTES de que el JS arme las celdas en la página
     que llega, para que no se vea un destello del contenido sin cubrir */
  html.trans-llega::before{content:"";position:fixed;inset:0;background:#000;
    z-index:199}

  /* COLUMNAS. La partición de palabras es lo que evita que el justificado
     abra huecos entre palabras; necesita el `lang="es"` del documento. */
  .cols{margin-top:clamp(34px,5vh,56px);display:grid;
    gap:clamp(28px,3vw,54px);grid-template-columns:1fr}
  @media(min-width:900px){.cols{grid-template-columns:repeat(2,1fr)}}
  .cols p{color:var(--tx2);font-size:clamp(1.05rem,1.32vw,1.2rem);
    line-height:1.62;text-align:justify;hyphens:auto;-webkit-hyphens:auto}
  .cols strong{color:var(--tx);font-weight:700}


  /* El alto mínimo de las piezas de media va SOLO en escritorio: junto a
     `aspect-ratio` en móvil manda el alto y la proporción infla el ANCHO —
     756px de pieza dentro de una pantalla de 390 (medido 17-ago). */
  @media(min-width:960px){
    .media-b .hueco,.marco-foto,.media-b .marco-video{min-height:min(56vh,560px)}
    .paisaje-b{min-height:min(62vh,620px)}
    .banda-b .hueco,.banda-b.hueco{min-height:min(66vh,660px)}
  }

  /* ---------- FILAS APILADAS (patrón Featured Projects) ----------
     Lo que Diego pidió, medido en la referencia: cada proyecto es una FILA
     —media ancha a la izquierda, texto a la derecha— y al hacer scroll la
     fila se queda pegada arriba mientras la siguiente se le monta encima,
     como una baraja de tarjetas. Es `position:sticky` puro: cero JS, cero
     coste, y solo funciona si cada fila lleva fondo OPACO. */
  .apilada{position:sticky;top:52px;background:var(--bg);
    border-top:1px solid var(--filo);
    padding:clamp(18px,2.6vh,30px) 0 clamp(26px,4vh,48px);
    display:grid;grid-template-columns:1fr;gap:clamp(18px,2.5vw,36px)}
  @media(min-width:960px){
    /* El texto arranca a la ALTURA DEL TOPE de la imagen, como en la
       referencia (Diego, 17-ago): párrafo pegado arriba y, debajo, las
       categorías a modo de subtítulo. El blanco que sobra queda abajo, que
       es donde la fila siguiente se monta. */
    .apilada{grid-template-columns:minmax(0,1.55fr) minmax(0,1fr);
      align-items:start}
  }
  /* la media de la fila: ancha, a escuadra y con la cuadrícula de fondo */
  .apilada .marco-video,.apilada .hueco,.apilada .marco-foto{
    position:relative;overflow:hidden;
    aspect-ratio:16/9;width:100%;min-height:0;border-radius:0}
  .apilada .marco-video video{position:absolute;inset:0;width:100%;height:100%;
    object-fit:cover}
  .apilada-info{display:flex;flex-direction:column;gap:clamp(12px,1.8vh,20px)}
  .apilada-info .arriba{display:flex;flex-direction:column;gap:14px}
  .apilada-info p{font-size:clamp(1.05rem,1.45vw,1.3rem);font-weight:600;
    line-height:1.28;letter-spacing:-.02em;color:var(--tx);max-width:24em}
  /* subtítulo de la fila: dos líneas de categoría bajo el párrafo, en el
     gris de estructura. NO va al fondo (`margin-top:auto`) porque la fila
     siguiente se monta encima y lo tapaba. */
  .apilada-info .pie-fila-b{display:flex;flex-direction:column;gap:2px;
    font-size:clamp(1rem,1.3vw,1.2rem);font-weight:600;letter-spacing:-.02em;
    color:var(--gris2)}

  /* ---------- DÍPTICO: dos piezas juntas, mismo alto, con su pie ----------
     Pedido de Diego (17-ago): las dos imágenes de la home van PAREJAS, no una
     por sección. Comparten fila y proporción; cada una lleva su rótulo debajo. */
  .dip-b{display:grid;grid-template-columns:1fr;gap:clamp(24px,3vw,40px)}
  @media(min-width:900px){.dip-b{grid-template-columns:1fr 1fr}}
  .dip-b figure{display:flex;flex-direction:column;gap:clamp(14px,2vh,20px)}
  .dip-b .marco-video,.dip-b .hueco{aspect-ratio:4/3;width:100%;
    min-height:0;position:relative;overflow:hidden}
  .dip-b figcaption{display:flex;flex-direction:column;gap:8px}
  .dip-b figcaption b{font-size:clamp(1.25rem,2vw,1.75rem);font-weight:600;
    letter-spacing:-.03em;line-height:1.1;color:var(--tx)}
  .dip-b figcaption span{font-size:clamp(1rem,1.25vw,1.15rem);font-weight:600;
    line-height:1.35;letter-spacing:-.015em;color:var(--tx);max-width:34em}
  /* dentro del díptico el video llena su marco (fuera de .media-b no heredaba
     el posicionamiento absoluto y quedaba a su tamaño intrínseco) */
  .dip-b .marco-video video{position:absolute;inset:0;
    width:100%;height:100%;object-fit:cover}
  /* la primera fila apilada NO repite filo: el título de sección ya trae el
     suyo debajo y juntos se veían como una doble raya (Diego, 17-ago) */
  .tit-b + .apilada,.etq-b + .apilada,.capa-decl + .apilada{border-top:0}

  /* Titular de portada, ahora fuera del bloque de la imagen (Diego, 17-ago:
     "el hero es solo imagen, el titular baja debajo"). Va al final para ganar
     por orden a las reglas viejas de `.port-b h1`. */
  .bstm .tit-port{font-size:clamp(2.6rem,6.6vw,6rem);font-weight:600;
    color:var(--tx);letter-spacing:-.04em;line-height:.92;text-wrap:balance;
    max-width:none}



  /* El cierre de contacto se alinea con la columna indentada del manifiesto
     (la de "En hojas de cálculo"), no con el filo de la página: pedido de
     Diego (17-ago) para que el remate no quede suelto al borde. */
  .cierre-b{margin-inline-start:clamp(0px,11vw,160px)}
  /* La ÚLTIMA fila apilada no necesita su colchón inferior: sumado al de la
     sección y al de la siguiente daba 171px de vacío tras la imagen
     (Diego, 17-ago). Las filas intermedias lo conservan: ahí el colchón es
     lo que deja ver la fila de abajo montándose. */
  .apilada:last-of-type{padding-bottom:0}
  section:has(.apilada){padding-bottom:clamp(30px,4vh,56px)}

  /* ---------- La fuente del sitio es GEIST, también fuera del contenido ----
     El pie, la barra y los botones seguían en Satoshi (la tipografía de la
     etapa anterior) porque el lenguaje nuevo se declaró solo en `.bstm`:
     se notaba justo en el pie, que convive con texto Geist (Diego, 17-ago).
     FIRMA: comparar `fontFamily` de una pieza de chrome contra una de
     contenido — si no coinciden, hay dos tipografías conviviendo. */
  body{font-family:GeistVar,Satoshi,system-ui,-apple-system,sans-serif}
  .pie-lado,.pie-enlaces a,nav.links a,.sheet a,.btn,form button,
  .field label,.field input,.field textarea,.msg{
    font-family:GeistVar,Satoshi,system-ui,sans-serif}

  /* el pie: mismo cuerpo en sus tres zonas y aire propio entre renglones */
  .pie-lado,.pie-enlaces a{font-size:12.5px;font-weight:600;
    line-height:1.35;letter-spacing:.06em}
  .pie-enlaces{gap:clamp(18px,2.6vw,36px)}

  /* ---------- FILA DE VALORES (patrón Our Values de la referencia) --------
     MEDIDO en basement.studio/people a 1440px: tres columnas IGUALES de
     461px — titular grande a la izquierda, imagen vertical (0.74) al centro,
     párrafo de 20px a la derecha — con filo entre filas. Nada de "una de
     texto y otra de imagen": las tres conviven en la misma fila. */
  .valores-b{display:flex;flex-direction:column}
  .valor-b{display:grid;grid-template-columns:1fr;gap:clamp(20px,2.4vw,30px);
    padding:clamp(24px,3.4vh,40px) 0;border-top:1px solid var(--filo)}
  @media(min-width:960px){
    .valor-b{grid-template-columns:repeat(3,1fr);gap:clamp(16px,1.6vw,24px);
      align-items:start}
  }
  .valor-b h3{font-size:clamp(2.1rem,4.4vw,4.75rem);font-weight:600;
    letter-spacing:-.04em;line-height:.94;color:var(--tx);margin:0}
  .valor-b .hueco{aspect-ratio:3/4;border-radius:0;width:100%}
  .valor-b p{font-size:clamp(1.05rem,1.4vw,1.25rem);font-weight:600;
    line-height:1.3;letter-spacing:-.02em;color:var(--tx);margin:0}

  /* Marco de la captura de producto: la pieza va a escuadra y con filo, sin
     esquinas redondeadas ni sombras — es una lámina, no una tarjeta. La
     captura ya trae su propio blanco, así que NO se le aplica el filtro de
     grises de las fotos (es interfaz, no fotografía). */
  .marco-panel{position:relative;overflow:hidden;border:1px solid var(--tx);
    background:var(--bg);aspect-ratio:1760/838}
  .marco-panel img{width:100%;height:100%;object-fit:cover;object-position:top left}

  /* ================= CONTACTO: LA TERMINAL =================
     Adaptación del efecto de basement (Diego, 18-ago): allá el formulario vive
     dentro de un walkie-talkie 3D; aquí vive dentro de una TERMINAL — la misma
     idea (el formulario es un objeto que se abre, no una sección más) sin
     modelo 3D ni megas de descarga. Todo lo que se mueve es transform y
     opacity, que son gratis (§7-bis). */
  .term-velo{position:fixed;inset:0;z-index:150;background:rgba(0,0,0,.55);
    opacity:0;visibility:hidden;transition:opacity .35s var(--ease),visibility .35s}
  body.term-abierta .term-velo{opacity:1;visibility:visible}

  .term{position:fixed;z-index:160;inset-inline:var(--gutter);bottom:0;
    margin-inline:auto;max-width:900px;
    background:#000;border:1px solid #000;
    transform:translateY(100%);transition:transform .5s var(--ease);
    max-height:min(88svh,860px);overflow:auto}
    /* El estado del BODY se llama distinto que el componente: con las dos
     clases iguales, `body.term` hacía que el propio body casara con `.term`
     y se tragara `position:fixed` y el `translateY(100%)` — pantalla negra y
     todo desplazado una ventana (medido 18-ago). */
  body.term-abierta .term{transform:translateY(0)}
  @media(prefers-reduced-motion:reduce){
    .term,.term-velo{transition:none}
  }

  /* la carcasa: filo claro por dentro, como el bisel de una pantalla */
  .term-caja{border:1px solid #2a2a2a;margin:10px;padding:clamp(18px,2.4vw,30px);
    font-family:var(--mono);color:#fff}
  .term-barra{display:flex;align-items:center;justify-content:space-between;
    gap:16px;font-size:12px;letter-spacing:.06em;text-transform:uppercase;
    padding-bottom:14px;margin-bottom:20px;border-bottom:1px dashed #3a3a3a}
  .term-barra button{background:none;border:0;color:#fff;font:inherit;
    cursor:pointer;letter-spacing:.06em;transition:opacity .25s}
  .term-barra button:hover{opacity:.6}

  .term-campos{display:grid;grid-template-columns:1fr;gap:18px 24px}
  @media(min-width:720px){.term-campos{grid-template-columns:1fr 1fr}}
  .term-campo{display:flex;flex-direction:column;gap:6px}
  .term-campo.ancho{grid-column:1/-1}
  .term-campo label{font-size:11.5px;letter-spacing:.08em;text-transform:uppercase;
    color:#9a9a9a}
  .term-campo input,.term-campo textarea{
    background:transparent;border:0;border-bottom:1px dashed #3a3a3a;
    padding:6px 0;color:#fff;font-family:var(--mono);font-size:14px;
    transition:border-color .25s var(--ease)}
  .term-campo input:focus,.term-campo textarea:focus{outline:none;
    border-bottom-color:#fff}
  .term-campo textarea{resize:vertical;min-height:110px}
  .term-campo input::placeholder,.term-campo textarea::placeholder{color:#4a4a4a}

  /* el cursor que parpadea: es lo que hace que se lea como terminal */
  .term-cursor{display:inline-block;width:.55em;height:1em;background:#fff;
    vertical-align:-.12em;margin-left:.15em;animation:term-late 1.1s steps(1) infinite}
  @keyframes term-late{0%,49%{opacity:1}50%,100%{opacity:0}}
  @media(prefers-reduced-motion:reduce){.term-cursor{animation:none}}

  .term-enviar{grid-column:1/-1;margin-top:6px;width:100%;border-radius:0;
    background:transparent;border:1px solid #fff;color:#fff;
    font-family:var(--mono);font-size:13px;letter-spacing:.08em;
    text-transform:uppercase;padding:14px;cursor:pointer;
    transition:background-color .25s var(--ease),color .25s var(--ease)}
  .term-enviar:hover{background:#fff;color:#000}
  .term-pie{display:flex;flex-wrap:wrap;justify-content:space-between;gap:12px;
    margin-top:22px;padding-top:16px;border-top:1px dashed #3a3a3a;
    font-size:11.5px;letter-spacing:.06em;text-transform:uppercase;color:#9a9a9a}
  .term-pie a{color:#fff;transition:opacity .25s}
  .term-pie a:hover{opacity:.6}
  .term-msg{grid-column:1/-1;min-height:18px;font-size:12px;color:#9a9a9a}

  /* La acción del cierre tiene que LEERSE como acción (Diego, 18-ago: "nadie
     sabe que puede hacer clic"). Sin color de acento en la paleta, el
     distintivo es de FORMA: caja de tinta con letra en papel, que se invierte
     al pasar el cursor. Nada de subrayado, que está vetado. */
  .caja-b .correo-b{display:inline-block;background:var(--tx);color:var(--bg);
    padding:.04em .3em .12em;margin-top:.18em;
    transition:background-color .3s var(--ease),color .3s var(--ease)}
  .caja-b:hover .correo-b{background:var(--bg);color:var(--tx);
    box-shadow:inset 0 0 0 1px var(--tx)}
  .caja-b:hover{opacity:1}

  /* El cierre se parte en DOS piezas: la frase es TEXTO y solo "Agendar" es el
     enlace (Diego, 18-ago: el resalte saltaba con el cursor en cualquier lado
     porque el enlace envolvía el bloque entero, que ocupa todo el ancho).
     Ahora la zona sensible mide exactamente lo que mide la palabra. */
  .cierre-frase{font-size:clamp(1.9rem,4.4vw,3.6rem);font-weight:600;
    letter-spacing:-.035em;line-height:1.02;color:var(--tx);max-width:16ch}
  .agendar-b{display:inline-block;margin-top:.12em;
    font-size:clamp(1.9rem,4.4vw,3.6rem);font-weight:600;letter-spacing:-.035em;
    line-height:1.02;background:var(--tx);color:var(--bg);padding:.04em .3em .12em;
    box-shadow:inset 0 0 0 1px var(--tx);
    transition:background-color .3s var(--ease),color .3s var(--ease)}
  .agendar-b:hover{background:var(--bg);color:var(--tx)}

  /* el marco vertical acepta foto igual que hueco: misma proporción y filo */
  .marco-foto.vert-b{aspect-ratio:3/4}

  /* el marco de captura también existe en vertical (3:4) */
  .marco-panel.vert-b{aspect-ratio:3/4}
  .marco-panel.vert-b img{object-position:top left}

  /* ---------- PORTADA DE MARCA (Diego, 18-ago-2026: variante 3) ------------
     Sustituye al hueco de imagen 21:10 que abría el sitio. La marca ocupa la
     primera pantalla a tamaño de cartel y la frase de servicio va debajo.
     `svh` y no `vh`: en iOS la barra del navegador se come el 100vh y la
     frase quedaría bajo el pliegue, que es justo lo que esta portada no
     puede permitirse. */
  /* 100svh EXACTOS, sin descontar la barra: el header es `position:fixed`, así
     que no ocupa flujo — restarle 52px dejaba justo esa rendija por la que se
     asomaba la primera línea del párrafo siguiente (Diego, 18-ago: "que al
     entrar no se muestre texto cortado abajo"). `svh` y no `vh` porque en iOS
     el 100vh es el viewport GRANDE y la barra del navegador se comería otro
     tanto. Sigue siendo min-height: si la pantalla es muy baja, la portada
     crece con su contenido en vez de recortarlo. */
  .port-marca{min-height:100svh;display:flex;flex-direction:column;
    justify-content:center;padding-block:clamp(40px,6vh,80px)}
  /* El cartel YA NO es texto: es el logotipo vectorizado desde el PNG de marca
     (Diego, 18-ago: "ocupo la misma fuente del logo para estas letras
     grandes"). Geist no daba esas formas —la marca es lettering, no una
     tipografía que se pueda teclear—, así que se trazó el propio logo a SVG y
     se dibuja con `currentColor`: misma forma exacta, nítida a cualquier
     tamaño y sin una petición extra. El tamaño se manda por ANCHO, no por
     font-size. */
  .port-marca .marca-cartel{display:block;width:76%;height:auto;color:var(--tx)}
  .port-marca .frase-cartel{margin-top:clamp(18px,2.6vh,30px);
    font-size:clamp(1.15rem,2.1vw,2.1rem);font-weight:600;letter-spacing:-.02em;
    line-height:1.12;max-width:24ch;color:var(--tx);text-wrap:balance}
  /* La sección que sigue conserva su colchón superior, y aquí NO es estética:
     es el margen de seguridad para que un redondeo de subpíxel deje asomar
     blanco y nunca media línea de texto. */
  .port-marca + .sec-b{padding-top:clamp(34px,6vh,72px)}
  /* En móvil 26vw dejaba el cartel al 53% del ancho: gigante en escritorio y
     mediano en el teléfono, que es donde más se abre. Se sube a 40vw para que
     llene como cartel (medido: 81% del ancho útil a 390px). */
  @media(max-width:700px){
    .port-marca .marca-cartel{width:92%}
    .port-marca .frase-cartel{font-size:1.35rem;max-width:20ch}
  }
  /* ---------- LA MARCA DE PORTADA, HECHA DE BRASAS (Diego, 21-ago) ----------
     El SVG NO se va: es lo que se ve sin JavaScript, y esa es la regla dura de
     §5 (la landing se verifica con el script bloqueado). El lienzo se monta
     encima y solo cuando ya está listo el SVG se esconde CONSERVANDO SU HUECO
     — con `display:none` el hueco desaparecería y el lienzo, que se mide contra
     él, nacería de cero píxeles. */
  .port-marca .marca-brasas{position:relative;width:76%;margin-inline:auto}
  .port-marca .marca-brasas .marca-cartel{width:100%}
  .port-marca .marca-brasas canvas{position:absolute;inset:0;width:100%;height:100%;
    opacity:0;transition:opacity .28s var(--ease)}
  .port-marca .marca-brasas[data-brasas="on"] .marca-cartel{visibility:hidden}
  .port-marca .marca-brasas[data-brasas="on"] canvas{opacity:1}
  @media(max-width:700px){ .port-marca .marca-brasas{width:92%} }
  /* con movimiento reducido no hay brasas: se queda el logotipo, quieto */
  @media(prefers-reduced-motion:reduce){
    .port-marca .marca-brasas[data-brasas="on"] .marca-cartel{visibility:visible}
    .port-marca .marca-brasas canvas{display:none}
  }

  /* El logo de la barra se retira mientras el cartel de portada está a la
     vista: el nombre ya lo está diciendo la página a 26vw, y verlo dos veces
     en la misma pantalla es lo que se pidió quitar. Vuelve al bajar. La
     transición es de opacidad y transform, las dos baratas (§7-bis). */
  #nav .brand{transition:opacity .32s cubic-bezier(.22,.61,.36,1),
    transform .32s cubic-bezier(.22,.61,.36,1)}
  #nav.sin-marca .brand{opacity:0;transform:translateY(-6px);pointer-events:none}
  @media(prefers-reduced-motion:reduce){
    #nav .brand{transition-duration:.01ms}
    #nav.sin-marca .brand{transform:none}
  }

  /* ---------- EL APILADO NO SE FUNDE: TAPA (Diego, 18-ago) ----------
     Las filas apiladas llevan fondo opaco justamente para que la de abajo
     tape a la de arriba al montarse. Pero el revelado (`.rv`) le animaba la
     opacidad AL CONTENEDOR, y un fondo opaco dentro de una capa a opacity .4
     no tapa nada: durante toda la transición se veían las dos fotos mezcladas
     — la bodega encima de la gráfica.
     El fundido pasa a los HIJOS: el contenedor entra opaco desde el primer
     cuadro y lo que aparece es su contenido. Es la regla de §7-bis.2-bis
     ("en un cruce, taparse sale más barato que fundirse") aplicada al caso de
     fondo claro. Sigue siendo transform + opacity, o sea composición pura. */
  .anima .apilada.rv{opacity:1;transform:none;transition:none}
  .anima .apilada.rv > *{opacity:0;transform:translateY(22px);
    transition:opacity 1.15s var(--ease),transform 1.15s var(--ease)}
  .anima .apilada.rv.in > *{opacity:1;transform:none}
  .anima .apilada.rv.in > *:nth-child(2){transition-delay:.07s}
  @media(prefers-reduced-motion:reduce){
    .anima .apilada.rv > *{opacity:1!important;transform:none!important;
      transition:none}
  }
  /* Y la MEDIA de la fila no se funde en absoluto: entra opaca, tapando. Si se
     le anima la opacidad, durante ~1 s se ve un rectángulo blanco del tamaño
     de la foto, que es igual de feo que la mezcla que veníamos de arreglar.
     El fundido se queda donde no estorba: la columna de texto. */
  .anima .apilada.rv > figure,
  .anima .apilada.rv > .marco-foto,
  .anima .apilada.rv > .marco-video,
  .anima .apilada.rv > .hueco{opacity:1;transform:none;transition:none}

  /* EL MENÚ MÓVIL DECÍA "INICIOINICIO" (Diego, 18-ago, revisión en teléfono).
     Cada enlace del nav lleva DOS copias del rótulo para el efecto de hover de
     escritorio: allí `nav.links a` es un inline-grid con overflow:hidden que
     las apila y solo enseña una. La hoja móvil reusa el mismo marcado sin esas
     dos reglas, así que las copias se leían seguidas. En un teléfono no hay
     hover, así que la segunda sobra: se oculta. */
  .sheet a span:last-child{display:none}
  /* En teléfono los campos suben a 16px: por debajo de esa cifra Safari iOS
     hace ZOOM automático al enfocar el campo, y el visitante se queda con la
     página descuadrada a media captura de datos — justo en el formulario que
     es la conversión del sitio. Se sube solo en móvil para no engordar la
     estética de terminal en escritorio, donde el zoom no existe. */
  @media(max-width:700px){
    .term-campo input,.term-campo textarea{font-size:16px}
  }
