/* =============================================================================
   selfLove.Yoga — Taste & Motion System (implementation)
   Source of truth: /selflove-redesign/TASTE-AND-MOTION-SYSTEM.md
   Load order: Tailwind CDN -> taste.css -> page inline <style>
   (page inline styles may still override taste.css for one-off cases, but
   every shared component — buttons, cards, reveals — is owned here so the
   whole site shares one motion vocabulary instead of 13 reinventions of it.)
   ============================================================================= */

:root {
  /* -- Motion tokens (the only two easings allowed anywhere on this site) -- */
  --ease-out-expo: cubic-bezier(0.16, 1, 0.3, 1);        /* entrances: fast start, gentle settle */
  --ease-in-out-quart: cubic-bezier(0.76, 0, 0.24, 1);   /* state changes: toggles, modals, accordions */
  --ease-spring: cubic-bezier(0.34, 1.56, 0.64, 1);      /* gesture-driven: drag, swipe, day-select — slight overshoot then settle */

  --duration-fast: 150ms;   /* hover, button press */
  --duration-base: 250ms;   /* card reveals, dropdowns */
  --duration-slow: 400ms;   /* modals, page-level transitions */
  --duration-spring: 350ms; /* spring-approximation moments */

  --stagger-step: 50ms;     /* 40-60ms stagger between siblings, capped at 6 items */
}

/* =============================================================================
   1. Buttons — canonical definitions (token-driven, replaces the ad hoc
   `transition:all .2s ease` copy-pasted per page).
   ============================================================================= */
.btn-primary {
  background: #FF6B35;
  color: #fff;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: .03em;
  padding: 1rem 2rem;
  border-radius: 9999px;
  box-shadow: 0 10px 25px -8px rgba(255, 107, 53, .6);
  transition: transform var(--duration-fast) var(--ease-out-expo),
              box-shadow var(--duration-fast) var(--ease-out-expo),
              background-color var(--duration-fast) var(--ease-out-expo);
  display: inline-block;
  border: none;
  cursor: pointer;
}
.btn-primary:hover, .btn-primary:focus-visible {
  background: #e8551f;
  transform: translateY(-2px);
  box-shadow: 0 14px 30px -8px rgba(255, 107, 53, .7);
}
.btn-primary:active { transform: translateY(0); }

.btn-outline {
  border: 2.5px solid #1A1A1A;
  color: #1A1A1A;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: .03em;
  padding: 1rem 2rem;
  border-radius: 9999px;
  background: none;
  cursor: pointer;
  transition: transform var(--duration-fast) var(--ease-out-expo),
              background-color var(--duration-fast) var(--ease-out-expo),
              color var(--duration-fast) var(--ease-out-expo);
  display: inline-block;
}
.btn-outline:hover, .btn-outline:focus-visible { background: #1A1A1A; color: #fff; transform: translateY(-2px); }
.btn-outline:active { transform: translateY(0); }

.btn-outline-white {
  border: 2.5px solid #fff;
  color: #fff;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: .03em;
  padding: 1rem 2rem;
  border-radius: 9999px;
  transition: transform var(--duration-fast) var(--ease-out-expo),
              background-color var(--duration-fast) var(--ease-out-expo),
              color var(--duration-fast) var(--ease-out-expo);
  display: inline-block;
}
.btn-outline-white:hover, .btn-outline-white:focus-visible { background: #fff; color: #1A1A1A; transform: translateY(-2px); }
.btn-outline-white:active { transform: translateY(0); }

/* =============================================================================
   2. Hover / focus — transform-only (translateY(-2px) + shadow), never
   color-only. Use `.hover-lift` on any card/tile/chip that isn't already
   covered by `.card-hover` below.
   ============================================================================= */
.card-hover, .hover-lift {
  transition: transform var(--duration-fast) var(--ease-out-expo),
              box-shadow var(--duration-fast) var(--ease-out-expo);
}
.card-hover:hover, .card-hover:focus-visible,
.hover-lift:hover, .hover-lift:focus-visible {
  transform: translateY(-2px);
  box-shadow: 0 20px 40px -12px rgba(0, 0, 0, .18);
}
.card-hover:active, .hover-lift:active { transform: translateY(0); }

/* Larger media/feature cards get a slightly stronger lift */
.hover-lift-lg {
  transition: transform var(--duration-fast) var(--ease-out-expo),
              box-shadow var(--duration-fast) var(--ease-out-expo);
}
.hover-lift-lg:hover, .hover-lift-lg:focus-visible {
  transform: translateY(-4px);
  box-shadow: 0 24px 48px -14px rgba(0, 0, 0, .22);
}

/* Small icon chips (social icons, cart/login glyphs) — subtle scale+lift,
   transform-based instead of a color-only swap. */
.icon-hover {
  transition: transform var(--duration-fast) var(--ease-out-expo),
              background-color var(--duration-fast) var(--ease-out-expo);
}
.icon-hover:hover, .icon-hover:focus-visible {
  transform: translateY(-2px) scale(1.06);
}

/* =============================================================================
   3. Imagery — brand color-grade + treatment (spec section 6)
   `.photo-grade`: apply directly to every <img>/<video> on the site. A
   single, consistent warm grade so stock photography reads as shot-for-
   this-brand. `.photo-frame`: apply to a wrapper when you also want the
   literal gradient-overlay treatment (used on hero/feature imagery).
   ============================================================================= */
.photo-grade {
  filter: saturate(1.1) contrast(1.03) sepia(8%) hue-rotate(-8deg) brightness(0.99);
}

.photo-frame {
  position: relative;
  overflow: hidden;
  isolation: isolate;
}
.photo-frame::after {
  content: '';
  position: absolute;
  inset: 0;
  background: linear-gradient(135deg, rgba(255, 107, 53, .16) 0%, rgba(255, 183, 3, .11) 55%, rgba(26, 26, 26, .12) 100%);
  pointer-events: none;
}

/* Never show a photo at native crop with zero treatment: rounded corner +
   1px inset border, for any image that doesn't already carry its own
   rounded-* utility context. */
.photo-treated {
  border-radius: 1rem;
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, .3);
}

/* =============================================================================
   4. Staggered reveal — purposeful entrance, not a generic fade-in.
   `.reveal` is toggled to `.revealed` by the existing IntersectionObserver
   in script.js; this is the one canonical definition (was previously
   duplicated per-page with a flat `.7s ease`).  Entrances arrive with
   momentum (--ease-out-expo) and settle. Siblings inside a `.grid`/`.flex`
   row stagger 50ms apart, capped at 6 items so a long list doesn't crawl.
   ============================================================================= */
.reveal {
  opacity: 0;
  transform: translateY(20px);
  transition: opacity var(--duration-slow) var(--ease-out-expo),
              transform var(--duration-slow) var(--ease-out-expo);
}
.reveal.revealed { opacity: 1; transform: translateY(0); }

.grid > .reveal:nth-child(2), .flex > .reveal:nth-child(2) { transition-delay: var(--stagger-step); }
.grid > .reveal:nth-child(3), .flex > .reveal:nth-child(3) { transition-delay: calc(var(--stagger-step) * 2); }
.grid > .reveal:nth-child(4), .flex > .reveal:nth-child(4) { transition-delay: calc(var(--stagger-step) * 3); }
.grid > .reveal:nth-child(5), .flex > .reveal:nth-child(5) { transition-delay: calc(var(--stagger-step) * 4); }
.grid > .reveal:nth-child(6), .flex > .reveal:nth-child(6) { transition-delay: calc(var(--stagger-step) * 5); }
.grid > .reveal:nth-child(n+7), .flex > .reveal:nth-child(n+7) { transition-delay: calc(var(--stagger-step) * 5); }

/* Keyframe alternative for elements animated in on load rather than on
   scroll (e.g. a watermark numeral, a hero card) — same momentum curve. */
@keyframes taste-rise-in {
  from { opacity: 0; transform: translateY(24px) scale(.98); }
  to   { opacity: 1; transform: translateY(0) scale(1); }
}
.rise-in {
  animation: taste-rise-in var(--duration-slow) var(--ease-out-expo) both;
}
.rise-in-delay-1 { animation-delay: var(--stagger-step); }
.rise-in-delay-2 { animation-delay: calc(var(--stagger-step) * 2); }
.rise-in-delay-3 { animation-delay: calc(var(--stagger-step) * 3); }

/* =============================================================================
   5. State-change transitions — accordions, drawers, modals, filter swaps.
   Always --ease-in-out-quart, always a token duration. Animate transform/
   opacity/max-height only (max-height is the one layout property this
   codebase relies on for accordions; kept intentionally, never top/left).
   ============================================================================= */
.accordion-panel {
  max-height: 0;
  overflow: hidden;
  transition: max-height var(--duration-base) var(--ease-in-out-quart);
}
.accordion-icon { transition: transform var(--duration-base) var(--ease-in-out-quart); }

.state-transition {
  transition: transform var(--duration-base) var(--ease-in-out-quart),
              opacity var(--duration-base) var(--ease-in-out-quart);
}

/* Spring-ish overshoot for gesture/physically-interactive moments (cart
   drawer, day-picker, slot buttons) when a real JS spring isn't in play. */
.spring-pop {
  transition: transform var(--duration-spring) var(--ease-spring);
}

/* =============================================================================
   6. Reduced motion
   ============================================================================= */
@media (prefers-reduced-motion: reduce) {
  .reveal, .rise-in, .card-hover, .hover-lift, .hover-lift-lg, .icon-hover,
  .btn-primary, .btn-outline, .btn-outline-white, .spring-pop, .accordion-panel, .accordion-icon {
    transition: none !important;
    animation: none !important;
  }
  .reveal { opacity: 1; transform: none; }
}
