/* ============================================================
   Motion layer - keyframes + reveal pattern + reduced-motion.
   Durations/easings follow the extracted motion spec:
   0.25s / 0.3s / 0.5s / 0.7s scale; cubic-bezier(0,.25,.5,1) for fills.
   ============================================================ */

/* --- scroll reveal --- */
html.js .reveal {
  opacity: 0;
  transform: translateY(40px);
  transition:
    opacity 0.3s cubic-bezier(0.4, 0, 0.2, 1),
    transform 0.3s cubic-bezier(0.4, 0, 0.2, 1);
}
html.js .reveal.visible {
  opacity: 1;
  transform: translateY(0);
}

/* --- wave: per-letter shimmer on accent words --- */
.wave-word { display: inline-block; white-space: nowrap; }
.wave-letter {
  display: inline-block;
  animation: wave 2.4s ease infinite;
  transform-origin: 50% 70%;
}
@keyframes wave {
  0% { transform: translate3d(0, 0, 0) scale(1) rotateY(0deg); text-shadow: 0 0 0 rgb(255 235 216 / 0); }
  12% { transform: translate3d(2px, -2px, 2px) scale(1.16) rotateY(6deg); }
  15% { text-shadow: 0 0 2px currentColor; }
  24% { transform: translate3d(0, 0, 0) scale(1) rotateY(0deg); opacity: 1; }
  36% { transform: scale(1); }
  100% { transform: scale(1); opacity: 0.85; }
}

/* same wave, but a bright Antique White glow so a muted/taupe word still
   catches a highlight as the shimmer passes (hero emphasis word "Works") */
@keyframes wave-bright {
  0% { transform: translate3d(0, 0, 0) scale(1) rotateY(0deg); text-shadow: 0 0 0 rgb(255 235 216 / 0); }
  12% { transform: translate3d(2px, -2px, 2px) scale(1.16) rotateY(6deg); }
  15% { text-shadow: 0 0 10px rgb(216 167 20 / 0.95); }
  24% { transform: translate3d(0, 0, 0) scale(1) rotateY(0deg); opacity: 1; }
  36% { transform: scale(1); text-shadow: 0 0 0 rgb(216 167 20 / 0); }
  100% { transform: scale(1); opacity: 0.85; }
}
.hero-heading .line--accent .wave-letter { animation-name: wave-bright; animation-duration: 2.88s; }

/* --- big text ticker --- */
.ticker { overflow: hidden; white-space: nowrap; }
.ticker .m-scroll {
  display: inline-block;
  white-space: nowrap;
  animation: scrollText 35s linear infinite forwards;
}
.ticker-dup { display: inline; }
@keyframes scrollText {
  0% { transform: translateX(0%); }
  100% { transform: translateX(-50%); }
}

/* --- image marquee --- */
.marquee { overflow: hidden; }
.marquee__inner {
  display: flex;
  width: fit-content;
  animation: marquee 15s linear infinite;
  will-change: transform;
}
.marquee__group { display: flex; flex-shrink: 0; }
@keyframes marquee {
  0% { transform: translate3d(var(--move-initial), 0, 0); }
  100% { transform: translate3d(var(--move-final), 0, 0); }
}

/* --- portfolio split-scroll showcase (single-portfolio pattern) --- */
.sp-scroll.animate .sp-left-image { animation: moveScaleLeft 12s ease-in-out forwards; }
.sp-scroll.animate .sp-right-image { animation: moveScaleRight 12s ease-in-out forwards; }
@keyframes moveScaleLeft {
  0% { transform: translateY(0) scale(1); }
  45% { transform: translateY(-500px) scale(0.85); }
  55% { transform: translateY(-500px) scale(0.85); }
  100% { transform: translateY(0) scale(1); }
}
@keyframes moveScaleRight {
  0% { transform: translateY(0) scale(1); }
  45% { transform: translateY(750px) scale(0.85); }
  55% { transform: translateY(750px) scale(0.85); }
  100% { transform: translateY(0) scale(1); }
}

/* --- testimonial slider --- */
.testimonial-slide.exit-next { animation: next1 0.5s ease forwards; }
.testimonial-slide.enter-next { animation: next2 0.5s ease forwards; }
.testimonial-slide.exit-prev { animation: prev1 0.5s ease forwards; }
.testimonial-slide.enter-prev { animation: prev2 0.5s ease forwards; }
@keyframes next1 { 0% { left: 0%; } 100% { left: -100%; } }
@keyframes next2 { 0% { left: 100%; } 100% { left: 0%; } }
@keyframes prev1 { 0% { left: 0%; } 100% { left: 100%; } }
@keyframes prev2 { 0% { left: -100%; } 100% { left: 0%; } }
@keyframes blink { 0% { opacity: 0; } 50% { opacity: 1; } 100% { opacity: 0; } }

/* --- generic utility motions --- */
@keyframes spin { 0% { transform: rotate(0deg); } 100% { transform: rotate(360deg); } }
@keyframes fade-in { 0% { opacity: 0; } 100% { opacity: 1; } }
@keyframes slide-up { 0% { transform: translate3d(0, 100%, 0); } 100% { transform: translateZ(0); } }

/* --- freeze mode (verify captures): pause every infinite animation,
   settle all reveals so captures match the reference's settled state --- */
.freeze .wave-letter,
.freeze .ticker .m-scroll,
.freeze .marquee__inner {
  animation-play-state: paused !important;
}
.freeze .reveal {
  opacity: 1 !important;
  transform: none !important;
  transition: none !important;
}

/* --- reduced motion kill switch --- */
@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
  .reveal { opacity: 1; transform: none; }
}
