/* The recording stage.
 *
 * Fixed 1920x1080 and scaled to fit, so what a screen recorder captures is
 * identical on a laptop and on the machine that renders the final cut. A
 * layout that reflows with the window is a layout that looks different in
 * every take. */

:root {
  --paper: #f3ecdd;
  --paper-alt: #ece2cd;
  --card: #faf6ec;
  --ink: #1c2433;
  --ink-dim: #4b5769;
  --ink-faint: #7c8494;
  --accent: #3f5c78;
  --accent-deep: #24374a;
  --border: rgba(28, 36, 51, 0.14);
  --border-strong: rgba(28, 36, 51, 0.26);

  /* Telegram's own palette, so the phone reads as the app people know. */
  --tg-bg: #0e1621;
  --tg-bg-pattern: #17212b;
  --tg-in: #182533;
  --tg-out: #2b5278;
  --tg-text: #ecf0f4;
  --tg-text-dim: #7d8c9c;
  --tg-bar: #17212b;
  --tg-link: #62a3e0;
}

* { box-sizing: border-box; }

html, body {
  margin: 0;
  height: 100%;
  background: #0b0f14;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica,
    Arial, sans-serif, "Apple Color Emoji", "Segoe UI Emoji";
  overflow: hidden;
}

/* ---------- stage ---------- */

#stage-wrap {
  position: fixed;
  inset: 0;
  overflow: hidden;
}

/* Centred by absolute position, not by grid: a grid item larger than its
   container clamps to the start edge rather than centring (overflow
   alignment), so the scale-about-centre landed half off-screen. */
#stage {
  position: absolute;
  top: 50%;
  left: 50%;
  width: 1920px;
  height: 1080px;
  transform-origin: center center;
  background: var(--paper);
  display: grid;
  grid-template-columns: 1fr 720px;
  overflow: hidden;
}

/* ---------- left: the argument ---------- */

.pane-copy {
  padding: 96px 80px 96px 104px;
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 0;
  position: relative;
}

.brandline {
  position: absolute;
  top: 64px;
  left: 104px;
  display: flex;
  align-items: center;
  gap: 12px;
  font-weight: 700;
  font-size: 26px;
  letter-spacing: -0.01em;
  color: var(--ink);
}

.brandline img { width: 30px; height: 30px; border-radius: 6px; }

.act-no {
  font-size: 17px;
  font-weight: 700;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--accent);
  margin-bottom: 22px;
}

.act-title {
  font-size: 66px;
  line-height: 1.04;
  font-weight: 700;
  letter-spacing: -0.025em;
  color: var(--ink);
  margin: 0 0 26px;
  max-width: 15ch;
}

.act-blurb {
  font-size: 26px;
  line-height: 1.5;
  color: var(--ink-dim);
  margin: 0;
  max-width: 34ch;
}

/* The annotation that appears beside the phone as a beat lands. */
.act-note {
  margin-top: 44px;
  min-height: 112px;
  max-width: 36ch;
}

.note-card {
  border-left: 3px solid var(--accent);
  padding: 4px 0 4px 20px;
  font-size: 22px;
  line-height: 1.45;
  color: var(--accent-deep);
  opacity: 0;
  transform: translateY(8px);
}

.note-card.in { animation: note-in 420ms ease forwards; }

@keyframes note-in {
  to { opacity: 1; transform: none; }
}

/* Fade the whole copy pane between acts rather than swapping words in place. */
.pane-copy .act-body { transition: opacity 320ms ease, transform 320ms ease; }
.pane-copy.turning .act-body { opacity: 0; transform: translateY(-10px); }

/* ---------- right: the phone ---------- */

.pane-phone {
  background: var(--paper-alt);
  display: grid;
  place-items: center;
  border-left: 1px solid var(--border);
  position: relative;
}

.phone {
  width: 460px;
  height: 920px;
  border-radius: 46px;
  background: #05080c;
  padding: 12px;
  box-shadow: 0 40px 90px rgba(18, 24, 34, 0.32), 0 3px 10px rgba(18, 24, 34, 0.2);
}

.screen {
  width: 100%;
  height: 100%;
  border-radius: 34px;
  overflow: hidden;
  background: var(--tg-bg);
  display: grid;
  grid-template-rows: auto 1fr auto;
  position: relative;
}

/* chat header */
.tg-bar {
  background: var(--tg-bar);
  padding: 14px 16px;
  display: flex;
  align-items: center;
  gap: 12px;
  border-bottom: 1px solid rgba(0, 0, 0, 0.35);
}

.tg-avatar {
  width: 38px; height: 38px;
  border-radius: 50%;
  object-fit: cover;
  background: var(--accent);
  display: grid; place-items: center;
  color: #fff; font-weight: 700; font-size: 15px;
  flex: none;
}

.tg-title { color: var(--tg-text); font-size: 16px; font-weight: 600; line-height: 1.2; }
.tg-sub { color: var(--tg-text-dim); font-size: 12.5px; line-height: 1.3; }

/* log */
.tg-log {
  padding: 16px 14px 10px;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  gap: 8px;
  justify-content: flex-end;
  background:
    radial-gradient(1200px 700px at 70% -10%, rgba(63, 92, 120, 0.22), transparent 60%),
    var(--tg-bg);
}

.row { display: flex; gap: 8px; align-items: flex-end; }
.row.out { justify-content: flex-end; }

.row-avatar {
  width: 28px; height: 28px; border-radius: 50%;
  display: grid; place-items: center;
  font-size: 12px; font-weight: 700; color: #fff;
  flex: none; margin-bottom: 2px;
}

.bubble {
  max-width: 330px;
  padding: 8px 12px 7px;
  border-radius: 14px;
  font-size: 15.5px;
  line-height: 1.42;
  color: var(--tg-text);
  white-space: pre-wrap;
  word-wrap: break-word;
  position: relative;
  animation: pop 260ms cubic-bezier(0.2, 0.9, 0.3, 1.2);
}

@keyframes pop {
  from { opacity: 0; transform: translateY(10px) scale(0.97); }
  to { opacity: 1; transform: none; }
}

.bubble.in { background: var(--tg-in); border-bottom-left-radius: 5px; }
.bubble.out { background: var(--tg-out); border-bottom-right-radius: 5px; }

.bubble .who {
  display: block;
  font-size: 13px;
  font-weight: 700;
  margin-bottom: 2px;
}

/* A rendered view: monospace, full width, no tail — it is a report, not talk. */
.bubble.view {
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 13.5px;
  line-height: 1.5;
  max-width: 100%;
  width: 100%;
  background: #14202c;
  border: 1px solid rgba(98, 163, 224, 0.22);
  border-radius: 10px;
}

/* An unprompted message gets a mark, so nobody watching thinks it was typed. */
.bubble.pushed::before {
  content: "";
  position: absolute;
  left: -7px; top: 14px;
  width: 3px; height: calc(100% - 28px);
  border-radius: 2px;
  background: var(--tg-link);
}

.tg-time {
  font-size: 11px;
  color: rgba(236, 240, 244, 0.45);
  margin-left: 8px;
  float: right;
  position: relative;
  top: 5px;
}

/* the typing indicator */
.typing { display: flex; gap: 4px; padding: 12px 14px; }
.typing i {
  width: 7px; height: 7px; border-radius: 50%;
  background: var(--tg-text-dim);
  animation: blink 1.1s infinite ease-in-out;
}
.typing i:nth-child(2) { animation-delay: 0.16s; }
.typing i:nth-child(3) { animation-delay: 0.32s; }

@keyframes blink {
  0%, 60%, 100% { opacity: 0.28; transform: translateY(0); }
  30% { opacity: 1; transform: translateY(-3px); }
}

/* composer */
.tg-input {
  background: var(--tg-bar);
  padding: 12px 14px;
  display: flex;
  align-items: center;
  gap: 10px;
  border-top: 1px solid rgba(0, 0, 0, 0.35);
  min-height: 56px;
}

.tg-field {
  flex: 1;
  min-width: 0;
  color: var(--tg-text);
  font-size: 15.5px;
  min-height: 21px;
  line-height: 1.35;
  /* A pasted recipe URL is one unbreakable token wider than the composer.
     Without this it overflows on a single line and the end of what is being
     typed — the part the viewer is reading — is the part that gets clipped. */
  overflow-wrap: anywhere;
  max-height: 84px;
  overflow: hidden;
}

.tg-field.empty { color: var(--tg-text-dim); }

.caret {
  display: inline-block;
  width: 1.5px;
  height: 17px;
  background: var(--tg-link);
  vertical-align: -3px;
  margin-left: 1px;
  animation: caret 1s step-end infinite;
}

@keyframes caret { 50% { opacity: 0; } }

.send {
  width: 30px; height: 30px; border-radius: 50%;
  background: var(--tg-link);
  display: grid; place-items: center;
  color: #fff; font-size: 15px;
  opacity: 0.25;
  transition: opacity 160ms ease, transform 160ms ease;
}
.send.live { opacity: 1; }
.send.fire { transform: scale(0.82); }

/* ---------- a wall-clock overlay for the scheduled beats ---------- */

.clockflash {
  position: absolute;
  inset: 0;
  display: grid;
  place-items: center;
  background: rgba(5, 8, 12, 0.72);
  color: #fff;
  font-size: 46px;
  font-weight: 700;
  letter-spacing: -0.02em;
  text-align: center;
  padding: 0 28px;
  overflow-wrap: anywhere;
  opacity: 0;
  pointer-events: none;
}
.clockflash.show { animation: clockflash 1500ms ease forwards; }

@keyframes clockflash {
  0% { opacity: 0; }
  18% { opacity: 1; }
  74% { opacity: 1; }
  100% { opacity: 0; }
}

/* ---------- progress + chapters ---------- */

.progress {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  height: 5px;
  background: rgba(28, 36, 51, 0.1);
}
.progress .bar {
  height: 100%;
  background: var(--accent);
  width: 0%;
  transition: width 220ms linear;
}

.chapters {
  position: absolute;
  left: 104px;
  bottom: 56px;
  display: flex;
  gap: 7px;
}

.chapters .dot {
  width: 30px; height: 4px; border-radius: 2px;
  background: rgba(28, 36, 51, 0.18);
  transition: background 200ms ease;
}
.chapters .dot.done { background: rgba(63, 92, 120, 0.55); }
.chapters .dot.now { background: var(--accent-deep); }

/* ---------- the closing card ---------- */

.closer {
  position: absolute;
  inset: 0;
  background: var(--ink);
  color: var(--paper);
  display: grid;
  place-items: center;
  text-align: center;
  opacity: 0;
  pointer-events: none;
  transition: opacity 600ms ease;
}
.closer.show { opacity: 1; }

/* An explicit width, not `22ch`: a ch on this element is measured against
   its own inherited 16px, not the 76px heading inside it, which collapsed
   the card to one word per line and pushed the button off the bottom. */
.closer-inner { max-width: 1000px; padding: 0 60px; }
.closer h2 { font-size: 76px; line-height: 1.08; letter-spacing: -0.03em; margin: 0 0 28px; }
.closer p { font-size: 28px; color: rgba(243, 236, 221, 0.68); margin: 0 0 40px; }
.closer .cta {
  display: inline-block;
  font-size: 26px;
  font-weight: 700;
  padding: 16px 32px;
  border-radius: 8px;
  background: var(--paper);
  color: var(--ink);
  text-decoration: none;
}
.closer .mark { width: 54px; height: 54px; margin-bottom: 30px; border-radius: 10px; }

/* ---------- operator chrome (hidden for the take) ---------- */

.chrome {
  position: fixed;
  left: 50%;
  bottom: 18px;
  transform: translateX(-50%);
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 8px 12px;
  border-radius: 999px;
  background: rgba(12, 16, 22, 0.86);
  border: 1px solid rgba(255, 255, 255, 0.12);
  backdrop-filter: blur(8px);
  z-index: 50;
  font-size: 13px;
  color: #dfe6ee;
}

.chrome button, .chrome select {
  font: inherit;
  color: inherit;
  background: rgba(255, 255, 255, 0.08);
  border: 1px solid rgba(255, 255, 255, 0.14);
  border-radius: 6px;
  padding: 5px 10px;
  cursor: pointer;
}
.chrome button:hover, .chrome select:hover { background: rgba(255, 255, 255, 0.16); }
.chrome .hint { color: #8b97a5; padding-left: 4px; }

body.clean .chrome { display: none; }
body.clean { cursor: none; }


/* ---------- flow mode: phones, and any window too small to scale into ----------
 *
 * The stage above is a fixed 1920x1080 canvas scaled to fit, which is what
 * makes two takes frame-comparable. On a phone in portrait that same rule
 * scales it to about a fifth and the whole thing is unreadable: the scale
 * has to satisfy the narrow axis, and 1920 against 390 is the narrow axis.
 *
 * So below the breakpoint the stage stops being a canvas and becomes an
 * ordinary column — caption on top, the chat full-bleed underneath, no
 * phone bezel around a phone. Nothing about the script changes; only the
 * frame it plays in. `body.flow` is set by the player from one matchMedia,
 * so the breakpoint has a single definition rather than one here and one
 * there.
 */

body.flow #stage-wrap { position: static; overflow: visible; }

body.flow #stage {
  /* Still positioned: the closing card and the progress bar are absolute
     against it. Just no longer centred-and-scaled. */
  position: relative;
  top: auto;
  left: auto;
  width: 100%;
  height: 100vh;
  height: 100dvh;
  transform: none;
  display: flex;
  flex-direction: column;
}

body.flow .pane-copy {
  flex: none;
  padding: 14px 18px 12px;
  justify-content: flex-start;
  border-bottom: 1px solid var(--border);
}

body.flow .brandline {
  position: static;
  font-size: 17px;
  margin-bottom: 10px;
}
body.flow .brandline img { width: 20px; height: 20px; }

body.flow .act-no { font-size: 12px; margin-bottom: 7px; }

body.flow .act-title {
  font-size: clamp(22px, 6.4vw, 34px);
  margin-bottom: 8px;
  max-width: none;
}

body.flow .act-blurb { font-size: 15px; line-height: 1.45; max-width: none; }

body.flow .act-note { margin-top: 12px; min-height: 0; max-width: none; }
body.flow .note-card { font-size: 14px; padding-left: 12px; }

body.flow .pane-phone {
  flex: 1;
  min-height: 0;
  display: block;
  border-left: none;
  background: var(--tg-bg);
}

body.flow .phone {
  width: 100%;
  height: 100%;
  padding: 0;
  border-radius: 0;
  background: none;
  box-shadow: none;
}

/* Capped and centred: flow mode also catches a tablet and a phone on its
   side, and a chat run edge to edge at 820px reads as a document rather
   than as a conversation. */
body.flow .screen {
  border-radius: 0;
  max-width: 640px;
  margin: 0 auto;
}

/* A percentage rather than the desktop's fixed 330px, since the log is now
   as wide as the screen — but capped for the same reason the column is. */
body.flow .bubble { max-width: min(78%, 460px); }
body.flow .bubble.view { max-width: 100%; font-size: 12px; }

body.flow .chapters { position: static; margin-top: 12px; }

body.flow .clockflash { font-size: 30px; }

body.flow .closer-inner { padding: 0 26px; }
body.flow .closer h2 { font-size: clamp(28px, 7.6vw, 44px); margin-bottom: 16px; }
body.flow .closer p { font-size: 16px; margin-bottom: 26px; }
body.flow .closer .cta { font-size: 17px; padding: 12px 24px; }
body.flow .closer .mark { width: 38px; height: 38px; margin-bottom: 18px; }

body.flow .chrome {
  bottom: 8px;
  font-size: 11px;
  gap: 6px;
  padding: 6px 8px;
  max-width: 94vw;
  flex-wrap: wrap;
  justify-content: center;
}
body.flow .chrome .hint { display: none; }

/* A phone on its side has no room for the argument and the chat both, and
   the chat is the half that is actually showing the product. */
@media (max-height: 520px) {
  body.flow .brandline,
  body.flow .act-blurb,
  body.flow .act-note,
  body.flow .chapters { display: none; }
  body.flow .act-title { font-size: 20px; margin-bottom: 0; }
  body.flow .act-no { margin-bottom: 4px; }
  body.flow .pane-copy { padding: 9px 14px 8px; }
}
