/* World Clock website. Same system as the app (src/renderer/style.css):
   pale blue canvas / deep navy, light card = day, navy card = night, one system-blue accent,
   thin big digits, hairlines, calm motion. One self-hosted display face (Outfit, OFL); no third-party requests. */

@font-face {
  font-family: "Outfit";
  src: url("fonts/outfit-var.woff2") format("woff2");
  font-weight: 150 600; font-style: normal; font-display: swap;
}

:root {
  --s1: 4px; --s2: 8px; --s3: 12px; --s4: 16px; --s5: 20px; --s6: 24px; --s8: 32px; --s10: 40px; --s12: 48px; --s16: 64px; --s24: 96px; --s32: 128px;
  --gutter: clamp(16px, 4vw, 40px);
  --maxw: 1240px;
  --nav-h: 64px;
  --r-tile: 28px; --r-app: 20px; --r-card: 18px; --r-group: 14px; --r-pill: 999px;
  --ring: var(--accent); /* focus ring; turns pale on night surfaces */
  --frost: blur(16px) saturate(1.5); /* the scrolled nav's glass (demo.js warms its GPU program up once at idle) */
  /* motion: one family of curves and durations, shared by CSS and demo.js (which reads them back) */
  --ease: cubic-bezier(.2, .8, .2, 1);          /* UI state changes */
  --ease-out: cubic-bezier(.16, 1, .3, 1);      /* things arriving */
  --ease-in-out: cubic-bezier(.65, 0, .35, 1);  /* things travelling (the scripted cursor) */
  --ease-spring: cubic-bezier(.34, 1.4, .64, 1); /* things settling back (magnetic buttons) */
  --dur-1: 120ms; --dur-2: 200ms; --dur-3: 320ms; --dur-4: 600ms; --dur-5: 900ms; --dur-6: 1200ms;
  --stagger: 70ms;

  /* type scale: five steps, one tracking rule (tighter as it grows) */
  --fs-mega: clamp(3rem, 1rem + 8vw, 8rem);
  --fs-display: clamp(2.6rem, 1.2rem + 5.2vw, 5.5rem);
  --fs-h2: clamp(2.2rem, 1.2rem + 3.6vw, 4.5rem);
  --fs-h2s: clamp(1.8rem, 1rem + 2.6vw, 3.5rem);
  --fs-h3: clamp(1.375rem, 1.1rem + .9vw, 1.875rem);
  --fs-lede: clamp(1.0625rem, 1rem + .4vw, 1.3125rem);

  --font: "Segoe UI Variable Text", "Segoe UI Variable", "Segoe UI", -apple-system, BlinkMacSystemFont, "SF Pro Text", system-ui, sans-serif;
  --display: "Outfit", "Segoe UI Variable Display", "Segoe UI", -apple-system, BlinkMacSystemFont, system-ui, sans-serif;

  --canvas: oklch(0.965 0.014 245);
  --canvas-2: oklch(0.945 0.02 245);
  --group: oklch(1 0 0);
  --fg: oklch(0.22 0.03 258);
  --fg-2: oklch(0.44 0.025 255);
  --fg-3: oklch(0.52 0.022 255);
  --hair: oklch(0.35 0.04 255 / 0.10);
  --hair-strong: oklch(0.35 0.04 255 / 0.18);
  --field: oklch(0.35 0.04 255 / 0.06);
  --field-hover: oklch(0.35 0.04 255 / 0.10);
  --switch-off: oklch(0.35 0.03 255 / 0.18);
  --tint: oklch(0.965 0.014 245 / 0.8);

  --day: oklch(0.995 0.004 240 / 0.9);
  --day-solid: oklch(0.995 0.004 240);
  --day-fg: oklch(0.21 0.03 258); --day-fg-2: oklch(0.46 0.025 255); --day-hair: oklch(0.35 0.04 255 / 0.10);
  --night: oklch(0.29 0.06 263 / 0.96);
  --night-solid: oklch(0.29 0.06 263);
  --night-fg: oklch(0.985 0.006 250); --night-fg-2: oklch(0.83 0.025 252); --night-hair: oklch(1 0 0 / 0.12);

  --accent: oklch(0.58 0.2 255);
  --accent-ink: oklch(0.50 0.2 257);
  --accent-on-night: oklch(0.80 0.11 245);
  --accent-soft: oklch(0.58 0.2 255 / 0.12);
  --btn: oklch(0.50 0.2 257);
  --btn-hover: oklch(0.45 0.2 258);
  --on-btn: #fff;

  --band-night: oklch(0.25 0.055 263);
  --band-night-2: oklch(0.30 0.06 263);
  --band-fg: oklch(0.975 0.006 250);
  --band-fg-2: oklch(0.84 0.025 252);

  --map-sea: oklch(0.915 0.032 240);
  --map-land: oklch(0.985 0.006 240);
  --map-night: oklch(0.3 0.11 268);

  --shadow-app: 0 0 0 0.5px oklch(0.3 0.04 255 / 0.14), 0 24px 64px -18px oklch(0.3 0.06 255 / 0.34), 0 2px 6px oklch(0.3 0.05 255 / 0.06);
  --shadow-card: 0 0 0 0.5px oklch(0.3 0.04 255 / 0.07), 0 1px 2px oklch(0.3 0.05 255 / 0.05), 0 6px 18px -8px oklch(0.3 0.06 255 / 0.18);
  --shadow-lift: 0 0 0 0.5px oklch(0.3 0.04 255 / 0.08), 0 2px 4px oklch(0.3 0.05 255 / 0.06), 0 14px 30px -10px oklch(0.3 0.06 255 / 0.28);
  --shadow-shot: 0 0 0 0.5px oklch(0.3 0.04 255 / 0.12), 0 30px 70px -24px oklch(0.25 0.06 258 / 0.45), 0 4px 10px -4px oklch(0.25 0.06 258 / 0.14);
  /* sky cards, as in the app: each card is lit by its own sky (day, golden hour, dawn, twilight, night) */
  --g-day: linear-gradient(180deg, oklch(0.995 0.004 240), oklch(0.965 0.02 238));
  --g-night: linear-gradient(180deg, oklch(0.315 0.06 263), oklch(0.255 0.055 267));
  --g-golden: linear-gradient(180deg, oklch(0.975 0.032 78), oklch(0.93 0.052 28));
  --g-dawn: linear-gradient(180deg, oklch(0.955 0.03 300), oklch(0.955 0.042 58));
  --g-twilight: linear-gradient(180deg, oklch(0.315 0.07 283), oklch(0.335 0.085 318));
  /* planner cells, as in the app */
  --cell: oklch(0.35 0.04 255 / 0.065); --cell-fg: oklch(0.5 0.022 255);
  --cell-work: oklch(0.905 0.05 255); --cell-work-fg: oklch(0.46 0.19 258);
  --cell-night: oklch(0.5 0.035 262); --cell-night-fg: #fff;
  color-scheme: light;
}

/* dark: prefers-color-scheme unless the visitor picked light; and the explicit toggle */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    --canvas: oklch(0.19 0.04 262);
    --canvas-2: oklch(0.215 0.042 262);
    --group: oklch(0.25 0.042 260);
    --fg: oklch(0.97 0.008 250);
    --fg-2: oklch(0.80 0.025 252);
    --fg-3: oklch(0.72 0.025 252);
    --hair: oklch(0.9 0.03 250 / 0.10);
    --hair-strong: oklch(0.9 0.03 250 / 0.18);
    --field: oklch(0.9 0.03 250 / 0.08);
    --field-hover: oklch(0.9 0.03 250 / 0.14);
    --switch-off: oklch(0.9 0.03 250 / 0.22);
    --tint: oklch(0.19 0.04 262 / 0.8);
    --day: oklch(0.36 0.05 255 / 0.94);
    --day-solid: oklch(0.36 0.05 255);
    --day-fg: oklch(0.985 0.006 250); --day-fg-2: oklch(0.85 0.022 252); --day-hair: oklch(1 0 0 / 0.10);
    --night: oklch(0.155 0.035 265 / 0.96);
    --night-solid: oklch(0.155 0.035 265);
    --night-fg: oklch(0.95 0.01 250); --night-fg-2: oklch(0.76 0.028 252); --night-hair: oklch(1 0 0 / 0.08);
    --accent: oklch(0.72 0.14 250);
    --accent-ink: oklch(0.80 0.11 248);
    --accent-on-night: oklch(0.78 0.12 248);
    --accent-soft: oklch(0.72 0.14 250 / 0.18);
    --btn: oklch(0.52 0.19 257);
    --btn-hover: oklch(0.57 0.19 256);
    --band-night: oklch(0.145 0.035 265);
    --band-night-2: oklch(0.17 0.038 265);
    --map-sea: oklch(0.215 0.04 262);
    --map-land: oklch(0.34 0.045 256);
    --map-night: oklch(0.08 0.03 268);
    --shadow-app: 0 0 0 0.5px oklch(1 0 0 / 0.10), 0 28px 70px -18px oklch(0.05 0.03 265 / 0.7);
    --shadow-card: 0 0 0 0.5px oklch(1 0 0 / 0.07), 0 6px 18px -8px oklch(0.05 0.03 265 / 0.5);
    --shadow-lift: 0 0 0 0.5px oklch(1 0 0 / 0.10), 0 16px 32px -10px oklch(0.05 0.03 265 / 0.7);
    --shadow-shot: 0 0 0 0.5px oklch(1 0 0 / 0.10), 0 30px 70px -24px oklch(0.02 0.02 265 / 0.8);
  --g-day: linear-gradient(180deg, oklch(0.39 0.05 255), oklch(0.335 0.05 258));
  --g-night: linear-gradient(180deg, oklch(0.18 0.035 265), oklch(0.135 0.03 266));
  --g-golden: linear-gradient(180deg, oklch(0.41 0.06 62), oklch(0.36 0.07 20));
  --g-dawn: linear-gradient(180deg, oklch(0.37 0.06 295), oklch(0.39 0.06 48));
  --g-twilight: linear-gradient(180deg, oklch(0.25 0.06 288), oklch(0.235 0.075 322));
  --cell: oklch(0.9 0.03 250 / 0.07); --cell-fg: oklch(0.8 0.025 252);
  --cell-work: oklch(0.44 0.08 256); --cell-work-fg: oklch(0.975 0.01 250);
  --cell-night: oklch(0.13 0.03 265); --cell-night-fg: oklch(0.9 0.02 250);
    color-scheme: dark;
  }
}
:root[data-theme="dark"] {
  --canvas: oklch(0.19 0.04 262);
  --canvas-2: oklch(0.215 0.042 262);
  --group: oklch(0.25 0.042 260);
  --fg: oklch(0.97 0.008 250);
  --fg-2: oklch(0.80 0.025 252);
  --fg-3: oklch(0.72 0.025 252);
  --hair: oklch(0.9 0.03 250 / 0.10);
  --hair-strong: oklch(0.9 0.03 250 / 0.18);
  --field: oklch(0.9 0.03 250 / 0.08);
  --field-hover: oklch(0.9 0.03 250 / 0.14);
  --switch-off: oklch(0.9 0.03 250 / 0.22);
  --tint: oklch(0.19 0.04 262 / 0.8);
  --day: oklch(0.36 0.05 255 / 0.94);
  --day-solid: oklch(0.36 0.05 255);
  --day-fg: oklch(0.985 0.006 250); --day-fg-2: oklch(0.85 0.022 252); --day-hair: oklch(1 0 0 / 0.10);
  --night: oklch(0.155 0.035 265 / 0.96);
  --night-solid: oklch(0.155 0.035 265);
  --night-fg: oklch(0.95 0.01 250); --night-fg-2: oklch(0.76 0.028 252); --night-hair: oklch(1 0 0 / 0.08);
  --accent: oklch(0.72 0.14 250);
  --accent-ink: oklch(0.80 0.11 248);
  --accent-on-night: oklch(0.78 0.12 248);
  --accent-soft: oklch(0.72 0.14 250 / 0.18);
  --btn: oklch(0.52 0.19 257);
  --btn-hover: oklch(0.57 0.19 256);
  --band-night: oklch(0.145 0.035 265);
  --band-night-2: oklch(0.17 0.038 265);
  --map-sea: oklch(0.215 0.04 262);
  --map-land: oklch(0.34 0.045 256);
  --map-night: oklch(0.08 0.03 268);
  --shadow-app: 0 0 0 0.5px oklch(1 0 0 / 0.10), 0 28px 70px -18px oklch(0.05 0.03 265 / 0.7);
  --shadow-card: 0 0 0 0.5px oklch(1 0 0 / 0.07), 0 6px 18px -8px oklch(0.05 0.03 265 / 0.5);
  --shadow-lift: 0 0 0 0.5px oklch(1 0 0 / 0.10), 0 16px 32px -10px oklch(0.05 0.03 265 / 0.7);
  --shadow-shot: 0 0 0 0.5px oklch(1 0 0 / 0.10), 0 30px 70px -24px oklch(0.02 0.02 265 / 0.8);
  --g-day: linear-gradient(180deg, oklch(0.39 0.05 255), oklch(0.335 0.05 258));
  --g-night: linear-gradient(180deg, oklch(0.18 0.035 265), oklch(0.135 0.03 266));
  --g-golden: linear-gradient(180deg, oklch(0.41 0.06 62), oklch(0.36 0.07 20));
  --g-dawn: linear-gradient(180deg, oklch(0.37 0.06 295), oklch(0.39 0.06 48));
  --g-twilight: linear-gradient(180deg, oklch(0.25 0.06 288), oklch(0.235 0.075 322));
  --cell: oklch(0.9 0.03 250 / 0.07); --cell-fg: oklch(0.8 0.025 252);
  --cell-work: oklch(0.44 0.08 256); --cell-work-fg: oklch(0.975 0.01 250);
  --cell-night: oklch(0.13 0.03 265); --cell-night-fg: oklch(0.9 0.02 250);
  color-scheme: dark;
}
/* theme switches land in one frame: no colour transition can leave text on a half-changed background */
:root.theme-switch *, :root.theme-switch *::before, :root.theme-switch *::after { transition: none !important; }
/* theme toggle: where supported, the new theme spreads as a circle from the button (theme.js drives the clip) */
::view-transition-old(root), ::view-transition-new(root) { animation: none; mix-blend-mode: normal; }

/* ---------- base ---------- */
*, *::before, *::after { box-sizing: border-box; }
[hidden] { display: none !important; }
html { -webkit-text-size-adjust: 100%; text-size-adjust: 100%; scroll-behavior: smooth; scroll-padding-top: 80px; }
body {
  margin: 0; background: var(--canvas); color: var(--fg);
  font: 400 1.0625rem/1.6 var(--font); -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale;
  overflow-x: clip;
}
img, svg, canvas { display: block; max-width: 100%; }
img { height: auto; }
a { color: var(--accent-ink); text-decoration-thickness: 1px; text-underline-offset: 0.22em; text-decoration-color: color-mix(in oklch, currentColor 45%, transparent); }
a:hover { text-decoration-color: currentColor; }
button, input, select { font: inherit; color: inherit; }
::selection { background: color-mix(in oklch, var(--accent) 28%, transparent); color: inherit; }
.hero.sky-dark ::selection, .night-band ::selection, .night-tile ::selection, .download ::selection, .footer ::selection { background: oklch(0.82 0.09 245 / .38); }
:focus-visible { outline: 2px solid var(--ring); outline-offset: 3px; }
a:not(.btn):focus-visible, summary:focus-visible { border-radius: 6px; }
.hero.sky-dark, .nav.on-dark:not(.scrolled), .nav.over-dark, .night-band, .night-tile, .download, .footer { --ring: oklch(0.86 0.09 245); }
h1, h2, h3 { font-family: var(--display); margin: 0; text-wrap: balance; }
p { margin: 0; text-wrap: pretty; }
.sr-only { position: absolute !important; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0; }
.wrap { width: 100%; max-width: calc(var(--maxw) + 2 * var(--gutter)); margin: 0 auto; padding: 0 var(--gutter); }
.num { font-variant-numeric: tabular-nums; }
html { scrollbar-color: color-mix(in oklch, var(--fg-2) 45%, transparent) transparent; }

.skip { position: absolute; left: var(--s4); top: -60px; z-index: 100; padding: 10px 16px; border-radius: var(--r-pill); background: var(--btn); color: var(--on-btn); font-weight: 600; text-decoration: none; transition: top var(--dur-2) var(--ease); }
.skip:focus { top: var(--s3); }

/* icons: one family, 1.6 stroke, round caps */
.i { width: 18px; height: 18px; flex: none; fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round; }

/* ---------- buttons ---------- */
.btn {
  display: inline-flex; align-items: center; justify-content: center; gap: 10px; min-height: 52px; padding: 0 24px;
  border: 0; border-radius: var(--r-pill); font-weight: 600; font-size: 1rem; letter-spacing: -0.005em; text-decoration: none; white-space: nowrap; cursor: pointer;
  transition: background-color var(--dur-2) var(--ease), transform var(--dur-2) var(--ease);
}
.btn:active { transform: scale(.98); transition-duration: var(--dur-1); }
/* magnetic buttons (demo.js, fine pointers only): the pill leans toward the cursor, its label leans a little further,
   a soft highlight follows the pointer, and it springs home on leave. Transform and opacity only. */
.magnetic { position: relative; isolation: isolate; overflow: hidden; --mx: 0px; --my: 0px; --press: 1;
  transform: translate3d(var(--mx), var(--my), 0) scale(var(--press)); transition: transform var(--dur-4) var(--ease-spring), background-color var(--dur-2) var(--ease); }
.magnetic > * { transform: translate3d(calc(var(--mx) * .35), calc(var(--my) * .35), 0); transition: transform var(--dur-4) var(--ease-spring); }
.magnetic::after { content: ""; position: absolute; z-index: -1; left: var(--gx, 50%); top: var(--gy, 50%); width: 180px; height: 180px; margin: -90px 0 0 -90px; border-radius: 50%;
  background: radial-gradient(closest-side, oklch(1 0 0 / .26), transparent); opacity: 0; transition: opacity var(--dur-3) var(--ease); pointer-events: none; }
.magnetic.is-near { transition-duration: var(--dur-2), var(--dur-2); }
.magnetic.is-near > * { transition-duration: var(--dur-2); }
.magnetic.is-near::after { opacity: 1; }
.magnetic:active { transform: translate3d(var(--mx), var(--my), 0) scale(.97); }
.btn-quiet.magnetic::after, .btn-tinted.magnetic::after { background: radial-gradient(closest-side, color-mix(in oklch, currentColor 16%, transparent), transparent); }
.download .btn-primary.magnetic::after { background: radial-gradient(closest-side, oklch(0.78 0.1 250 / .22), transparent); }
.btn-primary { background: var(--btn); color: var(--on-btn); box-shadow: 0 1px 2px oklch(0.3 0.1 257 / 0.2), 0 10px 24px -10px oklch(0.45 0.2 257 / 0.55); }
.btn-primary:hover { background: var(--btn-hover); }
.btn-tinted { background: var(--accent-soft); color: var(--accent-ink); }
.btn-tinted:hover { background: color-mix(in oklch, var(--accent) 22%, transparent); }
.btn-quiet { background: transparent; color: var(--fg); box-shadow: inset 0 0 0 1px var(--hair-strong); }
.btn-quiet:hover { background: var(--field); }
.btn-sm { min-height: 38px; padding: 0 16px; font-size: .9375rem; }

/* ---------- nav ---------- */
.nav { position: fixed; inset: 0 0 auto 0; z-index: 50; height: var(--nav-h); color: var(--fg); transition: background-color var(--dur-3) var(--ease), box-shadow var(--dur-3) var(--ease); }
.nav.on-dark:not(.scrolled) { color: oklch(0.975 0.006 250); }
.nav.scrolled { background: var(--tint); -webkit-backdrop-filter: var(--frost); backdrop-filter: var(--frost); box-shadow: 0 0.5px 0 var(--hair-strong); color: var(--fg); }
/* over the night band, the dusk and the footer the bar turns to night with them, so it never floats as a pale strip */
.nav.scrolled.over-dark { background: oklch(0.2 0.045 266 / 0.72); box-shadow: 0 0.5px 0 oklch(1 0 0 / 0.1); color: oklch(0.975 0.006 250); }
.nav .wrap { height: 100%; display: flex; align-items: center; gap: var(--s6); }
.brand { display: inline-flex; flex: none; align-items: center; gap: 10px; white-space: nowrap; color: inherit; text-decoration: none; font-family: var(--display); font-weight: 600; font-size: 1.125rem; letter-spacing: -0.01em; }
.brand img { width: 28px; height: 28px; border-radius: 7px; transition: rotate var(--dur-4) var(--ease-spring); }
.brand:hover img { rotate: -10deg; }
.brand span { transition: opacity var(--dur-2) var(--ease); }
.brand:hover span { opacity: .78; }
.nav-actions { display: flex; align-items: center; gap: var(--s2); margin-left: auto; }
.theme-btn { width: 38px; height: 38px; display: inline-grid; place-items: center; border: 0; border-radius: 50%; background: transparent; color: inherit; cursor: pointer; }
.theme-btn:hover { background: color-mix(in oklch, currentColor 10%, transparent); }
.theme-btn:active { background: color-mix(in oklch, currentColor 16%, transparent); transform: scale(.94); }
.theme-btn { transition: background-color var(--dur-1) var(--ease), transform var(--dur-2) var(--ease-spring); }
.theme-btn .i { transition: rotate var(--dur-4) var(--ease-spring); }
.theme-btn:hover .i { rotate: 30deg; }
.theme-btn .i { width: 19px; height: 19px; }
.theme-btn [data-show] { display: none; }
:root[data-theme-pref="system"] .theme-btn [data-show="system"],
:root[data-theme-pref="light"] .theme-btn [data-show="light"],
:root[data-theme-pref="dark"] .theme-btn [data-show="dark"] { display: block; }
.nav .btn-sm { background: var(--btn); color: var(--on-btn); }
.nav .btn-sm:hover { background: var(--btn-hover); }
/* page links in the bar: none below 900px (the Menu lists every page), Features and FAQ from 900px, all from 1100px.
   They take the bar's own colour, so they stay legible over the hero sky, the night band and the dusk. */
.nav-links { display: none; align-items: center; gap: 2px; margin: 0 0 0 var(--s2); padding: 0; list-style: none; }
.nav-links a { display: inline-flex; align-items: center; min-height: 44px; padding: 0 14px; border-radius: var(--r-pill);
  color: inherit; font-size: .9375rem; font-weight: 500; text-decoration: none; transition: background-color var(--dur-2) var(--ease); }
.nav-links a:hover, .nav-links a[aria-current="page"] { background: color-mix(in oklch, currentColor 10%, transparent); }
.nav-links .wide { display: none; }
@media (min-width: 900px) { .nav-links { display: flex; } }
@media (min-width: 1100px) { .nav-links .wide { display: inline-flex; } }
/* Menu: a plain <details>, so it opens without JavaScript. Below 1100px it holds every page the bar has no room for
   (from 900px Features and FAQ stay in the bar, .in-bar). theme.js closes it on Escape or a click outside.
   The panel is solid canvas with its own text colour: the bar's colour turns light over the hero sky and the night
   band, and the scrolled bar's frosted glass would not blur the page through a second layer. */
.nav nav { display: flex; align-items: center; }
.nav-menu { border: 0; }
.nav-menu > summary { display: inline-flex; align-items: center; gap: 8px; min-height: 44px; padding: 0 14px; border-radius: var(--r-pill);
  font: 500 .9375rem/1 var(--font); letter-spacing: 0; color: inherit; white-space: nowrap; transition: background-color var(--dur-2) var(--ease); }
.nav-menu > summary::after { content: ""; width: 6px; height: 6px; margin-top: -3px; border: solid currentColor; border-width: 0 1.6px 1.6px 0; transform: rotate(45deg); transition: transform var(--dur-2) var(--ease); }
.nav-menu[open] > summary::after { margin-top: 3px; transform: rotate(225deg); }
.nav-menu > summary:hover, .nav-menu[open] > summary { color: inherit; background: color-mix(in oklch, currentColor 10%, transparent); }
.nav-menu::details-content { block-size: auto; overflow: visible; transition: none; }
.nav-menu > ul { --ring: var(--accent); position: absolute; top: var(--nav-h); right: 16px; z-index: 1; min-width: 220px; max-height: calc(100svh - var(--nav-h) - 16px); overflow-y: auto;
  margin: 0; padding: 6px; list-style: none; border-radius: 16px; background: var(--canvas); color: var(--fg); box-shadow: 0 0 0 0.5px var(--hair-strong), var(--shadow-lift); }
.nav-menu a { display: flex; align-items: center; min-height: 44px; padding: 0 14px; border-radius: 10px; color: var(--fg); font-size: .9375rem; font-weight: 500; text-decoration: none; white-space: nowrap; }
.nav-menu a:hover { background: var(--field); }
.nav-menu a[aria-current="page"] { background: var(--accent-soft); color: var(--accent-ink); }
@media (min-width: 760px) {
  /* beside the name (and Features and FAQ from 900px), the panel hangs from the Menu button itself */
  .nav-menu { position: relative; }
  .nav-menu > ul { top: calc(100% + 10px); left: 0; right: auto; }
}
@media (min-width: 900px) { .nav-menu .in-bar { display: none; } }
@media (min-width: 1100px) { .nav-menu { display: none; } }
/* up to 1279px the bar also holds the language picker, Support and Download, in three languages: tighter gaps and
   pills, and the picker shows its globe only (its aria-label still says the language) */
@media (max-width: 1279px) {
  .nav .wrap { gap: var(--s4); }
  .nav-links a, .nav-menu > summary { padding: 0 12px; }
  .lang-menu > summary { padding: 0; width: 38px; }
  .lang-menu > summary span { display: none; }
}
@media (max-width: 759px) {
  /* phones: name, Menu and theme on one line; the Menu sits at the right, next to the theme button */
  .nav .wrap { gap: var(--s3); }
  .nav nav { margin-left: auto; }
  .nav-actions { margin-left: 0; }
}
/* narrow phones: the name, Menu and theme leave no room for the Download pill, and Download is in the Menu */
@media (max-width: 479px) { .nav-actions .btn-sm { display: none; } }

/* Language picker (English, Português, Español; links to this same page in each, assets/i18n.js remembers the pick):
   a globe and the language code in the bar from 760px, a plain <details> like the Menu (theme.js adds the ways out).
   Below 760px the bar has no room, so the Menu lists the other two languages at its end (.menu-lang). */
.lang-menu { position: relative; display: none; border: 0; }
.lang-menu > summary { display: inline-flex; justify-content: center; gap: 6px; min-height: 38px; padding: 0 10px; border-radius: var(--r-pill);
  font: 600 .8125rem/1 var(--font); letter-spacing: .04em; color: inherit; white-space: nowrap; transition: background-color var(--dur-2) var(--ease); }
.lang-menu > summary .i { width: 18px; height: 18px; color: inherit; transition: none; }
.lang-menu > summary:hover, .lang-menu[open] > summary { color: inherit; background: color-mix(in oklch, currentColor 10%, transparent); }
.lang-menu > summary:hover .i, .lang-menu > summary:active .i { color: inherit; transform: none; }
.lang-menu::details-content { block-size: auto; overflow: visible; transition: none; }
.lang-menu > ul { --ring: var(--accent); position: absolute; top: calc(100% + 10px); right: 0; z-index: 1; min-width: 180px;
  margin: 0; padding: 6px; list-style: none; border-radius: 16px; background: var(--canvas); color: var(--fg); box-shadow: 0 0 0 0.5px var(--hair-strong), var(--shadow-lift); }
.lang-menu a { display: flex; align-items: center; min-height: 44px; padding: 0 14px; border-radius: 10px; color: var(--fg); font-size: .9375rem; font-weight: 500; text-decoration: none; white-space: nowrap; }
.lang-menu a:hover { background: var(--field); }
.lang-menu a[aria-current] { background: var(--accent-soft); color: var(--accent-ink); }
.nav-menu .menu-lang .i { width: 18px; height: 18px; margin-right: 10px; color: var(--fg-2); }
.nav-menu .menu-lang-first { margin-top: 6px; padding-top: 6px; border-top: 1px solid var(--hair-strong); }
@media (min-width: 760px) { .lang-menu { display: block; } .nav-menu .menu-lang { display: none; } }

/* Support: the project's Ko-fi, a quiet outline pill beside Download that takes the bar's own colour (so it reads over
   the hero sky, the night band and the frosted bar alike). Its click opens the Ko-fi panel under the nav (kofi.js),
   and from 760px it replaces the floating button. The cup alone up to 1279px; aria-label names it at every width. */
.nav .btn-sm.nav-kofi { display: none; gap: 7px; padding: 0 15px 0 12px; background: transparent; color: inherit; box-shadow: inset 0 0 0 1px color-mix(in oklch, currentColor 34%, transparent); }
.nav .btn-sm.nav-kofi:hover, .nav .btn-sm.nav-kofi[aria-expanded="true"] { background: color-mix(in oklch, currentColor 10%, transparent); }
.nav-kofi .i { width: 18px; height: 18px; transform-origin: 40% 80%; transition: transform var(--dur-3) var(--ease-spring); }
.nav-kofi:hover .i { transform: rotate(-10deg); }
.nav-kofi[aria-busy="true"] .i { animation: kofiSip .7s var(--ease-in-out) infinite alternate; }
@media (min-width: 760px) {
  .nav .btn-sm.nav-kofi { display: inline-flex; }
  .kofi-fab { display: none !important; }
}
@media (max-width: 1279px) {
  .nav .btn-sm.nav-kofi { width: 38px; padding: 0; justify-content: center; }
  .nav-kofi span { display: none; }
}

/* the English home page's suggestion for Portuguese and Spanish browsers (assets/i18n.js): fixed, so it moves nothing */
.lang-hint { position: fixed; right: max(16px, calc(env(safe-area-inset-right) + 8px)); bottom: max(16px, calc(env(safe-area-inset-bottom) + 8px)); z-index: 46;
  display: flex; align-items: center; gap: 2px; max-width: calc(100vw - 32px); padding: 4px; border-radius: var(--r-pill);
  background: var(--canvas); color: var(--fg); box-shadow: 0 0 0 0.5px var(--hair-strong), var(--shadow-lift); animation: hintIn var(--dur-4) var(--ease-out) both; }
.lang-hint a { display: inline-flex; align-items: center; gap: 8px; min-height: 40px; padding: 0 14px 0 12px; border-radius: var(--r-pill);
  color: var(--accent-ink); font-size: .9375rem; font-weight: 600; text-decoration: none; white-space: nowrap; transition: background-color var(--dur-2) var(--ease); }
.lang-hint a:hover { background: var(--field); }
.lang-hint-x { width: 40px; height: 40px; flex: none; display: inline-grid; place-items: center; border: 0; border-radius: 50%; background: transparent; color: var(--fg-2); cursor: pointer; transition: background-color var(--dur-2) var(--ease); }
.lang-hint-x:hover { background: var(--field); color: var(--fg); }
@keyframes hintIn { from { opacity: 0; transform: translateY(12px); } }
@media (pointer: coarse) { .lang-hint a { min-height: 44px; } .lang-hint-x { width: 44px; height: 44px; } }

/* first-visit GPU warm-up (demo.js): real effects drawn once in view at 0.4% opacity, then removed */
.gpu-warm { position: fixed; left: 0; top: 0; z-index: 60; width: 100%; height: 100%; overflow: hidden; pointer-events: none; }
.gpu-warm > * { opacity: .004; }
.gpu-warm-nav { height: var(--nav-h); background: var(--tint); -webkit-backdrop-filter: var(--frost); backdrop-filter: var(--frost); }

/* ---------- 1. hero: the headline under the sky over your city, then the real app, live, in a window ---------- */
.hero {
  /* light sky: fg-2 at L 0.38 keeps at least 4.8:1 on the lightest sky stop */
  --hero-fg: oklch(0.2 0.03 258); --hero-fg-2: oklch(0.38 0.03 258);
  --sky-a: oklch(0.82 0.075 242); --sky-b: oklch(0.89 0.05 236); --sky-c: oklch(0.95 0.025 222);
  /* the app's frame: its height is set here, before anything loads, so the page never moves (CLS 0) */
  --frame-h: clamp(380px, 6vw + 316px, 440px);
  position: relative; isolation: isolate; overflow: hidden;
  padding: calc(var(--nav-h) + clamp(28px, 5.5vh, 64px)) 0 clamp(80px, 9vw, 136px);
  color: var(--hero-fg);
  /* the sky holds the words; under the window it settles into the page, so the hero has no bottom edge */
  background: linear-gradient(180deg, var(--sky-a) 0%, var(--sky-b) 30%, var(--sky-c) 56%, var(--canvas) 88%);
}
.hero.sky-dark { --hero-fg: oklch(0.975 0.006 250); --hero-fg-2: oklch(0.9 0.02 252); }
.sun {
  position: absolute; z-index: -1; left: 0; top: 0; width: 44vmin; height: 44vmin; margin: -22vmin 0 0 -22vmin; border-radius: 50%; pointer-events: none;
  background: radial-gradient(circle, oklch(0.995 0.02 90) 0 14%, oklch(0.98 0.05 85 / 0.5) 22%, oklch(0.97 0.06 80 / 0.14) 45%, transparent 70%);
  transform: translate(70vw, 30vh); opacity: 0;
}
/* dark site theme by day: the sun stays a warm light source (added with screen), never a grey disc behind the words */
.sun.dim {
  width: 36vmin; height: 36vmin; margin: -18vmin 0 0 -18vmin; mix-blend-mode: screen;
  background: radial-gradient(circle, oklch(0.88 0.1 84 / .92) 0 5.5%, oklch(0.8 0.13 70 / .45) 13%, oklch(0.7 0.13 56 / .2) 26%, oklch(0.62 0.12 48 / .08) 44%, transparent 66%);
}
.hero-inner { display: flex; flex-direction: column; align-items: center; gap: clamp(36px, 5vh, 60px); }
.hero-head { display: flex; flex-direction: column; align-items: center; max-width: 64rem; text-align: center; }
.hero-where { align-self: stretch; min-height: 1.6em; margin-bottom: var(--s4); font-size: .9375rem; color: var(--hero-fg-2); font-variant-numeric: tabular-nums; }
.hero h1 { font-weight: 500; }
.h1-big { display: block; font-size: clamp(2.6rem, 1rem + 4.6vw, 5.5rem); line-height: .98; letter-spacing: -0.04em; }
.h1-sub { display: block; max-width: 36ch; margin: var(--s4) auto 0; font-family: var(--font); font-size: clamp(1.0625rem, 1rem + .5vw, 1.375rem); line-height: 1.4; font-weight: 400; letter-spacing: -0.01em; color: var(--hero-fg-2); }
.cta-row { display: flex; flex-wrap: wrap; gap: var(--s3); }
.hero .cta-row { justify-content: center; margin-top: clamp(24px, 3.4vh, 36px); }
/* phones (the inline <head> script sets .not-windows before the first paint, so showing these never moves the
   page): Share the link takes the place of Other downloads in the hero, so the hero keeps its height and the Store
   button its place, and one short line says why. Without that script they stay hidden */
.share-link, .share-note { display: none; }
.not-windows .share-link { display: inline-flex; }
.not-windows .share-note { display: block; }
.not-windows .cta-row .other-dl { display: none; }
.share-note { margin-top: var(--s3); max-width: 44ch; font-size: .95rem; color: var(--hero-fg-2, var(--fg-2)); }
.pg-hero .share-note { color: var(--fg-2); }
.hero .btn-tinted { background: color-mix(in oklch, var(--hero-fg) 10%, transparent); color: var(--hero-fg); }
.hero .btn-tinted:hover { background: color-mix(in oklch, var(--hero-fg) 16%, transparent); }

/* the app window: a slim bar with Share over the real app (site/app/ in a same-origin frame). Its colours are the
   app's own canvas, so bar and app read as one window; the depth is two soft shadows, wider and fainter than a card's */
.hero-app { position: relative; width: 100%; scroll-margin-top: calc(var(--nav-h) + 16px); }
/* big screens: the window grows past the text column (centred, so it overhangs both sides evenly) */
@media (min-width: 1600px) { .hero-app { width: min(1480px, calc(100vw - 2 * var(--gutter) - 200px)); flex: none; } }
.hero-app::before { /* a wide pale glow under the window, so it sits on the sky instead of on the page */
  content: ""; position: absolute; z-index: -1; inset: 8% 4% -6%; border-radius: 50%; pointer-events: none;
  background: radial-gradient(closest-side, oklch(1 0 0 / .5), transparent); }
.hero.sky-dark .hero-app::before { background: radial-gradient(closest-side, oklch(0.62 0.12 262 / .28), transparent); }
.app-win {
  position: relative; overflow: hidden; border-radius: 22px; background: var(--canvas); color: var(--fg);
  box-shadow: 0 0 0 0.5px oklch(0.3 0.04 255 / 0.16), 0 2px 6px -2px oklch(0.3 0.05 255 / 0.12), 0 24px 56px -22px oklch(0.28 0.07 258 / 0.36), 0 56px 110px -44px oklch(0.28 0.07 258 / 0.3);
}
:root[data-theme="dark"] .app-win { box-shadow: 0 0 0 0.5px oklch(1 0 0 / 0.12), 0 2px 6px -2px oklch(0 0 0 / 0.4), 0 26px 60px -24px oklch(0.04 0.03 265 / 0.8), 0 56px 110px -44px oklch(0.04 0.03 265 / 0.7); }
@media (prefers-color-scheme: dark) { :root:not([data-theme="light"]) .app-win { box-shadow: 0 0 0 0.5px oklch(1 0 0 / 0.12), 0 2px 6px -2px oklch(0 0 0 / 0.4), 0 26px 60px -24px oklch(0.04 0.03 265 / 0.8), 0 56px 110px -44px oklch(0.04 0.03 265 / 0.7); } }
.app-win-bar { display: flex; align-items: center; gap: var(--s3); min-height: 46px; padding: 5px 7px 5px 18px; box-shadow: inset 0 -1px 0 var(--hair); }
.app-win-title { flex: 1; min-width: 0; display: flex; align-items: center; gap: 10px; font-size: .875rem; font-weight: 600; color: var(--fg); white-space: nowrap; overflow: hidden; }
.app-win-text { min-width: 0; overflow: hidden; text-overflow: ellipsis; }
.app-win-hint { font-weight: 400; color: var(--fg-2); }
/* live: a small green light, the way a status bar says something is running */
.app-win-live { flex: none; width: 8px; height: 8px; border-radius: 50%; background: oklch(0.72 0.17 150); box-shadow: 0 0 0 3px oklch(0.72 0.17 150 / .18); }
.app-win-share { display: inline-flex; flex: none; align-items: center; gap: 7px; min-height: 34px; padding: 0 14px 0 12px; border: 0; border-radius: var(--r-pill);
  background: var(--field); color: var(--fg); font-size: .8125rem; font-weight: 600; cursor: pointer; transition: background-color var(--dur-2) var(--ease), transform var(--dur-1) var(--ease); }
.app-win-share:hover { background: var(--field-hover); }
.app-win-share:active { transform: scale(.97); }
.app-win-share .i { width: 16px; height: 16px; }
.app-win-share.is-done { background: var(--accent-soft); color: var(--accent-ink); }
:root:not(.js) .app-frame { display: none; }
.app-noscript { padding: 48px 24px; text-align: center; color: var(--fg-2); }
.app-frame { display: block; width: 100%; height: var(--frame-h); border: 0; background: var(--canvas); color-scheme: normal; }

/* ---------- shared section type ---------- */
.section { padding: clamp(88px, 11vw, 160px) 0; }
.big-h { font-size: var(--fs-h2); line-height: 1.02; font-weight: 500; letter-spacing: -0.035em; text-wrap: balance; }
.lede { margin-top: var(--s4); font-size: var(--fs-lede); color: var(--fg-2); }

/* ---------- 2. time zone converter: the real widget, playing itself until you touch it ---------- */
.demo { position: relative; z-index: 1; text-align: center; padding-bottom: clamp(40px, 5vw, 80px); background: linear-gradient(180deg, var(--hero-end, var(--canvas)) 0, var(--canvas) clamp(72px, 9vw, 140px)); }
.stage { position: relative; margin-top: clamp(32px, 5vw, 64px); text-align: left; }
.wc {
  --ctl-h: 30px;
  position: relative; max-width: 1160px; margin: 0 auto; border-radius: var(--r-app);
  background: var(--canvas-2); box-shadow: var(--shadow-app); color: var(--fg); font-size: 13px; line-height: 1.35;
  -webkit-user-select: none; user-select: none;
}
.wc-bar { display: flex; align-items: center; gap: var(--s2); padding: var(--s3) var(--s3) var(--s2) var(--s4); min-height: 52px; }
.wc-conv { display: flex; align-items: center; gap: var(--s2); flex: 1; min-width: 0; }
.wc-lbl { color: var(--fg-2); white-space: nowrap; }
.wc-field { height: var(--ctl-h); border: 0; border-radius: var(--r-pill); background: var(--field); padding: 0 var(--s3); outline: none; transition: background-color var(--dur-1) var(--ease), box-shadow var(--dur-1) var(--ease); }
.wc-field:hover { background-color: var(--field-hover); }
.wc-field:focus-visible, .wc-field.ghost-focus { box-shadow: 0 0 0 3px var(--accent-soft), inset 0 0 0 1px var(--accent); }
#wcTime { width: 92px; text-align: center; font-family: var(--display); font-size: 15px; font-weight: 500; font-variant-numeric: tabular-nums; -webkit-user-select: text; user-select: text; }
#wcTime::placeholder { font: 400 13px var(--font); color: var(--fg-3); opacity: 1; }
#wcTime.invalid { box-shadow: inset 0 0 0 1px oklch(0.58 0.2 27); }
#wcZone { max-width: 190px; min-width: 0; padding-right: var(--s2); cursor: pointer; }
.wc-chip { cursor: default; }
#wcZone option { background: var(--group); color: var(--fg); }
#wcSlider { -webkit-appearance: none; appearance: none; width: 150px; min-width: 60px; flex-shrink: 1; height: var(--ctl-h); margin: 0; background: transparent; cursor: pointer; }
#wcSlider::-webkit-slider-runnable-track { height: 4px; border-radius: 2px; background: var(--switch-off); }
#wcSlider::-moz-range-track { height: 4px; border-radius: 2px; background: var(--switch-off); }
#wcSlider::-webkit-slider-thumb { -webkit-appearance: none; width: 20px; height: 20px; margin-top: -8px; border-radius: 50%; background: #fff; box-shadow: 0 0 0 0.5px oklch(0 0 0 / 0.14), 0 2px 6px oklch(0 0 0 / 0.22); }
#wcSlider::-moz-range-thumb { width: 20px; height: 20px; border: 0; border-radius: 50%; background: #fff; box-shadow: 0 0 0 0.5px oklch(0 0 0 / 0.14), 0 2px 6px oklch(0 0 0 / 0.22); }
#wcSlider::-webkit-slider-thumb { transition: scale var(--dur-2) var(--ease); }
#wcSlider:hover::-webkit-slider-thumb { scale: 1.12; }
#wcSlider:active::-webkit-slider-thumb { scale: .96; }
#wcSlider:focus-visible { outline: none; }
#wcSlider:focus-visible::-webkit-slider-thumb { box-shadow: 0 0 0 3px var(--accent-soft), 0 0 0 1px var(--accent), 0 2px 6px oklch(0 0 0 / 0.22); }
.wc-pill { height: var(--ctl-h); display: inline-flex; align-items: center; gap: 6px; flex-shrink: 0; white-space: nowrap; cursor: pointer; padding: 0 var(--s3); border: 0; border-radius: var(--r-pill); background: var(--accent-soft); color: var(--accent-ink); font-weight: 600; }
.wc-pill:hover { background: color-mix(in oklch, var(--accent) 22%, transparent); }
.wc-pill:active, .wc-icon-btn:active { transform: scale(.95); }
.wc-pill, .wc-icon-btn { transition: background-color var(--dur-1) var(--ease), color var(--dur-1) var(--ease), transform var(--dur-1) var(--ease); }
.wc-icon-btn { width: var(--ctl-h); height: var(--ctl-h); display: inline-grid; place-items: center; flex: none; border: 0; border-radius: 50%; background: transparent; color: var(--fg-2); cursor: pointer; }
.wc-icon-btn:hover { background: var(--field-hover); color: var(--fg); }
.wc .i { width: 15px; height: 15px; }
.wc-hint { color: var(--fg-2); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; min-width: 0; }
/* the app's date chip and toolbar, drawn for fidelity (decorative, not controls) */
.wc-chip { height: var(--ctl-h); display: inline-flex; align-items: center; gap: 3px; flex: none; padding: 0 9px 0 12px; border-radius: var(--r-pill); background: var(--field); white-space: nowrap; }
.wc-chip .i { width: 13px; height: 13px; color: var(--fg-2); }
.wc-tools { display: flex; align-items: center; gap: 4px; flex: none; margin-left: auto; color: var(--fg-2); }
.wc-seg { display: flex; padding: 2px; margin-right: 4px; border-radius: var(--r-pill); background: var(--field); }
.wc-seg span, .wc-tool { display: grid; place-items: center; border-radius: var(--r-pill); }
.wc-seg span { width: 30px; height: 26px; }
.wc-seg .on { background: var(--group); color: var(--fg); box-shadow: 0 0 0 0.5px var(--hair-strong), 0 1px 2px oklch(0.2 0.03 258 / 0.1); }
.wc-tool { width: 30px; height: 30px; }
.wc-tool.pinned { background: var(--btn); color: #fff; }

.wc-strip { display: flex; gap: var(--s3); padding: var(--s2) var(--s4) var(--s4); overflow-x: auto; overscroll-behavior-x: contain; scroll-snap-type: x proximity; scroll-padding: var(--s4); scrollbar-width: none; }
.wc-strip::-webkit-scrollbar { display: none; }
/* cards: the day/night flip is an opacity crossfade of a navy layer, so it stays on the compositor */
.card {
  --c-fg: var(--day-fg); --c-fg-2: var(--day-fg-2); --c-hair: var(--day-hair); --c-accent: var(--accent);
  flex: 1 1 196px; min-width: 196px; max-width: 270px; scroll-snap-align: start;
  display: grid; grid-template-rows: auto 1fr auto auto; position: relative; isolation: isolate; min-height: 186px;
  padding: var(--s3) var(--s4); background: var(--g-day); color: var(--c-fg); border-radius: var(--r-card); box-shadow: var(--shadow-card);
  cursor: ns-resize; outline: none;
  transition: transform var(--dur-2) var(--ease), box-shadow var(--dur-2) var(--ease);
}
.card::before { content: ""; position: absolute; inset: 0; z-index: -1; border-radius: inherit; background: var(--g-night); opacity: 0; transition: opacity var(--dur-3) var(--ease); }
/* golden hour, dawn and twilight: a second sky layer over day or night, crossfaded on the compositor */
.card .sky { position: absolute; inset: 0; z-index: -1; border-radius: inherit; opacity: 0; pointer-events: none; transition: opacity var(--dur-4) var(--ease); }
.card[data-sky="golden"] .sky { background: var(--g-golden); }
.card[data-sky="dawn"] .sky { background: var(--g-dawn); }
.card[data-sky="twilight"] .sky { background: var(--g-twilight); }
.card.warm .sky { opacity: 1; }
.card-more { position: absolute; top: 9px; right: 13px; font-size: 13px; line-height: 1; letter-spacing: 1px; color: var(--c-fg-2); pointer-events: none; }
.card.is-night { --c-fg: var(--night-fg); --c-fg-2: var(--night-fg-2); --c-hair: var(--night-hair); --c-accent: var(--accent-on-night); }
.card.is-night::before { opacity: 1; }
.card:hover { transform: translateY(-2px); box-shadow: var(--shadow-lift); }
.card.home { box-shadow: 0 0 0 2px var(--accent), var(--shadow-card); }
.card.home:hover { box-shadow: 0 0 0 2px var(--accent), var(--shadow-lift); }
.card:focus-visible { box-shadow: 0 0 0 2px var(--canvas), 0 0 0 4px var(--accent), var(--shadow-card); }
.card-head { min-width: 0; padding-right: 18px; }
.city-row { display: flex; align-items: center; gap: 6px; min-width: 0; }
.city { font-family: var(--display); font-size: 15px; font-weight: 600; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.badge { flex: none; padding: 0 7px; border-radius: var(--r-pill); background: var(--accent-ink); color: #fff; font-size: 10.5px; font-weight: 600; line-height: 16px; }
:root[data-theme="dark"] .badge { background: oklch(0.52 0.19 257); }
@media (prefers-color-scheme: dark) { :root:not([data-theme="light"]) .badge { background: oklch(0.52 0.19 257); } }
.phase-row { display: flex; align-items: center; gap: 5px; margin-top: 1px; font-size: 12.5px; color: var(--c-fg-2); }
.moon { width: 12px; height: 12px; fill: currentColor; stroke: none; }
.display { display: flex; align-items: flex-end; padding-top: var(--s2); }
.time { display: flex; align-items: flex-start; gap: 3px; font-family: var(--display); font-weight: 250; font-size: 50px; line-height: .92; letter-spacing: -1.5px; font-variant-numeric: tabular-nums; color: var(--c-fg); }
.time .hm { display: inline-flex; transition: opacity var(--dur-3) var(--ease); }
.time .ch { display: inline-block; }
.time .sec { font-size: 14px; font-weight: 500; letter-spacing: 0; color: var(--c-fg-2); margin-top: 4px; }
.card.converted.source .time .hm { color: var(--c-accent); }
.card.converted:not(.source) .time .hm { position: relative; }
.card.converted:not(.source) .time .hm::after { content: ""; position: absolute; left: 1px; right: 2px; bottom: -6px; height: 1.5px; border-radius: 1px; background: color-mix(in oklch, var(--c-accent) 70%, transparent); }
.card.asleep .time .hm { opacity: .55; }
.arc { position: relative; height: 2px; margin: var(--s3) 0 var(--s2); background: var(--c-hair); border-radius: 1px; cursor: ew-resize; touch-action: pan-y; }
.arc::before { content: ""; position: absolute; inset: -11px -4px; }
.arc-dot { transition: scale var(--dur-2) var(--ease); }
.arc:hover .arc-dot { scale: 1.5; }
.arc-work { position: absolute; top: 0; bottom: 0; left: 37.5%; width: 37.5%; background: var(--c-fg-2); opacity: .35; border-radius: 1px; }
.card.working .arc-work { opacity: .55; background: var(--c-accent); }
.arc-track { position: absolute; inset: 0; transform: translateX(calc(var(--p, 0) * 100%)); transition: transform var(--dur-3) var(--ease-out); pointer-events: none; }
.arc-dot { position: absolute; top: 50%; left: 0; width: 8px; height: 8px; margin: -4px 0 0 -4px; border-radius: 50%; background: var(--c-fg); }
.card.converted .arc-dot { background: var(--c-accent); }
.meta { display: flex; align-items: baseline; gap: var(--s2); min-width: 0; white-space: nowrap; font-size: 12px; color: var(--c-fg-2); font-variant-numeric: tabular-nums; }
.meta .rel { margin-left: auto; font-weight: 600; color: var(--c-fg); }
.meta .rel.home { color: var(--c-fg-2); font-weight: 500; }
.meta .dshift { margin-left: auto; padding: 0 6px; border-radius: var(--r-pill); font-size: 11px; font-weight: 600; line-height: 16px; color: var(--c-fg); background: color-mix(in oklch, var(--c-fg) 11%, transparent); }
.meta .dshift:not([hidden]) + .rel { margin-left: 0; }
.dshift:not([hidden]) { animation: pop var(--dur-3) var(--ease-spring); }

.stage-note { display: flex; justify-content: center; align-items: center; gap: 8px; margin-top: var(--s5); font-size: .9375rem; color: var(--fg-2); text-align: center; }
.stage-note .i { width: 20px; height: 20px; }
@media (hover: none) { .stage-note .i { display: none; } }

/* the scripted cursor */
.ghost { position: absolute; left: 0; top: 0; z-index: 6; width: 24px; height: 24px; pointer-events: none; opacity: 0;
  transition: transform 750ms var(--ease-in-out), opacity var(--dur-3) var(--ease); will-change: transform; }
.ghost.on { opacity: 1; }
.ghost svg { width: 24px; height: 24px; overflow: visible; filter: drop-shadow(0 2px 3px oklch(0 0 0 / 0.3)); transition: transform var(--dur-1) var(--ease); transform-origin: 4px 3px; }
.ghost.press svg { transform: scale(.82); }
.ghost::after { content: ""; position: absolute; left: -10px; top: -11px; width: 28px; height: 28px; border-radius: 50%; border: 2px solid var(--accent); opacity: 0; transform: scale(.3); }
.ghost.press::after { animation: ripple var(--dur-4) var(--ease-out); }
.ghost .wheel { position: absolute; left: 22px; top: 18px; width: 12px; height: 18px; border-radius: 6px; border: 1.5px solid var(--fg); background: var(--canvas); opacity: 0; transition: opacity var(--dur-2) var(--ease); }
.ghost .wheel::after { content: ""; position: absolute; left: 50%; top: 3px; width: 2px; height: 5px; margin-left: -1px; border-radius: 1px; background: var(--fg); }
.ghost.scrolling .wheel { opacity: 1; }
.ghost.touch svg, .ghost.touch .wheel { display: none; }
.ghost.touch::before { content: ""; position: absolute; left: -15px; top: -15px; width: 30px; height: 30px; border-radius: 50%;
  background: oklch(1 0 0 / .45); box-shadow: 0 0 0 1.5px oklch(1 0 0 / .8), 0 4px 14px oklch(0 0 0 / .28); transition: transform var(--dur-2) var(--ease); }
.ghost.touch.press::before, .ghost.touch.drag::before { transform: scale(.82); }
.ghost.touch::after { left: -14px; top: -14px; }
.ghost.scrolling .wheel::after { animation: wheel 420ms linear infinite; }
@keyframes ripple { from { opacity: .9; transform: scale(.3); } to { opacity: 0; transform: scale(1.4); } }
@keyframes wheel { from { transform: translateY(-2px); opacity: 1; } to { transform: translateY(5px); opacity: .2; } }
@keyframes pop { from { opacity: 0; transform: scale(.6); } to { opacity: 1; transform: none; } }

/* ---------- 3. scene: the world, lit by the sun; scrolling slides night across ---------- */
.scene { position: relative; height: 320vh; background: var(--canvas); }
.scene-sticky {
  position: sticky; top: 0; height: 100vh; height: 100svh; overflow: hidden;
  display: flex; flex-direction: column; justify-content: center; gap: clamp(14px, 3vh, 32px);
  padding: var(--nav-h) 0 clamp(12px, 3vh, 28px);
}
.beats { display: grid; text-align: center; }
.beat { grid-area: 1 / 1; margin: 0; font-family: var(--display); text-wrap: balance; font-size: var(--fs-h2s); line-height: 1.04; font-weight: 500; letter-spacing: -0.035em;
  opacity: 0; transform: translateY(.4em); transition: opacity var(--dur-4) var(--ease-out), transform var(--dur-5) var(--ease-out); }
.beat:not(.on) { transition-duration: var(--dur-3), var(--dur-4); transform: translateY(-.3em); }
.beat.on ~ .beat:not(.on) { transform: translateY(.4em); }
.beat.on { opacity: 1; transform: none; }

.map { position: relative; flex: none; width: 100%; height: min(36.95vw, calc(100svh - var(--nav-h) - 13rem)); overflow: hidden; background: var(--map-sea); contain: strict; }
.map-world {
  --hx: .5;
  position: absolute; top: 0; left: 50%; height: 100%; aspect-ratio: 3600 / 1330;
  transform: translateX(calc(-50% + (0.5 - var(--hx)) * 100%));
}
.map-land { position: absolute; top: 0; left: -100%; width: 300%; height: 100%; max-width: none; fill: var(--map-land); }
.map-night { position: absolute; top: 0; left: -100%; width: 400%; height: 100%; color: var(--map-night); will-change: transform; pointer-events: none; }
.map-night svg { width: 100%; height: 100%; max-width: none; overflow: hidden; }
.map-pins { position: absolute; inset: 0; }
.pin { position: absolute; width: 0; height: 0; }
.pin-dot { position: absolute; left: -5px; top: -5px; width: 10px; height: 10px; border-radius: 50%; background: var(--fg); box-shadow: 0 0 0 2px var(--map-land); transition: background-color var(--dur-3) var(--ease), box-shadow var(--dur-3) var(--ease); }
/* night cities are moonlit: a navy dot in a pale cool ring. Warm yellow belongs to the sun alone. */
.pin.is-night .pin-dot { background: var(--night-solid); box-shadow: 0 0 0 1.5px oklch(0.88 0.045 250), 0 0 10px 1px oklch(0.8 0.08 250 / .4); }
.pin.home .pin-dot, .pin.home.is-night .pin-dot { background: var(--accent); box-shadow: 0 0 0 2px var(--map-land), 0 0 0 5px color-mix(in oklch, var(--accent) 30%, transparent); }
.pin.home.is-night .pin-dot { background: var(--accent-on-night); box-shadow: 0 0 0 2px var(--night-solid), 0 0 0 5px color-mix(in oklch, var(--accent-on-night) 35%, transparent); }
.pin-label {
  position: absolute; left: 12px; top: -13px; height: 26px; display: flex; align-items: center; gap: 7px; padding: 0 10px; border-radius: var(--r-pill);
  background: var(--day-solid); color: var(--day-fg); font-size: 12.5px; line-height: 1; white-space: nowrap; box-shadow: var(--shadow-card);
}
.pin.flip .pin-label { left: -12px; transform: translateX(-100%); } /* anchored by transform, so a width change never shifts layout */
.pin.is-night .pin-label { background: var(--night-solid); color: var(--night-fg); }
.pin-label b { font-family: var(--display); font-weight: 600; }
.pin-label .t { font-family: var(--display); font-variant-numeric: tabular-nums; opacity: .85; }
.pin-label .moon { display: none; flex: none; width: 11px; height: 11px; margin-left: -4px; color: var(--accent-on-night); }
.pin.is-night .pin-label .moon { display: block; }

.scene-rows { display: none; }
.ruler { max-width: 720px; }
.ruler-track { position: relative; height: 4px; margin-bottom: 34px; border-radius: 2px; background: color-mix(in oklch, var(--fg) 14%, transparent); }
.ruler-fill { position: absolute; inset: 0; border-radius: 2px; background: var(--accent); transform-origin: left; transform: scaleX(0); }
.ruler-move { position: absolute; inset: 0; transform: translateX(0); }
.ruler-thumb { position: absolute; top: 50%; left: 0; width: 20px; height: 20px; margin: -10px 0 0 -10px; border-radius: 50%; background: #fff; box-shadow: 0 0 0 0.5px oklch(0 0 0 / 0.14), 0 2px 8px oklch(0 0 0 / 0.25); }
/* the tag leans right at the start and left at the end, so it never leaves the track (or the screen) */
.ruler-tag { position: absolute; top: 26px; left: 50%; transform: translateX(-50%); padding: 3px 10px; border-radius: var(--r-pill); background: var(--btn); color: #fff; font-size: .8125rem; font-weight: 600; white-space: nowrap; }
/* a quiet way out of the scene to the page about the map; it sits under the ruler tag's own space, so it never meets it */
.scene-more { margin: -6px auto 0; text-align: center; font-size: .9375rem; }
.scene-more a { display: inline-flex; align-items: center; min-height: 44px; padding: 0 4px; color: var(--fg-2); }
.scene-more a:hover { color: var(--fg); }

/* ---------- 4. features: bento of live mini demos ---------- */
.features { padding-bottom: clamp(56px, 6vw, 96px); background: linear-gradient(180deg, var(--canvas) 0, var(--canvas-2) 200px, var(--canvas-2) calc(100% - 220px), var(--canvas) 100%); }
.bento { display: grid; grid-template-columns: repeat(12, minmax(0, 1fr)); gap: clamp(12px, 1.6vw, 20px); margin-top: clamp(40px, 6vw, 72px); }
.tile { position: relative; display: flex; flex-direction: column; min-height: 340px; padding: clamp(20px, 2.4vw, 32px); border-radius: var(--r-tile); overflow: hidden;
  background: var(--group); box-shadow: 0 0 0 0.5px var(--hair-strong), var(--shadow-card); }
.tile h3 { margin-top: auto; padding-top: var(--s6); font-size: var(--fs-h3); line-height: 1.1; font-weight: 500; letter-spacing: -0.025em; }
/* each tile is one link to the page that covers it: the heading's link stretches over the whole tile. The heading stays
   unpositioned so the stretched ::after takes the tile as its box; the words sit above the pointer halo on their own. */
.tile h3 a { color: inherit; text-decoration: none; }
.tile h3 a > span { position: relative; z-index: 2; }
.tile h3 a::after { content: ""; position: absolute; inset: 0; z-index: 3; border-radius: var(--r-tile); }
.tile h3 a:hover { text-decoration: underline; text-decoration-thickness: 1.5px; text-underline-offset: 0.18em; }
@supports selector(:has(a)) {
  /* the ring sits outside the tile, on the page, so it takes the page's accent even around a night tile */
  .tile:has(h3 a:focus-visible) { outline: 2px solid var(--accent); outline-offset: 3px; }
  .tile h3 a:focus-visible { outline: none; }
}
.tile-demo { position: relative; z-index: 1; flex: 1; display: grid; place-items: center; min-height: 180px; }
/* a soft light follows a mouse pointer across a tile (transform and opacity only; demo.js, fine pointers) */
.tile-glow { position: absolute; left: 0; top: 0; z-index: 0; width: 520px; height: 520px; margin: -260px 0 0 -260px; border-radius: 50%; pointer-events: none;
  background: radial-gradient(closest-side, color-mix(in oklch, var(--accent) 13%, transparent), transparent); opacity: 0; transition: opacity var(--dur-4) var(--ease); will-change: transform; }
.night-tile .tile-glow { background: radial-gradient(closest-side, oklch(0.8 0.1 250 / .14), transparent); }
.tile.is-hot .tile-glow { opacity: 1; transition-duration: var(--dur-3); }
.night-tile { background: var(--band-night); color: var(--band-fg); box-shadow: 0 0 0 0.5px oklch(1 0 0 / 0.08), var(--shadow-card); }
.t-conv { grid-column: span 7; }
.t-plan { grid-column: span 5; }
.t-pin { grid-column: span 5; }
.t-copy { grid-column: span 4; }
.t-label { grid-column: span 3; }
.t-theme { grid-column: span 7; }
.t-lang { grid-column: span 5; }

/* the typing caret hangs off the right edge of the text itself, so typing grows one box and never moves another (CLS 0).
   It blinks with opacity on its own tiny layer (compositor, no style work per frame) and only while its tile is on screen. */
.caret-text { position: relative; display: inline-block; min-height: 1.1em; padding-right: 4px; }
.caret-text::after { content: ""; position: absolute; top: .06em; right: 0; bottom: .06em; width: 2px; border-radius: 1px; background: var(--accent);
  animation: blink 1.1s steps(1) infinite paused; }
.in-view .caret-text::after { animation-play-state: running; }
@keyframes blink { 50% { opacity: 0; } }

/* converter tile */
.mconv { display: flex; align-items: center; gap: var(--s2); flex-wrap: wrap; justify-content: center; font-size: .9375rem; color: var(--fg-2); }
.mconv-field { display: inline-flex; align-items: center; width: 112px; height: 40px; justify-content: flex-start; padding: 0 16px 0 22px; border-radius: var(--r-pill); background: var(--field); color: var(--fg); font-family: var(--display); font-size: 1.125rem; font-weight: 500; box-shadow: 0 0 0 3px var(--accent-soft), inset 0 0 0 1px var(--accent); }
.mconv-zone { height: 40px; display: inline-flex; align-items: center; padding: 0 16px; border-radius: var(--r-pill); background: var(--field); color: var(--fg); font-weight: 500; }
.mcards { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--s3); width: 100%; margin-top: var(--s6); }
.mcard { --c-fg: var(--day-fg); --c-fg-2: var(--day-fg-2); display: grid; gap: 2px; padding: 14px 16px; border-radius: var(--r-card); background: var(--g-day); color: var(--c-fg); box-shadow: var(--shadow-card); }
.mcard.is-night { --c-fg: var(--night-fg); --c-fg-2: var(--night-fg-2); background: var(--g-night); }
.mcard[data-sky="golden"] { background: var(--g-golden); }
.mcard[data-sky="dawn"] { background: var(--g-dawn); }
.mcard[data-sky="twilight"] { background: var(--g-twilight); }
:root:not([data-theme="dark"]) .t-conv .mcard:not(.is-night) { box-shadow: 0 0 0 0.5px var(--hair-strong), var(--shadow-card); }
.mcard.source { box-shadow: 0 0 0 2px var(--accent), var(--shadow-card) !important; }
.mcard-city { font-family: var(--display); font-weight: 600; font-size: .9375rem; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.mcard-time { display: inline-flex; font-family: var(--display); font-weight: 250; font-size: clamp(2rem, 1.4rem + 1.8vw, 2.75rem); line-height: 1; letter-spacing: -0.035em; margin: 8px 0 4px; font-variant-numeric: tabular-nums; }
.mcard-time .ch { display: inline-block; }
.mcard.source .mcard-time { color: var(--accent-ink); }
.mcard.source.is-night .mcard-time { color: var(--accent-on-night); }
.mcard-meta { display: flex; justify-content: space-between; gap: var(--s2); font-size: .8125rem; color: var(--c-fg-2); }
.mcard-shift { font-weight: 600; color: var(--c-fg); }
/* placeholder cards in the HTML: they hold the tile's height until demo.js builds the real ones, so the build moves
   nothing on phones, where the tile takes its height from its content */
.mcard-hold { visibility: hidden; }

/* planner tile: the app's hour grid. Each cell is that city's local hour; blue = working, slate = night.
   One grid holds cells, the overlap block and the selected-hour line, so they always line up. */
.planner { width: 100%; }
.planner-top { display: flex; align-items: baseline; flex-wrap: wrap; gap: 2px var(--s3); margin-bottom: var(--s4); font-size: .8125rem; }
.planner-sum { font-family: var(--display); font-weight: 600; font-size: 1.125rem; letter-spacing: -0.015em; color: var(--accent-ink); }
.planner-title { color: var(--fg-2); }
.pgrid { --cols: 12; position: relative; isolation: isolate; display: grid; grid-template-columns: minmax(0, 6.25rem) auto repeat(var(--cols), minmax(0, 1fr)); column-gap: 3px; row-gap: 5px; align-items: center; }
.pname { padding-right: var(--s2); font-size: .875rem; font-weight: 600; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.pname.home { color: var(--accent-ink); }
.ptime { padding-right: var(--s3); font-size: .75rem; color: var(--fg-2); }
.pc { position: relative; z-index: 1; height: 24px; display: grid; place-items: center; border-radius: 6px; background: var(--cell); color: var(--cell-fg); font-size: .6875rem; font-weight: 600; line-height: 1; }
.pc.night { background: var(--cell-night); color: var(--cell-night-fg); }
.pc.work { background: var(--cell-work); color: var(--cell-work-fg); }
.pc.day0 { font-size: .5625rem; letter-spacing: .01em; }
.pc.sel { box-shadow: inset 0 0 0 1.5px var(--accent); }
.psel { position: relative; z-index: 0; justify-self: center; align-self: stretch; width: 2px; margin: -9px 0 -3px; border-radius: 1px; background: var(--accent); transform-origin: top; }
.psel::before { content: ""; position: absolute; left: -3px; top: -2px; width: 8px; height: 8px; border-radius: 50%; background: var(--accent); }
.pover { z-index: 2; align-self: stretch; margin: -4px -3px; border-radius: 10px; box-shadow: inset 0 0 0 1.5px var(--accent), 0 0 0 4px var(--accent-soft); pointer-events: none; transform-origin: center; }

/* pin tile: a chat window slides under the pinned strip, clipped to the demo so it never covers the title */
.t-pin .tile-demo { overflow: hidden; margin: calc(-1 * var(--s2)) calc(-1 * clamp(20px, 2.4vw, 32px)) 0; padding: var(--s4) clamp(20px, 2.4vw, 32px) 0;
  -webkit-mask-image: linear-gradient(180deg, #000 72%, transparent); mask-image: linear-gradient(180deg, #000 72%, transparent); }
.desk { position: relative; width: 100%; max-width: 380px; height: 220px; }
.desk-win { position: absolute; left: 6%; right: 0; top: 46px; bottom: -30px; padding: 30px 16px 16px; border-radius: 14px; background: oklch(0.97 0.008 250); color: oklch(0.25 0.03 258);
  box-shadow: 0 20px 40px -18px oklch(0 0 0 / 0.6); display: flex; flex-direction: column; gap: 8px; font-size: .875rem; }
.desk-win-bar { position: absolute; top: 10px; left: 12px; display: flex; gap: 5px; }
.desk-win-bar span { width: 8px; height: 8px; border-radius: 50%; background: oklch(0.8 0.01 250); }
.bubble { max-width: 78%; padding: 7px 12px; border-radius: 14px; line-height: 1.3; }
.bubble.in { align-self: flex-start; background: oklch(0.91 0.01 250); }
.bubble.out { align-self: flex-end; background: var(--btn); color: #fff; }
.bubble.skel { width: 40%; height: 30px; }
.bubble.skel.w1 { width: 62%; }
.bubble.skel.w2 { width: 50%; }
.desk-widget { position: absolute; left: 0; right: 10%; top: 0; z-index: 2; display: flex; gap: 6px; padding: 7px; border-radius: 14px;
  background: oklch(0.965 0.014 245 / 0.94); box-shadow: 0 12px 30px -10px oklch(0 0 0 / 0.55), 0 0 0 0.5px oklch(1 0 0 / 0.3); }
.pchip { flex: 1; min-width: 0; display: grid; padding: 6px 9px; border-radius: 9px; background: oklch(0.995 0.004 240); color: oklch(0.22 0.03 258); font-size: .6875rem; line-height: 1.2; }
.pchip b { font-weight: 600; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.pchip span { font-family: var(--display); font-weight: 300; font-size: 1.25rem; letter-spacing: -0.02em; }
.pchip.is-night { background: oklch(0.29 0.06 263); color: oklch(0.985 0.006 250); }
.desk-pin { flex: none; align-self: center; width: 28px; height: 28px; display: grid; place-items: center; border-radius: 50%; background: var(--btn); color: #fff; }
.desk-pin .i { width: 15px; height: 15px; }

/* copy tile */
.mcopy { width: 100%; display: grid; justify-items: start; gap: var(--s4); }
.mcopy-btn { display: inline-flex; align-items: center; gap: 8px; height: 38px; padding: 0 16px; border-radius: var(--r-pill); background: var(--accent-soft); color: var(--accent-ink); font-weight: 600; font-size: .9375rem;
  transition: transform var(--dur-2) var(--ease); }
.mcopy-btn .i { width: 16px; height: 16px; }
.mcopy-btn.press { transform: scale(.94); }
.mcopy-paper { width: 100%; display: grid; gap: 3px; padding: 14px 16px; border-radius: 14px; background: var(--canvas-2); box-shadow: inset 0 0 0 0.5px var(--hair-strong); font-size: .8125rem; line-height: 1.45; }
.mcopy-paper span { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; opacity: .18; transform: translateY(4px); transition: opacity var(--dur-4) var(--ease-out), transform var(--dur-4) var(--ease-out); transition-delay: calc(var(--i) * var(--stagger)); }
.mcopy-paper .hd { font-weight: 600; }
.t-copy.copied .mcopy-paper span { opacity: 1; transform: none; }

/* label tile */
.mlabel.card { width: 100%; max-width: 230px; min-height: 0; cursor: default; grid-template-rows: auto auto auto; padding: 14px 16px 16px; }
.mlabel.card:hover { transform: none; box-shadow: var(--shadow-card); }
:root:not([data-theme="dark"]) .mlabel.card:not(.is-night) { box-shadow: 0 0 0 0.5px var(--hair-strong), var(--shadow-card); }
.mlabel .city { overflow: visible; }
.mlabel .time { font-size: 44px; }

/* theme tile: light and dark, wiped by scroll (transform only) */
.t-theme .tile-demo { place-items: center start; }
.t-theme .wipe { width: 136%; max-width: none; }
.wipe { position: relative; margin: 0; width: 100%; border-radius: var(--r-card); overflow: hidden; box-shadow: var(--shadow-shot); view-timeline-name: --wipe; }
.wipe img { width: 100%; }
.wipe-dark { position: absolute; inset: 0; overflow: hidden; transform: translateX(50%); box-shadow: inset 2px 0 0 #fff; }
.wipe-dark img { position: absolute; inset: 0; height: 100%; object-fit: cover; transform: translateX(-50%); }

/* language tile */
.langs { width: 100%; margin: 0; padding: 0; list-style: none; display: grid; gap: var(--s3); }
.langs li { display: flex; align-items: baseline; justify-content: space-between; gap: var(--s4); padding-bottom: var(--s3); border-bottom: 1px solid oklch(1 0 0 / 0.12); }
.langs b { font-family: var(--display); font-weight: 250; font-size: clamp(1.75rem, 1.2rem + 1.6vw, 2.5rem); letter-spacing: -0.03em; }
.langs span { color: var(--band-fg-2); font-size: .8125rem; font-weight: 600; letter-spacing: .08em; }

/* ---------- 5. compare: one line ---------- */
.compare { padding-block: clamp(64px, 8vw, 112px); }
.compare-line { max-width: 22ch; margin: 0 auto; text-align: center; font-family: var(--display); font-size: var(--fs-h2s); line-height: 1.1; font-weight: 400; letter-spacing: -0.03em; }
.compare-line span { color: var(--fg-2); }
.compare-line a { color: inherit; text-decoration-thickness: 2px; text-underline-offset: 0.14em; }

/* ---------- 6. privacy ---------- */
.night-band { position: relative; isolation: isolate; color: var(--band-fg); }
/* the band's sky is its own layer so it can open from a rounded card to full bleed as night arrives */
.band-sky { position: absolute; inset: 0; z-index: -1; overflow: hidden; background: var(--band-night); }
/* a few fixed stars, drawn with gradients (no image, no JS) */
.band-sky::before, .dusk-stars {
  background-image:
    radial-gradient(1.2px 1.2px at 12% 22%, oklch(1 0 0 / .9) 50%, transparent 100%),
    radial-gradient(1px 1px at 31% 71%, oklch(1 0 0 / .7) 50%, transparent 100%),
    radial-gradient(1.4px 1.4px at 47% 12%, oklch(0.95 0.05 85 / .9) 50%, transparent 100%),
    radial-gradient(1px 1px at 63% 48%, oklch(1 0 0 / .6) 50%, transparent 100%),
    radial-gradient(1.2px 1.2px at 78% 83%, oklch(1 0 0 / .8) 50%, transparent 100%),
    radial-gradient(1px 1px at 89% 29%, oklch(1 0 0 / .7) 50%, transparent 100%),
    radial-gradient(1px 1px at 5% 91%, oklch(1 0 0 / .5) 50%, transparent 100%);
  background-size: 340px 260px; background-repeat: repeat;
}
.band-sky::before { content: ""; position: absolute; inset: -20% 0; opacity: .55; pointer-events: none; }
.privacy-wrap { text-align: center; }
.privacy-big .w { display: inline-block; }
.privacy-big { font-size: var(--fs-mega); line-height: .95; font-weight: 500; letter-spacing: -0.045em; }

/* ---------- 6b. values: why it's free, in two lines, with the source and the policy one click away ---------- */
.values { padding-bottom: 0; }
.values-wrap { text-align: center; }
.values-h { max-width: 18ch; margin: 0 auto; font-size: var(--fs-h2); line-height: 1.02; font-weight: 500; letter-spacing: -0.035em; text-wrap: balance; }
.values-h span { display: inline-block; }
.values-why { max-width: 44ch; margin: var(--s5) auto 0; font-size: var(--fs-lede); color: var(--fg-2); text-wrap: pretty; }
.values-links { display: flex; flex-wrap: wrap; justify-content: center; gap: 0 var(--s8); margin-top: var(--s5); }
.values-links a { display: inline-flex; align-items: center; min-height: 44px; font-weight: 600; }

/* ---------- 7. faq ---------- */
.faq-grid { display: grid; grid-template-columns: minmax(0, 5fr) minmax(0, 7fr); gap: clamp(32px, 5vw, 80px); align-items: start; }
.faq-list { border-top: 1px solid var(--hair-strong); }
details { border-bottom: 1px solid var(--hair-strong); interpolate-size: allow-keywords; }
summary { display: flex; align-items: center; justify-content: space-between; gap: var(--s4); padding: 22px 0; cursor: pointer; list-style: none; font-family: var(--display); font-size: 1.3125rem; font-weight: 500; letter-spacing: -0.01em; border-radius: 8px; }
summary::-webkit-details-marker { display: none; }
summary { transition: color var(--dur-2) var(--ease); }
summary:hover { color: var(--accent-ink); }
summary:hover .i { color: var(--accent-ink); }
summary:active .i { transform: scale(.85); }
details[open] summary:active .i { transform: rotate(45deg) scale(.85); }
summary .i { width: 22px; height: 22px; color: var(--fg-2); transition: transform var(--dur-3) var(--ease), color var(--dur-2) var(--ease); }
details[open] summary .i { transform: rotate(45deg); }
details::details-content { block-size: 0; overflow: hidden; transition: block-size var(--dur-3) var(--ease), content-visibility var(--dur-3) allow-discrete; }
details[open]::details-content { block-size: auto; }
.answer { padding: 0 0 24px; color: var(--fg-2); max-width: 60ch; }
.faq-more { margin-top: var(--s4); }
.faq-more a { display: inline-flex; align-items: center; min-height: 44px; font-weight: 600; }

/* ---------- 8. download: dusk into night ---------- */
/* the last scene: dusk. As it scrolls in, the sun sinks behind the curve of the earth, the sky deepens and stars come out.
   The earth is the footer's colour, so the page ends on the night side of the planet. */
.download { --horizon: clamp(64px, 10vw, 140px); --sun: min(52vw, 560px);
  position: relative; overflow: hidden; isolation: isolate; color: var(--band-fg); text-align: center;
  background: linear-gradient(180deg, var(--canvas) 0%, oklch(0.56 0.09 305) 30%, oklch(0.36 0.085 280) 62%, oklch(0.27 0.07 270) 100%); }
.dusk { position: absolute; inset: 0; z-index: -1; pointer-events: none; }
.dusk::before { content: ""; position: absolute; inset: 0; background: linear-gradient(180deg, transparent 0%, oklch(0.2 0.05 268 / .55) 40%, oklch(0.18 0.045 266 / .7) 100%); }
.dusk-stars { position: absolute; inset: 18% 0 30%; -webkit-mask-image: linear-gradient(180deg, transparent, #000 35%, #000 70%, transparent); mask-image: linear-gradient(180deg, transparent, #000 35%, #000 70%, transparent); }
.dusk-sun { position: absolute; left: 50%; top: calc(100% - var(--horizon)); width: var(--sun); height: var(--sun); margin: calc(var(--sun) / -2) 0 0 calc(var(--sun) / -2); border-radius: 50%;
  background: radial-gradient(circle closest-side, oklch(0.98 0.04 90) 0 10%, oklch(0.92 0.11 78 / .85) 14%, oklch(0.82 0.15 58 / .4) 28%, oklch(0.7 0.14 38 / .16) 52%, transparent 100%);
  transform: translate3d(0, -4%, 0); }
.dusk-earth { position: absolute; left: 50%; top: calc(100% - var(--horizon)); width: 320vw; height: 320vw; margin-left: -160vw; border-radius: 50%;
  background: var(--band-night);
  box-shadow: 0 0 0 1px oklch(0.88 0.09 70 / .55), 0 -6px 24px oklch(0.85 0.12 62 / .35), 0 -30px 90px oklch(0.72 0.14 45 / .28); }
.download .inner { position: relative; padding-top: clamp(120px, 16vw, 200px); padding-bottom: calc(var(--horizon) + clamp(88px, 11vw, 150px)); display: grid; justify-items: center; }
.dl-icon { width: 96px; height: 96px; } /* the bare globe (logo-small.svg): its gold rim reads on the dusk, no plate needed */
.download h2 { margin-top: var(--s8); font-size: var(--fs-display); line-height: .98; font-weight: 500; letter-spacing: -0.04em; max-width: 13ch; }
.dl-buttons { display: flex; flex-wrap: wrap; justify-content: center; gap: var(--s3); margin-top: var(--s10); }
.download .btn-primary { min-height: 60px; padding: 0 30px; font-size: 1.0625rem; background: #fff; color: oklch(0.25 0.06 262); box-shadow: 0 16px 40px -14px oklch(0.1 0.05 265 / 0.7); }
.download .btn-primary:hover { background: oklch(0.94 0.02 250); }
.download .btn-quiet { color: var(--band-fg); box-shadow: inset 0 0 0 1px oklch(1 0 0 / 0.3); min-height: 60px; }
.download .btn-quiet:hover { background: oklch(1 0 0 / 0.08); }
.reqs { display: flex; flex-wrap: wrap; justify-content: center; gap: var(--s2) var(--s6); margin: var(--s8) 0 0; padding: 0; list-style: none; color: var(--band-fg-2); font-size: .9375rem; }
.reqs li { display: inline-flex; align-items: center; gap: 6px; }
.reqs .i { width: 16px; height: 16px; stroke-width: 2; color: oklch(0.82 0.1 160); }
.soon { display: inline-flex; align-items: center; gap: 8px; margin-top: var(--s5); padding: 7px 14px 7px 11px; border-radius: var(--r-pill); font-size: .875rem; color: var(--band-fg-2);
  background: oklch(1 0 0 / .06); box-shadow: inset 0 0 0 1px oklch(1 0 0 / .12); }
.soon .i { width: 16px; height: 16px; }

.footer { position: relative; overflow: hidden; background: var(--band-night); color: var(--band-fg-2); padding: var(--s10) 0 var(--s10); font-size: .9375rem; }
.footer:has(.footer-mark) { padding-bottom: 0; }
/* the name once more, drawn as thin as the hero clock, sinking into the night like the sun above it
   (sized so "Open World Clock" spans about 78% of the width, like the old two-word mark did) */
.footer-mark { margin: clamp(24px, 4vw, 56px) 0 0; height: .6em; overflow: hidden; text-align: center; white-space: nowrap;
  font-family: var(--display); font-weight: 150; font-size: clamp(42px, 10.9vw, 198px); line-height: .8; letter-spacing: -0.05em;
  -webkit-user-select: none; user-select: none; }
.footer .wrap { display: flex; flex-wrap: wrap; align-items: center; gap: var(--s2) var(--s8); }
.footer .brand { min-height: 44px; color: var(--band-fg); }
.footer nav ul { display: flex; flex-wrap: wrap; gap: 0 var(--s6); margin: 0; padding: 0; list-style: none; }
.footer nav a { display: inline-flex; align-items: center; min-height: 44px; }
.footer a { color: var(--band-fg-2); transition: color var(--dur-2) var(--ease); }
.footer a:hover { color: var(--band-fg); }
/* the gradient lives on the span: a parent's background-clip cannot reach a child that animates on its own layer */
.footer-mark span { display: inline-block; color: transparent; background: linear-gradient(180deg, oklch(0.9 0.04 255 / .32), oklch(0.9 0.04 255 / .04) 62%); -webkit-background-clip: text; background-clip: text; }
.footer .legal { margin-left: auto; }
/* the language links: the same page in English, Portuguese and Spanish */
.footer .footer-langs { display: flex; align-items: center; gap: 10px; }
.footer .footer-langs .i { width: 16px; height: 16px; }
.footer .footer-langs ul { gap: 0 var(--s4); }
.footer .footer-langs a[aria-current] { color: var(--band-fg); }
/* the full list of pages (home and the content pages) sits in a tidy grid instead of one long wrapping row */
.footer nav:has(.footer-pages) { flex: 1 1 520px; }
.footer .footer-pages { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 0 var(--s6); }
@media (min-width: 900px) { .footer .footer-pages { grid-template-columns: repeat(3, minmax(0, max-content)); column-gap: var(--s10); } }

/* ---------- Ko-fi ---------- */
/* Our own button, styled like Ko-fi's floating one. Nothing from Ko-fi loads until it is clicked (assets/kofi.js).
   Fixed, so showing it moves nothing. It is display: none until after load (.is-ready, then it fades in from its
   @starting-style), so it costs the first paint nothing and is never the LCP candidate, and it
   steps aside (.is-tucked) over the hero (its headline and Store button own those corners) and where the download
   section and footer have their own Ko-fi link. On every page it also steps away while you scroll down
   (.is-away, below 1400px). */
:root { --kofi-x: max(16px, calc(env(safe-area-inset-left) + 8px)); --kofi-y: max(16px, calc(env(safe-area-inset-bottom) + 8px)); }
.kofi-fab { position: fixed; left: var(--kofi-x); bottom: var(--kofi-y); z-index: 45;
  display: none; align-items: center; gap: 8px; min-height: 46px; padding: 0 18px 0 13px; border-radius: var(--r-pill);
  background: #00b9fe; color: #0a1326; font-size: .9375rem; font-weight: 700; line-height: 1; letter-spacing: -0.005em; text-decoration: none; white-space: nowrap;
  text-shadow: none; -webkit-tap-highlight-color: transparent; /* navy on Ko-fi blue: 8.26:1 (9.48:1 on hover) */
  box-shadow: 0 1px 2px oklch(0.3 0.08 240 / .25), 0 10px 24px -10px oklch(0.3 0.1 245 / .6);
  opacity: 0; visibility: hidden; transform: translate3d(0, 12px, 0) scale(.94);
  transition: opacity var(--dur-3) var(--ease), transform var(--dur-3) var(--ease-out), visibility 0s linear var(--dur-3), background-color var(--dur-2) var(--ease); }
.kofi-fab.is-ready { display: inline-flex; opacity: 1; visibility: visible; transform: none; transition-delay: 0s; }
@starting-style { .kofi-fab.is-ready { opacity: 0; transform: translate3d(0, 12px, 0) scale(.94); } }
.kofi-fab.is-ready.is-tucked:not([aria-expanded="true"]) { opacity: 0; visibility: hidden; transform: translate3d(0, 12px, 0) scale(.94); transition-delay: 0s, 0s, var(--dur-3), 0s; }
.kofi-fab:hover { background: #33c7ff; }
.kofi-fab.is-ready:active { transform: scale(.97); transition-duration: var(--dur-1); }
.kofi-fab:focus-visible { outline: 2px solid transparent; box-shadow: 0 0 0 2px #fff, 0 0 0 4.5px oklch(0.24 0.06 262), 0 10px 24px -10px oklch(0.3 0.1 245 / .6); }
.kofi-cup { width: 24px; height: 24px; flex: none; transform-origin: 40% 80%; transition: transform var(--dur-3) var(--ease-spring); }
/* the cup and its handle take the label's colour (CSS beats the fill and stroke attributes), so they keep the label's
   contrast and stay visible in forced colours; the red heart keeps its own fill */
.kofi-cup path:first-child { fill: currentColor; }
.kofi-cup path:nth-child(2) { stroke: currentColor; }
.kofi-fab:hover .kofi-cup { transform: rotate(-10deg); }
.kofi-fab[aria-busy="true"] .kofi-cup { animation: kofiSip .7s var(--ease-in-out) infinite alternate; }
@keyframes kofiSip { to { transform: rotate(-14deg) translateY(-1px); } }
@media (scripting: none) { .kofi-fab { display: inline-flex; opacity: 1; visibility: visible; transform: none; } }
/* below 1600px just the cup, in a 46px circle, so it covers less of the page (the 145px pill reached past the left edge
   of the content pages' text until 1600px); aria-label="Support the creator on Ko-fi" still names it (from 760px the nav's Support button replaces it) */
@media (max-width: 1599px) {
  .kofi-fab { width: 46px; padding: 0; justify-content: center; }
  .kofi-fab span { position: absolute; width: 1px; height: 1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; }
}
/* every page, up to 1399px: while you read downwards the button steps away (.is-away, set by kofi.js from the
   scroll direction) and it comes back when you scroll up or reach the end of the page. An open panel keeps it */
@media (max-width: 1399px) {
  .kofi-fab.is-ready.is-away:not([aria-expanded="true"]) { opacity: 0; visibility: hidden; transform: translate3d(0, 12px, 0) scale(.94); transition-delay: 0s, 0s, var(--dur-3), 0s; }
}
/* Ko-fi's own floating button stays hidden (ours opens and closes the panel), but keeps its box so Ko-fi can size
   the panel from it; the panel opens just above our button, clear of phone safe areas */
.floatingchat-container-wrap, .floatingchat-container-wrap-mobi { visibility: hidden !important; pointer-events: none !important; left: var(--kofi-x) !important; bottom: var(--kofi-y) !important; }
.floating-chat-kofi-popup-iframe, .floating-chat-kofi-popup-iframe-mobi { left: var(--kofi-x) !important; bottom: calc(var(--kofi-y) + 58px) !important; max-width: calc(100vw - 2 * var(--kofi-x)); }
/* opened from the nav's Support button (kofi.js sets .kofi-at-nav): the panel hangs under the nav, at the right */
.kofi-at-nav .floating-chat-kofi-popup-iframe, .kofi-at-nav .floating-chat-kofi-popup-iframe-mobi { left: auto !important; right: var(--gutter) !important; top: calc(var(--nav-h) + 6px) !important; bottom: auto !important; max-height: calc(100svh - var(--nav-h) - 16px); }
/* the quiet links: one line in the download section, one in the footer */
.dl-kofi { margin-top: var(--s3); font-size: .875rem; }
.dl-kofi a { display: inline-flex; align-items: center; gap: 6px; min-height: 44px; color: var(--band-fg-2); text-decoration: none; transition: color var(--dur-2) var(--ease); }
.dl-kofi a:hover { color: var(--band-fg); text-decoration: underline; }
.dl-kofi .i { width: 16px; height: 16px; }
/* the full download page, for the winget line, the file names and the SmartScreen steps */
.dl-all { margin-top: var(--s4); font-size: .9375rem; }
.dl-all a { display: inline-flex; align-items: center; min-height: 44px; color: var(--band-fg-2); transition: color var(--dur-2) var(--ease); }
.dl-all a:hover { color: var(--band-fg); }

/* ---------- privacy page ---------- */
.doc { padding: calc(64px + clamp(48px, 8vw, 104px)) 0 clamp(80px, 10vw, 128px); }
.doc article { max-width: 68ch; }
.doc h1 { font-size: clamp(2.4rem, 1.4rem + 3.6vw, 4rem); line-height: 1.02; font-weight: 500; letter-spacing: -0.035em; }
.doc .updated { margin-top: var(--s4); color: var(--fg-2); }
.doc .summary { margin-top: var(--s10); padding: var(--s6) 28px; border-radius: var(--r-card); background: var(--night); color: var(--night-fg); font-size: 1.1875rem; line-height: 1.5; box-shadow: var(--shadow-card); }
.doc .summary strong { color: inherit; }
.doc .intro { margin-top: var(--s10); }
.doc h2 { margin-top: 56px; font-size: 1.5rem; font-weight: 500; letter-spacing: -0.02em; }
.doc p, .doc li { color: var(--fg-2); }
.doc h2 + p, .doc h2 + ul { margin-top: var(--s3); }
.doc p + p, .doc ul + p { margin-top: var(--s3); }
.doc ul { padding-left: 1.2em; margin: var(--s3) 0 0; }
.doc li + li { margin-top: 10px; }
.doc li::marker { color: var(--accent); }
.doc strong { color: var(--fg); font-weight: 600; }
.doc code { font-family: ui-monospace, "Cascadia Mono", "Cascadia Code", Consolas, "SF Mono", Menlo, monospace; font-size: .92em;
  padding: 1px 6px; border-radius: 6px; background: var(--field); color: var(--fg); overflow-wrap: anywhere; }
.doc .back { margin-top: 56px; }

/* ---------- 404: the usual bar and footer around a night sky, with a few ways back ---------- */
.lost { min-height: 100vh; min-height: 100svh; display: flex; flex-direction: column; }
.lost-main { --ring: oklch(0.86 0.09 245); flex: 1 0 auto; display: grid; place-items: center; text-align: center; padding: calc(var(--nav-h) + 48px) 0 64px;
  background: linear-gradient(180deg, oklch(0.20 0.055 266), oklch(0.33 0.08 292) 70%, oklch(0.45 0.1 330)); color: var(--band-fg); }
.lost-code { font-family: var(--display); font-weight: 150; font-size: clamp(5rem, 3rem + 10vw, 11rem); line-height: .9; letter-spacing: -0.04em; }
.lost h1 { margin: var(--s6) auto 0; max-width: 18ch; font-size: clamp(1.8rem, 1.2rem + 2vw, 2.6rem); line-height: 1.1; font-weight: 500; letter-spacing: -0.03em; }
.lost-sub { margin-top: var(--s4); color: var(--band-fg-2); }
.lost-cta { justify-content: center; margin-top: var(--s8); }
.lost .btn-primary { background: #fff; color: oklch(0.25 0.06 262); }
.lost-links { display: flex; flex-wrap: wrap; justify-content: center; gap: 0 var(--s5); margin: var(--s5) 0 0; padding: 0; list-style: none; }
.lost-links a { display: inline-flex; align-items: center; min-height: 44px; padding: 0 4px; color: var(--band-fg); font-weight: 500; }

/* ---------- motion: transform and opacity only; scroll-driven where supported; visible by default ---------- */
@keyframes rise { from { opacity: 0; transform: translateY(28px); } to { opacity: 1; transform: none; } }
@keyframes tileIn { from { opacity: 0; transform: translateY(40px) scale(.97); } to { opacity: 1; transform: none; } }
@keyframes grow { from { transform: scaleX(0); } to { transform: scaleX(1); } }
@keyframes band { from { opacity: 0; transform: scaleX(.2); } to { opacity: 1; transform: none; } }
@keyframes slideUnder { from { transform: translateY(70px); } to { transform: translateY(-78px); } }
@keyframes wipeBox { from { transform: translateX(100%); } to { transform: translateX(0); } }
@keyframes wipeImg { from { transform: translateX(-100%); } to { transform: translateX(0); } }
@keyframes enter { from { opacity: .001; transform: translateY(16px); } to { opacity: 1; transform: none; } }
@keyframes winIn { from { opacity: 0; transform: translateY(28px) scale(.985); } to { opacity: 1; transform: none; } }
@keyframes nightSlide { from { transform: translate3d(0, 0, 0); } to { transform: translate3d(-25%, 0, 0); } }
@keyframes rulerMove { from { transform: translateX(0); } to { transform: translateX(100%); } }
@keyframes wordIn { from { opacity: .14; transform: translateY(.16em); } to { opacity: 1; transform: none; } }
@keyframes drift { from { transform: translate3d(0, -6%, 0); } to { transform: translate3d(0, 6%, 0); } }
@keyframes sunset { from { transform: translate3d(0, calc(-1 * min(56vh, 540px)), 0); } to { transform: translate3d(0, -4%, 0); } }
@keyframes fadeIn { from { opacity: 0; } to { opacity: 1; } }
@keyframes tagLean { from { transform: translateX(-14px); } to { transform: translateX(calc(-100% + 14px)); } }
@keyframes cellIn { from { opacity: 0; transform: scale(.55); } to { opacity: 1; transform: none; } }
@keyframes growY { from { transform: scaleY(0); } to { transform: scaleY(1); } }
@keyframes bandOpen { from { clip-path: inset(0 max(16px, 5%) round var(--r-tile)); } to { clip-path: inset(0 0 round 0); } }
@keyframes markRise { from { transform: translate3d(0, 55%, 0); opacity: .15; } to { transform: none; opacity: 1; } }

@media (prefers-reduced-motion: no-preference) {
  /* hero entrance: the headline is painted at once (it is the largest paint), the rest arrives under it: the place,
     the buttons, then the app's window rising into place. Transform and opacity only, so nothing moves the page */
  .js .hero-where, .js .hero .cta-row, .js .share-note { animation: enter var(--dur-5) var(--ease-out) both; }
  .js .hero-where { animation-delay: 80ms; }
  .js .hero .cta-row, .js .share-note { animation-delay: 160ms; }
  .js .hero-app { animation: winIn var(--dur-6) var(--ease-out) both; animation-delay: 240ms; }

  @supports (animation-timeline: view()) {
    .reveal { animation: rise linear both; animation-timeline: view(); animation-range: entry 0% entry 60%; }
    .tile.reveal { animation-name: tileIn; }
    .t-plan { view-timeline-name: --plan; }
    /* planner: hours light up column by column, then the selected hour drops in and the overlap block settles around it */
    .t-plan .pc { animation: cellIn linear both; animation-timeline: --plan; animation-range: entry calc(20% + var(--c) * 4%) entry calc(45% + var(--c) * 4%); }
    .t-plan .psel { animation: growY linear both; animation-timeline: --plan; animation-range: entry 70% cover 42%; }
    .t-plan .pover { animation: band linear both; animation-timeline: --plan; animation-range: cover 36% cover 52%; }
    .t-pin { view-timeline-name: --pin; }
    .desk-win { animation: slideUnder linear both; animation-timeline: --pin; animation-range: entry 30% exit 40%; }
    .wipe-dark { animation: wipeBox linear both; animation-timeline: --wipe; animation-range: cover 25% cover 65%; }
    .wipe-dark img { animation: wipeImg linear both; animation-timeline: --wipe; animation-range: cover 25% cover 65%; }
    /* the scene: night and the ruler follow scroll on the compositor; JS only swaps text each quarter hour */
    .scene { view-timeline: --scene block; }
    .map-night { animation: nightSlide linear both; animation-timeline: --scene; animation-range: contain 0% contain 100%; }
    .ruler-fill { animation: grow linear both; animation-timeline: --scene; animation-range: contain 0% contain 100%; }
    .ruler-move { animation: rulerMove linear both; animation-timeline: --scene; animation-range: contain 0% contain 100%; }
    .ruler-tag { animation: tagLean linear both; animation-timeline: --scene; animation-range: contain 0% contain 100%; }
    /* privacy: the words light up one by one as the band crosses the screen; the stars drift a little slower than the page */
    .night-band { view-timeline-name: --priv; }
    .privacy-big .w { animation: wordIn linear both; animation-timeline: --priv; animation-range: cover calc(10% + var(--i) * 7%) cover calc(28% + var(--i) * 6%); }
    .band-sky::before { animation: drift linear both; animation-timeline: --priv; }
    .band-sky { animation: bandOpen linear both; animation-timeline: --priv; animation-range: entry 0% cover 42%; }
    /* the name at the foot of the page rises into view like the moon after the sunset above it */
    .footer { view-timeline-name: --foot; }
    .footer-mark span { animation: markRise linear both; animation-timeline: --foot; animation-range: entry 0% entry 100%; }
    /* dusk: sun sets, sky deepens, stars come out, all tied to the scroll */
    .download { view-timeline-name: --dusk; }
    .dusk-sun { animation: sunset linear both; animation-timeline: --dusk; animation-range: entry 15% entry 100%; }
    .dusk::before { animation: fadeIn linear both; animation-timeline: --dusk; animation-range: entry 35% entry 100%; }
    .dusk-stars { animation: fadeIn linear both; animation-timeline: --dusk; animation-range: entry 55% entry 100%; }
  }
  /* fallback: IntersectionObserver adds .in */
  .no-sda .reveal { opacity: 0; transform: translateY(28px); transition: opacity var(--dur-5) var(--ease-out), transform var(--dur-6) var(--ease-out); }
  .no-sda .reveal.in { opacity: 1; transform: none; }
  .no-sda .t-plan .pc { opacity: 0; transform: scale(.55); transition: opacity var(--dur-4) var(--ease-out), transform var(--dur-4) var(--ease-out); transition-delay: calc(250ms + var(--c) * 45ms); }
  .no-sda .t-plan .pover, .no-sda .t-plan .psel { opacity: 0; transition: opacity var(--dur-4) var(--ease-out) 900ms; }
  .no-sda .t-plan.in .pc, .no-sda .t-plan.in .pover, .no-sda .t-plan.in .psel { opacity: 1; transform: none; }
}

/* ---------- responsive ---------- */
/* scene rows: the cities under the map where it is cropped tall (phones, portrait tablets) */
.srow { position: relative; isolation: isolate; display: grid; grid-template-columns: minmax(0, 1fr) auto; align-items: center; column-gap: var(--s3); padding: 6px 14px; border-radius: 12px;
  background: var(--g-day); color: var(--day-fg); box-shadow: var(--shadow-card); }
.srow::before { content: ""; position: absolute; inset: 0; z-index: -1; border-radius: inherit; background: var(--g-night); opacity: 0; transition: opacity var(--dur-3) var(--ease); }
.srow.is-night { color: var(--night-fg); }
.srow.is-night::before { opacity: 1; }
.srow.home { box-shadow: 0 0 0 2px var(--accent), var(--shadow-card); }
.srow-city { font-family: var(--display); font-weight: 600; font-size: .9375rem; line-height: 1.25; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.srow-phase { grid-row: 2; font-size: .75rem; line-height: 1.3; opacity: .8; }
.srow-time { grid-row: 1 / 3; grid-column: 2; font-family: var(--display); font-weight: 250; font-size: 1.625rem; letter-spacing: -0.02em; font-variant-numeric: tabular-nums; }

/* small laptops and landscape tablets: the three small tiles share a row in equal thirds */
@media (max-width: 1239px) {
  .t-pin, .t-copy, .t-label { grid-column: span 4; }
  .pchip span { font-size: 1.125rem; }
}
@media (max-width: 1100px) {
  .wc-hint { display: none; }
  .wc-seg, .wc-tool:not(.pinned) { display: none; }
}
/* tablets (641 to 1100): all five clocks fit the widget instead of the fifth being cut off at its edge */
@media (min-width: 641px) and (max-width: 1100px) {
  .card { flex: 1 1 0; min-width: 0; max-width: none; min-height: 176px; }
  .time { font-size: clamp(34px, 4.6vw, 48px); letter-spacing: -0.03em; }
}
@media (min-width: 641px) and (max-width: 900px) {
  /* portrait tablets: the narrower cards keep the time and the offset, and drop what the ring and "Local" already say */
  .card { padding: var(--s3); }
  .card-head { padding-right: 14px; }
  .city { font-size: 14px; }
  .card .badge, .card .utc, .time .sec { display: none; }
  .card-more { right: 10px; }
}
/* portrait tablets: the bento reads as pairs */
@media (max-width: 999px) {
  .t-conv { grid-column: span 12; }
  .t-plan, .t-pin, .t-copy, .t-label { grid-column: span 6; }
}
/* portrait tablets: a bigger clock, and a taller crop of the map with the cities as a row of cards under it */
@media (min-width: 761px) and (max-width: 1100px) and (orientation: portrait) {
  .scene-sticky { gap: clamp(20px, 2.6vh, 32px); }
  .map { height: min(64vw, 46svh); }
  .pin-label { display: none; }
  .scene-rows { display: grid; grid-auto-flow: column; grid-auto-columns: minmax(0, 1fr); gap: var(--s3); }
  .srow { grid-template-columns: minmax(0, 1fr); padding: 12px 14px 10px; border-radius: var(--r-group); }
  .srow-phase { grid-row: auto; }
  .srow-time { grid-row: auto; grid-column: auto; margin-top: 6px; font-size: clamp(1.75rem, 1rem + 1.6vw, 2.25rem); line-height: 1; }
}
@media (max-width: 960px) {
  .faq-grid { grid-template-columns: 1fr; gap: var(--s6); }
}
@media (max-width: 900px) {
  .wc-chip { display: none; }
}
@media (max-width: 760px) {
  #wcSlider { display: none; }
  .wc-tools { display: none; }
  .t-plan, .t-pin, .t-copy, .t-label, .t-theme, .t-lang { grid-column: span 12; }
  .tile { min-height: 0; }
  .t-theme .wipe { width: 190%; }

  /* scene on phones: a taller crop of the map, centred on you, plus the cities as rows */
  .scene { height: 280vh; }
  .scene-sticky { gap: var(--s4); justify-content: safe center; padding-top: calc(var(--nav-h) + 8px); }
  .beat { font-size: clamp(1.6rem, 1rem + 3vw, 2.2rem); }
  .map { height: clamp(160px, 26svh, 260px); }
  .pin-label { display: none; }
  .scene-rows { display: grid; gap: 6px; }
}
@media (max-width: 640px) {
  /* phones: the words on the left, full-width buttons, and a tall window for the app's stacked rows */
  .hero { --frame-h: 560px; padding-top: calc(var(--nav-h) + 20px); }
  .hero-inner { gap: 28px; }
  .hero-head { align-items: stretch; text-align: left; }
  .h1-sub { margin-left: 0; }
  .app-win { border-radius: 18px; }
  .app-win-hint { display: none; }
  .wc-bar { flex-wrap: wrap; row-gap: var(--s2); padding: var(--s3) var(--s3) var(--s1); }
  .wc-conv { flex-wrap: wrap; row-gap: var(--s2); }
  /* row 1: the time and the city; row 2: the slider, with Back to now and Copy beside it, so nothing below moves when they appear */
  #wcZone { flex: 1 1 calc(100% - 170px); min-width: 0; max-width: none; }
  #wcSlider { display: block; order: 5; flex: 1 1 90px; width: auto; }
  #wcClear { order: 6; }
  #wcCopy { order: 7; }
  .wc-lbl.in { display: none; }
  .wc-strip { padding: var(--s2) var(--s3) var(--s3); gap: var(--s2); }
  .card { min-width: 172px; flex-basis: 172px; min-height: 170px; }
  .time { font-size: 44px; }
  .cta-row .btn, .dl-buttons .btn { flex: 1 1 100%; white-space: normal; }
  .mcards { gap: var(--s2); }
  .mcard { padding: 10px 10px 12px; }
  .mcard-time { font-size: 1.75rem; }
  .mcard-meta { flex-direction: column; gap: 0; }
  /* the day marker gets its own line here: keep that line while there is no marker, so the cards keep their height
     when the tile's demo types a time that changes the date (CLS 0) */
  .mcard-shift:empty::before { content: "\00a0"; }
  .pgrid { grid-template-columns: minmax(0, 5rem) 0 repeat(var(--cols), minmax(0, 1fr)); column-gap: 2px; }
  .pname { font-size: .8125rem; }
  .ptime { display: none; }
  .pc { height: 22px; font-size: .625rem; border-radius: 5px; }
  .footer .legal { margin-left: 0; }
}
@media (max-width: 374px) {
  .nav .brand span { display: none; }
}
@media (max-width: 400px) {
  .mconv { gap: 6px; }
  .mconv-field { width: 96px; padding: 0 12px; }
  .mconv-zone { padding: 0 12px; }
}
@media (max-height: 640px) and (min-width: 761px) {
  .beat { font-size: clamp(1.6rem, 1rem + 1.8vw, 2.4rem); }
}

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after { animation: none !important; transition-duration: 0ms !important; }
  .scene { height: auto; }
  .scene-sticky { position: relative; height: auto; padding: clamp(88px, 11vw, 160px) 0; }
  .beat:not(:first-child) { position: absolute !important; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); }
  .ruler, .ghost { display: none; }
  .card:hover { transform: none; }
  .caret-text::after { opacity: 0; }
}
/* touch: every control at least 44px */
@media (pointer: coarse) {
  .theme-btn { width: 44px; height: 44px; }
  .btn-sm { min-height: 44px; }
  .nav .btn-sm.nav-kofi { min-width: 44px; }
  .lang-menu > summary { min-height: 44px; }
  .nav .brand { min-height: 44px; min-width: 44px; }
  .wc { --ctl-h: 44px; }
  .wc-icon-btn { width: 44px; }
}
@media (forced-colors: active) {
  .card, .wc, .map, .tile, .mcard, .srow { border: 1px solid CanvasText; }
  .btn, .kofi-fab { border: 1px solid ButtonText; }
  .nav-menu > ul, .lang-menu > ul, .lang-hint { border: 1px solid CanvasText; }
  .nav-menu a[aria-current="page"], .lang-menu a[aria-current] { outline: 1px solid CanvasText; outline-offset: -1px; }
  /* the converter's fields and slider are drawn with background colours, which forced colours remove: outline the
     fields (an outline, not a border, so the time field keeps the width its placeholder needs) and let the slider
     fall back to the system's own. Their focus rings are box-shadows, which forced colours remove too: draw them
     as outlines, and the cards' as well */
  .wc-field { outline: 1px solid ButtonText; outline-offset: -1px; }
  .wc-field:focus-visible, .card:focus-visible, #wcSlider:focus-visible { outline: 2px solid Highlight; outline-offset: 2px; }
  #wcSlider { -webkit-appearance: auto; appearance: auto; }
}

/* ---------- print: the words and the product, in ink on paper ---------- */
@media print {
  @page { margin: 16mm; }
  :root, :root[data-theme="dark"] { --canvas: #fff; --canvas-2: #fff; --fg: #111; --fg-2: #444; --fg-3: #555; --hair-strong: #ccc; --band-fg: #111; --band-fg-2: #444; color-scheme: light; }
  *, *::before, *::after { animation: none !important; transition: none !important; box-shadow: none !important; text-shadow: none !important; }
  html, body { background: #fff !important; color: #111 !important; }
  .nav, .skip, .ghost, .sun, .hero-app, .ruler, .scene-rows, .band-sky, .dusk, .footer-mark, .cta-row, .dl-buttons, .wc-tools, .tile-glow, .gpu-warm, #announce, .kofi-fab, .dl-kofi, .lang-hint, .footer-langs, [id^="kofi-widget-overlay"] { display: none !important; }
  .hero { --hero-fg: #111; --hero-fg-2: #444; min-height: 0; padding: 0 0 12mm; background: none !important; }
  .section, .compare, .download .inner { padding-block: 10mm; }
  .scene { height: auto; } .scene-sticky { position: static; height: auto; padding: 0; }
  .beats { display: block; } .beat { opacity: 1 !important; transform: none !important; margin-bottom: 4mm; }
  .no-sda .reveal { opacity: 1; transform: none; }
  .night-band, .download, .footer, .night-tile { background: none !important; color: #111; }
  .tile, .wc, .map, .card, .mcard { break-inside: avoid; border: 1px solid #ccc; }
  .card, .mcard, .mlabel.card { --c-fg: #111; --c-fg-2: #444; color: #111; }
  .pchip, .desk-widget { background: none; color: #111; }
  .mcopy-paper span { opacity: 1; transform: none; }
  .privacy-big { font-size: 40pt; }
  details::details-content { block-size: auto; content-visibility: visible; }
  summary .i { display: none; }
}
