/* ==========================================================================
   animations.css — motion layer (crisp, mechanical, exact)
   Personality: engineering precision — short precise reveals, a circuit
   "draw-on", count-ups. Coherent easing, never a grab-bag.
   ========================================================================== */

/* scroll-reveal base — JS adds .in-view */
[data-reveal] {
  opacity: 0;
  transform: translateY(22px);
  transition:
    opacity var(--dur-3) var(--ease-out),
    transform var(--dur-3) var(--ease-out);
  transition-delay: calc(var(--i, 0) * 70ms);
}
[data-reveal].in-view { opacity: 1; transform: none; }

[data-reveal="mask"] {
  clip-path: inset(0 0 100% 0);
  opacity: 1;
  transform: none;
  transition: clip-path var(--dur-3) var(--ease-out);
  transition-delay: calc(var(--i, 0) * 70ms);
}
[data-reveal="mask"].in-view { clip-path: inset(0 0 0 0); }

/* hero on-load choreography (driven by html.is-loaded) */
.hero__copy > * {
  opacity: 0;
  transform: translateY(18px);
}
html.is-loaded .hero__copy > * {
  animation: rise var(--dur-3) var(--ease-out) forwards;
}
html.is-loaded .hero__copy > *:nth-child(1) { animation-delay: 0.05s; }
html.is-loaded .hero__copy > *:nth-child(2) { animation-delay: 0.14s; }
html.is-loaded .hero__copy > *:nth-child(3) { animation-delay: 0.23s; }
html.is-loaded .hero__copy > *:nth-child(4) { animation-delay: 0.32s; }
html.is-loaded .hero__copy > *:nth-child(5) { animation-delay: 0.41s; }

.hero__media {
  opacity: 0;
  clip-path: inset(0 0 0 0);
}
html.is-loaded .hero__media {
  animation: media-in var(--dur-3) var(--ease-out) 0.18s forwards;
}

@keyframes rise { to { opacity: 1; transform: none; } }
@keyframes media-in {
  from { opacity: 0; clip-path: inset(8% 8% 8% 8%); }
  to   { opacity: 1; clip-path: inset(0 0 0 0); }
}

/* SVG circuit trace draw-on */
.trace-path {
  stroke-dasharray: var(--len, 1200);
  stroke-dashoffset: var(--len, 1200);
}
html.is-loaded .trace-path {
  animation: draw 2.4s var(--ease-in-out) 0.3s forwards;
}
.trace-node { opacity: 0; }
html.is-loaded .trace-node { animation: node-pulse 0.5s var(--ease-out) 1.6s forwards; }
@keyframes draw { to { stroke-dashoffset: 0; } }
@keyframes node-pulse { to { opacity: 1; } }

/* pulsing "live" dot in rating badge */
.live-dot { position: relative; }
.live-dot::after {
  content: "";
  position: absolute; inset: 0;
  border-radius: 50%;
  box-shadow: 0 0 0 0 color-mix(in srgb, var(--c-ok) 60%, transparent);
  animation: ping 2.4s var(--ease-out) infinite;
}
@keyframes ping {
  0%   { box-shadow: 0 0 0 0 color-mix(in srgb, var(--c-ok) 55%, transparent); }
  70%  { box-shadow: 0 0 0 10px transparent; }
  100% { box-shadow: 0 0 0 0 transparent; }
}

/* fallback: if JS never runs, content must still show */
.no-js [data-reveal],
.no-js .hero__copy > *,
.no-js .hero__media { opacity: 1 !important; transform: none !important; clip-path: none !important; }

/* ---------- reduced motion: reveal everything, kill motion ---------- */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation: none !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
  [data-reveal],
  .hero__copy > *,
  .hero__media { opacity: 1 !important; transform: none !important; clip-path: none !important; }
  .trace-path { stroke-dashoffset: 0 !important; }
  .trace-node { opacity: 1 !important; }
  .marquee__track { animation: none !important; }
}
