/* ==========================================================================
   SuperApp marketing site — design system
   Source of truth: SuperApp Brand & Experience Guide, Launch edition 2026.

   Tokens
   - Paper #FBFAFD, Deep Ink #0D0B12, SuperApp Violet #8463CE,
     Violet Mist #EEE9F8, Line #DED8E8, Muted #6D6777,
     Success #39C987, Attention #FF7C63.
   - Voice type: Manrope (variable 200–800). System voice: IBM Plex Mono.
   - Color behavior: lead neutral, violet is the signal, status sparingly.
   ========================================================================== */

@font-face {
  font-family: "Manrope";
  src: url("../fonts/manrope-latin-200-800.woff2") format("woff2");
  font-weight: 200 800;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "IBM Plex Mono";
  src: url("../fonts/ibmplexmono-latin-500.woff2") format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "IBM Plex Mono";
  src: url("../fonts/ibmplexmono-latin-600.woff2") format("woff2");
  font-weight: 600;
  font-style: normal;
  font-display: swap;
}

:root {
  --paper: #fbfafd;
  --ink: #0d0b12;
  --muted: #6d6777;
  --violet: #8463ce;
  --violet-deep: #5d3da7;
  --mist: #eee9f8;
  --line: #ded8e8;
  --white: #ffffff;
  --green: #39c987;
  --coral: #ff7c63;
  --unread: #5a52fa;

  --font-voice: "Manrope", system-ui, -apple-system, "Segoe UI", sans-serif;
  --font-system: "IBM Plex Mono", ui-monospace, "SF Mono", Menlo, monospace;

  /* Violet tick, the marker every list of claims takes. */
  --tick: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%238463ce' stroke-width='3.4' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M4 12.5l5.5 5.5L20 6.5'/%3E%3C/svg%3E");

  --wrap: 1200px;
  --radius: 28px;
  --radius-sm: 18px;
}

/* Base ------------------------------------------------------------------ */

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

html {
  scroll-behavior: smooth;
  -webkit-text-size-adjust: 100%;
}

body {
  font-family: var(--font-voice);
  font-size: 17px;
  line-height: 1.55;
  letter-spacing: -0.012em;
  background: var(--paper);
  color: var(--ink);
  font-optical-sizing: auto;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
}

img, svg { display: block; max-width: 100%; }
a { color: inherit; text-decoration: none; }
ul, ol { list-style: none; }

::selection { background: var(--violet); color: #fff; }

:focus-visible {
  outline: 2px solid var(--violet);
  outline-offset: 3px;
  border-radius: 4px;
}

section { scroll-margin-top: 76px; }

.wrap {
  width: min(var(--wrap), calc(100% - clamp(40px, 8vw, 120px)));
  margin-inline: auto;
}

/* Type ------------------------------------------------------------------ */

.eyebrow {
  font-family: var(--font-system);
  font-size: 13px;
  line-height: 1;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  font-weight: 600;
  color: var(--muted);
}

.rule-label {
  font-family: var(--font-system);
  font-size: 12px;
  line-height: 1.6;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  font-weight: 600;
  color: var(--muted);
}

/* One statement scale, used by every page-top hero, every closing band and
   every catalog title — matching the size the signed-out app landing settled
   on (`.sa-login-hero .hero-h` in `Login/site/loginCss.ts`).

   Four scales used to open a page: 96px on the landing, 76px on Enterprise and
   Brand, 54px on Security and Pricing, 32px on the company collections, all at
   1440. The largest also grew half again as fast with the viewport, so it
   filled the screen before it could be read. They are one rule now, and a
   change to it moves every page at once.

   `.cat-head` keeps only its spacing below; `.display` is the closing band and
   nothing else uses it. Section headings stay `.title`. */
.hero-h,
.display,
.cat-head {
  font-size: clamp(38px, 5.2vw, 72px);
  line-height: 0.94;
  letter-spacing: -0.052em;
  font-weight: 800;
}

/* A measure for the opening statement. Without one it takes the whole column,
   and the Enterprise hero ran 44 characters to the line at 1180px — a
   paragraph's width set at a headline's size. 12em is about 72% of the column,
   which holds the longest headings to two balanced lines and lets the landing
   headline fall to two as well: the app's signed-out landing breaks that line
   regardless, because its first fold carries the sign-in card, so two lines is
   the consistent answer rather than a compromise.

   In em rather than a percentage, so the characters per line stay put as the
   size clamps down on a narrow screen — a percentage would keep widening the
   measure relative to the type. `text-wrap: balance` evens the lines where a browser
   supports it and is ignored where it does not. Never a hard `<br>`: that
   fixes one width and breaks every other. */
.hero-h {
  max-width: 12em;
  text-wrap: balance;
}

.title {
  font-size: clamp(32px, 4.4vw, 54px);
  line-height: 1.03;
  letter-spacing: -0.047em;
  font-weight: 800;
}

.subhead {
  font-size: clamp(22px, 2.4vw, 30px);
  line-height: 1.18;
  letter-spacing: -0.025em;
  font-weight: 700;
}

.copy {
  font-size: clamp(17px, 1.7vw, 21px);
  line-height: 1.52;
  letter-spacing: -0.012em;
  color: var(--muted);
}

.small { font-size: 15px; line-height: 1.48; color: var(--muted); }

.mono { font-family: var(--font-system); }
.violet { color: var(--violet); }

/* Shared atoms ----------------------------------------------------------- */

.hairline { height: 1px; background: var(--line); border: 0; }



/* Base row of calls to action. The hero and the closing band set their own
   rhythm on top of this. */
.cta-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 14px;
  margin-top: clamp(32px, 4vw, 44px);
}

.dot {
  width: 10px; height: 10px; flex: none;
  border-radius: 999px; background: var(--violet);
}

.pill {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  padding: 10px 15px;
  border: 1px solid var(--line);
  border-radius: 999px;
  font-size: 14px;
  font-weight: 700;
  background: rgba(255, 255, 255, 0.65);
}

.btn {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  white-space: nowrap;
  padding: 15px 26px;
  border-radius: 999px;
  border: 1px solid transparent;
  font: 800 16px/1 var(--font-voice);
  letter-spacing: -0.01em;
  cursor: pointer;
  transition: background-color 0.18s ease, border-color 0.18s ease,
    color 0.18s ease, transform 0.18s ease;
}
.btn .arrow { transition: transform 0.18s ease; }
.btn:hover .arrow { transform: translateX(3px); }

.btn-primary { background: var(--violet); color: #fff; }
.btn-primary:hover { background: var(--violet-deep); }

.btn-ghost {
  border-color: var(--line);
  color: var(--ink);
  background: rgba(255, 255, 255, 0.6);
}
.btn-ghost:hover { border-color: var(--violet); color: var(--violet-deep); }

.btn-inverse { background: #fff; color: var(--violet-deep); }
.btn-inverse:hover { background: var(--mist); }

/* Section scaffolding ----------------------------------------------------- */

.section { padding-block: clamp(76px, 10vw, 136px); }

/* First section on a page that opens with one instead of the hero: clears the
   fixed header and gives the heading the same breathing room the hero has. */
/* The gap under the fixed header, the same on every page and the same as the
   app's signed-out landing. Four values used to open a page — 230px on this
   site's landing, 200px on most pages, 140px on the collections, 168px on the
   app's — so the header sat a different distance from the first word depending
   on where a reader arrived. This is the app's, the tightest of them, which is
   the one sized against a first screen that has to hold something else too.
   `.hero` takes it as well; only its bottom padding is its own. */
.section.page-top,
.hero { padding-block-start: clamp(116px, 15vh, 168px); }

.section-head { max-width: 980px; }
/* For a head whose longest line is a full sentence: the copy under it keeps
   its own measure, so only the heading gets the extra room. */
.section-head.wide { max-width: 1180px; }
.section-head .copy { margin-top: 26px; max-width: 720px; }
/* A second paragraph in a head is the next beat of the same thought, so it
   sits closer than the gap under the heading. */
.section-head .copy + .copy { margin-top: 15px; }

/* Gallery: one use case per section, its heading over the scene itself.
   `.bare` is for scenes that already carry their own width and spacing —
   the model orbit and the editor stack. */
.gal-intro { padding-block-end: 0; }
.gal-stage { margin-top: clamp(40px, 5vw, 60px); }
.gal-stage.bare { margin-top: 0; }
/* The room-only frame has no sidebar to fill a full-width column. */
.gal-stage.narrow { max-width: 880px; margin-inline: auto; }

.dark { background: var(--ink); color: #fff; }
.dark .copy { color: rgba(255, 255, 255, 0.72); }
.dark .small { color: rgba(255, 255, 255, 0.64); }
.dark .rule-label { color: rgba(255, 255, 255, 0.66); }
.dark .hairline { background: rgba(255, 255, 255, 0.18); }

.purple { background: var(--violet); color: #fff; }
.purple .rule-label { color: rgba(255, 255, 255, 0.78); }
.purple .copy { color: rgba(255, 255, 255, 0.85); }
.purple .hairline { background: rgba(255, 255, 255, 0.32); }

.mist-bg { background: var(--mist); }
.mist-bg .pill { background: rgba(255, 255, 255, 0.75); }

/* Film-grain veil (brand texture, kept nearly invisible) */
.noise-host { position: relative; }
.noise {
  position: absolute;
  inset: 0;
  z-index: 0;
  opacity: 0.02;
  pointer-events: none;
  background-image: url("data:image/svg+xml,%3Csvg viewBox='0 0 180 180' xmlns='http://www.w3.org/2000/svg'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.9' numOctaves='3' stitchTiles='stitch'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)' opacity='.8'/%3E%3C/svg%3E");
}
.noise-host > .wrap { position: relative; z-index: 1; }

/* Header ------------------------------------------------------------------ */

.site-header {
  position: fixed;
  inset: 0 0 auto 0;
  z-index: 40;
  background: rgba(251, 250, 253, 0.82);
  -webkit-backdrop-filter: blur(14px);
  backdrop-filter: blur(14px);
  border-bottom: 1px solid transparent;
  transition: border-color 0.25s ease;
}
.site-header.scrolled { border-bottom-color: var(--line); }

.site-header .bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 24px;
  height: 76px;
}

.site-header .logo img { width: 176px; height: auto; }

.site-nav { display: flex; align-items: center; gap: 34px; }
.site-nav a:not(.btn) {
  font-size: 15px;
  font-weight: 700;
  color: var(--muted);
  transition: color 0.15s ease;
}
.site-nav a:not(.btn):hover { color: var(--ink); }

.site-header .btn { padding: 12px 20px; font-size: 15px; }

/* Hamburger toggle and the in-panel CTA only exist on small screens. */
.site-nav .menu-cta { display: none; }
.nav-toggle {
  display: none;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 6px;
  width: 44px;
  height: 44px;
  margin-right: -11px;
  padding: 0;
  border: 0;
  background: none;
  cursor: pointer;
  color: var(--ink);
}
.nav-toggle:hover { color: var(--violet-deep); }
.nav-toggle .nt-bar {
  width: 21px;
  height: 2px;
  border-radius: 999px;
  background: currentColor;
  transition: transform 0.22s ease;
}
.menu-open .nav-toggle .nt-bar:first-child { transform: translateY(4px) rotate(45deg); }
.menu-open .nav-toggle .nt-bar:last-child { transform: translateY(-4px) rotate(-45deg); }

/* Hero -------------------------------------------------------------------- */

.hero {
  padding-block-end: clamp(72px, 9vw, 110px);
}

/* The field: a soft violet glow with a thin ring riding its edge, top-right,
   from the brand "fields" motif. Every page wears it in the same corner at
   the same size, so arriving anywhere on the site looks like arriving at the
   same place — whether the page opens on the hero or on a plain section.

   The pseudos sit at `z-index: 0` rather than behind the element, so a band
   with a background of its own — `/pricing` opens on `.mist-bg` — does not
   paint over them; `.wrap` is lifted above so the glow stays behind the
   words.

   The band is clipped, so it is also held to the height the field needs: the
   ring's lowest point is 470px down, and a shorter band would end the field on
   a straight edge instead of on its own fade. Only the gallery's intro, which
   hands straight over to its first scene, is short enough for that to bite. */
.hero,
.section.page-top {
  position: relative;
  overflow: hidden;
  isolation: isolate;
  min-height: 480px;
}
.hero::before,
.hero::after,
.section.page-top::before,
.section.page-top::after {
  content: "";
  position: absolute;
  border-radius: 50%;
  z-index: 0;
  pointer-events: none;
}
.hero::before,
.section.page-top::before {
  width: 880px; height: 880px;
  right: -280px; top: -330px;
  background: radial-gradient(
    circle,
    rgba(132, 99, 206, 0.2) 0,
    rgba(132, 99, 206, 0.08) 42%,
    rgba(132, 99, 206, 0) 70%
  );
}
.hero::after,
.section.page-top::after {
  width: 620px; height: 620px;
  right: -90px; top: -150px;
  border: 1px solid rgba(132, 99, 206, 0.22);
}
.hero > .wrap,
.section.page-top > .wrap { position: relative; z-index: 1; }


.hero .lede {
  margin-top: 36px;
  max-width: 720px;
  text-wrap: pretty;
}

.hero .cta-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 14px;
  margin-top: 44px;
}

/* Product pillars: the three superpowers as freedom-style cards on the
   section's mist field. */

.pillars {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 22px;
  margin-top: clamp(44px, 6vw, 72px);
}
.pillars > div {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 30px 28px;
  display: flex;
  flex-direction: column;
  gap: 14px;
}
.pillars .rule-label { display: block; color: var(--violet-deep); }
.pillars .statement {
  font-size: clamp(22px, 2.2vw, 27px);
  line-height: 1.15;
  letter-spacing: -0.028em;
  font-weight: 800;
  max-width: 300px;
}

/* The four brand principles, in the plain numbered-grid voice (not cards).
   They carry their own section between Productivity and Freedom. */
.principles {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  --colpad: clamp(22px, 2.8vw, 36px);
  column-gap: 0;
  row-gap: clamp(32px, 4vw, 48px);
  margin-top: clamp(40px, 5vw, 60px);
}
/* Brand-guide column rules: thin vertical hairlines between columns. */
.principle {
  padding-inline: var(--colpad);
  border-left: 1px solid var(--line);
}
.principle:nth-child(4n + 1) { border-left: 0; padding-left: 0; }
/* Three across where a section has three of them. One row, so the existing
   first-in-row rule already clears the leading border, and the ≤2-column and
   1-column rules below still catch it. */
.principles.three { grid-template-columns: repeat(3, 1fr); }

/* A list of names, in the same hairline-ruled voice the numbered grid uses —
   each one gets its own rule rather than a bullet, and the columns fill to
   whatever the width allows. */
.inv-list {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 0 clamp(22px, 2.8vw, 36px);
  margin: 20px 0 0;
  padding: 0;
  list-style: none;
}
@media (max-width: 900px) {
  .inv-list { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 620px) {
  .inv-list { grid-template-columns: 1fr; }
}
.inv-list li {
  padding: 14px 0 16px;
  border-top: 1px solid var(--line);
  font-size: clamp(16px, 1.4vw, 19px);
  font-weight: 700;
  line-height: 1.3;
  letter-spacing: -0.02em;
}
/* Set like the names on the board tile — same size, weight and tracking — so
   the two blocks of plain fact on this page read as one voice. Only two things
   differ, and both are about being a stacked block rather than list rows:
   `<address>` is italic by default and should not be, and four lines want a
   little more leading than two do. */
/* One voice for a fact and one for what qualifies it, at the same size
   wherever either appears on this page: the tiles' own headline, the names on
   the board tile, and the postal block all share the first; the line under a
   tile and the role under a name share the second. The product page's tiles
   carry a much larger `.stanza`, which is right for three words of claim and
   wrong for a company fact sitting beside two of them. */
.card-people li,
.postal,
.make-grid.info .stanza {
  font-size: 19px;
  font-weight: 700;
  letter-spacing: -0.02em;
}
.make-grid.info .stanza { line-height: 1.3; }
/* The wide tile carries sentences rather than a name: the leading a sentence
   wants, and two weights at one size. The mission is the claim and what
   follows is the reasoning behind it, which is a difference in emphasis rather
   than in importance — so weight separates them and size does not. */
.make-grid.info .wide .stanza { font-weight: 500; line-height: 1.5; }
.make-grid.info .wide .stanza strong { font-weight: 700; }
.make-grid.info .copy {
  margin-top: 9px;
  font-size: 14px;
  font-weight: 500;
  line-height: 1.5;
  letter-spacing: 0;
}
.postal {
  margin: 0;
  font-style: normal;
  line-height: 1.5;
}

/* Two columns of contact: the addresses you write to, and the one you post to.
   The email list drops to one column inside them, and the postal block takes
   the same ruled row the list rows have so the two sides start on one line. */
.contact-cols {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 0 clamp(22px, 2.8vw, 36px);
  margin-top: 20px;
}
.contact-cols .inv-list { grid-template-columns: 1fr; margin-top: 0; }
/* No rules in this band. The list rules them row by row, which read as three
   things against one and made the two sides look unrelated. Here the column
   gap does the separating and the rows just breathe. */
.contact-cols .inv-list li {
  padding: 0;
  border-top: 0;
}
.contact-cols .inv-list li + li { margin-top: 24px; }
@media (max-width: 700px) {
  .contact-cols { grid-template-columns: 1fr; }
}

/* An address is the actionable part of its row, so it takes the violet the
   rest of the site gives a link. */
.inv-list a { color: var(--violet-deep); }
.inv-list a:hover { text-decoration: underline; text-underline-offset: 3px; }
/* What someone sits on the board for, or what an address is for: a second line
   under the name, in the copy voice rather than the name's. */
.inv-note {
  display: block;
  margin-top: 3px;
  font-size: 14px;
  font-weight: 500;
  letter-spacing: 0;
  color: var(--muted);
}
.principle .num {
  font-family: var(--font-system);
  font-size: 13px;
  font-weight: 600;
  letter-spacing: 0.13em;
  color: var(--violet);
}
.principle h3 {
  font-size: clamp(20px, 2vw, 24px);
  font-weight: 800;
  letter-spacing: -0.025em;
  margin-top: 12px;
}
.principle p { margin-top: 8px; }

/* Quiet text link out to the Enterprise deep dives. Deliberately not a
   button: it sits under a section's cards and must not compete with the
   page's primary CTA. */
.more-link {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  margin-top: clamp(32px, 4vw, 44px);
  color: var(--violet-deep);
  font-size: 17px;
  font-weight: 700;
  letter-spacing: -0.01em;
  text-decoration: none;
}
.more-link:hover { text-decoration: underline; text-underline-offset: 3px; }
.more-link .arrow { transition: transform 0.18s ease; }
.more-link:hover .arrow { transform: translateX(3px); }

/* The same link set into a run of body text rather than standing on its own:
   it takes the surrounding size and sits on that text's baseline. */
.more-link.more-inline {
  /* Not inline-flex: a flex box inflates the line it sits in, which shows up
     as a gap above the sentence's last line. */
  display: inline;
  margin-top: 0;
  font-size: inherit;
}
/* The arrow keeps its hover shift: transform does not apply to an inline box,
   which is what it becomes once the link around it stops being a flex box. */
.more-link.more-inline .arrow { display: inline-block; }

/* Feature sections ------------------------------------------------------------ */

/* Conversation feature — headline column beside the live thread itself;
   the full shell (dock + sidebar) already appears in the hero, so this
   frame is just the room. */
.comm-feature {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: clamp(36px, 4.5vw, 68px);
  align-items: center;
}
.comm-feature .feature-text .copy { margin-top: 22px; max-width: 400px; }
.comm-wrap { min-width: 0; }
.comm-app { padding: 18px 26px; height: 632px; }
.comm-app .msgs { margin-top: 4px; }
.comm-frame .comm-app .msgs .agent-block { --mh: 420px; }
.comm-app .msgs > .chat-msg { --mh: 116px; }
.comm-app .pfp { width: 30px; height: 30px; font-size: 10.5px; }
.comm-app .agent-avatar { width: 30px; height: 30px; }
.comm-app .agent-avatar img { width: 17px; height: 17px; }
.comm-app .cm-name { font-size: 13.5px; }
.comm-app .cm-time { font-size: 10.5px; }
.comm-app .cm-text, .comm-app .agent-text, .comm-app .agent-done { font-size: 14.5px; }
.comm-app .cm-text, .comm-app .agent-text { max-width: 640px; }

/* Finished work arrives as an attachment on the agent message: a document
   thumbnail (mini cover) plus the file chip, as in the product. */
/* One connected card, as in the product: the cover preview and the file
   bar share a single border and radius. */
.attach {
  max-width: 400px;
  border: 1px solid var(--line);
  border-radius: 10px;
  background: #fff;
  box-shadow: 0 10px 26px rgba(40, 24, 70, 0.08);
  overflow: hidden;
}
.att-cover {
  background: linear-gradient(176deg, #fbf9fe 40%, #efe9f8);
  padding: 16px 16px 14px;
  min-height: 158px;
  display: flex;
  flex-direction: column;
  gap: 7px;
  overflow: hidden;
}
.att-mast { display: flex; align-items: center; justify-content: space-between; gap: 10px; }
.att-mast .att-logo {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  font-size: 10px;
  font-weight: 800;
  letter-spacing: -0.02em;
  color: var(--violet);
}
.att-mast .att-logo img { width: 13px; height: 13px; }
.att-meta {
  font-family: var(--font-system);
  font-size: 5.75px;
  font-weight: 600;
  letter-spacing: 0.15em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
.att-title {
  font-size: 13px;
  font-weight: 800;
  letter-spacing: -0.03em;
  line-height: 1.08;
}
.att-deck { font-size: 6.5px; line-height: 1.45; color: var(--muted); }
.att-body { font-size: 6px; line-height: 1.5; color: #3f3a49; }
.att-quote {
  border-left: 2.5px solid var(--violet);
  padding-left: 8px;
  font-size: 7.25px;
  font-weight: 800;
  letter-spacing: -0.01em;
}
.att-chip {
  display: flex;
  align-items: center;
  gap: 8px;
  border-top: 1px solid var(--line);
  background: #fff;
  padding: 8px 10px;
}
.att-chip .att-ic { flex: none; width: 12px; height: 12px; color: #8b8398; }
.att-chip .att-ic svg { width: 100%; height: 100%; }
.att-chip .att-name {
  font-family: var(--font-system);
  font-size: 9.5px;
  font-weight: 500;
  color: #3f3a49;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  min-width: 0;
}
.att-chip .att-latest {
  margin-left: auto;
  flex: none;
  display: inline-flex;
  align-items: center;
  gap: 4px;
  font-size: 9px;
  font-weight: 700;
  color: var(--muted);
}
.att-chip .att-latest::after {
  content: "";
  border-left: 3px solid transparent;
  border-right: 3px solid transparent;
  border-top: 3.5px solid #a49bb3;
}
.att-chip .att-kebab {
  flex: none;
  margin-left: 2px;
  color: #8b8398;
  font-size: 12px;
  line-height: 1;
  letter-spacing: 0.06em;
}
@keyframes cue-13 { 0%, 66% { opacity: 0; transform: translateY(6px); } 69%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(6px); } }
.an-13 { animation: cue-13 16s ease infinite; }

/* Emoji reactions collect on a finished message, as in the product */
.react-row { display: flex; gap: 6px; padding-top: 4px; }
.react {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  border: 1px solid var(--line);
  border-radius: 999px;
  background: #fff;
  padding: 3px 10px;
  font-size: 11.5px;
  font-weight: 700;
  color: #3f3a49;
}
.react.mine {
  border-color: rgba(132, 99, 206, 0.55);
  background: rgba(132, 99, 206, 0.08);
  color: var(--violet-deep);
}

/* Model orbit (Intelligence) */
/* The orbit's base layout is fluid — the svg, core and readable chips
   track the column — so it renders correctly at every width even with
   scripting unavailable. With scripting (html.js), widths above 900px
   upgrade to a fixed 1124x300 design space scaled to the column (the
   editor-canvas pattern), which keeps the chip-to-ellipse gaps exactly
   proportional; below 900px the fluid layout stays, holding the chips
   at a readable size instead of scaling the labels away. */
.orbit-stage {
  position: relative;
  max-width: 1124px;
  margin: clamp(44px, 6vw, 72px) auto 0;
  aspect-ratio: 1124 / 300;
  container-type: inline-size;
  overflow: hidden;
}
.orbit-canvas { position: absolute; inset: 0; }
.orbit-canvas svg { position: absolute; inset: 0; width: 100%; height: 100%; }
.orbit-stage .core {
  position: absolute;
  left: 50%; top: 50%;
  width: clamp(40px, 12vw, 64px);
  transform: translate(-50%, -50%);
}
.model-pill {
  position: absolute;
  padding: 6px 10px;
  border-radius: 999px;
  background: #fff;
  color: var(--ink);
  font-size: 11px;
  font-weight: 800;
  letter-spacing: -0.01em;
  white-space: nowrap;
  box-shadow: 0 6px 18px rgba(0, 0, 0, 0.35);
}
.mp-claude { left: 13.1%; top: 14%; }
.mp-gpt { right: 14%; top: 13.3%; }
.mp-gemini { left: 15.7%; bottom: 6%; }
.mp-grok { right: 16.2%; bottom: 5.3%; }
@media (min-width: 901px) {
  html.js .orbit-canvas {
    inset: auto;
    top: 0; left: 0;
    width: 1124px;
    height: 300px;
    transform-origin: 0 0;
    transform: scale(var(--osc, calc(100cqw / 1124px)));
  }
  html.js .orbit-stage .core { width: 104px; }
  html.js .model-pill {
    padding: 11px 18px;
    font-size: 15px;
    box-shadow: 0 10px 30px rgba(0, 0, 0, 0.35);
  }
  html.js .mp-claude { left: 147px; top: 42px; }
  html.js .mp-gpt { right: 157px; top: 40px; }
  html.js .mp-gemini { left: 177px; bottom: 18px; }
  html.js .mp-grok { right: 182px; bottom: 16px; }
}

/* Routing pulse: each step lights up the model chosen for it — Claude,
   then GPT, then Gemini, then Grok — while its spoke brightens. */
@keyframes route-pill {
  0%, 2.5% { background: #fff; color: var(--ink); box-shadow: 0 10px 30px rgba(0, 0, 0, 0.35); }
  5.5%, 21% { background: var(--violet); color: #fff; box-shadow: 0 12px 36px rgba(132, 99, 206, 0.6); }
  26.5%, 100% { background: #fff; color: var(--ink); box-shadow: 0 10px 30px rgba(0, 0, 0, 0.35); }
}
@keyframes route-spoke {
  0%, 2.5% { stroke: rgba(132, 99, 206, 0.55); }
  5.5%, 21% { stroke: #c9b8f2; }
  26.5%, 100% { stroke: rgba(132, 99, 206, 0.55); }
}
.orbit-stage .model-pill:nth-of-type(1) { animation: route-pill 14s ease infinite; }
.orbit-stage .model-pill:nth-of-type(2) { animation: route-pill 14s ease infinite; animation-delay: 3.5s; }
.orbit-stage .model-pill:nth-of-type(3) { animation: route-pill 14s ease infinite; animation-delay: 7s; }
.orbit-stage .model-pill:nth-of-type(4) { animation: route-pill 14s ease infinite; animation-delay: 10.5s; }
.orbit-stage .sp1 { animation: route-spoke 14s ease infinite; }
.orbit-stage .sp2 { animation: route-spoke 14s ease infinite; animation-delay: 3.5s; }
.orbit-stage .sp3 { animation: route-spoke 14s ease infinite; animation-delay: 7s; }
.orbit-stage .sp4 { animation: route-spoke 14s ease infinite; animation-delay: 10.5s; }
/* One breath per routing slot (3.5s = 14s / 4 models): the core swells as
   each model lights and settles before the handoff to the next. */
@keyframes core-pulse {
  0%, 100% { transform: translate(-50%, -54%) scale(1); }
  50% { transform: translate(-50%, -54%) scale(1.12); }
}
.orbit-stage .core { animation: core-pulse 3.5s ease-in-out infinite; }

/* Make tiles (Productivity) */
.make-grid {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 22px;
  margin-top: clamp(44px, 6vw, 72px);
}
/* One wide tile over a row of three. The legal name carries a sentence and the
   other three carry a line apiece, so the sentence takes the width and sets no
   ratio — it is as tall as it needs to be — while the three below are cut to
   the ID-1 card (85.6 × 53.98mm, what every bank card is cut to), which holds
   them to one height without a magic pixel value. */
/* Rows size to what is in them. The wide tile carries a sentence and takes a
   sentence's height — the same height it has on the Newsroom and the Blog,
   where it stands alone — while the three below take theirs from the card
   ratio. Equalising the two rows made the mission tile as tall as a row of
   cards for no reason but symmetry. */
.make-grid.info { grid-template-columns: repeat(3, 1fr); }
.make-grid.info .wide { grid-column: 1 / -1; }
/* `min-height` has to go before the ratio can mean anything. The product
   page's tiles carry a floor of 264px, and a box with both a floor and a ratio
   takes its *width* from that floor — 264 × 1.586 = 419px, against a 378px
   track, so the row overflowed and the tiles sat on top of each other. With no
   floor the width comes from the track and the ratio gives the height. */
.make-grid.info .make-card { min-height: 0; }
.make-grid.info .make-card:not(.wide) { aspect-ratio: 85.6 / 53.98; }
@media (max-width: 1060px) {
  .make-grid.info { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 700px) {
  .make-grid.info { grid-template-columns: 1fr; }
  .make-grid.info .make-card:not(.wide) { aspect-ratio: auto; }
}

.make-card {
  border-radius: var(--radius);
  padding: 30px 28px 26px;
  /* A grid item is `min-width: auto` by default, which is its content's
     minimum — so one unbreakable line (a name and a firm, say) widens the
     track past its share and pushes the row off the side of the page. */
  min-width: 0;
  min-height: 264px;
  display: flex;
  flex-direction: column;
}
.make-card .rule-label { margin-bottom: 22px; }
.make-card .stanza {
  font-size: clamp(22px, 2.2vw, 28px);
  line-height: 1.22;
  letter-spacing: -0.03em;
  font-weight: 800;
}
.make-card .rule {
  height: 3px;
  border-radius: 999px;
  margin-top: auto;
}
.make-card.doc { background: var(--mist); }
.make-card.doc .rule { background: var(--violet); }
.make-card.deck { background: #fff; border: 1px solid var(--line); }
.make-card.deck .rule { background: var(--ink); }
.make-card.sheet { background: var(--ink); color: #fff; }
.make-card.sheet .rule-label { color: rgba(255, 255, 255, 0.66); }
.make-card.sheet .rule { background: var(--green); }
.make-card.artifact { background: var(--violet); color: #fff; }
.make-card.artifact .rule-label { color: rgba(255, 255, 255, 0.78); }
.make-card.artifact .rule { background: #fff; }

/* A tile carrying a fact rather than a file kind gets a line under the stanza
   qualifying it, and on the two dark tiles that line has to lift off the
   ground it sits on. */
.make-card .copy { margin-top: 13px; }
/* The headquarters tile qualifies its stanza with a real postal address, so
   that line is an `<address>` rather than a paragraph. Browsers italicise the
   element by default, which is not the voice the tile's copy is set in. */
.make-card address.copy { font-style: normal; }
/* Names inside a tile, where it holds a short roster rather than one stanza.
   Sized to the list voice, not the stanza's, so a tile of two people does not
   out-shout the tiles beside it. */
.card-people { margin: 4px 0 0; padding: 0; list-style: none; }
/* Size, weight and tracking are shared with the mailing address, up beside
   `.postal`; a list row only needs its own leading and the gap between rows. */
.card-people li { line-height: 1.3; }
.card-people li + li { margin-top: 14px; }
.make-card.sheet .copy,
.make-card.artifact .copy { color: rgba(255, 255, 255, 0.72); }
.make-card.sheet .inv-note,
.make-card.artifact .inv-note { color: rgba(255, 255, 255, 0.72); }



/* Freedom ------------------------------------------------------------------------ */

.freedom-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 22px;
  margin-top: clamp(44px, 6vw, 72px);
}
.freedom-card {
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 30px 28px;
  display: flex;
  flex-direction: column;
  gap: 14px;
}
.freedom-card .rule-label { color: var(--violet-deep); }
.freedom-card h3 {
  font-size: clamp(22px, 2.2vw, 27px);
  letter-spacing: -0.028em;
  font-weight: 800;
}
.freedom-card h3 span { color: var(--muted); font-weight: 700; }

/* Trust ---------------------------------------------------------------------------- */

/* The ledger card: an excerpt of the agent_steps_ledger — one piece of
   work recorded end to end, in the operator's-own-database voice. Wide
   rows scroll inside the card, never the page. */
.ledger-card {
  margin-top: clamp(44px, 6vw, 72px);
  background: var(--ink);
  color: #fff;
  border-radius: 22px;
  padding: 22px 26px 16px;
  overflow-x: auto;
}
.ledger-head,
.ledger-rows,
.ledger-foot { min-width: 1500px; }
.ledger-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 18px;
  padding-bottom: 14px;
}
.lh-left {
  display: flex;
  flex-direction: column;
  gap: 7px;
}
/* Violet, lightened for small mono legibility on ink */
.lh-name {
  font-family: var(--font-system);
  font-size: 13px;
  font-weight: 600;
  letter-spacing: 0.08em;
  color: #a98ee0;
}
.lh-ask {
  font-family: var(--font-system);
  font-size: 11.5px;
  font-weight: 500;
  color: rgba(255, 255, 255, 0.62);
}
.lh-note {
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: rgba(255, 255, 255, 0.58);
}
/* Columns mirror the real export: step_num, tool_name, args, args_hint,
   status, summary, output, fingerprint, created_at. JSON cells truncate
   at their column edge, exactly as the Studio grid renders them. */
.lrow,
.lhead-row {
  display: grid;
  grid-template-columns: 34px 148px 200px minmax(180px, 1fr) 44px 230px 230px 80px 158px;
  gap: 16px;
  align-items: baseline;
  white-space: nowrap;
  font-family: var(--font-system);
}
.lhead-row {
  padding-bottom: 10px;
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.06em;
  color: rgba(255, 255, 255, 0.55);
}
.lrow {
  padding: 10px 0;
  border-top: 1px solid rgba(255, 255, 255, 0.09);
  font-size: 12px;
  font-weight: 500;
  line-height: 1.55;
}
/* Dim tones stay ≥4.5:1 on the ink card (WCAG AA for normal text). */
.lc-step { color: rgba(255, 255, 255, 0.52); }
.lc-tool { color: #a98ee0; font-weight: 600; }
.lc-hint { color: rgba(255, 255, 255, 0.85); overflow: hidden; text-overflow: ellipsis; }
.lc-args,
.lc-sum,
.lc-out { color: rgba(255, 255, 255, 0.66); overflow: hidden; text-overflow: ellipsis; }
.lc-status { color: rgba(255, 255, 255, 0.62); }
.lc-status .ok { color: var(--green); }
.lc-status .err { color: var(--coral); }
.lc-fp,
.lc-ts { color: rgba(255, 255, 255, 0.52); }
.lc-fp { overflow: hidden; text-overflow: ellipsis; }
.ledger-foot {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 18px;
  padding-top: 12px;
  border-top: 1px solid rgba(255, 255, 255, 0.09);
  font-family: var(--font-system);
  font-size: 11px;
  font-weight: 500;
  letter-spacing: 0.04em;
  color: rgba(255, 255, 255, 0.55);
}

.ledger-caption { margin-top: 14px; font-size: 14.5px; color: #5b5567; }
/* A caption hugs the figure it captions; following a list it is a remark on
   the section instead, and needs the room to read as one. */
.rely-list + .ledger-caption { margin-top: clamp(24px, 3vw, 32px); }

/* The lock-in argument. The frame and the violet rule carry the emphasis, so
   the type only has to sit a step above the copy around it. */
.freedom-note {
  margin-top: clamp(28px, 3.4vw, 40px);
  padding: 24px 28px;
  background: #fff;
  border: 1px solid var(--line);
  border-left: 3px solid var(--violet);
  border-radius: var(--radius);
  font-size: clamp(18px, 1.7vw, 21px);
  font-weight: 500;
  line-height: 1.45;
  letter-spacing: -0.02em;
  color: var(--ink);
}
/* Under the hero the note is the page's thesis, not a section's footnote:
   wider measure, more air above it, and the call to action reads off it. */
.hero-note {
  max-width: 980px;
  margin-top: clamp(40px, 5vw, 60px);
}
.hero-cta { margin-top: clamp(28px, 3.4vw, 38px); }

/* The line that hands the hero's lede to the tick list under it: the freedoms
   it names take the skim weight, the clause introducing the list does not. */
.hero-lede b { font-weight: 800; color: var(--ink); }

/* The three freedoms, one line each. The tick list further down the page
   rules its rows off from one another; a hero wants air instead, so the
   claim leads in ink and its consequence trails behind an em dash in grey. */
.hero-list {
  display: grid;
  gap: clamp(10px, 1.1vw, 14px);
  max-width: 900px;
  margin-top: clamp(28px, 3.2vw, 38px);
}
.hero-list li {
  position: relative;
  padding-left: 32px;
  font-size: clamp(17px, 1.7vw, 21px);
  line-height: 1.42;
  letter-spacing: -0.02em;
  font-weight: 800;
  text-wrap: pretty;
}
.hero-list li::before {
  content: "";
  position: absolute;
  left: 0;
  top: 0.33em;
  width: 16px;
  height: 16px;
  background: var(--tick) center / contain no-repeat;
}
.hero-list li span { font-weight: 500; color: var(--muted); }

/* A quotation, not another callout: the bordered note above it already owns
   that treatment, so this reads as a quoted line — open quote in violet, no
   box around it. */
.pull-quote {
  position: relative;
  max-width: 900px;
  margin-top: clamp(34px, 4.2vw, 48px);
  padding-left: clamp(30px, 3.6vw, 46px);
  font-size: clamp(19px, 2.1vw, 26px);
  line-height: 1.34;
  letter-spacing: -0.028em;
  font-weight: 700;
  text-wrap: pretty;
}
.pull-quote + .pull-quote { margin-top: clamp(24px, 2.8vw, 32px); }
.pull-quote::before {
  content: "\201C";
  position: absolute;
  left: 0;
  top: -0.06em;
  font-size: 2.4em;
  line-height: 1;
  color: var(--violet);
}

/* Customer voices: quotations with no card around any of them — the violet
   open quote and the portrait carry the attribution. The type is quiet, not
   the display treatment .pull-quote takes: these run several sentences each,
   and set larger they read as marketing rather than as someone talking.
   Portraits are circular and cover-cropped, so a supplied headshot lands
   correctly at any aspect ratio. */
.voices {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  column-gap: clamp(44px, 5.2vw, 76px);
  row-gap: 0;
  margin-top: clamp(40px, 4.6vw, 58px);
}
/* Ruled rather than boxed, the construct the tick lists take: quotations
   this long need something marking where one ends and the next begins, and
   a card around each one gives six near-identical white rectangles. Rows
   stretch to a common height, so a row's two rules meet across the gap. */
.voice {
  padding: clamp(26px, 3vw, 34px) 0;
  border-bottom: 1px solid var(--line);
}
/* The quote takes the smaller-text size the pricing notes use. The
   attribution keeps its own scale above it: the violet open quote and the
   portrait are what mark the words as quoted, so the name is free to be the
   heavier of the two. */
.voice-quote {
  position: relative;
  padding-left: clamp(26px, 2.6vw, 34px);
  font-size: 15px;
  line-height: 1.55;
  letter-spacing: -0.012em;
  font-weight: 400;
  text-wrap: pretty;
}
.voice-quote::before {
  content: "\201C";
  position: absolute;
  left: 0;
  top: -0.06em;
  font-size: 2.6em;
  line-height: 1;
  color: var(--violet);
}
/* Sits directly under the quote it attributes. Pinning it to the foot of the
   cell would level the citations across a row, at the price of a gap under
   every quote shorter than the one beside it — and the rules already carry
   that alignment. Left over space falls at the foot of the cell, where it
   reads as a paragraph ending rather than as a hole. */
.voice-cite {
  display: flex;
  align-items: center;
  gap: 13px;
  margin-top: clamp(16px, 1.8vw, 20px);
  padding-left: clamp(26px, 2.6vw, 34px);
  font-style: normal;
}
/* The portrait carries its own fallback: initials sit under the photo, and
   the image is alt="" so a missing file collapses silently instead of
   drawing a broken-image glyph over them. The speaker's name is already in
   .voice-name beside it, which is what makes the empty alt correct. */
.voice-portrait {
  position: relative;
  width: 50px;
  height: 50px;
  flex: none;
  border-radius: 50%;
  background: var(--violet);
}
.voice-initials {
  position: absolute;
  inset: 0;
  display: grid;
  place-items: center;
  font-size: 15px;
  font-weight: 700;
  letter-spacing: 0.02em;
  color: #fff;
}
.voice-portrait img {
  position: relative;
  z-index: 1;
  width: 100%;
  height: 100%;
  border-radius: 50%;
  object-fit: cover;
}
.voice-name {
  display: block;
  font-weight: 700;
  font-size: 15.5px;
  letter-spacing: -0.012em;
}
.voice-role {
  display: block;
  margin-top: 2px;
  font-size: 13.8px;
  color: var(--muted);
}

@media (max-width: 900px) {
  .voices { grid-template-columns: minmax(0, 1fr); }
  .voice { padding: 24px 0; }
}

/* Architectural footnote inside a freedom card: secondary to the card's
   own copy, but still body text rather than fine print. */
.freedom-card .small { font-size: 15.5px; color: #5b5567; }

.trust-points {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  --colpad: clamp(22px, 2.8vw, 36px);
  column-gap: 0;
  row-gap: clamp(36px, 5vw, 52px);
  margin-top: clamp(44px, 6vw, 64px);
}
/* Same brand-guide column rules as .principles. */
.trust-points > div {
  padding-inline: var(--colpad);
  border-left: 1px solid var(--line);
}
.trust-points > div:nth-child(3n + 1) { border-left: 0; padding-left: 0; }
.trust-points h3 {
  font-size: 21px;
  font-weight: 800;
  letter-spacing: -0.02em;
  margin-bottom: 8px;
}

/* Attestations closing the trust section: a struck seal per attestation, then
   the name under it. The seals are typographic — the ring, the perforation and
   the stacked lockup do the work, so they hold up at 84px and carry the
   section's own palette instead of a row of foreign badge art. */
.compliance {
  margin-top: clamp(40px, 5vw, 56px);
  padding-top: clamp(26px, 3.2vw, 34px);
  border-top: 1px solid var(--line);
}
.cert-grid {
  display: flex;
  flex-wrap: wrap;
  gap: clamp(26px, 3.4vw, 46px);
  margin-top: clamp(20px, 2.4vw, 26px);
}
.cert {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 13px;
  width: 136px;
}
.cert-name {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  font-size: 14.5px;
  font-weight: 700;
  letter-spacing: -0.012em;
}
.cert-name::before {
  content: "";
  width: 13px;
  height: 13px;
  flex: none;
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%238463ce' stroke-width='3.4' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M4 12.5l5.5 5.5L20 6.5'/%3E%3C/svg%3E") center / contain no-repeat;
}

/* Issuer marks arrive at whatever proportion their issuer drew them, so the
   frame — not the artwork — is what lines the row up. */
.cert-mark {
  display: flex;
  align-items: center;
  justify-content: center;
  height: clamp(78px, 6.8vw, 92px);
}
/* Both dimensions stay auto and both are capped: a percentage height would let
   the base img max-width cap the width without touching the height, which
   flattens a round seal into an ellipse. */
.cert-mark img {
  flex: none;
  max-height: 100%;
  max-width: 100%;
  width: auto;
  height: auto;
}

/* Closing --------------------------------------------------------------------------- */

.closing {
  position: relative;
  overflow: hidden;
  text-align: left;
  isolation: isolate;
}
.closing::before {
  content: "";
  position: absolute;
  width: 720px; height: 720px;
  right: -240px; top: -260px;
  border-radius: 50%;
  background: radial-gradient(
    circle,
    rgba(255, 255, 255, 0.16) 0,
    rgba(255, 255, 255, 0.05) 45%,
    rgba(255, 255, 255, 0) 70%
  );
  z-index: -1;
}
.closing::after {
  content: "";
  position: absolute;
  width: 460px; height: 460px;
  right: -60px; top: -90px;
  border: 1px solid rgba(255, 255, 255, 0.28);
  border-radius: 50%;
  z-index: -1;
}
.closing .display { max-width: 900px; }
.closing .copy { margin-top: 26px; }
.closing .cta-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 22px;
  margin-top: 46px;
}
.closing .domain {
  font-family: var(--font-system);
  font-size: 13px;
  font-weight: 600;
  letter-spacing: 0.18em;
  color: rgba(255, 255, 255, 0.85);
}

/* Catalog ---------------------------------------------------------------------------- */

/* The Newsroom and the Blog: one list of published packages, filtered, paged,
   and each card previewing the document it links to. Built by `catalog.js`
   from a collection's `index.json`, so nothing here is written per page. */

.catalog { margin-top: clamp(34px, 4vw, 48px); }

.cat-page .catalog { margin-top: 0; }
/* These pages are a title, a mission and a list. The title takes the statement
   scale every page-top heading takes; all this rule owns is the space under
   it, which is what places the mission tile rather than the tile's own
   margin. */
.cat-head { margin: 0 0 clamp(24px, 2.8vw, 34px); }
.cat-page .make-grid { margin-top: 0; }
.cat-page .make-grid + .catalog { margin-top: clamp(34px, 4vw, 48px); }

.cat-controls {
  display: flex;
  flex-direction: column;
  gap: 14px;
  padding-bottom: 24px;
  border-bottom: 1px solid var(--line);
}
/* A facet is its name and its values on one line, wrapping together — the
   label keeps a column so the rows line up under each other. */
.cat-facet { display: flex; flex-wrap: wrap; align-items: center; gap: 10px 16px; }
.cf-label {
  min-width: 72px;
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--muted);
}
.cf-chips { display: flex; flex-wrap: wrap; gap: 8px; }
.cf-chip {
  padding: 8px 15px;
  font: 500 14px/1 var(--font-voice);
  color: var(--muted);
  background: var(--white);
  border: 1px solid var(--line);
  border-radius: 999px;
  cursor: pointer;
  transition: color 0.15s ease, border-color 0.15s ease, background 0.15s ease;
}
.cf-chip:hover { color: var(--ink); border-color: #c9c0da; }
.cf-chip.on { color: #fff; background: var(--ink); border-color: var(--ink); }

.cat-count {
  margin: 20px 0 0;
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--muted);
}
.cat-empty { margin: 20px 0 0; font-size: 17px; color: var(--muted); }

/* `min(300px, 100%)` rather than a bare 300px: on a phone narrow enough that
   the column would not fit, a fixed minimum track is wider than its container
   and pushes the whole page sideways. */
.cat-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(300px, 100%), 1fr));
  gap: clamp(22px, 2.6vw, 32px);
  margin: 22px 0 0;
  padding: 0;
  list-style: none;
}

.cat-card { animation: cat-in 0.4s ease both; }
@keyframes cat-in {
  from { opacity: 0; transform: translateY(10px); }
  to { opacity: 1; transform: none; }
}

/* The card is an envelope and the preview is the letter in it: a band of
   Violet Mist at the top, the document full-bleed across the middle on its own
   paper, and the metadata below on mist again. The document is the only white
   in the card, which is what makes it read as something tucked inside rather
   than printed on. */
.cc-link {
  display: flex;
  flex-direction: column;
  height: 100%;
  /* One inset for the whole interior: mist above the letter and down both
     sides of it, and the metadata below starting on the same line the letter's
     edge does. The letter is held rather than mounted, which is the difference
     between an envelope and a panel. */
  padding: 22px 16px 0;
  color: inherit;
  background: var(--mist);
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  overflow: hidden;
  transition: border-color 0.18s ease, transform 0.18s ease, box-shadow 0.18s ease;
}
.cc-link:hover {
  border-color: #c9c0da;
  transform: translateY(-2px);
  box-shadow: 0 14px 34px rgba(13, 11, 18, 0.09);
}

/* The preview is the document itself, at the width it was laid out for and
   scaled by `catalog.js` to whatever width the card ended up — so the box
   shows the head of a real page rather than a picture of one. Clicks pass
   through it to the card's link. */
/* No rule along the top. A package lays its sheet on a page surround of its
   own — the announcement's is #E9E5EE under 24px of body padding, a hair off
   our own mist — so the first slice of every preview is that surround rather
   than the document. A line there cuts it off as a separate grey bar; without
   one it joins the strip above and reads as the envelope the letter sits in.
   The rule underneath stays: that edge is the letter meeting the mist. */
.cc-preview {
  position: relative;
  aspect-ratio: 8.5 / 5.6;
  overflow: hidden;
  background: var(--paper);
  border-bottom: 1px solid var(--line);
}
.cc-preview iframe {
  position: absolute;
  inset: 0;
  width: 816px;
  height: 1056px;
  border: 0;
  transform-origin: 0 0;
  pointer-events: none;
  background: var(--paper);
}
/* Under the frame, and all there is when a preview cannot be built: the
   package named, in the voice of the thing it stands for. */
.cc-stand {
  position: absolute;
  inset: 0;
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  gap: 9px;
  padding: 22px;
}
.cc-stand-kind {
  font-family: var(--font-system);
  font-size: 9px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--violet-deep);
}
.cc-stand-title {
  font-size: 19px;
  font-weight: 800;
  line-height: 1.16;
  letter-spacing: -0.024em;
}
.cc-preview.has-preview .cc-stand { display: none; }

/* No horizontal padding of its own — the card's inset is the one that lines
   the text up with the letter above it. */
.cc-body {
  display: flex;
  flex: 1;
  flex-direction: column;
  gap: 10px;
  padding: 20px 0 22px;
}
.cc-meta { display: flex; flex-wrap: wrap; align-items: center; gap: 8px 12px; margin: 0; }
/* White, not mist: the card's own field is mist now, and a mist chip on it
   would be a label with no edge. */
.cc-cat {
  padding: 5px 11px;
  font-family: var(--font-system);
  font-size: 9px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--violet-deep);
  background: var(--white);
  border-radius: 999px;
}
.cc-date { font-size: 13px; color: var(--muted); }
.cc-title { margin: 0; font-size: 20px; font-weight: 800; line-height: 1.2; letter-spacing: -0.025em; }
.cc-summary { margin: 0; font-size: 15px; line-height: 1.55; color: var(--muted); }
/* `margin-block-start: auto` pins the byline to the bottom, so cards of
   different summary lengths still rule off at the same place. */
.cc-foot {
  display: flex;
  justify-content: space-between;
  gap: 12px;
  margin: auto 0 0;
  padding-top: 13px;
  border-top: 1px solid rgba(93, 61, 167, 0.16);
  font-size: 12px;
  color: var(--muted);
}
.cat-pager {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: center;
  gap: 8px;
  margin-top: clamp(30px, 4vw, 44px);
}
.cp-numbers { display: flex; flex-wrap: wrap; gap: 6px; }
.cp-step,
.cp-num {
  min-width: 40px;
  padding: 9px 15px;
  font: 600 14px/1 var(--font-voice);
  color: var(--muted);
  background: var(--white);
  border: 1px solid var(--line);
  border-radius: 999px;
  cursor: pointer;
  transition: color 0.15s ease, border-color 0.15s ease, background 0.15s ease;
}
.cp-step:hover:not([disabled]),
.cp-num:hover { color: var(--ink); border-color: #c9c0da; }
.cp-step[disabled] { opacity: 0.4; cursor: default; }
.cp-num.on { color: #fff; background: var(--ink); border-color: var(--ink); }

@media (prefers-reduced-motion: reduce) {
  .cat-card { animation: none; }
  .cc-link:hover { transform: none; }
}

/* Footer ---------------------------------------------------------------------------- */

.site-footer { padding-block: clamp(48px, 6vw, 72px); }
.site-footer .top {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: 24px;
}
.site-footer .logo img { width: 168px; height: auto; }
.site-footer .hairline { margin-block: 34px; }
.site-footer .bottom {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: 14px 24px;
}
.site-footer .bottom a:hover { color: #fff; }

/* Link band: one column per group, each headed by what it collects. The
   columns divide the width evenly, so a group added later takes a share of it
   rather than a place in a fixed grid. */
.site-footer .links {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
  gap: 36px 40px;
}
.footer-col { display: flex; flex-direction: column; align-items: flex-start; }
.fc-head {
  margin-bottom: 18px;
  font-size: 15px;
  font-weight: 800;
  letter-spacing: -0.01em;
  color: #fff;
}
.footer-col a {
  font-size: 15px;
  font-weight: 500;
  line-height: 1.5;
  color: rgba(255, 255, 255, 0.62);
  transition: color 0.15s ease;
}
.footer-col a + a { margin-top: 12px; }
.footer-col a:hover { color: #fff; }

/* App-window illustrations ------------------------------------------------------------
   Stylized recreations of real product screens (home, rooms, split artifact
   view, editors, library). Fictional content only — never real user data. */

.app-frame {
  border: 1px solid var(--line);
  border-radius: 22px;
  background: #fff;
  box-shadow: 0 32px 90px rgba(40, 24, 70, 0.14);
  overflow: hidden;
}
.app-frame .chrome {
  position: relative;
  display: flex;
  align-items: center;
  padding: 13px 16px;
  border-bottom: 1px solid var(--line);
  background: var(--paper);
}
.traffic { display: flex; gap: 7px; }
.traffic span { width: 11px; height: 11px; border-radius: 50%; }
.traffic span:nth-child(1) { background: #ff5f57; }
.traffic span:nth-child(2) { background: #febc2e; }
.traffic span:nth-child(3) { background: #28c840; }

/* Every frame is a browser window onto the product, so the chrome carries
   the domain rather than a per-scene title. */
.chrome .tab {
  position: absolute;
  left: 50%;
  transform: translateX(-50%);
  font-family: var(--font-system);
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
/* Hero: dock + sidebar + room + artifact split view */
.hero-visual { margin-top: clamp(56px, 7vw, 88px); }
.hero-app .body {
  display: grid;
  /* The sidebar holds its longest real channel name plus a mention badge;
     at 204px the longest row already touched the edge. */
  grid-template-columns: 56px 228px minmax(0, 1fr) minmax(0, 1.06fr);
  min-height: 520px;
}

/* A room frame shown for what it produces rather than for the app around it:
   no dock, no channel list, just the thread and the artifact it writes. Its
   panel matches the room's padding so the page card's top lands on the room
   rule and its bottom on the composer. */
.hero-app.no-shell .body { grid-template-columns: minmax(0, 1fr) minmax(0, 1.06fr); }


/* Far-left navigation dock, as in the product: icon + label, avatar at
   the bottom. */
.app-dock {
  border-right: 1px solid var(--line);
  background: var(--paper);
  padding: 14px 4px 12px;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 13px;
}
.dock-collapse { color: var(--muted); margin-bottom: 3px; }
.dock-collapse svg { width: 16px; height: 16px; }
.dock-item {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 3px;
  color: var(--muted);
}
.dock-item svg { width: 16px; height: 16px; }
.dock-item .di {
  position: relative;
  display: flex;
  align-items: center;
  justify-content: center;
  width: 30px; height: 24px;
  border-radius: 8px;
}
.dock-item span { font-size: 7.5px; font-weight: 700; }
.dock-item.on { color: var(--ink); }
.dock-item.on .di { background: #eceaf1; }
/* Unread dot rides the top-right corner of the icon, as in the product */
.dock-item.alert-dot .di::after {
  content: "";
  position: absolute;
  top: -2px;
  right: 0;
  width: 6px; height: 6px;
  border-radius: 50%;
  background: var(--unread);
}
.dock-avatar {
  margin-top: auto;
  position: relative;
  width: 24px; height: 24px;
  border-radius: 50%;
  background: #b0628c;
  color: #fff;
  font-size: 8.5px;
  font-weight: 800;
  display: flex;
  align-items: center;
  justify-content: center;
}
.dock-avatar::after {
  content: "";
  position: absolute;
  right: -1px; bottom: -1px;
  width: 7px; height: 7px;
  border-radius: 50%;
  background: var(--green);
  border: 1.5px solid var(--paper);
}

.app-side {
  border-right: 1px solid var(--line);
  background: var(--paper);
  padding: 14px 12px 16px;
  display: flex;
  flex-direction: column;
  gap: 12px;
}

/* Sidebar top tabs: Inbox pill + threads / channels / DMs / new */
.side-tabs { display: flex; align-items: center; gap: 4px; min-width: 0; }
.side-tabs .stab {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 4px 9px;
  border-radius: 8px;
  background: #eceaf2;
  font-size: 10px;
  font-weight: 700;
  color: var(--ink);
  white-space: nowrap;
}
.side-tabs .sicon {
  width: 21px; height: 21px;
  flex: none;
  border-radius: 6px;
  display: flex;
  align-items: center;
  justify-content: center;
  color: var(--muted);
  font-size: 10.5px;
  font-weight: 700;
}
.side-tabs .sicon svg { width: 12px; height: 12px; }
.side-tabs .sicon.plus { font-size: 13.5px; font-weight: 800; }
.side-tabs .sicon { position: relative; }
.side-tabs .sicon .tdot {
  position: absolute;
  top: 1px;
  right: 1px;
  width: 4.5px; height: 4.5px;
  border-radius: 50%;
  background: var(--unread);
}
.side-tabs .stab { position: relative; }
.side-tabs .stab .tdot {
  position: absolute;
  top: -2px;
  right: -2px;
  width: 5px; height: 5px;
  border-radius: 50%;
  background: var(--unread);
}
.side-tabs .sp { flex: 1; }
.app-side .search {
  height: 30px;
  flex: none;
  border: 1px solid var(--line);
  border-radius: 8px;
  background: #fff;
  display: flex;
  align-items: center;
  gap: 6px;
  padding: 0 9px;
  font-size: 10.5px;
  font-weight: 600;
  color: #8f879c;
  white-space: nowrap;
  overflow: hidden;
}
.slens {
  width: 7px; height: 7px;
  flex: none;
  border: 1.4px solid #a49bb3;
  border-radius: 50%;
  position: relative;
}
.slens::after {
  content: "";
  position: absolute;
  width: 4px; height: 1.4px;
  background: #a49bb3;
  border-radius: 2px;
  right: -3.5px;
  bottom: -1px;
  transform: rotate(45deg);
}
.app-side .group-label {
  display: flex;
  align-items: center;
  gap: 6px;
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
  margin-top: 6px;
}
.app-side .group-label::before {
  content: "";
  width: 4.5px; height: 4.5px;
  border-right: 1.4px solid #a49bb3;
  border-bottom: 1.4px solid #a49bb3;
  transform: rotate(45deg) translateY(-1px);
}
.chan {
  display: flex;
  align-items: center;
  gap: 9px;
  padding: 7px 9px;
  border-radius: 8px;
  font-size: 13px;
  font-weight: 600;
  color: #3f3a49;
  white-space: nowrap;
}
.chan .glyph {
  width: 20px; height: 20px;
  flex: none;
  border-radius: 50%;
  background: #fff;
  border: 1px solid var(--line);
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 9px;
  font-weight: 800;
  color: var(--muted);
}
.chan.active { background: #eceaf1; color: var(--ink); }
/* Sidebar rows for people and group DMs: round avatar instead of # tile */
.chan .glyph.av { border: 0; color: #fff; font-size: 7px; }
/* Private channels and threads carry the product's lock / threads icons */
.chan .glyph svg { width: 10px; height: 10px; }
/* Unread rows read bold ink with the product's blue dot; rows where you
   were mentioned carry a blue "@ n" badge instead. */
.chan.unread { color: var(--ink); font-weight: 800; }
/* A row carrying a badge gives the name up before it gives up the count:
   the label truncates so the badge always lands inside the sidebar. */
.chan .cn { min-width: 0; overflow: hidden; text-overflow: ellipsis; }
.chan .badge {
  margin-left: auto;
  flex: none;
  min-width: 16px;
  height: 16px;
  padding: 0 6px;
  border-radius: 999px;
  background: var(--unread);
  color: #fff;
  font-size: 8.5px;
  font-weight: 800;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 1px;
}


.app-chat {
  display: flex;
  flex-direction: column;
  padding: 18px 22px;
  gap: 14px;
  min-width: 0;
}
.room-head {
  position: relative;
  display: flex;
  align-items: baseline;
  gap: 10px;
  padding-bottom: 12px;
  border-bottom: 1px solid var(--line);
}
.room-head .name { font-weight: 800; font-size: 15px; }
.room-head .meta { font-size: 12px; color: var(--muted); }
/* The frame keeps a FIXED height while messages arrive: the chat column is
   pinned, and the bottom-anchored stack pushes history up inside it. */
.hero-app .app-chat { height: 656px; }

/* The message stack is bottom-anchored like real chat: column-reverse with
   newest-first markup keeps the bottom pinned even once the canvas is full,
   so arrivals push the oldest messages up under the clipped top. */
.app-chat .msgs {
  display: flex;
  flex-direction: column-reverse;
  flex: 1;
  min-height: 0;
  overflow: hidden;
  /* Clip at the TOP of the room rule — the column gap plus the rule's own
     1px — so history disappears beneath the line itself rather than a
     pixel after it. .room-head is positioned so the rule paints on top. */
  margin-top: -15px;
}
/* Never squish messages to fit — let the stack overflow past the clipped
   top edge instead, so a full canvas pushes the oldest messages out. */
.app-chat .msgs > * { flex: none; }
.app-chat .msgs > * + * { margin-bottom: 12px; }
/* Arriving items reveal bottom-up inside their growing box, so a new
   message rides in whole from the composer edge — a scroll, not an
   accordion — while the stack above is pushed toward the clipped top. */
.app-chat .msgs > [class*="an-"],
.app-chat .msgs > [class*="lr-"] {
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  overflow: hidden;
}
.chat-msg .replies { margin-top: 4px; }

/* Historical context, as in the product: an older message with its reply
   thread, and an AI catch-up summary line. */
.ai-note {
  display: flex;
  align-items: flex-start;
  gap: 8px;
  font-size: 11.5px;
  line-height: 1.5;
  color: var(--muted);
  padding-left: 2px;
}
.ai-note .spark { flex: none; width: 13px; height: 13px; margin-top: 2px; color: var(--violet); }
.ai-note .spark svg { width: 100%; height: 100%; }

/* Arrival choreography: same cue timings as the fades, plus max-height
   growth so each message physically pushes the stack up. */
@keyframes gc-1 { 0%, 5% { max-height: 0; opacity: 0; margin-bottom: 0; } 8%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes gc-2 { 0%, 14% { max-height: 0; opacity: 0; margin-bottom: 0; } 17%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes gc-3 { 0%, 19% { max-height: 0; opacity: 0; margin-bottom: 0; } 22%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes gc-4 { 0%, 27% { max-height: 0; opacity: 0; margin-bottom: 0; } 30%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes gc-5 { 0%, 37% { max-height: 0; opacity: 0; margin-bottom: 0; } 40%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes gc-7 { 0%, 48% { max-height: 0; opacity: 0; margin-bottom: 0; } 51%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes gc-8 { 0%, 57% { max-height: 0; opacity: 0; margin-bottom: 0; } 60%, 87% { max-height: var(--mh, 100px); opacity: 1; margin-bottom: 12px; } 93%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.app-chat .msgs .an-1 { animation-name: gc-1; }
.app-chat .msgs .an-2 { animation-name: gc-2; }
.app-chat .msgs .an-3 { animation-name: gc-3; }
.app-chat .msgs .an-4 { animation-name: gc-4; }
.app-chat .msgs .an-5 { animation-name: gc-5; }
.app-chat .msgs .an-7 { animation-name: gc-7; }
.app-chat .msgs .an-8 { animation-name: gc-8; }
.app-chat .msgs .agent-block { --mh: 150px; }
/* Diary updates are multi-item, the way they are in the room, so both
   sides of that thread need more headroom than a one-line ask. */
.sc-diary .msgs > * { --mh: 122px; }
.sc-diary .msgs .agent-block { --mh: 168px; }
.replies {
  align-self: flex-start;
  display: inline-flex;
  align-items: center;
  gap: 8px;
}
.replies b { font-size: 12px; font-weight: 800; letter-spacing: -0.01em; color: var(--ink); }
.replies em { font-size: 11.5px; font-style: normal; color: var(--muted); }
.rfaces { display: inline-flex; }
.rfaces i {
  width: 18px; height: 18px;
  margin-left: -6px;
  border-radius: 50%;
  border: 1.5px solid #fff;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  font-size: 6.5px;
  font-style: normal;
  font-weight: 800;
  color: #fff;
}
.rfaces i:first-child { margin-left: 0; }
.rfaces i.more { background: #e6e2ee; color: var(--muted); }
/* Agent presence, as in the product: avatar + name header, first-person
   status line, three thinking dots, Stop chip while generating. */
.agent-block { display: flex; flex-direction: column; gap: 7px; }
.agent-avatar {
  width: 26px; height: 26px;
  flex: none;
  border: 1px solid var(--line);
  border-radius: 50%;
  background: #fff;
  display: flex;
  align-items: center;
  justify-content: center;
}
.agent-avatar img { width: 15px; height: 15px; }
.stop-chip {
  font-size: 10.5px;
  font-weight: 700;
  color: #b43e2b;
  border: 1px solid rgba(255, 124, 99, 0.55);
  background: rgba(255, 124, 99, 0.08);
  border-radius: 999px;
  padding: 3px 10px;
}
.agent-text { font-size: 13.5px; line-height: 1.45; }
.think-dots { display: flex; gap: 5px; padding: 3px 0 0 2px; }
.think-dots span {
  width: 7px; height: 7px;
  border-radius: 50%;
  background: var(--violet);
  animation: think 1.3s ease-in-out infinite;
}
.think-dots span:nth-child(2) { animation-delay: 0.18s; }
.think-dots span:nth-child(3) { animation-delay: 0.36s; }
@keyframes think {
  0%, 60%, 100% { opacity: 0.35; transform: scale(0.8); }
  30% { opacity: 1; transform: scale(1); }
}

/* Agent wrap-up: while the work runs the tail shows thinking dots (plus the
   Stop chip in the header); the moment the work lands, both give way to a
   plain "Done." line — exactly the beat the product ends on. */
.agent-tail { position: relative; min-height: 20px; }
.agent-tail .think-dots { position: absolute; left: 2px; top: 5px; padding: 0; }
.agent-done {
  position: absolute;
  left: 0; top: 0;
  font-size: 13.5px;
  line-height: 1.45;
  opacity: 0;
}
.composer {
  display: flex;
  align-items: center;
  gap: 10px;
  border: 1px solid var(--line);
  border-radius: 14px;
  padding: 10px 12px;
  background: #fff;
}
.composer .hint { font-size: 13px; color: var(--muted); flex: 1; white-space: nowrap; overflow: hidden; }
.composer .auto {
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.1em;
  color: var(--muted);
  border: 1px solid var(--line);
  border-radius: 999px;
  padding: 4px 8px;
  white-space: nowrap;
}
.composer .send {
  width: 26px; height: 26px;
  flex: none;
  border-radius: 50%;
  background: var(--violet);
  color: #fff;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 13px;
  font-weight: 800;
}

.app-panel {
  border-left: 1px solid var(--line);
  background: #f4f1f9;
  padding: 22px;
  display: flex;
  flex-direction: column;
  gap: 14px;
  min-width: 0;
}
.app-panel .panel-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  min-height: 22px;
  gap: 10px;
}
.app-panel .panel-head .file {
  display: flex;
  min-width: 0;
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.06em;
  color: var(--muted);
  white-space: nowrap;
}
/* Truncate the stem, never the extension — the file type is the part that
   tells you what you are looking at. */
/* The trailing letter-space after the mono ellipsis reads as a word gap
   before the extension; pull it back. */
.app-panel .panel-head .file .fstem { min-width: 0; overflow: hidden; text-overflow: ellipsis; margin-right: -1px; }
.app-panel .panel-head .file .fext { flex: none; }

/* Version ticks up as each diary update lands */
.version { position: relative; flex: none; width: 44px; height: 22px; margin-left: auto; }
.version .v {
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.08em;
  color: var(--violet-deep);
  border: 1px solid rgba(132, 99, 206, 0.45);
  background: rgba(132, 99, 206, 0.08);
  border-radius: 999px;
  opacity: 0;
}
.version .v1 { opacity: 1; animation: ver-1 16s linear infinite; }
.version .v2 { animation: ver-2 16s linear infinite; }
.version .v3 { animation: ver-3 16s linear infinite; }
.version .v4 { animation: ver-4 16s linear infinite; }
@keyframes ver-1 { 0%, 22.5% { opacity: 1; } 23.5%, 92.5% { opacity: 0; } 93.5%, 100% { opacity: 1; } }
@keyframes ver-2 { 0%, 22.5% { opacity: 0; } 23.5%, 45.5% { opacity: 1; } 46.5%, 100% { opacity: 0; } }
@keyframes ver-3 { 0%, 45.5% { opacity: 0; } 46.5%, 64.5% { opacity: 1; } 65.5%, 100% { opacity: 0; } }
@keyframes ver-4 { 0%, 64.5% { opacity: 0; } 65.5%, 92.5% { opacity: 1; } 93.5%, 100% { opacity: 0; } }
.app-panel .panel-head .state {
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--violet-deep);
  border: 1px solid rgba(132, 99, 206, 0.45);
  background: rgba(132, 99, 206, 0.1);
  border-radius: 999px;
  padding: 4px 9px;
  white-space: nowrap;
}

/* Scene choreography: one 16s clock, elements enter on their own cue,
   hold, then the scene fades and replays — like a looping product demo. */
.an-1 { animation: cue-1 16s ease infinite; }
.an-2 { animation: cue-2 16s ease infinite; }
.an-3 { animation: cue-3 16s ease infinite; }
.an-4 { animation: cue-4 16s ease infinite; }
.an-5 { animation: cue-5 16s ease infinite; }
.an-6 { animation: cue-6 16s ease infinite; }
.an-7 { animation: cue-7 16s ease infinite; }
.an-8 { animation: cue-8 16s ease infinite; }
.an-9 { animation: cue-9 16s ease infinite; }
.an-10 { animation: cue-10 16s ease infinite; }
.an-11 { animation: cue-11 16s ease infinite; }

@keyframes cue-1 { 0%, 5% { opacity: 0; transform: translateY(9px); } 8%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes cue-2 { 0%, 14% { opacity: 0; transform: translateY(9px); } 17%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes cue-3 { 0%, 19% { opacity: 0; transform: translateY(8px); } 22%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes cue-4 { 0%, 27% { opacity: 0; transform: translateY(9px); } 30%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes cue-5 { 0%, 37% { opacity: 0; transform: translateY(7px); } 40%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(7px); } }
@keyframes cue-6 { 0%, 42% { opacity: 0; transform: translateY(8px); } 45%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes cue-7 { 0%, 48% { opacity: 0; transform: translateY(9px); } 51%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes cue-8 { 0%, 57% { opacity: 0; transform: translateY(9px); } 60%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes cue-9 { 0%, 61% { opacity: 0; transform: translateY(8px); } 64%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes cue-10 { 0%, 70% { opacity: 0; } 73%, 87% { opacity: 1; } 93%, 100% { opacity: 0; } }
@keyframes cue-11 { 0%, 79% { opacity: 0; transform: scale(0.9); } 82%, 87% { opacity: 1; transform: none; } 93%, 100% { opacity: 0; transform: scale(0.9); } }
@keyframes cue-12 { 0%, 76% { opacity: 0; } 79%, 87% { opacity: 1; } 93%, 100% { opacity: 0; } }
.an-12 { animation: cue-12 16s ease infinite; }

/* Done handoffs, on the same 16s clock. Hero: agent 1 finishes when Maya's
   diary entry lands (~34%), agent 2 when Kai's lands (~57%). The Stop chip
   rides the same curve as the dots. */
@keyframes tail-work-1 { 0%, 34% { opacity: 1; } 36%, 100% { opacity: 0; } }
@keyframes tail-done-1 { 0%, 34.5% { opacity: 0; transform: translateY(3px); } 36.5%, 100% { opacity: 1; transform: none; } }
@keyframes tail-work-2 { 0%, 57% { opacity: 1; } 59%, 100% { opacity: 0; } }
@keyframes tail-done-2 { 0%, 57.5% { opacity: 0; transform: translateY(3px); } 59.5%, 100% { opacity: 1; transform: none; } }
.hero-app .an-2 .think-dots,
.hero-app .an-2 .stop-chip { animation: tail-work-1 16s linear infinite; }
.hero-app .an-2 .agent-done { animation: tail-done-1 16s ease infinite; }
.hero-app .an-5 .think-dots,
.hero-app .an-5 .stop-chip { animation: tail-work-2 16s linear infinite; }
.hero-app .an-5 .agent-done { animation: tail-done-2 16s ease infinite; }

/* Conversation room: the agent thinks from ~40% and lands Done at ~62%,
   then the message collects reactions. */
@keyframes tail-work-c { 0%, 61% { opacity: 1; } 63%, 100% { opacity: 0; } }
@keyframes tail-done-c { 0%, 61.5% { opacity: 0; transform: translateY(3px); } 63.5%, 100% { opacity: 1; transform: none; } }
.comm-app .an-5 .think-dots,
.comm-app .an-5 .stop-chip { animation: tail-work-c 16s linear infinite; }
.comm-app .an-5 .agent-done { animation: tail-done-c 16s ease infinite; }

/* Multiplayer chat rows, as in the product: avatar + name/timestamp header,
   message text below at the left margin so the column stays aligned. */
.chat-msg { display: flex; flex-direction: column; gap: 7px; }

/* The signed-in user's own messages sit on the right as a mist bubble
   with no header, exactly like the product. */
.chat-msg.mine { align-items: flex-end; }
.chat-msg.mine .cm-text {
  background: var(--mist);
  color: #2f1f54;
  padding: 9px 13px;
  border-radius: 14px 14px 4px 14px;
  max-width: 82%;
}
.chat-msg.mine .replies { align-self: flex-end; }

/* The typing indicator lives in ONE fixed slot above the composer, as in
   the product; the name swaps in just before each message arrives. */
.pstack { position: relative; min-height: 18px; }
.pline {
  position: absolute;
  left: 0; top: 0;
  display: flex;
  align-items: center;
  gap: 7px;
  white-space: nowrap;
  opacity: 0;
}
@keyframes pl-a { 0%, 1% { opacity: 0; } 2.5%, 5% { opacity: 1; } 6.5%, 100% { opacity: 0; } }
@keyframes pl-b { 0%, 22.5% { opacity: 0; } 24%, 27% { opacity: 1; } 28.5%, 100% { opacity: 0; } }
@keyframes pl-c { 0%, 43.5% { opacity: 0; } 45%, 48% { opacity: 1; } 49.5%, 100% { opacity: 0; } }
@keyframes pl-d { 0%, 52.5% { opacity: 0; } 54%, 57% { opacity: 1; } 58.5%, 100% { opacity: 0; } }
@keyframes pl-e { 0%, 70% { opacity: 0; } 73%, 87% { opacity: 1; } 93%, 100% { opacity: 0; } }
@keyframes pl-f { 0%, 9.5% { opacity: 0; } 11%, 14% { opacity: 1; } 15.5%, 100% { opacity: 0; } }
@keyframes pl-g { 0%, 15.5% { opacity: 0; } 17%, 19% { opacity: 1; } 20.5%, 100% { opacity: 0; } }
@keyframes pl-h { 0%, 76% { opacity: 0; } 79%, 87% { opacity: 1; } 93%, 100% { opacity: 0; } }
.pline.pl-a { animation: pl-a 16s ease infinite; }
.pline.pl-b { animation: pl-b 16s ease infinite; }
.pline.pl-c { animation: pl-c 16s ease infinite; }
.pline.pl-d { animation: pl-d 16s ease infinite; }
.pline.pl-e { animation: pl-e 16s ease infinite; }
.pline.pl-f { animation: pl-f 16s ease infinite; }
.pline.pl-g { animation: pl-g 16s ease infinite; }
.pline.pl-h { animation: pl-h 16s ease infinite; }
.pfp {
  width: 26px; height: 26px;
  flex: none;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 9.5px;
  font-weight: 800;
  color: #fff;
}
.cm-head { display: flex; align-items: center; gap: 9px; }
.cm-id { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.cm-name {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 12.5px;
  font-weight: 800;
  letter-spacing: -0.01em;
}
.cm-time { font-size: 10px; color: var(--muted); }
.cm-text { font-size: 13px; line-height: 1.45; color: #3f3a49; }

/* Live multiplayer document: attributed sections write themselves
   concurrently, each with a presence caret — the Google-Docs moment. */

.presence {
  display: flex;
  align-items: center;
  gap: 7px;
  font-size: 11.5px;
  font-weight: 600;
  color: var(--muted);
}
.presence .think-dots { padding: 0; }
.presence .think-dots span { width: 4px; height: 4px; }

/* Single full-height document page; content grows and pushes down,
   sliding under the page's bottom margin. */
.pages {
  --page-pad: 24px;
  position: relative;
  flex: 1;
  min-height: 448px;
  display: flex;
  flex-direction: column;
}
.page-card {
  position: relative;
  flex: 1;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 0;
  box-shadow: 0 14px 40px rgba(40, 24, 70, 0.1);
}
/* Clip at the text area, not the padding box, so the white page margins
   stay clean and content slides under them like real print margins. */
.page-inner {
  position: absolute;
  top: var(--page-pad);
  bottom: var(--page-pad);
  left: 24px;
  right: 24px;
  overflow: hidden;
}
.page-inner::after {
  content: "";
  position: absolute;
  left: 0; right: 0; bottom: 0;
  height: 12px;
  background: linear-gradient(180deg, rgba(255, 255, 255, 0), #fff 88%);
  pointer-events: none;
}
.page-card .flow { display: flex; flex-direction: column; gap: 12px; }
.doc-head, .doc-rule, .doc-sec { flex: none; }
.doc-head { display: flex; align-items: center; gap: 9px; }
.doc-head img { width: 20px; height: 20px; }
.doc-head .t { font-size: 14px; font-weight: 800; letter-spacing: -0.02em; }
.doc-head .w {
  margin-left: auto;
  font-family: var(--font-system);
  font-size: 8.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
.doc-rule { height: 1px; background: var(--line); }

.live-block {
  background: #fff;
  border: 1px solid var(--line);
  border-left: 3px solid var(--violet);
  border-radius: 10px;
  padding: 10px 13px;
  display: flex;
  flex-direction: column;
  gap: 5px;
}
.live-block .attr {
  font-size: 12px;
  font-weight: 800;
  letter-spacing: -0.015em;
  color: var(--ink);
}
.doc-sec { font-size: 15px; font-weight: 800; letter-spacing: -0.025em; }
.sec-eyebrow {
  font-family: var(--font-system);
  font-size: 8.5px;
  font-weight: 600;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--violet-deep);
  margin-bottom: -6px;
}
.sum-card {
  border: 1px solid var(--line);
  border-radius: 10px;
  padding: 11px 13px;
  display: flex;
  flex-direction: column;
  gap: 7px;
}
.sum-line { font-size: 11px; line-height: 1.5; color: var(--muted); }
.sum-line b { color: #3f3a49; font-weight: 800; }

.kt-list { display: block; }
.kt-list .live-block { margin-bottom: 10px; }
.kt-list .live-block:last-child { margin-bottom: 0; }

.live-block .body-line { font-size: 11.5px; line-height: 1.5; color: #3f3a49; }

/* A person's week is a list with a state against each item, the way it reads
   in the document itself. */
.live-block .wk-list { list-style: none; padding: 0; display: flex; flex-direction: column; gap: 3px; }
.live-block .wk-list li { display: flex; gap: 6px; font-size: 10.5px; line-height: 1.45; color: #3f3a49; }
.live-block .wk-list li::before {
  content: "";
  flex: none;
  width: 3px; height: 3px;
  margin-top: 6px;
  border-radius: 50%;
  background: #a49bb3;
}
.live-block .wk-list em {
  font-style: normal;
  font-weight: 700;
  color: var(--muted);
  white-space: nowrap;
}

/* New items expand into the page, pushing everything below them down */
.live-block.b1, .live-block.b2, .live-block.b3 { overflow: hidden; }
.live-block.b1 { animation: grow-1 16s ease infinite; }
.live-block.b2 { animation: grow-2 16s ease infinite; }
.live-block.b3 { animation: grow-3 16s ease infinite; }
@keyframes grow-1 {
  0%, 19% { max-height: 0; margin-bottom: 0; opacity: 0; border-width: 0 0 0 3px; padding-block: 0; }
  23%, 87% { max-height: 140px; margin-bottom: 10px; opacity: 1; }
  93%, 100% { max-height: 0; margin-bottom: 0; opacity: 0; border-width: 0 0 0 3px; padding-block: 0; }
}
@keyframes grow-2 {
  0%, 42% { max-height: 0; margin-bottom: 0; opacity: 0; border-width: 0 0 0 3px; padding-block: 0; }
  46%, 87% { max-height: 140px; margin-bottom: 10px; opacity: 1; }
  93%, 100% { max-height: 0; margin-bottom: 0; opacity: 0; border-width: 0 0 0 3px; padding-block: 0; }
}
@keyframes grow-3 {
  0%, 61% { max-height: 0; margin-bottom: 0; opacity: 0; border-width: 0 0 0 3px; padding-block: 0; }
  65%, 87% { max-height: 140px; margin-bottom: 10px; opacity: 1; }
  93%, 100% { max-height: 0; margin-bottom: 0; opacity: 0; border-width: 0 0 0 3px; padding-block: 0; }
}



/* Launch-release scene (hero) -----------------------------------------------
   The room where a launch release is argued into shape. Everything rides one
   58s clock: an angle goes in, SuperApp drafts the release into the panel
   beside the thread, someone asks the agent what it actually thinks, it
   disagrees with the direction it was given and proposes copy of its own,
   the room argues it out, the release is rewritten by three people and
   SuperApp at once, and the team then lands the final line together.

   It reuses the hero shell (dock, sidebar, room, panel) and carries its own
   cue namespace — lr-* for the thread, pr-*/c*/n* for the document — so
   nothing collides with the 16s cues the other scenes run on. */

/* Each arrival grows to its own ceiling; the ceiling must clear the tallest
   the message ever gets, attachment chip and reactions included. */
.sc-release .msgs > * { --mh: 118px; }
.sc-release .msgs .lr-2 { --mh: 178px; }
.sc-release .msgs .lr-3 { --mh: 100px; }
.sc-release .msgs .lr-4 { --mh: 340px; }
.sc-release .msgs .lr-5 { --mh: 100px; }
.sc-release .msgs .lr-6 { --mh: 100px; }
.sc-release .msgs .lr-7 { --mh: 100px; }
.sc-release .msgs .lr-8 { --mh: 100px; }
.sc-release .msgs .lr-9 { --mh: 194px; }
.sc-release .msgs .lr-10 { --mh: 80px; }
.sc-release .msgs .lr-11 { --mh: 104px; }
.sc-release .msgs .lr-12 { --mh: 420px; }
.sc-release .msgs .lr-13 { --mh: 76px; }
.sc-release .msgs .lr-14 { --mh: 156px; }

.lr-1 { animation: lrc-1 58s ease infinite; }
.lr-2 { animation: lrc-2 58s ease infinite; }
.lr-3 { animation: lrc-3 58s ease infinite; }
.lr-4 { animation: lrc-4 58s ease infinite; }
.lr-5 { animation: lrc-5 58s ease infinite; }
.lr-6 { animation: lrc-6 58s ease infinite; }
.lr-7 { animation: lrc-7 58s ease infinite; }
.lr-8 { animation: lrc-8 58s ease infinite; }
.lr-9 { animation: lrc-9 58s ease infinite; }
.lr-10 { animation: lrc-10 58s ease infinite; }
.lr-11 { animation: lrc-11 58s ease infinite; }
.lr-12 { animation: lrc-12 58s ease infinite; }
.lr-13 { animation: lrc-13 58s ease infinite; }
.lr-14 { animation: lrc-14 58s ease infinite; }

@keyframes lrc-1 { 0%, 1.55% { opacity: 0; transform: translateY(9px); } 3.45%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-2 { 0%, 5.34% { opacity: 0; transform: translateY(9px); } 7.24%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-3 { 0%, 18.97% { opacity: 0; transform: translateY(9px); } 20.86%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-4 { 0%, 22.07% { opacity: 0; transform: translateY(9px); } 23.97%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-5 { 0%, 31.03% { opacity: 0; transform: translateY(9px); } 32.93%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-6 { 0%, 34.83% { opacity: 0; transform: translateY(9px); } 36.72%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-7 { 0%, 38.62% { opacity: 0; transform: translateY(9px); } 40.52%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-8 { 0%, 43.28% { opacity: 0; transform: translateY(9px); } 45.17%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-9 { 0%, 47.07% { opacity: 0; transform: translateY(9px); } 48.97%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-10 { 0%, 64.14% { opacity: 0; transform: translateY(9px); } 66.03%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-11 { 0%, 68.28% { opacity: 0; transform: translateY(9px); } 70.17%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-12 { 0%, 72.76% { opacity: 0; transform: translateY(9px); } 74.66%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-13 { 0%, 80.0% { opacity: 0; transform: translateY(9px); } 81.9%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }
@keyframes lrc-14 { 0%, 83.79% { opacity: 0; transform: translateY(9px); } 85.69%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(9px); } }

/* Arrivals also grow their box so each message physically pushes the thread
   up, the same trick the 16s scenes use. The newest message sits at the
   bottom of the stack, so it carries no spacing of its own — the composer
   gap below it is the room's. */
@keyframes lrg-1 { 0%, 1.55% { max-height: 0; opacity: 0; margin-bottom: 0; } 3.45%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-2 { 0%, 5.34% { max-height: 0; opacity: 0; margin-bottom: 0; } 7.24%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-3 { 0%, 18.97% { max-height: 0; opacity: 0; margin-bottom: 0; } 20.86%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-4 { 0%, 22.07% { max-height: 0; opacity: 0; margin-bottom: 0; } 23.97%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-5 { 0%, 31.03% { max-height: 0; opacity: 0; margin-bottom: 0; } 32.93%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-6 { 0%, 34.83% { max-height: 0; opacity: 0; margin-bottom: 0; } 36.72%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-7 { 0%, 38.62% { max-height: 0; opacity: 0; margin-bottom: 0; } 40.52%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-8 { 0%, 43.28% { max-height: 0; opacity: 0; margin-bottom: 0; } 45.17%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-9 { 0%, 47.07% { max-height: 0; opacity: 0; margin-bottom: 0; } 48.97%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-10 { 0%, 64.14% { max-height: 0; opacity: 0; margin-bottom: 0; } 66.03%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-11 { 0%, 68.28% { max-height: 0; opacity: 0; margin-bottom: 0; } 70.17%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-12 { 0%, 72.76% { max-height: 0; opacity: 0; margin-bottom: 0; } 74.66%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-13 { 0%, 80.0% { max-height: 0; opacity: 0; margin-bottom: 0; } 81.9%, 93.97% { max-height: var(--mh, 118px); opacity: 1; margin-bottom: 12px; } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes lrg-14 { 0%, 83.79% { max-height: 0; opacity: 0; } 85.69%, 93.97% { max-height: var(--mh, 118px); opacity: 1; } 97.41%, 100% { max-height: 0; opacity: 0; } }

.app-chat .msgs .lr-1 { animation-name: lrg-1; }
.app-chat .msgs .lr-2 { animation-name: lrg-2; }
.app-chat .msgs .lr-3 { animation-name: lrg-3; }
.app-chat .msgs .lr-4 { animation-name: lrg-4; }
.app-chat .msgs .lr-5 { animation-name: lrg-5; }
.app-chat .msgs .lr-6 { animation-name: lrg-6; }
.app-chat .msgs .lr-7 { animation-name: lrg-7; }
.app-chat .msgs .lr-8 { animation-name: lrg-8; }
.app-chat .msgs .lr-9 { animation-name: lrg-9; }
.app-chat .msgs .lr-10 { animation-name: lrg-10; }
.app-chat .msgs .lr-11 { animation-name: lrg-11; }
.app-chat .msgs .lr-12 { animation-name: lrg-12; }
.app-chat .msgs .lr-13 { animation-name: lrg-13; }
.app-chat .msgs .lr-14 { animation-name: lrg-14; }

/* Done handoffs: each agent message drops its dots and Stop chip the moment
   its work lands in the document beside it. */
@keyframes lrt-work-1 { 0%, 15.17% { opacity: 1; } 16.72%, 100% { opacity: 0; } }
@keyframes lrt-done-1 { 0%, 15.52% { opacity: 0; transform: translateY(3px); } 17.07%, 100% { opacity: 1; transform: none; } }
.sc-release .lr-2 .think-dots,
.sc-release .lr-2 .stop-chip { animation: lrt-work-1 58s linear infinite; }
.sc-release .lr-2 .agent-done { animation: lrt-done-1 58s ease infinite; }
@keyframes lrt-work-2 { 0%, 59.14% { opacity: 1; } 60.69%, 100% { opacity: 0; } }
@keyframes lrt-done-2 { 0%, 59.48% { opacity: 0; transform: translateY(3px); } 61.03%, 100% { opacity: 1; transform: none; } }
.sc-release .lr-9 .think-dots,
.sc-release .lr-9 .stop-chip { animation: lrt-work-2 58s linear infinite; }
.sc-release .lr-9 .agent-done { animation: lrt-done-2 58s ease infinite; }
@keyframes lrt-work-3 { 0%, 86.9% { opacity: 1; } 88.45%, 100% { opacity: 0; } }
@keyframes lrt-done-3 { 0%, 87.24% { opacity: 0; transform: translateY(3px); } 88.79%, 100% { opacity: 1; transform: none; } }
.sc-release .lr-14 .think-dots,
.sc-release .lr-14 .stop-chip { animation: lrt-work-3 58s linear infinite; }
.sc-release .lr-14 .agent-done { animation: lrt-done-3 58s ease infinite; }

/* Every reply that changed the release carries the file it produced, as in
   the product. In the room the chip stands alone, without the cover preview
   the Conversation frame shows — the release itself is already open in the
   panel beside it. */
.att-stack { display: flex; flex-direction: column; gap: 6px; }
/* Mentions read the way they do in the room. */
.mention {
  color: var(--violet-deep);
  font-weight: 700;
  background: rgba(132, 99, 206, 0.11);
  border-radius: 4px;
  padding: 0 3px;
}
.att-chip.solo {
  max-width: 400px;
  border: 1px solid var(--line);
  border-radius: 10px;
  box-shadow: 0 6px 18px rgba(40, 24, 70, 0.06);
}
@keyframes lra-1 { 0%, 17.07% { opacity: 0; transform: translateY(6px); } 18.97%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(6px); } }
.att-chip.lra-1 { animation: lra-1 58s ease infinite; }
@keyframes lra-2 { 0%, 61.03% { opacity: 0; transform: translateY(6px); } 62.93%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(6px); } }
.att-chip.lra-2 { animation: lra-2 58s ease infinite; }
@keyframes lra-3 { 0%, 88.97% { opacity: 0; transform: translateY(6px); } 90.86%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: translateY(6px); } }
.att-chip.lra-3 { animation: lra-3 58s ease infinite; }

/* Copy the agent proposes, set apart from what it is saying about it —
   the same violet rail the document uses for a pulled-out line. */
.agent-quote {
  display: flex;
  flex-direction: column;
  gap: 4px;
  padding: 3px 0 3px 10px;
  border-left: 2px solid var(--violet);
  font-size: 13px;
  line-height: 1.5;
  color: #342852;
}
.agent-quote b { font-weight: 800; }

/* Specific notes the agent gives back on a draft. */
.agent-notes { list-style: none; padding: 0; display: flex; flex-direction: column; gap: 5px; }
.agent-notes li { display: flex; gap: 8px; font-size: 12.5px; line-height: 1.45; color: #3f3a49; }
.agent-notes li::before {
  content: "";
  flex: none;
  width: 4px; height: 4px;
  margin-top: 7px;
  border-radius: 50%;
  background: var(--violet);
}

/* Reactions land a beat after the message they answer: the room backs
   SuperApp's objection, then the locked copy collects its own. */
@keyframes lrr-1 { 0%, 28.1% { opacity: 0; transform: scale(0.9); } 29.66%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: scale(0.9); } }
.react-row.lrr-1 { animation: lrr-1 58s ease infinite; }
@keyframes lrr-2 { 0%, 77.24% { opacity: 0; transform: scale(0.9); } 78.79%, 93.97% { opacity: 1; transform: none; } 97.41%, 100% { opacity: 0; transform: scale(0.9); } }
.react-row.lrr-2 { animation: lrr-2 58s ease infinite; }
.sc-release .chat-msg.mine .react-row { align-self: flex-end; }

/* Typing presence, on the same clock. Each line runs just before that
   person's message lands; your own messages get none, as in the product. */
@keyframes lrp-a { 0%, 16.72% { opacity: 0; } 17.41%, 18.97% { opacity: 1; } 19.66%, 100% { opacity: 0; } }
@keyframes lrp-b { 0%, 28.79% { opacity: 0; } 29.48%, 31.03% { opacity: 1; } 31.72%, 100% { opacity: 0; } }
@keyframes lrp-c { 0%, 32.59% { opacity: 0; } 33.28%, 34.83% { opacity: 1; } 35.52%, 100% { opacity: 0; } }
@keyframes lrp-d { 0%, 36.38% { opacity: 0; } 37.07%, 38.62% { opacity: 1; } 39.31%, 100% { opacity: 0; } }
@keyframes lrp-e { 0%, 41.03% { opacity: 0; } 41.72%, 43.28% { opacity: 1; } 43.97%, 100% { opacity: 0; } }
@keyframes lrp-f { 0%, 66.03% { opacity: 0; } 66.72%, 68.28% { opacity: 1; } 68.97%, 100% { opacity: 0; } }
.pline.lrp-a { animation: lrp-a 58s ease infinite; }
.pline.lrp-b { animation: lrp-b 58s ease infinite; }
.pline.lrp-c { animation: lrp-c 58s ease infinite; }
.pline.lrp-d { animation: lrp-d 58s ease infinite; }
.pline.lrp-e { animation: lrp-e 58s ease infinite; }
.pline.lrp-f { animation: lrp-f 58s ease infinite; }

/* The chat column and the panel are one split view, so their horizontals
   have to line up: the panel's top padding matches the room's, which puts
   the page card's top on the room rule.

   The page then runs off the bottom of the frame rather than ending inside
   it. A document viewer never shows a page that stops short — the page is
   taller than the viewport and text simply continues under its edge — so
   there is no card bottom, no shadow and no fade to soften the cut. */
.pr-panel, .no-shell .app-panel { padding-block: 18px 0; }
.pr-panel .pages, .no-shell .pages { min-height: 0; }
.pr-panel .page-card, .no-shell .page-card { border-bottom: 0; box-shadow: 0 6px 26px rgba(40, 24, 70, 0.08); }
.pr-panel .page-inner, .no-shell .page-inner { bottom: 0; }
.pr-panel .page-inner::after, .no-shell .page-inner::after { content: none; }

/* The panel opens empty — no artifact yet — and the release appears the
   moment SuperApp starts drafting it. */
.pr-panel .panel-head, .pr-panel .page-card { opacity: 0; animation: lr-open 58s ease infinite; }
@keyframes lr-open { 0%, 5.0% { opacity: 0; } 6.9%, 93.97% { opacity: 1; } 97.41%, 100% { opacity: 0; } }

/* The version ticks once per edit that lands, so the rewrite reads as four
   separate saves rather than one. */
@keyframes rver-1 { 0%, 7.59% { opacity: 0; } 9.14%, 51.21% { opacity: 1; } 52.76%, 100% { opacity: 0; } }
.version.vr .v1 { animation: rver-1 58s linear infinite; }
@keyframes rver-2 { 0%, 52.41% { opacity: 0; } 53.97%, 55.34% { opacity: 1; } 56.9%, 100% { opacity: 0; } }
.version.vr .v2 { animation: rver-2 58s linear infinite; }
@keyframes rver-3 { 0%, 56.21% { opacity: 0; } 57.76%, 58.45% { opacity: 1; } 60.0%, 100% { opacity: 0; } }
.version.vr .v3 { animation: rver-3 58s linear infinite; }
@keyframes rver-4 { 0%, 59.14% { opacity: 0; } 60.69%, 86.9% { opacity: 1; } 88.45%, 100% { opacity: 0; } }
@keyframes rver-5 { 0%, 88.45% { opacity: 0; } 90.0%, 93.97% { opacity: 1; } 97.41%, 100% { opacity: 0; } }
.version.vr .v4 { animation: rver-4 58s linear infinite; }
.version.vr .v5 { animation: rver-5 58s linear infinite; }

/* The version number is the only state the head carries: it ticks once
   per save and nothing narrates the run in words. */

/* The release itself, at the panel's scale: masthead, headline, deck and
   opening, in the published document's hierarchy. */
.pr-mast { display: flex; align-items: center; gap: 9px; }
.pr-mast img { width: 18px; height: 18px; }
.pr-mast .t { font-size: 12.5px; font-weight: 800; letter-spacing: -0.02em; }
.pr-mast .w {
  margin-left: auto;
  font-family: var(--font-system);
  font-size: 8px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
.pr-title { font-size: 16px; line-height: 1.15; letter-spacing: -0.04em; font-weight: 800; color: var(--ink); }
.pr-deck { font-size: 11.4px; line-height: 1.42; letter-spacing: -0.01em; font-weight: 600; color: var(--muted); }
.pr-lede { font-size: 10.6px; line-height: 1.55; color: #302840; }
.pr-lede b { font-weight: 800; }
.pr-body { font-size: 10.6px; line-height: 1.55; color: #4b4459; }
.pr-sec-h { font-size: 12.4px; line-height: 1.2; letter-spacing: -0.025em; font-weight: 800; }
.pr-emph {
  padding: 2px 0 2px 9px;
  border-left: 2px solid var(--violet);
  font-size: 10.6px;
  line-height: 1.4;
  font-weight: 700;
  color: #342852;
}

/* The three superpowers, as the release sets them: one card each, the
   middle one holding both the draft's line and the one that replaces it. */
.pr-triad { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 7px; }
/* The middle card swaps in place: both versions occupy the same box so the
   card never changes height and the row stays aligned while it is edited. */
.pr-tcol { position: relative; min-width: 0; }
.pr-tcol > .pr-tcard { position: absolute; inset: 0; }
.pr-tcard {
  height: 100%;
  padding: 8px 9px 9px;
  border: 1px solid var(--line);
  border-radius: 10px;
  background: var(--mist);
  display: flex;
  flex-direction: column;
  gap: 3px;
}
.pr-tcard .lab {
  font-family: var(--font-system);
  font-size: 6.6px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--violet-deep);
}
.pr-tcard p { font-size: 8.6px; line-height: 1.42; color: #4b4459; }
.pr-tcard b { font-weight: 800; color: var(--ink); }

.pr-quote { padding: 5px 0 5px 10px; border-left: 2.5px solid var(--violet); }
.pr-quote p { font-size: 10.2px; line-height: 1.5; color: #302840; }
.pr-quote cite {
  display: block;
  margin-top: 4px;
  font-family: var(--font-system);
  font-size: 7.4px;
  font-style: normal;
  font-weight: 600;
  letter-spacing: 0.11em;
  text-transform: uppercase;
  color: var(--muted);
}

/* Blocks that write themselves in, and the ones they later replace. Spacing
   lives on the element, not just in the keyframes, so the document still
   reads as a document when animation is off — and because a flex gap would
   hold open the space of a block that has already been cut. */
.pr-flow { display: flex; flex-direction: column; }
.pr-flow > * { overflow: hidden; margin-bottom: var(--mb, 11px); }
.pr-flow .pr-out, .pr-flow .pr-new { overflow: hidden; }
.pr-triad .pr-out, .pr-triad .pr-new { --mb: 0px; }
.pr-flow .pr-mast { --mb: 7px; overflow: visible; }
.pr-flow .doc-rule { --mb: 12px; }
.pr-flow .pr-title { --mb: 9px; }
.pr-flow .pr-deck { --mb: 10px; }
.pr-sec { display: flex; flex-direction: column; gap: 7px; }

@keyframes pr-write-w1 { 0%, 7.24% { max-height: 0; opacity: 0; margin-bottom: 0; } 8.79%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-in.w1 { animation: pr-write-w1 58s ease infinite; }
@keyframes pr-write-w4 { 0%, 10.69% { max-height: 0; opacity: 0; margin-bottom: 0; } 12.24%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-in.w4 { animation: pr-write-w4 58s ease infinite; }
@keyframes pr-write-w5 { 0%, 11.38% { max-height: 0; opacity: 0; margin-bottom: 0; } 12.93%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-in.w5 { animation: pr-write-w5 58s ease infinite; }
@keyframes pr-write-w6 { 0%, 12.07% { max-height: 0; opacity: 0; margin-bottom: 0; } 13.62%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-in.w6 { animation: pr-write-w6 58s ease infinite; }
@keyframes pr-write-w7 { 0%, 12.93% { max-height: 0; opacity: 0; margin-bottom: 0; } 14.48%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-in.w7 { animation: pr-write-w7 58s ease infinite; }
@keyframes pr-write-w8 { 0%, 13.62% { max-height: 0; opacity: 0; margin-bottom: 0; } 15.17%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-in.w8 { animation: pr-write-w8 58s ease infinite; }

/* The first draft's headline, deck and opening give way at the rewrite. */
@keyframes pr-cut-c1 { 0%, 7.93% { max-height: 0; opacity: 0; margin-bottom: 0; } 9.48%, 50.52% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 52.07%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-out.c1 { animation: pr-cut-c1 58s ease infinite; }
@keyframes pr-cut-c2 { 0%, 8.79% { max-height: 0; opacity: 0; margin-bottom: 0; } 10.34%, 51.55% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 53.1%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-out.c2 { animation: pr-cut-c2 58s ease infinite; }
@keyframes pr-cut-c3 { 0%, 9.48% { max-height: 0; opacity: 0; margin-bottom: 0; } 11.03%, 52.76% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 54.31%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-out.c3 { animation: pr-cut-c3 58s ease infinite; }
@keyframes pr-cut-c4 { 0%, 11.38% { max-height: 0; opacity: 0; margin-bottom: 0; } 12.93%, 55.0% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 56.55%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-out.c4 { animation: pr-cut-c4 58s ease infinite; }

/* Four edits inside one window, overlapping on purpose: the headline and
   opening are SuperApp's, the deck and the added blocks are people's, and
   for a few seconds every one of them is in flight at once. */
@keyframes pr-set-n1 { 0%, 51.55% { max-height: 0; opacity: 0; margin-bottom: 0; } 53.45%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-new.n1 { animation: pr-set-n1 58s ease infinite; }
@keyframes pr-set-n2 { 0%, 52.76% { max-height: 0; opacity: 0; margin-bottom: 0; } 54.66%, 86.9% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 88.45%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
@keyframes pr-set-n7 { 0%, 87.76% { max-height: 0; opacity: 0; margin-bottom: 0; } 89.66%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-new.n2 { animation: pr-set-n2 58s ease infinite; }
.pr-new.n7 { animation: pr-set-n7 58s ease infinite; }
@keyframes pr-set-n3 { 0%, 53.79% { max-height: 0; opacity: 0; margin-bottom: 0; } 55.69%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-new.n3 { animation: pr-set-n3 58s ease infinite; }
@keyframes pr-set-n4 { 0%, 55.0% { max-height: 0; opacity: 0; margin-bottom: 0; } 56.9%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-new.n4 { animation: pr-set-n4 58s ease infinite; }
@keyframes pr-set-n6 { 0%, 56.55% { max-height: 0; opacity: 0; margin-bottom: 0; } 58.45%, 93.97% { max-height: 420px; opacity: 1; margin-bottom: var(--mb, 11px); } 97.41%, 100% { max-height: 0; opacity: 0; margin-bottom: 0; } }
.pr-new.n6 { animation: pr-set-n6 58s ease infinite; }

/* The middle triad card crossfades rather than resizing, so the row holds. */
@keyframes pr-swap-out { 0%, 11.38% { opacity: 0; } 12.93%, 55.0% { opacity: 1; } 56.55%, 100% { opacity: 0; } }
@keyframes pr-swap-in { 0%, 56.55% { opacity: 0; } 58.45%, 93.97% { opacity: 1; } 97.41%, 100% { opacity: 0; } }
.pr-triad .pr-out.c4 { animation: pr-swap-out 58s ease infinite; }
.pr-triad .pr-new.n6 { animation: pr-swap-in 58s ease infinite; }

/* Nothing marks who is typing inside the document: the product has no
   per-person cursor there, so the scene does not invent one. Concurrency
   reads from the edits themselves — several blocks change inside one window
   and the version chip ticks once per save. */


/* Editor stage (Productivity): one full-width frame cycling between the
   fact sheet writing itself and the brand deck advancing, with the
   Document / Slides switcher underneath. Everything rides one 43s clock —
   a 16s document window plus a 27s slides window — so the inner loops
   stay phase-aligned with the crossfade. The stage renders a fixed
   940×560 canvas scaled to the frame. */
.editors {
  max-width: 980px;
  margin: clamp(44px, 6vw, 72px) auto 0;
  display: flex;
  flex-direction: column;
  gap: clamp(56px, 7vw, 88px);
}
.ebody {
  position: relative;
  aspect-ratio: 940 / 560;
  overflow: hidden;
}
.ecanvas {
  position: absolute;
  top: 0; left: 0;
  width: 940px;
  height: 560px;
  padding: 20px 26px 26px;
  display: flex;
  flex-direction: column;
  transform-origin: 0 0;
  transform: scale(var(--esc, 0.61));
}
/* The document frame is deeper than the slides frame because it holds a
   portrait page. The card below is A4 (548 wide, so 775 tall); the canvas
   is that plus the viewer bar above it and the canvas padding below. */
.ebody.rf-doc { aspect-ratio: 940 / 990; }
.rf-doc .ecanvas { height: 990px; }
.rf-doc { background: #f5f2f9; }
.rf-slides { background: var(--paper); }

/* Artifact-viewer chrome above doc and slides: filename + Latest on the
   left, boxed pager + zoom on the right, as in the product viewer. */
.viewer-bar {
  flex: none;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 14px;
  padding-bottom: 11px;
  margin-bottom: 16px;
  border-bottom: 1px solid var(--line);
}
.viewer-bar .vleft {
  display: flex;
  align-items: center;
  gap: 9px;
  min-width: 0;
}
.viewer-bar .vfile {
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.05em;
  color: #3f3a49;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.viewer-bar .vlatest {
  flex: none;
  display: inline-flex;
  align-items: center;
  gap: 5px;
  font-size: 10px;
  font-weight: 700;
  color: var(--muted);
}
.viewer-bar .vlatest::after {
  content: "";
  border-left: 3px solid transparent;
  border-right: 3px solid transparent;
  border-top: 3.5px solid #a49bb3;
}
.viewer-bar .vmeta {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  font-family: var(--font-system);
  font-size: 9.5px;
  font-weight: 600;
  letter-spacing: 0.06em;
  color: var(--muted);
  white-space: nowrap;
}
.viewer-bar .varr { color: #a49bb3; font-size: 12px; line-height: 1; }
.viewer-bar .vnum {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--line);
  border-radius: 5px;
  background: #fff;
  padding: 2px 6px;
  color: #3f3a49;
  line-height: 1;
}
.viewer-bar .vzoom { margin-left: 8px; }
/* The deck pager digit ticks through the visible slides */
.vpage { position: relative; display: block; width: 1.5em; height: 10px; }
.vpage span {
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
}
.vpage span:not(.pg-1) { opacity: 0; }

/* Document loop (16s, independent of the slides 43s clock): the fact sheet writes itself top to bottom, holds
   fully formed, then clears and replays — the agent authoring the page. */
@keyframes df-1 { 0%, 1.99% { opacity: 0; transform: translateY(8px); } 5.51%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes df-2 { 0%, 4.19% { opacity: 0; transform: translateY(8px); } 7.71%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes df-3 { 0%, 6.4% { opacity: 0; transform: translateY(8px); } 9.89%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes df-4 { 0%, 8.6% { opacity: 0; transform: translateY(8px); } 12.09%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(8px); } }
@keyframes df-5 { 0%, 10.8% { opacity: 0; transform: translateY(7px); } 14.32%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(7px); } }
@keyframes df-6 { 0%, 13.01% { opacity: 0; transform: translateY(7px); } 16.53%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(7px); } }
@keyframes df-7 { 0%, 15.18% { opacity: 0; transform: translateY(7px); } 18.71%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(7px); } }
@keyframes df-8 { 0%, 17.39% { opacity: 0; transform: translateY(7px); } 20.91%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(7px); } }
@keyframes df-9 { 0%, 19.59% { opacity: 0; transform: translateY(6px); } 23.11%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(6px); } }
@keyframes df-10 { 0%, 21.8% { opacity: 0; transform: translateY(6px); } 25.3%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(6px); } }
@keyframes df-11 { 0%, 24% { opacity: 0; transform: translateY(6px); } 27.5%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(6px); } }
@keyframes df-12 { 0%, 26.2% { opacity: 0; transform: translateY(6px); } 29.7%, 92% { opacity: 1; transform: none; } 94.5%, 100% { opacity: 0; transform: translateY(6px); } }

/* Page 1 writes itself, block by block, on the 16s clock. */
.rf-doc .dy-mast { animation: df-1 16s ease infinite; }
.rf-doc .s1 { animation: df-2 16s ease infinite; }
.rf-doc .t1 { animation: df-3 16s ease infinite; }
.rf-doc .t2 { animation: df-4 16s ease infinite; }
.rf-doc .t3 { animation: df-5 16s ease infinite; }
.rf-doc .t4 { animation: df-6 16s ease infinite; }
.rf-doc .t5 { animation: df-7 16s ease infinite; }
.rf-doc .t6 { animation: df-8 16s ease infinite; }
.rf-doc .t7 { animation: df-9 16s ease infinite; }
.rf-doc .s2 { animation: df-10 16s ease infinite; }
.rf-doc .m1 { animation: df-11 16s ease infinite; }
.rf-doc .m2 { animation: df-12 16s ease infinite; }


/* Slides loop (43s): the deck advances through the first six brand-guide
   slides, about seven seconds each; the canvas, the active thumbnail ring
   and the pager digit all move together. Consecutive ramps overlap so the
   canvas crossfades instead of dipping to white between slides. */
@keyframes sf-1 { 0%, 15.87% { opacity: 1; } 16.67%, 99.2% { opacity: 0; } 100% { opacity: 1; } }
@keyframes sf-2 { 0%, 15.87% { opacity: 0; } 16.67%, 32.53% { opacity: 1; } 33.33%, 100% { opacity: 0; } }
@keyframes sf-3 { 0%, 32.53% { opacity: 0; } 33.33%, 49.2% { opacity: 1; } 50%, 100% { opacity: 0; } }
@keyframes sf-4 { 0%, 49.2% { opacity: 0; } 50%, 65.87% { opacity: 1; } 66.67%, 100% { opacity: 0; } }
@keyframes sf-5 { 0%, 65.87% { opacity: 0; } 66.67%, 82.53% { opacity: 1; } 83.33%, 100% { opacity: 0; } }
@keyframes sf-6 { 0%, 82.53% { opacity: 0; } 83.33%, 99.2% { opacity: 1; } 100% { opacity: 0; } }
.rf-slides .sl-1, .rf-slides .pg-1, .rf-slides .th-1::after { animation: sf-1 43s linear infinite; }
.rf-slides .sl-2, .rf-slides .pg-2, .rf-slides .th-2::after { animation: sf-2 43s linear infinite; }
.rf-slides .sl-3, .rf-slides .pg-3, .rf-slides .th-3::after { animation: sf-3 43s linear infinite; }
.rf-slides .sl-4, .rf-slides .pg-4, .rf-slides .th-4::after { animation: sf-4 43s linear infinite; }
.rf-slides .sl-5, .rf-slides .pg-5, .rf-slides .th-5::after { animation: sf-5 43s linear infinite; }
.rf-slides .sl-6, .rf-slides .pg-6, .rf-slides .th-6::after { animation: sf-6 43s linear infinite; }


/* Document frame: the media fact sheet, as published — lavender field,
   embargo notice, headline with the violet word, journey thread, pillars,
   proof band, facts and folio. */
.ed-doc {
  flex: 1;
  min-height: 0;
  display: grid;
  grid-template-columns: 172px minmax(0, 1fr);
  gap: 22px;
}
/* Sections rail, as in the document viewer: compact rows — a small page
   icon, title and snippet — with the active row highlighted. They fill in
   as the page writes itself. */
.sec-rail {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-height: 0;
  overflow: hidden;
}
.sec-item {
  display: flex;
  align-items: center;
  gap: 7px;
  border-radius: 7px;
  padding: 4px 8px;
  min-width: 0;
}
.sec-item .sec-ic { flex: none; width: 11px; height: 11px; color: #8b8398; }
.sec-item .sec-ic svg { width: 100%; height: 100%; }
.sec-item .sec-tx {
  display: flex;
  flex-direction: column;
  gap: 1px;
  min-width: 0;
}
.sec-item b {
  font-size: 8.25px;
  letter-spacing: -0.01em;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.sec-item .sec-tx span {
  font-size: 6.5px;
  color: var(--muted);
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.sec-item.on { background: var(--mist); }
.sec-item.on .sec-ic { color: var(--violet-deep); }
/* The diary's pages are stacked in one stage and the viewer shows one at a
   time, so the outline row, the pager digit and the visible page agree. */
/* The viewer stacks A4 pages with a gutter between them, so the frame
   shows the first page whole and the head of the second below it — the
   document carrying on, as it does on screen. */
.doc-stage {
  justify-self: center;
  width: min(548px, 100%);
  display: flex;
  flex-direction: column;
  gap: 14px;
}
/* Both cards clip the same flow; the second starts one page further down,
   so whatever the page break lands on is cut on page 1 and resumes at the
   top of page 2 exactly as it would in the document. */
.dy-view { flex: 1; min-height: 0; overflow: hidden; }
.dy-flow { display: flex; flex-direction: column; gap: 9px; }
/* One page of the flow. The view sizes itself from what the masthead and
   folio leave, so this cannot be derived in CSS — it is the measured
   .dy-view height and must be re-measured if either changes. */
.rf-doc { --page-flow: 676px; }
.fs-page.p2 .dy-flow { transform: translateY(calc(-1 * var(--page-flow))); }
/* Nudge the second summary card so the break falls in the gap between the
   two, leaving last week whole on page 1 and opening page 2 with this
   week rather than slicing a card's top edge off. */
.dy-flow .m2 { margin-top: 44px; }
.fs-page {
  position: relative;
  flex: none;
  width: 100%;
  aspect-ratio: 210 / 297;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 10px;
  box-shadow: 0 16px 44px rgba(40, 24, 70, 0.1);
  padding: 20px 26px 14px;
  display: flex;
  flex-direction: column;
  gap: 9px;
  overflow: hidden;
}
/* Diary pages, recreated at the card's width from the published document:
   a masthead, a section heading, violet-ruled topic cards and the summary
   card the team writes into each week. */
.fs-label {
  font-family: var(--font-system);
  font-size: 6.5px;
  font-weight: 600;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--violet-deep);
}
.dy-mast {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 14px;
  padding-bottom: 7px;
  border-bottom: 1px solid #d9d0e8;
}
.dy-logo { display: inline-flex; align-items: center; gap: 6px; }
.dy-logo img { width: 15px; height: 15px; }
.dy-logo b { font-size: 10.5px; letter-spacing: -0.02em; }
.dy-week {
  font-family: var(--font-system);
  font-size: 6.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
.dy-h { font-size: 13px; font-weight: 800; letter-spacing: -0.03em; }
.dy-topics { display: flex; flex-direction: column; gap: 6px; }
.dy-topic {
  border: 1px solid var(--line);
  border-left: 2.5px solid var(--violet);
  border-radius: 0 7px 7px 0;
  background: #fff;
  padding: 6px 9px;
  display: flex;
  flex-direction: column;
  gap: 2px;
}
.dy-topic > b { font-size: 8.25px; letter-spacing: -0.015em; color: var(--violet-deep); }
.dy-topic span, .dy-topic li { font-size: 6.9px; line-height: 1.45; color: var(--muted); }
.dy-topic ul, .dy-topic ol { margin: 1px 0 0; padding-left: 11px; display: flex; flex-direction: column; gap: 1px; }
.dy-topic li b { color: #3f3a49; }
.dy-topic i { font-style: normal; font-family: var(--font-system); font-size: 6.4px; color: #3f3a49; }
.dy-sum {
  border: 1px solid var(--line);
  border-radius: 8px;
  background: #fff;
  padding: 8px 10px;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.dy-sum-h { font-size: 8.75px; letter-spacing: -0.02em; }
.dy-sum ul { margin: 0; padding-left: 11px; display: flex; flex-direction: column; gap: 3px; }
.dy-sum li { font-size: 6.9px; line-height: 1.45; color: var(--muted); }
.dy-sum li b { color: #3f3a49; }
.fs-folio {
  margin-top: auto;
  padding-top: 8px;
  border-top: 1px solid #d9d0e8;
  display: flex;
  justify-content: space-between;
  gap: 12px;
  font-family: var(--font-system);
  font-size: 6.25px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
.fs-folio .sig { color: var(--violet-deep); }

/* Slides frame: the brand-guide deck in the slides editor — thumbnail rail
   on the left, one 16:9 slide on the canvas. */
.ed-slides {
  flex: 1;
  min-height: 0;
  display: grid;
  grid-template-columns: 118px minmax(0, 1fr);
  gap: 22px;
}
.ed-slides .thumbs { display: flex; flex-direction: column; gap: 10px; min-height: 0; overflow: hidden; }
.thumb {
  position: relative;
  flex: none;
  aspect-ratio: 16 / 9;
  border-radius: 6px;
  border: 1px solid var(--line);
  background: #fff;
  padding: 0;
  overflow: hidden;
}
/* Each thumbnail is a true miniature: the same slide markup scaled to the
   rail (116 / 748 of the fixed design canvas). */
.thumb .tmini {
  position: absolute;
  top: 0; left: 0;
  width: 748px;
  height: 421px;
  transform: scale(0.1551);
  transform-origin: 0 0;
  pointer-events: none;
}
.thumb .tmini .bslide { opacity: 1 !important; animation: none !important; }
/* Active-slide ring, handed between thumbs as the deck advances */
.thumb::after {
  content: "";
  position: absolute;
  inset: 0;
  border: 2px solid var(--violet);
  border-radius: 6px;
  opacity: 0;
}
.th-1::after { opacity: 1; }

.canvas-stack {
  position: relative;
  width: 100%;
  aspect-ratio: 16 / 9;
  align-self: center;
  border: 1px solid var(--line);
  border-radius: 12px;
  overflow: hidden;
  box-shadow: 0 16px 44px rgba(40, 24, 70, 0.12);
  background: #fff;
}
.bslide {
  position: absolute;
  inset: 0;
  padding: 5.5% 6.5%;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
/* Every slide after the first starts hidden; the loop reveals it */
.bslide:not(.sl-1) { opacity: 0; }
.sl-mist { background: var(--mist); }
.sl-plain { background: #fdfcfe; }

/* Type scale = the deck shell's 1280-wide scale x 0.584 (our 748 canvas):
   title 54->31.5, copy 21->12.3, small 15->8.8, eyebrow 13->7.6,
   rule-label 12->7. Keep this factor for anything new. */
.bs-eyebrow {
  font-family: var(--font-system);
  font-size: 7.6px;
  font-weight: 600;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--muted);
}
.bs-title {
  font-size: 31.5px;
  font-weight: 800;
  letter-spacing: -0.047em;
  line-height: 1.03;
  margin-top: 11px;
}
.bs-pager {
  position: absolute;
  right: 12px;
  bottom: 9px;
  font-family: var(--font-system);
  font-size: 7px;
  font-weight: 600;
  letter-spacing: 0.13em;
  color: var(--muted);
}

/* Shared slide scaffolding: layout variants and the deck type roles at
   the shell scale (hero 104->60.7, display 86->50.2, copy 21->12.3). */
.sl-between { justify-content: space-between; }
.sl-center { justify-content: center; }
.sl-dark { background: var(--ink); color: #fff; }
.sl-dark .bs-eyebrow { color: rgba(255, 255, 255, 0.72); }
.sl-dark .bs-copy { color: rgba(255, 255, 255, 0.72); }
.sl-dark .bs-pager { color: rgba(255, 255, 255, 0.55); }
.bs-hero { font-size: 60.7px; line-height: 0.9; letter-spacing: -0.066em; font-weight: 800; }
.bs-display { font-size: 50.2px; line-height: 0.96; letter-spacing: -0.058em; font-weight: 800; }
.bs-copy { font-size: 12.3px; line-height: 1.52; letter-spacing: -0.012em; color: var(--muted); }

/* Slide 1 - the cover: violet field circles, masthead row, hero statement */
.sl-cover { background: var(--paper); }
.sl-cover::before {
  content: "";
  position: absolute;
  width: 444px; height: 444px;
  right: -146px; top: -181px;
  border-radius: 50%;
  background: radial-gradient(circle, rgba(132, 99, 206, 0.2) 0, rgba(132, 99, 206, 0.08) 42%, rgba(132, 99, 206, 0) 70%);
  pointer-events: none;
}
.sl-cover::after {
  content: "";
  position: absolute;
  width: 304px; height: 304px;
  right: -41px; top: -79px;
  border: 1px solid rgba(132, 99, 206, 0.22);
  border-radius: 50%;
  pointer-events: none;
}
.cv-top, .cv-mid, .cv-bot { position: relative; z-index: 1; }
.cv-top { display: flex; align-items: center; justify-content: space-between; gap: 14px; }
.cv-logo { width: 152px; height: auto; }
.cv-mid { max-width: 566px; }
.cv-mid .bs-eyebrow { display: block; margin-bottom: 14px; }
.cv-bot { display: flex; align-items: flex-end; justify-content: space-between; gap: 14px; }
.cv-bot .bs-copy { max-width: 374px; }
.cv-sig { color: var(--violet); }

/* Slide 2 - the premise, on Deep Ink */
.pm-display { max-width: 654px; }
.pm-row { display: flex; align-items: center; gap: 14px; }
.pm-bar { flex: none; width: 2px; height: 36px; border-radius: 999px; background: var(--violet); }
.pm-row .bs-copy { max-width: 444px; }

/* Slide 3 - the split workday: Talk / Ask / Make columns and their pills */
.pb-title { max-width: 467px; }
.pb-grid { flex: 1; min-height: 0; display: grid; grid-template-columns: 1fr 1fr 1fr; margin-top: 33px; }
.pb-col {
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  gap: 12px;
  padding-inline: 23px;
  border-right: 1px solid var(--line);
}
.pb-col:first-child { padding-left: 0; }
.pb-col:last-child { border-right: 0; padding-right: 0; }
.pb-word { font-size: 42px; line-height: 1; letter-spacing: -0.06em; font-weight: 800; }
.pb-col .bs-copy { margin-top: 14px; }
.pb-pill {
  align-self: flex-start;
  display: inline-flex;
  align-items: center;
  gap: 6px;
  padding: 6px 9px;
  border: 1px solid var(--line);
  border-radius: 999px;
  background: rgba(255, 255, 255, 0.65);
  font-size: 8.2px;
  font-weight: 700;
}
.pb-pill .dot { width: 6px; height: 6px; }
.pb-foot {
  margin-top: 16px;
  font-family: var(--font-system);
  font-size: 7px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--muted);
}

/* Slide 4 - the handoff tax: fanned context cards, the ink one marked
   Missing */
.hf-grid { flex: 1; min-height: 0; display: grid; grid-template-columns: 2fr 1fr; gap: 14px; }
.hf-left { display: flex; flex-direction: column; justify-content: center; }
.hf-left .bs-eyebrow { margin-bottom: 16px; }
.hf-right { position: relative; min-height: 0; }
.hf-card {
  position: absolute;
  width: 181px; height: 123px;
  border-radius: 16px;
  background: #fff;
  border: 1px solid var(--line);
}
.hf-card.c1 { left: 5px; top: 68px; transform: rotate(-4deg); }
.hf-card.c2 { left: 19px; top: 109px; }
.hf-card.c3 {
  left: 33px; top: 149px;
  transform: rotate(4deg);
  background: var(--ink);
  border: 0;
  color: #fff;
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  padding: 19px 19px 27px;
}
.hf-card.c3 .bs-eyebrow { color: rgba(255, 255, 255, 0.72); }
.hf-why { font-size: 19.9px; font-weight: 700; line-height: 1.25; letter-spacing: -0.02em; }

/* Slide 5 - our belief: two statements on Deep Ink, the second violet */
.bl-eyebrow { display: block; margin-bottom: 21px; }
.bl-line { font-size: 42px; line-height: 1.02; letter-spacing: -0.055em; font-weight: 800; max-width: 631px; }
.bl-line + .bl-line { margin-top: 19px; }

/* Slide 6 - what SuperApp is: three superpowers and the summary line */
.wh-title { max-width: 543px; }
.wh-grid { display: grid; grid-template-columns: 1fr 1fr 1fr; }
.wh-col { padding-inline: 16px; border-right: 1px solid var(--line); }
.wh-col:last-child { border-right: 0; }
.wh-label {
  display: block;
  font-family: var(--font-system);
  font-size: 7px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--muted);
  margin-bottom: 12px;
}
.wh-stat { font-size: 21.5px; line-height: 1.25; letter-spacing: -0.04em; font-weight: 800; }
.wh-foot { display: flex; flex-direction: column; gap: 14px; font-size: 16.4px; font-weight: 700; letter-spacing: -0.02em; }
.wh-rule { height: 1px; background: var(--line); }

/* Pricing ----------------------------------------------------------------------------
   Plan cards on the mist band: Monthly/Annual segment, four cards, and
   Lite/Pro/Max tier tabs inside Personal and Team. Annual is ten months
   for the year, so both price spans (.p-m monthly / .p-a annual) are in the
   DOM and the section's data-billing attribute picks one. */

[hidden] { display: none !important; }

.plans-head {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  justify-content: space-between;
  gap: 28px;
}
.plans-head .bill-seg { margin-bottom: 6px; }

.bill-seg {
  display: inline-flex;
  gap: 4px;
  padding: 5px;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: 999px;
}
.bseg-btn {
  display: inline-flex;
  align-items: center;
  gap: 9px;
  border: 0;
  background: transparent;
  border-radius: 999px;
  padding: 10px 20px;
  font: 700 15px/1 var(--font-voice);
  letter-spacing: -0.01em;
  color: var(--muted);
  cursor: pointer;
  transition: background-color 0.16s ease, color 0.16s ease;
}
.bseg-btn:hover { color: var(--ink); }
.bseg-btn.on {
  background: var(--mist);
  color: var(--violet-deep);
}
.save-tag {
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--violet-deep);
  background: rgba(132, 99, 206, 0.14);
  border-radius: 999px;
  padding: 4px 8px;
  transition: background-color 0.16s ease, color 0.16s ease;
}
.bseg-btn.on .save-tag { background: var(--violet); color: #fff; }

.plans {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: 18px;
  align-items: stretch;
  margin-top: clamp(44px, 6vw, 64px);
}

.plan-card {
  position: relative;
  display: flex;
  flex-direction: column;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: 30px 26px 28px;
}
.plan-card.featured {
  border-color: var(--violet);
  box-shadow: 0 22px 48px -26px rgba(93, 61, 167, 0.45);
}

.plan-flag {
  position: absolute;
  top: -13px;
  left: 26px;
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: #fff;
  background: var(--violet);
  border-radius: 999px;
  padding: 6px 12px;
}

.plan-name {
  font-size: 21px;
  font-weight: 800;
  letter-spacing: -0.02em;
}

/* Price block (one per tier inside tabbed cards) */
.tier-price { margin-top: 16px; }
.price-row {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 6px;
  font-weight: 800;
  letter-spacing: -0.045em;
}
.price-row .amt { font-size: clamp(38px, 3.4vw, 46px); line-height: 1; }
.price-row .per {
  font-family: var(--font-system);
  font-size: 12px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--muted);
  white-space: nowrap;
}
.price-row .amt.word { font-size: clamp(30px, 2.8vw, 36px); letter-spacing: -0.03em; }
.bill-note {
  margin-top: 8px;
  font-size: 13.5px;
  line-height: 1.4;
  color: var(--muted);
  min-height: 19px;
}

/* Billing-period swap: both spans are in the DOM, CSS shows one. */
#pricing[data-billing="monthly"] .p-a { display: none; }
#pricing[data-billing="annual"] .p-m { display: none; }

/* Tier tabs inside a card */
.tier-tabs {
  display: inline-flex;
  align-self: flex-start;
  gap: 4px;
  padding: 4px;
  margin-top: 18px;
  background: #f3f0fa;
  border-radius: 999px;
}
.ttab {
  border: 0;
  background: transparent;
  border-radius: 999px;
  padding: 7px 15px;
  font: 700 13.5px/1 var(--font-voice);
  letter-spacing: -0.01em;
  color: var(--muted);
  cursor: pointer;
  transition: background-color 0.16s ease, color 0.16s ease, box-shadow 0.16s ease;
}
.ttab:hover { color: var(--ink); }
.ttab.on {
  background: #fff;
  color: var(--ink);
  box-shadow: 0 1px 3px rgba(13, 11, 18, 0.12);
}
html:not(.js) .tier-tabs { display: none; }

/* Per-tier body: description, credits, feature list, CTA */
.tier-body {
  display: flex;
  flex-direction: column;
  flex: 1;
  margin-top: 18px;
}
.plan-desc { font-size: 14.5px; line-height: 1.5; color: var(--muted); }

.credit-line {
  margin-top: 14px;
  font-size: 14.5px;
  color: var(--muted);
}
.credit-line b {
  font-size: 19px;
  font-weight: 800;
  letter-spacing: -0.02em;
  color: var(--ink);
}
.credit-line + .credit-line { margin-top: 2px; }

.plan-card .hairline { margin-block: 18px; }

.inc-label {
  font-size: 13.5px;
  font-weight: 700;
  color: var(--ink);
}

.checklist { margin-top: 12px; display: grid; gap: 9px; }
.checklist li {
  position: relative;
  padding-left: 24px;
  font-size: 14.5px;
  line-height: 1.42;
  color: var(--muted);
}
.checklist li::before {
  content: "";
  position: absolute;
  left: 1px;
  top: 3.5px;
  width: 13px;
  height: 13px;
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%238463ce' stroke-width='3.4' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M4 12.5l5.5 5.5L20 6.5'/%3E%3C/svg%3E") center / contain no-repeat;
}

.plan-cta { margin-top: auto; padding-top: 26px; }
.plan-cta .btn { width: 100%; justify-content: center; }

.fineprint {
  margin-top: clamp(26px, 3.5vw, 36px);
  font-size: 13.5px;
  line-height: 1.5;
  color: var(--muted);
}

/* Enterprise ------------------------------------------------------------------------- */

/* Model freedom, demonstrated. Eight capabilities, each with its own menu of
   models in preference order; the line under all of them never moves — that
   contrast is the whole argument, so nothing in the card animates. */
.mf-card {
  position: relative;
  margin-top: clamp(44px, 6vw, 72px);
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  padding: clamp(26px, 3.2vw, 40px);
}
.mf-steps {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  --colpad: clamp(18px, 2.4vw, 32px);
}
.mf-steps.four-up {
  grid-template-columns: repeat(4, minmax(0, 1fr));
  row-gap: clamp(26px, 3.2vw, 38px);
}
.mf-steps.four-up .mf-step:nth-child(4n + 1) { border-left: 0; padding-left: 0; }

.mf-step {
  display: flex;
  flex-direction: column;
  gap: 12px;
  min-height: 132px;
  padding-inline: var(--colpad);
  border-left: 1px solid var(--line);
}
.mf-step:first-child { border-left: 0; padding-left: 0; }
.mf-n {
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.04em;
  color: var(--violet);
  overflow: hidden;
  text-overflow: ellipsis;
}
.mf-sub {
  display: block;
  margin-top: 5px;
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--muted);
}
.mf-what {
  font-size: clamp(20px, 2vw, 25px);
  font-weight: 800;
  line-height: 1.1;
  letter-spacing: -0.028em;
}
/* The chain, whole. Each capability shows its lead and the models behind it
   in resolution order — a rotating single badge showed where the chain was at
   that instant and never what the chain is. Nothing animates here, so there is
   no auto-updating content to pause and no timing left to get wrong. */
/* Says which selection the chains below are resolved for, and how to read
   them. Both sit on one line above the rail. */
.mf-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 8px 20px;
  margin-bottom: clamp(18px, 2.2vw, 26px);
}
.mf-plan {
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
}
.mf-chain {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 5px 6px;
  margin-top: auto;
  padding-top: 4px;
}
.mf-model {
  padding: 6px 11px;
  border: 1px solid transparent;
  border-radius: 14px;
  background: var(--mist);
  color: var(--violet-deep);
  font: 600 11px/1.4 var(--font-system);
}
/* A failover reads as available-but-not-in-use: same shape, no fill. */
.mf-model.fb {
  background: none;
  border-color: var(--line);
  color: var(--muted);
}
.mf-next {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
.mf-arrow { font-size: 12px; line-height: 1; color: #a49daf; }
.mf-legend {
  font-family: var(--font-system);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: #a49daf;
}

.mf-line {
  height: 4px;
  margin-top: clamp(24px, 3vw, 32px);
  border-radius: 999px;
  background: var(--violet);
}
.mf-foot {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px 24px;
  margin-top: 14px;
}
.mf-under {
  font-family: var(--font-system);
  font-size: 11.5px;
  font-weight: 600;
  letter-spacing: 0.06em;
  color: var(--muted);
}
.mf-claim {
  font-size: clamp(17px, 1.7vw, 20px);
  font-weight: 800;
  letter-spacing: -0.024em;
}
/* Runs the full column like the configuration note under it — the two read
   as one pair of remarks on the rail, so they share its measure rather than
   the narrower one body copy takes elsewhere. */
.mf-consequence {
  margin-top: clamp(32px, 4vw, 44px);
}

/* What the rail buys, stated then unpacked: the claim line sits close to the
   tick list under it, the way a head sits over its own list rather than over
   the next section. */
.mf-yield {
  max-width: 900px;
  margin-top: clamp(40px, 4.8vw, 58px);
}
.mf-yield + .rely-list { margin-top: clamp(18px, 2.2vw, 26px); }

/* Measured figures and the primitive inventory, as plain tables. Numbers are
   mono so the columns line up. */
.metrics {
  width: 100%;
  margin-top: clamp(36px, 4.6vw, 54px);
  border-collapse: collapse;
  text-align: left;
}
.metrics th,
.metrics td {
  padding: 15px 18px 15px 0;
  border-bottom: 1px solid var(--line);
  vertical-align: baseline;
}
.metrics thead th {
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
  color: var(--muted);
  padding-bottom: 11px;
}
.metrics tbody th {
  font-size: 16px;
  font-weight: 800;
  letter-spacing: -0.018em;
}
.metrics tbody th span {
  display: block;
  margin-top: 3px;
  font-size: 13.5px;
  font-weight: 500;
  letter-spacing: 0;
  color: var(--muted);
}
.metrics td {
  font-family: var(--font-system);
  font-size: 15px;
  font-weight: 600;
}
/* Four prose columns do not fit a phone. The table scrolls inside its own
   box, never the page — the same rule the ledger card follows. */
.table-scroll {
  margin-top: clamp(36px, 4.6vw, 54px);
  overflow-x: auto;
}
.table-scroll > .metrics { margin-top: 0; min-width: 620px; }

/* An inventory table carries prose in its cells, not figures. */
.metrics.wide td {
  font-family: var(--font-voice);
  font-size: 15px;
  font-weight: 500;
  line-height: 1.45;
  color: #3f3a49;
}
.metrics tbody tr:last-child th,
.metrics tbody tr:last-child td { border-bottom: 0; }

/* One ledger row opened up, field by field. The excerpt on /enterprise shows
   that everything is recorded; this shows what a single row actually holds,
   so it names real columns and the real primary key. */
.row-anatomy {
  margin-top: clamp(36px, 4.6vw, 54px);
  padding: 24px 26px 20px;
  border-radius: 22px;
  background: var(--ink);
  color: #fff;
  overflow-x: auto;
}
.ra-head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 6px 18px;
  padding-bottom: 16px;
  border-bottom: 1px solid rgba(255, 255, 255, 0.09);
  font-family: var(--font-system);
  font-size: 12px;
  font-weight: 600;
}
.ra-head b { color: #a98ee0; font-weight: 600; letter-spacing: 0.08em; }
.ra-head span { color: rgba(255, 255, 255, 0.55); font-weight: 500; }
.ra-grid {
  display: grid;
  grid-template-columns: max-content minmax(0, 1fr);
  gap: 0 26px;
  padding-block: 6px;
  font-family: var(--font-system);
  font-size: 12px;
  line-height: 1.5;
}
.ra-grid > * { padding-block: 6px; }
.ra-col { color: #a98ee0; font-weight: 600; white-space: nowrap; }
.ra-val {
  color: rgba(255, 255, 255, 0.85);
  font-weight: 500;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.ra-val em {
  font-style: normal;
  color: rgba(255, 255, 255, 0.5);
}
/* The two tables that complete the picture — the row alone is not the whole
   record, and the page would be lying if it implied otherwise. */
.ra-sib {
  margin-top: 12px;
  padding-top: 14px;
  border-top: 1px solid rgba(255, 255, 255, 0.09);
}
.ra-sib-head {
  font-family: var(--font-system);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: rgba(255, 255, 255, 0.5);
  margin-bottom: 10px;
}

/* Introduces the tick list under it, so it sits closer to that list than a
   caption sits under the thing it captions. */
.loop-lede { margin-top: clamp(30px, 3.6vw, 42px); }
.loop-lede + .rely-list { margin-top: clamp(18px, 2.2vw, 26px); }

/* A two-column tick list, one line per property. */
.rely-list {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  column-gap: clamp(28px, 4vw, 60px);
  row-gap: 4px;
  margin-top: clamp(36px, 4.6vw, 52px);
}
.rely-list li {
  position: relative;
  padding: 13px 0 13px 30px;
  border-bottom: 1px solid var(--line);
  font-size: 16.5px;
  line-height: 1.4;
  letter-spacing: -0.014em;
}
.rely-list li::before {
  content: "";
  position: absolute;
  left: 1px;
  top: 17px;
  width: 15px;
  height: 15px;
  background: var(--tick) center / contain no-repeat;
}
.rely-list li span { color: var(--muted); }

@media (max-width: 1060px) {
  /* Two per row: four columns cannot hold a chain of model names. */
  .mf-steps.four-up { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .mf-steps.four-up .mf-step:nth-child(n) { border-left: 1px solid var(--line); padding-left: var(--colpad); }
  .mf-steps.four-up .mf-step:nth-child(2n + 1) { border-left: 0; padding-left: 0; }
}

@media (max-width: 700px) {
  .mf-steps.four-up { grid-template-columns: 1fr; row-gap: clamp(22px, 4vw, 30px); }
  .mf-steps.four-up .mf-step:nth-child(n) { border-left: 0; padding-inline: 0; min-height: 0; }
}

@media (max-width: 900px) {
  /* Two stages per row: four columns put the stage names on three lines.
     The min-height that keeps four bindings on one baseline is dead weight
     over two rows — the row itself equalises them. */
  .mf-steps { grid-template-columns: repeat(2, minmax(0, 1fr)); row-gap: clamp(24px, 4vw, 34px); }
  .mf-step { min-height: 0; }
  .mf-step:nth-child(2n + 1) { border-left: 0; padding-left: 0; }
  .mf-step:nth-child(2n) { border-left: 1px solid var(--line); }
}

@media (max-width: 760px) {
  .rely-list { grid-template-columns: 1fr; }
  .metrics th, .metrics td { padding-right: 12px; font-size: 14px; }
  .metrics.wide td { font-size: 14px; }
}

/* Brand ------------------------------------------------------------------------------ */

/* The one paragraph under the page title carries it, so it is set larger than
   body copy and measured to break where the sentence does.

   Named for the page and not `.lede`: the landing hero already wears that
   class, and `.hero .lede` sets only its margin and measure — so bare type
   rules under that name reach the primary hero unopposed and restyle it. */
.brand-lede {
  max-width: 720px;
  font-size: clamp(19px, 2vw, 24px);
  line-height: 1.42;
  letter-spacing: -0.018em;
}
.section-head .brand-lede { margin-top: clamp(20px, 2.2vw, 28px); }
.section-head .eyebrow { margin-bottom: clamp(20px, 2.2vw, 28px); }

/* The logo idea: the argument on the left, the master asset on the right, at
   the size the deck gives it. */
.idea-grid {
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
  align-items: center;
  gap: clamp(40px, 6vw, 90px);
}
.idea-copy .eyebrow { margin-bottom: clamp(20px, 2.2vw, 28px); }
.idea-copy .copy { margin-top: clamp(22px, 2.4vw, 30px); max-width: 510px; }

.idea-mark {
  position: relative;
  display: grid;
  justify-items: center;
  isolation: isolate;
}
/* The glow is anchored to the mark rather than to the band, so the symbol sits
   in its own light wherever the column lands. */
.idea-mark::before {
  content: "";
  position: absolute;
  z-index: 0;
  width: clamp(320px, 34vw, 560px);
  aspect-ratio: 1;
  top: 50%; left: 50%;
  transform: translate(-50%, -58%);
  border-radius: 50%;
  background: radial-gradient(circle,
    rgba(132, 99, 206, 0.22) 0,
    rgba(132, 99, 206, 0.07) 45%,
    rgba(132, 99, 206, 0) 70%);
  pointer-events: none;
}
.idea-mark img {
  position: relative;
  z-index: 1;
  width: clamp(190px, 20vw, 340px);
  height: auto;
}
.idea-mark figcaption { position: relative; z-index: 1; margin-top: 20px; }

/* Identity: one section, three blocks, ruled apart. A hairline separates them
   where a band would have broken the argument into three. */
.id-block + .id-rule,
.id-rule { margin: clamp(56px, 6.4vw, 84px) 0; }
.id-block > .block-head + * { margin-top: clamp(30px, 3.6vw, 42px); }
.block-head { max-width: 820px; }
.block-head .copy { margin-top: 14px; font-size: clamp(16px, 1.5vw, 18.5px); }
.section-head + .id-block { margin-top: clamp(44px, 5vw, 64px); }

/* An asset card is a preview over the two files that hand it over. The stage
   grounds each piece of artwork on a field it is approved for, so the white
   lockup is never shown on paper where it would be invisible. */
.asset-grid {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: clamp(18px, 2vw, 26px);
}
/* The symbols are small enough to sit four to a row. */
.asset-grid.symbols { grid-template-columns: repeat(5, minmax(0, 1fr)); }

/* The whole card is the field, not a coloured stage with a white shelf under
   it. The grounds are the site's own band helpers — `.mist-bg`, `.purple`,
   `.dark` — so a card's label, copy and links take the contrast those already
   define instead of a second set written here. */
.asset-card {
  display: flex;
  flex-direction: column;
  border: 1px solid transparent;
  border-radius: var(--radius-sm);
  overflow: hidden;
}
.asset-card.ground-paper { background: #fff; border-color: var(--line); }
.asset-card.mist-bg { background: var(--mist); }

.asset-stage {
  display: grid;
  place-items: center;
  padding: clamp(30px, 3.6vw, 48px) 24px;
  min-height: 156px;
}
.asset-stage img { width: auto; max-height: 52px; }
.asset-grid.symbols .asset-stage { min-height: 148px; }
.asset-grid.symbols .asset-stage img { max-height: 72px; }

.asset-card figcaption {
  display: flex;
  flex-direction: column;
  flex: 1;
  padding: 18px 22px 20px;
  border-top: 1px solid var(--line);
}
.asset-card.mist-bg figcaption { border-top-color: rgba(13, 11, 18, 0.1); }
.asset-card.purple figcaption,
.asset-card.dark figcaption { border-top-color: rgba(255, 255, 255, 0.18); }
/* The links sit on the card's floor whatever the caption above them runs to,
   so a row of cards reads as one ruled band rather than as four ragged ones. */
.asset-card .asset-links { margin-top: auto; padding-top: 16px; }

/* Files read as a row of formats rather than as prose, so they are set in the
   system voice at the size of a label. */
.asset-links {
  display: flex;
  flex-wrap: wrap;
  gap: 8px 16px;
}
.asset-links a {
  font-family: var(--font-system);
  font-size: 11.5px;
  font-weight: 600;
  letter-spacing: 0.07em;
  color: var(--violet-deep);
}
.asset-links a:hover { text-decoration: underline; text-underline-offset: 3px; }
.asset-card.purple .asset-links a,
.asset-card.dark .asset-links a { color: #fff; }
/* A band sets its label well back because it heads paragraphs. On a card the
   label is the only text there is, so it is lifted to read as quiet white
   rather than as grey. */
.asset-card.purple .rule-label,
.asset-card.dark .rule-label { color: rgba(255, 255, 255, 0.88); }

.asset-note { margin-top: clamp(24px, 3vw, 34px); max-width: 760px; }
.asset-note a { color: var(--violet-deep); text-decoration: underline; text-underline-offset: 3px; }

/* The size of a download belongs on the button, in the system voice: it is a
   fact about the file rather than part of the invitation. */
.dl-size {
  font-family: var(--font-system);
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.12em;
  opacity: 0.75;
}

.spec-card {
  padding: clamp(22px, 2.4vw, 28px);
  border-radius: var(--radius-sm);
  background: #fff;
  border: 1px solid var(--line);
}
.spec-figure {
  margin-top: 10px;
  font-size: clamp(30px, 3.2vw, 40px);
  line-height: 1.05;
  font-weight: 800;
  letter-spacing: -0.04em;
}
.spec-figure em { font-style: italic; }
.spec-figure .spec-unit { font-size: 0.5em; font-weight: 700; letter-spacing: -0.02em; margin-left: 3px; }
.spec-figure .spec-of {
  font-size: 0.44em;
  font-weight: 600;
  letter-spacing: -0.015em;
  color: var(--muted);
}

/* Clear space, drawn. The guides are one SVG on the deck's own 660x300 grid,
   and the symbol is laid over its centre — so the artwork stays a real file
   rather than a path copied into the diagram and left to drift. */
.cs-grid {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: clamp(30px, 4vw, 60px);
  align-items: center;
}
.cs-right { display: grid; gap: clamp(16px, 1.8vw, 22px); }
.cs-figure {
  position: relative;
  aspect-ratio: 660 / 300;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius-sm);
  overflow: hidden;
}
.cs-guides { position: absolute; inset: 0; width: 100%; height: 100%; }
.cs-mark {
  position: absolute;
  left: 50%; top: 50%;
  transform: translate(-50%, -50%);
  width: 22.7%;
  height: auto;
}
.cs-figure figcaption { position: absolute; right: 22px; bottom: 16px; }
.cs-mins { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: clamp(16px, 1.8vw, 22px); }
.cs-foot { display: block; }

/* Color, as the deck lays it out: violet takes the room, ink answers it, and
   the two quiet fields share a column — the proportion is the argument. */
.pal-board {
  display: grid;
  grid-template-columns: 2.1fr 1fr 1fr;
  gap: clamp(16px, 1.8vw, 22px);
  margin-top: clamp(40px, 4.8vw, 58px);
  min-height: clamp(240px, 26vw, 330px);
}
.pal-stack { display: grid; grid-template-rows: 1fr 1fr; gap: clamp(16px, 1.8vw, 22px); }
.pal-card {
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  gap: 20px;
  padding: clamp(22px, 2.4vw, 32px);
  border-radius: var(--radius);
  border: 1px solid transparent;
}
.pal-card.violet { background: var(--violet); color: #fff; }
.pal-card.ink { background: var(--ink); color: #fff; }
.pal-card.paper { background: var(--paper); border-color: var(--line); }
.pal-card.mist { background: var(--mist); border-color: rgba(13, 11, 18, 0.07); }
.pal-card.violet .rule-label,
.pal-card.ink .rule-label { color: rgba(255, 255, 255, 0.72); }
.pal-card.violet .small,
.pal-card.ink .small { color: rgba(255, 255, 255, 0.78); margin-top: 6px; }
.pal-hex {
  font-size: clamp(24px, 2.9vw, 42px);
  line-height: 1;
  font-weight: 800;
  letter-spacing: -0.04em;
}
.pal-card.ink .pal-hex,
.pal-card.paper .pal-hex,
.pal-card.mist .pal-hex { font-size: clamp(21px, 2.1vw, 30px); }

.pal-foot {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px 24px;
  margin-top: clamp(20px, 2.2vw, 26px);
}
/* Darkened from the brand values. #39C987 and #FF7C63 are signal colours,
   sized for a dot or a chip; as 15px words on a light field neither comes near
   the 4.5:1 WCAG AA asks for. The first darkening was not enough either —
   4.30:1 and 3.94:1 on Paper, and 3.75:1 and 3.44:1 on Violet Mist. These
   clear it on both, at the same hue: 5.21:1 on Paper, 4.55:1 on Mist. Measure
   before moving them. */
.acc-ok { color: #14794f; }
.acc-warn { color: #c03a25; }

/* The proportion, as one bar. Four named colors cannot say how much of each. */
.ratio { margin-top: clamp(34px, 4vw, 48px); }
.ratio-bar {
  display: flex;
  height: 14px;
  border-radius: 999px;
  overflow: hidden;
  border: 1px solid var(--line);
}
.rb.paper { background: var(--paper); }
.rb.ink { background: var(--ink); }
.rb.violet { background: var(--violet); }
.rb.green { background: var(--green); }
.rb.coral { background: var(--coral); }
.ratio-keys {
  display: flex;
  flex-wrap: wrap;
  gap: 8px 28px;
  margin-top: 14px;
  font-family: var(--font-system);
  font-size: 11.5px;
  font-weight: 600;
  letter-spacing: 0.09em;
  text-transform: uppercase;
  color: var(--muted);
}
.ratio-keys b { color: var(--ink); }

/* Type specimen: four columns between two rules, each showing a weight's
   letterforms over the line it is used for. */
.spec-row {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  border-top: 1px solid var(--line);
  border-bottom: 1px solid var(--line);
  margin-top: clamp(40px, 4.8vw, 58px);
}
.spec-col {
  display: flex;
  flex-direction: column;
  gap: clamp(20px, 2.4vw, 30px);
  padding: clamp(22px, 2.4vw, 28px) clamp(16px, 1.8vw, 24px);
  border-right: 1px solid var(--line);
}
.spec-col:first-child { padding-left: 0; }
.spec-col:last-child { padding-right: 0; border-right: 0; }
.spec-top { display: grid; gap: 5px; }
.spec-glyphs { margin-top: auto; }
.spec-glyphs.w800 { font-size: clamp(28px, 3.8vw, 55px); line-height: 1.16; font-weight: 800; letter-spacing: -0.055em; color: var(--violet); }
.spec-glyphs.w700 { font-size: clamp(27px, 3.6vw, 52px); line-height: 1.19; font-weight: 700; letter-spacing: -0.045em; }
.spec-glyphs.w400 { font-size: clamp(25px, 3.3vw, 47px); line-height: 1.23; font-weight: 400; letter-spacing: -0.035em; }
.spec-glyphs.wmono { font-family: var(--font-system); font-size: clamp(20px, 2.8vw, 40px); line-height: 1.34; font-weight: 600; letter-spacing: -0.035em; }
.spec-line.s800 { font-size: 17px; font-weight: 800; letter-spacing: -0.02em; }
.spec-line.s700 { font-size: 16px; font-weight: 700; color: var(--violet); }
.spec-line.s400 { font-size: 15px; line-height: 1.45; color: #4e4857; }
.spec-line.smono {
  font-family: var(--font-system);
  font-size: 12px;
  font-weight: 600;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--violet);
}

/* Type hierarchy: the argument on paper, the ladder on mist. */
.hier-grid {
  display: grid;
  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
  gap: 0;
  margin-top: clamp(44px, 5vw, 64px);
  border-radius: var(--radius);
  overflow: hidden;
  border: 1px solid var(--line);
}
.hier-copy {
  display: flex;
  flex-direction: column;
  gap: 18px;
  padding: clamp(30px, 3.4vw, 48px);
  background: #fff;
}
.hier-copy .hier-sub { margin-top: auto; font-size: clamp(20px, 1.9vw, 26px); }
.hier-copy .copy { font-size: clamp(16px, 1.5vw, 18px); }
.hier-copy .asset-links { gap: 8px 20px; }
.hier-rows {
  display: grid;
  gap: clamp(18px, 2vw, 26px);
  padding: clamp(30px, 3.4vw, 48px);
  background: var(--mist);
}
.hier-row {
  display: grid;
  grid-template-columns: 154px minmax(0, 1fr);
  gap: 18px;
  align-items: start;
  padding-top: 16px;
  border-top: 1px solid #bdb3d2;
}
.hier-key { display: grid; gap: 5px; }
.h-hero { font-size: clamp(30px, 4.2vw, 60px); line-height: 0.95; letter-spacing: -0.058em; font-weight: 800; }
.h-emph { font-size: clamp(24px, 3.2vw, 46px); line-height: 1; letter-spacing: -0.048em; font-weight: 700; color: var(--violet); }
.h-body { font-size: clamp(16px, 1.5vw, 19px); line-height: 1.48; color: #4e4857; }
.h-chip {
  display: inline-block;
  padding: 12px 17px;
  border: 1px solid #bdb3d2;
  border-radius: 999px;
  background: var(--paper);
  font-family: var(--font-system);
  font-size: clamp(10px, 1vw, 13px);
  font-weight: 600;
  letter-spacing: 0.13em;
  text-transform: uppercase;
}

/* Motion: three principles, each with the shape of the move it names. The
   figures are drawn, not animated — the page is the specification. */
.motion-grid {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: clamp(18px, 2vw, 28px);
  margin-top: clamp(40px, 4.8vw, 58px);
}
.motion-card {
  display: flex;
  flex-direction: column;
  padding: clamp(26px, 2.8vw, 34px);
  border-radius: var(--radius);
  border: 1px solid transparent;
}
.motion-card.ground-paper { background: #fff; border-color: var(--line); }
.motion-card .subhead { margin-top: auto; }
.motion-card .small { margin-top: 9px; }
.motion-card.purple .small { color: rgba(255, 255, 255, 0.82); }

.mo-fig { position: relative; height: 125px; margin: 22px 0 26px; }
/* Arrive: three discs gathering into full violet, travelling one line. */
.mo-arrive .mo-track {
  position: absolute; left: 2%; right: 6%; top: 53%;
  height: 1px; background: #cdbfea;
}
.mo-arrive .mo-track::after {
  content: ""; position: absolute; right: -8px; top: -4px;
  border-top: 5px solid transparent; border-bottom: 5px solid transparent;
  border-left: 8px solid var(--violet);
}
.mo-arrive .mo-dot {
  position: absolute; top: 26%; width: 70px; height: 70px; border-radius: 50%;
}
.mo-arrive .d1 { left: 0; background: var(--mist); }
.mo-arrive .d2 { left: 30%; background: #cdbfea; }
.mo-arrive .d3 { left: 60%; background: var(--violet); }
/* Connect: one unbroken thread from where the work began to where it landed. */
.mo-connect .mo-thread {
  position: absolute; left: 0; right: 0; top: 50%;
  height: 3px;
  background: linear-gradient(90deg, var(--violet), rgba(132, 99, 206, 0.15));
}
.mo-connect .mo-end {
  position: absolute; top: 50%; width: 16px; height: 16px;
  margin-top: -8px; border-radius: 50%;
}
.mo-connect .start { left: 0; background: var(--violet); }
.mo-connect .finish { right: 0; background: #fff; }
/* Resolve: three loose sheets settling into one finished object. */
.mo-resolve .mo-sheet {
  position: absolute; width: 120px; height: 72px; border-radius: 12px;
}
.mo-resolve .s1 { left: 6%; top: 2px; border: 1px solid rgba(255, 255, 255, 0.3); transform: rotate(-3deg); }
.mo-resolve .s2 { left: 16%; top: 22px; border: 1px solid rgba(255, 255, 255, 0.5); transform: rotate(3deg); }
.mo-resolve .s3 { left: 30%; top: 44px; background: #fff; }

.motion-foot {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: 8px 28px;
  margin-top: clamp(24px, 2.8vw, 34px);
}

/* Applied identity. Both stages are fixed-proportion canvases measured in
   container widths, so every object inside keeps the deck's geometry at any
   page width instead of being re-laid-out per breakpoint. */
.stage {
  position: relative;
  container-type: inline-size;
  aspect-ratio: 1124 / 400;
  margin-top: clamp(34px, 4vw, 48px);
}
.stage-foot {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  justify-content: space-between;
  gap: 10px 28px;
  margin-top: clamp(20px, 2.2vw, 26px);
  padding-top: 18px;
  border-top: 1px solid var(--line);
}
.stage-foot .small { max-width: 690px; }
.applied-next { margin-top: clamp(56px, 6.4vw, 84px); }

.bcard {
  position: absolute;
  width: 43.2cqw;
  height: 24.4cqw;
  border-radius: 1.1cqw;
  box-shadow: 0 2.5cqw 4.8cqw rgba(34, 20, 56, 0.18);
}
.bcard img { position: absolute; left: 3.4cqw; top: 3.6cqw; width: 25.4cqw; height: auto; }
.bcard-line {
  position: absolute; left: 3.6cqw; bottom: 3cqw;
  font-family: var(--font-system);
  font-size: 1.07cqw;
  font-weight: 600;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  white-space: nowrap;
}
.bcard.violet { left: 10.5cqw; top: 3.9cqw; background: var(--violet); transform: rotate(-7deg); }
.bcard.violet .bcard-line { color: rgba(255, 255, 255, 0.78); }
.bcard.paper { right: 8.4cqw; top: 7.6cqw; background: #fff; border: 1px solid var(--line); transform: rotate(6deg); }
.bcard.paper img { width: 22cqw; }
.bcard.paper .bcard-line { color: var(--muted); }

.book { position: absolute; border-radius: 1.6cqw; overflow: hidden; box-shadow: 0 2.5cqw 4.8cqw rgba(34, 20, 56, 0.2); }
.book.ink { background: var(--ink); }
.book.violet { background: var(--violet); }
.book img { position: absolute; left: 2.5cqw; top: 2.5cqw; width: 6.4cqw; height: auto; }
.book-spine { position: absolute; right: 2.1cqw; top: 0; width: 0.9cqw; height: 100%; }
.book-spine.violet { background: var(--violet); }
.book-spine.ink { background: var(--ink); }
.book-line {
  position: absolute; left: 2.5cqw; right: 2.5cqw; bottom: 2.5cqw;
  font-family: var(--font-system);
  font-size: 0.78cqw;
  line-height: 1.45;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: rgba(255, 255, 255, 0.72);
}
.book.ink.lg { left: 3cqw; top: 2cqw; width: 24cqw; height: 31.5cqw; transform: rotate(-5deg); }
.book.violet.lg { right: 9.3cqw; top: 1.2cqw; width: 22.2cqw; height: 31.7cqw; transform: rotate(5deg); }
.book.ink.sm { right: 0.7cqw; top: 11cqw; width: 12.3cqw; height: 19cqw; border-radius: 1.2cqw; transform: rotate(-3deg); }
.book.ink.sm img { width: 4.6cqw; left: 1.6cqw; top: 1.6cqw; }
.book.ink.sm .book-line { font-size: 0.66cqw; left: 1.6cqw; right: 1.1cqw; bottom: 1.8cqw; }

.book-open {
  position: absolute;
  left: 25.4cqw; top: 6.4cqw;
  width: 41.8cqw; height: 26.7cqw;
  transform: rotate(2deg);
  filter: drop-shadow(0 2.2cqw 2.7cqw rgba(34, 20, 56, 0.16));
}
.book-open .page {
  position: absolute; top: 0;
  width: 20.9cqw; height: 26.7cqw;
  background: #fff;
  border: 1px solid var(--line);
  /* The ruling is the sheet's own background, so it stays square as the stage
     scales — a stretched SVG grid would not. */
  background-image:
    linear-gradient(to right, var(--mist) 1px, transparent 1px),
    linear-gradient(to bottom, var(--mist) 1px, transparent 1px);
  background-size: 1.6cqw 1.6cqw;
}
.book-open .left { left: 0; border-radius: 1.4cqw 0.3cqw 0.3cqw 1.4cqw; }
.book-open .right { right: 0; border-left: 0; border-radius: 0.3cqw 1.4cqw 1.4cqw 0.3cqw; }
.book-open .page-fold {
  position: absolute; left: 20.7cqw; top: 0.7cqw;
  width: 0.3cqw; height: 25.3cqw;
  background: #d8d2e0;
  box-shadow: 0 0 0.9cqw rgba(13, 11, 18, 0.12);
}

.use-cols {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  column-gap: clamp(28px, 4vw, 60px);
  margin-top: clamp(40px, 4.8vw, 58px);
}
.use-col h3 { margin-bottom: 6px; }
.use-list li {
  position: relative;
  padding: 13px 0 13px 30px;
  border-bottom: 1px solid var(--line);
  font-size: 16.5px;
  line-height: 1.4;
  letter-spacing: -0.014em;
}
.use-list li em { font-style: italic; }
.use-list li::before {
  content: "";
  position: absolute;
  left: 1px;
  top: 17px;
  width: 15px;
  height: 15px;
  background: var(--tick) center / contain no-repeat;
}
/* The Never column takes a cross in Attention, so the two lists are told
   apart by their markers before a word of either is read. */
.use-list.never li::before {
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23ff7c63' stroke-width='3.4' stroke-linecap='round'%3E%3Cpath d='M5 5l14 14M19 5L5 19'/%3E%3C/svg%3E")
    center / contain no-repeat;
}

@media (max-width: 1060px) {
  .asset-grid.symbols { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .spec-row { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .spec-col:nth-child(2) { padding-right: 0; border-right: 0; }
  .spec-col:nth-child(3) { padding-left: 0; border-top: 1px solid var(--line); }
  .spec-col:nth-child(4) { border-top: 1px solid var(--line); }
  .hier-row { grid-template-columns: 1fr; gap: 10px; }
}

@media (max-width: 900px) {
  /* The mark below the argument rather than beside it: at this width the two
     columns leave the symbol too small to be the master asset. */
  .idea-grid { grid-template-columns: 1fr; gap: clamp(36px, 6vw, 54px); }
  .idea-copy .copy { max-width: none; }
  .cs-grid { grid-template-columns: 1fr; gap: clamp(28px, 5vw, 40px); }
  .hier-grid { grid-template-columns: 1fr; }
  .pal-board { grid-template-columns: 1fr 1fr; min-height: 0; }
  .pal-card { min-height: 150px; }
  .pal-stack { grid-column: 1 / -1; grid-template-rows: none; grid-template-columns: 1fr 1fr; }
  .motion-grid { grid-template-columns: 1fr; }
  .mo-fig { height: 105px; }
}

@media (max-width: 760px) {
  .asset-grid,
  .asset-grid.symbols,
  .cs-mins,
  .use-cols { grid-template-columns: 1fr; }
  .spec-row { grid-template-columns: 1fr; }
  .spec-col { padding-inline: 0; border-right: 0; border-top: 1px solid var(--line); }
  .spec-col:first-child { border-top: 0; }
  .pal-board { grid-template-columns: 1fr; }
  .pal-stack { grid-template-columns: 1fr 1fr; }
  .motion-foot { flex-direction: column; gap: 6px; }
  /* The applied-identity stages are one composition each; below this width
     they are an impression rather than a mockup, so they take more height
     rather than shrinking their objects into illegibility. */
  .stage { aspect-ratio: 1124 / 520; }
  .use-cols { row-gap: clamp(28px, 5vw, 40px); }
  .ratio-keys { gap: 6px 20px; }
}

@media (max-width: 480px) {
  /* A `.btn` never wraps, so the size stamp is what pushes this one past the
     column. The label is the invitation; the stamp is a nicety. */
  .dl-size { display: none; }
}

/* Reveal on scroll ------------------------------------------------------------------- */

html.js .reveal {
  opacity: 0;
  transform: translateY(18px);
  transition: opacity 0.7s ease, transform 0.7s ease;
}
html.js .reveal.in { opacity: 1; transform: none; }

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  html.js .reveal { opacity: 1; transform: none; transition: none; }
  .btn, .btn .arrow, .more-link .arrow, .bseg-btn, .save-tag, .ttab,
  .nav-toggle .nt-bar { transition: none; }
  [class*="an-"], .app-frame *, .orbit-stage *,
  .typing, .think-dots span, .site-nav { animation: none !important; }
  /* Static composition shows finished work: the final diary version, and
     every agent message resolved to Done. */
  .version .v1 { opacity: 0; }
  .version .v4 { opacity: 1; }
  .agent-tail .think-dots, .cm-name .stop-chip { opacity: 0; }
  .agent-done { opacity: 1; }

  /* The launch release rests on its approved version: the first draft's
     headline, deck and opening are gone rather than stacked above the ones
     that replaced them, and the panel is open. */
  .pr-panel .panel-head, .pr-panel .page-card { opacity: 1; }
  /* Three of the release's blocks are replaced during the run and one —
     the deck — is replaced twice, so the intermediate state has to go as
     well or it stacks above the copy that superseded it. */
  .pr-out, .pr-mid { display: none; }
  /* The release panel's ladder runs one further than the diary's, so the
     generic .v4 rule above has to be taken back off it — both chips are
     absolutely positioned and would otherwise overlap. */
  .version.vr .v4 { opacity: 0; }
  .version.vr .v5 { opacity: 1; }
}

/* Responsive -------------------------------------------------------------------------- */

@media (max-width: 1060px) {
  .make-grid { grid-template-columns: repeat(2, 1fr); }
  .principles { grid-template-columns: repeat(2, 1fr); }
  .trust-points { grid-template-columns: repeat(2, 1fr); }

  /* Column rules follow the 2-col layout: only every other item starts a row. */
  .principle:nth-child(4n + 1) { border-left: 1px solid var(--line); padding-left: var(--colpad); }
  .principle:nth-child(2n + 1) { border-left: 0; padding-left: 0; }
  .trust-points > div:nth-child(3n + 1) { border-left: 1px solid var(--line); padding-left: var(--colpad); }
  .trust-points > div:nth-child(2n + 1) { border-left: 0; padding-left: 0; }
}

@media (max-width: 900px) {
  /* The bar wraps: logo + CTA + hamburger on the first line, and the nav
     opens as a full-width panel below it carrying its own CTA. Scriptless
     clients get the panel always open. */
  .site-header .bar {
    height: auto;
    min-height: 76px;
    padding-block: 16px;
    flex-wrap: wrap;
    row-gap: 0;
  }
  .site-header .bar > .btn { margin-left: auto; }

  /* Content smudges through the tall open panel at the bar's 82% alpha. */
  .site-header.menu-open { background: rgba(251, 250, 253, 0.97); }

  /* The open panel can outgrow a short landscape viewport once the nav
     carries five links and the CTA. The header is fixed, so anything past
     the fold would be unreachable: cap it to the viewport and let the
     panel scroll inside itself. Scriptless is unaffected — that header is
     static, so the panel scrolls with the page. */
  html.js .site-header.menu-open {
    max-height: 100vh;
    max-height: 100dvh;
    overflow-y: auto;
    overscroll-behavior: contain;
  }

  html.js .nav-toggle { display: inline-flex; }

  .site-nav {
    order: 3;
    flex-basis: 100%;
    flex-direction: column;
    align-items: stretch;
    gap: 0;
    margin-top: 14px;
    padding-block: 4px 8px;
    border-top: 1px solid var(--line);
  }
  html.js .site-nav { display: none; }
  html.js .menu-open .site-nav { display: flex; animation: menu-in 0.22s ease; }

  /* Scriptless: the panel is always open, so a fixed header would ride
     its full height over the hero and every anchor target. Flow instead. */
  html:not(.js) .site-header {
    position: static;
    border-bottom: 1px solid var(--line);
  }

  .site-nav a:not(.btn) {
    font-size: 17px;
    color: var(--ink);
    padding-block: 14px;
  }
  .site-nav a + a:not(.btn) { border-top: 1px solid var(--line); }
}

@keyframes menu-in {
  from { opacity: 0; transform: translateY(-5px); }
}

@media (max-width: 760px) {
  .pillars { grid-template-columns: 1fr; }

  .freedom-grid, .trust-points { grid-template-columns: 1fr; }
  .make-grid, .make-grid.two { grid-template-columns: 1fr; }
  /* :nth-child(n) matches every item at the same specificity as the
     ≤1060 row-start re-adds, so this later rule wins at one column. */
  .trust-points > div:nth-child(n) { border-left: 0; padding-inline: 0; }
}

/* The field is drawn for a wide band. Narrower than this it would sit over the
   first line of the page rather than behind the corner, so the glow pulls back
   into the corner and the ring — the part that reads as a drawn object — goes
   rather than crowd the heading. */
@media (max-width: 900px) {
  .hero::before,
  .section.page-top::before { width: 460px; height: 460px; right: -190px; top: -200px; }
  .hero::after,
  .section.page-top::after { display: none; }
  /* The smaller glow is spent 190px down, well inside any band, so the floor
     the wide field needs would only be empty room here. */
  .hero,
  .section.page-top { min-height: 0; }
}

@media (max-width: 520px) {
  .principles { grid-template-columns: 1fr; }
  .principle:nth-child(n) { border-left: 0; padding-inline: 0; }
  .site-header .logo img { width: 148px; }
  .site-header .btn { padding: 11px 16px; font-size: 14px; }
  /* Menu over CTA on phones: the bar CTA yields to the hamburger and the
     CTA moves into the panel. */
  .site-header .bar > .btn { display: none; }
  .site-nav .menu-cta {
    display: inline-flex;
    justify-content: center;
    margin-block: 12px 8px;
  }
  .comm-app { padding: 16px; }
}

/* Illustration responsiveness: 4 columns → 2 panels → the same 2 panels
   scaled. The room + diary split is the hero's story, so it never stacks. */
@media (max-width: 1180px) {
  .hero-app .body { grid-template-columns: minmax(0, 1fr) minmax(0, 1.06fr); }
  .hero-app .app-side, .hero-app .app-dock { display: none; }
  .comm-feature { grid-template-columns: 1fr; gap: 44px; }
  .comm-feature .feature-text .copy { max-width: 520px; }
}

/* Below 900px the body renders the fixed 828×656 two-panel canvas — the
   layout as it stands at the breakpoint — and scales to the frame width,
   the same trick as the editor canvases. The negative bottom margin hands
   the frame the scaled height in place of the canvas's layout height.
   The factor is a frame width divided by a canvas width, which CSS cannot
   reduce to a number, so it is measured in script and the whole upgrade is
   gated on JS. Scriptless clients keep the fluid two-panel grid from the
   ≤1180 rule: cramped on a phone, but never stacked. */
@media (max-width: 900px) {
  html.js .hero-app .body {
    width: 828px;
    height: 656px;
    min-height: 0;
    transform: scale(var(--hsc, 0.4));
    transform-origin: 0 0;
    margin-bottom: calc(656px * var(--hsc, 0.4) - 656px);
  }
}

/* Pricing responsiveness: 4 columns → 2 → 1 */
@media (max-width: 1180px) {
  .plans { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

@media (max-width: 680px) {
  .plans { grid-template-columns: 1fr; }
  .bill-seg { width: 100%; justify-content: center; }
  .bseg-btn { flex: 1; justify-content: center; }
}

