/* =========================================================================
   VECTOR ENGINEERING — ANIMATIONS
   Keyframes + scroll-reveal utility classes + reduced-motion governance.
   ========================================================================= */

/* ---- Generic reveal classes (driven by GSAP/IntersectionObserver via JS
   adding .is-visible; CSS defines the before/after states) ---- */
[data-reveal]{
  opacity: 0;
  transform: translateY(28px);
  transition: opacity 760ms var(--ease-out), transform 760ms var(--ease-out);
}
[data-reveal].is-visible{ opacity: 1; transform: translateY(0); }

[data-reveal="fade"]{ transform: none; }
[data-reveal="left"]{ transform: translateX(-36px); }
[data-reveal="left"].is-visible{ transform: translateX(0); }
[data-reveal="right"]{ transform: translateX(36px); }
[data-reveal="right"].is-visible{ transform: translateX(0); }
[data-reveal="scale"]{ transform: scale(0.92); }
[data-reveal="scale"].is-visible{ transform: scale(1); }

[data-reveal-group] [data-reveal]{ transition-delay: var(--reveal-delay, 0ms); }

@keyframes float-y{
  0%, 100%{ transform: translateY(0); }
  50%{ transform: translateY(-14px); }
}
@keyframes pulse-ring{
  0%{ transform: scale(0.92); opacity: 0.6; }
  70%{ transform: scale(1.25); opacity: 0; }
  100%{ opacity: 0; }
}
@keyframes spin-slow{
  to{ transform: rotate(360deg); }
}
@keyframes shimmer{
  0%{ background-position: -200% 0; }
  100%{ background-position: 200% 0; }
}
@keyframes marquee{
  from{ transform: translateX(0); }
  to{ transform: translateX(-50%); }
}

.float{ animation: float-y 5.5s var(--ease-in-out) infinite; }
.spin-slow{ animation: spin-slow 18s linear infinite; }

/* ---- Skeleton shimmer for lazy media before load ---- */
.skeleton{
  background: linear-gradient(90deg, var(--bg-alt) 25%, var(--border) 37%, var(--bg-alt) 63%);
  background-size: 400% 100%;
  animation: shimmer 1.6s ease-in-out infinite;
}

/* =========================================================================
   REDUCED MOTION
   Two triggers set the SAME state:
   1) OS-level prefers-reduced-motion
   2) Manual toggle in the a11y panel -> html[data-motion="reduced"]
   ========================================================================= */
html[data-motion="reduced"] *,
html[data-motion="reduced"] *::before,
html[data-motion="reduced"] *::after{
  animation-duration: 0.001ms !important;
  animation-iteration-count: 1 !important;
  transition-duration: 0.001ms !important;
  scroll-behavior: auto !important;
}
html[data-motion="reduced"] [data-reveal]{
  opacity: 1 !important;
  transform: none !important;
}
html[data-motion="reduced"] .float,
html[data-motion="reduced"] .spin-slow{ animation: none !important; }

@media (prefers-reduced-motion: reduce){
  html:not([data-motion="forced-on"]) [data-reveal]{
    opacity: 1; transform: none; transition: none;
  }
  html:not([data-motion="forced-on"]) *{
    animation-duration: 0.001ms !important;
    transition-duration: 0.001ms !important;
  }
}

/* No-JS fallback: ensure all content is visible without scripting */
.no-js [data-reveal]{ opacity: 1 !important; transform: none !important; }
.no-js .page-loader{ display: none !important; }
