/* ============================================================
   INDITHAR — Ink & Candlelight
   The screen is a continuation of a dark room.
   ============================================================ */

:root {
  --ink:        oklch(0.13 0.012 70);
  --void:       oklch(0.08 0.008 260);
  --bone:       oklch(0.90 0.02 85);
  --bone-dim:   oklch(0.72 0.02 85);
  --faded:      oklch(0.48 0.015 80);
  --candle:     oklch(0.78 0.13 78);
  --candle-deep:oklch(0.62 0.14 65);
  --hairline:   oklch(0.30 0.02 75);

  --covenant: oklch(0.70 0.02 250);
  --choir:    oklch(0.85 0.09 95);
  --pact:     oklch(0.45 0.14 25);
  --court:    oklch(0.60 0.07 240);
  --wound:    oklch(0.35 0.10 300);

  --serif: 'Spectral', Georgia, serif;
  --fell:  'IM Fell English SC', serif;
  --fell-text: 'IM Fell English', serif;

  --ease: cubic-bezier(0.22, 1, 0.36, 1); /* out-quint */
}

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

[hidden] { display: none !important; }

html { scrollbar-color: var(--hairline) var(--void); }

body {
  background: var(--void);
  color: var(--bone);
  font-family: var(--serif);
  font-weight: 300;
  line-height: 1.75;
  overflow: hidden;
  -webkit-font-smoothing: antialiased;
}

::selection { background: var(--candle-deep); color: var(--void); }

img { max-width: 100%; display: block; }
a { color: var(--candle); text-decoration: none; }
button { font: inherit; color: inherit; background: none; border: 0; cursor: pointer; }

/* ---------- shared layers ---------- */

/* THE LAMP — the wall of the room, and the only light falling on it.
   This canvas sits behind every room and is the reason the paintings have
   surfaces now. See js/lamp.js. */
#lamp {
  position: fixed; inset: 0; z-index: 0; pointer-events: none;
  width: 100%; height: 100%;
  opacity: 0;
  transition: opacity 900ms ease-in;
  transform: translateY(calc(var(--shock, 0) * 2px));
}
#lamp.lit { opacity: 1; }

/* THE AIR — everything between you and the wall: the flame you carry, the dust
   it catches, and the other people who are quietly in here with you. One layer,
   one loop. See js/air.js. */
#air {
  position: fixed; inset: 0; z-index: 28; pointer-events: none;
  width: 100%; height: 100%;
  mix-blend-mode: screen;
  transform: translateY(calc(var(--shock, 0) * 3px));
}

/* film, not video: the grain is quantised to twelve frames a second */
#grain {
  position: fixed; inset: -8%; z-index: 29; pointer-events: none;
  opacity: 0.038;
  mix-blend-mode: screen;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='220' height='220'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.82' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='220' height='220' filter='url(%23n)'/%3E%3C/svg%3E");
  animation: grainshift 0.5s steps(1) infinite;
}
@keyframes grainshift {
  0%     { transform: translate(0, 0); }
  16.6%  { transform: translate(-3%, 2%); }
  33.3%  { transform: translate(2%, -3%); }
  50%    { transform: translate(-2%, -2%); }
  66.6%  { transform: translate(3%, 2%); }
  83.3%  { transform: translate(-1%, 3%); }
  100%   { transform: translate(0, 0); }
}

/* living paintings: ambient video over the still */
.bg-video {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover;
  opacity: 0;
  transition: opacity 1600ms ease-in;
}
.bg-video.live { opacity: 1; }

/* room arrival: settle out of the dark */
.room.arrive > * { animation: settle 1100ms var(--ease) both; }
.room.arrive > *:nth-child(2) { animation-delay: 90ms; }
.room.arrive > *:nth-child(3) { animation-delay: 180ms; }
.room.arrive > *:nth-child(4) { animation-delay: 260ms; }
@keyframes settle {
  from { opacity: 0; transform: scale(1.015); filter: blur(5px); }
  to   { opacity: 1; transform: none; filter: none; }
}

/* headings ink themselves in */
.room.arrive h2 { animation: inkin 1300ms var(--ease) 200ms both; }
@keyframes inkin {
  from { opacity: 0; filter: blur(7px); letter-spacing: 0.16em; }
  to   { opacity: 1; filter: none; }
}

/* scroll reveals */
.reveal { opacity: 0; transform: translateY(26px); }
.reveal.revealed {
  opacity: 1; transform: none;
  transition: opacity 1000ms var(--ease), transform 1000ms var(--ease);
}

/* The veil is a canvas now: it does not fade, it CLOSES — a hole shrinking onto the
   exact point you touched, so the door you chose is the last thing alive on screen.
   See js/transit.js. */
#veil {
  position: fixed; inset: 0; z-index: 90;
  width: 100%; height: 100%;
  pointer-events: none;
}

/* The wordmark used to sit on the void, so it needed nothing behind it. Then the
   Atlas filled the screen with pale parchment and it vanished into the mountains.
   A scrim you cannot see in a dark room, and can in a bright one. */
#chrome::before {
  content: ''; position: absolute; inset: 0 0 auto 0; height: 260%;
  background: linear-gradient(180deg, oklch(0.05 0.008 260 / 0.88), oklch(0.05 0.008 260 / 0.4) 45%, transparent);
  pointer-events: none; z-index: -1;
}

#chrome {
  position: fixed; z-index: 80; inset: 0 0 auto 0;
  display: flex; justify-content: space-between; align-items: baseline;
  padding: clamp(1rem, 3vh, 1.6rem) clamp(1.2rem, 4vw, 3rem);
  pointer-events: none;
}
#chrome > * { pointer-events: all; }

#wordmark {
  font-family: var(--fell);
  font-size: 1.05rem; letter-spacing: 0.22em; color: var(--bone-dim);
  transition: color 400ms;
}
#wordmark:hover { color: var(--candle); }

#mute {
  font-variant-caps: small-caps; letter-spacing: 0.14em;
  font-size: 0.8rem; color: var(--faded); transition: color 400ms;
}
#mute:hover { color: var(--candle); }
#mute .off { display: none; }
#mute[aria-pressed="true"] .on { display: none; }
#mute[aria-pressed="true"] .off { display: inline; }

/* ---------- rooms ---------- */

.room {
  position: fixed; inset: 0;
  display: block;
}
.room[hidden] { display: none; }
.room-scroll { overflow-y: auto; overflow-x: hidden; }

/* ---------- placard: the atom ---------- */

.placard-label {
  font-variant-caps: small-caps; letter-spacing: 0.16em;
  font-size: 0.78rem; color: var(--faded); font-weight: 400;
}

.hairline { border: 0; border-top: 1px solid var(--hairline); }

/* ============================================================
   INTRO — the threshold
   ============================================================ */

.intro-scene {
  position: absolute; inset: 0; overflow: hidden;
  display: grid; place-items: center;
  background: var(--void);
}

.intro-tome {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; opacity: 0;
  transition: opacity 2400ms ease-in;
  filter: brightness(0.75) saturate(0.85);
}
.intro-scene.lit .intro-tome { opacity: 0.85; }

.intro-fog {
  position: absolute; inset: -20%;
  background:
    radial-gradient(ellipse 60% 40% at 30% 80%, oklch(0.35 0.01 260 / 0.16), transparent 70%),
    radial-gradient(ellipse 50% 35% at 75% 70%, oklch(0.35 0.01 260 / 0.11), transparent 70%);
  animation: fogdrift 26s ease-in-out infinite alternate;
  opacity: 0;
  transition: opacity 3000ms ease-in;
}
.intro-scene.lit .intro-fog { opacity: 1; }
@keyframes fogdrift {
  from { transform: translateX(-3%) translateY(0); }
  to   { transform: translateX(3%) translateY(-2%); }
}

.intro-lines {
  position: relative; z-index: 2;
  font-family: var(--fell-text); font-style: italic;
  font-size: clamp(1.25rem, 3.2vw, 2rem);
  letter-spacing: 0.08em;
  color: var(--bone-dim);
  min-height: 2.6em;
  text-align: center;
  text-shadow: 0 2px 24px oklch(0.05 0 0 / 0.9);
  transform: translateY(-16vh);
}

.intro-title {
  position: relative; z-index: 2;
  font-family: var(--fell);
  font-weight: 400;
  font-size: clamp(3rem, 10vw, 7.5rem);
  letter-spacing: 0.18em;
  text-indent: 0.18em; /* optically recenter tracked caps */
  color: var(--bone);
  text-shadow: 0 0 60px oklch(0.78 0.13 78 / 0.25), 0 2px 30px oklch(0.05 0 0 / 0.95);
  transform: translateY(-6vh);
}
.intro-title span {
  display: inline-block;
  opacity: 0; transform: translateY(0.16em) scale(1.05); filter: blur(7px);
  transition: opacity 1100ms var(--ease), transform 1300ms var(--ease), filter 1100ms var(--ease);
  transition-delay: calc(var(--i, 0) * 95ms);
}
.intro-scene.titled .intro-title span { opacity: 1; transform: none; filter: none; }
/* no-JS / reduced fallback: plain text node inside h1 still shows via .titled */
.intro-title:not(:has(span)) { opacity: 0; transition: opacity 2200ms var(--ease); }
.intro-scene.titled .intro-title:not(:has(span)) { opacity: 1; }

.intro-sub {
  position: relative; z-index: 2;
  margin-top: -5vh;
  font-variant-caps: small-caps; letter-spacing: 0.34em; text-indent: 0.34em;
  color: var(--faded); font-size: clamp(0.8rem, 1.6vw, 1rem);
  opacity: 0; transition: opacity 2400ms ease-in 600ms;
}
.intro-scene.titled .intro-sub { opacity: 1; }

.enter-btn {
  position: relative; z-index: 2;
  margin-top: 7vh;
  font-family: var(--fell);
  font-size: clamp(1.1rem, 2.4vw, 1.5rem);
  letter-spacing: 0.3em; text-indent: 0.3em;
  color: var(--candle);
  padding: 0.9em 2.4em;
  border: 1px solid oklch(0.40 0.06 75 / 0.6);
  background: oklch(0.10 0.01 70 / 0.35);
  opacity: 0; transform: translateY(12px);
  transition: opacity 1400ms var(--ease), transform 1400ms var(--ease),
              border-color 500ms, color 500ms, box-shadow 500ms;
}
.enter-btn.shown { opacity: 1; transform: translateY(0); }
.enter-btn:hover, .enter-btn:focus-visible {
  color: var(--bone); border-color: var(--candle);
  box-shadow: 0 0 40px oklch(0.78 0.13 78 / 0.18), inset 0 0 24px oklch(0.78 0.13 78 / 0.07);
}

.skip-note {
  position: absolute; z-index: 2; bottom: 4vh; left: 50%; transform: translateX(-50%);
  font-variant-caps: small-caps; letter-spacing: 0.14em;
  font-size: 0.78rem; color: var(--faded);
  opacity: 0; transition: opacity 1600ms ease-in 1200ms, color 400ms;
}
.skip-note.shown { opacity: 0.85; }
.skip-note:hover { color: var(--candle); }

/* ============================================================
   HUB — the great library
   ============================================================ */

.hub-art {
  position: absolute; inset: 0; overflow: hidden;
  transform: scale(1.07);
  transition: transform 400ms linear;
}
.hub-art img {
  width: 100%; height: 100%; object-fit: cover;
  filter: brightness(0.9);
}
.hub-art .bg-video { filter: brightness(0.9); }

.hub-grade {
  position: absolute; inset: 0; pointer-events: none;
  background:
    linear-gradient(90deg, oklch(0.08 0.008 260 / 0.88) 0%, oklch(0.08 0.008 260 / 0.55) 34%, transparent 62%),
    linear-gradient(0deg, oklch(0.08 0.008 260 / 0.85) 0%, transparent 30%),
    linear-gradient(180deg, oklch(0.08 0.008 260 / 0.55) 0%, transparent 22%);
}

.hub-doors {
  position: absolute; z-index: 3;
  left: clamp(1.4rem, 6vw, 6rem);
  top: 50%; transform: translateY(-50%);
  display: flex; flex-direction: column;
  gap: clamp(0.5rem, 1.9vh, 1.15rem);
  max-width: min(560px, 88vw);
}

.hub-eyebrow {
  font-variant-caps: small-caps; letter-spacing: 0.2em;
  color: var(--faded); font-size: 0.8rem;
  margin-bottom: clamp(0.6rem, 2.4vh, 1.6rem);
}

.door { display: block; opacity: 0; transform: translateX(-14px); }
.door.lit { opacity: 1; transform: none; transition: opacity 900ms var(--ease), transform 900ms var(--ease); }

.door-name {
  display: block;
  font-family: var(--fell);
  font-size: clamp(1.5rem, 3.6vh, 2.2rem);
  letter-spacing: 0.06em;
  color: var(--bone-dim);
  transition: color 450ms, text-shadow 450ms, transform 600ms var(--ease);
}
.door-whisper {
  display: block;
  font-style: italic; font-family: var(--fell-text);
  font-size: clamp(0.85rem, 1.8vh, 1rem);
  color: transparent;
  letter-spacing: 0.04em;
  max-height: 0; overflow: hidden;
  transition: color 600ms 100ms, max-height 500ms var(--ease);
}
.door:hover .door-name, .door:focus-visible .door-name {
  color: var(--candle);
  text-shadow: 0 0 34px oklch(0.78 0.13 78 / 0.35);
  transform: translateX(6px);
}
.door:hover .door-whisper, .door:focus-visible .door-whisper {
  color: var(--faded); max-height: 2.2em;
}

.colophon-link {
  position: absolute; z-index: 3;
  right: clamp(1.2rem, 4vw, 3rem); bottom: clamp(1rem, 3vh, 1.6rem);
  font-variant-caps: small-caps; letter-spacing: 0.14em;
  font-size: 0.78rem; color: var(--faded);
  transition: color 400ms;
}
.colophon-link:hover { color: var(--candle); }

/* ============================================================
   ATLAS
   ============================================================ */

.atlas-stage { position: absolute; inset: 0; background: oklch(0.10 0.01 70); }

#atlas-canvas { position: absolute; inset: 0; width: 100%; height: 100%; cursor: grab; touch-action: none; }
#atlas-canvas.grabbing { cursor: grabbing; }

#atlas-pins { position: absolute; inset: 0; pointer-events: none; overflow: hidden; }

.pin {
  position: absolute; pointer-events: all;
  transform: translate(-50%, -50%);
  display: grid; place-items: center;
  width: 34px; height: 34px;
  background: none; border: 0; cursor: pointer;
}
.pin::before {
  content: ''; display: block; width: 9px; height: 9px;
  background: var(--pin-tint, var(--candle));
  transform: rotate(45deg);
  box-shadow: 0 0 12px oklch(0.78 0.13 78 / 0.5);
  transition: transform 350ms var(--ease), box-shadow 350ms;
}
.pin:hover::before, .pin:focus-visible::before, .pin.active::before {
  transform: rotate(45deg) scale(1.5);
  box-shadow: 0 0 22px var(--pin-tint, var(--candle));
}
.pin-label {
  position: absolute; top: 100%; left: 50%; transform: translateX(-50%);
  white-space: nowrap;
  font-variant-caps: small-caps; letter-spacing: 0.12em; font-size: 0.72rem;
  color: var(--bone-dim);
  text-shadow: 0 1px 8px oklch(0.05 0 0), 0 0 3px oklch(0.05 0 0);
  opacity: 0; transition: opacity 300ms;
  pointer-events: none;
}
.pin:hover .pin-label, .pin:focus-visible .pin-label, .pin.active .pin-label { opacity: 1; }
#atlas-pins.close-in .pin-label { opacity: 0.9; }

.atlas-hint {
  position: absolute; left: 50%; bottom: clamp(0.9rem, 2.4vh, 1.4rem); transform: translateX(-50%);
  font-variant-caps: small-caps; letter-spacing: 0.16em;
  font-size: 0.74rem; color: var(--faded);
  pointer-events: none;
  transition: opacity 1200ms;
}
.atlas-hint.gone { opacity: 0; }

/* side placard panel (atlas + shared) */
.placard-panel {
  position: absolute; z-index: 5;
  top: 0; right: 0; bottom: 0;
  width: min(430px, 92vw);
  background: linear-gradient(90deg, transparent, oklch(0.10 0.01 70 / 0.96) 12%);
  padding: clamp(4rem, 10vh, 6rem) clamp(1.6rem, 3vw, 2.6rem) 3rem clamp(2.6rem, 5vw, 4rem);
  overflow-y: auto;
  transform: translateX(24px); opacity: 0;
  transition: transform 600ms var(--ease), opacity 600ms var(--ease);
}
.placard-panel.open { transform: none; opacity: 1; }
.placard-panel h2 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(1.5rem, 3.4vw, 2rem); letter-spacing: 0.05em;
  color: var(--bone); margin: 0.35em 0 0.7em;
}
.placard-panel p { margin-bottom: 1em; color: var(--bone-dim); font-size: 0.98rem; }
.placard-panel em { color: var(--bone); }
.panel-close {
  position: absolute; top: 1.1rem; right: 1.2rem;
  color: var(--faded); font-size: 1rem; transition: color 300ms;
}
.panel-close:hover { color: var(--candle); }

.panel-seal {
  margin-top: 1.6rem; padding-top: 1rem; border-top: 1px solid var(--hairline);
  font-style: italic; font-family: var(--fell-text);
  color: var(--faded); font-size: 0.92rem;
}

/* ============================================================
   ROOM WALLS
   These four rooms used to hang a flat JPEG at opacity 0.30 behind the text,
   lit or not lit, which is why they all read as the same room. The wall is on
   the #lamp canvas now and it only exists where your flame falls. The rooms
   themselves are transparent, and they ride the impulse bus.
   ============================================================ */

/* one transform, carrying two things: the impulse bus, and which way this room lies
   in the building (js/transit.js writes --tx/--ty/--tz) */
.room {
  transform:
    translate(var(--tx, 0px), calc(var(--ty, 0px) + var(--shock, 0) * 3px))
    scale(var(--tz, 1));
}

/* nothing behind the reading rooms but the dark, and whatever you brought */
#room-archives, #room-library, #room-bestiary, #room-halls { background: transparent; }

/* if there is no WebGL2, we do not leave people in an empty black box */
body.no-lamp #room-archives, body.no-lamp #room-library,
body.no-lamp #room-bestiary, body.no-lamp #room-halls {
  background-size: cover; background-position: center;
  background-blend-mode: multiply;
  background-color: oklch(0.08 0.008 260 / 0.72);
}
body.no-lamp #room-archives { background-image: url('../assets/img/bg-archives.jpg'); }
body.no-lamp #room-library  { background-image: url('../assets/img/bg-library.jpg'); }
body.no-lamp #room-bestiary { background-image: url('../assets/img/bg-bestiary.jpg'); }
body.no-lamp #room-halls    { background-image: url('../assets/img/library.jpg'); }

/* ============================================================
   ARCHIVES — timeline
   ============================================================ */

#room-archives { display: flex; flex-direction: column; }

.archives-head {
  padding: clamp(4.5rem, 12vh, 7rem) clamp(1.4rem, 6vw, 6rem) 0;
  flex: 0 0 auto;
}
.archives-head h2 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(1.8rem, 4.5vw, 3rem); letter-spacing: 0.05em;
  margin: 0.2em 0 0.3em;
}
.archives-note { color: var(--faded); font-style: italic; font-family: var(--fell-text); max-width: 60ch; }

.timeline {
  flex: 1 1 auto;
  display: flex; align-items: stretch;
  gap: 0;
  overflow-x: auto; overflow-y: hidden;
  scroll-snap-type: x proximity;
  padding: clamp(2rem, 6vh, 4rem) clamp(1.4rem, 6vw, 6rem);
  scrollbar-width: thin;
  outline: none;
}

.epoch {
  position: relative;
  flex: 0 0 auto;
  width: min(420px, 78vw);
  padding: 2.2rem 3.2rem 0 0;
  scroll-snap-align: start;
  border-top: 1px solid var(--hairline);
}
.epoch::before {
  content: ''; position: absolute; top: -5px; left: 0;
  width: 9px; height: 9px; transform: rotate(45deg);
  background: var(--epoch-tint, var(--faded));
}
.epoch-year {
  font-family: var(--fell); font-size: 1rem; letter-spacing: 0.14em;
  color: var(--candle);
}
.epoch h3 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(1.3rem, 2.6vw, 1.7rem); letter-spacing: 0.04em;
  margin: 0.3em 0 0.5em; color: var(--bone);
}
.epoch p { color: var(--bone-dim); font-size: 0.95rem; max-width: 46ch; }
.epoch .placard-label { margin-bottom: 0.4rem; }

.epoch.torn { color: var(--faded); }
.epoch.torn h3 { color: var(--faded); }
.epoch.torn p {
  color: var(--faded);
  -webkit-mask-image: linear-gradient(180deg, black 30%, transparent 95%);
  mask-image: linear-gradient(180deg, black 30%, transparent 95%);
}
.epoch.torn .epoch-year { color: var(--faded); }

/* ============================================================
   LIBRARY — shelf + reader
   ============================================================ */

#room-library { overflow-y: auto; }

.library-shelf {
  min-height: 100%;
  padding: clamp(4.5rem, 12vh, 7rem) clamp(1.4rem, 6vw, 6rem) 4rem;
  max-width: 1100px; margin-inline: auto;
}
.shelf-section { margin-bottom: clamp(2.5rem, 7vh, 4.5rem); }
.shelf-section h2 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(1.6rem, 3.6vw, 2.4rem); letter-spacing: 0.05em;
  margin: 0.2em 0 0.8em;
}
.shelf-blurb { color: var(--faded); font-style: italic; font-family: var(--fell-text); max-width: 58ch; margin-bottom: 1.8rem; }

.tome-row { display: flex; flex-wrap: wrap; gap: 1.4rem; align-items: stretch; }

.tome {
  flex: 1 1 240px; max-width: 330px;
  text-align: left;
  padding: 1.5rem 1.5rem 1.2rem;
  border: 1px solid var(--hairline);
  background: linear-gradient(160deg, oklch(0.16 0.015 60 / 0.75), oklch(0.11 0.01 70 / 0.9));
  transition: border-color 450ms, box-shadow 450ms, transform 600ms var(--ease);
}
.tome:hover, .tome:focus-visible {
  border-color: oklch(0.45 0.07 75 / 0.8);
  box-shadow: 0 8px 44px oklch(0.05 0 0 / 0.6), 0 0 30px oklch(0.78 0.13 78 / 0.06);
  transform: translateY(-3px);
}
.tome-kind { font-variant-caps: small-caps; letter-spacing: 0.14em; font-size: 0.72rem; color: var(--faded); }
.tome-title {
  display: block; font-family: var(--fell); font-size: 1.25rem; letter-spacing: 0.04em;
  color: var(--bone); margin: 0.5em 0 0.55em; line-height: 1.3;
}
.tome-desc { font-size: 0.9rem; color: var(--bone-dim); font-style: italic; font-family: var(--fell-text); }

.tome.sealed { opacity: 0.55; cursor: default; }
.tome.sealed:hover { transform: none; border-color: var(--hairline); box-shadow: none; }
.tome.sealed .tome-title { color: var(--faded); }

/* reader */
.reader {
  position: absolute; inset: 0; z-index: 6;
  background: var(--void);
  display: flex; flex-direction: column; align-items: center;
  padding: clamp(3.4rem, 8vh, 5rem) clamp(0.8rem, 3vw, 2rem) 1rem;
}
.reader-exit {
  position: absolute; top: clamp(3.2rem, 7vh, 4.2rem); right: clamp(1.2rem, 4vw, 3rem);
  font-variant-caps: small-caps; letter-spacing: 0.14em; font-size: 0.8rem;
  color: var(--faded); transition: color 300ms;
}
.reader-exit:hover { color: var(--candle); }

.reader-book {
  position: relative;
  width: min(1060px, 96vw);
  flex: 1 1 auto; min-height: 0;
  display: grid; grid-template-columns: 1fr 1fr;
  background: linear-gradient(180deg, oklch(0.90 0.015 85), oklch(0.84 0.02 82));
  box-shadow: 0 30px 90px oklch(0.03 0 0 / 0.85), inset 0 0 90px oklch(0.6 0.03 80 / 0.25);
  perspective: 2200px;
}
.reader-book::before { /* gutter shadow */
  content: ''; position: absolute; inset: 0 auto 0 50%; width: 90px; transform: translateX(-50%);
  background: linear-gradient(90deg, transparent, oklch(0.35 0.02 80 / 0.35), transparent);
  pointer-events: none; z-index: 2;
}

.reader-page {
  padding: clamp(1.6rem, 4vh, 3rem) clamp(1.4rem, 3.4vw, 3rem);
  color: oklch(0.24 0.02 60);
  font-size: clamp(0.92rem, 1.35vw, 1.06rem);
  line-height: 1.72;
  overflow: hidden;
  font-weight: 400;
}
.reader-page p { margin-bottom: 0.85em; text-indent: 1.4em; }
.reader-page p.noindent { text-indent: 0; }
.reader-page .chap-label { font-variant-caps: small-caps; letter-spacing: 0.2em; text-align: center; color: oklch(0.45 0.03 60); text-indent: 0; margin: 1.2em 0 0.6em; }
.reader-page h3 {
  font-family: var(--fell); font-weight: 400; text-align: center;
  font-size: 1.7em; letter-spacing: 0.06em; margin: 0.4em 0 1.2em;
  color: oklch(0.2 0.02 60);
}
.reader-page .sep { text-align: center; text-indent: 0; letter-spacing: 0.6em; color: oklch(0.45 0.03 60); margin: 1.1em 0; }
.reader-page .torn-end {
  margin-top: 2em; text-indent: 0; text-align: center;
  font-style: italic; color: oklch(0.45 0.03 60);
}

.reader-flip {
  position: absolute; top: 0; bottom: 0; left: 50%; right: 0; z-index: 3;
  transform-origin: left center;
  background: linear-gradient(180deg, oklch(0.90 0.015 85), oklch(0.84 0.02 82));
  box-shadow: -4px 0 24px oklch(0.2 0.02 60 / 0.25);
  backface-visibility: hidden;
  display: none;
}
.reader-flip.flipping { display: block; animation: pageflip 620ms var(--ease) forwards; }
.reader-flip.flipping.back { animation: pageflipback 620ms var(--ease) forwards; }
@keyframes pageflip { from { transform: rotateY(0); } to { transform: rotateY(-178deg); } }
@keyframes pageflipback { from { transform: rotateY(-178deg); } to { transform: rotateY(0); } }

.reader-nav {
  flex: 0 0 auto;
  display: flex; align-items: baseline; gap: 2rem;
  padding: 0.9rem 0 0.4rem;
  color: var(--faded);
}
.reader-nav button { font-family: var(--fell); font-size: 1.5rem; color: var(--bone-dim); transition: color 300ms; padding: 0 0.6em; }
.reader-nav button:hover:not(:disabled) { color: var(--candle); }
.reader-nav button:disabled { opacity: 0.25; cursor: default; }
#page-num { font-variant-caps: small-caps; letter-spacing: 0.16em; font-size: 0.78rem; }
#read-aloud { margin-left: 1.4rem; }

/* ============================================================
   HALL OF KINGS
   ============================================================ */

#room-halls { scroll-snap-type: y proximity; }

.hall-intro {
  min-height: 88vh;
  display: grid; place-content: center; text-align: center;
  padding: 2rem; scroll-snap-align: start;
}
.hall-intro h2 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(2rem, 6vw, 3.6rem); letter-spacing: 0.08em;
  margin: 0.25em 0;
}
.hall-intro p { color: var(--bone-dim); font-style: italic; font-family: var(--fell-text); max-width: 52ch; margin-inline: auto; }
.hall-scroll-cue { margin-top: 8vh; color: var(--faded); font-variant-caps: small-caps; letter-spacing: 0.2em; font-size: 0.76rem; }

/* Each alcove is now the whole screen, and the portrait behind it is on the #lamp
   canvas being lit by that power's own rules. The plate of text is the only thing
   standing in the room — so it carries its own dark, or the Choir would bleach it
   off the wall entirely. */
.hall {
  min-height: 100svh;
  min-height: 100vh;
  display: grid;
  grid-template-columns: minmax(0, 34rem);
  align-content: center;
  padding: clamp(3rem, 9vh, 6rem) clamp(1.4rem, 6vw, 6rem);
  scroll-snap-align: start;
}
.hall[data-power="court"], .hall[data-power="choir"] { justify-content: end; }

.hall-plate {
  padding: clamp(1.6rem, 3vw, 2.4rem) clamp(1.6rem, 3vw, 2.6rem);
  border: 1px solid var(--hairline);
  border-left: 2px solid color-mix(in oklab, var(--hall-tint) 55%, transparent);
  background: linear-gradient(180deg, oklch(0.07 0.008 260 / 0.82), oklch(0.07 0.008 260 / 0.9));
  backdrop-filter: blur(3px);
  box-shadow: 0 30px 90px oklch(0.02 0 0 / 0.6);
}
.hall-name h3 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(2rem, 5.2vw, 3.4rem); letter-spacing: 0.05em;
  color: var(--bone); line-height: 1.15; margin: 0.2em 0 0.4em;
}
.hall-name .placard-label { color: color-mix(in oklab, var(--hall-tint) 60%, var(--faded)); }
.hall-motto { font-style: italic; font-family: var(--fell-text); color: var(--bone-dim); font-size: clamp(1rem, 2vw, 1.2rem); max-width: 40ch; }

/* the portraits are not thumbnails any more — they are the walls */

.hall-name { margin-bottom: 1.4rem; }
.hall-body p { margin-bottom: 1em; color: var(--bone-dim); font-size: 0.98rem; max-width: 58ch; }
.hall-body em { color: var(--bone); }
.hall-classes {
  margin-top: 1.4rem; padding-top: 1rem; border-top: 1px solid var(--hairline);
  display: flex; gap: 2rem; flex-wrap: wrap;
}
.hall-class { min-width: 110px; }
.hall-class b {
  display: block; font-family: var(--fell); font-weight: 400; font-size: 1.05rem;
  letter-spacing: 0.05em; color: color-mix(in oklab, var(--hall-tint) 55%, var(--bone));
}
.hall-class span { font-size: 0.82rem; color: var(--faded); font-style: italic; font-family: var(--fell-text); }

.veiled-row {
  min-height: 70vh;
  padding: clamp(3rem, 9vh, 6rem) clamp(1.4rem, 6vw, 6rem);
  border-top: 1px solid var(--hairline);
  scroll-snap-align: start;
}
.veiled-row h3 { font-family: var(--fell); font-weight: 400; font-size: clamp(1.5rem, 3.4vw, 2.2rem); letter-spacing: 0.06em; margin: 0.3em 0 1.4em; }
.veiled-figures { display: flex; flex-wrap: wrap; gap: clamp(1.2rem, 3vw, 2.6rem); }
.veiled {
  flex: 1 1 180px; max-width: 250px;
  padding: 2.4rem 1.3rem 1.2rem;
  border: 1px solid var(--hairline);
  background: linear-gradient(180deg, oklch(0.14 0.01 70 / 0.6), transparent);
  text-align: center;
}
.veiled::before {
  content: ''; display: block; margin: 0 auto 1.4rem;
  width: 54px; height: 84px;
  background: linear-gradient(180deg, oklch(0.28 0.015 75), oklch(0.16 0.012 70));
  clip-path: polygon(50% 0%, 78% 18%, 88% 100%, 12% 100%, 22% 18%);
  opacity: 0.85;
}
.veiled b { display: block; font-family: var(--fell); font-weight: 400; letter-spacing: 0.06em; color: var(--bone-dim); font-size: 1rem; }
.veiled span { font-size: 0.8rem; color: var(--faded); font-style: italic; font-family: var(--fell-text); }

/* ============================================================
   BESTIARY
   ============================================================ */

.bestiary-frame {
  position: absolute; inset: 0;
  display: grid; grid-template-columns: minmax(220px, 320px) 1fr;
  padding-top: clamp(3.6rem, 9vh, 5.4rem);
}

.bestiary-index {
  overflow-y: auto;
  padding: 1.5rem clamp(1rem, 2.5vw, 2rem) 2rem clamp(1.4rem, 4vw, 3rem);
  border-right: 1px solid var(--hairline);
  display: flex; flex-direction: column; gap: 0.15rem;
}
.bestiary-index .placard-label { margin-bottom: 0.9rem; }
.beast-link {
  text-align: left; padding: 0.5em 0.2em;
  font-family: var(--fell); font-size: 1.05rem; letter-spacing: 0.05em;
  color: var(--bone-dim);
  border-bottom: 1px solid transparent;
  transition: color 300ms;
}
.beast-link:hover { color: var(--candle); }
.beast-link.active { color: var(--candle); }
.beast-link.torn { color: var(--faded); font-style: italic; font-family: var(--fell-text); font-size: 0.9rem; cursor: default; }

.bestiary-page {
  overflow-y: auto;
  padding: 1.5rem clamp(1.6rem, 5vw, 5rem) 4rem;
  max-width: 70ch;
}
.bestiary-page h2 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(1.7rem, 4vw, 2.6rem); letter-spacing: 0.05em; margin: 0.3em 0 0.2em;
}
.beast-taxon { font-style: italic; font-family: var(--fell-text); color: var(--faded); margin-bottom: 1.6rem; }
.beast-plate {
  margin: 0 0 1.8rem;
  max-width: 540px;
  border: 1px solid var(--hairline);
  background: oklch(0.10 0.01 70 / 0.6);
  padding: 8px;
}
.beast-plate img { width: 100%; }
.bestiary-page p { color: var(--bone-dim); margin-bottom: 1em; }
.bestiary-page em { color: var(--bone); }
.beast-field { margin-top: 1.4rem; padding-top: 0.9rem; border-top: 1px solid var(--hairline); }
.beast-field .placard-label { margin-bottom: 0.3rem; }
.beast-field p { margin-bottom: 0; }

/* ============================================================
   PORTAL CHAMBER
   ============================================================ */

.portal-art {
  position: absolute; inset: 0; overflow: hidden;
  transform: scale(1.045);
  transition: transform 400ms linear;
}
.portal-art img { width: 100%; height: 100%; object-fit: cover; filter: brightness(0.92); }

.portal-grade {
  position: absolute; inset: 0; pointer-events: none;
  background: linear-gradient(0deg, oklch(0.08 0.008 260 / 0.7) 0%, transparent 26%),
              linear-gradient(180deg, oklch(0.08 0.008 260 / 0.5) 0%, transparent 18%);
}

.portal-zones { position: absolute; inset: 0; display: grid; grid-template-columns: 1fr 1fr 1fr; }

.portal-zone {
  position: relative; display: block;
  border: 0; background: none; cursor: pointer;
}
.portal-zone::before { /* bloom */
  content: ''; position: absolute; inset: 0;
  background: radial-gradient(ellipse 46% 62% at 50% 52%, var(--bloom, transparent), transparent 72%);
  opacity: 0; transition: opacity 700ms var(--ease);
  pointer-events: none;
}
.portal-zone[data-portal="green"] { --bloom: oklch(0.55 0.12 155 / 0.22); }
.portal-zone[data-portal="red"]   { --bloom: oklch(0.5 0.16 25 / 0.22); }
.portal-zone[data-portal="black"] { --bloom: oklch(0.3 0.05 300 / 0.18); }
.portal-zone:hover::before, .portal-zone:focus-visible::before { opacity: 1; }

.portal-caption {
  position: absolute; left: 50%; bottom: clamp(2.2rem, 7vh, 4.4rem); transform: translateX(-50%) translateY(8px);
  text-align: center; white-space: nowrap;
  opacity: 0; transition: opacity 600ms var(--ease), transform 600ms var(--ease);
  pointer-events: none;
}
.portal-zone:hover .portal-caption, .portal-zone:focus-visible .portal-caption { opacity: 1; transform: translateX(-50%) translateY(0); }
.portal-caption em {
  display: block; font-style: normal;
  font-family: var(--fell); font-size: clamp(1.3rem, 3vw, 1.9rem); letter-spacing: 0.14em;
  color: var(--bone); text-shadow: 0 2px 18px oklch(0.05 0 0);
}
.portal-caption small {
  font-variant-caps: small-caps; letter-spacing: 0.16em; font-size: 0.74rem;
  color: var(--bone-dim); text-shadow: 0 1px 10px oklch(0.05 0 0);
}

.portal-zone[data-portal="black"].refused { animation: refuse 500ms ease-in-out; }
@keyframes refuse {
  0%, 100% { transform: translateX(0); }
  20% { transform: translateX(-5px); } 40% { transform: translateX(4px); }
  60% { transform: translateX(-3px); } 80% { transform: translateX(2px); }
}

/* ============================================================
   COLOPHON
   ============================================================ */

.colophon {
  max-width: 62ch;
  margin-inline: auto;
  padding: clamp(5rem, 14vh, 8rem) clamp(1.4rem, 5vw, 2rem) 5rem;
}
.colophon h2 {
  font-family: var(--fell); font-weight: 400;
  font-size: clamp(2rem, 5vw, 3rem); letter-spacing: 0.1em; margin: 0.25em 0 0.7em;
}
.colophon p { margin-bottom: 1.1em; color: var(--bone-dim); }
.colophon .hairline { margin: 2rem 0; }
.authors-note { font-style: italic; font-family: var(--fell-text); color: var(--faded); }
.fineprint { font-size: 0.82rem; color: var(--faded); }
.return {
  display: inline-block; margin-top: 1.6rem;
  font-variant-caps: small-caps; letter-spacing: 0.16em; font-size: 0.85rem;
}

/* ============================================================
   SHARPENING — type ornaments, drop caps, small ceremonies
   ============================================================ */

:focus-visible { outline: 1px solid var(--candle-deep); outline-offset: 3px; }

/* engraved flourish beneath the great room titles */
.archives-head h2::after,
.hall-intro h2::after,
.colophon h2::after {
  content: '';
  display: block;
  width: 200px; height: 12px;
  margin-top: 0.55em;
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='200' height='12' viewBox='0 0 200 12'%3E%3Cpath d='M0 6h82M118 6h82' stroke='%23776a4e' stroke-width='1'/%3E%3Crect x='96' y='2' width='8' height='8' transform='rotate(45 100 6)' fill='none' stroke='%23b99a5f'/%3E%3C/svg%3E") no-repeat;
  opacity: 0.7;
}
.hall-intro h2::after { margin-inline: auto; }

/* drop caps: the first letter of a chapter is a small ceremony */
.reader-page h3 + p::first-letter {
  font-family: var(--fell);
  font-size: 3.1em;
  float: left;
  line-height: 0.78;
  padding: 0.06em 0.1em 0 0;
}
#atlas-panel-body > p:first-of-type::first-letter,
.bestiary-page .beast-taxon ~ p:first-of-type::first-letter {
  font-family: var(--fell);
  font-size: 2.5em;
  float: left;
  line-height: 0.8;
  padding: 0.04em 0.09em 0 0;
  color: var(--bone);
}

/* map pins breathe */
@keyframes pinbreath {
  0%, 100% { box-shadow: 0 0 10px oklch(0.78 0.13 78 / 0.35); }
  50%      { box-shadow: 0 0 20px oklch(0.78 0.13 78 / 0.65); }
}
.pin::before { animation: pinbreath 4.6s ease-in-out infinite; }
.pin:nth-child(2n)::before { animation-delay: 1.1s; }
.pin:nth-child(3n)::before { animation-delay: 2.3s; }

/* the enter button breathes like a flame */
@keyframes enterbreath {
  0%, 100% { box-shadow: 0 0 26px oklch(0.78 0.13 78 / 0.10), inset 0 0 18px oklch(0.78 0.13 78 / 0.05); }
  50%      { box-shadow: 0 0 46px oklch(0.78 0.13 78 / 0.22), inset 0 0 26px oklch(0.78 0.13 78 / 0.09); }
}
.enter-btn.shown { animation: enterbreath 4.4s ease-in-out infinite; }

/* the reader is a real block of pages */
.reader-book {
  box-shadow:
    0 2px 0 oklch(0.82 0.02 82),
    0 4px 0 oklch(0.76 0.025 80),
    0 6px 0 oklch(0.70 0.025 78),
    0 8px 0 oklch(0.62 0.03 75),
    0 34px 90px oklch(0.03 0 0 / 0.85),
    inset 0 0 90px oklch(0.6 0.03 80 / 0.25);
}

/* a light passes over the veiled statues, rarely */
@keyframes veilsheen {
  0%, 86% { background-position: -180% 0; }
  100%    { background-position: 280% 0; }
}
.veiled::before {
  background:
    linear-gradient(115deg, transparent 42%, oklch(0.75 0.03 85 / 0.20) 50%, transparent 58%) 0 0 / 260% 100%,
    linear-gradient(180deg, oklch(0.28 0.015 75), oklch(0.16 0.012 70));
  animation: veilsheen 11s ease-in-out infinite;
}
.veiled:nth-child(2)::before { animation-delay: 2.8s; }
.veiled:nth-child(3)::before { animation-delay: 5.4s; }
.veiled:nth-child(4)::before { animation-delay: 8.1s; }

/* the voice controls */
.listen-btn {
  font-variant-caps: small-caps; letter-spacing: 0.16em;
  font-size: 0.78rem; color: var(--candle);
  padding: 0.35em 0;
  border-bottom: 1px solid transparent;
  transition: color 300ms, border-color 300ms;
}
.listen-btn:hover { color: var(--bone); border-color: var(--candle-deep); }
.listen-btn::before { content: '◆ '; font-size: 0.6em; vertical-align: 0.22em; color: var(--candle-deep); }
.beast-listen { display: inline-block; margin: -0.6rem 0 1.2rem; }

/* thin engraved scrollbars where scrolling is part of the room */
.timeline::-webkit-scrollbar, .room-scroll::-webkit-scrollbar,
.bestiary-index::-webkit-scrollbar, .bestiary-page::-webkit-scrollbar,
#room-library::-webkit-scrollbar, .placard-panel::-webkit-scrollbar {
  width: 6px; height: 6px;
}
.timeline::-webkit-scrollbar-thumb, .room-scroll::-webkit-scrollbar-thumb,
.bestiary-index::-webkit-scrollbar-thumb, .bestiary-page::-webkit-scrollbar-thumb,
#room-library::-webkit-scrollbar-thumb, .placard-panel::-webkit-scrollbar-thumb {
  background: var(--hairline);
}
.timeline::-webkit-scrollbar-track, .room-scroll::-webkit-scrollbar-track,
.bestiary-index::-webkit-scrollbar-track, .bestiary-page::-webkit-scrollbar-track,
#room-library::-webkit-scrollbar-track, .placard-panel::-webkit-scrollbar-track {
  background: transparent;
}

/* ============================================================
   THE MARKS — glyphs that answer only the lamp
   ============================================================ */

.glyph {
  color: oklch(0.80 0.08 80);
  opacity: 0;
  width: 44px; height: 44px;
  display: grid; place-items: center;
  cursor: default;
  filter: drop-shadow(0 0 6px oklch(0.78 0.13 78 / 0.5));
  transition: transform 500ms var(--ease);
}
.glyph[data-lit="1"] { cursor: pointer; }
.glyph[data-lit="1"]:hover { transform: scale(1.12); }
.glyph.claimed {
  animation: glyphclaim 2400ms var(--ease) forwards;
  pointer-events: none;
}
@keyframes glyphclaim {
  0%   { opacity: 1; transform: scale(1); filter: drop-shadow(0 0 10px oklch(0.78 0.13 78 / 0.9)); }
  30%  { opacity: 1; transform: scale(1.5); filter: drop-shadow(0 0 26px oklch(0.78 0.13 78 / 1)); }
  100% { opacity: 0; transform: scale(0.6); filter: drop-shadow(0 0 0 transparent); }
}

.sealed-page { margin-top: 1.8rem; padding: 1rem 1.1rem; border: 1px solid var(--hairline); }
.sealed-page.unsealed { border-color: oklch(0.45 0.07 75 / 0.8); background: oklch(0.15 0.014 65 / 0.5); }
.sealed-page .page-text { color: var(--bone-dim); line-height: 1.65; margin-bottom: 0.7em !important; }
.sealed-page .page-text b { color: var(--candle); font-weight: 500; }
.dim-italic { color: var(--faded); font-style: italic; font-family: var(--fell-text); }

/* ============================================================
   BLOOD MOON — the site follows the actual sky
   ============================================================ */

/* A blood moon is no longer a red sheet thrown over the screen. It is the moon,
   and the moon is the fill light — so on a blood moon the SHADOWS go red, in the
   shader, which is a considerably worse thing to be standing in. The rooms with
   no lit wall keep a hint of it. */
body.bloodmoon .hub-grade::after, body.bloodmoon .portal-grade::after {
  content: ''; position: absolute; inset: 0; pointer-events: none;
  background: radial-gradient(ellipse 90% 70% at 50% 0%, oklch(0.35 0.13 25 / 0.16), transparent 62%),
              radial-gradient(ellipse 120% 60% at 50% 110%, oklch(0.28 0.12 25 / 0.13), transparent 70%);
  mix-blend-mode: screen;
}
body.bloodmoon .intro-sub { color: oklch(0.55 0.1 25); }
body.bloodmoon .portal-zone[data-portal="red"]::before { opacity: 0.45; }
body.bloodmoon .portal-zone[data-portal="red"]:hover::before { opacity: 1; }
body.bloodmoon #wordmark:hover { color: oklch(0.6 0.13 25); }

/* ============================================================
   THE LEDGER, THE GHOSTS, THE CLOCK
   ============================================================ */

#ledger-btn {
  position: fixed; z-index: 80;
  left: clamp(1.2rem, 4vw, 3rem); bottom: clamp(1rem, 3vh, 1.6rem);
  font-variant-caps: small-caps; letter-spacing: 0.16em;
  font-size: 0.78rem; color: var(--faded);
  transition: color 400ms;
}
#ledger-btn:hover { color: var(--candle); }
#ledger-btn::before { content: '◆ '; font-size: 0.6em; vertical-align: 0.22em; color: var(--candle-deep); }

.ledger-side {
  position: fixed; z-index: 85;
  left: 0; right: auto; top: 0; bottom: 0;
  width: min(410px, 92vw);
  background: linear-gradient(270deg, transparent, oklch(0.10 0.01 70 / 0.97) 12%);
  padding: clamp(4rem, 10vh, 6rem) clamp(2.4rem, 5vw, 4rem) 3rem clamp(1.6rem, 3vw, 2.6rem);
  transform: translateX(-24px);
}
.ledger-side.open { transform: none; }

.ledger-greeting { font-style: italic; font-family: var(--fell-text); color: var(--bone-dim); margin-bottom: 1.6rem; }
.ledger-section { margin-bottom: 1.3rem; }
.ledger-section .placard-label { margin-bottom: 0.35rem; }
.ledger-item { font-size: 0.92rem; color: var(--bone-dim); margin: 0.15em 0 !important; }
.ledger-item.dim { color: var(--faded); letter-spacing: 0.3em; }
.ledger-count { color: var(--bone); }
.ledger-whisper { font-style: italic; font-family: var(--fell-text); color: var(--faded); }
.ledger-fine { font-size: 0.74rem; color: var(--faded); margin-top: 1.6rem; font-variant-caps: small-caps; letter-spacing: 0.12em; }

.librarian-whisper {
  position: fixed; z-index: 70;
  left: 50%; bottom: clamp(3rem, 8vh, 5rem); transform: translateX(-50%) translateY(8px);
  font-style: italic; font-family: var(--fell-text);
  font-size: 1rem; color: var(--bone-dim);
  text-shadow: 0 2px 14px oklch(0.05 0 0);
  opacity: 0; pointer-events: none;
  transition: opacity 2000ms ease-in, transform 2000ms var(--ease);
}
.librarian-whisper.shown { opacity: 0.9; transform: translateX(-50%) translateY(0); }

/* nightfall: between the tenth hour and the sixth, the library dims
   (the lit rooms dim inside the shader — see uNight in js/lamp.js) */
body.nightfall .hub-art img, body.nightfall .hub-art .bg-video { filter: brightness(0.72) saturate(0.9); }
body.nightfall .intro-tome { filter: brightness(0.6) saturate(0.85); }
body.nightfall .portal-art img, body.nightfall .portal-art .bg-video { filter: brightness(0.78); }
body.nightfall #air { opacity: 0.72; }

.bleeding-counter { margin-top: 1.6rem; max-width: 60ch; }
.bleeding-counter .placard-label { display: block; margin-bottom: 0.3rem; }
.bleeding-line { display: block; color: var(--bone-dim); font-size: 0.95rem; }
.bleeding-num {
  font-weight: 500; color: var(--candle);
  font-variant-numeric: tabular-nums;
  letter-spacing: 0.03em;
}
.bleeding-note { display: block; margin-top: 0.3rem; font-style: italic; font-family: var(--fell-text); color: var(--faded); font-size: 0.9rem; }

/* ============================================================
   RESPONSIVE
   ============================================================ */

@media (max-width: 760px) {
  /* On a phone the plate is taller than the screen, so if it starts at the top it
     covers the alcove entirely — and the alcove is the whole point. Give the wall the
     top third and let the text begin under it. */
  .hall {
    grid-template-columns: 1fr;
    align-content: start;
    padding-top: 34svh;
    padding-bottom: 10svh;
    scroll-snap-align: none;
  }
  .hall-plate { backdrop-filter: blur(6px); }

  /* a thumb is not a mouse pointer: these all cleared the 24px minimum and none of
     them cleared 44, which is the number that decides whether a door opens on the
     first try or the third */
  #wordmark, #mute {
    display: inline-flex; align-items: center;
    min-height: 44px;
  }
  .door { padding-block: 0.4rem; }
  .atlas-hint { padding: 0.5rem 0; }
  .colophon-link, #ledger-btn {
    display: inline-flex; align-items: center;
    min-height: 44px;
  }
  .bestiary-frame { grid-template-columns: 1fr; grid-template-rows: auto 1fr; }
  .bestiary-index { flex-direction: row; flex-wrap: wrap; gap: 0.2rem 1.1rem; border-right: 0; border-bottom: 1px solid var(--hairline); padding-bottom: 0.9rem; }
  .bestiary-index .placard-label { flex-basis: 100%; margin-bottom: 0.2rem; }
  .reader-book { grid-template-columns: 1fr; }
  #page-right { display: none; }
  .reader-book::before { display: none; }
  .portal-zones { grid-template-columns: 1fr; grid-template-rows: 1fr 1fr 1fr; }
  .portal-caption { opacity: 1; transform: translateX(-50%); }
  .intro-lines { transform: translateY(-20vh); }

  /* The placard was a 430px column pinned to the right — which on a 390px phone left
     the continent itself a thirty-pixel sliver, and put the close button underneath
     the chrome. On a small screen the placard rises from the bottom instead, and you
     go on looking at the map while you read about it. */
  .placard-panel {
    top: auto; right: 0; left: 0; bottom: 0;
    width: 100%;
    max-height: 58vh;
    max-height: 58svh;
    border-top: 1px solid var(--hairline);
    background: linear-gradient(0deg, oklch(0.09 0.01 70 / 0.985), oklch(0.09 0.01 70 / 0.94));
    padding: 1.5rem clamp(1.2rem, 5vw, 2rem) calc(1.4rem + env(safe-area-inset-bottom));
    transform: translateY(28px);
    overscroll-behavior: contain;
  }
  .placard-panel.open { transform: none; }
  .panel-close {
    top: 0.9rem; right: 1rem;
    width: 44px; height: 44px;      /* a thumb is not a mouse pointer */
    display: grid; place-items: center;
  }
  /* The ledger sat directly on top of the last line of every scrolling room, in the
     same colour as it. It keeps its corner — the colophon owns the other one — but it
     now carries its own dark behind it, and the rooms end above it instead of under it. */
  #ledger-btn {
    bottom: calc(0.8rem + env(safe-area-inset-bottom));
    padding: 0.5rem 0.8rem 0.5rem 0.6rem;
    background: linear-gradient(0deg, oklch(0.08 0.008 260 / 0.94), oklch(0.08 0.008 260 / 0.72));
  }
  /* and when a placard or a book has risen over the room, the ledger gets out of the
     way entirely — it was printing itself across the middle of the page */
  body:has(.placard-panel.open) #ledger-btn,
  body:has(#reader:not([hidden])) #ledger-btn {
    opacity: 0; pointer-events: none;
  }
  #room-library, #room-bestiary, .bestiary-page, #room-halls, #room-colophon {
    padding-bottom: calc(4.5rem + env(safe-area-inset-bottom));
  }
  .ledger-side { width: 100%; }
}

/* ============================================================
   REDUCED MOTION
   ============================================================ */

@media (prefers-reduced-motion: reduce) {
  * { animation-duration: 0.01ms !important; transition-duration: 0.01ms !important; }
  .intro-fog { animation: none; }
  #grain { display: none; }
  /* the lamp stays — it is the light in the room, not an animation — but nothing
     shudders, nothing drifts, and the flame holds perfectly still */
  .room, #air, #lamp { transform: none !important; }
}
