/* ============================================================== Flashy site
   Shared by index.html and privacy.html.

   Two sources, deliberately kept apart:

   BRAND comes from the app icon — #4d16b9 is 87.6% of its pixels, white is the
   rest. Amber is the one added hue, taken from the lightning bolt in the mark.

   NEUTRALS come from the app itself, so the page and the product are the same
   white. They are the Material scheme Flutter generates from AppTheme.seed
   (#4f5b92), read out of the running theme rather than guessed: surface
   #fbf8ff, onSurface #1b1b21, outlineVariant #c6c5d0, and so on. The card
   surfaces use #fffbfe / #1c1b1f, which is what HandwritingCanvas paints on.
   ========================================================================= */

:root{
  color-scheme: light;

  --violet:#4d16b9;
  --violet-deep:#2b0a6b;
  --violet-lift:#7a4be8;
  --accent:#ffc24b;

  --paper:#fbf8ff;           /* ColorScheme.surface */
  --mist:#efedf4;            /* surfaceContainer */
  --mist-2:#e3e1e9;          /* surfaceContainerHighest */
  --ink:#1b1b21;             /* onSurface */
  --ink-soft:#45464f;        /* onSurfaceVariant */
  --rule:#c6c5d0;            /* outlineVariant */

  --band:var(--violet);
  --band-ink:#ffffff;
  --band-soft:#d8c9f7;
  --band-rule:#6a3ccb;

  --card:#fffbfe;            /* HandwritingCanvas paper */
  --card-rule:#e3e1e9;

  --shadow:0 1px 2px rgba(27,27,33,.07), 0 12px 32px -12px rgba(43,10,107,.2);
  --shadow-lift:0 2px 4px rgba(27,27,33,.09), 0 24px 48px -16px rgba(43,10,107,.3);

  --measure:63ch;
  --radius:18px;

  --display:"Instrument Serif", Georgia, "Times New Roman", serif;
  --body:"Instrument Sans", -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
  --hand:"Caveat", "Segoe Script", cursive;

  --ease:cubic-bezier(.2,.7,.3,1);
}

@media (prefers-color-scheme: dark){
  :root{
    color-scheme: dark;
    --paper:#121318;
    --mist:#1b1b21;
    --mist-2:#1f1f25;
    --ink:#e3e1e9;
    --ink-soft:#c6c5d0;
    --rule:#45464f;
    --band:var(--violet-deep);
    --band-rule:#4a1f9e;
    --card:#1c1b1f;
    --card-rule:#34343a;
    --shadow:0 1px 2px rgba(0,0,0,.45), 0 12px 32px -12px rgba(0,0,0,.65);
    --shadow-lift:0 2px 4px rgba(0,0,0,.55), 0 24px 48px -16px rgba(0,0,0,.75);
  }
}

/* ------------------------------------------------------------------- reset */
*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%}
@media (prefers-reduced-motion: no-preference){ html{scroll-behavior:smooth} }
body{
  margin:0;
  background:var(--paper);
  color:var(--ink);
  font:400 17px/1.6 var(--body);
  letter-spacing:-.005em;
  overflow-x:hidden;
}
img{max-width:100%;height:auto;display:block}
a{color:inherit}
:where(a,button,summary,[tabindex]):focus-visible{
  outline:3px solid var(--accent);
  outline-offset:3px;
  border-radius:6px;
}

/* ------------------------------------------------------------------ layout */
.wrap{
  width:100%;
  max-width:1080px;
  margin-inline:auto;
  padding-inline:20px;
}
.section{padding-block:clamp(56px,9vw,100px)}
.narrow{max-width:var(--measure)}
section[id]{scroll-margin-top:84px}

/* ------------------------------------------------------------------- type */
h1,h2,h3{
  font-family:var(--display);
  font-weight:400;
  line-height:1.05;
  letter-spacing:-.02em;
  text-wrap:balance;
  margin:0;
}
h1{font-size:clamp(2.6rem,7vw,4.4rem)}
h2{font-size:clamp(1.9rem,4.4vw,2.9rem)}
h3{font-size:1.25rem;line-height:1.2}
p{margin:0}

.eyebrow{
  font:500 .72rem/1 var(--body);
  letter-spacing:.14em;
  text-transform:uppercase;
  color:var(--ink-soft);
  margin:0;
}
.lede{font-size:clamp(1.05rem,2vw,1.2rem);color:var(--ink-soft);max-width:var(--measure)}

/* ====================================================================== motion

   Two mechanisms, and they stay separate.

   The hero runs a short load sequence in CSS alone, so it needs no script and
   finishes within about two seconds.

   Everything below the fold waits for `.seen`, which the observer adds. The
   hidden state lives behind `.js`, a class the page only sets when the observer
   exists AND the reader has not asked for reduced motion — so with no script,
   an old browser, or motion turned down, every section is simply visible.
   ======================================================================== */

@keyframes riseIn{ from{opacity:0;transform:translateY(14px)} to{opacity:1;transform:none} }
@keyframes drawRule{ from{transform:scaleX(0)} to{transform:scaleX(1)} }
/* the ink arriving left to right, a line at a time */
@keyframes writeIn{ from{clip-path:inset(-30% 100% -30% 0)} to{clip-path:inset(-30% -4% -30% 0)} }
@keyframes drift{
  from{transform:translate3d(-3%,-2%,0) scale(1)}
  to{transform:translate3d(4%,3%,0) scale(1.14)}
}
@keyframes cardCycle{
  0%,26%   {transform:rotateY(0deg)}
  34%,72%  {transform:rotateY(-180deg)}
  80%,100% {transform:rotateY(0deg)}
}
/* stepped, so the swap is instant and the two never overlap */
@keyframes showQ{ 0%{opacity:1} 30%{opacity:0} 76%{opacity:1} }
@keyframes showA{ 0%{opacity:0} 30%{opacity:1} 76%{opacity:0} }

.js .reveal{opacity:0;transform:translateY(18px)}
.js .reveal.seen{
  opacity:1;transform:none;
  transition:opacity .6s var(--ease), transform .6s var(--ease);
  transition-delay:calc(var(--i, 0) * 70ms);
}

@media (prefers-reduced-motion: reduce){
  *,*::before,*::after{
    animation:none !important;
    transition-duration:.001ms !important;
  }
  .reveal{opacity:1 !important;transform:none !important}
  .hand .step{clip-path:none !important}
  /* Without the animation nothing hides the answer, and both faces would be
     painted on top of each other. The card simply stays on its question. */
  .face.a{opacity:0}
}

/* ------------------------------------------------------------------ header */
.site-head{
  position:sticky;
  top:0;
  z-index:40;
  background:color-mix(in srgb, var(--paper) 88%, transparent);
  backdrop-filter:saturate(1.6) blur(14px);
  border-bottom:1px solid var(--rule);
}
.site-head .wrap{display:flex;align-items:center;gap:14px;padding-block:11px}
.brand{display:flex;align-items:center;gap:10px;text-decoration:none;font-weight:600;letter-spacing:-.01em}
.brand img{width:30px;height:30px;border-radius:8px;transition:transform .3s var(--ease)}
.brand:hover img{transform:rotate(-8deg) scale(1.06)}
.site-head nav{margin-left:auto;display:flex;align-items:center;gap:22px}
/* `:not(.btn)` matters: without it this rule outranks .btn-primary's own
   colour and paints the Play button's label in body grey on violet. */
.site-head nav a:not(.btn){text-decoration:none;color:var(--ink-soft);font-size:.92rem}
.site-head nav a:not(.btn):hover{color:var(--ink)}
@media (max-width:720px){ .site-head nav a.hide-sm{display:none} }

/* ----------------------------------------------------------------- buttons */
.btn{
  display:inline-flex;align-items:center;justify-content:center;gap:9px;
  padding:13px 22px;
  border-radius:999px;
  border:1px solid transparent;
  font:500 .98rem/1 var(--body);
  text-decoration:none;
  cursor:pointer;
  transition:transform .18s var(--ease), box-shadow .18s var(--ease), background-color .18s ease;
}
.btn-primary{background:var(--violet);color:#fff;box-shadow:var(--shadow)}
.btn-primary:hover{background:var(--violet-lift);transform:translateY(-2px);box-shadow:var(--shadow-lift)}
.btn-ghost{background:transparent;color:var(--ink);border-color:var(--rule)}
.btn-ghost:hover{border-color:var(--violet);color:var(--violet)}
.btn-sm{padding:9px 16px;font-size:.88rem}

/* ------------------------------------------------------------------ footer */
.site-foot{border-top:1px solid var(--rule);background:var(--mist)}
.site-foot .wrap{
  padding-block:34px;
  display:flex;flex-wrap:wrap;gap:14px 28px;align-items:center;
  font-size:.88rem;color:var(--ink-soft);
}
.site-foot a{color:var(--ink-soft);text-decoration:none;border-bottom:1px solid var(--rule)}
.site-foot a:hover{color:var(--violet);border-bottom-color:var(--violet)}
.site-foot .spacer{margin-left:auto}

/* ========================================================== front page only */

.hero{
  display:grid;
  grid-template-columns:minmax(0,1fr) minmax(0,420px);
  gap:clamp(36px,5vw,64px);
  align-items:center;
  padding-block:clamp(44px,7vw,80px) clamp(48px,7vw,84px);
}
@media (max-width:900px){ .hero{grid-template-columns:minmax(0,1fr)} }

.hero-copy{display:flex;flex-direction:column;gap:22px;align-items:flex-start}
.hero-copy > *{animation:riseIn .6s var(--ease) both}
.hero-copy > *:nth-child(1){animation-delay:.04s}
.hero-copy > *:nth-child(2){animation-delay:.12s}
.hero-copy > *:nth-child(3){animation-delay:.2s}
.hero-copy > *:nth-child(4){animation-delay:.28s}
.hero-copy > *:nth-child(5){animation-delay:.36s}

.hero h1 .bolt{color:var(--violet);position:relative;white-space:nowrap}
@media (prefers-color-scheme: dark){ .hero h1 .bolt{color:var(--violet-lift)} }
/* drawn on, like a line ruled under a word */
.hero h1 .bolt::after{
  content:"";position:absolute;left:0;right:0;bottom:.06em;height:.1em;
  background:var(--accent);border-radius:999px;z-index:-1;
  transform-origin:left center;
  animation:drawRule .7s .5s var(--ease) both;
}
.hero-actions{display:flex;flex-wrap:wrap;gap:12px;align-items:center}
.hero-note{font-size:.9rem;color:var(--ink-soft)}

/* ------------------------------------------------- the card illustration */
.stack{
  position:relative;
  padding:32px 16px 0 6px;
  perspective:1500px;
  animation:riseIn .7s .3s var(--ease) both;
}
.card{
  position:relative;
  background:var(--card);
  border:1px solid var(--card-rule);
  border-radius:var(--radius);
  box-shadow:var(--shadow-lift);
  padding:16px 20px 22px;
  min-height:218px;
  overflow:hidden;
}
/* ruled paper, the way a card actually looks */
.card::before{
  content:"";position:absolute;inset:0;
  background-image:repeating-linear-gradient(
    to bottom, transparent 0 31px, var(--card-rule) 31px 32px);
  opacity:.7;pointer-events:none;
}
.card > *{position:relative;z-index:1}

/* Inset from the left and flush right, so it is narrower than the card in
   front and shows only as a band along the top and right. */
.card.behind{
  position:absolute;
  top:0;left:40px;right:0;
  transform:rotate(2deg);
  z-index:0;
}

/* Both faces share one grid cell, so the taller of the two sets the height and
   neither can be clipped. */
.flipper{
  display:grid;
  transform-style:preserve-3d;
  /* ease-in-out, not --ease: the swap below happens at the midpoint of each
     half-turn, and only a symmetric curve actually puts the card edge-on at
     that midpoint. With a front-loaded curve the card passes 90° early and
     there is a gap where neither face is painted. */
  animation:cardCycle 13s 2.4s ease-in-out infinite;
}
.face{
  grid-area:1/1;
  backface-visibility:hidden;
  -webkit-backface-visibility:hidden;
}
.face.a{transform:rotateY(180deg)}

/* backface-visibility alone was not enough: the question showed through the
   answer, mirrored. These step the two faces in and out instead, so exactly
   one is ever painted. Same duration and delay as the turn above, switching
   at the midpoint of each half-turn (30% and 76%). */
.face.q{animation:showQ 13s 2.4s step-end infinite}
.face.a{animation:showA 13s 2.4s step-end infinite}
.stack:hover .flipper,
.stack:hover .face{animation-play-state:paused}

.card-tag{
  font:500 .64rem/1 var(--body);letter-spacing:.14em;text-transform:uppercase;
  color:var(--ink-soft);margin-bottom:16px;
}
.hand{font-family:var(--hand);font-size:1.7rem;line-height:1.55;color:var(--ink)}
.hand .step{display:block}
.hand .ink-blue{color:#1976d2}
.hand .ink-red{color:#d32f2f}
@media (prefers-color-scheme: dark){
  .hand .ink-blue{color:#42a5f5}
  .hand .ink-red{color:#ef5350}
}
.hand-cjk{font-family:var(--body);font-weight:500;font-size:1.5rem}

/* the sketch beside the question — a drawn diagram is half of what the app is
   for, and nothing else on the page was showing one */
.card-body{display:flex;align-items:center;gap:18px}
.sketch{flex:none;width:98px}
.sketch svg{width:100%;height:auto;display:block}
.sketch path{
  fill:none;stroke:currentColor;stroke-width:2.4;
  stroke-linecap:round;stroke-linejoin:round;
}
.sketch circle{fill:currentColor;stroke:none}
.sketch text{fill:currentColor;stroke:none;font-family:var(--hand);font-size:19px}
.lines .l{display:block}

/* only the question writes itself in, and only once: the answer was written
   earlier, which is also how it works in the app */
.face.q .hand .step{animation:writeIn .8s var(--ease) both}
.face.q .hand .step:nth-child(1){animation-delay:.6s}
.face.q .hand .step:nth-child(2){animation-delay:1.3s}

.grade-strip{
  display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:8px;
  margin-top:14px;
}
.grade{
  display:flex;flex-direction:column;gap:3px;
  align-items:center;justify-content:center;text-align:center;
  padding:11px 8px;
  background:var(--card);border:1px solid var(--rule);border-radius:13px;
  animation:riseIn .5s var(--ease) both;
}
.grade:nth-child(1){animation-delay:1.5s}
.grade:nth-child(2){animation-delay:1.6s}
.grade:nth-child(3){animation-delay:1.7s}
.grade b{font-weight:500;font-size:.82rem;color:var(--ink);line-height:1.15}
.grade span{font-size:.72rem;color:var(--ink-soft);font-variant-numeric:tabular-nums}
.stack-note{
  font-size:.84rem;color:var(--ink-soft);margin-top:12px;text-align:center;
  animation:riseIn .5s 1.85s var(--ease) both;
}

/* ------------------------------------------------------------------ thesis */
.thesis{background:var(--mist);border-block:1px solid var(--rule)}
.thesis h2{margin-bottom:20px}
.thesis p + p{margin-top:14px}
.thesis .lede{color:var(--ink)}

/* ------------------------------------------------------------- feature rows */
.rows{display:flex;flex-direction:column;gap:clamp(40px,5.5vw,64px)}
.row{display:grid;grid-template-columns:minmax(0,.8fr) minmax(0,1.2fr);gap:clamp(20px,4vw,52px);align-items:start}
@media (max-width:820px){ .row{grid-template-columns:minmax(0,1fr);gap:18px} }
.row > header{display:flex;flex-direction:column;gap:10px}
.row h2{font-size:clamp(1.7rem,3.3vw,2.3rem)}

.points{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:14px}
.points li{
  display:grid;grid-template-columns:auto minmax(0,1fr);gap:13px;align-items:start;
  padding-bottom:14px;border-bottom:1px solid var(--rule);
}
.points li:last-child{border-bottom:0;padding-bottom:0}
.points .mark{
  width:8px;height:8px;border-radius:50%;background:var(--violet);margin-top:.55em;
  transition:transform .3s var(--ease);
}
.points li:hover .mark{transform:scale(1.6)}
.points b{display:block;font-weight:600;font-size:.98rem;letter-spacing:-.01em}
.points p{color:var(--ink-soft);font-size:.95rem;margin-top:3px}

.swatches{display:flex;flex-wrap:wrap;gap:7px;margin-top:9px}
.swatches i{
  width:24px;height:24px;border-radius:50%;display:block;
  box-shadow:0 0 0 1px var(--rule) inset;
  transition:transform .25s var(--ease);
}
.swatches i:hover{transform:scale(1.25)}
.swatch-note{font-size:.82rem;color:var(--ink-soft);margin-top:9px}

/* ------------------------------------------------------------------- modes */
.modes{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:16px;margin-top:32px}
@media (max-width:820px){ .modes{grid-template-columns:minmax(0,1fr)} }
.mode{
  padding:24px 22px;background:var(--card);
  border:1px solid var(--rule);border-radius:var(--radius);
  display:flex;flex-direction:column;gap:9px;
  transition:transform .28s var(--ease), box-shadow .28s var(--ease), border-color .28s ease;
}
.mode:hover{transform:translateY(-4px);box-shadow:var(--shadow-lift);border-color:var(--violet)}
.mode h3{font-family:var(--body);font-weight:600;font-size:1.02rem;letter-spacing:-.01em}
.mode p{color:var(--ink-soft);font-size:.94rem}
.mode .tagline{font-family:var(--hand);font-size:1.3rem;color:var(--violet);line-height:1}
@media (prefers-color-scheme: dark){ .mode .tagline{color:var(--accent)} }

/* -------------------------------------------------------------- the band */
.band{background:var(--band);color:var(--band-ink);position:relative;overflow:hidden}
/* slow weather behind the type, not a gradient hero */
.band::before{
  content:"";position:absolute;inset:-35%;pointer-events:none;
  background:
    radial-gradient(38% 48% at 22% 28%, rgba(255,194,75,.2), transparent 70%),
    radial-gradient(44% 54% at 78% 72%, rgba(122,75,232,.55), transparent 72%);
  animation:drift 30s ease-in-out infinite alternate;
}
.band > *{position:relative;z-index:1}
.band h2,.band h3{color:#fff}
.band .eyebrow{color:var(--band-soft)}
.band p{color:var(--band-soft)}
.band .points li{border-bottom-color:var(--band-rule)}
.band .points .mark{background:var(--accent)}
.band .points b{color:#fff}
.band .points p{color:var(--band-soft)}

.dials{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:14px;margin-top:28px}
@media (max-width:620px){ .dials{grid-template-columns:minmax(0,1fr)} }
.dial{
  padding:20px;border:1px solid var(--band-rule);border-radius:var(--radius);
  background:rgba(255,255,255,.06);
  display:flex;flex-direction:column;gap:5px;
  transition:transform .28s var(--ease), background-color .28s ease;
}
.dial:hover{transform:translateY(-4px);background:rgba(255,255,255,.12)}
.dial b{font-weight:500;font-size:.95rem;color:#fff}
.dial .days{font-family:var(--display);font-size:2.3rem;line-height:1;color:var(--accent);font-variant-numeric:tabular-nums}
.dial span{font-size:.84rem;color:var(--band-soft)}

/* ------------------------------------------------------------------- price */
.price{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));gap:16px;margin-top:32px}
@media (max-width:760px){ .price{grid-template-columns:minmax(0,1fr)} }
.tier{
  padding:26px 24px;border:1px solid var(--rule);border-radius:var(--radius);
  background:var(--card);display:flex;flex-direction:column;gap:12px;
  transition:transform .28s var(--ease), box-shadow .28s var(--ease);
}
.tier:hover{transform:translateY(-4px);box-shadow:var(--shadow-lift)}
.tier.lead{border-color:var(--violet);box-shadow:var(--shadow)}
.tier h3{font-family:var(--body);font-weight:600;font-size:1.05rem}
.tier ul{list-style:none;margin:0;padding:0;display:flex;flex-direction:column;gap:8px}
.tier li{font-size:.94rem;color:var(--ink-soft);padding-left:20px;position:relative}
.tier li::before{
  content:"";position:absolute;left:0;top:.52em;width:9px;height:9px;
  border-radius:50%;background:var(--accent);
}
.badge{
  align-self:flex-start;
  font:500 .68rem/1 var(--body);letter-spacing:.12em;text-transform:uppercase;
  padding:6px 10px;border-radius:999px;background:var(--mist-2);color:var(--ink-soft);
}
.tier.lead .badge{background:var(--violet);color:#fff}

/* ------------------------------------------------------------------ closer */
.closer{text-align:center;display:flex;flex-direction:column;align-items:center;gap:22px}
.closer img{
  width:76px;height:76px;border-radius:20px;box-shadow:var(--shadow-lift);
  transition:transform .35s var(--ease);
}
.closer img:hover{transform:rotate(-6deg) scale(1.05)}

/* the policy link in the privacy section's header */
.policy-link{color:var(--violet);text-decoration:underline;text-underline-offset:4px}
.policy-link:hover{color:var(--violet-lift)}
@media (prefers-color-scheme: dark){ .policy-link{color:var(--violet-lift)} }

/* ============================================================ privacy page */

.doc{max-width:68ch;margin-inline:auto;padding-block:clamp(40px,6vw,72px)}
.doc-head{display:flex;flex-direction:column;gap:12px;margin-bottom:38px}
.doc-head h1{font-size:clamp(2.1rem,5vw,3.1rem)}
.doc-date{font-size:.9rem;color:var(--ink-soft)}
.doc-summary{
  background:var(--mist);
  border:1px solid var(--rule);
  border-left:4px solid var(--violet);
  border-radius:0 14px 14px 0;
  padding:20px 22px;
  margin-bottom:38px;
  font-size:1.05rem;
}
.doc h2{
  font-size:clamp(1.4rem,2.8vw,1.8rem);
  margin-top:40px;margin-bottom:14px;
  padding-top:22px;border-top:1px solid var(--rule);
}
.doc h2:first-of-type{margin-top:0}
.doc p{margin-bottom:14px;color:var(--ink)}
.doc p:last-child{margin-bottom:0}
.doc ul{margin:0 0 14px;padding-left:22px;display:flex;flex-direction:column;gap:7px}
.doc li{color:var(--ink)}
.doc a:not(.btn){color:var(--violet);text-decoration:underline;text-underline-offset:3px}
@media (prefers-color-scheme: dark){ .doc a:not(.btn){color:var(--violet-lift)} }
.doc code{
  font-family:ui-monospace,SFMono-Regular,Menlo,monospace;
  font-size:.88em;background:var(--mist-2);
  padding:2px 6px;border-radius:5px;
}
.doc-foot-note{
  margin-top:44px;padding-top:22px;border-top:1px solid var(--rule);
  font-size:.92rem;color:var(--ink-soft);
}
