/* orvos_motion.css — DESIGN1b (2026-05-29)
   Motion + 3D utility layer for the public orvos.uz surface
   (index.html landing, /catalog, /offers, /planner). Loaded
   AFTER styles.css and landing.css.

   Design rule: this is a marketing surface — we lean in. Real
   perspective, tilt on hover, scroll-driven reveals, glass
   panels, gradient flow. Everything is pure CSS + a tiny
   IntersectionObserver (no GSAP, no Three.js dependency)
   so first-paint stays under-budget on 3G. The 3D bits use
   transform-style + perspective only — GPU-composited, no
   layout. prefers-reduced-motion disables all of it. */

:root {
  /* Motion tokens — slightly slower/dramatic than sotuvchi
     because the user is browsing, not transacting. */
  --motion-fast:   200ms;
  --motion-base:   320ms;
  --motion-slow:   520ms;
  --motion-hero:   900ms;
  --ease-out-soft: cubic-bezier(0.22, 0.61, 0.36, 1);
  --ease-out-expo: cubic-bezier(0.16, 1, 0.3, 1);
  --ease-spring:   cubic-bezier(0.34, 1.56, 0.64, 1);

  /* 3D stage tokens — perspective drives how deep tilt feels.
     Lower px = stronger 3D. 1100px = "premium product page"
     (Apple uses ~1200 on watch pages). */
  --persp-hero:    1100px;
  --persp-card:    900px;

  /* Premium accent gradients — used by .gradient-text +
     .gradient-flow. Built around the existing brand gold so
     it doesn't clash with already-shipped pages. */
  --grad-gold:   linear-gradient(135deg, #c6a55c 0%, #e6cb8e 30%, #ffe9b3 50%, #c6a55c 70%, #9e7428 100%);
  --grad-emerald:linear-gradient(135deg, #0f2a23 0%, #1a4538 50%, #0f2a23 100%);

  /* Elevation — deeper than sotuvchi; reads as "lifted glass". */
  --o-elev-1: 0 2px 6px rgba(4, 15, 11, 0.18);
  --o-elev-2: 0 10px 24px rgba(4, 15, 11, 0.22), 0 2px 4px rgba(4, 15, 11, 0.10);
  --o-elev-3: 0 24px 60px rgba(4, 15, 11, 0.34), 0 6px 12px rgba(4, 15, 11, 0.14);
  --o-glow-gold:   0 0 40px rgba(198, 165, 92, 0.35);
  --o-glow-strong: 0 0 80px rgba(230, 203, 142, 0.40);
}

/* ---------- 3D Tilt card ---------- */
/* Wrap a card with `.tilt3d` and (optionally) a child
   `.tilt3d-inner` for the actual surface. JS hooks mouse
   coords into --tx / --ty (range -0.5..0.5) and CSS does the
   rotation. With no JS, the static styles still look premium. */
.tilt3d {
  perspective: var(--persp-card);
  transform-style: preserve-3d;
}
.tilt3d-inner {
  --tx: 0;
  --ty: 0;
  transform:
    rotateY(calc(var(--tx) * 12deg))
    rotateX(calc(var(--ty) * -12deg))
    translateZ(0);
  transform-style: preserve-3d;
  transition: transform var(--motion-base) var(--ease-out-soft),
              box-shadow var(--motion-base) var(--ease-out-soft);
  will-change: transform;
  box-shadow: var(--o-elev-2);
}
.tilt3d:hover .tilt3d-inner {
  box-shadow: var(--o-elev-3), var(--o-glow-gold);
}
/* Optional inner layers pop out of the card on hover by
   declaring `data-depth="20"` (px) — JS reads it, no-JS
   ignores it. */
.tilt3d-layer {
  transform: translateZ(var(--depth, 0px));
  transition: transform var(--motion-base) var(--ease-out-expo);
}

/* ---------- Tilt-3D, wrapper-less variant ---------- */
/* Single-element 3D tilt: the perspective + the rotation live
   on the same element. Use this when adding a wrapper would
   disturb an existing grid (e.g. the trust strip's
   .trust-strip-grid expects .trust-card as direct children).
   Declared AFTER .reveal.is-visible so its transform wins
   post-reveal; the rest state is identity rotation, so the
   .reveal entrance animation still interpolates cleanly from
   the initial offset to identity, then the JS-driven tilt
   takes over on hover. */
.tilt3d-self {
  --tx: 0;
  --ty: 0;
  transform:
    perspective(var(--persp-card))
    rotateY(calc(var(--tx) * 12deg))
    rotateX(calc(var(--ty) * -12deg));
  transform-style: preserve-3d;
  transition:
    transform var(--motion-base) var(--ease-out-soft),
    box-shadow var(--motion-base) var(--ease-out-soft);
  will-change: transform;
}
.tilt3d-self:hover {
  box-shadow: var(--o-elev-3), var(--o-glow-gold);
}

/* ---------- Scroll-reveal ---------- */
/* Initial state: invisible + offset. IntersectionObserver
   toggles `.is-visible` which restores. Direction modifiers
   `.reveal--up | --right | --left | --scale`. */
.reveal {
  opacity: 0;
  transform: translateY(28px);
  transition:
    opacity var(--motion-slow) var(--ease-out-soft),
    transform var(--motion-slow) var(--ease-out-soft);
  will-change: opacity, transform;
}
/* `transform: none` (instead of an explicit identity) leaves the
   transform slot free so a .tilt3d-self on the same element can
   take it over once the reveal finishes — without `none` the
   CSS would still pin transform to translateY(0) etc, which has
   higher cascade than the tilt rule and the rotation would never
   apply. */
.reveal.is-visible { opacity: 1; transform: none; }
.reveal--right { transform: translateX(-32px); }
.reveal--left  { transform: translateX(32px); }

/* Stagger — set `style="--reveal-delay: 80ms"` on each child,
   or just use these helpers. */
.reveal[data-delay="1"] { transition-delay: 80ms; }
.reveal[data-delay="2"] { transition-delay: 160ms; }
.reveal[data-delay="3"] { transition-delay: 240ms; }
.reveal[data-delay="4"] { transition-delay: 320ms; }
.reveal[data-delay="5"] { transition-delay: 400ms; }
.reveal[data-delay="6"] { transition-delay: 480ms; }

/* ---------- Glass surface ---------- */
/* Frosted card for hero / pricing tiles / modals.
   backdrop-filter is supported everywhere modern, falls
   back to flat translucent. */
.glass {
  background: linear-gradient(135deg,
    rgba(26, 69, 56, 0.78) 0%,
    rgba(15, 42, 35, 0.66) 100%);
  backdrop-filter: blur(18px) saturate(140%);
  -webkit-backdrop-filter: blur(18px) saturate(140%);
  border: 1px solid rgba(198, 165, 92, 0.22);
  box-shadow: var(--o-elev-2),
              inset 0 1px 0 rgba(255, 255, 255, 0.06);
  border-radius: 18px;
}
.glass-strong {
  background: linear-gradient(135deg,
    rgba(26, 69, 56, 0.92) 0%,
    rgba(11, 31, 26, 0.86) 100%);
  backdrop-filter: blur(24px) saturate(160%);
  -webkit-backdrop-filter: blur(24px) saturate(160%);
  border: 1px solid rgba(198, 165, 92, 0.32);
  box-shadow: var(--o-elev-3);
  border-radius: 22px;
}

/* ---------- Gradient text (animated) ---------- */
.gradient-text {
  background: var(--grad-gold);
  background-size: 200% 200%;
  -webkit-background-clip: text;
          background-clip: text;
  color: transparent;
  animation: gradFlow 8s var(--ease-out-soft) infinite;
}
@keyframes gradFlow {
  0%, 100% { background-position: 0% 50%; }
  50%      { background-position: 100% 50%; }
}

/* ---------- Hover lift ---------- */
@media (hover: hover) and (pointer: fine) {
  .o-lift {
    transition:
      transform var(--motion-fast) var(--ease-out-expo),
      box-shadow var(--motion-fast) var(--ease-out-soft);
  }
  .o-lift:hover {
    transform: translateY(-4px);
    box-shadow: var(--o-elev-3);
  }
}

/* ---------- Floating element (slow vertical drift) ---------- */
@keyframes orvosFloat {
  0%, 100% { transform: translateY(0) rotate(0deg); }
  50%      { transform: translateY(-12px) rotate(0.6deg); }
}
.float-slow  { animation: orvosFloat 7s ease-in-out infinite; }
.float-slower{ animation: orvosFloat 11s ease-in-out infinite; }

/* ---------- Hero perspective stage ---------- */
/* Wrap the hero image/illustration with `.hero-stage`. The
   inner image gets a baseline rotateX (looks like a slight
   look-down) and JS optionally adjusts based on scrollY. */
.hero-stage {
  perspective: var(--persp-hero);
  perspective-origin: 50% 30%;
}
.hero-stage-inner {
  transform: rotateX(8deg) translateZ(0);
  transform-origin: 50% 80%;
  transition: transform var(--motion-hero) var(--ease-out-soft);
  will-change: transform;
}

/* ---------- Gradient flow background ---------- */
.bg-flow {
  background: linear-gradient(125deg,
    #0a2620 0%, #103126 30%, #1a4538 50%, #103126 70%, #0a2620 100%);
  background-size: 280% 280%;
  animation: bgFlow 18s ease-in-out infinite;
}
@keyframes bgFlow {
  0%, 100% { background-position: 0% 50%; }
  50%      { background-position: 100% 50%; }
}

/* ---------- Glow orb (decorative, absolutely positioned) ---------- */
.glow-orb {
  position: absolute;
  width: 380px; height: 380px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(198, 165, 92, 0.32) 0%, transparent 65%);
  filter: blur(40px);
  pointer-events: none;
  animation: orvosFloat 9s ease-in-out infinite;
}

/* ---------- Marquee ---------- */
@keyframes orvosMarquee {
  from { transform: translateX(0); }
  to   { transform: translateX(-50%); }
}
.marquee {
  overflow: hidden;
  -webkit-mask-image: linear-gradient(90deg, transparent, #000 12%, #000 88%, transparent);
          mask-image: linear-gradient(90deg, transparent, #000 12%, #000 88%, transparent);
}
.marquee-track {
  display: inline-flex;
  gap: 40px;
  white-space: nowrap;
  animation: orvosMarquee 30s linear infinite;
  will-change: transform;
}

/* ---------- Hero cursor spotlight ---------- */
/* Radial gold glow that tracks the pointer inside the dark hero.
   Sits above .hero-overlay (z-index 1, DOM order) but below
   .hero-content (later in DOM at same z-index). Only wired by JS
   on devices with a fine pointer — touch gets nothing.
   --sx / --sy default to -999px so the glow is offscreen until
   the first pointermove fires. */
@media (hover: hover) and (pointer: fine) {
  .hero-spotlight {
    position: absolute;
    inset: 0;
    z-index: 1;
    pointer-events: none;
    background: radial-gradient(
      480px circle at var(--sx, -999px) var(--sy, -999px),
      rgba(198, 165, 92, 0.11),
      transparent 65%
    );
  }
}

/* ---------- Reduced motion ---------- */
@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;
  }
  .tilt3d-inner   { transform: none !important; }
  .reveal         { opacity: 1; transform: none; }
  .hero-stage-inner { transform: none !important; }
  .float-slow, .float-slower { animation: none !important; }
}
