/* =========================================================
   PromptHaus — Selected Work (client portfolio)
   Distinct system from the main site: per-chapter color mood,
   editorial full-bleed layout, side chapter-nav instead of a top nav.
   Each chapter is a deck: card 1 is the project, swipe right for
   the services delivered.
   ========================================================= */

:root {
  --bg: #08090a;
  --surface: #121316;
  --border: rgba(255,255,255,0.09);
  --border-strong: rgba(255,255,255,0.18);
  --text: #f4f4f2;
  --dim: #a9adb4;
  --faint: #6f747c;
  --accent-default: #e8e8e6;

  --font-head: 'Space Grotesk', 'Inter', system-ui, sans-serif;
  --font-body: 'Inter', system-ui, -apple-system, sans-serif;
  --font-mono: 'JetBrains Mono', 'SF Mono', monospace;
  --ease: cubic-bezier(.22,.61,.36,1);
}

* { box-sizing: border-box; }
html { scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  .deck-track { scroll-behavior: auto !important; }
  * { animation-duration: .01ms !important; animation-iteration-count: 1 !important; transition-duration: .01ms !important; }
}

body {
  margin: 0; background: var(--bg); color: var(--text);
  font-family: var(--font-body); line-height: 1.55;
  -webkit-font-smoothing: antialiased; overflow-x: hidden;
}
img { max-width: 100%; display: block; }
a { color: inherit; text-decoration: none; }
h1, h2, h3 { font-family: var(--font-head); margin: 0; font-weight: 600; letter-spacing: -0.02em; }
p { margin: 0; }
button { font: inherit; color: inherit; background: none; border: none; cursor: pointer; }
:focus-visible { outline: 2px solid var(--accent, var(--accent-default)); outline-offset: 3px; border-radius: 4px; }

.grain {
  position: fixed; inset: 0; z-index: 999; pointer-events: none;
  opacity: 0.035; mix-blend-mode: overlay;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='120' height='120'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
}

.reveal { opacity: 0; transform: translateY(32px); transition: opacity .9s var(--ease), transform .9s var(--ease); }
.reveal.in-view { opacity: 1; transform: translateY(0); }
/* Chapters fade without moving: a transform on the ancestor of a scroll-snap
   container makes the browser re-snap to the first card when it's removed. */
.reveal-fade { opacity: 0; transition: opacity .9s var(--ease); }
.reveal-fade.in-view { opacity: 1; }

/* =========================================================
   TOP BAR
   ========================================================= */
.topbar {
  position: fixed; top: 0; left: 0; right: 0; z-index: 100;
  padding: 20px 32px;
}
.topbar-inner { display: flex; align-items: center; justify-content: space-between; }
.brand { display: flex; align-items: center; gap: 9px; color: var(--text); }
.brand-icon { width: 26px; height: 26px; object-fit: contain; opacity: .92; }
.brand-name { font-family: var(--font-head); font-size: 0.98rem; letter-spacing: -0.01em; font-weight: 400; }
.brand-name strong { font-weight: 700; }
.topbar-actions { display: flex; align-items: center; gap: 18px; }
.btn-home {
  display: inline-flex; align-items: center; gap: 6px;
  font-size: 0.84rem; font-weight: 500; color: var(--dim);
  transition: color .25s;
}
.btn-home svg { width: 14px; height: 14px; }
.btn-home:hover { color: var(--text); }
.btn-talk {
  font-size: 0.84rem; font-weight: 600; padding: 9px 18px; border-radius: 999px;
  border: 1px solid var(--border-strong); backdrop-filter: blur(8px);
  transition: border-color .25s, background .25s;
}
.btn-talk:hover { border-color: rgba(255,255,255,0.5); background: rgba(255,255,255,0.06); }

/* =========================================================
   CHAPTER SIDE NAV
   ========================================================= */
.chapter-nav {
  position: fixed; right: 30px; top: 50%; transform: translateY(-50%); z-index: 90;
  display: flex; flex-direction: column; gap: 8px; align-items: center;
}
/* the rail the dots sit on */
.chapter-nav::before {
  content: ''; position: absolute; top: 6px; bottom: 6px; left: 50%;
  width: 1px; margin-left: -0.5px; pointer-events: none;
  background: linear-gradient(to bottom, transparent, var(--border-strong) 18%, var(--border-strong) 82%, transparent);
}
/* fixed-size hit target keeps every dot on the same vertical line */
.dot-link { position: relative; display: grid; place-items: center; width: 20px; height: 20px; }
.dot {
  width: 7px; height: 7px; border-radius: 50%; background: var(--border-strong);
  box-shadow: 0 0 0 3px var(--bg);
  transition: background .3s var(--ease), transform .3s var(--ease), box-shadow .3s var(--ease);
}
/* labels are absolute so their differing widths never shift the dots */
.dot-label {
  position: absolute; right: calc(100% + 4px); top: 50%;
  font-family: var(--font-mono); font-size: 0.7rem; color: var(--faint);
  opacity: 0; transform: translateY(-50%) translateX(6px);
  transition: opacity .25s var(--ease), transform .25s var(--ease), color .3s;
  white-space: nowrap; pointer-events: none;
}
.dot-link:hover .dot { background: var(--dim); }
.dot-link:hover .dot-label { opacity: 1; transform: translateY(-50%) translateX(0); }
.dot-link.active .dot {
  background: var(--accent-default); transform: scale(1.45);
  box-shadow: 0 0 0 3px var(--bg), 0 0 10px var(--accent-default);
}
.dot-link.active .dot-label { opacity: 1; transform: translateY(-50%) translateX(0); color: var(--text); }

/* =========================================================
   HERO
   ========================================================= */
.hero {
  position: relative; min-height: 100vh;
  display: flex; flex-direction: column; justify-content: center;
  padding: 160px 0 0;
  overflow: hidden;
}
.hero-bg { position: absolute; inset: 0; z-index: 0; }
.blob { position: absolute; border-radius: 50%; filter: blur(110px); opacity: 0.28; }
.blob-a { width: 620px; height: 620px; top: -220px; right: -160px; background: radial-gradient(circle, #6366f1, transparent 70%); }
.blob-b { width: 520px; height: 520px; bottom: -200px; left: -160px; background: radial-gradient(circle, #ec4899, transparent 70%); opacity: 0.2; }

.hero-inner { position: relative; z-index: 2; max-width: 900px; margin: 0 auto; padding: 0 32px; text-align: center; }
.eyebrow {
  display: inline-flex; align-items: center; gap: 8px;
  font-family: var(--font-mono); font-size: 0.78rem; letter-spacing: 0.16em;
  color: var(--dim); text-transform: uppercase; margin: 0 0 26px;
}
.dot-mark { width: 6px; height: 6px; border-radius: 50%; background: currentColor; }
.eyebrow.center { justify-content: center; }

.hero-title {
  font-size: clamp(2.4rem, 6.4vw, 4.6rem); line-height: 1.06; margin-bottom: 30px;
}
.text-outline { color: transparent; -webkit-text-stroke: 1.5px var(--text); }
.text-accent { background: linear-gradient(120deg, #ec4899, #6366f1); -webkit-background-clip: text; background-clip: text; color: transparent; }

.hero-sub { font-size: 1.06rem; color: var(--dim); max-width: 620px; margin: 0 auto 44px; }

.hero-scroll { display: inline-flex; flex-direction: column; align-items: center; gap: 10px; }
.hero-scroll span:first-child { font-family: var(--font-mono); font-size: 0.72rem; letter-spacing: 0.1em; color: var(--faint); text-transform: uppercase; }
.scroll-line { width: 1px; height: 40px; background: linear-gradient(to bottom, var(--faint), transparent); animation: scroll-pulse 2s ease-in-out infinite; }
@keyframes scroll-pulse { 0%,100% { opacity: 0.3; } 50% { opacity: 1; } }

.hero-strip {
  position: relative; z-index: 2; margin-top: 80px;
  border-top: 1px solid var(--border); padding: 26px 0; overflow: hidden;
  /* fade the logos out at both ends instead of cutting them off */
  -webkit-mask-image: linear-gradient(to right, transparent, #000 90px, #000 calc(100% - 90px), transparent);
  mask-image: linear-gradient(to right, transparent, #000 90px, #000 calc(100% - 90px), transparent);
}
.strip-track {
  display: flex; align-items: center; width: max-content;
  animation: strip-scroll 44s linear infinite;
}
.hero-strip:hover .strip-track { animation-play-state: paused; }

/* Every logo carries its own trailing margin — including the last one. That
   makes the two duplicated sets exactly equal in width, so translating by -50%
   lands the second set precisely where the first began and the loop is seamless.
   A flex `gap` would leave the seam half a gap short. */
/* Each file is pre-normalised to a matching optical size and centred in an
   identical canvas, so a fixed box here keeps them all visually equal. */
.strip-logo {
  flex: 0 0 auto; width: 150px; height: 70px; object-fit: contain;
  margin-right: 56px; opacity: 0.45;
  transition: opacity .3s var(--ease);
}
.strip-logo:hover { opacity: 0.95; }

@keyframes strip-scroll { from { transform: translateX(0); } to { transform: translateX(-50%); } }
@media (prefers-reduced-motion: reduce) { .strip-track { animation-name: none; } }

/* =========================================================
   CHAPTERS
   ========================================================= */
.chapter {
  position: relative; min-height: 100vh; display: flex; align-items: center;
  padding: 120px 0; border-top: 1px solid var(--border); overflow: hidden;
}
.chapter-glow {
  position: absolute; inset: 0; z-index: 0; pointer-events: none;
  background: radial-gradient(ellipse 60% 50% at 80% 30%, var(--glow), transparent 70%);
}
.chapter.reverse .chapter-glow { background: radial-gradient(ellipse 60% 50% at 20% 30%, var(--glow), transparent 70%); }

.chapter-deck { position: relative; z-index: 1; width: 100%; }

.chapter-inner {
  max-width: 1280px; margin: 0 auto; padding: 0 48px;
  display: grid; grid-template-columns: 0.92fr 1.08fr; gap: 72px; align-items: center;
}
.chapter.reverse .chapter-inner { grid-template-columns: 1.08fr 0.92fr; }
/* screenshot cards: give the image the space, since the image IS the point */
.chapter-inner.wide-visual { grid-template-columns: 0.66fr 1.34fr; gap: 56px; }
.chapter.reverse .chapter-inner.wide-visual { grid-template-columns: 1.34fr 0.66fr; }
.chapter.reverse .chapter-text { order: 2; }
.chapter.reverse .chapter-visual { order: 1; }

.chapter-index {
  display: block; font-family: var(--font-head); font-weight: 700;
  font-size: clamp(3.2rem, 6vw, 5rem); line-height: 1; color: var(--accent); opacity: .9;
  margin-bottom: 14px;
}
.chapter-tags {
  font-family: var(--font-mono); font-size: 0.78rem; letter-spacing: 0.08em;
  color: var(--accent); text-transform: uppercase; margin-bottom: 18px;
}
.chapter-text h2 { font-size: clamp(2rem, 3.6vw, 3rem); line-height: 1.1; margin-bottom: 14px; }
.chapter-text h3 { font-size: clamp(1.7rem, 2.8vw, 2.3rem); line-height: 1.12; margin-bottom: 14px; }
.chapter-collab { font-size: 0.98rem; color: var(--dim); font-style: italic; margin-bottom: 20px; }
.chapter-desc { font-size: 1.04rem; color: var(--dim); max-width: 480px; margin-bottom: 30px; }
.chapter-list { margin: -10px 0 30px; padding: 0; list-style: none; display: grid; gap: 10px; max-width: 480px; }
.chapter-list li { position: relative; padding-left: 20px; font-size: 0.98rem; color: var(--dim); }
.chapter-list li::before {
  content: ''; position: absolute; left: 0; top: 0.62em;
  width: 6px; height: 6px; border-radius: 50%; background: var(--accent);
}
.chapter-link {
  display: inline-flex; align-items: center; gap: 8px;
  font-weight: 600; font-size: 0.98rem; color: var(--text);
  border-bottom: 1px solid var(--accent); padding-bottom: 3px;
  transition: gap .25s var(--ease), color .25s;
}
.chapter-link:hover { gap: 13px; color: var(--accent); }
.chapter-note {
  display: block; margin-top: 14px; font-family: var(--font-mono); font-size: 0.74rem;
  color: var(--faint); letter-spacing: 0.04em;
}

/* =========================================================
   THE DECK: card 1 is the project, swipe right for services
   ========================================================= */
.deck-track {
  display: flex; width: 100%;
  overflow-x: auto; overscroll-behavior-x: contain;
  scroll-snap-type: x mandatory; scroll-behavior: smooth;
  scrollbar-width: none; -ms-overflow-style: none;
}
.deck-track::-webkit-scrollbar { display: none; }
.card { flex: 0 0 100%; scroll-snap-align: center; scroll-snap-stop: always; }

/* nav sits under the cards, on the same 1280 rhythm as the content */
.deck-nav {
  max-width: 1280px; margin: 44px auto 0; padding: 0 48px;
  display: flex; align-items: center; justify-content: space-between; gap: 24px;
}
.deck-dots { display: flex; align-items: center; gap: 9px; }
.deck-dot {
  width: 7px; height: 7px; padding: 0; border-radius: 50%;
  background: var(--border-strong);
  transition: background .3s var(--ease), transform .3s var(--ease), box-shadow .3s var(--ease);
}
.deck-dot[aria-selected="true"] { background: var(--accent); transform: scale(1.45); box-shadow: 0 0 10px var(--glow); }
.deck-dot:hover { background: var(--accent); }

.deck-controls { display: flex; align-items: center; gap: 14px; }
.deck-label {
  font-family: var(--font-mono); font-size: 0.74rem; letter-spacing: 0.08em;
  color: var(--faint); text-transform: uppercase; white-space: nowrap;
}
.deck-label b { color: var(--dim); font-weight: 500; }
.deck-btn {
  width: 38px; height: 38px; border-radius: 50%; border: 1px solid var(--border-strong);
  display: grid; place-items: center; color: var(--text);
  transition: border-color .25s, background .25s, opacity .25s;
}
.deck-btn svg { width: 16px; height: 16px; }
.deck-btn:hover:not(:disabled) { border-color: var(--accent); background: rgba(255,255,255,0.06); }
.deck-btn:disabled { opacity: .25; cursor: default; }

/* ---------- device mockup visual ---------- */
/* min-width:0 overrides the grid item's default auto min-width, which would
   otherwise inherit the full content width of a scrollable descendant (like
   the video row's fixed-width cards) instead of letting it clip and scroll */
.chapter-visual { position: relative; min-width: 0; }
/* The padding is what lets the phone overhang the browser's corner while
   staying inside the card — the deck scrolls, so anything outside gets clipped. */
.device-stack { position: relative; padding: 0 7% 7% 0; }
.chapter.reverse .device-stack { padding: 0 0 7% 7%; }
.device-browser {
  background: var(--surface); border: 1px solid var(--border-strong);
  border-radius: 14px; overflow: hidden;
  box-shadow: 0 40px 90px -30px rgba(0,0,0,0.7);
}
.device-bar {
  display: flex; align-items: center; gap: 6px; padding: 11px 14px;
  background: rgba(255,255,255,0.03); border-bottom: 1px solid var(--border);
}
.device-bar span { width: 8px; height: 8px; border-radius: 50%; background: var(--border-strong); }
.device-browser img { width: 100%; display: block; }

.device-phone {
  position: absolute; width: 26%; right: 0; bottom: 0;
  border-radius: 22px; overflow: hidden; border: 4px solid #1b1c1f;
  box-shadow: 0 30px 60px -20px rgba(0,0,0,0.8), 0 0 0 1px rgba(255,255,255,0.08);
  background: #000;
}
.chapter.reverse .device-phone { right: auto; left: 0; }
.device-phone img { width: 100%; display: block; }

/* ---------- art frame (hero imagery) ---------- */
.art-frame {
  position: relative; border-radius: 18px; overflow: hidden;
  border: 1px solid var(--border-strong);
  box-shadow: 0 40px 90px -30px rgba(0,0,0,0.7);
  aspect-ratio: 3/4; max-height: 58vh; margin-inline: auto;
}
.art-frame img { width: 100%; height: 100%; object-fit: cover; }
.art-frame::after {
  content: ''; position: absolute; inset: 0;
  background: linear-gradient(to top, rgba(0,0,0,0.25), transparent 40%);
  pointer-events: none;
}

/* ---------- media grids inside the visual column ---------- */
.media-grid { display: grid; gap: 16px; }
.media-grid + .media-grid { margin-top: 22px; }
.cols-2 { grid-template-columns: repeat(2, 1fr); }
.cols-3 { grid-template-columns: repeat(3, 1fr); }
.cols-4 { grid-template-columns: repeat(4, 1fr); }
.media-label {
  display: block; margin-bottom: 10px;
  font-family: var(--font-mono); font-size: 0.7rem; letter-spacing: 0.12em;
  color: var(--accent); text-transform: uppercase;
}

/* =========================================================
   NESTED SLIDER — slides within a card (e.g. the LMS screens)
   ========================================================= */
/* Coverflow: the focused card sits centre with its neighbours peeking in,
   scaled back and dimmed. Controls sit to the RIGHT of the deck rather than
   underneath, so the nested slider never reads as the chapter nav. */
.subdeck {
  /* one card at a time, with a sliver of its neighbours showing */
  --card-w: calc(100% - 148px);
  position: relative; padding-bottom: 30px;
}
/* galleries run narrower cards so several sit in view at once */
.subdeck.gallery { --card-w: 37%; }
.subdeck.gallery.g-wide { --card-w: 52%; }

/* video-row: a mix of landscape and portrait videos can't share one card
   width (a 9:16 clip at a 16:9 card's width would be nearly 2x taller than
   its neighbours). Instead every card shares one HEIGHT and derives its own
   width from its own ratio, so a vertical short just reads as a narrower
   card in the same row — same mechanism real video-editor timelines use. */
.subdeck.video-row { --row-h: clamp(230px, 36vh, 350px); }
/* padding must be able to fit HALF of the widest possible card (16:9) on each
   side — otherwise the track has no scroll range left to centre a much
   narrower card (the 9:16 short) sitting at the end of the row. */
/* min() caps the padding against the track's own width so it can never force
   the border-box wider than its container — without this, a narrow mobile
   viewport (where --row-h is driven by vh, not available width) makes the
   16:9-sized padding alone wider than the whole container, and the box has
   no choice but to blow out past its parent to fit the mandatory padding */
.subdeck.video-row .subdeck-track { padding-inline: min(calc(var(--row-h) * 16 / 9 / 2), calc(50% - 60px)); }
.subdeck.video-row { min-width: 0; }
.subdeck.video-row .subcard { flex: 0 0 auto; }
.subdeck.video-row .subcard-shot { height: var(--row-h); aspect-ratio: auto; }
.subdeck.video-row .subcard-shot.ar-16-9 { width: calc(var(--row-h) * 16 / 9); }
.subdeck.video-row .subcard-shot.ar-9-16 { width: calc(var(--row-h) * 9 / 16); }

/* vertical: a nested slide deck that scrolls top-to-bottom instead of side to
   side — used when the content itself is a presentation (e.g. a brand
   guideline PDF) rather than a row of separate shots, so "next" reads as
   down rather than right */
.subdeck.vertical { --shot-h: clamp(230px, 34vh, 360px); --peek-v: 34px; }
.subdeck.vertical .subdeck-track {
  flex-direction: column; padding-inline: 0;
  height: calc(var(--shot-h) + 2 * var(--peek-v));
  padding-block: var(--peek-v);
  overflow-x: hidden; overflow-y: auto; overscroll-behavior-y: contain;
  scroll-snap-type: y mandatory;
}
.subdeck.vertical .subcard { flex: 0 0 auto; width: min(100%, calc(var(--shot-h) * 1.4142)); margin-inline: auto; }
.subdeck.vertical .subcard-shot { height: var(--shot-h); aspect-ratio: auto; width: 100%; }

.sub-nav.vertical { flex-direction: column; align-items: center; justify-content: space-between; }
.sub-nav.vertical .deck-btn svg { transform: rotate(90deg); }

.subdeck-track {
  width: 100%;
  display: flex; gap: 22px;
  /* the padding is what creates the peek: a card is 100% of the content box, so
     centring it leaves the same sliver of its neighbours on each side */
  padding-inline: calc((100% - var(--card-w)) / 2);
  overflow-x: auto; overscroll-behavior-x: contain;
  scroll-snap-type: x mandatory; scroll-behavior: smooth;
  scrollbar-width: none; -ms-overflow-style: none;
}
.subdeck-track::-webkit-scrollbar { display: none; }

.subcard {
  flex: 0 0 100%; scroll-snap-align: center; scroll-snap-stop: always;
  margin: 0; border-radius: 18px; overflow: hidden;
  background: var(--surface); border: 1px solid var(--border);
  box-shadow: 0 34px 70px -34px rgba(0,0,0,0.95);
  transform: scale(0.94); opacity: 0.4;
  transition: transform .5s var(--ease), opacity .5s var(--ease), border-color .3s;
}
.subcard.is-active { transform: scale(1); opacity: 1; border-color: var(--border-strong); }

/* the screenshot sits in browser chrome, so it reads as a real product screen
   rather than a loose image */
.subcard-media { display: block; }
.subcard-media .device-bar { display: flex; }
/* ratio comes from an ar-* class, so the same shot works for a 16:10 screen,
   a 4:5 poster or a 1:1 feed tile */
.subcard-shot { display: block; aspect-ratio: 16/10; overflow: hidden; background: #000; }
.subcard-shot img { width: 100%; height: 100%; object-fit: cover; object-position: top; }
/* finished artwork — posters, key visuals — is shown whole rather than cropped,
   so it keeps its own edges even when its ratio differs from the slot */
.subcard-shot.fit { background: #0b0c0e; }
.subcard-shot.fit img { object-fit: contain; object-position: center; }

/* a placeholder fills the shot rather than drawing its own frame inside it */
.subcard-shot > .ph { height: 100%; border: none; border-radius: 0; }
.subcard-shot > .ph:hover { transform: none; }

/* a shot holding a real image opens full size on click */
.subcard-shot.zoomable { cursor: zoom-in; position: relative; }
.subcard-shot.zoomable::after {
  content: ''; position: absolute; inset: 0; opacity: 0;
  background: radial-gradient(circle at 50% 50%, rgba(255,255,255,0.10), transparent 60%);
  transition: opacity .3s var(--ease); pointer-events: none;
}
.subcard.is-active .subcard-shot.zoomable:hover::after { opacity: 1; }

/* play affordance on a real video thumbnail */
.subcard-shot.playable::before {
  content: ''; position: absolute; inset: 0;
  background: linear-gradient(to top, rgba(0,0,0,0.45), transparent 45%);
  pointer-events: none;
}
.subcard-play {
  position: absolute; top: 50%; left: 50%; transform: translate(-50%, -50%);
  width: 46px; height: 46px; border-radius: 50%; display: grid; place-items: center;
  background: rgba(8,9,10,0.55); border: 1px solid rgba(255,255,255,0.35);
  backdrop-filter: blur(3px); color: var(--text); pointer-events: none;
  transition: transform .25s var(--ease), background .25s;
}
.subcard-play svg { width: 17px; height: 17px; margin-left: 2px; }
.subcard.is-active .subcard-shot.playable:hover .subcard-play {
  transform: translate(-50%, -50%) scale(1.1); background: var(--accent);
}

/* =========================================================
   LIGHTBOX — full-screen view of a single image
   ========================================================= */
.lightbox {
  position: fixed; inset: 0; z-index: 1000;
  display: grid; grid-template-columns: auto minmax(0, 1fr) auto;
  align-items: center; gap: 16px; padding: 56px 28px 40px;
  background: rgba(4,5,6,0.94); backdrop-filter: blur(12px);
  animation: lb-in .25s var(--ease);
}
.lightbox[hidden] { display: none; }
@keyframes lb-in { from { opacity: 0; } to { opacity: 1; } }

.lb-stage {
  margin: 0; min-width: 0; display: flex; flex-direction: column;
  align-items: center; justify-content: center; gap: 16px;
}
.lb-stage img {
  max-width: 100%; max-height: calc(100vh - 170px);
  width: auto; height: auto; object-fit: contain;
  border-radius: 10px; box-shadow: 0 40px 100px -30px rgba(0,0,0,0.9);
}
.lb-stage figcaption {
  font-family: var(--font-mono); font-size: 0.72rem; letter-spacing: 0.12em;
  text-transform: uppercase; color: var(--dim); text-align: center;
}
.lb-stage figcaption b { color: var(--text); font-weight: 500; }

.lb-btn {
  display: grid; place-items: center; border-radius: 50%;
  border: 1px solid var(--border-strong); color: var(--text);
  background: rgba(255,255,255,0.05);
  transition: background .25s, border-color .25s, opacity .25s;
}
.lb-btn:hover:not(:disabled) { background: rgba(255,255,255,0.12); border-color: rgba(255,255,255,0.45); }
.lb-btn:disabled { opacity: 0.25; cursor: default; }
.lb-frame {
  width: min(100%, 1200px); aspect-ratio: 16/9; max-height: calc(100vh - 190px);
  border: 0; border-radius: 10px; background: #000;
  box-shadow: 0 40px 100px -30px rgba(0,0,0,0.9);
}
/* a vertical short in a fixed 16:9 frame would letterbox down to a sliver in
   the middle — give it its own tall, narrow frame instead */
.lb-frame.portrait {
  width: auto; aspect-ratio: 9/16; height: calc(100vh - 190px); max-width: min(92vw, 480px);
}
.lb-frame[hidden], .lb-watch[hidden] { display: none; }
/* a self-hosted clip has its own intrinsic size, unlike the iframe above, so
   it just needs the same box constraints rather than a forced aspect-ratio */
.lb-video {
  display: block; width: min(100%, 1200px); max-height: calc(100vh - 190px);
  border: 0; border-radius: 10px; background: #000;
  box-shadow: 0 40px 100px -30px rgba(0,0,0,0.9);
}
.lb-video.portrait {
  width: auto; height: calc(100vh - 190px); max-width: min(92vw, 480px);
}
.lb-video[hidden] { display: none; }
.lb-watch {
  font-family: var(--font-mono); font-size: 0.7rem; letter-spacing: 0.1em;
  text-transform: uppercase; color: var(--dim);
  border-bottom: 1px solid var(--border-strong); padding-bottom: 3px;
  transition: color .25s, border-color .25s;
}
.lb-watch:hover { color: var(--text); border-color: var(--text); }
.lb-nav { width: 46px; height: 46px; }
.lb-nav svg { width: 18px; height: 18px; }
.lb-close { position: absolute; top: 20px; right: 24px; width: 40px; height: 40px; }
.lb-close svg { width: 16px; height: 16px; }

.subcard-body { padding: 15px 18px 17px; display: grid; gap: 5px; }
.subcard-kicker {
  font-family: var(--font-mono); font-size: 0.6rem; letter-spacing: 0.14em;
  text-transform: uppercase; color: var(--accent);
}
.subcard-body h4 {
  font-family: var(--font-head); font-weight: 600; font-size: 1.02rem;
  letter-spacing: -0.01em; margin: 0;
}
.subcard-body p { font-size: 0.84rem; color: var(--dim); }

/* arrows flank the card, sitting over the dimmed peek on either side; the
   count drops underneath so it never covers the screenshot */
.sub-nav {
  position: absolute; left: 6px; right: 6px; top: 0; bottom: 30px;
  display: flex; align-items: center; justify-content: space-between;
  pointer-events: none; z-index: 2;
}
.sub-nav .deck-btn {
  pointer-events: auto; width: 36px; height: 36px;
  background: rgba(8,9,10,0.66); backdrop-filter: blur(7px);
  border-color: var(--border-strong);
}
.sub-nav .deck-btn:hover:not(:disabled) { background: rgba(8,9,10,0.85); }
.sub-nav .deck-btn svg { width: 15px; height: 15px; }
.sub-nav .deck-label {
  position: absolute; left: 50%; bottom: -26px; transform: translateX(-50%);
  font-size: 0.62rem; letter-spacing: 0.12em; white-space: nowrap;
  font-variant-numeric: tabular-nums;
}

/* a real screenshot in a slot — same footprint as the placeholder it replaces */
.shot { margin: 0; display: grid; gap: 9px; }
.shot-frame {
  display: block; border-radius: 12px; overflow: hidden;
  border: 1px solid var(--border-strong); background: var(--surface);
  box-shadow: 0 22px 46px -24px rgba(0,0,0,0.8);
  transition: border-color .25s, transform .25s var(--ease);
}
.shot-frame img { width: 100%; height: 100%; object-fit: cover; object-position: top; }
.shot:hover .shot-frame { border-color: var(--accent); transform: translateY(-2px); }
.shot figcaption {
  font-family: var(--font-mono); font-size: 0.66rem; letter-spacing: 0.1em;
  text-transform: uppercase; color: var(--faint); text-align: center;
  transition: color .25s;
}
.shot:hover figcaption { color: var(--dim); }
.shot-frame.zoomable { cursor: zoom-in; }

/* placeholder — names the asset that belongs here */
.ph {
  position: relative; display: flex; flex-direction: column;
  align-items: center; justify-content: center; gap: 6px;
  padding: 12px; text-align: center; border-radius: 12px;
  border: 1px dashed var(--border-strong);
  background:
    linear-gradient(150deg, rgba(255,255,255,0.045), rgba(255,255,255,0.012)),
    var(--surface);
  transition: border-color .25s, transform .25s var(--ease);
}
.ph:hover { border-color: var(--accent); transform: translateY(-2px); }
.ph-kind {
  font-family: var(--font-mono); font-size: 0.6rem; letter-spacing: 0.13em;
  text-transform: uppercase; color: var(--accent);
}
.ph-label { font-size: 0.8rem; color: var(--text); line-height: 1.3; }
.ph-spec { font-family: var(--font-mono); font-size: 0.6rem; color: var(--faint); }
.ph-play {
  width: 30px; height: 30px; border-radius: 50%; display: grid; place-items: center;
  border: 1px solid var(--border-strong); color: var(--accent); margin-bottom: 2px;
}
.ph-play svg { width: 12px; height: 12px; }

.ar-1-1   { aspect-ratio: 1/1; }
.ar-4-5   { aspect-ratio: 4/5; }
.ar-3-4   { aspect-ratio: 3/4; }
.ar-16-9  { aspect-ratio: 16/9; }
.ar-9-16  { aspect-ratio: 9/16; }
.ar-16-10 { aspect-ratio: 16/10; }
.ar-4-3   { aspect-ratio: 4/3; }

.phone-frame {
  border-radius: 22px; overflow: hidden; border: 4px solid #1b1c1f; background: #000;
  box-shadow: 0 26px 54px -22px rgba(0,0,0,0.8), 0 0 0 1px rgba(255,255,255,0.07);
}
.phone-frame .ph { border-radius: 0; border: none; height: 100%; }

/* =========================================================
   BUTTONS
   ========================================================= */
.btn {
  display: inline-flex; align-items: center; gap: 8px;
  padding: 15px 28px; border-radius: 999px; font-weight: 600; font-size: 0.98rem;
  border: 1px solid transparent; transition: transform .25s var(--ease), box-shadow .25s var(--ease), border-color .25s, color .25s;
}
.btn-primary { background: var(--text); color: #0a0a0b; }
.btn-primary:hover { transform: translateY(-2px); box-shadow: 0 14px 30px -10px rgba(255,255,255,0.25); }
.btn-ghost { border-color: var(--border-strong); }
.btn-ghost:hover { border-color: rgba(255,255,255,0.5); transform: translateY(-2px); }
.btn-lg { padding: 17px 30px; }

/* =========================================================
   CLOSING
   ========================================================= */
.closing {
  position: relative; min-height: 90vh; display: flex; align-items: center;
  border-top: 1px solid var(--border); text-align: center; overflow: hidden;
}
.closing-glow {
  position: absolute; inset: 0;
  background: radial-gradient(ellipse 70% 60% at 50% 40%, rgba(236,72,153,0.10), transparent 70%);
}
.closing-inner { position: relative; z-index: 1; max-width: 720px; margin: 0 auto; padding: 0 32px; }
.closing h2 { font-size: clamp(2.1rem, 4.2vw, 3.2rem); line-height: 1.12; margin: 16px 0 20px; }
.closing-sub { color: var(--dim); font-size: 1.06rem; max-width: 520px; margin: 0 auto; }
.closing-actions { display: flex; justify-content: center; gap: 14px; margin-top: 40px; flex-wrap: wrap; }

/* =========================================================
   FOOTER
   ========================================================= */
.footer {
  padding: 56px 32px 40px; text-align: center;
  display: flex; flex-direction: column; align-items: center; gap: 10px;
  border-top: 1px solid var(--border);
}
.footer-mark { width: 26px; opacity: 0.55; }
.footer p { font-size: 0.92rem; color: var(--dim); }
.footer span { font-size: 0.78rem; color: var(--faint); }

/* =========================================================
   RESPONSIVE
   ========================================================= */
@media (max-width: 1080px) {
  .chapter-nav { display: none; }
  /* .wide-visual carries its own two-class grid-template-columns rule that
     otherwise out-specifies this reset and keeps screenshot cards side by
     side on mobile, crushing the coverflow into an unreadable sliver */
  .chapter-inner, .chapter-inner.wide-visual { grid-template-columns: 1fr; gap: 48px; }
  .chapter.reverse .chapter-inner, .chapter.reverse .chapter-inner.wide-visual { grid-template-columns: 1fr; }
  .chapter.reverse .chapter-text { order: 1; }
  .chapter.reverse .chapter-visual { order: 2; }
  .chapter-desc, .chapter-list { max-width: none; }
  .device-phone { width: 24%; }
  .art-frame { max-height: 46vh; }
  .deck-nav { margin-top: 34px; padding: 0 32px; }
  .subdeck { --peek: 46px; }
}

@media (max-width: 640px) {
  .topbar { padding: 16px 20px; }
  .hero { padding-top: 130px; }
  .hero-inner { padding: 0 22px; }
  .hero-sub { margin-bottom: 34px; }
  .hero-strip { margin-top: 56px; }
  .chapter { padding: 76px 0; }
  .chapter-inner { padding: 0 22px; gap: 40px; }
  .chapter-index { font-size: clamp(2.6rem, 13vw, 3.4rem); }
  .device-phone { width: 28%; }
  .cols-4 { grid-template-columns: repeat(2, 1fr); }
  .deck-nav { padding: 0 22px; margin-top: 28px; }
  /* narrow screens: keep the arrows flanking, just tucked tighter to the edges */
  .subdeck { --peek: 30px; }
  /* on desktop these run narrower so several cards sit in view at once, or so
     a fixed viewport-height budget is respected — neither reason holds on a
     phone, where the page just scrolls and there's only room for one card at
     a time anyway, so every type gets close to the full width: video, image,
     and everything else reads as big as the hero imagery instead of a strip */
  .subdeck { --card-w: 92%; }
  .subdeck.gallery { --card-w: 92%; }
  .subdeck.gallery.g-wide { --card-w: 94%; }
  /* a 9:16 phone-screen shot at the same 92% width as a poster runs nearly
     the full viewport height — it needs a narrower card so it reads as a
     phone mockup, not a full-bleed image */
  .subdeck.gallery.phone { --card-w: 56%; }
  .subdeck.vertical { --peek-v: 22px; --shot-h: clamp(230px, 60vw, 300px); }
  .subdeck.video-row { --row-h: clamp(170px, 48vw, 230px); }
  .sub-nav .deck-btn { width: 32px; height: 32px; }
  .subcard-body { padding: 13px 15px 15px; }
  .deck-label { display: none; }
  .closing-actions { flex-direction: column; align-items: stretch; }
  .closing-actions .btn { justify-content: center; }
}
