/* ============================================================================
   Kit — reset, base, layout, components. One file, token-driven.
   Class names here are the contract between the ten agents: do not rename them,
   and do not restyle a component in a page's own <style>. Add a modifier instead.
   ========================================================================== */

/* --- reset --------------------------------------------------------------- */
*,*::before,*::after{ box-sizing:border-box }
html{ -webkit-text-size-adjust:100%; scroll-behavior:smooth }
body,h1,h2,h3,h4,p,figure,blockquote,dl,dd{ margin:0 }
ul[class],ol[class]{ list-style:none; margin:0; padding:0 }
img,picture,svg,video{ max-width:100%; display:block }
/* `display:block` on every image beats the `hidden` attribute, because a presentation
   rule outranks the attribute's own UA style. The wizard's logo preview is `hidden` until
   a file is chosen, and it was rendering as a broken-image glyph on first load. */
[hidden]{ display:none !important }
input,button,textarea,select{ font:inherit; color:inherit }
button{ background:none; border:0; cursor:pointer }
a{ color:var(--brand-500); text-decoration:none }
a:hover{ text-decoration:underline }
table{ border-collapse:collapse; width:100% }

/* Motion is decoration here — never the only way to understand a screen — so a
   visitor who asks for less motion loses nothing but the movement. */
@media (prefers-reduced-motion: reduce){
  *,*::before,*::after{ animation-duration:.01ms!important; animation-iteration-count:1!important;
    transition-duration:.01ms!important; scroll-behavior:auto!important }
}

/* --- base ---------------------------------------------------------------- */
body{
  font-family:var(--font-sans); font-size:var(--text-base); line-height:1.65;
  color:var(--ink-900); background:var(--canvas);
  -webkit-font-smoothing:antialiased; text-rendering:optimizeLegibility;
}
h1,h2,h3,h4{ line-height:1.2; letter-spacing:-.02em; font-weight:700; text-wrap:balance }
h1{ font-size:clamp(2rem,1.4rem + 2.6vw,3rem) }
h2{ font-size:clamp(1.5rem,1.15rem + 1.5vw,2.25rem) }
h3{ font-size:var(--text-xl) }
h4{ font-size:var(--text-lg) }
p{ text-wrap:pretty }
small,.text-sm{ font-size:var(--text-sm) }
.muted{ color:var(--ink-500) }
.lead{ font-size:var(--text-lg); color:var(--ink-700); max-width:62ch }
code,kbd{ font-family:var(--font-mono); font-size:.9em; background:var(--ink-100);
  padding:.15em .4em; border-radius:var(--radius-sm) }

/* Focus must be visible on every interactive thing. Removing it strands keyboard users. */
:focus-visible{ outline:3px solid var(--brand-500); outline-offset:2px; border-radius:var(--radius-sm) }

/* Visible only to screen readers — used for the skip link and for icon-only buttons. */
.sr-only{ position:absolute; width:1px; height:1px; padding:0; margin:-1px; overflow:hidden;
  clip:rect(0,0,0,0); white-space:nowrap; border:0 }
.skip-link{ position:absolute; left:-9999px; top:0; z-index:100; padding:var(--space-3) var(--space-4);
  background:var(--paper); color:var(--ink-900); font-weight:600;
  border-radius:0 0 var(--radius-md) 0; box-shadow:var(--shadow-md) }
.skip-link:focus{ left:0 }

/* --- layout -------------------------------------------------------------- */
.container{ width:100%; max-width:var(--container); margin-inline:auto; padding-inline:var(--space-6) }
.section{ padding-block:var(--space-20) }
.section--tight{ padding-block:var(--space-12) }
.section--flush{ padding-block:0 }
.section--alt{ background:var(--surface) }
.section--dark{ background:var(--brand-900); color:#fff }
.section--dark h1,.section--dark h2,.section--dark h3{ color:#fff }
.section--dark .muted,.section--dark .lead{ color:rgba(255,255,255,.72) }
.section__head{ max-width:72ch; margin-bottom:var(--space-10); display:flex;
  flex-direction:column; gap:var(--space-4); align-items:flex-start }
.section__head h2{ font-size:clamp(1.75rem,1.3rem + 1.9vw,2.6rem); letter-spacing:-.03em; margin:0 }
.section__head p{ margin:0; color:var(--ink-500); font-size:var(--text-lg); line-height:1.7 }
.section--dark .section__head p{ color:rgba(255,255,255,.72) }

.grid{ display:grid; gap:var(--space-6) }
.grid--2{ grid-template-columns:repeat(auto-fit,minmax(280px,1fr)) }
.grid--3{ grid-template-columns:repeat(auto-fit,minmax(260px,1fr)) }
.grid--4{ grid-template-columns:repeat(auto-fit,minmax(220px,1fr)) }
.stack{ display:flex; flex-direction:column; gap:var(--space-4) }
.stack--sm{ gap:var(--space-2) } .stack--lg{ gap:var(--space-8) }
.cluster{ display:flex; flex-wrap:wrap; gap:var(--space-3); align-items:center }
.cluster--between{ justify-content:space-between }

/* --- buttons ------------------------------------------------------------- */
.btn{
  display:inline-flex; align-items:center; justify-content:center; gap:var(--space-2);
  padding:var(--space-3) var(--space-6); border-radius:var(--radius-md);
  font-weight:600; font-size:var(--text-sm); line-height:1.2; text-decoration:none;
  border:1px solid transparent; white-space:nowrap; max-width:100%; min-height:46px;
  transition:background .18s ease, border-color .18s ease, transform .18s ease,
             color .18s ease, box-shadow .18s ease;
}
@media (max-width:640px){ .btn{ white-space:normal; text-align:center } }
.btn:hover{ text-decoration:none; transform:translateY(-1px) }
.btn:active{ transform:translateY(0) }
.btn[disabled],.btn[aria-disabled="true"]{ opacity:.45; cursor:not-allowed; transform:none }
/* The primary button carries a soft glow in its own colour rather than a grey drop
   shadow — on a dark ground a neutral shadow is invisible and does no work. */
.btn--primary{ background:var(--brand-600); color:#fff;
  box-shadow:0 6px 20px -6px color-mix(in srgb,var(--brand-500) 70%,transparent) }
.btn--primary:hover{ background:var(--brand-500); color:#fff;
  box-shadow:0 10px 28px -8px color-mix(in srgb,var(--brand-500) 85%,transparent) }
.btn--secondary{ background:var(--surface-2); color:var(--ink-900); border-color:var(--hairline) }
.btn--secondary:hover{ border-color:color-mix(in srgb,var(--brand-500) 45%,transparent); color:var(--brand-500) }
.btn--ghost{ background:transparent; color:var(--ink-700) }
.btn--ghost:hover{ background:var(--surface-2); color:var(--ink-900) }
.btn--accent{ background:var(--accent-600); color:#fff;
  box-shadow:0 6px 20px -6px color-mix(in srgb,var(--accent-500) 70%,transparent) }
.btn--accent:hover{ background:var(--accent-500); color:#fff }
/* LINE green is reserved for elements that *are* LINE — connect, add-friend, the phone
   frame. Using it as a general accent would imply an endorsement we do not have. */
.btn--line{ background:var(--line-green); color:#fff }
.btn--line:hover{ background:var(--line-green-dark); color:#fff }
.btn--lg{ padding:var(--space-4) var(--space-8); font-size:var(--text-base); min-height:56px;
  border-radius:var(--radius-md) }
.btn--sm{ padding:var(--space-2) var(--space-4); font-size:var(--text-xs); min-height:38px }
.btn--block{ width:100% }
.btn .icon{ width:1.1em; height:1.1em; flex:none }
/* An arrow that steps forward on hover. Small, but it is the difference between a link
   that looks live and one that looks printed. */
.btn--arrow .icon{ transition:transform .18s ease }
.btn--arrow:hover .icon{ transform:translateX(3px) }

/* --- badges -------------------------------------------------------------- */
.badge{
  display:inline-flex; align-items:center; gap:var(--space-2);
  padding:.34em .85em; border-radius:var(--radius-pill);
  font-size:var(--text-xs); font-weight:500; line-height:1.5;
  background:var(--surface-2); color:var(--ink-700);
  border:1px solid var(--hairline); white-space:nowrap;
}
/* The reference's tag pill: outlined, tinted, never a solid block. A grid of solid
   chips reads as a warning panel; outlined ones read as metadata. */
.badge--tag{ background:transparent; color:var(--brand-500);
  border-color:color-mix(in srgb,var(--brand-500) 34%,transparent) }
[data-theme="dark"] .badge--tag,[data-theme="dark"] .dash__nav button[aria-current="page"],
[data-theme="dark"] .dash__nav-link[aria-current="page"],[data-theme="dark"] .chip[aria-pressed="true"]{ color:var(--brand-300) }
@media (prefers-color-scheme: dark){ :root:not([data-theme="light"]) .badge--tag,
  :root:not([data-theme="light"]) .dash__nav button[aria-current="page"],
  :root:not([data-theme="light"]) .dash__nav-link[aria-current="page"],
  :root:not([data-theme="light"]) .chip[aria-pressed="true"]{ color:var(--brand-300) } }
.badge--trial{ background:color-mix(in srgb,var(--accent-500) 12%,transparent);
  color:var(--accent-500); border-color:color-mix(in srgb,var(--accent-500) 30%,transparent) }
[data-theme="dark"] .badge--trial{ color:var(--accent-300) }
@media (prefers-color-scheme: dark){ :root:not([data-theme="light"]) .badge--trial{ color:var(--accent-300) } }
.badge--new{ background:var(--ok); color:#fff; border-color:transparent }
.badge--line{ background:color-mix(in srgb,var(--line-green) 14%,transparent);
  color:var(--line-green); border-color:color-mix(in srgb,var(--line-green) 34%,transparent) }
.badge--soon{ background:var(--surface-2); color:var(--ink-500) }
.badge--live{ background:color-mix(in srgb,var(--ok) 13%,transparent); color:var(--ok);
  border-color:color-mix(in srgb,var(--ok) 30%,transparent) }
.badge--beta{ background:color-mix(in srgb,var(--info) 13%,transparent); color:var(--info);
  border-color:color-mix(in srgb,var(--info) 30%,transparent) }
.badge--planned{ background:var(--surface-2); color:var(--ink-500) }
.badge--cost{ background:color-mix(in srgb,var(--warn) 13%,transparent); color:var(--warn);
  border-color:color-mix(in srgb,var(--warn) 30%,transparent) }

/* --- eyebrow ------------------------------------------------------------- */
/* A short rule, then a letterspaced label. It is the reference's section signature and
   it does more work than a coloured heading: it says "a new idea starts here". */
.eyebrow{ display:inline-flex; align-items:center; gap:var(--space-3);
  font-size:var(--text-xs); font-weight:600; letter-spacing:.14em; text-transform:uppercase;
  color:var(--brand-500) }
.eyebrow::before{ content:""; width:28px; height:2px; border-radius:2px; background:currentColor; flex:none }
.eyebrow--accent{ color:var(--accent-500) }

/* --- cards --------------------------------------------------------------- */
.card{
  background:var(--surface); border:1px solid var(--hairline); border-radius:var(--radius-lg);
  padding:var(--space-7); display:flex; flex-direction:column; gap:var(--space-3);
  transition:border-color .2s ease, box-shadow .2s ease, transform .2s ease;
  position:relative;
}
.card--link:hover{ border-color:color-mix(in srgb,var(--brand-500) 45%,transparent);
  box-shadow:var(--shadow-md); transform:translateY(-3px) }
.card__title{ font-size:var(--text-lg); font-weight:650; color:var(--ink-900); letter-spacing:-.01em }
.card__body{ color:var(--ink-700); font-size:var(--text-sm); line-height:1.7; flex:1 }
.card__foot{ display:flex; align-items:center; justify-content:space-between; gap:var(--space-3);
  margin-top:auto; padding-top:var(--space-4); border-top:1px solid var(--hairline) }
/* The icon tile: a rounded, tinted square. It is the single most recognisable piece of
   the reference's card, and it gives a text card somewhere for the eye to land. */
.card__icon{ width:48px; height:48px; border-radius:var(--radius-md); flex:none; display:grid;
  place-items:center; color:var(--brand-500);
  background:color-mix(in srgb,var(--brand-500) 12%,transparent);
  border:1px solid color-mix(in srgb,var(--brand-500) 20%,transparent) }
.card__icon .icon{ width:22px; height:22px }
.card__icon--accent{ color:var(--accent-500);
  background:color-mix(in srgb,var(--accent-500) 12%,transparent);
  border-color:color-mix(in srgb,var(--accent-500) 20%,transparent) }

.card--bot .card__price{ font-size:var(--text-xl); font-weight:700; color:var(--ink-900);
  letter-spacing:-.02em }
.card--bot .card__price small{ font-weight:500; color:var(--ink-500); font-size:var(--text-sm) }
.card--feature{ border:1px solid var(--hairline); background:var(--surface) }
.card--case{ border-left:3px solid var(--accent-500) }
.card--case .card__metric{ font-size:var(--text-3xl); font-weight:700; color:var(--accent-500);
  line-height:1.1; letter-spacing:-.03em }
/* A "learn more" that is a link, not a button — the whole card is already the target. */
.card__more{ display:inline-flex; align-items:center; gap:var(--space-2);
  color:var(--brand-500); font-size:var(--text-sm); font-weight:600 }
.card__more .icon{ width:15px; height:15px; transition:transform .18s ease }
.card--link:hover .card__more .icon{ transform:translateX(3px) }

/* --- stat card ----------------------------------------------------------- */
/* Big number, a short accent rule under it, then the label. Reads at a glance from
   across a room, which is what a proof strip is for. */
.stat{ background:var(--surface); border:1px solid var(--hairline); border-radius:var(--radius-lg);
  padding:var(--space-7); display:flex; flex-direction:column; gap:var(--space-3) }
.stat__num{ font-size:clamp(2rem,1.4rem + 2vw,2.75rem); font-weight:700; line-height:1;
  letter-spacing:-.035em; color:var(--brand-500); font-variant-numeric:tabular-nums;
  display:inline-block; padding-bottom:var(--space-3);
  border-bottom:3px solid color-mix(in srgb,var(--brand-500) 45%,transparent);
  align-self:flex-start }
.stat__label{ font-size:var(--text-sm); color:var(--ink-700); line-height:1.6 }

/* --- panel (the hero's list card) ---------------------------------------- */
.panel{ background:var(--surface); border:1px solid var(--hairline); border-radius:var(--radius-xl);
  padding:var(--space-7); display:flex; flex-direction:column; gap:var(--space-4);
  position:relative; overflow:hidden; box-shadow:var(--shadow-lg) }
/* The gradient hairline along the top edge. One line of CSS, and it is what makes the
   card look designed rather than defaulted. */
.panel::before{ content:""; position:absolute; inset:0 0 auto; height:2px;
  background:linear-gradient(90deg,var(--accent-500),var(--brand-500) 45%,#3BD8C4) }
.panel__head{ display:flex; align-items:center; justify-content:space-between; gap:var(--space-4);
  flex-wrap:wrap }
.panel__title{ font-size:var(--text-lg); font-weight:650; color:var(--ink-900) }
.panel__row{ display:flex; align-items:flex-start; gap:var(--space-4);
  padding:var(--space-4); border-radius:var(--radius-md);
  background:var(--surface-2); border:1px solid var(--hairline);
  transition:border-color .2s ease, transform .2s ease }
.panel__row:hover{ border-color:color-mix(in srgb,var(--brand-500) 40%,transparent);
  transform:translateX(3px) }
.panel__row-icon{ width:42px; height:42px; border-radius:var(--radius-md); flex:none; display:grid;
  place-items:center; color:var(--brand-500);
  background:color-mix(in srgb,var(--brand-500) 13%,transparent) }
.panel__row-icon .icon{ width:20px; height:20px }
/* Both are spans inside a span, so without display:block the subtitle runs on from the
   title as one sentence — which is how "It opens the conversation first From a due date"
   ended up on the page. */
.panel__row-title{ display:block; font-weight:600; font-size:var(--text-sm);
  color:var(--ink-900); line-height:1.45 }
.panel__row-sub{ display:block; font-size:var(--text-xs); color:var(--ink-500);
  line-height:1.6; margin-top:4px }
.panel__row > span:last-child{ min-width:0 }

/* --- fact chips ---------------------------------------------------------- */
.facts{ display:flex; flex-wrap:wrap; gap:var(--space-3) }
.fact{ display:inline-flex; align-items:center; gap:var(--space-2);
  padding:var(--space-3) var(--space-5); border-radius:var(--radius-md);
  background:var(--surface-2); border:1px solid var(--hairline);
  font-size:var(--text-sm); color:var(--ink-500) }
.fact strong{ color:var(--brand-500); font-weight:650 }

/* --- nav ----------------------------------------------------------------- */
.nav{ position:sticky; top:0; z-index:50;
  background:color-mix(in srgb,var(--canvas) 82%,transparent);
  backdrop-filter:saturate(180%) blur(16px); -webkit-backdrop-filter:saturate(180%) blur(16px);
  border-bottom:1px solid var(--hairline) }
.nav__inner{ height:var(--nav-h); display:flex; align-items:center; gap:var(--space-8) }
.nav__brand{ font-weight:700; font-size:var(--text-lg); color:var(--ink-900); letter-spacing:-.02em;
  display:flex; align-items:center; gap:var(--space-3); flex:none }
.nav__brand:hover{ text-decoration:none }
.nav__brand-mark{ width:38px; height:38px; border-radius:var(--radius-md); flex:none;
  background:linear-gradient(145deg,var(--brand-500),var(--accent-500));
  display:grid; place-items:center; color:#fff; font-weight:800; font-size:15px;
  box-shadow:0 6px 18px -6px color-mix(in srgb,var(--brand-500) 80%,transparent) }
.nav__brand-mark::after{ content:"B" }
.nav__brand small{ display:block; font-size:11px; font-weight:500; color:var(--ink-500);
  letter-spacing:.06em; text-transform:uppercase; margin-top:1px }
.nav__links{ display:flex; gap:var(--space-7); margin-left:auto; align-items:center }
.nav__links a{ color:var(--ink-700); font-size:var(--text-sm); font-weight:500; position:relative;
  padding-block:var(--space-2) }
.nav__links a:hover{ color:var(--ink-900); text-decoration:none }
.nav__links a[aria-current="page"]{ color:var(--ink-900); font-weight:600 }
.nav__links a[aria-current="page"]::after{ content:""; position:absolute; inset:auto 0 0;
  height:2px; border-radius:2px; background:var(--brand-500) }
.nav__actions{ display:flex; gap:var(--space-3); align-items:center; flex:none }
.nav__icon-btn{ width:42px; height:42px; border-radius:var(--radius-md); display:grid; place-items:center;
  background:var(--surface-2); border:1px solid var(--hairline); color:var(--ink-700) }
.nav__icon-btn:hover{ color:var(--ink-900); border-color:var(--brand-300) }
.nav__toggle{ display:none; margin-left:auto; padding:var(--space-2); border-radius:var(--radius-sm) }
.nav__toggle .icon{ width:24px; height:24px }
@media (max-width:1000px){
  .nav__inner{ gap:var(--space-4) }
  .nav__toggle{ display:block }
  .nav__links,.nav__actions{ display:none }
  .nav[data-open="true"] .nav__links,.nav[data-open="true"] .nav__actions{
    display:flex; flex-direction:column; align-items:stretch; gap:var(--space-4);
    position:absolute; inset-inline:0; top:var(--nav-h); padding:var(--space-6);
    background:var(--paper); border-bottom:1px solid var(--hairline); box-shadow:var(--shadow-md) }
  .nav[data-open="true"] .nav__actions{ top:auto; position:static; box-shadow:none; border:0; padding-top:0 }
}

/* --- footer -------------------------------------------------------------- */
.footer{ background:var(--brand-900); color:rgba(255,255,255,.72); padding-block:var(--space-16) var(--space-8) }
.footer a{ color:rgba(255,255,255,.72); font-size:var(--text-sm) }
.footer a:hover{ color:#fff }
.footer__cols{ display:grid; gap:var(--space-8); grid-template-columns:repeat(auto-fit,minmax(160px,1fr));
  padding-bottom:var(--space-12); border-bottom:1px solid rgba(255,255,255,.12) }
.footer__col h3{ color:#fff; font-size:var(--text-sm); text-transform:uppercase;
  letter-spacing:.06em; margin-bottom:var(--space-4) }
.footer__col ul{ display:flex; flex-direction:column; gap:var(--space-2) }
.footer__legal{ padding-top:var(--space-6); display:flex; flex-wrap:wrap; gap:var(--space-4);
  justify-content:space-between; font-size:var(--text-xs) }
.footer__note{ max-width:70ch; margin-top:var(--space-4); font-size:var(--text-xs); line-height:1.7;
  color:rgba(255,255,255,.5) }

/* --- hero ---------------------------------------------------------------- */
/* Less air above, more below. With `align-items:center` a tall phone in the media column
   pushes the copy down the page, so the top padding was being paid twice and the fold
   landed halfway through the headline. */
.hero{ padding-block:var(--space-16) var(--space-20); position:relative; overflow:hidden }
.hero__inner{ display:grid; gap:var(--space-16); align-items:center;
  grid-template-columns:minmax(0,1.05fr) minmax(0,1fr) }
@media (max-width:980px){ .hero__inner{ grid-template-columns:minmax(0,1fr); gap:var(--space-12) } }
.hero__copy{ display:flex; flex-direction:column; gap:var(--space-6); align-items:flex-start }
.hero__copy h1{ margin:0 }
.hero__copy p.lead{ margin:0 }
.hero__eyebrow{ font-size:var(--text-sm); font-weight:600; color:var(--brand-500);
  letter-spacing:.04em; text-transform:uppercase }
.hero__price{ display:flex; flex-wrap:wrap; gap:var(--space-4); align-items:center;
  font-size:var(--text-sm); color:var(--ink-500); font-weight:500 }
.hero__price strong{ font-size:var(--text-2xl); color:var(--ink-900); letter-spacing:-.02em }
.hero__media{ min-width:0 }
/* The cap belongs to a phone inside the hero itself, where it must not set the height of
   the first screen. The product composition further down owns its own section and has
   the room — capping height there fought the aspect ratio and squashed a 1:2.34 handset
   to 1:1.59, which is exactly the "too short" it was meant to prevent. */
.hero .hero__media .phone{ max-height:min(620px,72vh) }

/* The headline. Tight tracking and a real size step are most of what separates a modern
   page from a dated one; the rest is restraint about everything around it. */
.hero h1{ font-size:clamp(2.5rem,1.6rem + 3.4vw,4rem); line-height:1.05; letter-spacing:-.035em;
  font-weight:700 }
.hero .lead{ font-size:var(--text-lg); line-height:1.75; color:var(--ink-700); max-width:56ch }

/* --- proof strip --------------------------------------------------------- */
.proof-strip{ display:grid; gap:var(--space-6); grid-template-columns:repeat(auto-fit,minmax(180px,1fr));
  padding-block:var(--space-8); border-block:1px solid var(--ink-300) }
.proof-strip__stat{ text-align:center }
.proof-strip__num{ font-size:var(--text-3xl); font-weight:700; letter-spacing:-.03em; color:var(--ink-900) }
.proof-strip__label{ font-size:var(--text-sm); color:var(--ink-500) }
/* Numbers the owner has not supplied yet are dotted, so every one is visible on the page
   and greppable in the source. They must never quietly become real-looking claims. */
[data-placeholder]{ border-bottom:1px dotted var(--warn); cursor:help }

/* --- pain list ----------------------------------------------------------- */
.pain-list{ display:grid; gap:var(--space-4); grid-template-columns:repeat(auto-fit,minmax(300px,1fr)) }
.pain-list li{ display:flex; gap:var(--space-3); align-items:flex-start; padding:var(--space-4);
  background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-md);
  color:var(--ink-700); font-size:var(--text-sm) }
.pain-list li::before{ content:"”"; font-size:var(--text-3xl); line-height:.7; color:var(--ink-300); flex:none }

/* --- steps --------------------------------------------------------------- */
.steps{ display:grid; gap:var(--space-8); grid-template-columns:repeat(auto-fit,minmax(240px,1fr));
  counter-reset:step }
.steps__item{ counter-increment:step; display:flex; flex-direction:column; gap:var(--space-3) }
.steps__item::before{ content:counter(step); width:40px; height:40px; border-radius:var(--radius-pill);
  background:var(--brand-600); color:#fff; display:grid; place-items:center; font-weight:700 }
.steps__title{ font-weight:700; font-size:var(--text-lg) }
.steps__body{ color:var(--ink-700); font-size:var(--text-sm) }

/* --- feature tiles ------------------------------------------------------- */
.feature-tiles{ display:grid; gap:var(--space-8); grid-template-columns:repeat(auto-fit,minmax(260px,1fr)) }

/* --- pricing ------------------------------------------------------------- */
/* Pricing is always real text, never an image: an image cannot be read by a screen
   reader, translated, or grepped when the owner changes a number. */
.pricing{ display:grid; gap:var(--space-6); grid-template-columns:repeat(auto-fit,minmax(260px,1fr)) }
.pricing__plan{ background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-lg);
  padding:var(--space-8); display:flex; flex-direction:column; gap:var(--space-4) }
.pricing__plan[data-featured="true"]{ border-color:var(--brand-500); box-shadow:var(--shadow-md); position:relative }
.pricing__plan[data-featured="true"]::before{ content:"Most popular"; position:absolute; top:-11px; left:var(--space-8);
  background:var(--brand-600); color:#fff; font-size:var(--text-xs); font-weight:600;
  padding:.15em .8em; border-radius:var(--radius-pill) }
.pricing__name{ font-weight:700; font-size:var(--text-lg) }
.pricing__price{ font-size:var(--text-4xl); font-weight:700; letter-spacing:-.03em; line-height:1 }
.pricing__price small{ font-size:var(--text-sm); font-weight:500; color:var(--ink-500); letter-spacing:0 }
.pricing__limits{ display:flex; flex-direction:column; gap:var(--space-2); font-size:var(--text-sm);
  color:var(--ink-700); flex:1 }
.pricing__limits li{ display:flex; gap:var(--space-2); align-items:flex-start }
.pricing__limits .icon{ width:16px; height:16px; color:var(--ok); flex:none; margin-top:.3em }
.pricing__note{ font-size:var(--text-xs); color:var(--ink-500); line-height:1.7 }

/* --- FAQ ----------------------------------------------------------------- */
.faq{ display:flex; flex-direction:column; gap:0; max-width:80ch }
.faq__item{ border-bottom:1px solid var(--ink-300) }
.faq__q{ width:100%; display:flex; justify-content:space-between; align-items:center; gap:var(--space-4);
  padding:var(--space-5) 0; font-weight:600; font-size:var(--text-base); text-align:left; color:var(--ink-900) }
.faq__q .icon{ width:20px; height:20px; color:var(--ink-500); flex:none; transition:transform .2s }
.faq__item[open] .faq__q .icon{ transform:rotate(45deg) }
.faq__a{ padding-bottom:var(--space-5); color:var(--ink-700); font-size:var(--text-sm); max-width:70ch }
.faq__a p + p{ margin-top:var(--space-3) }

/* --- industry tiles ------------------------------------------------------ */
.industry-tiles{ display:grid; gap:var(--space-3); grid-template-columns:repeat(auto-fill,minmax(200px,1fr)) }
.industry-tiles a{ display:flex; align-items:center; gap:var(--space-3); padding:var(--space-4);
  background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-md);
  color:var(--ink-900); font-size:var(--text-sm); font-weight:500; transition:border-color .15s,transform .15s }
.industry-tiles a:hover{ border-color:var(--brand-500); transform:translateY(-2px); text-decoration:none }
.industry-tiles .icon{ width:20px; height:20px; color:var(--brand-500); flex:none }

/* --- CTA band ------------------------------------------------------------ */
.cta-band{ background:linear-gradient(135deg,var(--brand-700),var(--brand-900)); color:#fff;
  border-radius:var(--radius-xl); padding:var(--space-16) var(--space-8); text-align:center }
.cta-band h2{ color:#fff; max-width:24ch; margin-inline:auto }
.cta-band p{ color:rgba(255,255,255,.78); max-width:60ch; margin:var(--space-4) auto var(--space-8) }
.cta-band .cluster{ justify-content:center }

/* --- phone ---------------------------------------------------------------- */
/* A real iPhone, seen straight on. Depth comes from the bezel, the glass edge and the
   shadow — not from rotating it, which skews the conversation and makes the one thing
   we are asking people to read harder to read. */
.phone{
  /* A slimmer band and a longer body. The old eleven-pixel bezel made it read as a
     prototype case; a modern handset is nearly all screen, and the extra height is what
     makes it look like a phone rather than a tile. */
  --bezel:7px;
  width:368px; max-width:min(368px,100%); aspect-ratio:368/862;
  position:relative; flex:none;
  padding:var(--bezel);
  border-radius:52px;
  background:
    linear-gradient(148deg,#8E97A8 0%,#4A5162 9%,#22262F 22%,#171A21 50%,
                    #22262F 78%, #4A5162 92%, #8E97A8 100%);
  box-shadow:
    0 0 0 1px rgba(255,255,255,.13),
    inset 0 0 0 1px rgba(255,255,255,.20),
    inset 0 1px 1px rgba(255,255,255,.28),
    0 1px 3px rgba(0,0,0,.4),
    0 26px 52px -18px rgba(0,0,0,.55),
    0 70px 130px -44px rgba(0,0,0,.72);
}
/* No side buttons. Drawn outside a 7px band they sit on the page rather than on the
   case and read as light tabs stuck to the edge — and the reference handsets show none
   at all. The frame is cleaner without them. */
.phone__side{ display:none }
/* The specular streak down the left edge. One gradient, and the frame stops looking
   like a grey rectangle. */
.phone::before{
  content:""; position:absolute; inset:0; border-radius:inherit; pointer-events:none; z-index:3;
  background:linear-gradient(105deg,rgba(255,255,255,.22) 0%,transparent 14%,
    transparent 86%,rgba(255,255,255,.10) 100%);
}
.phone__screen{
  position:absolute; inset:var(--bezel); border-radius:45px; overflow:hidden;
  display:flex; flex-direction:column; background:#8CABD8;
}
/* Status bar and dynamic island. They are what the eye reads as "phone" before it reads
   anything else on the screen. */
.phone__status-bar{
  position:absolute; inset:0 0 auto; height:50px; z-index:2; pointer-events:none;
  display:flex; align-items:center; justify-content:space-between;
  padding:15px 28px 0; font-size:13px; font-weight:600; color:#fff;
  font-variant-numeric:tabular-nums; letter-spacing:.01em;
}
.phone__island{
  position:absolute; top:15px; left:50%; transform:translateX(-50%); z-index:3;
  width:92px; height:26px; border-radius:var(--radius-pill); background:#05070B;
  box-shadow:inset 0 0 0 1px rgba(255,255,255,.07), 0 0 0 1px rgba(0,0,0,.5);
}
/* The camera, just off-centre inside the island. Nobody names it, but its absence is
   what makes a drawn phone look drawn. */
.phone__island::after{ content:""; position:absolute; right:7px; top:50%;
  transform:translateY(-50%); width:9px; height:9px; border-radius:50%;
  background:radial-gradient(circle at 34% 32%,#2B3A55 0%,#0B1220 58%,#05070B 100%);
  box-shadow:inset 0 0 0 .5px rgba(120,160,220,.35) }
.phone__signal{ display:flex; align-items:center; gap:5px }
.phone__signal svg{ width:16px; height:11px; fill:currentColor }
.phone__battery{ width:23px; height:11px; border-radius:3px; border:1px solid currentColor;
  position:relative; opacity:.9 }
.phone__battery::before{ content:""; position:absolute; inset:1.5px; right:5px; border-radius:1px;
  background:currentColor }
.phone__battery::after{ content:""; position:absolute; right:-3px; top:3px; width:1.5px; height:5px;
  border-radius:0 1px 1px 0; background:currentColor; opacity:.5 }
/* The home indicator. Without it the screen ends in nothing and reads as a picture. */
.phone__home{ position:absolute; inset:auto 0 7px; z-index:3; pointer-events:none;
  display:flex; justify-content:center }
.phone__home span{ width:134px; height:5px; border-radius:3px; background:rgba(0,0,0,.32) }

.phone__header{ background:var(--line-green); color:#fff; padding:58px var(--space-4) var(--space-3);
  display:flex; align-items:center; gap:var(--space-3); flex:none }
.phone__avatar{ width:34px; height:34px; border-radius:var(--radius-pill); background:rgba(255,255,255,.25);
  display:grid; place-items:center; font-weight:700; font-size:var(--text-xs); flex:none; overflow:hidden }
.phone__avatar img{ width:100%; height:100%; object-fit:cover }
.phone__name{ font-weight:600; font-size:var(--text-sm); line-height:1.3 }
.phone__status{ font-size:11px; opacity:.85; display:flex; align-items:center; gap:4px }
.phone__status::before{ content:""; width:6px; height:6px; border-radius:50%; background:#B9F6CA }
.phone__body{ flex:1; overflow-y:auto; padding:var(--space-4); display:flex; flex-direction:column;
  gap:var(--space-3); scroll-behavior:smooth; scrollbar-width:none }
.phone__body::-webkit-scrollbar{ display:none }
.phone__day{ align-self:center; background:rgba(0,0,0,.42); color:#fff; font-size:11px;
  padding:.15em .8em; border-radius:var(--radius-pill) }
.phone__foot{ flex:none; background:#fff; border-top:1px solid rgba(0,0,0,.08);
  padding:var(--space-2) var(--space-3) 26px; display:flex; gap:var(--space-2); align-items:center }
.phone__input{ flex:1; border:1px solid var(--ink-300); border-radius:var(--radius-pill);
  padding:var(--space-2) var(--space-4); font-size:var(--text-sm); background:#fff; color:#0F172A; min-width:0 }
.phone__send{ width:36px; height:36px; border-radius:50%; background:var(--line-green); color:#fff;
  display:grid; place-items:center; flex:none }
.phone__send .icon{ width:18px; height:18px }

.msg{ max-width:80%; font-size:14px; line-height:1.55; position:relative }
.msg--bot{ align-self:flex-start }
.msg--user{ align-self:flex-end }
.msg__bubble{ padding:var(--space-3) var(--space-4); border-radius:18px; white-space:pre-wrap;
  overflow-wrap:anywhere; box-shadow:0 1px 1px rgba(0,0,0,.08) }
.msg--bot .msg__bubble{ background:#fff; color:#0F172A; border-top-left-radius:5px }
.msg--user .msg__bubble{ background:#8DE055; color:#0F172A; border-top-right-radius:5px }
.msg__time{ font-size:10px; color:#2B3A55; margin-top:3px }
.msg--user .msg__time{ text-align:right }

.quick-replies{ display:flex; gap:var(--space-2); overflow-x:auto; padding:var(--space-1) 0 var(--space-2);
  scrollbar-width:none; align-self:stretch }
.quick-replies::-webkit-scrollbar{ display:none }
.quick-replies button{ flex:none; background:#fff; color:var(--line-green-dark);
  border:1px solid var(--line-green); border-radius:var(--radius-pill);
  padding:.42em 1em; font-size:13px; font-weight:600; white-space:nowrap; min-height:34px }
.quick-replies button:hover{ background:#E9FAF0 }

.flex-card{ background:#fff; border-radius:14px; overflow:hidden; box-shadow:0 2px 6px rgba(0,0,0,.16);
  align-self:flex-start; max-width:86%; width:266px }
/* A real photograph, not an icon in a tinted box. A Flex card in LINE nearly always
   leads with an image, and a glyph where a photo should be reads as a placeholder. */
.flex-card__img{ aspect-ratio:16/9; background:#E7EDF6; display:grid; place-items:center;
  color:var(--brand-700); overflow:hidden; position:relative }
.flex-card__img img{ width:100%; height:100%; object-fit:cover; display:block }
.flex-card__img .icon{ width:34px; height:34px }
.flex-card__body{ padding:var(--space-3) var(--space-4); color:#0F172A }
.flex-card__title{ font-weight:700; font-size:14px; line-height:1.35 }
/* The card's own greys are ours to choose, not LINE's — --ink-500 on white is 3.5:1. */
.flex-card__subtitle{ font-size:12px; color:#5A6478; margin-top:2px }
.flex-card__lines{ margin-top:var(--space-2); display:flex; flex-direction:column; gap:3px;
  font-size:12.5px; color:#39445A; line-height:1.5 }
.flex-card__buttons{ border-top:1px solid #E7EDF6; display:flex; flex-direction:column }
.flex-card__buttons button{ padding:var(--space-3); font-size:13px; font-weight:600;
  color:var(--line-green-dark); border-bottom:1px solid #E7EDF6; min-height:42px }
.flex-card__buttons button:last-child{ border-bottom:0 }
.flex-card__buttons button:hover{ background:#F3FBF6 }
.flex-carousel{ display:flex; gap:var(--space-2); overflow-x:auto; align-self:stretch; padding-bottom:var(--space-2) }
.flex-carousel .flex-card{ flex:none; width:224px; max-width:none }

.rich-menu{ display:grid; grid-template-columns:repeat(3,1fr); gap:1px; background:var(--ink-300);
  border-top:1px solid var(--ink-300); flex:none }
.rich-menu button{ background:var(--brand-600); color:#fff; padding:var(--space-4) var(--space-2);
  font-size:11px; font-weight:600; display:flex; flex-direction:column; align-items:center;
  gap:4px; min-height:56px }
.rich-menu .icon{ width:18px; height:18px }

/* --- demo frame ---------------------------------------------------------- */
/* Two panes on purpose: the left is what the customer sees in LINE, the right is what
   the business gets from the same conversation. Shown apart, neither makes the case. */
.demo-frame{ display:grid; grid-template-columns:minmax(320px,400px) minmax(0,1fr);
  gap:var(--space-6); align-items:start; container-type:inline-size }
/* A compact demo is mounted inside a hero column, not across the page, so it has to
   react to the width it is actually given. A viewport media query still reads "desktop"
   while the frame is overrunning a half-width column beside the hero copy. */
@container (max-width: 760px){ .demo-frame{ grid-template-columns:minmax(0,1fr) } }
/* mountDemo({height}) sets --demo-h. Without these rules it set a variable nobody read,
   so every "full height" demo on the site was silently the default size. */
.demo-frame[style*="--demo-h"] .phone{ height:var(--demo-h); aspect-ratio:auto }
.demo-frame[style*="--demo-h"] .log{ height:calc(var(--demo-h) - 260px); min-height:180px }
@media (max-width:900px){
  .demo-frame[style*="--demo-h"] .phone{ height:auto; aspect-ratio:375/812 }
  .demo-frame[style*="--demo-h"] .log{ height:260px }
}
@media (max-width:900px){ .demo-frame{ grid-template-columns:minmax(0,1fr) } }
/* Same trap as the phone column: overflow-x:auto only scrolls once the track is allowed
   to be narrower than its content, and a grid item's min-width:auto forbids that. Without
   min-width:0 the four 260px scenario chips widened the whole page instead of scrolling. */
.demo-frame__chips{ grid-column:1/-1; display:flex; gap:var(--space-2); overflow-x:auto;
  padding-bottom:var(--space-2); min-width:0 }
.demo-frame__chip{ flex:none; text-align:left; padding:var(--space-3) var(--space-4);
  background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-md);
  min-width:200px; max-width:260px; transition:border-color .15s,background .15s }
.demo-frame__chip:hover{ border-color:var(--brand-500) }
.demo-frame__chip[aria-pressed="true"]{ border-color:var(--brand-500); background:var(--brand-100) }
.demo-frame__chip strong{ display:block; font-size:var(--text-sm); color:var(--ink-900) }
.demo-frame__chip span{ display:block; font-size:var(--text-xs); color:var(--ink-500); margin-top:2px }
/* A grid item defaults to min-width:auto, which here means "never narrower than the
   phone's 375px" — so below the breakpoint the track refused to shrink and the page
   scrolled sideways on any handset under ~425px. The phone already carries
   max-width:100%; it was the column that would not yield. */
.demo-frame__phone{ display:flex; justify-content:center; min-width:0 }
/* With no chips and no business panel there is only one child, so the two-pane grid
   would leave an empty column beside the phone. */
.demo-frame:not(:has(.demo-frame__biz)){ grid-template-columns:minmax(0,1fr) }
.demo-frame__biz{ display:flex; flex-direction:column; gap:var(--space-4); min-width:0 }
.demo-frame__biz-head{ display:flex; justify-content:space-between; align-items:center; gap:var(--space-3) }
.demo-frame__biz-head h3{ font-size:var(--text-sm); text-transform:uppercase; letter-spacing:.06em;
  color:var(--ink-500) }

.kpi-tiles{ display:grid; gap:var(--space-3); grid-template-columns:repeat(auto-fit,minmax(140px,1fr)) }
.kpi-tile{ background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-md);
  padding:var(--space-4) }
.kpi-tile__value{ font-size:var(--text-3xl); font-weight:700; line-height:1; letter-spacing:-.03em;
  color:var(--ink-900); font-variant-numeric:tabular-nums }
.kpi-tile__label{ font-size:var(--text-xs); color:var(--ink-500); margin-top:var(--space-2); line-height:1.4 }
.kpi-tile[data-bumped="true"]{ border-color:var(--ok); background:color-mix(in srgb,var(--ok) 8%,var(--paper)) }

/* A console is dark in both themes — it is a terminal, not a surface. Painting it with
   `--ink-900` meant it inverted with the theme: in dark mode that token is near-white, so
   the log rendered as pale grey text on a white panel and could not be read at all. */
.log{ background:#070B14; color:#C3CEDF; border:1px solid rgba(255,255,255,.09);
  border-radius:var(--radius-md); padding:var(--space-4);
  font-family:var(--font-mono); font-size:11.5px; line-height:1.75; height:260px; overflow-y:auto;
  display:flex; flex-direction:column; gap:2px }
.log__line{ display:flex; gap:var(--space-2) }
.log__ts{ color:#64748B; flex:none }
.log__line[data-level="ok"] .log__text{ color:#86EFAC }
.log__line[data-level="info"] .log__text{ color:#93C5FD }
.log__line[data-level="warn"] .log__text{ color:#FCD34D }
.log__text b{ color:#fff }
.log__empty{ color:#8A99B3; font-style:italic }

/* --- wizard -------------------------------------------------------------- */
.wizard{ display:grid; gap:var(--space-8); grid-template-columns:220px minmax(0,1fr) 340px; align-items:start }
@media (max-width:1200px){ .wizard{ grid-template-columns:200px minmax(0,1fr) } .wizard__preview{ display:none } }
@media (max-width:900px){ .wizard{ grid-template-columns:minmax(0,1fr) } }
.wizard__steps{ display:flex; flex-direction:column; gap:var(--space-1); position:sticky; top:calc(var(--nav-h) + var(--space-6)) }
.wizard__step{ display:flex; gap:var(--space-3); align-items:center; padding:var(--space-3);
  border-radius:var(--radius-md); font-size:var(--text-sm); color:var(--ink-500); text-align:left; width:100% }
.wizard__step[aria-current="step"]{ background:var(--brand-100); color:var(--brand-700); font-weight:600 }
[data-theme="dark"] .wizard__step[aria-current="step"]{ color:var(--brand-300) }
@media (prefers-color-scheme: dark){ :root:not([data-theme="light"]) .wizard__step[aria-current="step"]{ color:var(--brand-300) } }
.wizard__step[data-done="true"]{ color:var(--ok) }
.wizard__step-num{ width:26px; height:26px; border-radius:50%; border:1.5px solid currentColor;
  display:grid; place-items:center; font-size:var(--text-xs); flex:none; font-weight:600 }
.wizard__panel{ background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-lg);
  padding:var(--space-8); display:flex; flex-direction:column; gap:var(--space-6) }
.wizard__preview{ position:sticky; top:calc(var(--nav-h) + var(--space-6)); display:flex;
  flex-direction:column; gap:var(--space-3); align-items:center }
.wizard__preview .phone{ width:300px; transform-origin:top center }
.wizard__foot{ display:flex; justify-content:space-between; gap:var(--space-4);
  padding-top:var(--space-6); border-top:1px solid var(--ink-100) }
.wizard__autosave{ font-size:var(--text-xs); color:var(--ink-500); display:flex; align-items:center; gap:var(--space-2) }

/* --- forms --------------------------------------------------------------- */
.form{ display:flex; flex-direction:column; gap:var(--space-5) }
.form__row{ display:grid; gap:var(--space-5); grid-template-columns:repeat(auto-fit,minmax(220px,1fr)) }
.field{ display:flex; flex-direction:column; gap:var(--space-2); min-width:0 }
.field__label{ font-size:var(--text-sm); font-weight:600; color:var(--ink-900) }
.field__label[data-required="true"]::after{ content:" *"; color:var(--err) }
.field__hint{ font-size:var(--text-xs); color:var(--ink-500); line-height:1.6 }
.field__error{ font-size:var(--text-xs); color:var(--err); font-weight:500 }
.field input[type=text],.field input[type=email],.field input[type=password],.field input[type=url],
.field input[type=tel],.field input[type=number],.field input[type=date],.field select,.field textarea{
  width:100%; padding:var(--space-3) var(--space-4); border:1px solid var(--ink-300);
  border-radius:var(--radius-md); background:var(--paper); color:var(--ink-900);
  font-size:var(--text-sm); min-height:44px; transition:border-color .15s }
.field textarea{ min-height:110px; resize:vertical; line-height:1.6 }
.field input:focus,.field select:focus,.field textarea:focus{ border-color:var(--brand-500) }
.field[data-invalid="true"] input,.field[data-invalid="true"] select,.field[data-invalid="true"] textarea{
  border-color:var(--err) }
.field input[type=color]{ width:52px; height:44px; padding:2px; border:1px solid var(--ink-300);
  border-radius:var(--radius-md); background:var(--paper) }
.field--inline{ flex-direction:row; align-items:center; gap:var(--space-3) }
.switch{ display:inline-flex; align-items:center; gap:var(--space-3); cursor:pointer; font-size:var(--text-sm) }
.switch input{ position:absolute; opacity:0; width:0; height:0 }
/* Both are spans, so both need a block display: width and height simply do not apply to
   an inline box, and the thumb was rendering at zero pixels wide — an invisible control
   on every feature toggle, every panel switch and the wizard's consent boxes. */
.switch__track{ display:block; width:44px; height:26px; border-radius:var(--radius-pill);
  background:var(--ink-300); padding:3px; transition:background .18s ease; flex:none;
  border:1px solid var(--hairline) }
.switch__thumb{ display:block; width:18px; height:18px; border-radius:50%; background:#fff;
  box-shadow:0 1px 3px rgba(0,0,0,.35); transition:transform .18s ease }
.switch input:checked + .switch__track{ background:var(--brand-500) }
.switch input:checked + .switch__track .switch__thumb{ transform:translateX(18px) }
.switch input:checked + .switch__track{ border-color:transparent }
.switch input:disabled + .switch__track{ opacity:.45 }
.switch input:focus-visible + .switch__track{ outline:3px solid var(--brand-500); outline-offset:2px }
.dropzone{ border:2px dashed var(--ink-300); border-radius:var(--radius-lg); padding:var(--space-8);
  text-align:center; color:var(--ink-500); font-size:var(--text-sm); transition:border-color .15s,background .15s }
.dropzone[data-over="true"]{ border-color:var(--brand-500); background:var(--brand-100) }
.dropzone img{ max-height:80px; margin:0 auto var(--space-3) }

/* --- table --------------------------------------------------------------- */
.table-wrap{ overflow-x:auto; border:1px solid var(--ink-300); border-radius:var(--radius-md) }
.table{ font-size:var(--text-sm); min-width:520px }
.table th,.table td{ padding:var(--space-3) var(--space-4); text-align:left;
  border-bottom:1px solid var(--ink-100); vertical-align:top }
.table th{ background:var(--ink-100); font-weight:600; color:var(--ink-700); white-space:nowrap }
.table tr:last-child td{ border-bottom:0 }
.table td .btn{ min-height:32px; padding:var(--space-1) var(--space-3) }

/* --- tabs ---------------------------------------------------------------- */
.tabs{ display:flex; gap:var(--space-1); border-bottom:1px solid var(--ink-300); overflow-x:auto }
.tabs button{ padding:var(--space-3) var(--space-5); font-size:var(--text-sm); font-weight:600;
  color:var(--ink-500); border-bottom:2px solid transparent; white-space:nowrap; margin-bottom:-1px }
.tabs button[aria-selected="true"]{ color:var(--brand-500); border-bottom-color:var(--brand-500) }

/* --- toast / modal / skeleton -------------------------------------------- */
.toast-host{ position:fixed; bottom:var(--space-6); inset-inline-end:var(--space-6); z-index:80;
  display:flex; flex-direction:column; gap:var(--space-3); pointer-events:none }
.toast{ background:#0B1220; color:#fff; border:1px solid rgba(255,255,255,.12);
  padding:var(--space-3) var(--space-5);
  border-radius:var(--radius-md); box-shadow:var(--shadow-lg); font-size:var(--text-sm);
  pointer-events:auto; max-width:380px; animation:toast-in .2s ease-out }
.toast[data-kind="error"]{ background:var(--err) }
.toast[data-kind="ok"]{ background:var(--ok) }
@keyframes toast-in{ from{ opacity:0; transform:translateY(8px) } to{ opacity:1; transform:none } }
.modal{ border:0; padding:0; border-radius:var(--radius-lg); max-width:560px; width:calc(100% - 2rem);
  background:var(--paper); color:var(--ink-900); box-shadow:var(--shadow-lg) }
.modal::backdrop{ background:rgba(15,23,42,.55) }
.modal__body{ padding:var(--space-8); display:flex; flex-direction:column; gap:var(--space-4) }
.modal__foot{ display:flex; justify-content:flex-end; gap:var(--space-3) }
.skeleton{ background:linear-gradient(90deg,var(--ink-100) 25%,var(--ink-300) 37%,var(--ink-100) 63%);
  background-size:400% 100%; animation:skeleton 1.4s ease infinite; border-radius:var(--radius-sm);
  min-height:1em; color:transparent }
@keyframes skeleton{ from{ background-position:100% 50% } to{ background-position:0 50% } }

/* --- misc ---------------------------------------------------------------- */
.breadcrumb{ display:flex; gap:var(--space-2); font-size:var(--text-sm); color:var(--ink-500);
  flex-wrap:wrap; margin-bottom:var(--space-6) }
.breadcrumb a{ color:var(--ink-500) }
.breadcrumb li:not(:last-child)::after{ content:"›"; margin-left:var(--space-2); color:var(--ink-300) }
.breadcrumb li{ display:flex }
.channel-badges{ display:flex; flex-wrap:wrap; gap:var(--space-2) }
.qr-placeholder{ width:160px; height:160px; border:2px dashed var(--ink-300); border-radius:var(--radius-md);
  display:grid; place-items:center; text-align:center; font-size:var(--text-xs); color:var(--ink-500);
  padding:var(--space-3) }
.icon{ width:20px; height:20px; fill:none; stroke:currentColor; stroke-width:1.75;
  stroke-linecap:round; stroke-linejoin:round; flex:none }
.icon--filled{ fill:currentColor; stroke:none }
.flow-strip{ display:flex; gap:var(--space-4); overflow-x:auto; padding-bottom:var(--space-4) }
.flow-strip__screen{ flex:none; width:190px; display:flex; flex-direction:column; gap:var(--space-2) }
.flow-strip__screen figcaption{ font-size:var(--text-xs); color:var(--ink-500); line-height:1.5 }
.flow-strip__shot{ aspect-ratio:9/16; background:var(--paper); border:1px solid var(--ink-300);
  border-radius:var(--radius-md); overflow:hidden; display:flex; flex-direction:column }

/* --- feature catalogue + composer ---------------------------------------- */
.feat-grid{ display:grid; gap:var(--space-3); grid-template-columns:repeat(auto-fill,minmax(300px,1fr)) }
.feat{ background:var(--paper); border:1px solid var(--ink-300); border-radius:var(--radius-md);
  padding:var(--space-4); display:flex; flex-direction:column; gap:var(--space-2); min-width:0 }
.feat__head{ display:flex; align-items:flex-start; gap:var(--space-2); justify-content:space-between }
.feat__name{ font-weight:600; font-size:var(--text-sm); line-height:1.35; color:var(--ink-900) }
.feat__what{ font-size:var(--text-xs); color:var(--ink-700); line-height:1.6 }
.feat__meta{ display:flex; flex-wrap:wrap; gap:var(--space-2); margin-top:auto; padding-top:var(--space-2) }
.feat[data-status="live"]{ border-left:3px solid var(--ok) }
.feat[data-status="beta"]{ border-left:3px solid var(--info) }
.feat[data-status="planned"]{ border-left:3px solid var(--ink-300) }
.feat[data-on="true"]{ border-color:var(--brand-500); background:color-mix(in srgb,var(--brand-100) 45%,var(--paper)) }
.badge--live{ background:color-mix(in srgb,var(--ok) 16%,transparent); color:var(--ok) }
.badge--beta{ background:color-mix(in srgb,var(--info) 16%,transparent); color:var(--info) }
.badge--planned{ background:var(--ink-100); color:var(--ink-500) }
.badge--cost{ background:color-mix(in srgb,var(--warn) 16%,transparent); color:var(--warn) }

.feat-rail{ display:flex; flex-direction:column; gap:2px; position:sticky;
  top:calc(var(--nav-h) + var(--space-4)) }
.feat-rail button{ text-align:left; padding:var(--space-2) var(--space-3); border-radius:var(--radius-sm);
  font-size:var(--text-sm); color:var(--ink-700); display:flex; justify-content:space-between; gap:var(--space-2) }
.feat-rail button[aria-current="true"]{ background:var(--brand-100); color:var(--brand-700); font-weight:600 }
.feat-rail small{ color:var(--ink-500); font-variant-numeric:tabular-nums }

.composer{ display:grid; grid-template-columns:280px minmax(0,1fr); gap:var(--space-6); align-items:start }
@media (max-width:900px){ .composer{ grid-template-columns:minmax(0,1fr) } }
.composer > *{ min-width:0 }
.composer__item{ width:100%; text-align:left; padding:var(--space-3); border-radius:var(--radius-md);
  border:1px solid var(--ink-300); background:var(--paper); display:flex; flex-direction:column; gap:4px }
.composer__item[aria-current="true"]{ border-color:var(--brand-500); background:var(--brand-100) }
.composer__item-name{ font-weight:600; font-size:var(--text-sm) }
.composer__item-meta{ font-size:var(--text-xs); color:var(--ink-500) }
.composer__block{ border-left:2px solid var(--ink-300); padding-left:var(--space-5);
  margin-block:var(--space-6); display:flex; flex-direction:column; gap:var(--space-4) }
.composer__block-head{ display:flex; align-items:center; gap:var(--space-2); margin-left:calc(-1 * var(--space-5) - 1px) }
.composer__step{ background:var(--brand-600); color:#fff; font-size:var(--text-xs); font-weight:700;
  padding:.2em .8em; border-radius:var(--radius-pill); letter-spacing:.04em; text-transform:uppercase }
.composer__block-head .icon{ color:var(--ink-500); width:16px; height:16px }
.composer__cond{ display:flex; gap:var(--space-3); align-items:flex-end; flex-wrap:wrap;
  padding:var(--space-3); border:1px solid var(--ink-300); border-radius:var(--radius-md) }
.composer__cond .field{ flex:1; min-width:140px }
.composer__action{ padding:var(--space-4); border:1px solid var(--ink-300); border-radius:var(--radius-md);
  display:flex; flex-direction:column; gap:var(--space-3) }
.composer__action-n{ width:32px; height:32px; border-radius:var(--radius-sm); flex:none;
  background:var(--brand-100); color:var(--brand-700); display:grid; place-items:center }
.composer__action-n .icon{ width:17px; height:17px }
.composer__action select{ flex:1; min-width:180px; padding:var(--space-2) var(--space-3);
  border:1px solid var(--ink-300); border-radius:var(--radius-sm); background:var(--paper) }

/* The catalogue rail sits beside the grid on a desktop and above it on a phone. Written
   as a class rather than an inline grid-template so the breakpoint exists at all — an
   inline two-column rule cannot carry a media query, which is how a 210px rail plus a
   300px minimum card came to overflow a 375px screen by 191px. */
.feat-layout{ display:grid; grid-template-columns:210px minmax(0,1fr); gap:var(--space-8); align-items:start }
.feat-layout > *{ min-width:0 }
@media (max-width:900px){
  .feat-layout{ grid-template-columns:minmax(0,1fr); gap:var(--space-6) }
  .feat-rail{ position:static; flex-direction:row; overflow-x:auto; padding-bottom:var(--space-2) }
  .feat-rail button{ flex:none; gap:var(--space-2) }
  .feat-grid{ grid-template-columns:repeat(auto-fill,minmax(240px,1fr)) }
}

/* The stat badge that overlaps a panel's corner. Absolute, so it breaks the card's
   silhouette — which is the whole point; a rectangle inside a rectangle reads as a table. */
/* It has to sit outside the card's own edge. Overlapping the last row covered the text
   it was meant to sit beside. */
/* Overhanging to the right pushed the page 24px wider than the viewport — the container's
   own padding is all the room there is. It overlaps downward instead, which the section's
   padding absorbs. */
.panel__badge{ position:absolute; right:var(--space-5); bottom:calc(-1 * var(--space-7));
  padding:var(--space-4) var(--space-5); border-radius:var(--radius-md);
  background:var(--surface-2); border:1px solid var(--hairline);
  box-shadow:var(--shadow-lg); font-size:var(--text-xs); color:var(--ink-500);
  line-height:1.5; max-width:190px }
.panel__badge strong{ display:block; font-size:var(--text-2xl); font-weight:700; line-height:1;
  color:var(--ink-900); letter-spacing:-.02em; font-variant-numeric:tabular-nums;
  margin-bottom:2px }
@media (max-width:980px){ .panel__badge{ position:static; max-width:none; box-shadow:none } }
/* The panel clips its own gradient edge, so an overlapping badge needs the clip lifted —
   and room reserved at the bottom, or the badge lands on the last row's text. */
.panel:has(.panel__badge){ overflow:visible; padding-bottom:var(--space-16) }
@media (max-width:980px){ .panel:has(.panel__badge){ padding-bottom:var(--space-7) } }
.panel:has(.panel__badge)::before{ border-radius:var(--radius-xl) var(--radius-xl) 0 0 }

/* A phone must never grow to fill whatever column it is handed — at 500px wide its
   375:812 ratio makes it 1,083px tall and it pushes the entire page down. */
.phone{ max-width:min(375px,100%) }

/* --- bot card ------------------------------------------------------------ */
/* The whole card is the link target, but the anchor is a stretched overlay rather than a
   wrapper — so the card's own contents can still hold lists and their own semantics
   instead of being flattened into one giant link for a screen reader. */
.card--bot{ padding:0; overflow:hidden; gap:0 }
.card__hit{ position:absolute; inset:0; z-index:1; border-radius:inherit }
.card__hit:focus-visible{ outline:3px solid var(--brand-500); outline-offset:2px }
.card__photo{ aspect-ratio:16/9; overflow:hidden; background:var(--ink-100);
  border-bottom:1px solid var(--hairline) }
.card__photo img{ width:100%; height:100%; object-fit:cover;
  transition:transform .7s cubic-bezier(.19,1,.22,1) }
.card--bot:hover .card__photo img{ transform:scale(1.05) }
.card__pad{ padding:var(--space-6); display:flex; flex-direction:column; gap:var(--space-3); flex:1 }
.card__lede{ font-size:var(--text-base); color:var(--ink-900); font-weight:500; line-height:1.55;
  letter-spacing:-.01em }
/* `flex:0` is shorthand for `flex:0 1 0%` — a zero basis that cannot grow, so in a
   column flex container the paragraph collapsed to zero height while its text sat
   invisibly in the DOM. `flex:0 0 auto` is what "size to your content" actually is. */
.card--bot .card__body{ font-size:var(--text-sm); color:var(--ink-500); flex:0 0 auto }
.card__for{ font-size:var(--text-xs); color:var(--ink-500); line-height:1.6 }
.card__for span{ color:var(--brand-500); font-weight:650; text-transform:uppercase;
  letter-spacing:.08em; margin-right:var(--space-2) }
.card__does{ display:flex; flex-direction:column; gap:var(--space-2); margin-top:var(--space-1) }
.card__does li{ display:flex; gap:var(--space-2); align-items:flex-start;
  font-size:var(--text-xs); color:var(--ink-700); line-height:1.6 }
.card__does .icon{ width:14px; height:14px; color:var(--ok); flex:none; margin-top:.25em }
.card--bot .card__foot{ margin-top:auto }
.card--bot .card__more{ position:relative; z-index:2 }

/* Three across at desktop, not four. A bot card carries a photo, a promise, an audience
   and three capabilities; at a quarter of the viewport that becomes a column of
   fragments. */
.grid--bots{ display:grid; gap:var(--space-6); grid-template-columns:repeat(auto-fill,minmax(330px,1fr)) }
/* Cap the descriptive block so cards in a row stay comparable heights. */
.card--bot .card__lede{ display:-webkit-box; -webkit-line-clamp:2; -webkit-box-orient:vertical;
  overflow:hidden }
.card--bot .card__body{ display:-webkit-box; -webkit-line-clamp:3; -webkit-box-orient:vertical;
  overflow:hidden }
.card__for{ display:-webkit-box; -webkit-line-clamp:2; -webkit-box-orient:vertical; overflow:hidden }

/* ============================================================ app chrome === */
/* The builder is an application, not a page of the marketing site. It gets its own top
   bar and no marketing footer — a "Start free trial" button above a workspace someone is
   already paying for is noise, and the footer's twenty product links are a trapdoor out
   of the thing they came here to do. */
.app{ min-height:100vh; display:flex; flex-direction:column; background:var(--canvas) }
.appbar{ position:sticky; top:0; z-index:50; border-bottom:1px solid var(--hairline);
  background:color-mix(in srgb,var(--canvas) 88%,transparent);
  backdrop-filter:saturate(180%) blur(16px); -webkit-backdrop-filter:saturate(180%) blur(16px) }
.appbar__inner{ height:64px; display:flex; align-items:center; gap:var(--space-5) }
.appbar__brand{ display:flex; align-items:center; gap:var(--space-3); font-weight:700;
  color:var(--ink-900); font-size:var(--text-base); flex:none }
.appbar__brand:hover{ text-decoration:none }
.appbar__sep{ width:1px; height:24px; background:var(--hairline); flex:none }
.appbar__ws{ display:flex; align-items:center; gap:var(--space-3); min-width:0 }
.appbar__ws-name{ font-weight:600; font-size:var(--text-sm); color:var(--ink-900);
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis }
.appbar__right{ margin-left:auto; display:flex; align-items:center; gap:var(--space-3); flex:none }
.appbar__meter{ display:flex; flex-direction:column; gap:4px; min-width:150px }
.appbar__meter-label{ font-size:11px; color:var(--ink-500); display:flex; justify-content:space-between;
  gap:var(--space-3) }
.appbar__meter-track{ height:5px; border-radius:3px; background:var(--ink-100); overflow:hidden }
.appbar__meter-fill{ height:100%; border-radius:3px;
  background:linear-gradient(90deg,var(--brand-500),var(--accent-500)) }
@media (max-width:900px){ .appbar__meter, .appbar__sep{ display:none } }
/* On a phone the bar holds a brand lockup, a workspace name and two status pills that
   together are wider than the screen. The workspace identity moves into the page, where
   there is room for it; the bar keeps only what has to be reachable from anywhere. */
@media (max-width:720px){
  .appbar__inner{ gap:var(--space-3) }
  .appbar__ws{ display:none }
  .appbar__brand small{ display:none }
  .appbar__right .btn{ padding-inline:var(--space-4) }
}

/* --- sidebar ------------------------------------------------------------- */
.dash{ display:grid; grid-template-columns:248px minmax(0,1fr); gap:var(--space-10);
  align-items:start; padding-block:var(--space-8) var(--space-16) }
.dash > *{ min-width:0 }
.dash__nav{ position:sticky; top:calc(64px + var(--space-6)); display:flex; flex-direction:column;
  gap:2px }
.dash__group{ font-size:10px; font-weight:700; letter-spacing:.14em; text-transform:uppercase;
  color:var(--ink-500); padding:var(--space-5) var(--space-3) var(--space-2) }
.dash__nav button{ display:flex; align-items:center; gap:var(--space-3);
  padding:var(--space-3) var(--space-3); border-radius:var(--radius-md);
  font-size:var(--text-sm); font-weight:500; color:var(--ink-700); text-align:left; width:100%;
  transition:background .15s ease, color .15s ease }
.dash__nav button:hover{ background:var(--surface-2); color:var(--ink-900) }
.dash__nav button[aria-current="page"]{ background:color-mix(in srgb,var(--brand-500) 13%,transparent);
  color:var(--brand-500); font-weight:600 }
.dash__nav-icon{ width:30px; height:30px; border-radius:8px; flex:none; display:grid; place-items:center;
  background:var(--surface-2); border:1px solid var(--hairline); color:inherit }
.dash__nav button[aria-current="page"] .dash__nav-icon{
  background:color-mix(in srgb,var(--brand-500) 20%,transparent);
  border-color:color-mix(in srgb,var(--brand-500) 34%,transparent) }
.dash__nav .icon{ width:16px; height:16px }
@media (max-width:900px){
  .dash{ grid-template-columns:minmax(0,1fr); gap:var(--space-6) }
  .dash__nav{ position:static; flex-direction:row; overflow-x:auto; padding-bottom:var(--space-2) }
  .dash__nav button{ flex:none } .dash__group{ display:none }
}

/* --- view header --------------------------------------------------------- */
.view-head{ display:flex; flex-wrap:wrap; gap:var(--space-5); align-items:flex-end;
  justify-content:space-between; margin-bottom:var(--space-8) }
.view-head h2{ font-size:var(--text-3xl); letter-spacing:-.03em; margin:0 }
.view-head p{ color:var(--ink-500); margin:var(--space-2) 0 0; max-width:64ch }

/* --- checklist ----------------------------------------------------------- */
.check{ display:flex; flex-direction:column; gap:var(--space-3) }
.check li{ display:flex; align-items:center; gap:var(--space-4);
  padding:var(--space-4) var(--space-5); border-radius:var(--radius-md);
  background:var(--surface-2); border:1px solid var(--hairline); font-size:var(--text-sm) }
.check__mark{ width:30px; height:30px; border-radius:50%; flex:none; display:grid; place-items:center }
.check li[data-ok="true"] .check__mark{ background:color-mix(in srgb,var(--ok) 16%,transparent);
  color:var(--ok) }
.check li[data-ok="false"] .check__mark{ background:var(--ink-100); color:var(--ink-500) }
.check li[data-ok="true"]{ border-color:color-mix(in srgb,var(--ok) 24%,transparent) }
.check .icon{ width:15px; height:15px }
.check__label{ font-weight:500; color:var(--ink-900) }
.check li[data-ok="true"] .check__label{ color:var(--ink-700) }
.check__action{ margin-left:auto }

/* --- progress ring ------------------------------------------------------- */
.ring{ --p:0; width:74px; height:74px; border-radius:50%; flex:none; display:grid; place-items:center;
  background:conic-gradient(var(--brand-500) calc(var(--p) * 1%), var(--ink-100) 0) }
.ring::before{ content:""; position:absolute; width:58px; height:58px; border-radius:50%;
  background:var(--surface) }
.ring span{ position:relative; font-weight:700; font-size:var(--text-sm); color:var(--ink-900) }
.dash__ws-mobile{ display:none }
@media (max-width:720px){ .dash__ws-mobile{ display:flex } }

/* ============================================================== directory === */
/* The catalogue as a filterable directory: a sticky rail of grouped chips on the left,
   a live count and a card grid on the right. Chips rather than dropdowns because the
   whole point is seeing what the axes *are* before you choose one. */
.dir{ display:grid; grid-template-columns:264px minmax(0,1fr); gap:var(--space-12); align-items:start }
.dir > *{ min-width:0 }
@media (max-width:980px){ .dir{ grid-template-columns:minmax(0,1fr); gap:var(--space-8) } }

.filters{ position:sticky; top:calc(var(--nav-h) + var(--space-6));
  display:flex; flex-direction:column; gap:var(--space-6) }
@media (max-width:980px){ .filters{ position:static } }
.filters__head{ display:flex; align-items:center; justify-content:space-between; gap:var(--space-3);
  padding-bottom:var(--space-4); border-bottom:1px solid var(--hairline) }
.filters__head h2{ font-size:var(--text-base); font-weight:650; margin:0; letter-spacing:-.01em }
.filters__group{ display:flex; flex-direction:column; gap:var(--space-3) }
.filters__legend{ font-size:11px; font-weight:700; letter-spacing:.14em; text-transform:uppercase;
  color:var(--ink-500); display:flex; align-items:center; gap:var(--space-2) }
.filters__legend::before{ content:""; width:3px; height:13px; border-radius:2px;
  background:var(--brand-500); flex:none }
.chips{ display:flex; flex-wrap:wrap; gap:var(--space-2) }
.chip{ padding:.5em 1em; border-radius:var(--radius-pill); font-size:var(--text-xs); font-weight:500;
  background:var(--surface); border:1px solid var(--hairline); color:var(--ink-700);
  transition:border-color .16s ease, color .16s ease, background .16s ease }
.chip:hover{ border-color:var(--brand-300); color:var(--ink-900) }
.chip[aria-pressed="true"]{ border-color:var(--brand-500); color:var(--brand-500);
  background:color-mix(in srgb,var(--brand-500) 10%,transparent); font-weight:600 }
.chip__n{ opacity:.6; margin-left:.4em; font-variant-numeric:tabular-nums }

/* A slot that cannot be booked. It stays in the row rather than disappearing — a diary
   that hides its full times leaves the merchant unable to tell "sold out" from "we never
   opened that hour". Struck through and dimmed, but still legible, because the label
   next to it carries the reason. */
.chip--muted{ background:var(--surface-2); color:var(--ink-500); border-style:dashed }
/* The time is struck through; the reason after it is not. Striking the whole chip made
   「満席です」 — the only part that tells the merchant anything — the hardest thing on the
   card to read. */
.chip--muted .chip__t{ text-decoration:line-through;
  text-decoration-color:color-mix(in srgb,var(--ink-500) 55%,transparent) }
.chip--muted:hover{ border-color:var(--hairline); color:var(--ink-500) }

.dir__count{ display:flex; align-items:baseline; gap:var(--space-3); font-size:var(--text-lg);
  font-weight:600; margin-bottom:var(--space-6) }
.dir__count b{ font-size:var(--text-3xl); color:var(--brand-500); letter-spacing:-.03em;
  font-variant-numeric:tabular-nums }

/* Two prices, side by side, the way the reference states them: what it costs to start
   and what it costs to keep. A single "from" figure hides the one people ask about. */
.price-pair{ display:flex; flex-wrap:wrap; gap:var(--space-2) }
.price-pair span{ display:inline-flex; align-items:center; gap:var(--space-2);
  border-radius:var(--radius-sm); overflow:hidden; font-size:var(--text-xs); border:1px solid var(--hairline) }
.price-pair span b{ background:var(--surface-2); padding:.4em .7em; font-weight:600; color:var(--ink-500) }
.price-pair span i{ font-style:normal; padding:.4em .7em; font-weight:700; color:var(--ink-900);
  font-variant-numeric:tabular-nums }
.card__by{ display:flex; align-items:center; gap:var(--space-2); font-size:var(--text-xs);
  color:var(--ink-500) }
.card__by .icon{ width:14px; height:14px }

/* ============================================================ package page === */
/* The LINE MINI App package layout: an artwork panel beside the identity, a spec strip
   of labelled facts, numbered capability blocks, and a customer journey told in phones. */

.pkg{ display:grid; grid-template-columns:minmax(0,1fr) minmax(0,1.02fr); gap:var(--space-10);
  align-items:center }
@media (max-width:980px){ .pkg{ grid-template-columns:minmax(0,1fr); gap:var(--space-8) } }

/* The artwork panel. A tinted board with the promise set large and a handset bleeding
   off its right edge — the reference's single most recognisable element. */
.pkg-art{ position:relative; border-radius:var(--radius-lg); overflow:hidden; min-height:376px;
  padding:var(--space-8); display:flex; flex-direction:column; justify-content:center;
  gap:var(--space-4); isolation:isolate; border:1px solid var(--hairline) }
/* The copy occupies the left half; the device owns the right. Without this the promise
   sets its own width and runs underneath the handset. */
.pkg-art > *:not(.pkg-art__device):not(.pkg-art__ribbon){ max-width:calc(100% - 232px) }
@media (max-width:640px){ .pkg-art > *:not(.pkg-art__device):not(.pkg-art__ribbon){ max-width:none } }
.pkg-art::before{ content:""; position:absolute; inset:0; z-index:-1;
  background:linear-gradient(135deg,
    color-mix(in srgb,var(--brand-500) 22%,var(--surface)) 0%,
    color-mix(in srgb,var(--accent-500) 14%,var(--surface)) 100%) }
.pkg-art__ribbon{ position:absolute; top:0; left:0; z-index:2;
  background:var(--brand-600); color:#fff; font-size:var(--text-xs); font-weight:650;
  padding:.5em 1.1em; border-radius:0 0 var(--radius-md) 0; letter-spacing:.02em }
.pkg-art__brand{ font-size:var(--text-sm); font-weight:650; color:var(--ink-500);
  letter-spacing:.02em }
.pkg-art__line{ font-size:clamp(1.35rem,1rem + 1.4vw,1.9rem); font-weight:700; line-height:1.25;
  letter-spacing:-.025em; color:var(--ink-900); max-width:11ch }
.pkg-art__marks{ display:flex; gap:var(--space-3) }
.pkg-art__marks span{ width:44px; height:44px; border-radius:50%; display:grid; place-items:center;
  background:var(--surface); border:1px solid var(--hairline); color:var(--brand-500) }
.pkg-art__marks .icon{ width:20px; height:20px }
/* The handset sits half outside the board, cropped at the bottom. Anchored to the TOP so
   the island and the frame's shoulder are what shows — cropping both ends left only a
   band of screen, which reads as a rectangle rather than a phone. */
.pkg-art__device{ position:absolute; right:18px; top:34px; width:206px; z-index:1;
  pointer-events:none; filter:drop-shadow(0 22px 38px rgba(0,0,0,.42)) }
.pkg-art__device .phone{ width:206px; max-width:206px; --bezel:5px; border-radius:32px }
.pkg-art__device .phone__screen{ border-radius:29px }
.pkg-art__device .phone__island{ width:60px; height:17px; top:9px }
.pkg-art__device .phone__island::after{ width:6px; height:6px; right:5px }
.pkg-art__device .phone__status-bar{ height:32px; padding:8px 16px 0; font-size:9px }
.pkg-art__device .phone__header{ padding:34px var(--space-3) var(--space-2) }
.pkg-art__device .phone__name{ font-size:11px } .pkg-art__device .phone__status{ font-size:9px }
.pkg-art__device .phone__avatar{ width:24px; height:24px; font-size:10px }
.pkg-art__device .msg{ font-size:10.5px } .pkg-art__device .msg__bubble{ padding:8px 10px }
.pkg-art__device .phone__body{ padding:10px; gap:8px }
@media (max-width:640px){ .pkg-art__device{ display:none } }

.pkg-id{ display:flex; flex-direction:column; gap:var(--space-4); align-items:flex-start }
.pkg-id h1{ font-size:clamp(1.9rem,1.4rem + 1.9vw,2.6rem); letter-spacing:-.03em; margin:0 }
.pkg-id__lede{ color:var(--ink-700); font-size:var(--text-base); line-height:1.75; max-width:56ch }

/* --- spec strip ----------------------------------------------------------- */
.spec{ display:flex; flex-direction:column; gap:var(--space-5) }
.spec__row{ display:flex; flex-wrap:wrap; gap:var(--space-4) var(--space-8); align-items:flex-start }
.spec__item{ display:flex; align-items:center; gap:var(--space-4); min-width:0 }
.spec__label{ display:inline-flex; align-items:center; gap:var(--space-2); flex:none;
  padding:var(--space-3) var(--space-5); border-radius:var(--radius-pill);
  background:var(--surface-2); border:1px solid var(--hairline);
  font-size:var(--text-xs); font-weight:650; color:var(--ink-700); white-space:nowrap }
.spec__label .icon{ width:17px; height:17px; color:var(--brand-500) }
.spec__value{ font-size:var(--text-lg); font-weight:650; color:var(--ink-900);
  letter-spacing:-.01em }
.spec__value small{ font-size:var(--text-sm); font-weight:500; color:var(--ink-500) }
.spec__detail{ font-size:var(--text-sm); color:var(--ink-700); line-height:1.85; max-width:80ch }
.spec__detail b{ color:var(--ink-900); font-weight:600 }
.spec__note{ font-size:var(--text-sm); color:var(--ink-500); line-height:1.85 }
.spec__note li{ display:flex; gap:var(--space-2) }
.spec__note li::before{ content:"·"; color:var(--brand-500); font-weight:700 }

/* --- numbered capability blocks ------------------------------------------- */
.numbered{ display:flex; flex-direction:column; gap:var(--space-5) }
.numbered__item{ display:grid; grid-template-columns:78px minmax(0,1fr) minmax(0,340px);
  gap:var(--space-6); align-items:center; padding:var(--space-7);
  background:var(--surface-2); border:1px solid var(--hairline); border-radius:var(--radius-lg) }
@media (max-width:900px){
  .numbered__item{ grid-template-columns:56px minmax(0,1fr); gap:var(--space-5) }
  .numbered__art{ grid-column:1/-1 }
}
.numbered__n{ width:62px; height:62px; border-radius:50%; display:grid; place-items:center;
  border:2px solid color-mix(in srgb,var(--brand-500) 55%,transparent); color:var(--brand-500);
  font-size:var(--text-xl); font-weight:700; font-variant-numeric:tabular-nums; flex:none }
@media (max-width:900px){ .numbered__n{ width:48px; height:48px; font-size:var(--text-base) } }
.numbered__title{ font-size:var(--text-xl); font-weight:650; color:var(--brand-500);
  letter-spacing:-.015em; margin-bottom:var(--space-3) }
.numbered__body{ color:var(--ink-700); font-size:var(--text-sm); line-height:1.8 }
.numbered__art{ border-radius:var(--radius-md); overflow:hidden; aspect-ratio:16/10;
  border:1px solid var(--hairline); position:relative }
.numbered__art img{ width:100%; height:100%; object-fit:cover }
.numbered__art--tint{ display:grid; place-items:center; color:var(--brand-500);
  background:linear-gradient(135deg,
    color-mix(in srgb,var(--brand-500) 16%,var(--surface)),
    color-mix(in srgb,var(--accent-500) 12%,var(--surface))) }
.numbered__art--tint .icon{ width:46px; height:46px }

/* --- customer journey ----------------------------------------------------- */
/* Phones in a row with arrows between. It reads left to right as a sequence, which a
   grid of screenshots never does. */
.journey{ display:flex; align-items:flex-start; gap:var(--space-3); overflow-x:auto;
  padding-bottom:var(--space-4); scroll-snap-type:x proximity }
.journey__step{ flex:none; width:236px; display:flex; flex-direction:column; align-items:center;
  gap:var(--space-4); scroll-snap-align:start }
/* Wide enough that a sentence does not wrap to three words a line, and shown whole —
   a clipped device reads as a cropped screenshot rather than a step in a sequence. */
.journey__step .phone{ width:236px; max-width:236px; --bezel:5px; border-radius:34px }
.journey__step .phone__screen{ border-radius:29px }
.journey__step .phone__island{ width:66px; height:18px; top:9px }
.journey__step .phone__island::after{ width:6px; height:6px; right:5px }
.journey__step .phone__status-bar{ height:34px; padding:9px 17px 0; font-size:9.5px }
.journey__step .phone__header{ padding:36px var(--space-3) var(--space-2) }
.journey__step .phone__name{ font-size:11.5px; line-height:1.25 }
.journey__step .phone__status{ font-size:9px }
.journey__step .phone__avatar{ width:25px; height:25px; font-size:10px }
/* Messages sit at the bottom, the way a real chat does — and it fills the screen instead
   of leaving two thirds of it empty blue. */
.journey__step .phone__body{ padding:11px; gap:8px; justify-content:flex-end }
.pkg-art__device .phone__body{ justify-content:flex-end }
.journey__step .msg{ font-size:11px; max-width:88% }
.journey__step .msg__bubble{ padding:9px 11px; border-radius:13px }
.journey__step .msg__time{ display:none }
.journey__step .quick-replies button{ font-size:10px; padding:.35em .8em; min-height:26px }
.journey__step .flex-card{ width:100%; max-width:100%; border-radius:10px }
.journey__step .flex-card__title{ font-size:11px }
.journey__step .flex-card__lines{ font-size:10px }
.journey__step .flex-card__body{ padding:9px 11px }
.journey__cap{ text-align:center }
.journey__cap b{ display:block; font-size:var(--text-base); font-weight:650; color:var(--ink-900);
  letter-spacing:-.01em }
.journey__cap span{ display:block; font-size:var(--text-xs); color:var(--ink-500); line-height:1.6;
  margin-top:4px }
.journey__arrow{ flex:none; align-self:center; margin-top:-56px; color:var(--brand-500);
  display:grid; place-items:center; width:34px; height:34px }
.journey__arrow .icon{ width:26px; height:26px }
@media (max-width:640px){ .journey__arrow{ display:none } }

/* --- operations band ------------------------------------------------------ */
.ops{ border-radius:var(--radius-lg); overflow:hidden; border:1px solid var(--hairline) }
.ops__head{ background:var(--accent-600); color:#fff; text-align:center; font-weight:700;
  padding:var(--space-4); font-size:var(--text-lg); letter-spacing:.02em }
.ops__grid{ display:grid; gap:1px; background:var(--hairline);
  grid-template-columns:repeat(auto-fit,minmax(200px,1fr)) }
.ops__col{ background:var(--surface); padding:var(--space-7) var(--space-5);
  display:flex; flex-direction:column; gap:var(--space-4); align-items:center; text-align:center }
.ops__col-title{ font-weight:650; font-size:var(--text-base); color:var(--ink-900); line-height:1.4 }
.ops__col-icon{ width:64px; height:64px; border-radius:var(--radius-lg); display:grid;
  place-items:center; color:var(--brand-500);
  background:color-mix(in srgb,var(--brand-500) 12%,transparent) }
.ops__col-icon .icon{ width:30px; height:30px }
.ops__col-body{ font-size:var(--text-sm); color:var(--ink-700); line-height:1.7 }
.ops__col-tool{ margin-top:auto; font-size:var(--text-xs); color:var(--ink-500);
  padding-top:var(--space-4); border-top:1px dashed var(--hairline); width:100% }

/* The account rail uses links rather than buttons — each section is its own page, so a
   button that navigates would be a link wearing the wrong element. */
.dash__nav-link{ display:flex; align-items:center; gap:var(--space-3);
  padding:var(--space-3); border-radius:var(--radius-md);
  font-size:var(--text-sm); font-weight:500; color:var(--ink-700); text-decoration:none;
  transition:background .15s ease, color .15s ease }
.dash__nav-link:hover{ background:var(--surface-2); color:var(--ink-900); text-decoration:none }
.dash__nav-link[aria-current="page"]{ background:color-mix(in srgb,var(--brand-500) 13%,transparent);
  color:var(--brand-500); font-weight:600 }
.dash__nav-link[aria-current="page"] .dash__nav-icon{
  background:color-mix(in srgb,var(--brand-500) 20%,transparent);
  border-color:color-mix(in srgb,var(--brand-500) 34%,transparent) }

/* ================================================================ LIFF ====== */
/* Inside LINE these fill the screen. Opened in a desktop browser — which they must
   support — they were a narrow column on an empty field. Framing them as a device at
   wide viewports says "this is a phone screen" instead of "this page is broken". */
@media (min-width:900px){
  body.is-liff{
    min-height:100vh; padding:var(--space-12) 0;
    display:flex; align-items:flex-start; justify-content:center;
    background:
      radial-gradient(60% 50% at 50% 0%, color-mix(in srgb,var(--brand-500) 16%,transparent), transparent 70%),
      var(--canvas);
  }
  body.is-liff > main{
    /* 430, not 390. The frame's own border and padding eat about sixty pixels, and at
       390 the content box fell below the 375 these pages are written for — so headings
       wrapped mid-word inside a device meant to demonstrate them. */
    width:430px; flex:none; min-height:780px; max-height:88vh; overflow-y:auto;
    background:var(--paper); border-radius:44px; padding:var(--space-6) var(--space-4);
    border:9px solid #1A1F29;
    box-shadow:
      0 0 0 1px rgba(255,255,255,.12), inset 0 0 0 1px rgba(255,255,255,.06),
      0 30px 60px -20px rgba(0,0,0,.55), 0 80px 140px -50px rgba(0,0,0,.7);
    scrollbar-width:none;
  }
  body.is-liff > main::-webkit-scrollbar{ display:none }
  /* A note for whoever opened it in the wrong place. */
  body.is-liff::after{
    content:"This page is a LIFF screen — it opens full-size inside LINE.";
    position:fixed; inset:auto 0 var(--space-6); text-align:center;
    font-size:var(--text-xs); color:var(--ink-500); pointer-events:none;
  }
}
