/* ==========================================================================
   Cinematic layer (prototype 2026-10-24): moments that react to the scroll and the cursor.
   Additive only: nothing here changes a feature. Remove the <link>, <script> and the .scene section to undo it.
   Everything respects reduced motion; touch devices skip the cursor effects.
   ========================================================================== */

/* ---------- 1. the pinned statement scene ---------- */
/* base look: works in every browser (a dark statement section with the words fully lit) */
.scene { position: relative; background: var(--ink) var(--grain-dark); color: var(--white); }
.scene__stage { position: relative; display: grid; align-items: center; min-height: 100svh; overflow: hidden; padding-block: 96px; }
.scene__bg { position: absolute; inset: 0; z-index: 0; overflow: hidden; }
.scene__bg img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 30%; filter: grayscale(1) contrast(1.15) brightness(0.8); opacity: 0.16; }
.scene__bg::after { content: ""; position: absolute; inset: 0; background: radial-gradient(ellipse at 50% 55%, rgba(0, 0, 0, 0) 0%, rgba(0, 0, 0, 0.75) 100%); }
.scene__inner { position: relative; z-index: 1; display: grid; gap: 28px; }
.scene__words {
  max-width: 17em;
  font-family: var(--font-display);
  font-weight: 200;
  font-size: clamp(1.9rem, 0.8rem + 4.6vw, 5.1rem);
  line-height: 1.12;
  letter-spacing: -0.04em;
  text-wrap: balance;
}
.scene__words b { font-weight: 600; }
.scene__inner > .label { display: flex; align-items: center; gap: 16px; }
.scene__inner > .label::after { content: ""; width: 56px; height: 1px; background: currentColor; opacity: 0.6; }
.scene__words .w { display: inline-block; margin-right: 0.26em; }

/* where the browser can tie animation to scroll: the stage stays put while the words light up one by one */
@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    .scene { height: 380vh; view-timeline: --scene block; }
    .scene__stage { position: sticky; top: 0; height: 100svh; min-height: 0; padding-block: 0; }
    .scene__bg img {
      animation: scene-bg linear both;
      animation-timeline: --scene;
      animation-range: cover 0% cover 100%;
    }
    @keyframes scene-bg {
      from { scale: 1.45; opacity: 0; }
      30%  { opacity: 0.28; }
      to   { scale: 1; opacity: 0.1; }
    }
    .scene__words .w {
      animation: scene-word cubic-bezier(0.2, 0.7, 0.2, 1) both;
      animation-timeline: --scene;
      animation-range:
        cover calc(27% + var(--i) * var(--step) * 1%)
        cover calc(27% + (var(--i) + 2.4) * var(--step) * 1%);
    }
    @keyframes scene-word {
      from { opacity: 0.12; filter: blur(8px); translate: 0 0.4em; }
      to   { opacity: 1; filter: blur(0); translate: 0 0; }
    }
    /* widescreen bars slide in as the scene pins, and out again as it lets go */
    .scene__stage::before, .scene__stage::after {
      content: "";
      position: absolute;
      left: 0;
      right: 0;
      height: 11vh;
      z-index: 3;
      background: #000;
      pointer-events: none;
      animation: scene-bars cubic-bezier(0.3, 0.7, 0.2, 1) both;
      animation-timeline: --scene;
      animation-range: cover 18% cover 82%;
    }
    .scene__stage::before { top: 0; --dir: -1; }
    .scene__stage::after { bottom: 0; --dir: 1; }
    @keyframes scene-bars {
      0%   { translate: 0 calc(var(--dir) * 100%); }
      14%  { translate: 0 0; }
      86%  { translate: 0 0; }
      100% { translate: 0 calc(var(--dir) * 100%); }
    }
    .scene__inner > .label { animation: scene-label linear both; animation-timeline: --scene; animation-range: cover 20% cover 32%; }
    @keyframes scene-label { from { opacity: 0; translate: 0 12px; } }
  }
}

/* ---------- 2. 3D tilt + glare on the shop photos (mouse only) ---------- */
@media (hover: hover) and (pointer: fine) and (prefers-reduced-motion: no-preference) {
  .product__media {
    transform: perspective(1000px) rotateX(var(--rx, 0deg)) rotateY(var(--ry, 0deg));
    transition: transform 0.6s var(--ease);
  }
  .product__media.is-tilting { transition: transform 0.1s linear; }
  .product__media::before {
    content: "";
    position: absolute;
    inset: 0;
    z-index: 2;
    pointer-events: none;
    opacity: 0;
    background: radial-gradient(circle at var(--mx, 50%) var(--my, 50%), rgba(255, 255, 255, 0.34), rgba(255, 255, 255, 0) 55%);
    mix-blend-mode: soft-light;
    transition: opacity 0.4s var(--ease);
  }
  .product__media.is-tilting::before { opacity: 1; }
}

/* ---------- 3. the colour lens on the lookbook (mouse only) ---------- */
/* the photo stays black and white everywhere except under the cursor, where colour shows through */
@media (hover: hover) and (pointer: fine) {
  .shot { isolation: isolate; }
  .shot img, .shot:hover img, .shot:focus-visible img { filter: none; }
  .shot::before {
    content: "";
    position: absolute;
    inset: 0;
    z-index: 1;
    pointer-events: none;
    background: hsl(0 0% 50%);
    mix-blend-mode: saturation;
    -webkit-mask-image: radial-gradient(circle 130px at var(--mx, -999px) var(--my, -999px), transparent 0, transparent 52%, #000 100%);
    mask-image: radial-gradient(circle 130px at var(--mx, -999px) var(--my, -999px), transparent 0, transparent 52%, #000 100%);
  }
}

/* ---------- 4. the footer wordmark: letters lean toward the cursor ---------- */
.wordmark .ch { display: inline-block; transition: translate 0.45s var(--ease), scale 0.45s var(--ease); will-change: translate, scale; }

/* a faint film-grain shimmer behind the words (computers only: it is constant motion) */
@media (hover: hover) and (pointer: fine) and (prefers-reduced-motion: no-preference) {
  .scene__bg::before {
    content: "";
    position: absolute;
    inset: -40%;
    z-index: 2;
    background: var(--grain-dark);
    opacity: 0.55;
    pointer-events: none;
    animation: film-grain 0.9s steps(1) infinite;
  }
  @keyframes film-grain {
    0%   { translate: 0 0; }
    20%  { translate: -3% 2%; }
    40%  { translate: 2% -4%; }
    60%  { translate: -4% -2%; }
    80%  { translate: 3% 3%; }
  }
}

/* ---------- 5. a curtain reveal for the lookbook photos ---------- */
@media (prefers-reduced-motion: no-preference) {
  .lookbook__grid li.reveal {
    clip-path: inset(16% 0 0 0 round 10px);
    transition: opacity 1.1s var(--ease), transform 1.1s var(--ease), clip-path 1.1s var(--ease);
    transition-delay: var(--reveal-delay, 0s);
  }
  .lookbook__grid li.reveal.is-in { clip-path: inset(0 0 0 0 round 10px); }
}

/* ---------- 6. depth in the hero: the film drifts a little against the cursor (computers only) ---------- */
@media (hover: hover) and (pointer: fine) and (prefers-reduced-motion: no-preference) {
  .hero__video, .live-hero {
    scale: 1.06;
    translate: calc(var(--px, 0) * -14px) calc(var(--py, 0) * -9px);
    transition: translate 0.9s var(--ease);
  }
}

/* ---------- 7. magnetic buttons (computers only) ---------- */
@media (hover: hover) and (pointer: fine) and (prefers-reduced-motion: no-preference) {
  body:not(.escape) .btn {
    transition: background-color 0.25s var(--ease), color 0.25s var(--ease), border-color 0.25s var(--ease), transform 0.2s var(--ease), translate 0.4s var(--ease);
  }
}


/* ==========================================================================
   Teaser scene (the new item): a knitted-rib texture rises as the line lights up, word by word.
   Same craft as the statement scene: pinned, scroll-driven, reduced motion and no-support fall back to a calm
   static section with everything visible.
   ========================================================================== */
.teaser { position: relative; background: #0b0b0b var(--grain-dark); color: var(--white); }
.teaser__stage { position: relative; display: grid; align-items: center; min-height: 100svh; overflow: hidden; padding-block: 96px; }
/* the knit: fine vertical ribs, like knitted ribbing, with a soft light across it */
.teaser__knit {
  position: absolute;
  inset: 0;
  z-index: 0;
  background:
    radial-gradient(ellipse at 70% 30%, rgba(255, 255, 255, 0.10), rgba(255, 255, 255, 0) 55%),
    repeating-linear-gradient(90deg, rgba(255, 255, 255, 0.075) 0 2px, rgba(0, 0, 0, 0.35) 2px 7px);
  opacity: 0.9;
  -webkit-mask-image: linear-gradient(180deg, transparent 0%, #000 22%, #000 78%, transparent 100%);
  mask-image: linear-gradient(180deg, transparent 0%, #000 22%, #000 78%, transparent 100%);
}
.teaser__inner { position: relative; z-index: 1; display: grid; gap: 26px; justify-items: start; }
.teaser__words {
  max-width: 14em;
  font-family: var(--font-display);
  font-weight: 200;
  font-size: clamp(2.2rem, 0.8rem + 6vw, 6.4rem);
  line-height: 1.06;
  letter-spacing: -0.04em;
  text-wrap: balance;
}
.teaser__words b { font-weight: 600; }
.teaser__words .w { display: inline-block; margin-right: 0.26em; }
.teaser__when { margin: 0; font-size: 0.8125rem; font-weight: 500; letter-spacing: 0.16em; text-transform: uppercase; color: var(--mist); font-variant-numeric: tabular-nums; }
.teaser__when b { color: var(--white); font-weight: 600; }
.teaser__cta { margin-top: 6px; }

@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    .teaser { height: 260vh; view-timeline: --teaser block; }
    .teaser__stage { position: sticky; top: 0; height: 100svh; min-height: 0; padding-block: 0; }
    /* the ribs rise from the bottom like fabric being drawn up, and sway a little as you scroll */
    .teaser__knit {
      animation: knit-rise cubic-bezier(0.3, 0.7, 0.2, 1) both;
      animation-timeline: --teaser;
      animation-range: cover 14% cover 48%;
    }
    @keyframes knit-rise { from { clip-path: inset(100% 0 0 0); } to { clip-path: inset(0 0 0 0); } }
    .teaser__words .w {
      animation: scene-word cubic-bezier(0.2, 0.7, 0.2, 1) both;
      animation-timeline: --teaser;
      animation-range:
        cover calc(30% + var(--i) * var(--step) * 1%)
        cover calc(30% + (var(--i) + 2.4) * var(--step) * 1%);
    }
    .teaser__inner > .label, .teaser__when, .teaser__cta { animation: scene-label linear both; animation-timeline: --teaser; animation-range: cover 22% cover 34%; }
    .teaser__when, .teaser__cta { animation-range: cover 56% cover 68%; }
  }
}


/* ==========================================================================
   More cinematic moments (2026-10-24): films, shop, about, lookbook.
   Same rules as above: scroll-driven, pure CSS, reduced motion respected, no feature changed.
   ========================================================================== */
@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {

    /* ruvori in motion: the film in the middle of the row is full size and bright; the ones at the edges sit back */
    .film {
      animation: film-focus linear both;
      animation-timeline: view(inline);
    }
    @keyframes film-focus {
      0%   { scale: 0.88; opacity: 0.5; }
      30%  { scale: 1; opacity: 1; }
      70%  { scale: 1; opacity: 1; }
      100% { scale: 0.88; opacity: 0.5; }
    }

    /* About: the photo opens up like a curtain as it arrives */
    .manifesto__frame {
      animation: frame-open linear both;
      animation-timeline: --drift;
      animation-range: entry 0% entry 85%;
    }
    @keyframes frame-open {
      from { clip-path: inset(14% 10% 14% 10% round 10px); }
      to   { clip-path: inset(0 0 0 0 round 10px); }
    }

    /* lookbook: neighbouring photos drift at different speeds, so the wall has depth */
    .lookbook__grid li:nth-child(even) { animation: lb-drift-a linear both; animation-timeline: view(); }
    .lookbook__grid li:nth-child(odd)  { animation: lb-drift-b linear both; animation-timeline: view(); }
    @keyframes lb-drift-a { from { translate: 0 38px; } to { translate: 0 -38px; } }
    @keyframes lb-drift-b { from { translate: 0 -14px; } to { translate: 0 14px; } }
  }

  /* phones can't hover, so the shop card shows the "worn" photo by itself as the card passes the middle of the screen */
  @media (hover: none) and (prefers-reduced-motion: no-preference) {
    .product__media .is-worn {
      animation: photo-drift linear both, worn-in linear both;
      animation-timeline: --drift, --drift;
      animation-range: cover 0% cover 100%, cover 30% cover 54%;
    }
    @keyframes worn-in { from { opacity: 0; } to { opacity: 1; } }
  }
}
