/* =============================================================
   HealthOrbis, coming soon
   Design tokens, colours, type and spacing are taken verbatim
   from the Figma file "Healthorbis (Copy)" →
   page "🚀 Coming/Launching soon Screen ✅".
   ============================================================= */

/* ---------- 1. Palette (Figma colour variables) ---------- */
:root {
  --indigo-100: #DBD9F5;
  --indigo-200: #B7B2EB;
  --indigo-300: #948CE1;
  --indigo-500: #4C3FCD;
  --indigo-600: #3D30B9;
  --indigo-700: #34299E;
  --indigo-1000: #19144B;

  --amethyst-900: #120E31;
  --amethyst-1000: #0D0A22;

  --sky-200: #B4E6F3;
  --sky-300: #8FD9ED;
  --sky-700: #1E97B7;
  --sky-800: #197C97;

  --flame-300: #F7A383;
  --flame-800: #A6350A;

  --brand-mark: #4B3FCD;
  --white: #FFFFFF;

  /* Type */
  --font-display: "Sora", "Segoe UI Variable Static Display", "Segoe UI", system-ui, sans-serif;
  --font-ui: "Segoe UI Variable Static Display", "Segoe UI Variable Display",
             "Segoe UI", "Inter", system-ui, -apple-system, "Helvetica Neue", Arial, sans-serif;

  /* Fluid scale, from the 393px mobile artboard to the 1440px desktop one */
  --pad: clamp(1.5rem, 0.188rem + 5.35vw, 5rem);          /* 24 → 80 */
  --fs-display: clamp(2rem, 1.25rem + 3.06vw, 4rem);      /* 32 → 64 */
  --fs-body: clamp(0.875rem, 0.781rem + 0.38vw, 1.125rem);/* 14 → 18 */
  --fs-stat: clamp(0.875rem, 0.828rem + 0.19vw, 1rem);    /* 14 → 16 */
  --fs-logo: clamp(1.344rem, 1.055rem + 1.18vw, 1.825rem);/* 21.5 → 29.2 */
  --header-top: clamp(1.688rem, 1.383rem + 1.24vw, 2.5rem); /* 27 → 40 */

  /* Elevation */
  --shadow-cta: 0 10px 15.5px 5px rgba(102, 36, 241, 0.15);
}

/* ---------- 2. Theme: dark (default in the Figma file) ---------- */
:root {
  color-scheme: dark;

  --bg: #010003;
  --pattern-color: var(--brand-mark);
  --pattern-opacity: 0.05;
  --pattern-blend: plus-lighter;

  --logo-fg: var(--white);
  --nav-fg: var(--white);

  --eyebrow-bg: rgba(255, 255, 255, 0.10);
  --eyebrow-border: rgba(255, 255, 255, 0.10);
  --eyebrow-fg: var(--indigo-100);
  --eyebrow-icon: var(--indigo-100);

  --display-fg: var(--indigo-300);
  --body-fg: var(--indigo-100);
  --label-fg: var(--white);

  --field-bg: #1A1A1A;
  --field-border: rgba(255, 255, 255, 0.10);
  --field-fg: var(--white);
  --field-placeholder: rgba(255, 255, 255, 0.50);

  --stat-fg: var(--indigo-100);
  --stat-divider: rgba(219, 217, 245, 0.50);
  --icon-verified: var(--sky-200);
  --icon-hospital: var(--sky-300);
  --icon-capsule: var(--flame-300);

  --footer-fg: rgba(219, 217, 245, 0.40);
  --footer-border: rgba(255, 255, 255, 0.05);

  --focus-ring: var(--indigo-300);
  --error-fg: #F5A9B0;
  --success-fg: #89F3D1;

  --snackbar-bg: #14122B;
  --snackbar-fg: var(--indigo-100);
  --snackbar-border: rgba(255, 255, 255, 0.10);

  --signal: #C9C3FF;
  --signal-strong: #FFFFFF;
  --dim-node: 0.35;
  --dim-base: 0.45;
}

/* ---------- 3. Theme: light ---------- */
:root[data-theme="light"] {
  color-scheme: light;

  --bg: var(--indigo-100);
  --pattern-opacity: 0.02;

  --logo-fg: var(--amethyst-900);
  --nav-fg: var(--amethyst-900);

  --eyebrow-bg: var(--indigo-200);
  --eyebrow-border: rgba(255, 255, 255, 0.10);
  --eyebrow-fg: var(--indigo-600);
  --eyebrow-icon: var(--indigo-600);

  --display-fg: var(--indigo-700);
  --body-fg: var(--amethyst-1000);
  --label-fg: var(--indigo-1000);

  --field-bg: #FAFAFA;
  --field-border: #EEEEEE;
  --field-fg: #1A1A1A;
  --field-placeholder: #606060;

  --stat-fg: var(--amethyst-900);
  --stat-divider: var(--amethyst-1000);
  --icon-verified: var(--sky-800);
  --icon-hospital: var(--sky-700);
  --icon-capsule: var(--flame-800);

  /* The Figma light board reuses the dark footer token, which is invisible on
     the light canvas. Same 40 % treatment, applied to the light ink instead. */
  --footer-fg: rgba(13, 10, 34, 0.45);
  --footer-border: rgba(13, 10, 34, 0.08);

  --focus-ring: var(--indigo-600);
  --error-fg: #A91421;
  --success-fg: #0D7E59;

  --snackbar-bg: #FFFFFF;
  --snackbar-fg: #0D0A22;
  --snackbar-border: rgba(13, 10, 34, 0.12);

  --signal: #5F51CD;
  --signal-strong: #2B2282;
  --dim-node: 0.5;
  --dim-base: 0.55;
}

@media (prefers-color-scheme: light) {
  :root:not([data-theme="dark"]) {
    color-scheme: light;

    --bg: var(--indigo-100);
    --pattern-opacity: 0.02;

    --logo-fg: var(--amethyst-900);
    --nav-fg: var(--amethyst-900);

    --eyebrow-bg: var(--indigo-200);
    --eyebrow-border: rgba(255, 255, 255, 0.10);
    --eyebrow-fg: var(--indigo-600);
    --eyebrow-icon: var(--indigo-600);

    --display-fg: var(--indigo-700);
    --body-fg: var(--amethyst-1000);
    --label-fg: var(--indigo-1000);

    --field-bg: #FAFAFA;
    --field-border: #EEEEEE;
    --field-fg: #1A1A1A;
    --field-placeholder: #606060;

    --stat-fg: var(--amethyst-900);
    --stat-divider: var(--amethyst-1000);
    --icon-verified: var(--sky-800);
    --icon-hospital: var(--sky-700);
    --icon-capsule: var(--flame-800);

    --footer-fg: rgba(13, 10, 34, 0.45);
    --footer-border: rgba(13, 10, 34, 0.08);

    --focus-ring: var(--indigo-600);
    --error-fg: #A91421;
    --success-fg: #0D7E59;

    --snackbar-bg: #FFFFFF;
    --snackbar-fg: #0D0A22;
    --snackbar-border: rgba(13, 10, 34, 0.12);

    --signal: #5F51CD;
    --signal-strong: #2B2282;
    --dim-node: 0.5;
    --dim-base: 0.55;
  }
}

/* ---------- 4. Reset ---------- */
*, *::before, *::after { box-sizing: border-box; }

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

body {
  margin: 0;
  background: var(--bg);
  color: var(--body-fg);
  font-family: var(--font-ui);
  font-size: var(--fs-body);
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

img, svg { display: block; max-width: 100%; }
button { font: inherit; color: inherit; }

:where(a, button, input):focus-visible {
  outline: 2px solid var(--focus-ring);
  outline-offset: 3px;
  border-radius: 6px;
}

.sr-only {
  position: absolute;
  width: 1px; height: 1px;
  padding: 0; margin: -1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
  border: 0;
}

/* ---------- 5. Page shell + background pattern ---------- */
.page {
  position: relative;
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  padding: 0 var(--pad) clamp(2rem, 1.2rem + 3.3vw, 3.5rem);
  max-width: 1440px;
  margin-inline: auto;
  overflow-x: clip;
  isolation: isolate;
}

/* Safari < 16 has no `overflow: clip`. */
@supports not (overflow: clip) {
  .page { overflow-x: hidden; }
}

.page-pattern {
  position: fixed;
  inset: 0;
  z-index: -1;
  pointer-events: none;
  background-color: var(--pattern-color);
  opacity: var(--pattern-opacity);
  mix-blend-mode: var(--pattern-blend);
  -webkit-mask-image: url("../img/pattern-tile.png");
  mask-image: url("../img/pattern-tile.png");
  -webkit-mask-repeat: repeat;
  mask-repeat: repeat;
  -webkit-mask-size: 85px 171px;
  mask-size: 85px 171px;
}

@media (min-width: 768px) {
  .page-pattern { -webkit-mask-size: 171px 341px; mask-size: 171px 341px; }
}

/* ---------- 6. Header ---------- */
.site-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding-block: var(--header-top) 0;
}

.logo {
  display: inline-flex;
  align-items: center;
  gap: 0.284em;
  font-family: "Inter", var(--font-ui);
  font-weight: 700;
  font-size: var(--fs-logo);
  line-height: 1.21;
  letter-spacing: -0.005em;
  color: var(--logo-fg);
  text-decoration: none;
}

.logo__mark { width: 1.109em; height: 1.121em; flex: none; }
.logo__mark path { fill: var(--brand-mark); }

.header-actions {
  display: flex;
  align-items: center;
  gap: clamp(0.75rem, 0.6rem + 0.6vw, 1rem);
}

/* Header waitlist pill (desktop) */
.cta-pill {
  display: none;
  align-items: center;
  gap: 16px;
  height: 48px;
  padding-inline: 20px;
  border: 1px solid rgba(255, 255, 255, 0.20);
  border-radius: 24px;
  background:
    linear-gradient(180deg, rgba(255, 255, 255, 0.20), rgba(0, 0, 0, 0.20)),
    var(--indigo-500);
  box-shadow: var(--shadow-cta);
  color: var(--white);
  font-size: 14px;
  font-weight: 600;
  line-height: 21px;
  text-decoration: none;
  white-space: nowrap;
  cursor: pointer;
  transition: transform 0.18s ease, box-shadow 0.18s ease, filter 0.18s ease;
}

.cta-pill:hover { filter: brightness(1.08); box-shadow: 0 12px 20px 5px rgba(102, 36, 241, 0.22); }
.cta-pill:active { transform: translateY(1px); }

@media (min-width: 768px) { .cta-pill { display: inline-flex; } }

.avatar-stack { display: flex; align-items: center; flex: none; }
.avatar-stack img {
  width: 20px; height: 20px;
  border-radius: 50%;
  border: 1px solid var(--white);
  object-fit: cover;
  background: #D9D9D9;
}
.avatar-stack img + img { margin-left: -4px; }

/* Menu button (mobile) */
.menu-button {
  display: inline-flex;
  flex-direction: column;
  justify-content: center;
  gap: 5px;
  width: 32px;
  height: 24px;
  padding: 0;
  border: 0;
  background: none;
  cursor: pointer;
}
.menu-button span {
  display: block;
  height: 1px;
  width: 32px;
  background: var(--nav-fg);
}
@media (min-width: 768px) { .menu-button { display: none; } }

/* Theme switch */
.theme-toggle {
  display: inline-grid;
  place-items: center;
  width: 40px; height: 40px;
  flex: none;
  border: 1px solid var(--eyebrow-border);
  border-radius: 50%;
  background: var(--eyebrow-bg);
  color: var(--eyebrow-fg);
  cursor: pointer;
  transition: background 0.18s ease, color 0.18s ease;
}
.theme-toggle:hover { color: var(--display-fg); }
.theme-toggle svg { width: 20px; height: 20px; }
.theme-toggle .icon-sun { display: none; }
:root[data-theme="light"] .theme-toggle .icon-sun { display: block; }
:root[data-theme="light"] .theme-toggle .icon-moon { display: none; }
@media (prefers-color-scheme: light) {
  :root:not([data-theme="dark"]) .theme-toggle .icon-sun { display: block; }
  :root:not([data-theme="dark"]) .theme-toggle .icon-moon { display: none; }
}

/* ---------- 7. Main ---------- */
.main {
  flex: 1;
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: clamp(2.5rem, 1.6rem + 3.7vw, 4.5rem);
  padding-block: clamp(2.5rem, 1.5rem + 4.2vw, 4.5rem);
}

.hero {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: clamp(2.5rem, 2rem + 2vw, 3.5rem);
}

@media (min-width: 1080px) {
  .hero {
    /* 1.136 keeps the 588 / 725 split of the 1440 artboard at full width. */
    grid-template-columns: minmax(0, 1fr) minmax(0, 1.136fr);
    gap: 24px;
    align-items: center;
  }
}

/* Hero copy */
.hero__copy {
  display: flex;
  flex-direction: column;
  gap: 40px;
  max-width: 588px;
}

.hero__intro { display: flex; flex-direction: column; gap: 24px; align-items: flex-start; }

.eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 5px 8px;
  border: 1px solid var(--eyebrow-border);
  border-radius: 100px;
  background: var(--eyebrow-bg);
  color: var(--eyebrow-fg);
  font-size: 14px;
  line-height: 1.5;
}
.eyebrow svg { width: 20px; height: 20px; flex: none; color: var(--eyebrow-icon); }

.hero__title {
  margin: 0;
  font-family: var(--font-display);
  font-weight: 800;
  font-size: var(--fs-display);
  line-height: 1;
  letter-spacing: -0.01em;
  color: var(--display-fg);
}
@media (min-width: 1024px) { .hero__title { max-width: 599px; } }

.hero__lede { margin: 0; color: var(--body-fg); }

/* Waitlist form */
.waitlist { display: flex; flex-direction: column; gap: 24px; }

.waitlist__label {
  font-size: 14px;
  line-height: 1.6;
  color: var(--label-fg);
}

.waitlist__form { display: flex; flex-direction: column; gap: 24px; }

.field {
  display: flex;
  align-items: center;
  gap: 8px;
  min-height: 56px;
  padding: 3px 3px 3px 17px;
  border: 1px solid var(--field-border);
  border-radius: 1000px;
  background: var(--field-bg);
  transition: border-color 0.18s ease;
}
.field:focus-within { border-color: var(--focus-ring); }

.field input {
  flex: 1 1 auto;
  min-width: 0;
  padding: 10px 0;
  border: 0;
  background: none;
  color: var(--field-fg);
  font-family: inherit;
  font-size: 16px;
  line-height: 1.6;
}
.field input::placeholder { color: var(--field-placeholder); opacity: 1; }
.field input:focus { outline: none; }

.button {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  height: 48px;
  padding-inline: 16px;
  border: 1px solid rgba(255, 255, 255, 0.20);
  border-radius: 24px;
  background:
    linear-gradient(180deg, rgba(255, 255, 255, 0.20), rgba(0, 0, 0, 0.20)),
    var(--indigo-500);
  box-shadow: var(--shadow-cta);
  color: var(--white);
  font-size: 14px;
  font-weight: 600;
  line-height: 21px;
  white-space: nowrap;
  cursor: pointer;
  transition: transform 0.18s ease, box-shadow 0.18s ease, filter 0.18s ease;
}
.button:hover { filter: brightness(1.08); box-shadow: 0 12px 20px 5px rgba(102, 36, 241, 0.22); }
.button:active { transform: translateY(1px); }
.button[disabled] { opacity: 0.65; cursor: progress; }

/* Mobile: button sits under the field, full width (per the 393px artboard). */
.waitlist__form .button { width: 100%; }
.field .button { display: none; }

@media (min-width: 560px) {
  .waitlist { max-width: 405px; }   /* width of the field group on the 1440 artboard */
  .waitlist__form > .button { display: none; }
  .field .button { display: inline-flex; width: auto; flex: none; }
}

.form-message {
  margin: 0;
  font-size: 14px;
  line-height: 1.5;
  min-height: 0;
}
.form-message[data-state="error"] { color: var(--error-fg); }
.form-message[data-state="success"] { color: var(--success-fg); }
.form-message:empty { display: none; }

/* ---------- 7a. Entrance ---------- */
/* Gated on [data-anim="on"], which the head script sets before first paint and
   only when scripting is on. Without it these rules never apply, so a failed or
   blocked script leaves the page fully visible rather than blank. */
@keyframes reveal-in {
  from { opacity: 0; transform: translateY(18px); }
  to   { opacity: 1; transform: none; }
}

[data-anim="on"] .reveal {
  animation: reveal-in 720ms cubic-bezier(0.22, 0.8, 0.24, 1) both;
  animation-delay: var(--reveal-delay, 0ms);
}

/* The map carries its own continuous motion, so it only fades in; sliding it as
   well reads as two competing animations. */
[data-anim="on"] .hero__visual.reveal {
  animation-name: reveal-fade;
  animation-duration: 900ms;
}

@keyframes reveal-fade {
  from { opacity: 0; }
  to   { opacity: 1; }
}

/* Reduced motion keeps the staged arrival but drops the travel, which is the
   part that causes trouble. */
@media (prefers-reduced-motion: reduce) {
  [data-anim="on"] .reveal {
    animation-name: reveal-fade;
    animation-duration: 240ms;
    animation-timing-function: linear;
  }
}

/* ---------- 7b. Snackbar ---------- */
/* Submission outcomes surface here rather than as text appearing under the
   field. Field-level validation stays inline, next to the input it refers to. */
.snackbar {
  position: fixed;
  z-index: 60;
  left: 50%;
  bottom: max(24px, env(safe-area-inset-bottom, 0px) + 16px);
  display: flex;
  align-items: flex-start;
  gap: 12px;
  width: calc(100% - 32px);
  max-width: 420px;
  padding: 14px 14px 14px 16px;
  border: 1px solid var(--snackbar-border);
  border-radius: 12px;
  background: var(--snackbar-bg);
  color: var(--snackbar-fg);
  box-shadow: 0 12px 32px rgba(0, 0, 0, 0.28);
  font-size: 14px;
  line-height: 1.45;

  /* Closed state. Kept out of the a11y tree and off the pointer until opened. */
  visibility: hidden;
  opacity: 0;
  transform: translate(-50%, 12px);
  transition: opacity 220ms ease, transform 220ms ease, visibility 0s linear 220ms;
}

.snackbar[data-open="true"] {
  visibility: visible;
  opacity: 1;
  transform: translate(-50%, 0);
  transition: opacity 220ms ease, transform 220ms cubic-bezier(0.2, 0.8, 0.2, 1), visibility 0s;
}

.snackbar__text { flex: 1; min-width: 0; }

/* The status dot carries the meaning for anyone not reading the wording. */
.snackbar__icon {
  flex: none;
  width: 8px;
  height: 8px;
  margin-top: 7px;
  border-radius: 50%;
  background: currentColor;
}
.snackbar[data-state="success"] .snackbar__icon { color: var(--success-fg); }
.snackbar[data-state="error"] .snackbar__icon { color: var(--error-fg); }

.snackbar__close {
  flex: none;
  display: grid;
  place-items: center;
  width: 24px;
  height: 24px;
  margin: -2px -2px 0 0;
  padding: 0;
  border: 0;
  border-radius: 6px;
  background: none;
  color: inherit;
  opacity: 0.6;
  cursor: pointer;
}
.snackbar__close svg { width: 14px; height: 14px; }
.snackbar__close:hover { opacity: 1; }
.snackbar__close:focus-visible { outline: 2px solid currentColor; outline-offset: 2px; opacity: 1; }

@media (prefers-reduced-motion: reduce) {
  .snackbar { transition: opacity 120ms linear, visibility 0s linear 120ms; transform: translate(-50%, 0); }
  .snackbar[data-open="true"] { transition: opacity 120ms linear, visibility 0s; }
}

/* ---------- 8. Illustration ---------- */
.hero__visual {
  /* Matches the 393px artboard, where the map is 433px wide on a 393px frame. */
  --visual-w: min(calc(100% + var(--pad) * 2 + 40px), 640px);
  width: var(--visual-w);
  margin-inline: calc((100% - var(--visual-w)) / 2);
  align-self: center;
}
.hero__visual .globe { width: 100%; height: auto; }

@media (min-width: 1080px) {
  .hero__visual {
    --visual-w: calc(100% + min(56px, 3.9vw));
    width: var(--visual-w);
    margin-inline: 0 min(-56px, -3.9vw);
    justify-self: end;
  }
  .hero__visual .globe { max-width: 725px; margin-left: auto; }
}

/* ---------- 9. Stats ---------- */
.stats {
  display: flex;
  flex-direction: column;
  gap: 24px;
  margin: 0;
  padding: 0;
  list-style: none;
  color: var(--stat-fg);
  font-size: var(--fs-stat);
  line-height: 1.5;
}

.stats li { display: flex; align-items: center; gap: 9px; }
.stats svg { width: 24px; height: 24px; flex: none; }
.stats li:nth-child(1) svg { color: var(--icon-verified); }
.stats li:nth-child(2) svg { color: var(--icon-hospital); }
.stats li:nth-child(3) svg { color: var(--icon-capsule); }

/* The label keeps the figures readable as the market being built for, rather
   than as traction the product already has. Muted via opacity so it follows
   --stat-fg in both themes. */
.stats-block { display: flex; flex-direction: column; gap: 12px; }

.stats__label {
  margin: 0;
  font-size: var(--fs-stat);
  font-weight: 400;
  line-height: 1.5;
  color: var(--stat-fg);
  opacity: 0.65;
}

@media (min-width: 900px) {
  .stats { flex-direction: row; align-items: center; flex-wrap: wrap; }
  .stats li + li { padding-left: 24px; border-left: 1px solid var(--stat-divider); }
}

/* ---------- 10. Footer ---------- */
.site-footer {
  display: flex;
  flex-direction: column;
  gap: 24px;
  padding-top: 8px;
  border-top: 1px solid var(--footer-border);
  color: var(--footer-fg);
  font-size: 12px;
  line-height: 1;
}
.site-footer p { margin: 0; }

@media (min-width: 768px) {
  .site-footer { flex-direction: row; align-items: center; justify-content: space-between; }
}

/* =============================================================
   The live map
   Every path here is the Figma geometry; only motion is added.
   ============================================================= */

.globe {
  --parallax-x: 0;
  --parallax-y: 0;
}

.globe__base,
.globe__arcs,
.globe__nodes,
.globe__dots {
  transition: opacity 0.45s ease;
}

/* Parallax: the map drifts one way, the people drift the other. */
.globe__base  { transform: translate(calc(var(--parallax-x) * 5px),  calc(var(--parallax-y) * 5px)); }
.globe__arcs,
.globe__dots  { transform: translate(calc(var(--parallax-x) * -3px), calc(var(--parallax-y) * -3px)); }
.globe__nodes { transform: translate(calc(var(--parallax-x) * -9px), calc(var(--parallax-y) * -9px)); }

.globe__base,
.globe__arcs,
.globe__dots,
.globe__nodes { transition: transform 0.5s cubic-bezier(0.22, 1, 0.36, 1), opacity 0.45s ease; }

/* ---- Travelling signals along the real arc geometry ---- */
.globe__signal {
  stroke: var(--signal);
  stroke-linecap: round;
  stroke-dasharray: 6 94;
  opacity: 0.85;
  animation: globe-signal linear infinite;
  /* Each arc runs at its own pace, so the network never looks metronomic. */
  animation-duration: calc(7s + var(--i, 0) * 0.55s);
  animation-delay: calc(var(--i, 0) * -1.35s);
}

@keyframes globe-signal {
  from { stroke-dashoffset: 100; }
  to   { stroke-dashoffset: 0; }
}

/* ---- Junction dots ---- */
.globe__ripple {
  fill: none;
  stroke: var(--signal);
  stroke-width: 1;
  opacity: 0;
  transform-origin: calc(var(--cx) * 1px) calc(var(--cy) * 1px);
  animation: globe-ripple 4.5s ease-out infinite;
  animation-delay: calc(var(--i, 0) * -0.9s);
}

@keyframes globe-ripple {
  0%        { transform: scale(0.6); opacity: 0; }
  15%       { opacity: 0.55; }
  70%, 100% { transform: scale(3.4); opacity: 0; }
}

.globe__dot {
  animation: globe-dot 4.5s ease-in-out infinite;
  animation-delay: calc(var(--i, 0) * -0.9s);
}

@keyframes globe-dot {
  0%, 100% { transform: scale(1); }
  15%      { transform: scale(1.45); }
}

/* ---- The people ---- */
.globe__node {
  cursor: pointer;
  transition: transform 0.45s cubic-bezier(0.22, 1, 0.36, 1), opacity 0.35s ease;
}
.globe__node:focus { outline: none; }
.globe__node:focus-visible { outline: 2px solid var(--focus-ring); outline-offset: 2px; }

.globe__float {
  animation: globe-float 8s ease-in-out infinite;
  animation-delay: calc(var(--i, 0) * -1.1s);
}

@keyframes globe-float {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-4px); }
}

.globe__ring,
.globe__label,
.globe__avatar { transition: filter 0.35s ease, opacity 0.35s ease; }

/* The static line steps back so the signal riding on it reads clearly. */
.globe__arc { transition: opacity 0.35s ease; }
.globe.is-engaged .globe__arc { opacity: var(--dim-base); }

/* Hover, keyboard focus and tap all reach the same state. */
.globe__node:hover,
.globe__node:focus-visible,
.globe__node.is-active { transform: scale(1.08); }

.globe__node:hover .globe__ring,
.globe__node:focus-visible .globe__ring,
.globe__node.is-active .globe__ring {
  filter: drop-shadow(0 0 7px var(--node-color));
}

.globe__node:hover .globe__label,
.globe__node:focus-visible .globe__label,
.globe__node.is-active .globe__label {
  filter: drop-shadow(0 3px 6px rgba(0, 0, 0, 0.45));
}

.globe__node:focus-visible .globe__ring { stroke: var(--signal-strong); }

.globe__node:hover .globe__avatar,
.globe__node:focus-visible .globe__avatar,
.globe__node.is-active .globe__avatar { filter: saturate(1.12); }

/* One node in focus: everything else steps back, the network speeds up. */
.globe.is-engaged .globe__base  { opacity: var(--dim-base); }
.globe.is-engaged .globe__node:not(:hover):not(:focus-visible):not(.is-active) { opacity: var(--dim-node); }
.globe.is-engaged .globe__signal {
  opacity: 1;
  stroke: var(--signal-strong);
  animation-duration: calc(2.6s + var(--i, 0) * 0.18s);
}

/* Off-screen or backgrounded: stop burning frames. */
.globe.is-idle .globe__signal,
.globe.is-idle .globe__ripple,
.globe.is-idle .globe__dot,
.globe.is-idle .globe__float { animation-play-state: paused; }

/* Reduced motion falls all the way back to the static Figma artwork.
   Hover, focus and tap highlighting still work. */
@media (prefers-reduced-motion: reduce) {
  .globe__ripple,
  .globe__dot,
  .globe__float { animation: none; }
  .globe__signal { display: none; }
  .globe__ripple { opacity: 0; }
  .globe__base,
  .globe__arcs,
  .globe__dots,
  .globe__nodes { transform: none; }
}

/* ---------- 11. Motion ---------- */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.001ms !important;
    transition-duration: 0.001ms !important;
  }
}
