/* shared/room.css — the shared room-page layout (One Light, Four Rooms).
   Each page sets its temperature once via `--room-temp` on <body>; every
   glow/reveal below reads it. Backgrounds only --ground / --ground-raised,
   text only --ink / --ink-dim, per the framework's hard rules. */

body { --room-temp: var(--ink-dim); }

.room-head {
  padding: 152px 0 24px;
}
.room-head .type-meta { color: var(--ink-dim); margin-bottom: 16px; }
.room-statement {
  padding: 8px 0 24px;
  max-width: 760px;
}
.room-statement p { margin: 0 0 20px; color: var(--ink); }
.room-statement .footnote { color: var(--ink-dim); font-size: 14px; }

/* ---- Seær force-decode toggle ----
   Lets a reader hold the decaying statement legible instead of coaxing it
   with the cursor. Injected by js/room-seaer.js only when the shader is
   running; see shared/seaer-decay.js. */
.decode-toggle {
  display: inline-block; margin: 0 0 24px;
  color: var(--ink-dim); background: none; font: inherit;
  font-size: 13px; font-weight: 400;
  letter-spacing: 0.14em; text-transform: uppercase;
  border: 1px solid var(--line); padding: 10px 18px; cursor: pointer;
  transition: color .3s ease, border-color .3s ease;
}
.decode-toggle:hover { color: var(--ink); border-color: var(--temp-seaer); }
.decode-toggle[aria-pressed="true"] {
  color: var(--temp-seaer);
  border-color: color-mix(in srgb, var(--temp-seaer) 45%, var(--line));
}
.room-works-line {
  color: var(--ink-dim);
  border-top: 1px solid var(--line);
  border-bottom: 1px solid var(--line);
  padding: 16px 0;
  margin: 24px 0 0;
  font-size: 14px;
  line-height: 1.6;
}

.works { padding: 40px 0 120px; display: flex; flex-direction: column; gap: 96px; }

.work { scroll-margin-top: 96px; }
.work-title-row { display: flex; align-items: baseline; gap: 24px; flex-wrap: wrap; margin-bottom: 8px; }
.work-title-row .type-meta { color: var(--ink-dim); }
.work-note { color: var(--ink-dim); font-size: 14px; margin: 4px 0 0; }

.panel-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
  gap: 24px;
  margin-top: 24px;
}
.panel-grid .panel--wide { grid-column: 1 / -1; }

/* ---- The attended frame: image ↔ moving image, one light ---- */
.frame {
  position: relative;
  background: var(--ground-raised);
  overflow: hidden;
}
.frame img { width: 100%; height: auto; display: block; }
.frame video {
  position: absolute; inset: 0;
  width: 100%; height: 100%;
  object-fit: cover;
  opacity: 0;
  transition: opacity 0.9s ease;
}
.frame.is-attended video { opacity: 1; }

/* cursor-light sheen: a soft temp-tinted radial that tracks the pointer
   (layer 1 — consequence within one frame) */
.frame .sheen {
  position: absolute; inset: 0;
  pointer-events: none;
  opacity: 0;
  transition: opacity 0.4s ease;
  background: radial-gradient(circle 260px at var(--lx, 50%) var(--ly, 50%),
              color-mix(in srgb, var(--room-temp) 22%, transparent), transparent 70%);
  mix-blend-mode: screen;
}
.frame.is-lit .sheen { opacity: 1; }

/* fog treatment (Empathy for Place): the image is ALWAYS visible — fog is a
   dimming veil that attention burns off continuously, never a gate. */
.frame--fog img { filter: saturate(0.55) brightness(0.72); transition: filter 1.1s ease; }
.frame--fog.is-lit img { filter: saturate(0.8) brightness(0.86); }
.frame--fog.is-attended img { filter: saturate(1) brightness(1); }
.frame--fog::after {
  content: "";
  position: absolute; inset: 0;
  pointer-events: none;
  background: color-mix(in srgb, var(--room-temp) 12%, var(--ground) 30%);
  opacity: 0.5;
  transition: opacity 1.1s ease;
  mix-blend-mode: soft-light;
}
.frame--fog.is-attended::after { opacity: 0; }

/* scoped vignette (The Ethical Viewer only): borrowed field of view,
   widening under quiet attention — the piece's own device, not the page's */
.frame--viewer::before {
  content: "";
  position: absolute; inset: 0;
  pointer-events: none; z-index: 2;
  box-shadow: inset 0 0 140px 60px var(--ground);
  opacity: 0.9;
  transition: opacity 1.4s ease;
}
.frame--viewer.is-attended::before { opacity: 0; }

.caption {
  color: var(--ink-dim);
  font-size: 14px;
  line-height: 1.55;
  padding: 12px 0 0;
  max-width: 640px;
}

/* Resolution settle state (exit-behaviors.js) */
.work.is-settled .frame { box-shadow: 0 0 0 1px color-mix(in srgb, var(--room-temp) 35%, transparent); }

/* research/publications sidebar — instant, ungated, visually native */
.room-layout { display: grid; grid-template-columns: 1fr; gap: 48px; }
@media (min-width: 980px) {
  .room-layout--with-aside { grid-template-columns: 1fr 300px; align-items: start; }
  .room-aside { position: sticky; top: 104px; }
}
.room-aside {
  background: var(--ground-raised);
  border: 1px solid var(--line);
  padding: 24px;
}
.room-aside .type-meta { color: var(--ink-dim); margin-bottom: 16px; }
.room-aside p { color: var(--ink); font-size: 14px; line-height: 1.6; margin: 0 0 14px; }
.room-aside p:last-child { margin-bottom: 0; }

.doc-text-only {
  border: 1px dashed var(--line);
  padding: 24px;
}

/* video sound affordance — wordless: a speaker glyph appears on attended
   videos; clicking toggles sound (glyph, not instruction) */
.frame .sound {
  position: absolute; right: 12px; bottom: 12px; z-index: 3;
  width: 36px; height: 36px;
  border-radius: 50%;
  border: 1px solid var(--line);
  background: color-mix(in srgb, var(--ground) 72%, transparent);
  color: var(--ink);
  display: grid; place-items: center;
  cursor: pointer;
  opacity: 0;
  transition: opacity 0.4s ease;
  font-size: 13px;
}
.frame.is-attended .sound { opacity: 1; }
.frame .sound.is-on { border-color: var(--room-temp); color: var(--room-temp); }

/* ---- Export C additions ---- */
.work-byline { color: var(--ink-dim); font-size: 13px; letter-spacing: .04em; margin: 6px 0 0; }
.work-research-kicker { color: var(--room-temp); margin-bottom: 4px; width: 100%; }
.room-subtitle { color: var(--ink-dim); margin-top: 8px; }
.doc-text-only .work-byline { margin-top: 8px; }

/* Current-exhibition banner (Mutable Sculpture / Liminal Luminance) */
.room-banner { margin: 32px 0 8px; }
.banner-surface { position: relative; overflow: hidden; background: var(--ground-raised); }
.banner-surface canvas { display: block; width: 100%; }
.banner-overlay {
  position: absolute; left: 0; right: 0; bottom: 0; z-index: 3;
  padding: clamp(20px, 4vw, 44px);
  background: linear-gradient(0deg, color-mix(in srgb, var(--ground) 88%, transparent), transparent);
  pointer-events: none;
}
.banner-overlay .type-meta { color: var(--room-temp); }
.banner-overlay h2 { font-size: clamp(30px, 4.6vw, 52px); font-weight: 200; margin: 8px 0 6px; }
.banner-overlay p { color: var(--ink); max-width: 62ch; margin: 0; }
.banner-blurb { max-width: 760px; padding: 24px 0 8px; }
.banner-blurb p { margin: 0 0 18px; }
.banner-blurb .objects { color: var(--ink-dim); font-size: 13.5px; border-top: 1px solid var(--line); padding-top: 14px; }

/* ---- Exhibition checklist (title · year · medium · dimensions) ----
   Registrar-grade detail, per v8 §3.8. Data is CURRENT_EXHIBITION.objects
   in shared/content/api.js; rendered by js/room-mutable.js. */
.banner-blurb .objects-heading {
  color: var(--ink-dim);
  border-top: 1px solid var(--line);
  padding-top: 14px; margin: 0 0 4px;
}
.objects-list { list-style: none; margin: 0; padding: 0; }
.objects-list li {
  display: flex; flex-wrap: wrap; gap: 4px 14px; align-items: baseline;
  padding: 10px 0; border-bottom: 1px solid var(--line);
}
.objects-list li:last-child { border-bottom: none; }
.objects-list b { font-weight: 400; font-size: 15px; color: var(--ink); }
.objects-list .obj-meta { color: var(--ink-dim); font-size: 13px; }

/* ---- Export E: obvious, deterministic still->video transition ---- */
/* The video layer is visible whenever it is actually PLAYING (autoplay on
   visibility, or attention) — the crossfade no longer depends on hover
   alone. Slower fade (1.2s) so the material change reads clearly. */
.frame video { transition: opacity 1.2s ease; }
.frame.is-projecting video, .frame.video-live video { opacity: 1; }
/* one-time temperature pulse the instant the projection starts */
.frame.video-pulse {
  box-shadow: 0 0 0 2px color-mix(in srgb, var(--room-temp) 65%, transparent),
              0 0 42px color-mix(in srgb, var(--room-temp) 22%, transparent);
  transition: box-shadow .4s ease;
}
/* while the projection runs, a quiet playing marker sits top-right —
   wordless, in the room's temperature */
.frame.video-live::after {
  content: ""; position: absolute; top: 12px; right: 12px; z-index: 3;
  width: 7px; height: 7px; border-radius: 50%;
  background: var(--room-temp);
  animation: tx-live 2s ease-in-out infinite;
  pointer-events: none;
}
@keyframes tx-live { 0%,100% { opacity: .35; } 50% { opacity: .95; } }
@media (prefers-reduced-motion: reduce) {
  .frame.video-live::after { animation: none; opacity: .6; }
}
/* sound control is available whenever the projection is running */
.frame.video-live .sound { opacity: 1; }

/* ---- Small screens: tighter spacing, full-width panels ---- */
@media (max-width: 640px) {
  .room-head { padding: 96px 0 16px; }
  .room-statement { padding: 8px 0 16px; }
  .room-statement p { margin: 0 0 14px; }
  .decode-toggle { margin-bottom: 18px; padding: 9px 14px; font-size: 12px; }
  .room-works-line { padding: 12px 0; margin: 16px 0 0; font-size: 13px; }
  .works { padding: 24px 0 80px; gap: 56px; }
  .work-title-row { gap: 12px; margin-bottom: 4px; }
  .work-note { font-size: 13px; }
  .panel-grid { grid-template-columns: 1fr; gap: 16px; margin-top: 16px; }
  .panel-grid .panel--wide { grid-column: 1 / -1; }
  .caption { font-size: 13px; padding: 8px 0 0; }
  /* Banner: fill width, shorter aspect on mobile */
  .video-banner { aspect-ratio: 16 / 9; }
  .banner-overlay { padding: clamp(16px, 4vw, 24px); }
  .banner-overlay h2 { font-size: clamp(24px, 6vw, 32px); margin: 6px 0 4px; }
  .banner-overlay p { font-size: 14px; }
  .banner-blurb { padding: 16px 0 4px; }
  .banner-blurb p { margin: 0 0 14px; font-size: 15px; }
  .banner-blurb .objects { font-size: 12.5px; padding-top: 10px; }
  /* checklist stacks title over metadata on narrow screens */
  .banner-blurb .objects-heading { padding-top: 10px; }
  .objects-list li { flex-direction: column; gap: 2px; padding: 8px 0; }
  .objects-list b { font-size: 14px; }
  .objects-list .obj-meta { font-size: 12.5px; }
  /* Room layout: sidebar stacks below on mobile */
  .room-layout { gap: 32px; }
  .room-layout--with-aside { grid-template-columns: 1fr; }
  .room-aside { position: static !important; padding: 16px; }
  /* Sound button: larger touch target */
  .frame .sound { width: 40px; height: 40px; right: 8px; bottom: 8px; font-size: 14px; }
}

/* ---- Tablet: 2-col panel grid, moderate spacing ---- */
@media (min-width: 641px) and (max-width: 980px) {
  .panel-grid { grid-template-columns: repeat(auto-fit, minmax(260px, 1fr)); gap: 20px; }
  .works { gap: 72px; }
  .room-head { padding: 120px 0 20px; }
}

/* ---- Export G: reliable video banner (Mutable Sculpture current show) ---- */
.video-banner { position: relative; aspect-ratio: 16 / 9; overflow: hidden; background: var(--ground-raised); }
.video-banner video { width: 100%; height: 100%; object-fit: cover; display: block; }
/* older browsers without aspect-ratio: keep a sensible height */
@supports not (aspect-ratio: 1 / 1) { .video-banner { height: 56vw; max-height: 640px; } }
