/* Uppa landing: the settled story-card style. Pen-and-wash clouds, day sky, Fredoka (semibold for headers). */
@font-face {
  font-family: "Fredoka";
  src: url("fonts/fredoka-latin-wght.woff2") format("woff2");
  font-weight: 300 700;
  font-display: swap;
}
/* Greek letters: Fredoka has none, so they come from Comfortaa, a rounded face that sits well beside it (SIL OFL) */
@font-face {
  font-family: "Fredoka";
  src: url("fonts/comfortaa-greek-wght.woff2") format("woff2");
  font-weight: 300 700;
  font-display: swap;
  unicode-range: U+0370-03FF, U+1F00-1FFF;
}

:root {
  --sky-top: #e6eef6;
  --sky-bot: #f9e6e8;
  --ink: #2f2636;
  --line: #7d7396;
  --fill: #fbfaff;
  --pink: #9a6c82; /* the dusk pink the onboarding uses for its key words */
  --glass: rgba(255, 255, 255, .55);
  --glass-edge: rgba(255, 255, 255, .9);
  --gutter: clamp(16px, 4vw, 56px);
}

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

body {
  font-family: "Fredoka", system-ui, sans-serif;
  font-weight: 400;
  color: var(--ink);
  background: var(--sky-bot);
  -webkit-font-smoothing: antialiased;
}
/* the day sky stays put behind everything */
body::before {
  content: "";
  position: fixed;
  inset: 0;
  z-index: -1;
  background: linear-gradient(var(--sky-top), var(--sky-bot));
}

a { color: inherit; }

.eyebrow {
  font-size: 14px;
  font-weight: 500;
  letter-spacing: .16em;
  text-transform: uppercase;
  opacity: .6;
}
.light { font-weight: 400; }
.bold { font-weight: 600; }
.pink { color: var(--pink); fill: var(--pink); }
.lede { font-size: clamp(17px, 1.6vw, 21px); opacity: .66; }

.btn {
  display: inline-block;
  padding: 14px 26px;
  border-radius: 999px;
  background: var(--ink);
  color: #fff;
  font-weight: 500;
  font-size: clamp(15px, 1.3vw, 18px);
  text-decoration: none;
  white-space: nowrap;
}
/* on a small phone the header's button is a little tighter, so a long label (the Greek one) still fits on one line */
@media (max-width: 420px) { .site-header .btn { padding: 12px 16px; } }
.head-end { display: flex; align-items: center; gap: 10px; }
/* the language picker, top right: a small glass pill (globe and language code) that opens a list of languages, each
   named in its own language (js/lang.js closes it) */
.lang { position: relative; }
.lang summary {
  display: flex;
  align-items: center;
  gap: 6px;
  padding: 9px 12px;
  border-radius: 999px;
  background: rgba(255, 255, 255, .55);
  border: 1px solid rgba(255, 255, 255, .9);
  -webkit-backdrop-filter: blur(8px);
  backdrop-filter: blur(8px);
  font: 500 15px/1 "Fredoka", system-ui, sans-serif;
  color: var(--ink);
  cursor: pointer;
  list-style: none;
}
.lang summary::-webkit-details-marker { display: none; }
.lang summary svg { width: 16px; height: 16px; fill: none; stroke: currentColor; stroke-width: 1.5; }
.lang summary:focus-visible { outline: 3px solid var(--pink); outline-offset: 3px; }
.lang ul {
  position: absolute;
  right: 0;
  top: calc(100% + 8px);
  min-width: 170px;
  margin: 0;
  padding: 6px;
  list-style: none;
  border-radius: 16px;
  background: #fff;
  box-shadow: 0 12px 32px rgba(60, 45, 80, .16);
}
.lang li a { display: block; padding: 9px 14px; border-radius: 10px; font: 400 15px/1.2 "Fredoka", system-ui, sans-serif; color: var(--ink); text-decoration: none; }
.lang li a:hover, .lang li a:focus-visible { background: #f4eff6; outline: none; }
.lang li a[aria-current] { font-weight: 600; color: var(--pink); }

.btn:focus-visible, .logo:focus-visible, summary:focus-visible, .footer a:focus-visible { outline: 3px solid var(--line); outline-offset: 3px; }

/* ---------- header: logo top left, the one button top right, visible throughout ---------- */
.site-header {
  position: fixed;
  inset: 0 0 auto;
  z-index: 10;
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 20px var(--gutter);
}
.logo {
  font-weight: 600;
  font-size: clamp(26px, 2.6vw, 36px);
  text-decoration: none;
}
/* a slight gloss on the big wordmarks: a lighter band across the top of the letters with a soft edge, like the shine on
   a button. The middle logo also stands out a little in 3D, on a darker edge just below each letter (see index.html) */
.finale-mark text { fill: url(#gloss-ink); }
.finale-mark .pink { fill: url(#gloss-pink); }
.mark .mark-face { fill: url(#mark-gloss-ink); }
.mark .mark-face .pink { fill: url(#mark-gloss-pink); }
.mark .mark-edge { fill: #241c2a; }
.mark .mark-edge .pink { fill: #7d566a; }

/* gusts of wind: a short streak travelling along each line, faint, behind the logo */
.wind { position: absolute; inset: 0; width: 100%; height: 100%; pointer-events: none; }
.wind path {
  fill: none;
  stroke: #fff;
  stroke-width: 2.4;
  stroke-linecap: round;
  stroke-dasharray: 140 1800;
  stroke-dashoffset: 1940;
  opacity: .55;
  animation: gust var(--wd) linear var(--wl) infinite;
}
@keyframes gust { to { stroke-dashoffset: 0; } }

/* ---------- Acts 1–3: the cloud bank parts, uppa is revealed, the traveller jumps and falls through the worries,
   and the glider tears out of a cloud to catch them ---------- */
/* lite: the opening plays once on load and takes one screen; the fall, the worries and the catch are left out */
.act-open { height: 100vh; height: 100svh; }
/* the rhythm path now starts right under the opening and its top clouds reach up into it, over the opening's own. The
   medicine strip is lifted out of the stage (main.js moves it to the section) and stacked above them both */
.act-open { position: relative; }
.act-open > .med-strip { z-index: 2; }
[data-clouds="far"], [data-clouds="near"], [data-layer="fly"], [data-layer="veil"], .diver { display: none; }
.stage {
  position: sticky;
  top: 0;
  height: 100vh;
  height: 100svh;
  overflow: hidden;
}
/* a 1440 × 900 design frame, scaled by main.js to cover the viewport */
.frame {
  position: absolute;
  left: 50%;
  top: 50%;
  width: 1440px;
  height: 900px;
  transform: translate(-50%, -50%) scale(var(--frame-scale, 1));
  pointer-events: none;
}
.frame img {
  position: absolute;
  display: block;
  max-width: none;
}
.bank-fill { position: absolute; inset: 0; background: var(--fill); }
/* a layer of clouds that scrolls inside its frame (the frame keeps its own cover transform) */
.layer { position: absolute; inset: 0; will-change: transform; }
.layer .far-cloud { opacity: .7; }

/* a worry on a cloud: faded, softer still on far clouds */
.worry {
  position: absolute;
  transform: translateX(-50%);
  white-space: nowrap;
  font-weight: 500;
  font-size: 36px;
  line-height: 1;
  opacity: .5;
}
.worry.far { font-weight: 400; font-size: 27px; opacity: .35; }
/* the words stay in front of the neighbouring clouds, so a long phrase isn't hidden by the next cloud along; the torn
   nausea worry stays under its hole, so the tear cuts through it */
.worry:not(.rip-cloud) { z-index: 1; }

/* the falling traveller, sized from the design frame like the glider, so they're the same size as its pilot */
.diver {
  position: absolute;
  left: 0;
  top: 0;
  width: calc(66px * var(--frame-scale, 1));
  opacity: 0;
  will-change: transform;
}
.diver-body { display: block; width: 100%; height: auto; overflow: visible; }

/* the glider, about 208 px wide in the design frame: three stacked sprites, one shown at a time */
.glider {
  position: absolute;
  left: 0;
  top: 0;
  width: 208px;
  height: 104px;
  opacity: 0;
  will-change: transform;
}
.glider svg { position: absolute; inset: 0; width: 100%; height: 100%; overflow: visible; }
.g-pilot { opacity: 0; }
.frame img.rip-hole { opacity: 0; will-change: auto; }
.line-alone {
  position: absolute;
  left: 250px; /* on two lines, left of the catch cloud, which sits right of centre */
  top: 600px;
  transform: translateX(-50%);
  white-space: nowrap;
  text-align: center;
  font-weight: 600;
  font-size: 44px;
  line-height: 1.12;
  opacity: 0;
}

.reveal {
  position: absolute;
  inset: 0;
  display: grid;
  place-content: center;
  justify-items: center;
  gap: clamp(8px, 2vh, 24px);
  padding: 0 16px;
  text-align: center;
}
.mark { width: min(680px, 88vw); height: auto; overflow: visible; }
.mark text { font-family: "Fredoka", system-ui, sans-serif; font-weight: 600; fill: var(--ink); }
.tagline { font-weight: 600; font-size: clamp(24px, 3vw, 44px); line-height: 1.2; }

/* the medicines, in one row of soft white chips resting on the clouds at the bottom of the first screen. The row
   glides past on a loop: main.js puts a second copy after it, and the track moves left by exactly one copy, so the loop
   has no gap and no jump. It pauses while hovered or focused; with reduced motion it scrolls by hand instead */
.med-strip {
  position: absolute;
  left: 0;
  right: 0;
  bottom: clamp(16px, 3vh, 32px);
  overflow: hidden;
  text-align: left;
  -webkit-mask-image: linear-gradient(90deg, transparent, #000 var(--gutter), #000 calc(100% - var(--gutter)), transparent);
  mask-image: linear-gradient(90deg, transparent, #000 var(--gutter), #000 calc(100% - var(--gutter)), transparent);
}
.med-track { display: flex; width: max-content; animation: meds var(--med-dur, 40s) linear infinite; }
.med-strip:hover .med-track, .med-strip:focus-within .med-track { animation-play-state: paused; }
@keyframes meds { to { transform: translateX(-50%); } }
.med-row { display: flex; margin: 0; padding: 6px 0 10px; list-style: none; }
/* the space after each chip is margin, not gap, so the two copies are exactly the same width and the loop meets itself */
.med-row li {
  display: flex;
  align-items: center;
  gap: 10px;
  flex: none;
  margin-right: 12px;
  padding: 6px 16px 6px 6px;
  border-radius: 999px;
  background: rgba(255, 255, 255, .72);
  box-shadow: 0 4px 14px rgba(125, 115, 150, .12);
}
.med-row b { display: block; font-weight: 600; font-size: 14.5px; line-height: 1.2; }
.med-row small { display: block; font-size: 11.5px; line-height: 1.3; opacity: .6; }
/* each medicine's pip: a raised button in its colour, like the rhythm path's, with a white shot or pill on it */
.med-icon {
  display: grid;
  place-items: center;
  width: 32px;
  height: 32px;
  border-radius: 50%;
  background: var(--c);
  color: color-mix(in srgb, var(--c) 60%, #2f2636);
  box-shadow: inset 0 -3px 0 color-mix(in srgb, var(--c) 72%, #2f2636), inset 0 2px 0 rgba(255, 255, 255, .28);
}
.med-icon svg { width: 19px; height: 19px; margin-top: -1px; }
@media (prefers-reduced-motion: reduce) {
  .med-track { animation: none; }
  .med-strip { overflow-x: auto; scrollbar-width: none; }
  .med-row[aria-hidden] { display: none; }
}

/* ---------- Act 4: the rhythm path, a strip four screens tall that scrolls with the page. Its 1440 px design box is
   scaled like the frames above (--frame-scale) and centred; path.js sets --strip-h to the strip's height ---------- */
.act-path {
  position: relative;
  height: calc(var(--strip-h, 4600) * var(--frame-scale, 1) * 1px);
  overflow: hidden;
  overflow: clip visible; /* the bands of cloud spill over the top and bottom edges instead of being sliced off */
}
.path-box {
  position: absolute;
  left: 50%;
  top: 0;
  width: 1440px;
  height: calc(var(--strip-h, 4600) * 1px);
  transform: translateX(-50%) scale(var(--frame-scale, 1));
  transform-origin: 50% 0;
  pointer-events: none;
}
.path-layer { position: absolute; inset: 0; }
.path-layer img { position: absolute; display: block; max-width: none; }
.path-art { position: absolute; left: 0; top: 0; overflow: visible; }

/* a pip's description, laid out like a Day Sky section inside its cloud (sizes in design px) */
.section-copy {
  position: absolute;
  width: 600px;
  transform: translateX(-50%);
  display: grid;
  justify-items: center;
  text-align: center;
}
.section-copy .eyebrow { font-size: 18px; line-height: 1.2; letter-spacing: 0; text-transform: none; opacity: .7; }
.section-copy h2 { margin-top: 12px; font-size: 40px; line-height: 46px; font-weight: 600; white-space: nowrap; }
/* other languages run longer, so their headlines may wrap (lite: the English ones too, as they're longer) */
.section-copy h2 { white-space: normal; text-wrap: balance; }
.section-copy .lede { margin-top: 12px; max-width: 440px; font-size: 19px; line-height: 27px; }

/* the medicine names on their small clouds */


/* ---------- phones (and tablets upright): main.js shows the frames' middle 760 px across, so the design px below are
   about half size on screen; the copy is set larger to stay readable ---------- */
@media (max-aspect-ratio: 4/5) {
  .bank-fill { inset: -600px 0; }
  .line-alone { left: 720px; font-size: 52px; } /* main.js sets its top */
  .section-copy { width: 640px; transform: translate(-50%, -50%); }
  .section-copy .eyebrow { font-size: 28px; }
  .section-copy h2 { font-size: 58px; line-height: 64px; white-space: normal; text-wrap: balance; }
  .section-copy .lede { max-width: 600px; font-size: 30px; line-height: 40px; }
  .finale-sky { transform-origin: 50% 0; }
  /* a soft backdrop behind the header once the FAQ's words pass under it (main.js sets .over-copy) */
  .site-header::before {
    content: "";
    position: absolute;
    inset: 0 0 -18px;
    z-index: -1;
    background: linear-gradient(rgba(251, 250, 255, .94) 62%, rgba(251, 250, 255, 0));
    opacity: 0;
    transition: opacity .25s;
    pointer-events: none;
  }
  .site-header.over-copy::before { opacity: 1; }
}

/* ---------- FAQ (S11): the path ends at the last pip and the clouds open around it, as at the reveal ---------- */
.faq {
  position: relative;
  min-height: 1100px;
  overflow: hidden;
  overflow: clip visible; /* the cloud under the FAQ spills over into the closing section instead of being sliced */
  padding: 205px var(--gutter) 260px;
  display: grid;
  align-content: start;
  justify-items: center;
  gap: 14px;
  text-align: center;
}
.faq > :not(.faq-sky) { position: relative; }
/* a 1440 × 1100 design box behind the FAQ, centred, cropped at the sides on narrow screens */
.faq-sky, .finale-sky {
  position: absolute;
  left: 50%;
  top: 0;
  width: 1440px;
  margin-left: -720px;
  pointer-events: none;
}
.faq-sky { height: 1100px; }
/* the art sits at the box's origin; each cloud image carries its own left and top */
.faq-sky > *, .finale-sky > * { position: absolute; left: 0; top: 0; max-width: none; }
.faq h2 { font-size: clamp(32px, 3.4vw, 44px); line-height: 1.15; }
.panel {
  width: min(720px, 100%);
  margin-top: 18px;
  text-align: left;
  border-radius: 24px;
  background: var(--glass);
  border: 1px solid var(--glass-edge);
  -webkit-backdrop-filter: blur(12px);
  backdrop-filter: blur(12px);
}
.panel details + details { border-top: 1px solid var(--glass-edge); }
.panel summary {
  display: flex;
  justify-content: space-between;
  gap: 16px;
  padding: 20px 24px;
  font-weight: 500;
  font-size: 18px;
  cursor: pointer;
  list-style: none;
}
.panel summary::-webkit-details-marker { display: none; }
.panel summary::after { content: "+"; font-weight: 300; font-size: 24px; line-height: 1; }
.panel details[open] summary::after { content: "–"; }
.panel details p { padding: 0 24px 20px; font-size: 15.5px; line-height: 1.5; opacity: .66; }

/* ---------- the bottom of the page (S12): the big wordmark resting in a floor of cloud that holds the footer ---------- */
.finale { position: relative; height: 1200px; overflow: hidden; }
.finale-sky { height: 1200px; }
/* the solid base runs well past the 1440 design box, so wide screens don't show sky at its ends */
.finale-floor { top: 960px !important; left: -1280px !important; width: 4000px; height: 240px; background: var(--fill); }
.thread-glider { margin: -20px 0 0 -35px; transform-origin: 35px 20px; will-change: transform; }
.finale-mark text { font-family: "Fredoka", system-ui, sans-serif; font-weight: 600; }
.finale-copy {
  position: relative;
  padding: 150px var(--gutter) 0;
  display: grid;
  justify-items: center;
  gap: 16px;
  text-align: center;
}
.finale h2 { font-size: clamp(32px, 3.6vw, 52px); line-height: 1.15; }
.terms { font-size: 14px; opacity: .55; max-width: 560px; }
.terms a { color: inherit; }
/* the waitlist (js/waitlist.js): one glass pill holding the email field and the button, the answer underneath */
.sr-only { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; }
.waitlist { display: grid; justify-items: center; gap: 10px; width: min(100%, 480px); }
.wl-row {
  display: flex;
  width: 100%;
  padding: 5px;
  border-radius: 999px;
  background: var(--glass);
  border: 1px solid var(--glass-edge);
  backdrop-filter: blur(8px);
}
.wl-row:focus-within { outline: 3px solid var(--line); outline-offset: 3px; }
.wl-row input {
  flex: 1;
  min-width: 0;
  padding: 0 18px;
  border: 0;
  background: none;
  font: inherit;
  font-size: 17px;
  color: var(--ink);
  outline: none;
}
.wl-row input::placeholder { color: var(--ink); opacity: .4; }
.wl-row .btn { border: 0; cursor: pointer; font-family: inherit; }
/* on a phone the button goes under the field, so long labels (the Greek one) never push past the screen */
@media (max-width: 560px) {
  .wl-row { flex-direction: column; gap: 6px; border-radius: 28px; }
  .wl-row input { padding: 12px 18px; text-align: center; }
  .wl-row .btn { white-space: normal; }
}
.btn:disabled { opacity: .6; cursor: default; }
.wl-hp { position: absolute; left: -9999px; }
.wl-status { min-height: 1.4em; font-size: 15px; }
.waitlist[data-state="invalid"] .wl-status, .waitlist[data-state="error"] .wl-status { color: var(--pink); }
.wl-leave { padding: 10px 20px; border-radius: 999px; border: 1px solid var(--ink); background: none; color: var(--ink); font: inherit; cursor: pointer; }
.footer {
  position: absolute;
  left: 0;
  right: 0;
  top: 1105px;
  display: grid;
  gap: 8px;
  justify-items: center;
  padding: 0 var(--gutter);
  text-align: center;
}
.footer nav { display: flex; flex-wrap: wrap; justify-content: center; gap: 6px 22px; font-weight: 500; }
.footer nav a { text-decoration: none; opacity: .75; }
.footer p { font-size: 12.5px; opacity: .55; max-width: 900px; }

/* ---------- still version: reduced motion, or the motion library didn't load ---------- */
/* the wind: clouds in the still scenes sway a few px, each on its own slow period. The clouds that move with the scroll
   don't, which keeps the number of moving layers small */
/* the clouds breathe: they drift a little in the wind and swell and settle, a touch wider than tall. The torn nausea
   cloud and its hole stay still so the hole keeps its place */
@keyframes wind { from { translate: 0 0; scale: 1; } to { translate: var(--wx) var(--wy); scale: 1.055 1.04; } }
:is([data-clouds="parted"], [data-clouds="parted-front"], [data-clouds="bank"], [data-clouds="far"], [data-clouds="near"],
  [data-layer="veil"], [data-strip="bands"], [data-strip="words"], .faq-sky, .finale-sky) > img:not(.rip-cloud):not(.rip-hole) {
  animation: wind var(--wd) ease-in-out var(--wdl) infinite alternate;
}

@media (prefers-reduced-motion: reduce) {
  img, .wind path { animation: none !important; }
  .wind { display: none; }
  .act-open { height: 100vh; }
  .bank-fill, [data-clouds="bank"], [data-clouds="far"], [data-clouds="near"], [data-layer="fly"], [data-layer="veil"], .diver { display: none; }
}
.still .act-open { height: 100vh; }
.still .bank-fill, .still [data-clouds="bank"], .still [data-clouds="far"], .still [data-clouds="near"],
.still [data-layer="fly"], .still [data-layer="veil"], .still .diver { display: none; }
