/* ============================================================================
   Animations — scroll reveals, hover states, ambient motion
   All gated by prefers-reduced-motion via the duration tokens.
   ============================================================================ */

/* Scroll reveal: elements with .reveal start hidden, .is-visible reveals them.
   The IntersectionObserver in lwl-marketing.js adds the class. */
.reveal {
	opacity: 0;
	transform: translateY(24px);
	transition: opacity var(--dur-slow) var(--ease-out),
		transform var(--dur-slow) var(--ease-out);
	will-change: opacity, transform;
}

.reveal.is-visible {
	opacity: 1;
	transform: translateY(0);
}

/* Stagger children — apply .reveal-stagger to a parent and its direct children
   reveal sequentially with a slight delay. */
.reveal-stagger > * {
	opacity: 0;
	transform: translateY(20px);
	transition: opacity var(--dur-slow) var(--ease-out),
		transform var(--dur-slow) var(--ease-out);
}

.reveal-stagger.is-visible > *:nth-child(1) { transition-delay:   0ms; opacity: 1; transform: none; }
.reveal-stagger.is-visible > *:nth-child(2) { transition-delay: 100ms; opacity: 1; transform: none; }
.reveal-stagger.is-visible > *:nth-child(3) { transition-delay: 200ms; opacity: 1; transform: none; }
.reveal-stagger.is-visible > *:nth-child(4) { transition-delay: 300ms; opacity: 1; transform: none; }
.reveal-stagger.is-visible > *:nth-child(5) { transition-delay: 400ms; opacity: 1; transform: none; }
.reveal-stagger.is-visible > *:nth-child(6) { transition-delay: 500ms; opacity: 1; transform: none; }

/* Stat count-up — value starts visually empty until JS runs. JS sets data-target. */
.stat[data-counter] .stat__value {
	font-variant-numeric: tabular-nums;
}

/* Hero scene parallax — JS sets --parallax-y on each layer. */
.hero__scene .layer-foreground { transform: translate3d(0, var(--parallax-fg, 0), 0); }
.hero__scene .layer-near       { transform: translate3d(0, var(--parallax-near, 0), 0); }
.hero__scene .layer-mid        { transform: translate3d(0, var(--parallax-mid, 0), 0); }
.hero__scene .layer-far        { transform: translate3d(0, var(--parallax-far, 0), 0); }
.hero__scene .layer-sky        { transform: translate3d(0, var(--parallax-sky, 0), 0); }

/* Sakura petal slow drift (purely ambient). */
@keyframes sakura-drift {
	0%   { transform: translate(0, 0) rotate(0deg); }
	50%  { transform: translate(8px, 4px) rotate(20deg); }
	100% { transform: translate(0, 0) rotate(0deg); }
}

.hero__scene .sakura-petal {
	animation: sakura-drift 9s var(--ease-in-out) infinite;
	transform-origin: center;
	transform-box: fill-box;
}
.hero__scene .sakura-petal:nth-child(odd)  { animation-duration: 11s; }
.hero__scene .sakura-petal:nth-child(3n)   { animation-duration: 13s; animation-delay: -2s; }
.hero__scene .sakura-petal:nth-child(4n)   { animation-duration: 10s; animation-delay: -4s; }

/* ============================================================================
   Ambient drift — slow, subtle keynote-style color washes that drift across
   section backgrounds. Sitewide. Honors prefers-reduced-motion.
   ============================================================================ */

body::before {
	content: "";
	position: fixed;
	inset: -10vmin;
	pointer-events: none;
	z-index: -1;
	background:
		radial-gradient(36vmax 28vmax at 18% 22%, rgba(252, 60, 48, 0.07), transparent 60%),
		radial-gradient(40vmax 30vmax at 82% 78%, rgba(252, 192, 0, 0.07), transparent 60%),
		radial-gradient(30vmax 24vmax at 92% 12%, rgba(84, 96, 168, 0.05), transparent 60%),
		radial-gradient(34vmax 26vmax at 8%  88%, rgba(110, 159, 74, 0.05), transparent 60%);
	animation: ambient-drift 38s ease-in-out infinite alternate;
	will-change: transform;
}

@keyframes ambient-drift {
	0%   { transform: translate3d(0, 0, 0) scale(1); }
	50%  { transform: translate3d(2vmin, -2vmin, 0) scale(1.04); }
	100% { transform: translate3d(-2vmin, 2vmin, 0) scale(1.02); }
}

@media (prefers-reduced-motion: reduce) {
	body::before { animation: none; }
}

/* Mi enfoque — icons animate when their card reveals into view ----------- */
.section--enfoque .reveal-stagger.is-visible .service-card:nth-child(1) .service-card__icon {
	animation: enfoque-sprout 1.4s var(--ease-out) 0.1s both;
}
.section--enfoque .reveal-stagger.is-visible .service-card:nth-child(2) .service-card__icon {
	animation: enfoque-bonsai 1.6s var(--ease-out) 0.25s both, enfoque-sway 6s var(--ease-in-out) 1.6s infinite;
}
.section--enfoque .reveal-stagger.is-visible .service-card:nth-child(3) .service-card__icon {
	animation: enfoque-fly 1.6s var(--ease-out) 0.4s both;
}

@keyframes enfoque-sprout {
	0%   { opacity: 0; transform: scale(0.4) translateY(10px); }
	60%  { opacity: 1; transform: scale(1.06) translateY(-2px); }
	100% { opacity: 1; transform: scale(1) translateY(0); }
}

@keyframes enfoque-bonsai {
	0%   { opacity: 0; transform: scale(0.7) translateY(8px); }
	100% { opacity: 1; transform: scale(1) translateY(0); }
}

@keyframes enfoque-sway {
	0%, 100% { transform: rotate(0deg); transform-origin: 44px 70px; }
	50%      { transform: rotate(2deg); transform-origin: 44px 70px; }
}

@keyframes enfoque-fly {
	0%   { opacity: 0; transform: translate(-30px, 18px) rotate(-12deg); }
	60%  { opacity: 1; transform: translate(4px, -3px) rotate(3deg); }
	100% { opacity: 1; transform: translate(0, 0) rotate(0); }
}

@media (prefers-reduced-motion: reduce) {
	.section--enfoque .reveal-stagger.is-visible .service-card .service-card__icon {
		animation: none;
		opacity: 1;
		transform: none;
	}
}

/* Section-level highlight wash — slower, even subtler, opt-in via .section--wash */
.section--wash {
	position: relative;
	overflow: hidden;
	isolation: isolate;
}

.section--wash::after {
	content: "";
	position: absolute;
	inset: -20%;
	pointer-events: none;
	z-index: 0;
	background:
		radial-gradient(50% 40% at 30% 40%, rgba(252, 120, 12, 0.08), transparent 60%),
		radial-gradient(60% 50% at 80% 60%, rgba(125, 168, 208, 0.10), transparent 60%);
	animation: wash-drift 50s ease-in-out infinite alternate;
}

.section--wash > .container {
	position: relative;
	z-index: 1;
}

@keyframes wash-drift {
	0%   { transform: translate(0, 0); }
	100% { transform: translate(-3vmin, 2vmin); }
}

@media (prefers-reduced-motion: reduce) {
	.section--wash::after { animation: none; }
}

/* Sun gentle pulse */
@keyframes sun-pulse {
	0%, 100% { opacity: 0.32; r: 56; }
	50%      { opacity: 0.42; r: 60; }
}

.hero__scene .sun-glow {
	animation: sun-pulse 8s var(--ease-in-out) infinite;
	transform-origin: center;
}

/* Logo swirl breathing */
@keyframes logo-breathe {
	0%, 100% { opacity: 0.55; transform: rotate(0deg); }
	50%      { opacity: 0.7;  transform: rotate(2deg); }
}

.site-logo__mark .swirl {
	animation: logo-breathe 6s var(--ease-in-out) infinite;
	/* Center of the path-crest viewBox (200×200, brand mark v2 from 2026-05-16).
	   transform-box: fill-box anchors the rotation to the element's own
	   bounding box so this stays correct if the viewBox ever changes. */
	transform-origin: center;
	transform-box: fill-box;
}
