/* =========================================================
   motion.css — the site's one animation system
   Tokens, scroll reveals, hero entrance, hover and press
   states, header behaviour. Everything animates transform
   and opacity only, so nothing here can cause layout shift.
   Every effect switches off under prefers-reduced-motion.
   ========================================================= */

:root {
	--m-fast: 160ms;
	--m-base: 280ms;
	--m-slow: 560ms;
	--m-reveal: 480ms;
	--m-out: cubic-bezier(0.22, 0.61, 0.36, 1);   /* settle */
	--m-spring: cubic-bezier(0.34, 1.3, 0.64, 1);  /* slight overshoot, for icons */
	--m-lift: -4px;
	--m-stagger: 60ms;
}

/* ---------------------------------------------------------
   Scroll reveals
   JS tags elements with data-reveal and adds .is-in when they
   enter the viewport. Without JS nothing is hidden.
   --------------------------------------------------------- */

.js [data-reveal] {
	opacity: 0;
	transition:
		opacity var(--m-reveal) var(--m-out),
		transform var(--m-reveal) var(--m-out);
	transition-delay: calc(var(--i, 0) * var(--m-stagger));
	will-change: opacity, transform;
}

.js [data-reveal="up"],
.js [data-reveal=""],
.js [data-reveal="true"] { transform: translate3d(0, 16px, 0); }
.js [data-reveal="down"]  { transform: translate3d(0, -14px, 0); }
.js [data-reveal="left"]  { transform: translate3d(-20px, 0, 0); }
.js [data-reveal="right"] { transform: translate3d(20px, 0, 0); }
.js [data-reveal="scale"] { transform: scale(0.96); }
.js [data-reveal="fade"]  { transform: none; }

.js [data-reveal].is-in {
	opacity: 1;
	transform: none;
	will-change: auto;
}

/* Section headings: the eyebrow, title and lede arrive one after another. */
.js .section-head > * { transition-delay: calc(var(--i, 0) * 90ms); }

/* ---------------------------------------------------------
   Hero entrance (runs on load, no observer)
   --------------------------------------------------------- */

@keyframes m-rise {
	from { opacity: 0; transform: translate3d(0, 18px, 0); }
	to   { opacity: 1; transform: none; }
}

@keyframes m-art {
	from { opacity: 0; transform: translate3d(20px, 0, 0) scale(0.97); }
	to   { opacity: 1; transform: none; }
}

@keyframes m-float {
	0%, 100% { transform: translate3d(0, 0, 0); }
	50%      { transform: translate3d(0, -10px, 0); }
}

.js .hero__copy > * {
	opacity: 0;
	animation: m-rise var(--m-slow) var(--m-out) forwards;
}

.js .hero__copy > :nth-child(1) { animation-delay: 80ms; }
.js .hero__copy > :nth-child(2) { animation-delay: 180ms; }
.js .hero__copy > :nth-child(3) { animation-delay: 300ms; }
.js .hero__copy > :nth-child(4) { animation-delay: 420ms; }
.js .hero__copy > :nth-child(5) { animation-delay: 540ms; }

.js .hero__art {
	opacity: 0;
	animation: m-art 900ms var(--m-out) 260ms forwards;
}

/* Once it has entered, the artwork drifts gently (img) and follows the pointer
   a little (container) - two elements so the two transforms never fight. */
.js .hero__art { transition: transform var(--m-slow) var(--m-out); }
.js .hero__art.is-live {
	animation: none;
	opacity: 1;
	transform: translate3d(var(--px, 0px), var(--py, 0px), 0);
}
.js .hero__art img { animation: m-float 7s ease-in-out 1.2s infinite; }

/* ---------------------------------------------------------
   Buttons and links
   --------------------------------------------------------- */

.btn {
	transition:
		transform var(--m-fast) var(--m-out),
		box-shadow var(--m-base) var(--m-out),
		background var(--m-base) var(--m-out),
		color var(--m-base) var(--m-out),
		border-color var(--m-base) var(--m-out);
}

.btn:hover { transform: translateY(-2px); }
.btn:active { transform: translateY(1px) scale(0.985); transition-duration: 80ms; }

/* Arrows nudge forward on hover, chevrons stay put. */
.btn .icon,
.post-card__more .icon,
.section-more .icon,
.product__cue .icon,
.card__cue { transition: transform var(--m-base) var(--m-spring); }

.btn:hover .icon,
.post-card:hover .post-card__more .icon,
.section-more a:hover .icon { transform: translateX(4px); }

/* Text links in body copy and the footer get a sliding underline. */
.prose a:not(.wp-block-button__link),
.footer-menu a,
.contact-list a,
.legal-menu a {
	background-image: linear-gradient(currentColor, currentColor);
	background-repeat: no-repeat;
	background-size: 0% 1px;
	background-position: 0 100%;
	text-decoration: none;
	transition: background-size var(--m-base) var(--m-out), color var(--m-base) var(--m-out);
}

.prose a:not(.wp-block-button__link):hover,
.footer-menu a:hover,
.contact-list a:hover,
.legal-menu a:hover { background-size: 100% 1px; }

/* ---------------------------------------------------------
   Cards, tiles and interactive blocks
   One rule for lift + shadow; component files keep their colours.
   --------------------------------------------------------- */

.card,
.reward,
.product,
.post-card,
.cert,
.quote-card,
.contact-card,
.dms__step,
.stat,
.gallery__tile,
.wizard-card,
.benefit {
	transition:
		transform var(--m-base) var(--m-out),
		box-shadow var(--m-base) var(--m-out),
		border-color var(--m-base) var(--m-out),
		background var(--m-base) var(--m-out);
}

.card:hover,
.post-card:hover,
.cert:hover,
.quote-card:hover,
.contact-card:hover,
.benefit:hover,
.dms__step:hover {
	transform: translateY(var(--m-lift));
	box-shadow: var(--shadow-md);
}

/* Icons inside cards rise with a little spring. */
.card__icon,
.benefit__icon,
.contact-card__icon,
.product__icon,
.reward__icon { transition: transform var(--m-base) var(--m-spring), background var(--m-base) var(--m-out), color var(--m-base) var(--m-out); }

.card:hover .card__icon,
.benefit:hover .benefit__icon,
.contact-card:hover .contact-card__icon,
.product--linked:hover .product__media .product__icon { transform: translateY(-3px) scale(1.06); }

/* Images inside media boxes zoom softly. */
.product__img,
.gallery__img,
.post-card__media img,
.reward__img { transition: transform var(--m-slow) var(--m-out); }

.post-card:hover .post-card__media img { transform: scale(1.05); }

/* Stats count up (numbers are set by JS; this just eases them in). */
.stat__value { display: inline-block; transition: transform var(--m-base) var(--m-out); }
.stat:hover .stat__value { transform: scale(1.04); }

/* ---------------------------------------------------------
   Sliders and galleries
   --------------------------------------------------------- */

/* The active banner eases in with a slow settle from a slight zoom. */
.banner__slide.is-active .banner__img {
	animation: m-settle 6s var(--m-out) forwards;
}

@keyframes m-settle {
	from { transform: scale(1.06); }
	to   { transform: scale(1); }
}

.carousel__dot { transition: width var(--m-base) var(--m-out), background var(--m-base) var(--m-out); }
.carousel__arrow { transition: transform var(--m-fast) var(--m-out), border-color var(--m-base) var(--m-out), color var(--m-base) var(--m-out), background var(--m-base) var(--m-out); }
.carousel__arrow:hover { transform: scale(1.06); }
.carousel__arrow:active { transform: scale(0.96); }

/* Marquee tiles lift as a whole; the image inside zooms. */
.gallery__tile { will-change: transform; }

/* ---------------------------------------------------------
   Header
   JS adds .is-stuck after a few pixels and .is-hidden when
   scrolling down past the hero, so the bar slides away and
   returns on the first upward scroll.
   --------------------------------------------------------- */

.site-header {
	transition:
		transform var(--m-base) var(--m-out),
		box-shadow var(--m-base) var(--m-out),
		background var(--m-base) var(--m-out);
}

.site-header.is-hidden { transform: translateY(-100%); }
.site-header.is-hidden:focus-within,
body.nav-open .site-header { transform: none; }

.site-nav .menu-link {
	position: relative;
	transition: color var(--m-base) var(--m-out), background var(--m-base) var(--m-out);
}

@media (min-width: 1024px) {
	/* Desktop: a short underline grows in under the item. */
	.site-nav .menu-link::after {
		content: "";
		position: absolute;
		left: 0.85rem;
		right: 0.85rem;
		bottom: 5px;
		height: 2px;
		border-radius: 2px;
		background: var(--teal-500);
		transform: scaleX(0);
		transform-origin: left;
		transition: transform var(--m-base) var(--m-out);
	}

	.site-nav .menu-link:hover::after,
	.site-nav .is-current > .menu-link::after,
	.site-nav .current-menu-item > .menu-link::after { transform: scaleX(1); }

	.site-nav .sub-menu { transition: opacity var(--m-base) var(--m-out), transform var(--m-base) var(--m-out), visibility var(--m-base); }
}

/* Mobile drawer and scrim already transition; make the items cascade in. */
.site-nav.is-open .menu-item {
	animation: m-rise var(--m-base) var(--m-out) both;
}

.site-nav.is-open .menu-item:nth-child(1) { animation-delay: 40ms; }
.site-nav.is-open .menu-item:nth-child(2) { animation-delay: 80ms; }
.site-nav.is-open .menu-item:nth-child(3) { animation-delay: 120ms; }
.site-nav.is-open .menu-item:nth-child(4) { animation-delay: 160ms; }
.site-nav.is-open .menu-item:nth-child(5) { animation-delay: 200ms; }
.site-nav.is-open .menu-item:nth-child(6) { animation-delay: 240ms; }
.site-nav.is-open .menu-item:nth-child(7) { animation-delay: 280ms; }
.site-nav.is-open .menu-item:nth-child(n+8) { animation-delay: 320ms; }

/* ---------------------------------------------------------
   Accordion, tabs, wizard, quick actions
   --------------------------------------------------------- */

.accordion__panel:not([hidden]) { animation: m-rise var(--m-base) var(--m-out) both; }
.tabs__pane:not([hidden]) { animation: m-rise var(--m-base) var(--m-out) both; }
.accordion__chev { transition: transform var(--m-base) var(--m-spring); }

.quick-actions__btn { transition: transform var(--m-fast) var(--m-spring), background var(--m-base) var(--m-out), opacity var(--m-base) var(--m-out), visibility var(--m-base); }
.quick-actions__btn:hover { transform: translateY(-3px) scale(1.06); }
.quick-actions__btn:active { transform: scale(0.95); }

/* ---------------------------------------------------------
   Reduced motion: keep hover colour changes, drop movement
   --------------------------------------------------------- */

@media (prefers-reduced-motion: reduce) {
	html { scroll-behavior: auto; }
	.js [data-reveal] { opacity: 1; transform: none; transition: none; }
	.js .hero__copy > *, .js .hero__art { opacity: 1; animation: none; }
	.js .hero__art img { animation: none; }
	.js .hero__art.is-live { transform: none; }
	.banner__slide.is-active .banner__img { animation: none; }
	.site-nav.is-open .menu-item, .accordion__panel:not([hidden]), .tabs__pane:not([hidden]) { animation: none; }
	.btn:hover, .btn:active, .card:hover, .post-card:hover, .cert:hover, .quote-card:hover, .contact-card:hover, .dms__step:hover,
	.carousel__arrow:hover, .quick-actions__btn:hover { transform: none; }
	.site-header.is-hidden { transform: none; }
	*, *::before, *::after { transition-duration: 0.01ms !important; animation-duration: 0.01ms !important; }
}
