/* ————————————————————————————————————————————————
   Autumn Portals · 01 — China · Ginkgo
   A start-menu, not a screensaver. The camera holds still;
   the wind and the whispers carry the life.
   ———————————————————————————————————————————————— */

:root {
  --ink: #0d0906;
  --umber: #1a1108;
  --gold: #d4a94e;
  --gold-bright: #eccf8a;
  --gold-dim: #9a7b3c;
  --parchment: #f3e7cb;
  --parchment-dim: #cdbb96;
  --copper: #8a5a2b;
  --halo: 236, 207, 138;
  --serif: "Cormorant Garamond", "Times New Roman", serif;
  --sans: "Jost", "Avenir Next", "Helvetica Neue", sans-serif;
  /* Shanghai Modeng is download-only (no webfont exists); it activates
     automatically if installed locally. ZCOOL XiaoWei carries the deco role
     live; Ma Shan Zheng = brush H2; ZCOOL KuaiLe = body. */
  --font-h1: "Shanghai Modeng", "上海摩登", "ZCOOL XiaoWei", "Cormorant Garamond", serif;
  --font-h2: "Ma Shan Zheng", "Cormorant Garamond", serif;
  --font-body: "Jost", "Avenir Next", "Helvetica Neue", sans-serif;
}

* { margin: 0; padding: 0; box-sizing: border-box; }

html, body {
  height: 100%;
  background: var(--ink);
  color: var(--parchment);
  font-family: var(--sans);
  overflow: hidden;
}

body { -webkit-font-smoothing: antialiased; text-rendering: optimizeLegibility; }

::selection { background: rgba(212, 169, 78, .35); }

button { font: inherit; color: inherit; background: none; border: none; cursor: pointer; }
a { color: inherit; text-decoration: none; }

/* —— the cursor: a quiet companion, not an arrow —— */

html, body { cursor: none; }
a, button, .chip, .fact-pin, .foot-note { cursor: pointer; }

#cursor {
  position: fixed; left: 0; top: 0;
  z-index: 95;
  pointer-events: none;
  opacity: 0;
  transition: opacity .35s ease;
  --swell: 1;
}
#cursor.on { opacity: 1; }
#cursor.hidden { opacity: 0; }
#cursor .c-dot {
  position: absolute;
  width: 4px; height: 4px; margin: -2px;
  border-radius: 50%;
  background: var(--gold-bright);
}
#cursor .c-ring {
  position: absolute;
  width: 26px; height: 26px; margin: -13px;
  border-radius: 50%;
  /* a 1px hairline aliases into a "pixelated circle" over the bright glow —
     draw the ring soft instead: 1.5px stroke + faint halo on both sides */
  border: 1.5px solid rgba(236, 207, 138, .42);
  box-shadow: 0 0 2px rgba(236, 207, 138, .35), inset 0 0 2px rgba(236, 207, 138, .3);
  transform: scale(var(--swell));
  transition: transform .25s ease;
}
@media (hover: none) { #cursor { display: none; } html, body { cursor: auto; } }

/* —— arrival: the page composes itself, one breath at a time —— */

body.intro #landingCopy .eyebrow { animation: introRise .9s ease .15s both; }
body.intro #landingCopy h1      { animation: introRise 1.05s ease .3s both; }
body.intro #landingCopy .sub    { animation: introRise 1.05s ease .5s both; }
body.intro:not(.entering) #catWrap  { animation: introFade 1.3s ease .7s both; }
body.intro:not(.entering) #chrome   { animation: introFade 1.1s ease .95s both; }
body.intro:not(.entering) #enterBtn { animation: introFade 1.5s ease 1.15s both; }
@keyframes introRise { from { opacity: 0; transform: translateY(18px); } to { opacity: 1; transform: none; } }
@keyframes introFade { from { opacity: 0; } to { opacity: 1; } }
@media (prefers-reduced-motion: reduce) {
  body.intro #landingCopy .eyebrow, body.intro #landingCopy h1, body.intro #landingCopy .sub,
  body.intro #catWrap, body.intro #chrome, body.intro #enterBtn { animation: none; }
}

/* —— film layers ——————————————————————————— */

#grain, #vignette {
  position: fixed; inset: 0;
  pointer-events: none;
  z-index: 90;
}
#grain {
  opacity: .055;
  mix-blend-mode: overlay;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='240' height='240'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
  animation: grainShift 1.4s steps(3) infinite;
}
@keyframes grainShift {
  0% { transform: translate(0, 0); }
  33% { transform: translate(-24px, 14px); }
  66% { transform: translate(18px, -22px); }
  100% { transform: translate(0, 0); }
}
#vignette {
  background:
    radial-gradient(ellipse 120% 90% at 50% 46%, transparent 52%, rgba(6, 3, 1, .6) 100%);
}

/* —— chrome ————————————————————————————————— */

#chrome { position: fixed; inset: 0; pointer-events: none; z-index: 60; }
#chrome > * { pointer-events: auto; }

.brand {
  position: absolute; top: 34px; left: 42px;
  display: flex; align-items: center; gap: 12px;
  font-size: 13px; letter-spacing: .18em; font-weight: 400;
  color: var(--parchment);
  text-transform: uppercase;
}
.brand .ring {
  width: 13px; height: 13px; border-radius: 50%;
  border: 1px solid var(--gold);
  box-shadow: 0 0 12px rgba(var(--halo), .5);
  transition: box-shadow .5s;
}
.brand:hover .ring { box-shadow: 0 0 18px rgba(var(--halo), .9); }

.top-right {
  position: absolute; top: 30px; right: 42px;
  display: flex; align-items: center; gap: 26px;
}
#portalLabel {
  font-size: 12px; letter-spacing: .18em; color: var(--parchment-dim);
  text-transform: uppercase;
}
.chip {
  display: flex; align-items: center; gap: 10px;
  padding: 11px 22px;
  border: 1px solid rgba(212, 169, 78, .45);
  border-radius: 999px;
  font-size: 11px; letter-spacing: .14em; text-transform: uppercase;
  color: var(--parchment);
  background: rgba(13, 9, 6, .25);
  backdrop-filter: blur(6px);
  -webkit-backdrop-filter: blur(6px);
  transition: border-color .4s, box-shadow .4s, color .4s;
}
.chip .ring {
  width: 9px; height: 9px; border-radius: 50%;
  border: 1px solid var(--gold);
  transition: background .4s, box-shadow .4s;
}
.chip:hover { border-color: var(--gold); }
.chip[aria-pressed="true"] { color: var(--gold-bright); border-color: var(--gold); }
.chip[aria-pressed="true"] .ring {
  background: var(--gold-bright);
  box-shadow: 0 0 10px rgba(var(--halo), .9);
}

.hanzi {
  position: absolute; top: 50%; right: 40px;
  transform: translateY(-50%);
  writing-mode: vertical-rl;
  font-family: var(--font-h2);
  font-size: 19px; letter-spacing: .9em;
  color: rgba(212, 169, 78, .62);
  user-select: none;
  pointer-events: none;
}

.foot-note {
  position: absolute; bottom: 28px; left: 42px;
  font-size: 11.5px; letter-spacing: .12em;
  color: rgba(243, 231, 203, .4);
  transition: color .4s, opacity .8s ease;
}
button.foot-note:hover { color: rgba(243, 231, 203, .75); }

.season-mark {
  position: absolute; bottom: 26px; right: 44px;
  font-family: var(--font-h2);
  font-size: 17px;
  color: rgba(212, 169, 78, .5);
  user-select: none;
  pointer-events: none;
}

/* —— scenes: stacked layers, revealed by dissolve —— */

.scene {
  position: fixed; inset: 0;
  overflow: hidden;
}
.scene[hidden] { display: none; }

#scene-portal {
  z-index: 10;
  opacity: 1;
  transform-origin: 57% 46%;      /* the portal's light — where the camera is headed */
  transition: opacity 2.6s ease, transform 3.4s cubic-bezier(.3, .1, .68, .9);
}
/* the dissolve keeps moving: as the portal thins away it also drifts forward,
   so the camera's motion never stops dead on the splice */
#scene-portal.gone { opacity: 0; transform: scale(1.06); pointer-events: none; }

#scene-grove {
  z-index: 5;
  opacity: 0;
  transition: opacity 2.6s ease;
}
#scene-grove.on { opacity: 1; }

/* — Scene 1 · the portal (a held frame, not a loop) — */

.vid-layer {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  object-fit: cover;
  object-position: 50% 50%;
  transition: opacity .6s ease;
}
#vidPush { opacity: 0; }
#heroStill { z-index: 2; }
body.still #heroStill { opacity: 1 !important; }

/* the warped curtain paints over the still's strand region, beneath the grade */
#curtainWarp {
  position: absolute; inset: 0;
  z-index: 2;
  width: 100%; height: 100%;
  pointer-events: none;
}
body.entering #curtainWarp { opacity: 0; transition: opacity .5s ease; }

/* the simulated strand curtain rides just above the warp; on Enter it hands
   back to the push video (whose frames carry the baked strands) in a soft fade */
#strands {
  position: absolute; inset: 0;
  z-index: 2;
  width: 100%; height: 100%;
  pointer-events: none;
}
body.entering #strands { opacity: 0; transition: opacity .45s ease; }

/* the reference grade: deeper shadows, richer amber, light held to the portal */
.grade-veil {
  position: absolute; inset: 0;
  z-index: 3;
  pointer-events: none;
  background:
    radial-gradient(ellipse 105% 92% at 57% 47%, transparent 30%, rgba(9, 4, 1, .30) 62%, rgba(7, 3, 1, .62) 100%),
    linear-gradient(180deg, rgba(9, 4, 1, .38) 0%, transparent 26% 68%, rgba(7, 3, 1, .5) 100%);
}
.glow-breathe {
  position: absolute; inset: 0;
  z-index: 3;
  pointer-events: none;
  background: radial-gradient(ellipse 46% 40% at 57% 42%, rgba(255, 224, 160, .16), transparent 70%);
  animation: glowBreathe 9s ease-in-out infinite;
}
@keyframes glowBreathe {
  0%, 100% { opacity: .45; }
  50%      { opacity: 1; }
}

.portal-scrim {
  position: absolute; inset: 0;
  z-index: 4;
  pointer-events: none;
  background:
    linear-gradient(96deg, rgba(9, 5, 2, .78) 0%, rgba(9, 5, 2, .34) 26%, transparent 52%),
    linear-gradient(0deg, rgba(9, 5, 2, .5) 0%, transparent 26%);
  opacity: .35;
  transition: opacity .8s ease;
}
body.entering .portal-scrim { opacity: 0; }

#leafField { position: absolute; inset: 0; z-index: 6; width: 100%; height: 100%; pointer-events: none; }

/* —— the cats ——————————————————————————————— */

.cat-wrap {
  position: absolute;
  z-index: 7;
  will-change: transform, opacity;
  pointer-events: none;
}
.cat-video {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  /* amber grade is baked into the plates; this seats them in the scene's light */
  filter:
    brightness(.66) sepia(.22) saturate(1.12) hue-rotate(-6deg) contrast(.94)
    drop-shadow(0 3px 14px rgba(6, 3, 0, .9));
}
.cat-video.walk { opacity: 0; }
/* Grounding: a tight dark core right under the body plus a wide soft penumbra.
   Without the core the animal reads as floating above the bright stone. */
.cat-shadow {
  position: absolute;
  left: 21%; bottom: -1.8%;
  width: 58%; height: 11%;
  background:
    radial-gradient(ellipse 46% 52% at 52% 46%, rgba(3, 1, 0, .8) 0%, rgba(3, 1, 0, .5) 38%, transparent 64%),
    radial-gradient(ellipse at center, rgba(4, 2, 0, .34) 0%, transparent 74%);
  filter: blur(6px);
  transform: translateZ(0);
}
/* deeper into the scene, deeper into its light: the courtyard's gold sits ON the coat */
#groveCatWrap .cat-video {
  filter: brightness(.38) sepia(.75) saturate(1.9) hue-rotate(-12deg) contrast(1.08)
          drop-shadow(0 3px 10px rgba(6, 3, 0, .9));
}
body.still .cat-wrap video { /* frozen, but present */ }

/* —— whispers: they surface near the cursor and die down after it —— */

.whisper {
  position: absolute;
  z-index: 9;
  transform: translate(-50%, -50%);
  pointer-events: none;
  --near: 0;
}
.whisper::before {
  content: "";
  position: absolute; left: 50%; top: 50%;
  width: 5px; height: 5px;
  transform: translate(-50%, -50%);
  border-radius: 50%;
  background: rgba(var(--halo), .9);
  box-shadow: 0 0 12px 3px rgba(var(--halo), .55);
  opacity: calc(var(--near) * .9);
  transition: opacity .25s ease;
}
.whisper .w-cap {
  position: absolute; left: 50%; top: calc(50% + 20px);
  transform: translateX(-50%) translateY(calc((1 - var(--near)) * 6px));
  font-family: var(--serif); font-style: italic;
  font-size: 18px;
  white-space: nowrap;
  color: #f7ecd2;
  padding: 7px 18px;
  border-radius: 999px;
  background: rgba(10, 6, 2, .68);
  border: 1px solid rgba(236, 207, 138, .28);
  backdrop-filter: blur(8px);
  -webkit-backdrop-filter: blur(8px);
  box-shadow: 0 4px 22px rgba(6, 3, 0, .55);
  text-shadow: 0 1px 3px rgba(6, 3, 0, .9);
  opacity: calc(var(--near) * 1.25 - 0.12);
  transition: opacity .25s ease;
}
/* the keeper's caption stands above her, not across her body */
#wCat .w-cap { top: auto; bottom: calc(50% + 20px); }

/* —— the way in: a lantern by the hut, found rather than shown —— */

#enterBtn {
  position: absolute;
  z-index: 9;
  transform: translate(-50%, -50%);
  width: 72px; height: 72px;
  border-radius: 50%;
  --near: 0;
}
#enterBtn .orb {
  position: absolute; left: 50%; top: 50%;
  width: 13px; height: 13px;
  transform: translate(-50%, -50%);
  border-radius: 50%;
  background: radial-gradient(circle at 38% 32%, #ffedbd, var(--gold) 68%);
  box-shadow: 0 0 14px 3px rgba(var(--halo), .55);
  transition: box-shadow .5s ease, width .5s ease, height .5s ease;
}
#enterBtn::before {                /* the halo: very soft, breathing slowly */
  content: "";
  position: absolute; inset: -26px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(var(--halo), calc(.16 + var(--near) * .22)) 0%, rgba(var(--halo), .06) 46%, transparent 72%);
  animation: haloBreath 4.6s ease-in-out infinite;
  pointer-events: none;
}
#enterBtn::after {                 /* a hairline ring that wakes with you */
  content: "";
  position: absolute; inset: 14px;
  border-radius: 50%;
  border: 1px solid rgba(var(--halo), calc(.12 + var(--near) * .55));
  transform: scale(calc(.82 + var(--near) * .18));
  transition: transform .4s ease;
  pointer-events: none;
}
@keyframes haloBreath {
  0%, 100% { opacity: .38; transform: scale(.93); }
  50%      { opacity: 1;   transform: scale(1.05); }
}
#enterBtn .lab {
  position: absolute; left: 50%; top: calc(100% - 2px);
  transform: translateX(-50%);
  font-size: 13px;
  letter-spacing: calc(.12em + var(--near) * .05em);
  text-indent: .12em;
  text-transform: uppercase;
  color: var(--gold-bright);
  text-shadow: 0 1px 6px rgba(6, 3, 0, 1), 0 0 18px rgba(6, 3, 0, .9);
  opacity: calc(var(--near) * 1.3 - .1);
  transition: opacity .3s ease;
  white-space: nowrap;
}
/* no cursor, no proximity: on touch screens the lantern introduces itself */
@media (hover: none) {
  #enterBtn .lab { opacity: .85; }
  #enterBtn .orb { width: 16px; height: 16px; box-shadow: 0 0 22px 6px rgba(var(--halo), .7); }
}
#enterBtn.awake .orb, #enterBtn:hover .orb, #enterBtn:focus-visible .orb {
  width: 17px; height: 17px;
  box-shadow: 0 0 26px 7px rgba(var(--halo), .8);
}
#enterBtn:hover .lab, #enterBtn:focus-visible .lab { opacity: 1; }
#enterBtn:focus-visible { outline: none; }
#enterBtn:focus-visible::after { border-color: rgba(var(--halo), .8); }
body.entering #enterBtn {
  opacity: 0;
  transition: opacity .7s ease;
  pointer-events: none;
}

/* landing copy */
#landingCopy {
  position: absolute;
  left: 6.6vw; top: 50%;
  transform: translateY(-52%);
  max-width: 580px;      /* XiaoWei runs wider than the old serif — keep the phrase whole */
  z-index: 7;
  transition: opacity .8s ease;
}
.eyebrow {
  display: flex; align-items: center; gap: 16px;
  font-size: 12px; letter-spacing: .2em; text-transform: uppercase;
  color: var(--gold);
  margin-bottom: 3.2vh;
}
.eyebrow::before {
  content: "";
  width: 44px; height: 1px;
  background: linear-gradient(90deg, transparent, var(--gold));
}
#landingCopy h1 {
  font-family: var(--font-h1);
  font-weight: 400;
  font-size: clamp(38px, 4.6vw, 62px);
  line-height: 1.12;
  color: var(--parchment);
}
#landingCopy h1 em {
  display: block;
  font-family: var(--serif);   /* serif italic against the deco line — the pairing IS the look */
  font-style: italic;
  font-weight: 400;
  color: var(--gold-bright);
}
#landingCopy .sub {
  margin-top: 3vh;
  max-width: 360px;
  font-family: var(--font-body);
  font-size: 15px; font-weight: 300;
  line-height: 1.7;
  letter-spacing: .04em;
  color: var(--parchment-dim);
}
body.entering #landingCopy,
body.entering #chrome .foot-note { opacity: 0; }

/* golden bloom used for the crossing — page-level, so it can fade over the grove */
#bloom {
  position: fixed; inset: 0;
  background:
    radial-gradient(ellipse 62% 58% at 55% 52%, rgba(255, 236, 190, .98) 0%, rgba(244, 206, 130, .88) 34%, rgba(122, 84, 34, .55) 62%, rgba(20, 12, 5, 0) 82%);
  opacity: 0;
  pointer-events: none;
  z-index: 40;
}

/* — Scene 2 · the grove ——————————————————— */

#treeWrap {
  position: absolute; inset: -2%;
  width: 104%; height: 104%;
  will-change: transform, filter;
  transform: scale(1.10) translateY(2.5%);
  filter: brightness(.68) saturate(.9);
}
#treeWrap.emerge {
  transform: scale(1) translateY(0);
  filter: brightness(1) saturate(1);
  transition:
    transform 5.5s cubic-bezier(.19, .55, .22, 1),
    filter 3.6s ease;
}
/* Both loop players MUST stack: as static children the second lays out BELOW
   the first — off-screen — and every crossfade hands the stage to an invisible
   player, blacking out the grove at the first loop point. */
#treeWrap video {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  object-fit: cover; object-position: 50% 38%;
  transition: opacity .35s ease;
}
#scene-grove .shade {
  position: absolute; inset: 0;
  background:
    linear-gradient(180deg, rgba(10, 6, 3, .74) 0%, rgba(10, 6, 3, .22) 16%, transparent 34%),
    linear-gradient(0deg, rgba(10, 6, 3, .82) 0%, rgba(10, 6, 3, .34) 22%, transparent 46%),
    radial-gradient(ellipse 64% 68% at 12% 88%, rgba(8, 5, 2, .9), transparent 74%),
    radial-gradient(ellipse 120% 92% at 50% 48%, transparent 46%, rgba(6, 3, 1, .58) 100%);
}
.mist {
  position: absolute; inset: -6% -14%;
  pointer-events: none;
  opacity: .5;
}
.mist.a {
  background: radial-gradient(ellipse 70% 34% at 24% 66%, rgba(240, 214, 150, .30), transparent 70%);
  animation: mistDrift 26s ease-in-out infinite alternate;
}
.mist.b {
  background: radial-gradient(ellipse 62% 30% at 78% 40%, rgba(228, 196, 128, .22), transparent 70%);
  animation: mistDrift 34s ease-in-out infinite alternate-reverse;
}
@keyframes mistDrift {
  from { transform: translateX(-2.4%) translateY(.6%); }
  to   { transform: translateX(2.4%) translateY(-.9%); }
}

#leaves { position: absolute; inset: 0; z-index: 6; width: 100%; height: 100%; pointer-events: none; }

/* the endless-breeze warp paints over the parked footage, beneath the shade */
#groveWarp {
  position: absolute; inset: 0;
  z-index: 1;
  width: 100%; height: 100%;
  pointer-events: none;
  opacity: 0;
  transition: opacity .6s ease;   /* the takeover breathes in, never snaps */
}
#groveWarp.on { opacity: 1; }

#groveCopy {
  position: absolute;
  left: 6vw; bottom: 9.5vh;
  z-index: 7;
  max-width: 520px;
}
#groveCopy h2 {
  font-family: var(--font-h2);
  font-weight: 400;
  font-size: clamp(30px, 3.4vw, 48px);
  line-height: 1.1;
  color: var(--parchment);
  text-shadow: 0 2px 30px rgba(13, 9, 6, .8);
}
#groveCopy h2 em { display: block; font-family: var(--serif); font-style: italic; font-size: .74em; margin-top: 2px; color: var(--gold-bright); }
#groveCopy .sub {
  margin-top: 1.6vh;
  max-width: 440px;
  font-family: var(--font-body);
  font-size: 15px; font-weight: 300; letter-spacing: .04em;
  line-height: 1.7;
  color: var(--parchment);
  text-shadow:
    0 1px 2px rgba(8, 5, 2, .95),
    0 2px 10px rgba(8, 5, 2, .85),
    0 6px 30px rgba(8, 5, 2, .7);
}

.back-link {
  position: absolute; top: 92px; left: 42px;
  display: inline-flex; align-items: center; gap: 10px;
  font-size: 12px; letter-spacing: .14em; text-transform: uppercase;
  color: var(--parchment-dim);
  z-index: 9;
  transition: color .4s;
}
.back-link:hover { color: var(--gold-bright); }
.back-link .arrow { font-family: var(--serif); font-size: 16px; }

/* fact pins — lanterns around the crown, speaking the Enter lantern's language */
.fact-pin {
  position: absolute;
  transform: translate(-50%, -50%);
  display: flex; flex-direction: column; align-items: center; gap: 13px;
  z-index: 8;
  opacity: 0;
  transition: opacity 1.2s ease, transform 1.2s ease;
}
.fact-pin.shown { opacity: 1; }
.fact-pin .dot {
  position: relative;
  width: 15px; height: 15px;
  border-radius: 50%;
  background: radial-gradient(circle at 40% 35%, #ffe9b3, var(--gold) 65%);
  box-shadow: 0 0 18px 4px rgba(var(--halo), .8);
}
.fact-pin .dot::before {
  content: "";
  position: absolute; inset: -22px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(var(--halo), .4) 0%, transparent 66%);
  animation: haloBreath 4.6s ease-in-out infinite;
}
.fact-pin:nth-of-type(2) .dot::before { animation-delay: -1.5s; }
.fact-pin:nth-of-type(3) .dot::before { animation-delay: -3s; }
.fact-pin .tag {
  padding: 12px 24px;
  border: 1px solid rgba(236, 207, 138, .46);
  border-radius: 999px;
  background: rgba(12, 7, 3, .82);
  box-shadow: 0 6px 30px rgba(6, 3, 1, .6);
  backdrop-filter: blur(10px);
  -webkit-backdrop-filter: blur(10px);
  font-size: 12px; letter-spacing: .12em; text-indent: .12em; text-transform: uppercase;
  color: var(--parchment);
  white-space: nowrap;
  transition: color .4s, border-color .4s, box-shadow .4s;
}
.fact-pin:hover .tag, .fact-pin:focus-visible .tag {
  color: var(--gold-bright);
  border-color: var(--gold-bright);
  box-shadow: 0 0 26px rgba(var(--halo), .35);
}
.fact-pin:focus-visible { outline: none; }
.fact-pin .num {
  position: absolute; top: -26px;
  font-family: var(--font-h2);
  font-size: 15px; color: rgba(236, 207, 138, .75);
}

#groveCopy, .back-link, .fact-pin { transition-property: opacity, transform, color; }
body.leaving #scene-grove { opacity: .45; transition: opacity 1.6s ease; }

/* —— reduced motion ————————————————————————— */

@media (prefers-reduced-motion: reduce) {
  #grain { animation: none; }
  .glow-breathe { animation: none; }
  #enterBtn::before, .fact-pin .dot::before { animation-duration: 9s; }
  .mist { animation: none; }
  #scene-portal, #scene-grove { transition-duration: .2s; }
  #treeWrap { transform: none; filter: none; }
  #treeWrap.emerge { transition-duration: .2s; }
}

/* —— small screens ————————————————————————— */

@media (max-width: 760px) {
  .brand { top: 22px; left: 22px; letter-spacing: .26em; font-size: 11px; }
  .top-right { top: 18px; right: 18px; gap: 14px; }
  #portalLabel { display: none; }
  .hanzi { display: none; }

  .portal-scrim {
    opacity: 1;
    background:
      linear-gradient(180deg, rgba(9, 5, 2, .88) 0%, rgba(9, 5, 2, .72) 28%, rgba(9, 5, 2, .3) 46%, transparent 62%),
      linear-gradient(96deg, rgba(9, 5, 2, .6) 0%, rgba(9, 5, 2, .2) 40%, transparent 70%),
      linear-gradient(0deg, rgba(9, 5, 2, .58) 0%, transparent 22%);
  }
  #landingCopy {
    left: 7vw; top: 15vh;
    transform: none;
    max-width: 86vw;
  }
  #landingCopy h1 { font-size: clamp(38px, 11vw, 54px); }
  #landingCopy .sub { max-width: 66vw; margin-top: 2.2vh; }
  .foot-note { left: 22px; bottom: 20px; max-width: 60vw; }
  .season-mark { right: 22px; }
  .back-link { top: 76px; left: 22px; }
  #groveCopy { left: 8vw; bottom: 12vh; max-width: 84vw; }
  .fact-pin .tag { padding: 10px 16px; font-size: 11px; letter-spacing: .1em; }
  .whisper .w-cap { font-size: 13px; }
}
