/* ==========================================================================
   PRLinkUp — Motion
   Slow, calm, premium. Everything respects prefers-reduced-motion.
   ========================================================================== */

/* ---------- Scroll reveal ----------
   [data-reveal]        fades up when it enters the viewport
   [data-reveal-group]  children appear one after another (--stagger apart)
   Hidden state applies only when JS is running (html.js) so content is
   never invisible without JavaScript.
   Uses keyframes on the individual `translate`/`scale` properties so it never
   fights with hover `transform` lifts or component transitions. */
.js [data-reveal],
.js [data-reveal-group] > * {
    opacity: 0;
}

.js [data-reveal].is-visible,
.js [data-reveal-group].is-visible > * {
    animation: reveal-up var(--dur-reveal) var(--ease-out) both;
    animation-delay: calc(var(--i, 0) * var(--stagger));
}

.js [data-reveal="scale"].is-visible {
    animation-name: reveal-scale;
}

/* ---------- Keyframes ---------- */
@keyframes float {
    0%, 100% { transform: translateY(0); }
    50%      { transform: translateY(-12px); }
}

@keyframes drift-1 {
    0%, 100% { transform: translate(0, 0) scale(1); }
    33%      { transform: translate(12%, 8%) scale(1.1); }
    66%      { transform: translate(-6%, 14%) scale(0.95); }
}

@keyframes drift-2 {
    0%, 100% { transform: translate(0, 0) scale(1); }
    50%      { transform: translate(-14%, -10%) scale(1.15); }
}

@keyframes drift-3 {
    0%, 100% { transform: translate(0, 0) scale(1.05); }
    40%      { transform: translate(10%, -12%) scale(0.9); }
    80%      { transform: translate(-8%, 6%) scale(1.1); }
}

@keyframes pulse-dot {
    0%   { box-shadow: 0 0 0 0 rgba(0, 210, 106, 0.55); }
    70%  { box-shadow: 0 0 0 7px rgba(0, 210, 106, 0); }
    100% { box-shadow: 0 0 0 0 rgba(0, 210, 106, 0); }
}

@keyframes grow-bar {
    from { transform: scaleX(0); }
    to   { transform: scaleX(1); }
}

@keyframes shimmer {
    from { background-position: 200% 0; }
    to   { background-position: -200% 0; }
}

@keyframes flow-dash {
    to { stroke-dashoffset: -24; }
}

@keyframes btn-shine {
    0%       { translate: -110% 0; }
    18%, 100%{ translate: 110% 0; }
}

@keyframes spin {
    to { transform: rotate(360deg); }
}

@property --angle {
    syntax: "<angle>";
    inherits: false;
    initial-value: 0deg;
}

@keyframes spin-angle {
    to { --angle: 360deg; }
}

/* Organic liquid shape */
@keyframes morph {
    0%, 100% { border-radius: 42% 58% 63% 37% / 41% 44% 56% 59%; rotate: 0deg; }
    33%      { border-radius: 63% 37% 45% 55% / 55% 62% 38% 45%; rotate: 60deg; }
    66%      { border-radius: 38% 62% 35% 65% / 62% 38% 62% 38%; rotate: -40deg; }
}

@keyframes text-pan {
    to { background-position: 200% center; }
}

@keyframes draw {
    to { stroke-dashoffset: 0; }
}

@keyframes ring-pulse {
    0%   { scale: 0.6; opacity: 0.6; }
    100% { scale: 1.6; opacity: 0; }
}

@keyframes rise-in {
    from { opacity: 0; translate: 0 28px; filter: blur(8px); }
    to   { opacity: 1; translate: 0 0; filter: blur(0); }
}

@keyframes pop-in {
    from { opacity: 0; scale: 0.86; }
    to   { opacity: 1; scale: 1; }
}

@keyframes stage-in {
    from { opacity: 0; scale: 0.94; translate: 0 30px; }
    to   { opacity: 1; scale: 1; translate: 0 0; }
}

@keyframes bar-up {
    from { scale: 1 0; }
    to   { scale: 1 1; }
}

@keyframes reveal-up {
    from { opacity: 0; translate: 0 24px; }
    to   { opacity: 1; translate: 0 0; }
}

@keyframes reveal-scale {
    from { opacity: 0; translate: 0 16px; scale: 0.96; }
    to   { opacity: 1; translate: 0 0; scale: 1; }
}

@media (prefers-reduced-motion: reduce) {
    .js [data-reveal],
    .js [data-reveal-group] > * {
        opacity: 1;
        animation: none !important;
    }
}
