/* Contigo · capa de movimiento
   Vocabulario tomado de la referencia Medora e interpretado con los tokens del
   sistema: entrada por elevación corta y opacidad, escalonada por bloques;
   fotografía que entra con una reducción mínima de escala; cabecera que se
   consolida al desplazar; y elevación en las piezas al pasar el puntero.

   Tres reglas que el sistema impone sobre la referencia:
   1. La distancia nunca supera 24 px. Un desplazamiento largo mueve el texto
      mientras se lee y, con gente mayor, eso se siente como un fallo.
   2. Nada aparece por debajo del 100 % de opacidad al final. Ningún texto queda
      atenuado a la espera de un evento.
   3. prefers-reduced-motion desactiva todo, no lo suaviza: el contenido queda
      visible y quieto desde el primer fotograma. */

@media (prefers-reduced-motion:no-preference){
  /* El ocultado depende de la clase js-motion, que añade motion.js justo antes
     de observar. Incondicional era un fallo grave: si el observador no disparaba,
     la página quedaba en blanco sin vuelta atrás. */
  .js-motion [data-mo]{opacity:0;transform:translate3d(0,var(--mo-y,18px),0)}
  .js-motion [data-mo="foto"]{opacity:0;transform:scale(1.035)}
  /* Mismo prefijo que las reglas de ocultado: si solo lo llevan estas últimas,
     su especificidad es mayor y ganan siempre, dejando todo invisible. */
  .js-motion [data-mo].mo--in{opacity:1;transform:none;
    transition:opacity .62s cubic-bezier(.22,.61,.36,1),transform .62s cubic-bezier(.22,.61,.36,1);
    transition-delay:var(--mo-d,0ms)}
  .js-motion [data-mo="foto"].mo--in{transition-duration:.9s}
  /* El titular de portada entra sin escalonar: es lo primero que se lee. */
  .port__t h1[data-mo]{--mo-y:22px}
  .port__t .port__p[data-mo]{--mo-d:90ms}
  .port__t .port__acc[data-mo]{--mo-d:170ms}
}

/* Cabecera: se consolida al desplazar. Hasta ahora --nav-solid estaba declarada
   y nunca se activaba; el guion la conmuta y la barra gana fondo y filete. */
.nav,.cab{transition:background-color .3s ease,box-shadow .3s ease,border-color .3s ease}
.cab.cab--solida{background:color-mix(in srgb,var(--white) 92%,transparent);backdrop-filter:blur(14px) saturate(1.15);-webkit-backdrop-filter:blur(14px) saturate(1.15);border-bottom-color:var(--piedra-200)}

/* Elevación al pasar el puntero. Sutil y solo donde hay destino. */
@media (hover:hover) and (prefers-reduced-motion:no-preference){
  .area,.pro,.dato,.svc{transition:transform .28s cubic-bezier(.22,.61,.36,1),box-shadow .28s ease}
  a:hover>.area,.area:has(a:hover),.pro:has(a:hover),.svc:has(a:hover){transform:translate3d(0,-3px,0)}
  .btn{transition:background-color .2s ease,transform .2s cubic-bezier(.22,.61,.36,1),box-shadow .2s ease}
  .btn:hover{transform:translate3d(0,-2px,0)}
  .btn:active{transform:none}
  .lam img,.pro__foto img{transition:transform .7s cubic-bezier(.22,.61,.36,1)}
  .lam:hover img,a:hover .pro__foto img{transform:scale(1.04)}
}

/* El foco nunca se mueve: una transición de transform sobre el foco desplaza el
   anillo mientras se navega con teclado. */
:focus-visible{transition:none!important;transform:none!important}


/* ── Capa GSAP + superficie procedural ──
   Vive aquí y no en web.css porque la home no carga web.css: motion.css es la
   única hoja que comparten las 17 rutas. */

/* Barra de progreso de lectura. transform-origin a la izquierda y scaleX 0:
   animar una transformación no fuerza recálculo de diseño en cada fotograma. */
.gs-prog{position:fixed;top:0;left:0;right:0;height:2px;z-index:200;transform:scaleX(0);transform-origin:0 50%;background:var(--oliva-600);pointer-events:none}
@media (prefers-reduced-motion:reduce){.gs-prog{display:none}}

/* Palabras del titular. inline-block para que yPercent tenga efecto. Sin
   overflow:hidden en el contenedor a propósito: una máscara convierte un tween
   que no arranca en un titular invisible. */
/* pre-wrap es imprescindible: el espacio va dentro del span y un espacio
   final en un inline-block se colapsa por defecto. */
.gs-w{display:inline-block;will-change:transform;white-space:pre-wrap}

/* Superficie procedural. El degradado es la reserva: si Three.js o WebGL no
   están, el texto se apoya en este fondo y nadie ve un hueco. */
[data-luz]{position:relative;isolation:isolate;background:linear-gradient(155deg,var(--mar-950) 0%,var(--mar-800) 52%,var(--mar-700) 100%)}
[data-luz]>*:not(canvas){position:relative;z-index:1}

/* Sin fotogramas: además de anular las duraciones, hay que REVELAR el estado
   final. El opacity:0 de [data-mo] y [data-reveal] es el estado BASE de su
   regla, no una transición a medias, así que anular la duración no lo tocaba:
   la entrada la aplica un guion que añade .mo--in / data-in cuando el elemento
   asoma, y ese barrido depende del reloj de fotogramas. En un documento que no
   compone se quedaban invisibles las fichas de profesional con sus retratos,
   los h2 de sección y los bloques de cuerpo: contenido publicado que nadie ve.
   Aquí el movimiento es un extra; el contenido, no. */
.sin-fotogramas [data-mo],.sin-fotogramas [data-reveal],.sin-fotogramas [data-words] span{opacity:1!important;transform:none!important;visibility:visible!important;clip-path:none!important}
