/* =====================================================================
   motion.css: Graphite Loop v3 motion layer (fs-theme port; loaded by functions.php when Settings > Reading > Motion is on)
   ---------------------------------------------------------------------
   Loads AFTER graphite-loop-v2.css and art-preview.css, with motion.js (deferred)
   and this one-liner in <head>:
     <script>document.documentElement.classList.add('m-js')</script>
   Rules of this layer:
   - Every effect is an opt-in class (a block option in the editor). No class, no motion.
   - Motion follows the visitor: it runs once on load, on scroll, on hover/focus or after
     a click. Nothing loops on its own (WCAG 2.2.2). No pointer-following effects.
   - Only transform, opacity, clip-path and filter are animated (compositor-friendly).
   - The end state of every animation IS the static v2 design. Reveals use backwards
     fill, so nothing stays clipped afterwards and focus rings are never cut.
   - prefers-reduced-motion: reduce -> nothing below moves; the page is the static v2
     design (the waveform stays as a still graphic).
   - Scroll-driven parts sit inside @supports (animation-timeline: view()); browsers
     without it get the static design.
   Class map (editor control in brackets):
     .m-type          kinetic heading on load        [Heading: Kinetic entrance]
     .m-title         kinetic heading on scroll      [Heading: Kinetic on scroll]
     .m-load-stagger  children rise in after load    [Group: Stagger in on load]
     .m-load-rule     top rule draws on load         [Group: Draw top rule]
     .m-enter-wipe    artwork unveils (scroll)       [Artwork: Entrance = Wipe]
     .m-enter-rise    artwork rises (scroll)         [Artwork: Entrance = Rise]
     .m-on-load       play the entrance on load      [Artwork: Play entrance on load]
     .m-drift         slow depth drift on scroll     [Artwork: Depth on scroll]
     .m-halo          soft light behind the lead     [Art panel: Ambient light] (dark panels only)
     .m-stagger       rail/grid items cascade in     [Gallery: Entrance = Cascade]
     .m-spotlight     hover dims the other works     [Gallery: Spotlight on hover]
     .m-draw          timeline ruler draws itself    [Timeline: Draw on scroll] (needs ruler.css v3: line drawn per stop)
     .m-write         signature writes itself        [Image: Write on scroll]
     .m-wave(-host)   waveform motif, reacts to play [Listen band: Waveform]
     .is-style-stack  hero recedes under the wall    [Group style: Hero stack]
     .m-links         crafted link underline redraw  [global, on body]
     .is-style-cascade post list: entries rise in,  [Post template style: Cascade] (Latest writing; static design in style.css 18)
                      rule draws and thumb lifts on hover/focus
   ===================================================================== */

:root {
  --m-out: cubic-bezier(0.16, 1, 0.3, 1);      /* entrances */
  --m-inout: cubic-bezier(0.65, 0, 0.35, 1);   /* lines, pen strokes */
  --m-drift: clamp(1.25rem, 2.5vw, 2.5rem);    /* depth travel of the lead painting */
}

/* ---------------------------------------------------------------------
   0. Static parts (also shown with reduced motion)
   --------------------------------------------------------------------- */
/* Waveform motif: an abstract graphic (not artwork), hairlines drawn by motion.js. */
.m-wave { display: flex; align-items: flex-end; justify-content: space-between; height: 3rem; margin: 0 0 var(--s-6); color: var(--c-on-night-2); }
.m-wave i { flex: 0 0 2px; height: 100%; background: currentColor; opacity: 0.45; transform: scaleY(var(--h, 0.5)); transform-origin: 50% 100%; }
.m-wave-host.is-on .m-wave { color: var(--c-night-accent); }
.m-wave-host.is-on .m-wave i { opacity: 1; }

@media (prefers-reduced-motion: no-preference) {

  /* 1. Kinetic heading on load (.m-type). motion.js wraps each word in .m-w. */
  .m-js :is(.m-type, .is-style-kinetic):not(.is-split) { opacity: 0; animation: m-failsafe 0s 1.2s forwards; } /* if JS fails, show after 1.2 s */
  :is(.m-type, .is-style-kinetic) .m-w { display: inline-block; animation: m-word 0.9s var(--m-out) backwards; animation-delay: calc(100ms + var(--i) * 30ms); }
  :is(.m-type, .is-style-kinetic) em .m-w { animation-name: m-word-em; animation-duration: 1s; animation-delay: calc(220ms + var(--i) * 30ms); }

  /* 2. Load stagger and rule (hero roles, page lede) */
  .m-load-stagger > * { animation: m-rise 0.9s var(--m-out) backwards; animation-delay: calc(550ms + var(--i, 0) * 90ms); }
  .m-load-stagger > span { display: inline-block; }
  .m-load-stagger > :nth-child(2) { --i: 1; } .m-load-stagger > :nth-child(3) { --i: 2; } .m-load-stagger > :nth-child(4) { --i: 3; }
  .m-load-rule { position: relative; border-top-color: transparent; }
  .m-load-rule::before { content: ""; position: absolute; inset: -2px 0 auto 0; height: 2px; background: var(--c-ink); transform-origin: 0 50%; animation: m-scalex 1.2s var(--m-inout) 0.35s backwards; }

  /* 3. Artwork entrance on load (first artwork of the page, above the fold) */
  .m-enter-wipe.m-on-load img { transform-origin: 50% 0; animation: m-unveil 1.4s var(--m-out) 0.25s backwards; }
  .m-enter-rise.m-on-load img { animation: m-rise-far 1.2s var(--m-out) 0.25s backwards; }

  /* 4. Hover and focus: gallery spotlight (dims the other works, lifts the chosen one) */
  .m-spotlight .art-preview-link img { transition: opacity 0.45s var(--m-out), filter 0.45s var(--m-out), transform 0.6s var(--m-out); }
  @media (hover: hover) {
    .m-spotlight:has(.art-preview-link:hover) .art-preview-link:not(:hover) img { opacity: 0.5; filter: grayscale(0.7); }
    .m-spotlight .art-preview-link:hover img { transform: translateY(-6px); }
  }
  .m-spotlight:has(.art-preview-link:focus-visible) .art-preview-link:not(:focus-visible) img { opacity: 0.5; filter: grayscale(0.7); }

  /* 5. Crafted links: the underline retracts and redraws on hover/focus */
  .m-links :is(.go, .is-style-go > a, .is-style-go-ext > a) { position: relative; text-decoration-color: transparent; }
  .m-links :is(.go, .is-style-go > a, .is-style-go-ext > a)::before { content: ""; position: absolute; left: 0; right: 1.5em; top: calc(50% + 0.72em); height: 2px; background: var(--m-line, var(--c-accent)); transform-origin: 0 50%; }
  .m-links :is(.closing, .is-style-closing) { --m-line: currentColor; }
  .m-links :is(.go, .is-style-go > a, .is-style-go-ext > a):is(:hover, :focus-visible)::before { animation: m-redraw 0.65s var(--m-inout); }
  :where(.m-links .art-view-larger) { position: relative; } /* zero specificity: the visually-hidden label rules must still win */
  .m-links .art-view-larger { border-bottom-color: transparent; }
  .m-links .art-view-larger::before { content: ""; position: absolute; left: 0; right: 0; bottom: -1px; height: 1px; background: currentColor; transform-origin: 0 50%; }
  .m-links .art-preview-link:is(:hover, :focus-visible) .art-view-larger::before { animation: m-redraw 0.65s var(--m-inout); }

  /* 6. Waveform: breathes while a play button is hovered/focused; surges for ~3 s after play */
  .m-wave i { transition: opacity 0.4s, background-color 0.4s; }
  .m-wave-host:has(.btn:is(:hover, :focus-visible)) .m-wave i { opacity: 0.8; animation: m-bar 1.1s var(--m-inout) infinite alternate; animation-delay: calc(var(--i) * -53ms); }
  .m-wave-host.is-on .m-wave i { animation: m-bar 0.5s var(--m-inout) 6 alternate; animation-delay: calc(var(--i) * -29ms); }

  /* 7. Page transitions (same-origin navigations). Shared artworks morph between pages
        through view-transition-name: art-<id> set on the <img> by the block (unique per page). */
  @view-transition { navigation: auto; }
  .site-header { view-transition-name: m-header; }
  ::view-transition-group(*) { animation-duration: 0.6s; animation-timing-function: var(--m-out); }
  ::view-transition-old(root), ::view-transition-new(root) { animation-duration: 0.3s; }

  /* 7b. Post list (.is-style-cascade, Latest writing): crafted hover/focus. The accent rule draws in
         from the left over the entry's top rule and retracts to the right; the thumbnail
         lifts 4 px. The static states (instant) are in latest.css. */
  .is-style-cascade > li::before { transform-origin: 100% 50%; transition: transform 0.7s var(--m-inout); }
  .is-style-cascade > li:is(:hover, :has(:focus-visible))::before { transform-origin: 0 50%; }
  .is-style-cascade .wp-block-post-title a { transition: color 0.35s var(--m-out); }
  .is-style-cascade .wp-block-post-featured-image img { transition: transform 0.6s var(--m-out); }
  @media (hover: hover) { .is-style-cascade > li:hover .wp-block-post-featured-image img { transform: translateY(-4px); } }
  .is-style-cascade > li:has(:focus-visible) .wp-block-post-featured-image img { transform: translateY(-4px); }

  /* 8. Scroll-driven effects */
  @supports (animation-timeline: view()) {

    /* Kinetic headings on scroll (.m-title): words assemble as the title arrives */
    :is(.m-title, .is-style-kinetic-scroll, .is-style-display, .is-style-poster):not(.is-split), :is(.m-title, .is-style-kinetic-scroll, .is-style-display, .is-style-poster) .m-w {
      animation: m-title backwards; animation-timing-function: var(--m-out);
      animation-timeline: view(); animation-range: entry 0% cover 30%;
    }
    :is(.m-title, .is-style-kinetic-scroll, .is-style-display, .is-style-poster) .m-w { display: inline-block; animation-range: cover calc(var(--i) * 1.8%) cover calc(16% + var(--i) * 1.8%); }

    /* Artwork entrances on scroll (not the on-load one) */
    .m-enter-wipe:not(.m-on-load) img {
      transform-origin: 50% 0; animation: m-unveil backwards; animation-timing-function: var(--m-out);
      animation-timeline: view(); animation-range: entry 0% cover 40%;
    }
    .m-enter-rise:not(.m-on-load) img {
      animation: m-rise-far backwards; animation-timing-function: var(--m-out);
      animation-timeline: view(); animation-range: entry 0% cover 35%;
    }

    /* Depth: the lead painting travels a little slower than its panel (whole image, never cropped) */
    .m-drift > .art-preview-link { animation: m-drift linear both; animation-timeline: view(); animation-range: cover 0% cover 100%; }

    /* Ambient light behind the lead painting: an abstract glow in the panel accent, scroll-linked.
       Dark panels only: on light panels (lilac, sage, stone) it reads as a stain, so it is off there. */
    .m-halo { position: relative; isolation: isolate; overflow: clip; view-timeline: --m-panel; }
    .m-halo::before {
      content: ""; position: absolute; z-index: -1; left: var(--halo-x, 32%); top: 50%;
      width: min(80vw, 62rem); aspect-ratio: 1; border-radius: 50%; pointer-events: none;
      background: radial-gradient(closest-side, color-mix(in srgb, var(--art-accent) 30%, transparent), color-mix(in srgb, var(--art-accent) 8%, transparent) 55%, transparent);
      animation: m-halo linear both; animation-timeline: --m-panel; animation-range: cover 0% cover 100%;
    }
    .m-halo:is(.art-panel--lilac, .art-panel--sage, .art-panel--stone)::before { content: none; }
    @media (max-width: 55em) { .m-halo { --halo-x: 50%; } .m-halo::before { top: 38%; } }

    /* Cascade for rails and grids (wide screens: items unveil one after another) */
    .m-stagger > li { --i: 0; }
    .m-stagger > li:nth-child(2) { --i: 1; } .m-stagger > li:nth-child(3) { --i: 2; } .m-stagger > li:nth-child(4) { --i: 3; }
    .m-stagger > li:nth-child(5) { --i: 4; } .m-stagger > li:nth-child(6) { --i: 5; } .m-stagger > li:nth-child(n+7) { --i: 6; }
    @media (min-width: 40em) {
      .m-stagger > li {
        animation: m-unveil-rise backwards; animation-timing-function: var(--m-out);
        animation-timeline: view(); animation-range: entry calc(var(--i) * 9%) cover calc(26% + var(--i) * 3%);
      }
    }
    /* Small screens: the rail scrolls sideways; the row rises in, and the work in focus
       is full size while its neighbours wait slightly smaller (whole images, no crop). */
    @media (max-width: 39.99em) {
      .m-stagger { animation: m-rise backwards; animation-timing-function: var(--m-out); animation-timeline: view(); animation-range: entry 0% cover 25%; }
      .m-stagger > li img { transform-origin: 50% 100%; animation: m-focus linear both; animation-timeline: view(inline); animation-range: cover 0% cover 100%; }
    }

    /* Post list (.is-style-cascade): each entry rises as it arrives and its thumbnail unveils top-down.
       Stacked rows (small screens) arrive one by one by themselves; in the three-column row
       (wide screens) a small offset makes them land left to right. */
    .is-style-cascade > li { animation: m-rise backwards; animation-timing-function: var(--m-out); animation-timeline: view(); animation-range: entry 0% cover 22%; }
    .is-style-cascade .wp-block-post-featured-image img { transform-origin: 50% 0; animation: m-unveil backwards; animation-timing-function: var(--m-out); animation-timeline: view(); animation-range: entry 15% cover 32%; }
    @media (min-width: 64em) {
      .is-style-cascade > li:nth-child(2) { --i: 1; } .is-style-cascade > li:nth-child(n+3) { --i: 2; }
      .is-style-cascade > li { animation-range: entry calc(var(--i, 0) * 14%) cover calc(20% + var(--i, 0) * 6%); }
    }

    /* Timeline ruler (.m-draw, with ruler.css v3).
       Small screens (list): rows rise as they arrive.
       From 40em (one row or rail): the line draws itself stop by stop, each marker lands,
       then the stop's text rises. Everything runs on the ruler's own view timeline, so it
       also works for stops scrolled out of the rail, and for any number of stops (6-8+).
       The line and markers are pseudo-elements of the li: only the li's children move. */
    .m-draw > li { animation: m-rise backwards; animation-timing-function: var(--m-out); animation-timeline: view(); animation-range: entry 0% cover 22%; }
    @media (min-width: 40em) {
      .m-draw { view-timeline: --m-ruler; }
      .m-draw > li { --i: 0; animation: none; }
      .m-draw > li:nth-child(2) { --i: 1; } .m-draw > li:nth-child(3) { --i: 2; } .m-draw > li:nth-child(4) { --i: 3; }
      .m-draw > li:nth-child(5) { --i: 4; } .m-draw > li:nth-child(6) { --i: 5; } .m-draw > li:nth-child(7) { --i: 6; }
      .m-draw > li:nth-child(n+8) { --i: 7; }
      .m-draw > li::after { transform-origin: 0 50%; animation: m-scalex backwards; animation-timing-function: linear; animation-timeline: --m-ruler; animation-range: cover calc(3% + var(--i) * 3.5%) cover calc(6.5% + var(--i) * 3.5%); }
      .m-draw > li::before { animation: m-pop backwards; animation-timing-function: var(--m-out); animation-timeline: --m-ruler; animation-range: cover calc(3% + var(--i) * 3.5%) cover calc(8% + var(--i) * 3.5%); }
      .m-draw > li > * { animation: m-rise backwards; animation-timing-function: var(--m-out); animation-timeline: --m-ruler; animation-range: cover calc(4% + var(--i) * 3.5%) cover calc(14% + var(--i) * 3.5%); }
    }

    /* The real signature writes itself, left to right (a wipe of his own PNG, nothing redrawn) */
    :is(.m-write, .wp-block-image.is-style-signature-write img) { animation: m-write backwards; animation-timing-function: var(--m-inout); animation-timeline: view(); animation-range: entry 10% cover 40%; }

    /* The waveform sweeps in from the left as the band arrives */
    .m-wave { animation: m-write backwards; animation-timing-function: var(--m-out); animation-timeline: view(); animation-range: entry 0% cover 35%; }

    /* Hero stack (first block of the page only): on wide screens the hero stays put and
       recedes while the painting wall slides over it. The wrapper is the .is-style-stack group (hero + next section). */
    @media (min-width: 64em) and (min-height: 44em) {
      .wp-block-group.is-style-stack > :first-child { position: sticky; top: var(--header-h); z-index: 0; }
      .wp-block-group.is-style-stack > :not(:first-child) { position: relative; z-index: 1; background: var(--c-paper); }
      .wp-block-group.is-style-stack > :first-child > * { animation: m-recede linear both; animation-timeline: scroll(root block); animation-range: 0px 50vh; }
    }
  }
}

/* Keyframes (the "to" state is always the static design) */
@keyframes m-failsafe { to { opacity: 1; } }
@keyframes m-word { from { opacity: 0; transform: translateY(0.5em); filter: blur(6px); } }
@keyframes m-word-em { from { opacity: 0; transform: translateY(0.3em) skewX(-14deg); filter: blur(6px); } }
@keyframes m-title { from { opacity: 0; transform: translateY(0.5em); filter: blur(6px); } }
@keyframes m-rise { from { opacity: 0; transform: translateY(1.5rem); } }
@keyframes m-rise-far { from { opacity: 0; transform: translateY(3rem) scale(0.97); } }
@keyframes m-scalex { from { transform: scaleX(0); } }
@keyframes m-pop { from { transform: scale(0) rotate(45deg); } }
@keyframes m-unveil { from { clip-path: inset(0 0 100% 0); transform: scale(1.06); } to { clip-path: inset(0 0 0 0); transform: none; } }
@keyframes m-unveil-rise { from { clip-path: inset(0 0 100% 0); transform: translateY(2.5rem); } to { clip-path: inset(0 0 0 0); transform: none; } }
@keyframes m-write { from { clip-path: inset(0 100% 0 0); } to { clip-path: inset(0 0 0 0); } }
@keyframes m-drift { from { transform: translateY(var(--m-drift)); } to { transform: translateY(calc(-1 * var(--m-drift))); } }
@keyframes m-halo {
  0%   { opacity: 0.15; transform: translate(-50%, -35%) scale(0.55); }
  50%  { opacity: 1;    transform: translate(-50%, -50%) scale(1); }
  100% { opacity: 0.3;  transform: translate(-50%, -65%) scale(1.2); }
}
@keyframes m-focus { 0% { transform: scale(0.86); opacity: 0.55; } 40%, 60% { transform: none; opacity: 1; } 100% { transform: scale(0.86); opacity: 0.55; } }
@keyframes m-recede { to { opacity: 0.2; transform: translateY(-2.5rem) scale(0.975); filter: blur(3px); } }
@keyframes m-bar { from { transform: scaleY(calc(var(--h, 0.5) * 0.3)); } to { transform: scaleY(var(--h, 0.5)); } }
@keyframes m-redraw {
  0%   { transform: scaleX(1); transform-origin: 100% 50%; }
  45%  { transform: scaleX(0); transform-origin: 100% 50%; }
  55%  { transform: scaleX(0); transform-origin: 0 50%; }
  100% { transform: scaleX(1); transform-origin: 0 50%; }
}
/* ---------- 9. Creative v5 (from design/mockups/v5-creative/creative-v5.css section 10) ---------- */
   New opt-in classes: .m-cascade (wall/strip/columns: works are hung one after another),
   .m-on-load (play it on load: the hero), .m-depth (hero wall: works drift apart a little as
   you scroll away), .is-style-stamp (stamp lands). End state = static design; reduced motion = static. */
.m-cascade > li:nth-child(2) { --i: 1; } .m-cascade > li:nth-child(3) { --i: 2; } .m-cascade > li:nth-child(4) { --i: 3; }
.m-cascade > li:nth-child(5) { --i: 4; } .m-cascade > li:nth-child(6) { --i: 5; } .m-cascade > li:nth-child(7) { --i: 6; }
.m-cascade > li:nth-child(8) { --i: 7; } .m-cascade > li:nth-child(9) { --i: 8; } .m-cascade > li:nth-child(10) { --i: 9; }
.m-cascade > li:nth-child(11) { --i: 10; } .m-cascade > li:nth-child(12) { --i: 11; } .m-cascade > li:nth-child(n+13) { --i: 12; }
.m-cascade > li:nth-child(even) { --tilt: 1.4deg; }
@media (prefers-reduced-motion: no-preference) {
  .m-cascade.m-on-load > li > * { animation: cv-hang 1.05s var(--m-out) backwards; animation-delay: calc(380ms + var(--i, 0) * 75ms); }
  .m-cascade.m-on-load > li > figure img { animation: cv-unveil 1.05s var(--m-out) backwards; animation-delay: calc(380ms + var(--i, 0) * 75ms); }
  @supports (animation-timeline: view()) {
    .m-cascade:not(.m-on-load) > li > * {
      animation: cv-hang linear backwards; animation-timing-function: var(--m-out);
      animation-timeline: view(); animation-range: entry calc(min(var(--i, 0), 5) * 5%) cover calc(24% + min(var(--i, 0), 5) * 3%);
    }
    .m-cascade:not(.m-on-load) > li > figure img {
      animation: cv-unveil linear backwards; animation-timing-function: var(--m-out);
      animation-timeline: view(); animation-range: entry calc(min(var(--i, 0), 5) * 5%) cover calc(24% + min(var(--i, 0), 5) * 3%);
    }
    .art-columns.m-cascade > li > *, .art-columns.m-cascade > li > figure img { animation-range: entry 0% cover 22%; }
    .is-style-stamp { animation: cv-stamp linear backwards; animation-timing-function: cubic-bezier(0.3, 1.5, 0.6, 1); animation-timeline: view(); animation-range: entry 30% cover 38%; }
    .cv-poster .is-style-poster .m-w { animation-range: cover calc(var(--i) * 4%) cover calc(22% + var(--i) * 4%); }
  }
  @supports (animation-timeline: scroll()) {
    @media (min-width: 40em) {
      .m-depth > li:nth-child(3n+2) { --z: 1; } .m-depth > li:nth-child(3n) { --z: 2; }
      .m-depth > li { animation: cv-depth linear both; animation-timeline: scroll(root block); animation-range: 0 100vh; }
    }
  }
}
@keyframes cv-hang { from { opacity: 0; transform: translateY(2.25rem) rotate(var(--tilt, -1.4deg)); } }
@keyframes cv-unveil { from { clip-path: inset(0 0 100% 0); } to { clip-path: inset(0 0 0 0); } }
@keyframes cv-depth { to { transform: translateY(calc(var(--z, 0) * -0.65rem)); } }
@keyframes cv-stamp { from { opacity: 0; scale: 1.9; rotate: -28deg; } }

/* ---------- 10. Home v5 "Studio wall" (from design/mockups/v5-home/home-v5-motion.css, on block classes)
   Hero on load: the words, then the field wipes in from the right, Telthia unveils, the works are hung one by one.
   Shuffle: a view transition in which only the four cards move (hang.js sets html.fs-vt). ---------- */
@media (prefers-reduced-motion: no-preference) {
  .is-style-studio-wall > .art-block--lead:has(.m-on-load) > .art-panel { animation: v5-field 1.1s var(--m-out) 0.05s backwards; }
  .is-style-studio-wall .m-enter-wipe.m-on-load img { animation-delay: 0.45s; }
  .is-style-studio-wall .m-enter-wipe.m-on-load figcaption { animation: m-rise 0.9s var(--m-out) 1.2s backwards; }
  .is-style-studio-wall .art-hang.m-cascade.m-on-load > li > * { animation-name: v5-hang; animation-duration: 0.95s; animation-delay: calc(0.95s + var(--i, 0) * 0.12s); }
  .is-style-studio-wall .art-hang.m-cascade.m-on-load > li > figure img { animation: none; }
  .is-style-studio-wall .art-hang__actions { animation: m-rise 0.8s var(--m-out) 1.6s backwards; }

  html.fs-vt { view-transition-name: none; }
  html.fs-vt .site-header, html.fs-vt img { view-transition-name: none !important; }
  ::view-transition-group(*.fs-card) { animation-duration: 0.6s; animation-timing-function: var(--m-out); }
  ::view-transition-old(*.fs-card) { animation: v5-unhang 0.3s cubic-bezier(0.4, 0, 1, 1) both; }
  ::view-transition-new(*.fs-card) { animation: v5-hang 0.75s var(--m-out) 0.12s both; }
  ::view-transition-new(fs-h1) { animation-delay: 0.19s; }
  ::view-transition-new(fs-h2) { animation-delay: 0.26s; }
  ::view-transition-new(fs-h3) { animation-delay: 0.33s; }

  .art-shuffle svg { transition: transform 0.6s var(--m-out); }
  .art-shuffle:is(:hover, :focus-visible) svg { transform: rotate(180deg); }

  @supports (animation-timeline: scroll()) {
    @media (min-width: 64em) {
      .is-style-studio-wall .m-depth > li:nth-child(1) { --z: 0; }
      .is-style-studio-wall .m-depth > li:nth-child(2) { --z: 3.4615; }
      .is-style-studio-wall .m-depth > li:nth-child(3) { --z: 1.1538; }
      .is-style-studio-wall .m-depth > li:nth-child(4) { --z: 4.6154; }
    }
    @media (max-width: 63.99em) { .is-style-studio-wall .m-depth > li { animation: none; } }
    p.is-style-loop, ul.is-style-publications { animation: m-rise backwards; animation-timing-function: var(--m-out); animation-timeline: view(); animation-range: entry 0% cover 25%; }
    p.is-style-loop::before { animation: v5-loop linear backwards; animation-timeline: view(); animation-range: entry 10% cover 35%; }
  }
}
@keyframes v5-field { from { clip-path: inset(0 0 0 100%); } to { clip-path: inset(0 0 0 0); } }
@keyframes v5-hang { from { opacity: 0; clip-path: inset(0 0 100% 0); transform: translateY(-0.9rem) rotate(-0.6deg); } to { opacity: 1; clip-path: inset(0 0 0 0); transform: none; } }
@keyframes v5-unhang { to { opacity: 0; transform: translateY(0.9rem); } }
@keyframes v5-loop { from { transform: rotate(-300deg); opacity: 0; } }

/* ---------- 11. Scroll reveals play once ----------
   motion.js marks a view()-timeline reveal as soon as it has reached its end (end state = static design);
   from then on the box is static, so it is never hidden again when it leaves the viewport. */
.m-shown, .m-shown-b::before, .m-shown-a::after { animation: none !important; }

