/* ==========================================================================
   Kidzy — direction 2: "Soft Systems"

   A deliberate opposite to direction 1. Where that one was white ground, 2px
   navy outlines and hard offset shadows, this is a pale mint ground, no
   outlines at all, and depth built from layered soft shadows, blurred aurora
   light and glass. Futurist but warm: nothing here has a sharp corner.

   Colour comes from the Kidzy logo. The raw logo colours are too light to
   carry text on a pale ground (1.9–3.3:1), so each one has a darkened ink
   variant for type; the raw values are used only as fills, glows and shapes.
   ========================================================================== */

/* --- Tokens ------------------------------------------------------------- */
:root {
  /* Ground and ink */
  /* Deep enough that a white card actually reads as a card: 1.15:1 against
     #FFF, where the old #F4F9F8 gave only 1.06 — near enough to nothing. */
  --ground:   #E9F1F0;
  --surface:  #FFFFFF;
  --ink:      #10323D;   /* 12.8:1 on ground */
  --ink-2:    #3D5A63;   /* 6.95:1 — secondary copy */
  --ink-3:    #6B858D;   /* labels only, never body text */

  /* Logo colours — fills, glows and shapes */
  --lime:     #8CC63F;
  --tangerine:#F5821F;
  --lagoon:   #0FAFC0;
  --ember:    #F4511E;

  /* Text-safe variants of the same hues, all ≥4.5:1 on the ground */
  --lime-ink: #4E7C1E;
  --tang-ink: #A85009;
  --lagoon-ink:#0A6F7C;
  --ember-ink:#C13A12;

  /* Washes */
  --lime-wash:    #EEF7E2;
  --tang-wash:    #FEF0E3;
  --lagoon-wash:  #E2F6F9;
  --ember-wash:   #FDEBE5;

  /* Depth. Two-part shadows: a tight contact shadow plus a wide soft one. */
  --sh-1: 0 1px 2px rgba(16,50,61,.07), 0 8px 20px -8px rgba(16,50,61,.18);
  --sh-2: 0 2px 4px rgba(16,50,61,.05), 0 20px 44px -20px rgba(16,50,61,.24);
  --sh-3: 0 4px 8px rgba(16,50,61,.06), 0 40px 80px -32px rgba(16,50,61,.30);

  --r-xs: 12px;
  --r-sm: 18px;
  --r:    26px;
  --r-lg: 36px;
  --r-xl: 52px;

  /* Sora is geometric and a little futurist; Lexend was designed to improve
     reading proficiency, which is the right signal for a page parents read. */
  --font-display: Sora, "Segoe UI", system-ui, sans-serif;
  --font-body:    Lexend, "Segoe UI", system-ui, -apple-system, sans-serif;

  --wrap: 1200px;
  --gut: 24px;
  --rail-gap: 20px;
  --rail-overhang: 44.5px;

  /* Shared icon glyphs, used by the habit steps and the hero glass badges. */
  --icon-plate: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 48 48' fill='none'%3E%3Ccircle cx='15' cy='14' r='5' fill='%23F5821F'/%3E%3Ccircle cx='26' cy='10' r='4' fill='%238CC63F'/%3E%3Ccircle cx='35' cy='14.5' r='4.5' fill='%23F4511E'/%3E%3Cpath d='M5 23h38a19 19 0 0 1-38 0Z' fill='%230FAFC0'/%3E%3C/svg%3E");
  --icon-ball: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 48 48' fill='none'%3E%3Ccircle cx='24' cy='24' r='17' fill='%230FAFC0'/%3E%3Cpath d='M10 15c10 4 18 12 22 25M38 15c-10 4-18 12-22 25' stroke='%23fff' stroke-width='2.6' stroke-linecap='round'/%3E%3C/svg%3E");  ;
  --icon-moon: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 48 48' fill='none'%3E%3Cpath d='M37 28A16 16 0 0 1 20 11a16 16 0 1 0 17 17Z' fill='%230FAFC0'/%3E%3Cpath d='M34 8l1.5 3.6L39 13l-3.5 1.4L34 18l-1.5-3.6L29 13l3.5-1.4Z' fill='%23F5821F'/%3E%3C/svg%3E");  ;
  --icon-check: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23000' stroke-width='2.6' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M6 12.4l4 3.9L18 8'/%3E%3C/svg%3E");
  --icon-heart: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 48 48' fill='none'%3E%3Cpath d='M24 40S6 28 6 17.5A9.6 9.6 0 0 1 24 12a9.6 9.6 0 0 1 18 5.5C42 28 24 40 24 40Z' fill='%23F4511E'/%3E%3C/svg%3E");  /* half an icon and a hair, to match the old 8% at four steps */

  --arrow: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23000' stroke-width='2.2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M5 12h13M13 6l6 6-6 6'/%3E%3C/svg%3E");
}

/* --- Reset -------------------------------------------------------------- */
*, *::before, *::after { box-sizing: border-box; }
html { -webkit-text-size-adjust: 100%; scroll-behavior: smooth; }

body {
  margin: 0;
  background: var(--ground);
  color: var(--ink);
  font-family: var(--font-body);
  font-size: 18px;
  font-weight: 350;
  line-height: 1.68;
  letter-spacing: -.005em;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

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

h1, h2, h3, h4 {
  font-family: var(--font-display);
  font-weight: 600;
  line-height: 1.08;
  letter-spacing: -.03em;
  margin: 0 0 .5em;
  text-wrap: balance;
}
h1 { font-size: clamp(2.5rem, 5.6vw, 4.4rem); font-weight: 700; }
h2 { font-size: clamp(2rem, 3.9vw, 3rem); }
h3 { font-size: clamp(1.2rem, 1.9vw, 1.45rem); }
p  { margin: 0 0 1.15em; }
p:last-child { margin-bottom: 0; }

.wrap { width: 100%; max-width: var(--wrap); margin-inline: auto; padding-inline: var(--gut); }
.wrap--narrow { max-width: 820px; }  /* was an inline max-width on the contact form wrap */
.lede { font-size: 1.14rem; color: var(--ink-2); max-width: 60ch; }
.muted { color: var(--ink-2); }
.center { text-align: center; }
.center .lede { margin-inline: auto; }

.vh {
  position: absolute !important; width: 1px; height: 1px;
  padding: 0; margin: -1px; overflow: hidden;
  clip-path: inset(50%); white-space: nowrap; border: 0;
}

.skip {
  position: absolute; left: -9999px; top: 0; z-index: 200;
  background: var(--ink); color: #fff; padding: 14px 22px; border-radius: 0 0 var(--r-sm) 0;
}
.skip:focus { left: 0; }

:where(a, button, input, select, textarea, [tabindex]):focus-visible {
  outline: 3px solid var(--lagoon-ink);
  outline-offset: 3px;
  border-radius: 6px;
}

/* --- Grain ---------------------------------------------------------------
   A whisper of noise over the whole page. Flat gradients on large areas band
   on 8-bit displays; this hides it and adds a little tooth. */
body::after {
  content: "";
  position: fixed; inset: 0; z-index: 999;
  pointer-events: none; opacity: .028;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='160' height='160'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='.85' numOctaves='3'/%3E%3C/filter%3E%3Crect width='160' height='160' filter='url(%23n)'/%3E%3C/svg%3E");
}

/* --- Aurora --------------------------------------------------------------
   Blurred colour fields behind the hero. This is where the raw logo colours
   live: nothing sits on top of them, so their lightness is an asset. */
.aurora { position: absolute; inset: 0; overflow: hidden; pointer-events: none; z-index: 0; }
.aurora span {
  position: absolute; border-radius: 50%;
  filter: blur(70px);
  opacity: .5;
}
.aurora .a1 { width: 46vw; height: 46vw; top: -14vw; left: -10vw;  background: var(--lagoon); }
.aurora .a2 { width: 38vw; height: 38vw; top: 6vw;   right: -8vw;  background: var(--lime);   opacity: .45; }
.aurora .a3 { width: 26vw; height: 26vw; bottom: -8vw; left: 32vw; background: var(--tangerine); opacity: .32; }

/* --- Reveal --------------------------------------------------------------
   Attribute-based on purpose: `[data-reveal]` is (0,1,0) and
   `[data-reveal].is-in` is (0,2,0), so the visible rule always outranks the
   hidden one. Gated on .has-reveal, set in <head> only when it is safe. */
/* Travel far enough, and let the fade finish well before the movement does,
   so this reads as something sliding into place rather than something
   appearing. `data-reveal="left|right"` slides in from the side instead. */
.has-reveal [data-reveal] {
  opacity: 0;
  translate: 0 56px;
  transition:
    opacity .42s ease-out,
    translate 1.05s cubic-bezier(.16, .86, .26, 1);
}
.has-reveal [data-reveal="left"]  { translate: -68px 0; }
.has-reveal [data-reveal="right"] { translate:  68px 0; }
.has-reveal [data-reveal].is-in { opacity: 1; translate: 0 0; }

@media (max-width: 960px) {
  /* Sideways travel on a narrow screen fights the horizontal scroll lock, so
     everything slides up instead. */
  .has-reveal [data-reveal="left"],
  .has-reveal [data-reveal="right"] { translate: 0 44px; }
}

/* --- Buttons ------------------------------------------------------------ */
.btn {
  display: inline-flex; align-items: center; justify-content: center; gap: .55em;
  font-family: var(--font-body); font-weight: 500; font-size: 1rem;
  letter-spacing: -.01em;
  padding: .92em 1.7em;
  border: 0; border-radius: 999px;
  background: var(--ink); color: #fff;
  text-decoration: none; cursor: pointer;
  box-shadow: var(--sh-1);
  transition: transform .2s cubic-bezier(.22,.7,.3,1), box-shadow .2s ease, background .2s ease;
}
.btn:hover  { transform: translateY(-2px); box-shadow: var(--sh-2); }
.btn:active { transform: translateY(0);    box-shadow: var(--sh-1); }

.btn--lime   { background: var(--lime);      color: var(--ink); }
.btn--lagoon { background: var(--lagoon);    color: var(--ink); }
.btn--tang   { background: var(--tangerine); color: var(--ink); }
.btn--ghost  { background: transparent; color: var(--ink); box-shadow: inset 0 0 0 1.5px rgba(16,50,61,.16); }
.btn--ghost:hover { background: var(--surface); box-shadow: inset 0 0 0 1.5px rgba(16,50,61,.16), var(--sh-1); }
.btn--light  { background: var(--surface); color: var(--ink); }
.btn--arrow::after {
  content: ""; width: 18px; height: 18px; flex: none;
  background: currentColor;
  -webkit-mask: var(--arrow) center / contain no-repeat;
          mask: var(--arrow) center / contain no-repeat;
  transition: transform .2s ease;
}
.btn--arrow:hover::after { transform: translateX(3px); }

/* An inline <svg> with no width/height and no CSS size expands to fill its
   flex container. Inside a width:100% button that means it eats the screen.
   Every icon in a button needs an explicit size and flex:none. */
.btn svg {
  width: 18px; height: 18px;
  flex: none;
  transition: transform .2s ease;
}
.btn:hover svg { transform: translateX(3px); }
.btn > span { min-width: 0; }

/* No URL for this yet — reads as a button, is not a dead link. */
.btn.is-pending { opacity: .5; cursor: default; box-shadow: inset 0 0 0 1.5px rgba(16,50,61,.14); background: transparent; color: var(--ink-2); }
.btn.is-pending:hover { transform: none; box-shadow: inset 0 0 0 1.5px rgba(16,50,61,.14); }

.textlink {
  display: inline-flex; align-items: center; gap: .45em;
  font-weight: 500; text-decoration: none; color: var(--ink);
  padding-bottom: 3px;
  background: linear-gradient(var(--lagoon), var(--lagoon)) no-repeat left bottom / 100% 2px;
  transition: background-size .25s ease;
}
.textlink:hover { background-size: 100% 8px; }

.arrowlink {
  display: inline-flex; align-items: center; gap: .45em;
  font-weight: 500; text-decoration: none; color: var(--lagoon-ink);
}
/* The arrow is drawn here rather than inlined as an <svg> in every link, so
   the link itself is nothing but editable text. Masked, not a background
   image, so it inherits the link's colour. */
.arrowlink::after {
  content: ""; width: 16px; height: 16px; flex: none;
  background: currentColor;
  -webkit-mask: var(--arrow) center / contain no-repeat;
          mask: var(--arrow) center / contain no-repeat;
  transition: transform .2s ease;
}
.arrowlink:hover::after { transform: translateX(4px); }

/* --- Chips and eyebrows ------------------------------------------------- */
.eyebrow {
  display: inline-flex; align-items: center; gap: .6em;
  font-family: var(--font-body); font-weight: 500;
  font-size: .78rem; letter-spacing: .14em; text-transform: uppercase;
  color: var(--ink-3);
  margin-bottom: 18px;
}
.eyebrow::before {
  content: ""; width: 26px; height: 2px; border-radius: 2px;
  background: var(--accent, var(--lagoon));
}
.center .eyebrow { justify-content: center; }
.eyebrow--lime  { --accent: var(--lime);      }
.eyebrow--tang  { --accent: var(--tangerine); }
.eyebrow--ember { --accent: var(--ember);     }

.chip {
  display: inline-flex; align-items: center; gap: .5em;
  font-size: .92rem; font-weight: 400; color: var(--ink);
  padding: .55em 1.1em;
  border-radius: 999px;
  background: var(--surface);
  box-shadow: var(--sh-1);
}
.chip .dot,
.chip:not(:has(.dot))::before {
  content: ""; width: 8px; height: 8px; border-radius: 50%;
  background: var(--accent, var(--lime)); flex: none;
}
.chip--lagoon { --accent: var(--lagoon);    }
.chip--lime   { --accent: var(--lime);      }
.chip--tang   { --accent: var(--tangerine); }
.chip-row { display: flex; flex-wrap: wrap; gap: 10px; margin-top: 32px; }

/* --- Header --------------------------------------------------------------
   A capsule that floats clear of the page edge and tightens on scroll. */
.site-header {
  position: fixed; inset: 14px 0 auto; z-index: 100;
  transition: inset .35s cubic-bezier(.22,.7,.3,1);
}
.site-header .bar {
  display: flex; align-items: center; gap: 18px;
  max-width: var(--wrap); margin-inline: auto;
  padding: 10px 12px 10px 22px;
  border-radius: 999px;
  background: rgba(255,255,255,.72);
  -webkit-backdrop-filter: blur(18px) saturate(160%);
  backdrop-filter: blur(18px) saturate(160%);
  box-shadow: 0 1px 0 rgba(255,255,255,.9) inset, var(--sh-1);
  transition: box-shadow .35s ease, background .35s ease, padding .35s ease;
}
.site-header.is-stuck { inset: 8px 0 auto; }
.site-header.is-stuck .bar {
  background: rgba(255,255,255,.88);
  box-shadow: 0 1px 0 rgba(255,255,255,.9) inset, var(--sh-2);
}
.site-header .wrap { padding-inline: var(--gut); }

/* Brand logo — the supplied artwork. Colour on light ground, white on dark.
   Sized by height so the 2:1 art keeps its ratio at every breakpoint. */
.brand { text-decoration: none; display: inline-flex; align-items: center; flex: none; }
.brand-logo { display: block; height: 46px; width: auto; }
.foot-brand .brand-logo { height: 52px; }
/* The artwork's box includes the sunburst, so centring the box leaves the
   letters sitting low against the nav. Lift by the mark's centre of mass -
   its letters occupy rows 119-238 of 239, putting the mass centre 17.7%
   below the geometric one. A percentage translate resolves against the
   element's own height, so this holds at every breakpoint, and translate
   does not move the box, so the capsule height is untouched. */
.site-header .brand-logo { translate: 0 -18%; }

.nav { margin-inline: auto; }
.nav ul { display: flex; gap: 2px; list-style: none; margin: 0; padding: 0; }
.nav a {
  display: block; padding: .5em .95em; border-radius: 999px;
  text-decoration: none; font-size: .98rem; font-weight: 400; color: var(--ink-2);
  transition: background .2s ease, color .2s ease;
}
.nav a:hover { background: rgba(16,50,61,.06); color: var(--ink); }
.nav a[aria-current="page"] { background: var(--ink); color: #fff; font-weight: 400; }

.lang {
  display: inline-flex; padding: 3px; flex: none;
  border-radius: 999px; background: rgba(16,50,61,.07);
}
.lang a,
.lang button {
  border: 0; background: transparent; cursor: pointer;
  font-family: var(--font-body); font-weight: 500; font-size: .8rem;
  padding: .35em .8em; border-radius: 999px; color: var(--ink-2);
  transition: background .2s ease, color .2s ease;
}
.lang a { text-decoration: none; }
.lang a.is-active,
.lang button.is-active { background: var(--surface); color: var(--ink); box-shadow: var(--sh-1); }

.nav-toggle {
  display: none; flex: none;
  width: 44px; height: 44px; padding: 0;
  border: 0; border-radius: 50%;
  background: rgba(16,50,61,.07); cursor: pointer;
}
.nav-toggle i {
  display: block; width: 18px; height: 1.8px; margin: 0 auto;
  background: var(--ink); border-radius: 2px; position: relative;
  transition: transform .25s ease;
}
.nav-toggle i::before, .nav-toggle i::after {
  content: ""; position: absolute; left: 0;
  width: 18px; height: 1.8px; background: var(--ink); border-radius: 2px;
  transition: transform .25s ease;
}
.nav-toggle i::before { top: -6px; }
.nav-toggle i::after  { top: 6px;  }
.site-header.is-open .nav-toggle i { transform: rotate(45deg); }
.site-header.is-open .nav-toggle i::before { transform: translateY(6px) rotate(-90deg); }
.site-header.is-open .nav-toggle i::after  { opacity: 0; }

/* --- Sections ----------------------------------------------------------- */
.section { position: relative; padding-block: clamp(72px, 9vw, 128px); }
.section--tight { padding-block: clamp(48px, 6vw, 80px); }
.section--flush-top { padding-top: 0; }  /* was an inline style on the CTA band */
.section--surface { background: var(--surface); }
.section-head { max-width: 58ch; margin-bottom: 52px; }
.section-head.center { margin-inline: auto; }

/* A soft tinted band, for alternation wherever white cards live. Alternation
   used to reach for pure white, which made a white card on it disappear
   outright; this keeps the rhythm and keeps the cards visible. */
.section--tint { background: linear-gradient(180deg, var(--lagoon-wash), var(--ground) 78%); }

/* --- Hero --------------------------------------------------------------- */
/* No overflow clip: .aurora already clips itself, and clipping the hero was
   cutting the art short on a phone. */
.hero {
  position: relative;
  padding-block: clamp(148px, 17vw, 216px) clamp(72px, 9vw, 120px);
}
.hero .wrap { position: relative; z-index: 1; }
.hero-grid {
  display: grid; grid-template-columns: 1.06fr .94fr;
  gap: clamp(36px, 5vw, 76px); align-items: center;
}
.hero h1 { margin-bottom: .3em; }
.hero .lede { font-size: 1.2rem; }
.hero-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 14px; margin-top: 34px; }

/* The highlighted words: a gradient between two text-safe inks, so it reads
   as one advanced move rather than a colour that has to be squinted at. */
/* A bare <span> counts too. Elementor's heading widget keeps inline tags but
   strips their class attributes, so a native heading can never carry .hl -
   this way the words to highlight are just wrapped in <span> in the panel and
   the heading stays a real, editable widget instead of raw HTML. */
.hl,
.e-heading-base > span,
.elementor-heading-title > span {
  background: linear-gradient(96deg, var(--lagoon-ink) 0%, var(--lime-ink) 46%, var(--tang-ink) 100%);
  -webkit-background-clip: text; background-clip: text;
  color: transparent;
  -webkit-text-fill-color: transparent;
}
@supports not (background-clip: text) {
  .hl,
  .e-heading-base > span,
  .elementor-heading-title > span { color: var(--lagoon-ink); -webkit-text-fill-color: currentColor; }
}

/* --- Hero art ----------------------------------------------------------- */
.hero-art { position: relative; aspect-ratio: 1 / 1.02; }

/* A tilted colour plate behind the photo gives the stack depth without an
   outline anywhere. */
.hero-art::before {
  content: "";
  position: absolute; inset: 7% 2% 3% 6%;
  border-radius: var(--r-xl);
  background: linear-gradient(150deg, var(--lagoon), var(--lime));
  rotate: -4deg;
  opacity: .9;
  box-shadow: var(--sh-3);
}
.hero-photo {
  position: absolute; inset: 0 6% 8% 0;
  border-radius: var(--r-xl);
  overflow: hidden;
  background: var(--surface);
  box-shadow: var(--sh-3);
}
.hero-photo img { width: 100%; height: 100%; object-fit: cover; }
.hero-photo img.pan-right { object-position: 74% center; }

/* Glass cards that overlap the photo edge. */
.glass {
  position: absolute; z-index: 3;
  display: flex; align-items: center; gap: 12px;
  padding: 14px 20px 14px 14px;
  border-radius: var(--r);
  background: rgba(255,255,255,.78);
  -webkit-backdrop-filter: blur(16px) saturate(170%);
  backdrop-filter: blur(16px) saturate(170%);
  box-shadow: 0 1px 0 rgba(255,255,255,.9) inset, var(--sh-2);
  font-size: .92rem; line-height: 1.35;
}
.glass b,
.glass .glass-t { display: block; font-family: var(--font-display); font-weight: 600; font-size: 1rem; letter-spacing: -.02em; }
.glass small,
.glass .glass-s { color: var(--ink-2); font-size: .82rem; }
.glass .ico {
  width: 40px; height: 40px; flex: none;
  border-radius: 14px; display: grid; place-items: center;
  background: var(--accent-wash, var(--lagoon-wash));
}
.glass .ico svg { width: 22px; height: 22px; }
.glass .ico:not(:has(svg))::before {
  content: ""; width: 22px; height: 22px;
  background: var(--glass-icon) center / contain no-repeat;
}
.glass-ico--heart { --glass-icon: var(--icon-heart); }
.glass-ico--plate { --glass-icon: var(--icon-plate); }

/* On desktop the wrapper vanishes so each card can position itself against
   .hero-art; on a phone it becomes a real two-up row instead. */
.glass-row { display: contents; }
.glass--a { left: -4%;  top: 16%; animation: float-a 9s ease-in-out infinite; --accent-wash: var(--lime-wash); }
.glass--b { right: -2%; bottom: 14%; animation: float-b 11s ease-in-out infinite; --accent-wash: var(--tang-wash); }

@keyframes float-a { 0%,100% { translate: 0 0; } 50% { translate: 0 -10px; } }
@keyframes float-b { 0%,100% { translate: 0 0; } 50% { translate: 0 9px; } }

/* --- Bento grid --------------------------------------------------------- */
/* The first tile spans two columns and two rows; everything after it flows
   into what is left. It keys off .tile--big rather than :first-child, because
   Elementor inserts its own helper element first in the editor and that was
   taking the span. Nothing here counts tiles, so adding or removing one just
   reflows. */
.bento {
  display: grid; gap: 20px;
  grid-template-columns: repeat(3, 1fr);
}
.bento > .tile--big { grid-column: span 2; grid-row: span 2; }

.tile {
  position: relative; overflow: hidden;
  display: flex; flex-direction: column;
  border-radius: var(--r-lg);
  background: var(--surface);
  box-shadow: var(--sh-1);
  text-decoration: none; color: inherit;
  transition: transform .3s cubic-bezier(.22,.7,.3,1), box-shadow .3s ease;
}
.tile:hover { transform: translateY(-4px); box-shadow: var(--sh-2); }
.tile-media { position: relative; overflow: hidden; background: var(--lagoon-wash); }
.tile-media img { width: 100%; height: 100%; object-fit: cover; transition: transform .6s cubic-bezier(.22,.7,.3,1); }
.tile:hover .tile-media img { transform: scale(1.04); }
.tile-body { padding: 26px 28px 30px; display: flex; flex-direction: column; flex: 1; gap: 10px; }
/* :not(.arrowlink) because the link is a <p> here rather than the original
   <span>, and this rule was only ever meant for the body copy. */
.tile-body p:not(.arrowlink) { font-size: .98rem; color: var(--ink-2); margin: 0; }
.tile-body .arrowlink { margin-top: auto; padding-top: 14px; }
.tile--big .tile-media { aspect-ratio: 16 / 10; }
.tile--big .tile-body { padding: 30px 34px 34px; }
.tile--big h3 { font-size: clamp(1.5rem, 2.4vw, 1.9rem); }
.tile--sm { flex-direction: row; align-items: stretch; }
.tile--sm .tile-media { width: 38%; flex: none; }
.tile--sm .tile-body { padding: 22px 24px; }

/* Two equal tiles, e.g. the team. A class rather than an inline style, so the
   media queries below can actually collapse it on a phone. */
.duo { display: grid; grid-template-columns: repeat(2, 1fr); gap: 20px; }
.duo .tile-media { aspect-ratio: 4 / 3; }

/* A hairline of colour along the top edge, per tile. */
.tile::before {
  content: ""; position: absolute; inset: 0 0 auto; height: 4px; z-index: 2;
  background: var(--accent, var(--lagoon));
}
.tile--lime   { --accent: var(--lime);      }
.tile--tang   { --accent: var(--tangerine); }
.tile--lagoon { --accent: var(--lagoon);    }
.tile--ember  { --accent: var(--ember);     }

/* --- Editorial split ---------------------------------------------------- */
.split { display: grid; grid-template-columns: 1fr 1fr; gap: clamp(36px, 5vw, 80px); align-items: center; }
.split--right .split-media { order: 2; }
.split-media {
  position: relative; aspect-ratio: 4 / 4.4;
  border-radius: var(--r-xl); overflow: hidden;
  box-shadow: var(--sh-3);
}
.split-media img { width: 100%; height: 100%; object-fit: cover; }

/* Was an inline margin-top on the paragraph wrapping the link. Scoped here
   instead so the link can be a plain text widget with nothing inline on it. */
.split p.arrowlink { margin-top: 28px; }  /* p. to outrank Elementor's margin reset */
.split-media--wide { aspect-ratio: 4 / 3.2; }

/* A soft colour wash sitting under the photo, offset. */
.split-media::after {
  content: ""; position: absolute; inset: auto 0 0; height: 32%;
  background: linear-gradient(to top, rgba(16,50,61,.34), transparent);
  pointer-events: none;
}

/* --- Habit rail --------------------------------------------------------- */
/* One row of equal columns, however many steps there are. */
.rail {
  position: relative;
  display: grid; gap: var(--rail-gap);
  grid-auto-flow: column; grid-auto-columns: 1fr;
}

/* The dotted spine. Each step draws the segment to its right-hand neighbour
   and the last one draws nothing, so the thread runs icon-centre to
   icon-centre for any number of steps. It used to be a single line on .rail
   inset by a percentage tuned for exactly four. Percentages in `right`
   resolve against the step's own width, so -50% - the gap lands precisely on
   the next icon's centre whatever the column width works out to be. */
.step::before {
  content: ""; position: absolute; z-index: 0;
  top: 42px; height: 2px;
  left: 50%; right: calc(-1 * var(--rail-gap) - 50%);
  background: repeating-linear-gradient(90deg, rgba(16,50,61,.18) 0 6px, transparent 6px 14px);
}
/* The first and last steps carry a short overhang so the thread pokes past
   the outer icons the way the old percentage inset did, instead of stopping
   dead at their centres. A fixed length, so it does not depend on how many
   steps there are. */
.step:first-child::before { left: calc(50% - var(--rail-overhang)); }
.step:last-child::before  { right: auto; width: var(--rail-overhang); }
.step { position: relative; z-index: 1; text-align: center; }
.step-ico {
  width: 84px; height: 84px; margin: 0 auto 22px;
  border-radius: 30px;
  display: grid; place-items: center;
  background: var(--surface);
  box-shadow: var(--sh-2);
  position: relative;
  transition: transform .3s cubic-bezier(.22,.7,.3,1);
}
.step:hover .step-ico { transform: translateY(-4px) rotate(-4deg); }
.step-ico::after {
  content: ""; position: absolute; inset: 0; border-radius: 30px;
  background: var(--wash, var(--lagoon-wash)); z-index: 0;
}
.step-ico svg { position: relative; z-index: 1; width: 40px; height: 40px; }

/* The step icons. These were four inline <svg> blocks in the markup; they are
   decoration, so they live here and the step only names which one it wants.
   Their fills are literal because a data URI cannot read the :root tokens -
   they are #F5821F tangerine, #8CC63F lime, #0FAFC0 lagoon, #F4511E ember, so
   a palette change has to touch them too. */
.step-ico::before {
  content: ""; position: relative; z-index: 1;
  width: 40px; height: 40px;
  background: var(--step-icon) center / contain no-repeat;
}
.step-ico--plate { --step-icon: var(--icon-plate); }
.step-ico--ball { --step-icon: var(--icon-ball); }
.step-ico--moon { --step-icon: var(--icon-moon); }
.step-ico--heart { --step-icon: var(--icon-heart); }

.step h3 { font-size: 1.16rem; margin-bottom: .35em; }
.step p { font-size: .96rem; color: var(--ink-2); margin: 0; }
.step--lime   { --wash: var(--lime-wash);   }
.step--tang   { --wash: var(--tang-wash);   }
.step--lagoon { --wash: var(--lagoon-wash); }
.step--ember  { --wash: var(--ember-wash);  }

/* --- Quote -------------------------------------------------------------- */
.quote { display: grid; grid-template-columns: 1.15fr 1fr; gap: 40px; align-items: center; }
.quote q,
.quote h2 {
  display: block; quotes: none;
  font-family: var(--font-display); font-weight: 600;
  font-size: clamp(1.6rem, 3.2vw, 2.5rem); line-height: 1.18; letter-spacing: -.03em;
  margin: 0;
}

/* --- CTA panel ---------------------------------------------------------- */
.panel {
  position: relative; overflow: hidden;
  border-radius: var(--r-xl);
  padding: clamp(42px, 6vw, 76px);
  background: var(--ink); color: #fff;
  box-shadow: var(--sh-3);
}
.panel h2 { color: #fff; }
.panel .lede { color: rgba(255,255,255,.82); }
.panel-actions { display: flex; flex-wrap: wrap; gap: 14px; margin-top: 32px; }
/* Aurora inside the dark panel, so it is not a flat block. */
.panel::before, .panel::after {
  content: ""; position: absolute; border-radius: 50%; filter: blur(70px); pointer-events: none;
}
.panel::before { width: 380px; height: 380px; top: -140px; right: -80px; background: var(--lagoon); opacity: .5; }
.panel::after  { width: 300px; height: 300px; bottom: -150px; left: -60px; background: var(--lime); opacity: .38; }
.panel > * { position: relative; z-index: 1; }

/* --- Plans -------------------------------------------------------------- */
.plans { display: grid; grid-template-columns: repeat(3, 1fr); gap: 22px; align-items: start; }
.plan {
  position: relative;
  border-radius: var(--r-lg);
  background: var(--surface);
  box-shadow: var(--sh-1);
  padding: 34px 32px 36px;
  transition: transform .3s cubic-bezier(.22,.7,.3,1), box-shadow .3s ease;
}
.plan:hover { transform: translateY(-4px); box-shadow: var(--sh-2); }
.plan .kicker {
  font-family: var(--font-display); font-weight: 600;
  font-size: .76rem; letter-spacing: .16em; text-transform: uppercase;
  color: var(--accent-ink, var(--lagoon-ink));
  display: block; margin-bottom: 14px;
}
.plan h3 { font-size: 1.5rem; margin-bottom: .45em; }
.plan > p { font-size: .98rem; color: var(--ink-2); }
.plan ul,
.plan .elementor-icon-list-items { list-style: none; margin: 26px 0; padding: 0; display: grid; gap: 13px; }
.plan li,
.plan .elementor-icon-list-item { position: relative; padding-left: 32px; font-size: .98rem; }
.plan li svg { position: absolute; left: 0; top: .28em; width: 20px; height: 20px; }
.plan .elementor-icon-list-item::before { content: ""; position: absolute; left: 0; top: .28em; width: 20px; height: 20px; border-radius: 50%; background: var(--wash, var(--lagoon-wash)); }
/* Four classes: the widget's own divider also lives on ::after and sets it to
   the full item width, which smeared a bar across the text. */
.elementor .plan .elementor-icon-list-items .elementor-icon-list-item::after {
  content: ""; position: absolute; left: 0; top: .28em; width: 20px; height: 20px;
  border: 0;
  background: var(--accent-ink, var(--lagoon-ink));
  -webkit-mask: var(--icon-check) center / 13px 13px no-repeat;
          mask: var(--icon-check) center / 13px 13px no-repeat;
}
/* The widget's own icon slot is unused - the tick above replaces it. */
.plan .elementor-icon-list-icon { display: none; }
.elementor .plan .elementor-icon-list-items { margin: 26px 0; padding: 0; }
.elementor .plan .elementor-icon-list-item { font-size: .98rem; padding-left: 32px; position: relative; }
.elementor .plan .elementor-icon-list-text { padding: 0; font-size: inherit; line-height: inherit; }
.plan .bestfor {
  font-size: .92rem; color: var(--ink-2);
  padding: 18px 20px; margin: 24px 0 26px;
  border-radius: var(--r-sm);
  background: var(--wash, var(--lagoon-wash));
}
.plan .bestfor b,
.plan .bestfor .bestfor-t { display: block; color: var(--ink); font-family: var(--font-display); font-weight: 600; font-size: .86rem; letter-spacing: .04em; text-transform: uppercase; margin-bottom: 4px; }
.plan .btn { width: 100%; }
.plan--lime   { --accent: var(--lime);      --accent-ink: var(--lime-ink);   --wash: var(--lime-wash);   }
.plan--tang   { --accent: var(--tangerine); --accent-ink: var(--tang-ink);   --wash: var(--tang-wash);   }
.plan--lagoon { --accent: var(--lagoon);    --accent-ink: var(--lagoon-ink); --wash: var(--lagoon-wash); }

/* The middle plan rides higher and wears a gradient ring. */
.plan--featured { box-shadow: var(--sh-3); }
.plan--featured::before {
  content: ""; position: absolute; inset: -2px; border-radius: calc(var(--r-lg) + 2px);
  background: linear-gradient(150deg, var(--lagoon), var(--lime), var(--tangerine));
  z-index: -1;
}
.plan--featured .flag {
  position: absolute; top: -14px; left: 50%; translate: -50% 0;
  font-size: .76rem; font-weight: 500; letter-spacing: .1em; text-transform: uppercase;
  padding: .45em 1.1em; border-radius: 999px;
  background: var(--ink); color: #fff; white-space: nowrap;
}
@media (min-width: 961px) { .plans > .plan--featured { margin-top: -18px; } }

/* --- Plans, presented as equals -----------------------------------------
   The alternative treatment. The gradient that used to ring the middle card
   and single it out is now the tray all three sit on, and every card carries
   an identical skin: same surface, same shadow, same accent, same button. No
   card is flagged, elevated or coloured differently, so the page describes
   three options instead of steering toward one. */
.plan-tray {
  background: linear-gradient(150deg, var(--lagoon), var(--lime) 52%, var(--tangerine));
  border-radius: var(--r-xl);
  padding: clamp(22px, 3.4vw, 46px);
  box-shadow: var(--sh-3);
}

/* One accent for all three, so the tick marks, kickers and washes match. */
.plans--equal .plan {
  --accent: var(--lagoon);
  --accent-ink: var(--lagoon-ink);
  --wash: var(--lagoon-wash);
  box-shadow: var(--sh-2);
  margin-top: 0;
}
.plans--equal .plan:hover { box-shadow: var(--sh-3); }
/* Nothing here is allowed to make one card louder than the others. */
.plans--equal .plan--featured::before,
.plans--equal .plan .flag { display: none; }

@media (max-width: 720px) {
  .plan-tray { padding: 18px; border-radius: var(--r-lg); }
}

/* --- Partner wall ------------------------------------------------------- */
.wall { display: grid; grid-template-columns: repeat(3, 1fr); gap: 20px; }
.partner {
  display: flex; flex-direction: column; gap: 6px;
  border-radius: var(--r-lg);
  background: var(--surface);
  box-shadow: var(--sh-1);
  padding: 26px 28px 30px;
  transition: transform .3s cubic-bezier(.22,.7,.3,1), box-shadow .3s ease;
}
.partner:hover { transform: translateY(-4px); box-shadow: var(--sh-2); }
/* Every logo in an identically sized well, per the brand direction. */
.partner-logo {
  width: 100%; height: 128px; margin-bottom: 20px;
  border-radius: var(--r); overflow: hidden;
  background: var(--ground);
  display: grid; place-items: center; padding: 16px;
}
.partner-logo img { max-height: 96px; width: auto; object-fit: contain; }
.partner h3 { font-size: 1.16rem; margin-bottom: .3em; }
/* :not(.btn) because the inert "Visit website" is a paragraph here, not the
   static page’s <span>, and must not take the body copy margin. */
.partner p:not(.btn) { font-size: .96rem; color: var(--ink-2); margin: 0 0 20px; }
.partner .btn { align-self: flex-start; margin-top: auto; }

/* --- Newsletter --------------------------------------------------------- */
.join-panel {
  border-radius: var(--r-xl);
  background: var(--surface);
  box-shadow: var(--sh-2);
  padding: clamp(36px, 5vw, 64px);
  display: grid; grid-template-columns: 1fr 1fr; gap: clamp(32px, 5vw, 64px); align-items: center;
}
/* The contact form is one column; the newsletter panel is two. Was an inline
   grid-template-columns on the form element. */
.join-panel--single { grid-template-columns: 1fr; }
/* Honeypot: off-screen rather than display:none, which some bots skip. */
.kidzy-hp { position: absolute; left: -9999px; width: 1px; height: 1px; overflow: hidden; }
.field { display: grid; gap: 8px; margin-bottom: 18px; }
label { font-size: .94rem; font-weight: 400; color: var(--ink-2); }
.req { color: var(--ember-ink); }
input[type="email"], input[type="text"], input[type="tel"], textarea, select {
  width: 100%; font: inherit; font-size: 1rem; font-weight: 350; color: var(--ink);
  padding: .92em 1.15em;
  background: var(--ground);
  border: 1.5px solid transparent;
  border-radius: var(--r-sm);
  transition: border-color .2s ease, background .2s ease;
}
input:focus, textarea:focus, select:focus { background: var(--surface); border-color: var(--lagoon); }
textarea { min-height: 160px; resize: vertical; }
::placeholder { color: var(--ink-3); }
.consent { display: flex; gap: 12px; align-items: flex-start; margin-bottom: 24px; font-size: .94rem; color: var(--ink-2); }
.consent input { width: 22px; height: 22px; margin: 1px 0 0; accent-color: var(--lagoon); flex: none; }

.form-status {
  border-radius: var(--r-sm); padding: 15px 20px; margin-bottom: 22px;
  font-size: .98rem; font-weight: 400;
}
.form-status--ok  { background: var(--lime-wash);  color: var(--lime-ink);  }
.form-status--err { background: var(--ember-wash); color: var(--ember-ink); }

/* --- Footer ------------------------------------------------------------- */
.site-footer {
  position: relative;
  background: var(--ink); color: rgba(255,255,255,.76);
  padding-block: clamp(64px, 8vw, 96px) 40px;
  margin-top: clamp(60px, 8vw, 110px);
  border-radius: var(--r-xl) var(--r-xl) 0 0;
}
.site-footer a { color: rgba(255,255,255,.76); text-decoration: none; transition: color .2s ease; }
.site-footer a:hover { color: #fff; }
.foot-top { display: flex; flex-wrap: wrap; gap: 40px; justify-content: space-between; }
.foot-brand { max-width: 32ch; }
.foot-brand p { margin-top: 14px; font-size: .98rem; }
.foot-col h4, .foot-col h3 { color: #fff; font-size: .82rem; letter-spacing: .14em; text-transform: uppercase; margin-bottom: 18px; font-weight: 500; }
.foot-col ul { list-style: none; margin: 0; padding: 0; display: grid; gap: 11px; font-size: .98rem; }
.social { display: flex; gap: 10px; }
.social a, .social span {
  width: 42px; height: 42px; border-radius: 14px;
  display: grid; place-items: center;
  background: rgba(255,255,255,.09); color: #fff;
  transition: background .2s ease, transform .2s ease;
}
.social a:hover { background: var(--lime); color: var(--ink); transform: translateY(-2px); }
.social svg { width: 19px; height: 19px; fill: currentColor; }
.social span.is-pending { opacity: .32; cursor: default; }
.foot-bottom {
  margin-top: 52px; padding-top: 26px;
  border-top: 1px solid rgba(255,255,255,.12);
  font-size: .92rem; color: rgba(255,255,255,.55);
}

/* --- Sticky mobile CTA ---------------------------------------------------
   A small pill in the bottom-right corner, not a bar across the whole width.
   It stays out of the way of the content it is sitting on top of. */
.mobile-cta {
  display: none;
  position: fixed;
  right: 14px; bottom: 14px; left: auto; z-index: 90;
  transition: transform .3s cubic-bezier(.22,.7,.3,1), opacity .3s ease;
}
.mobile-cta .btn {
  width: auto;
  font-size: .9rem;
  padding: .74em 1.15em;
  gap: .45em;
  box-shadow: 0 2px 6px rgba(16,50,61,.18), 0 14px 30px -10px rgba(16,50,61,.42);
}
.mobile-cta .btn svg { width: 16px; height: 16px; }
.mobile-cta .btn::after {
  content: ""; width: 16px; height: 16px; flex: none;
  background: currentColor;
  -webkit-mask: var(--arrow) center / contain no-repeat;
          mask: var(--arrow) center / contain no-repeat;
}
.mobile-cta.is-hidden { transform: translateY(150%); opacity: 0; pointer-events: none; }

[id] { scroll-margin-top: 110px; }

/* --- Version picker ------------------------------------------------------
   Appears on load on both plans pages so a visitor can see either version.
   The markup carries `hidden` in the HTML, so with no JS it never appears and
   the page simply works. */
.picker[hidden] { display: none; }
.picker {
  position: fixed; inset: 0; z-index: 300;
  display: grid; place-items: center;
  padding: 22px;
  background: rgba(16, 50, 61, .58);
  -webkit-backdrop-filter: blur(8px);
  backdrop-filter: blur(8px);
  animation: picker-fade .28s ease-out;
}
body.picker-open { overflow: hidden; }

.picker-card {
  position: relative;
  width: 100%; max-width: 520px;
  padding: clamp(28px, 4vw, 44px);
  border-radius: var(--r-xl);
  background: var(--surface);
  box-shadow: var(--sh-3);
  animation: picker-rise .5s cubic-bezier(.16, .86, .26, 1);
}
.picker-card h2 { font-size: clamp(1.35rem, 3.4vw, 1.85rem); margin-bottom: .5em; padding-right: 34px; }
.picker-card > p { font-size: 1rem; color: var(--ink-2); }

.picker-opts { display: grid; gap: 12px; margin: 26px 0 22px; }
.picker-opt {
  display: flex; align-items: center; gap: 14px;
  width: 100%; text-align: left; cursor: pointer;
  border: 0; border-radius: var(--r);
  padding: 17px 20px;
  background: var(--ground); color: var(--ink);
  font-family: var(--font-body); font-size: 1rem;
  transition: background .2s ease, transform .2s ease, box-shadow .2s ease;
}
.picker-opt:hover { background: var(--lagoon-wash); transform: translateY(-2px); box-shadow: var(--sh-1); }
.picker-opt .num {
  width: 42px; height: 42px; flex: none;
  display: grid; place-items: center;
  border-radius: 14px; background: var(--surface);
  font-family: var(--font-display); font-weight: 700; font-size: 1.05rem;
  box-shadow: var(--sh-1);
}
.picker-opt b { display: block; font-family: var(--font-display); font-weight: 600; letter-spacing: -.02em; }
.picker-opt small { color: var(--ink-2); font-size: .88rem; line-height: 1.4; }
/* The version already on screen, marked so the choice is not a guess. */
.picker-opt.is-current { box-shadow: inset 0 0 0 2px var(--lagoon); }
.picker-opt.is-current .num { background: var(--lagoon); }

.picker-note { font-size: .9rem; color: var(--ink-2); margin: 0; }

.picker-close {
  position: absolute; top: 16px; right: 16px;
  width: 38px; height: 38px; padding: 0;
  border: 0; border-radius: 50%;
  background: var(--ground); color: var(--ink-2);
  font-size: 1.2rem; line-height: 1; cursor: pointer;
  transition: background .2s ease, color .2s ease;
}
.picker-close:hover { background: var(--ember-wash); color: var(--ember-ink); }

@keyframes picker-fade { from { opacity: 0; } }
@keyframes picker-rise { from { opacity: 0; translate: 0 20px; scale: .97; } }

/* --- Responsive --------------------------------------------------------- */
@media (max-width: 1080px) {
  .bento { grid-template-columns: repeat(2, 1fr); }
  .bento > .tile--big { grid-column: span 2; grid-row: span 1; }
  .tile--sm { flex-direction: column; }
  .tile--sm .tile-media { width: 100%; aspect-ratio: 16 / 9; }
}

@media (max-width: 960px) {
  .hero-grid, .split, .quote, .join-panel { grid-template-columns: 1fr; }
  .split--right .split-media { order: 0; }
  .split-media { aspect-ratio: 4 / 3; }
  .hero-art { max-width: 460px; margin-inline: auto; }
  .plans, .wall { grid-template-columns: 1fr 1fr; }
  .rail { grid-auto-flow: row; grid-template-columns: repeat(2, 1fr); row-gap: 44px; }
  .step::before { content: none; }

  .nav-toggle { display: block; }
  .site-header .bar { flex-wrap: wrap; padding-right: 10px; }
  .brand { margin-right: auto; }
  .nav { order: 4; flex-basis: 100%; display: none; padding: 6px 4px 10px; }
  .site-header.is-open .nav { display: block; }
  .site-header.is-open .bar { border-radius: var(--r-lg); }
  .nav ul { flex-direction: column; gap: 2px; }
  .nav a { padding: .75em 1em; }
  .header-cta { display: none; }

  .mobile-cta { display: block; }
}

@media (max-width: 720px) {
  body { font-size: 17px; }
  .plans, .wall, .rail, .duo { grid-template-columns: 1fr; }
  /* One column, so the featured plan's flag has room in the gap above it. */
  .plans { gap: 34px; }
  .bento { grid-template-columns: 1fr; }
  .bento > .tile--big { grid-column: span 1; grid-row: span 1; }
  .tile--big .tile-body { padding: 24px 24px 28px; }

  /* The floating cards collided with the chip row above them and covered the
     photo. Below this width they stop floating and sit under it as a row. */
  .hero-art { aspect-ratio: auto; display: grid; gap: 12px; }
  .hero-art::before { display: none; }
  .hero-photo { position: relative; inset: auto; aspect-ratio: 4 / 3.3; }
  .glass-row { display: grid; grid-template-columns: 1fr 1fr; gap: 10px; }
  .glass {
    position: static; animation: none;
    align-items: flex-start;
    padding: 12px 14px 12px 12px; font-size: .84rem;
  }
  .glass .ico { width: 34px; height: 34px; border-radius: 11px; }
  .glass b { font-size: .9rem; }
  .glass small { font-size: .76rem; }

  .panel, .join-panel, .split-media, .hero-photo { border-radius: var(--r-lg); }
  .hero-art::before { border-radius: var(--r-lg); }
  .section-head { margin-bottom: 36px; }
  .plan { padding: 28px 24px 30px; }
  .partner { padding: 22px 22px 26px; }
  .quote q { font-size: clamp(1.45rem, 6.4vw, 1.9rem); }
}

@media (max-width: 480px) {
  :root { --gut: 18px; }
  h1 { font-size: clamp(2.05rem, 9.2vw, 2.6rem); }
  .hero { padding-block: 128px 60px; }
  .hero .lede { font-size: 1.06rem; }
  .hero-actions { gap: 10px; }
  .hero-art { max-width: 320px; }
  /* Chips read better stacked tight than wrapping mid-phrase. */
  .chip { font-size: .84rem; padding: .45em .9em; }
  .chip-row { gap: 8px; margin-top: 26px; }
  .brand-logo { height: 34px; }
  .site-header { inset: 8px 0 auto; }
  .site-header .bar { padding: 8px 8px 8px 16px; gap: 10px; }
  .lang button { padding: .3em .62em; font-size: .76rem; }
  .nav-toggle { width: 40px; height: 40px; }
  .mobile-cta .btn { font-size: .86rem; padding: .7em 1.05em; }
}

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after { transition-duration: .001ms !important; animation: none !important; }
}

/* --- Elementor compatibility -------------------------------------------
   Elementor ships two-class defaults that outrank this file's single-class
   selectors, and they change layout rather than decoration. They are undone
   here, once, rather than by setting values in Elementor's panels, so the
   design still lives entirely in this file. Both selectors deliberately sit
   one class above Elementor's own so they win on specificity, not load order
   - base-desktop.css prints after this file and cannot be reordered safely.

   1. Every atomic div-block gets padding: 10px, which insets any column that
      the design leaves unpadded.
   2. Every widget wrapper is position: relative, which makes it the
      containing block for .aurora, .hero-photo and .glass. Those resolve
      against a zero-height wrapper instead of .hero / .hero-art and collapse. */
.elementor .e-con.e-div-block-base { padding: 0; }

.hero .elementor-widget,
.section .elementor-widget { position: static; }

/* 3. Elementor's atomic paragraph zeroes every p margin, which drops the
      spacing under .eyebrow and between stacked paragraphs. These three
      restate the declarations from the Reset and Chips blocks above at the
      specificity Elementor forces - keep them in sync if those change. */
.elementor p.e-paragraph-base { margin-block-end: 1.15em; }
.elementor p.e-paragraph-base:last-child { margin-block-end: 0; }
.elementor .tile-body p.e-paragraph-base,
.elementor .step p.e-paragraph-base { margin-block-end: 0; }
.elementor .tile-body p.arrowlink { margin-top: auto; }

/* 5. .e-con.e-flex forces flex-direction:column on every container, which
      outranks .tile--sm and laid the small tiles out stacked instead of as a
      media/body row. Restated at the specificity Elementor forces. */
.elementor .tile    { flex-direction: column; }
.elementor .tile--sm { flex-direction: row; }

/* 6. .step h3 is one class and one element, which cannot outrank Elementor's
      two-class heading reset however it is ordered. Restated. */
.elementor .step h3.e-heading-base { margin-bottom: .35em; }
.elementor .quote h2.e-heading-base { margin: 0; }
.elementor .glass p.e-paragraph-base { margin: 0; }
/* Paragraphs standing in for inline UI - chips and the two link styles - must
   not carry the body paragraph's bottom margin; in a flex row it becomes line
   height. */
/* 11. Elementor resets form controls and labels to line-height 1. The design
       inherits the body's 1.68, which is what sizes every field. */
.elementor .field label,
.elementor .consent label,
.elementor input[type="text"],
.elementor input[type="email"],
.elementor input[type="tel"],
.elementor textarea,
.elementor select { line-height: 1.68; }

.elementor .chip.e-paragraph-base,
.elementor .textlink.e-paragraph-base,
.elementor .arrowlink.e-paragraph-base { margin-block-end: 0; }

/* 8. The atomic button lays itself out as a block, and .panel-actions is a
      container so it inherits the forced column direction. Both restated. */
/* The atomic button arrives with Elementor's own skin - blue, square, its own
   padding and font - all at two classes, which .btn cannot outrank. The Buttons
   block above is the source of these values; keep the two in step. */
.elementor .btn.e-button-base {
  display: inline-flex; align-items: center; justify-content: center; gap: .55em;
  font-family: var(--font-body); font-weight: 500; font-size: 1rem;
  letter-spacing: -.01em;
  padding: .92em 1.7em;
  border: 0; border-radius: 999px;
  background: var(--ink); color: #fff;
  box-shadow: var(--sh-1);
}
.elementor .btn--lime.e-button-base   { background: var(--lime);      color: var(--ink); }
.elementor .btn--lagoon.e-button-base { background: var(--lagoon);    color: var(--ink); }
.elementor .btn--tang.e-button-base   { background: var(--tangerine); color: var(--ink); }
.elementor .btn--light.e-button-base  { background: var(--surface);   color: var(--ink); }
.elementor .btn--ghost.e-button-base  { background: transparent; color: var(--ink); box-shadow: inset 0 0 0 1.5px rgba(16,50,61,.16); }

/* 9. Rule 1 zeroes div-block padding, which is what unpadded columns want but
      not .panel - it sets its own above. Any other padded div-block needs the
      same treatment. */
.elementor .panel.e-div-block-base { padding: clamp(42px, 6vw, 76px); }
.elementor .plan.e-div-block-base  { padding: 34px 32px 36px; }
.elementor .panel-actions,
.elementor .hero-actions,
.elementor .chip-row,
.elementor .glass { flex-direction: row; }

/* 10. Elementor gives every container width:100%, which overrides the left and
       right insets that size these against .hero-art, and blocks the
       display:contents that lets each badge position itself. */
.elementor .hero-photo,
.elementor .glass,
.elementor .glass > .e-con:not(.ico) { width: auto; }  /* the text column sizes to its text; the icon keeps its 40px */
.elementor .e-con.glass-row { display: contents; }  /* three classes, to beat .elementor .e-div-block-base */

/* 7. Hello Elementor constrains .site-header / .site-footer to the Elementor
      container width and centres them, which suits its own header markup. Ours
      is a full-bleed fixed capsule and a full-bleed footer, so that is undone
      here. Its selector uses :not(), which counts, so this matches it. */
.site-header:not(.dynamic-header),
.site-footer:not(.dynamic-footer) { max-width: none; margin-inline: 0; }
/* Its padding too, on the header only - the footer sets its own above and a
   blanket padding:0 here would outrank that. */
.site-header:not(.dynamic-header) { padding: 0; }
.elementor p.eyebrow { margin-bottom: 18px; }

/* 4. Same again for the atomic heading, which zeroes every heading margin.
      Restates the Reset block's h1-h4 rule; keep in sync with it. */
.elementor h1.e-heading-base,
.elementor h2.e-heading-base,
.elementor h3.e-heading-base,
.elementor h4.e-heading-base { margin: 0 0 .5em; }
.elementor .hero h1.e-heading-base { margin-bottom: .3em; }

/* 12. Reveal on scroll, class-driven.
   The design triggers this from `[data-reveal]`, but Elementor free cannot
   author a custom attribute (Advanced > Attributes is Pro). The CSS Classes
   field is free on every element, so `.reveal` is an exact alias of the
   attribute rules in the Reveal block above - same distances, same curves.
   Both selectors stay live: theme templates keep using the attribute, page
   content uses the class.
   `.reveal-left` / `.reveal-right` only override the direction, so they must
   be used alongside `.reveal`, never on their own. */
.has-reveal .reveal {
  opacity: 0;
  translate: 0 56px;
  transition:
    opacity .42s ease-out,
    translate 1.05s cubic-bezier(.16, .86, .26, 1);
}
.has-reveal .reveal-left  { translate: -68px 0; }
.has-reveal .reveal-right { translate:  68px 0; }
.has-reveal .reveal.is-in { opacity: 1; translate: 0 0; }

@media (max-width: 960px) {
  .has-reveal .reveal-left,
  .has-reveal .reveal-right { translate: 0 44px; }
}

/* 13. Contact details + map.
   Not part of the original design - added for the contact page's "Where to
   reach us" block. Two columns on desktop, stacked on a phone. The icon list
   and the map are classic Elementor widgets, so these rules reach through the
   widget wrapper rather than styling the element directly. */
.info-grid {
  display: grid;
  grid-template-columns: 1fr 1.15fr;
  gap: clamp(24px, 4vw, 48px);
  align-items: start;
}
.info-card {
  background: var(--surface);
  border-radius: var(--r-lg);
  box-shadow: var(--sh-1);
  padding: 30px 32px 34px;
}
.info-card h3 { font-size: 1.25rem; margin-bottom: 18px; }

.info-list .elementor-icon-list-item { align-items: center; }
.info-list .elementor-icon-list-icon { color: var(--lagoon); }
.info-list .elementor-icon-list-icon svg,
.info-list .elementor-icon-list-icon i { width: 18px; height: 18px; font-size: 18px; }
.info-list .elementor-icon-list-text {
  color: var(--ink-2);
  font-size: 1rem;
  padding-inline-start: 12px;
}

.info-map { border-radius: var(--r-lg); overflow: hidden; box-shadow: var(--sh-2); }
.info-map iframe { display: block; border: 0; width: 100%; }

@media (max-width: 860px) {
  .info-grid { grid-template-columns: 1fr; }
}

/* 15. Legal pages — Privacy Policy and Terms of Use.
   Long-form prose rather than marketing copy, so the measure is capped near
   68 characters, the line height opens up, and each numbered section is
   separated by a rule instead of the horizontal rules the source used.
   Body text comes from Elementor Text Editor widgets, so these selectors
   reach through .elementor-widget-container rather than styling an element
   directly. */
.legal { max-width: 68ch; margin-inline: auto; }

.legal h1 {
  font-size: clamp(2rem, 4.6vw, 2.7rem);
  line-height: 1.12;
  margin: 0 0 6px;
}

.legal h2 {
  font-family: var(--font-display);
  font-weight: 600;
  letter-spacing: -.02em;
  font-size: clamp(1.18rem, 2.4vw, 1.42rem);
  line-height: 1.28;
  color: var(--ink);
  margin: 0 0 .55em;
  padding-top: 1.5em;
  margin-top: 1.6em;
  border-top: 1px solid var(--edge);
}

.legal h3 {
  font-family: var(--font-display);
  font-weight: 600;
  font-size: 1.02rem;
  letter-spacing: -.01em;
  color: var(--ink);
  margin: 1.7em 0 .45em;
}

.legal p {
  margin: 0 0 1.15em;
  color: var(--ink-2);
  line-height: 1.78;
}

.legal ul { margin: 0 0 1.25em; padding-inline-start: 1.35em; }
.legal li { margin-bottom: .55em; color: var(--ink-2); line-height: 1.72; }
.legal li::marker { color: var(--lagoon); }

.legal strong { color: var(--ink); font-weight: 600; }

.legal a {
  color: var(--lagoon-ink);
  text-decoration: underline;
  text-decoration-thickness: 1px;
  text-underline-offset: 3px;
}
.legal a:hover { color: var(--ink); }

/* Elementor spaces its widgets; the rhythm here comes from the type instead. */
.legal .elementor-widget { margin-bottom: 0; }
.legal .elementor-widget-container > *:last-child { margin-bottom: 0; }

/* .center sets text-align, which does nothing for the items of a flex row.
   A centred action row has to say so on the cross axis too. */
.panel-actions.center { justify-content: center; }

/* 16. Contact CTA — a glass card, so the call to action sits on something
   rather than floating in an empty band. Same frosting as the hero badges. */
.cta-glass {
  position: relative; overflow: hidden;
  border-radius: var(--r-xl);
  background: rgba(255,255,255,.62);
  -webkit-backdrop-filter: blur(18px) saturate(170%);
  backdrop-filter: blur(18px) saturate(170%);
  box-shadow: 0 1px 0 rgba(255,255,255,.9) inset,
              0 0 0 1px rgba(16,50,61,.06),
              var(--sh-2);
}

/* The card sits where the wrap's gutter used to be, so it has to keep that
   gutter itself or it runs into the edge of a phone screen. */
.cta-glass { width: calc(100% - var(--gut) * 2); margin-inline: auto; }

/* Elementor prints its own padding for the container, and it wins on
   specificity, so the card has to claim it back. */
.cta-glass,
.elementor .cta-glass {
  padding: clamp(40px, 5.5vw, 68px) clamp(24px, 4vw, 56px);
}

.cta-glass::before, .cta-glass::after {
  content: ""; position: absolute; border-radius: 50%;
  filter: blur(70px); pointer-events: none;
}
.cta-glass::before { width: 320px; height: 320px; top: -130px; right: -70px; background: var(--lagoon); opacity: .22; }
.cta-glass::after  { width: 260px; height: 260px; bottom: -120px; left: -60px; background: var(--lime); opacity: .2; }
.cta-glass > * { position: relative; z-index: 1; }

/* The card supplies the breathing room; the parts inside can close up. */
.cta-glass .section-head { margin-bottom: 30px; }
.cta-glass .panel-actions { margin-top: 0; }
.cta-glass .muted { margin-top: 20px; }

@media (max-width: 720px) {
  .cta-glass { border-radius: var(--r-lg); }
}

/* The header floats over the page, and a hero is normally what sits behind it.
   A page that opens straight onto a plain section has to leave that room
   itself, or the card slides under the nav. */
.section--headroom, .elementor .section--headroom { padding-top: clamp(124px, 13vw, 168px); }

/* 17. Buttons. The pill was a flat fill with a grey shadow, which read as
   unfinished next to the rest of the page. Each variant now gets a shallow
   gradient and a shadow tinted with its own colour, so the button looks lit
   rather than pasted on. Modifiers are restated here because the fills above
   are shorthand, and shorthand wipes a background-image set later. */
.btn {
  font-weight: 600;
  background-image: linear-gradient(135deg, #17485A 0%, var(--ink) 52%, #0A2831 100%);
  box-shadow: 0 1px 2px rgba(16,50,61,.16), 0 12px 26px -12px rgba(10,111,124,.60);
}
.btn:hover {
  box-shadow: 0 2px 4px rgba(16,50,61,.14), 0 20px 38px -14px rgba(10,111,124,.70);
}

.btn--lime {
  background-image: linear-gradient(135deg, #A3D95C 0%, var(--lime) 55%, #74B02F 100%);
  box-shadow: 0 1px 2px rgba(16,50,61,.12), 0 12px 26px -12px rgba(78,124,30,.60);
}
.btn--lime:hover { box-shadow: 0 2px 4px rgba(16,50,61,.12), 0 20px 38px -14px rgba(78,124,30,.70); }

.btn--lagoon {
  background-image: linear-gradient(135deg, #33C6D6 0%, var(--lagoon) 55%, #0A8A99 100%);
  box-shadow: 0 1px 2px rgba(16,50,61,.12), 0 12px 26px -12px rgba(10,111,124,.60);
}
.btn--lagoon:hover { box-shadow: 0 2px 4px rgba(16,50,61,.12), 0 20px 38px -14px rgba(10,111,124,.70); }

.btn--tang {
  background-image: linear-gradient(135deg, #FF9F45 0%, var(--tangerine) 55%, #DA6B0E 100%);
  box-shadow: 0 1px 2px rgba(16,50,61,.12), 0 12px 26px -12px rgba(168,80,9,.55);
}
.btn--tang:hover { box-shadow: 0 2px 4px rgba(16,50,61,.12), 0 20px 38px -14px rgba(168,80,9,.68); }

/* These three are meant to be flat; keep them that way. */
.btn--ghost, .btn--light, .btn.is-pending { background-image: none; }
.btn--light { box-shadow: var(--sh-1); }
.btn--light:hover { box-shadow: var(--sh-2); }

/* The arrow rides in its own disc, so the button has somewhere to move. The
   glyph is a background here rather than a mask, because a mask would eat the
   disc behind it - hence one arrow drawn light and one drawn dark. */
.btn {
  --btn-arrow: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23ffffff' stroke-width='2.2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M5 12h13M13 6l6 6-6 6'/%3E%3C/svg%3E");
  --btn-disc: rgba(255,255,255,.16);
}
.btn--lime, .btn--lagoon, .btn--tang, .btn--light, .btn--ghost {
  --btn-arrow: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%2310323D' stroke-width='2.2' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M5 12h13M13 6l6 6-6 6'/%3E%3C/svg%3E");
  --btn-disc: rgba(16,50,61,.12);
}

.btn--arrow { padding-right: .5em; }
.btn--arrow::after {
  width: 2em; height: 2em;
  border-radius: 50%;
  -webkit-mask: none; mask: none;
  background: var(--btn-arrow) center / 17px 17px no-repeat, var(--btn-disc);
  transition: transform .2s cubic-bezier(.22,.7,.3,1);
}
.btn--arrow:hover::after { transform: translateX(3px); }
/* Same values for the atomic button, which Elementor skins at two classes. */
.elementor .btn.e-button-base {
  font-weight: 600;
  background-image: linear-gradient(135deg, #17485A 0%, var(--ink) 52%, #0A2831 100%);
  box-shadow: 0 1px 2px rgba(16,50,61,.16), 0 12px 26px -12px rgba(10,111,124,.60);
  transition: transform .2s cubic-bezier(.22,.7,.3,1), box-shadow .2s ease;
}
.elementor .btn.e-button-base:hover {
  transform: translateY(-2px);
  box-shadow: 0 2px 4px rgba(16,50,61,.14), 0 20px 38px -14px rgba(10,111,124,.70);
}
.elementor .btn--lime.e-button-base   { background-image: linear-gradient(135deg, #A3D95C 0%, var(--lime) 55%, #74B02F 100%); }
.elementor .btn--lagoon.e-button-base { background-image: linear-gradient(135deg, #33C6D6 0%, var(--lagoon) 55%, #0A8A99 100%); }
.elementor .btn--tang.e-button-base   { background-image: linear-gradient(135deg, #FF9F45 0%, var(--tangerine) 55%, #DA6B0E 100%); }
.elementor .btn--light.e-button-base,
.elementor .btn--ghost.e-button-base  { background-image: none; }

/* The card's call to action is the one thing on the page, so it can afford
   to be bigger than a button in a row of them. */
.cta-glass .btn,
.elementor .cta-glass .btn.e-button-base {
  font-size: 1.06rem;
  padding: .98em 1.2em .98em 2em;
}

/* 18. The arrow goes back to a plain glyph. The disc read as a different
   button from the one in the header, and those two should match. */
.btn--arrow { padding-right: 1.7em; }
.btn--arrow::after {
  width: 18px; height: 18px;
  border-radius: 0;
  background: currentColor;
  -webkit-mask: var(--arrow) center / contain no-repeat;
          mask: var(--arrow) center / contain no-repeat;
  transition: transform .2s ease;
}

/* 19. Glassy hover. Where a button sits on blue - the hero wash, a tinted
   band, or the dark panel - hovering frosts it rather than only lifting it.
   Each rule is restated for the atomic button, which Elementor skins at two
   classes and would otherwise keep its gradient through the hover. */
.hero .btn:hover,
.section--tint .btn:hover,
.elementor .hero .btn.e-button-base:hover,
.elementor .section--tint .btn.e-button-base:hover {
  background-color: rgba(255,255,255,.58);
  background-image: none;
  color: var(--ink);
  -webkit-backdrop-filter: blur(14px) saturate(175%);
          backdrop-filter: blur(14px) saturate(175%);
  box-shadow: 0 1px 0 rgba(255,255,255,.9) inset,
              0 0 0 1px rgba(16,50,61,.10),
              var(--sh-2);
}

/* The panel is deep blue, so the glass there is a light film, not a light fill. */
.panel .btn:hover,
.elementor .panel .btn.e-button-base:hover {
  background-color: rgba(255,255,255,.20);
  background-image: none;
  color: #fff;
  -webkit-backdrop-filter: blur(14px) saturate(160%);
          backdrop-filter: blur(14px) saturate(160%);
  box-shadow: 0 1px 0 rgba(255,255,255,.30) inset,
              0 0 0 1px rgba(255,255,255,.24),
              var(--sh-2);
}

/* 20. Link colours on hover.

   The parent theme's reset paints every anchor `a:active, a:hover { color:
   #333366 }`. That is one class + one pseudo-class, which outranks .btn's own
   single class, so hovering a white-on-dark button turned its label blue while
   the fill stayed dark. Every button and link variant pins its colour through
   all four link states. */
.btn, .btn:link, .btn:visited, .btn:hover, .btn:focus, .btn:active { color: #fff; }

.btn--lime,   .btn--lime:hover,   .btn--lime:focus,   .btn--lime:active,
.btn--lagoon, .btn--lagoon:hover, .btn--lagoon:focus, .btn--lagoon:active,
.btn--tang,   .btn--tang:hover,   .btn--tang:focus,   .btn--tang:active,
.btn--light,  .btn--light:hover,  .btn--light:focus,  .btn--light:active,
.btn--ghost,  .btn--ghost:hover,  .btn--ghost:focus,  .btn--ghost:active { color: var(--ink); }

.textlink:hover, .textlink:focus, .textlink:active { color: var(--ink); }
.arrowlink:hover, .arrowlink:focus, .arrowlink:active { color: var(--lagoon-ink); }
a.chip:hover, a.chip:focus, a.chip:active { color: var(--ink); }

/* 21. Hovering a button should change the button, not only its shadow. The
   fill lightens; on a blue ground the glass rules above take over instead. */
.btn:hover,
.elementor .btn.e-button-base:hover {
  background-image: linear-gradient(135deg, #1E5E74 0%, #164A5B 55%, #103642 100%);
}
.btn--lime:hover,
.elementor .btn--lime.e-button-base:hover   { background-image: linear-gradient(135deg, #B0E06B 0%, #97D14C 55%, #83C13B 100%); }
.btn--lagoon:hover,
.elementor .btn--lagoon.e-button-base:hover { background-image: linear-gradient(135deg, #48D2E1 0%, #1CB9C9 55%, #0FA0B0 100%); }
.btn--tang:hover,
.elementor .btn--tang.e-button-base:hover   { background-image: linear-gradient(135deg, #FFAE5E 0%, #FA8F2E 55%, #EC7C16 100%); }
.btn--light:hover  { background-color: #F3FAFA; background-image: none; }
.btn--ghost:hover  { background-color: var(--surface); background-image: none; }

/* 22. The nav's current page is a solid pill, so it needs a hover of its own -
   the plain-link hover underneath it changes nothing visible. */
.nav a[aria-current="page"]:hover,
.nav a[aria-current="page"]:focus { background: #1B5265; color: #fff; }

/* 23. A button on a white card that happens to sit inside a tinted band is
   not on blue. Frosting it there made it fade into the card, so those go back
   to the solid hover. */
.join-panel .btn:hover, .plan .btn:hover, .tile .btn:hover,
.elementor .join-panel .btn.e-button-base:hover,
.elementor .plan .btn.e-button-base:hover {
  background-color: transparent;
  background-image: linear-gradient(135deg, #1E5E74 0%, #164A5B 55%, #103642 100%);
  color: #fff;
  -webkit-backdrop-filter: none; backdrop-filter: none;
  box-shadow: 0 2px 4px rgba(16,50,61,.14), 0 20px 38px -14px rgba(10,111,124,.70);
}
.join-panel .btn--lime:hover, .plan .btn--lime:hover, .tile .btn--lime:hover,
.elementor .join-panel .btn--lime.e-button-base:hover,
.elementor .plan .btn--lime.e-button-base:hover {
  background-image: linear-gradient(135deg, #B0E06B 0%, #97D14C 55%, #83C13B 100%);
  color: var(--ink);
  box-shadow: 0 2px 4px rgba(16,50,61,.12), 0 20px 38px -14px rgba(78,124,30,.70);
}
.join-panel .btn--light:hover, .plan .btn--light:hover,
.join-panel .btn--ghost:hover, .plan .btn--ghost:hover {
  background-color: var(--surface); background-image: none; color: var(--ink);
}

/* 24. The sticky phone button sat low and small with a flat grey shadow, so it
   read as a different, plainer button than the rest. Same glow as the others,
   a size up, and lifted clear of the bottom edge (and of the home indicator on
   iPhones). */
.mobile-cta {
  right: 16px;
  bottom: calc(24px + env(safe-area-inset-bottom, 0px));
}
.mobile-cta .btn {
  font-size: 1rem;
  padding: .88em 1.45em;
  gap: .5em;
  box-shadow: 0 2px 4px rgba(16,50,61,.16),
              0 16px 34px -12px rgba(10,111,124,.70);
}
.mobile-cta .btn:hover,
.mobile-cta .btn:active {
  box-shadow: 0 2px 6px rgba(16,50,61,.18),
              0 22px 44px -14px rgba(10,111,124,.78);
}
.mobile-cta .btn::after { width: 17px; height: 17px; }

/* 25. The blog.

   Cards, article header and prose, all built from the same tokens as the rest
   of the site so a post does not read as a different website. The body reuses
   .legal's prose rules and only adds what an article needs on top. */
.post-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 26px;
  align-items: start;
}

.post-card {
  display: flex; flex-direction: column;
  overflow: hidden;
  border-radius: var(--r-lg);
  background: var(--surface);
  box-shadow: var(--sh-1);
  transition: transform .3s cubic-bezier(.22,.7,.3,1), box-shadow .3s ease;
}
.post-card:hover { transform: translateY(-4px); box-shadow: var(--sh-2); }

.post-card-media {
  display: block; aspect-ratio: 16 / 10;
  background: var(--lagoon-wash);
  overflow: hidden;
}
.post-card-media img { width: 100%; height: 100%; object-fit: cover; display: block; }
.post-card-fallback {
  display: block; width: 100%; height: 100%;
  background: linear-gradient(135deg, var(--lagoon-wash), var(--lime-wash));
}

.post-card-body { padding: 24px 26px 28px; display: flex; flex-direction: column; gap: 10px; flex: 1; }
.post-card-body h3 {
  font-family: var(--font-display); font-weight: 600;
  font-size: 1.22rem; line-height: 1.25; letter-spacing: -.02em;
  margin: 0;
}
.post-card-body h3 a { color: var(--ink); text-decoration: none; }
.post-card-body h3 a:hover,
.post-card-body h3 a:focus { color: var(--lagoon-ink); }
.post-card-excerpt { color: var(--ink-2); margin: 0; font-size: .96rem; line-height: 1.6; }

.post-meta {
  margin: auto 0 0; padding-top: 4px;
  color: var(--ink-3); font-size: .84rem;
  display: flex; align-items: center; gap: .5em; flex-wrap: wrap;
}

/* --- One article ------------------------------------------------------- */
.post-head { text-align: center; margin-bottom: 34px; }
.post-head h1 {
  font-family: var(--font-display); font-weight: 600;
  font-size: clamp(2rem, 4.4vw, 3.1rem); line-height: 1.12; letter-spacing: -.03em;
  margin: 12px 0 14px;
}
.post-head .post-meta { justify-content: center; }

.post-hero {
  margin: 0 0 38px;
  border-radius: var(--r-lg);
  overflow: hidden;
  box-shadow: var(--sh-2);
}
.post-hero img { display: block; width: 100%; height: auto; }

.post-body > *:first-child { margin-top: 0; }
.post-body img { border-radius: var(--r-sm); height: auto; }
.post-body figure { margin: 30px 0; }
.post-body figcaption { color: var(--ink-3); font-size: .86rem; text-align: center; margin-top: 10px; }
.post-body blockquote {
  margin: 30px 0; padding: 4px 0 4px 22px;
  border-left: 3px solid var(--lime);
  color: var(--ink); font-size: 1.08rem;
}
.post-body blockquote p:last-child { margin-bottom: 0; }

.post-back { margin-top: 42px; }

/* --- Between articles --------------------------------------------------- */
.post-nav { display: grid; grid-template-columns: 1fr 1fr; gap: 20px; }
.post-nav-item {
  display: block; padding: 22px 26px;
  border-radius: var(--r); background: var(--surface);
  box-shadow: var(--sh-1); text-decoration: none;
  transition: transform .3s cubic-bezier(.22,.7,.3,1), box-shadow .3s ease;
}
.post-nav-item:hover { transform: translateY(-3px); box-shadow: var(--sh-2); }
.post-nav-item--next { text-align: right; }
.post-nav-label { display: block; color: var(--ink-3); font-size: .8rem; letter-spacing: .08em; text-transform: uppercase; }
.post-nav-title { display: block; margin-top: 6px; color: var(--ink); font-family: var(--font-display); font-weight: 600; line-height: 1.3; }

/* --- Pagination --------------------------------------------------------- */
.pager { margin-top: 48px; }
.pager .nav-links { display: flex; justify-content: center; align-items: center; gap: 8px; flex-wrap: wrap; }
.pager .page-numbers {
  display: grid; place-items: center;
  min-width: 42px; height: 42px; padding: 0 14px;
  border-radius: 999px; text-decoration: none;
  color: var(--ink); background: var(--surface); box-shadow: var(--sh-1);
}
.pager .page-numbers:hover { background: #F3FAFA; }
.pager .page-numbers.current { background: var(--ink); color: #fff; }
.pager .page-numbers.dots { background: none; box-shadow: none; }

@media (max-width: 1000px) {
  .post-grid { grid-template-columns: repeat(2, 1fr); }
}
@media (max-width: 720px) {
  .post-grid { grid-template-columns: 1fr; }
  .post-nav { grid-template-columns: 1fr; }
  .post-nav-item--next { text-align: left; }
}

/* 26. Self-hosted type.

   Both families are variable fonts, so the whole weight range is one file each
   - 65 KB for the pair, against two round trips to fonts.googleapis.com and
   fonts.gstatic.com before a single character could paint. Latin subset only:
   the site is English, and the system stack catches anything outside it. */
@font-face {
  font-family: 'Sora';
  font-style: normal;
  font-weight: 400 700;
  font-display: swap;
  src: url('../fonts/sora-var.woff2') format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}
@font-face {
  font-family: 'Lexend';
  font-style: normal;
  font-weight: 300 600;
  font-display: swap;
  src: url('../fonts/lexend-var.woff2') format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+0304, U+0308, U+0329, U+2000-206F, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD;
}

/* 27. Label grey, darkened.

   --ink-3 was #6B858D, which measures 3.4:1 behind the eyebrow labels and
   3.9:1 behind post dates - under the 4.5:1 that text this size needs, and a
   failed contrast audit on every page of the site. #4E666E is the same grey,
   two steps down: 6.1:1 on white and 5.2:1 on the tinted ground. */
:root { --ink-3: #4E666E; }

/* 29. A section head's heading can now be an h1 - the contact page and the
   blog index have no other title - so it takes the h2 size there rather than
   hero size, which would overwhelm a page whose job is one card. */
.section-head h1 { font-size: clamp(2rem, 3.9vw, 3rem); font-weight: 600; }

/* 30. The eyebrow label sits over the hero's aurora, where the local
   background can be as light as #7cd0d8 - and --ink-3 measures 3.44:1 against
   that. This grey is dark enough for the aurora (4.7:1) without reading as
   body copy on the plain ground (8.3:1). */
.eyebrow { color: #35525B; }

/* Card titles are h2 now, so the blog index does not jump h1 -> h3. They keep
   the size they had. */
.post-card-body h2 {
  font-family: var(--font-display); font-weight: 600;
  font-size: 1.22rem; line-height: 1.25; letter-spacing: -.02em;
  margin: 0;
}
.post-card-body h2 a { color: var(--ink); text-decoration: none; }
.post-card-body h2 a:hover,
.post-card-body h2 a:focus { color: var(--lagoon-ink); }

/* 31. Founder biographies on the About page. Long-form text in a tile that
   was built for a name and a role, so it needs its own measure and rhythm. */
.tile-body .bio {
  margin: 14px 0 0;
  color: var(--ink-2);
  font-size: .96rem;
  line-height: 1.68;
}

/* 32. A menu item with children.

   Resources now opens onto Recipes and Workouts. On a pointer device the
   submenu drops on hover; on a phone the nav is already a stack, so the two
   simply sit indented underneath and no tap is wasted opening anything. */
.nav li { position: relative; }

.nav .sub-menu {
  list-style: none; margin: 0; padding: 8px;
  position: absolute; top: calc(100% + 10px); left: 50%;
  translate: -50% 0;
  min-width: 190px;
  display: grid; gap: 2px;
  border-radius: var(--r-sm);
  background: rgba(255,255,255,.92);
  -webkit-backdrop-filter: blur(16px) saturate(170%);
          backdrop-filter: blur(16px) saturate(170%);
  box-shadow: 0 1px 0 rgba(255,255,255,.9) inset, 0 0 0 1px rgba(16,50,61,.07), var(--sh-2);
  opacity: 0; visibility: hidden;
  translate: -50% 6px;
  transition: opacity .18s ease, translate .18s ease, visibility .18s;
  z-index: 60;
}

/* The gap between the item and the panel would drop the hover, so the panel
   reaches up to meet it with a transparent lip. */
.nav .sub-menu::before {
  content: ""; position: absolute; left: 0; right: 0; top: -12px; height: 12px;
}

.nav li:hover > .sub-menu,
.nav li:focus-within > .sub-menu {
  opacity: 1; visibility: visible; translate: -50% 0;
}

.nav .sub-menu a { white-space: nowrap; }

/* A quiet chevron, so it is obvious the item has more behind it. */
.nav .menu-item-has-children > a::after {
  content: ""; display: inline-block;
  width: 9px; height: 9px; margin-left: .45em;
  border-right: 2px solid currentColor; border-bottom: 2px solid currentColor;
  rotate: 45deg; translate: 0 -2px;
  opacity: .55;
  transition: rotate .2s ease, translate .2s ease;
}
.nav li:hover > a::after { rotate: -135deg; translate: 0 2px; }

@media (max-width: 1080px) {
  /* Stacked already: show both children, indented, and drop the chevron. */
  .nav .sub-menu {
    position: static; translate: none;
    opacity: 1; visibility: visible;
    min-width: 0; padding: 2px 0 6px 14px;
    background: none; box-shadow: none;
    -webkit-backdrop-filter: none; backdrop-filter: none;
  }
  .nav .sub-menu::before { display: none; }
  .nav .menu-item-has-children > a::after { display: none; }
  .nav .sub-menu a { font-size: .96rem; opacity: .9; }
}

/* 33. Founder portraits.

   The card already carries the shadow and the rounding; a second shadow on
   the photo inside it reads as a sticker stuck to the card. The portrait is a
   flat circle instead, centred over the name it belongs to, which is how the
   rest of the site treats a face. */
.page-id-33 .duo .tile > :first-child:has(img) {
  padding: 30px 28px 0;
  display: flex; justify-content: center;
}
.page-id-33 .duo .tile img {
  width: 116px; height: 116px;
  object-fit: cover; object-position: center 30%;
  border-radius: 50%;
  box-shadow: none;
}

/* The photo and the name belong together, so close the gap the banner left. */
.page-id-33 .duo .tile .tile-body { padding-top: 18px; }

@media (max-width: 680px) {
  .page-id-33 .duo .tile img { width: 112px; height: 112px; }
}

/* The media box above a tile is a 4:3 banner, which leaves a tall empty block
   once the photo inside it is a small square. On the team cards it shrinks to
   fit the portrait. */
.page-id-33 .duo .tile-media {
  aspect-ratio: auto;
  padding: 30px 28px 0;
  display: flex; justify-content: center;
}

/* With the portrait centred, the name and role read better centred too; the
   biography stays ranged left so it is still comfortable to read. */
.page-id-33 .duo .tile-body { text-align: center; }
.page-id-33 .duo .tile-body .bio { text-align: left; }

/* 34. The Kidzy logo at the top of About. It links home, so it needs to feel
   like a target without behaving like a button. */
.about-logo { padding-bottom: 0; }
.about-logo .wrap { display: flex; justify-content: center; }
.about-logo img {
  width: min(420px, 78vw); height: auto;
  transition: transform .25s cubic-bezier(.22,.7,.3,1);
}
.about-logo a { display: inline-block; line-height: 0; }
.about-logo a:hover img { transform: translateY(-3px) scale(1.02); }

/* 35. The Resources hub tiles.

   Eat and Move each open on a photo now. They are the only .duo cards with a
   full-width banner, so they take the same 4:3 media box and the same lift on
   hover as the mission tiles on the home page rather than the portrait
   treatment above. */
.page-id-35 .duo .tile { overflow: hidden; }
.page-id-35 .duo .tile-media {
  aspect-ratio: 16 / 10;
  border-radius: 0;
}
.page-id-35 .duo .tile-media img {
  width: 100%; height: 100%;
  object-fit: cover; object-position: center 45%;
  border-radius: 0;
}
.page-id-35 .duo .tile:hover .tile-media img { transform: scale(1.04); }

@media (max-width: 680px) {
  .page-id-35 .duo .tile-media { aspect-ratio: 16 / 9; }
}

/* 36. Event cards.

   These reuse .partner for the surface, shadow and hover lift, but they carry
   a photograph rather than a logo. The base .partner-logo is a fixed 128px
   well with centred, contained content, so every part of that has to be
   undone: the height, the padding, the centring and the img sizing. The
   negative margins cancel .partner's padding, which changes at 720px. */
.page-id-36 .partner { overflow: hidden; }
.page-id-36 .partner-logo {
  margin: -26px -28px 20px;
  padding: 0;
  width: auto;
  height: auto;
  aspect-ratio: 16 / 10;
  border-radius: var(--r-lg) var(--r-lg) 0 0;
  overflow: hidden;
  background: var(--lagoon-wash);
  display: grid;
  place-items: stretch;
}
/* Elementor wraps the image in its own element, which would otherwise shrink
   to the photo and leave the box half empty. */
.page-id-36 .partner-logo > * { min-width: 0; min-height: 0; height: 100%; }
.page-id-36 .partner-logo img {
  display: block;
  width: 100%; height: 100%;
  max-height: none;
  object-fit: cover;
  transition: transform .6s cubic-bezier(.22,.7,.3,1);
}
.page-id-36 .partner:hover .partner-logo img { transform: scale(1.04); }

/* The button sits at the foot of the card, left aligned like the others. */
.page-id-36 .partner .btn { align-self: flex-start; margin-top: auto; }

@media (max-width: 720px) {
  .page-id-36 .partner-logo { margin: -22px -22px 18px; }
}

/* 37. Plans, as three equals.

   The middle card no longer carries the featured ring, the badge or the
   upward offset, so nothing is permanently mid-hover. The three also held
   different heights, because .plans starts them at the top and the copy is
   not the same length. Stretching them matches every other card row on the
   site. The button lives inside a .plan-cta wrapper, so that is what gets
   pushed to the foot, and the selectors carry .elementor because the builder
   sets display on the container itself. */
.plans { align-items: stretch; }
.elementor .plans > .plan { display: flex; flex-direction: column; }
.elementor .plans > .plan > .plan-cta { margin-top: auto; }

/* 38. Mission tiles, given the recipe-card treatment.

   The recipe cards on /recipes/ carry the whole thing: a lift, a shadow tinted
   with the card's own colour, a wash of that colour up the bottom of the photo,
   the photo easing in, and the arrow stepping right. The home tiles had none of
   it, so they read as placeholders next to it.

   They also had no resting shadow at all: .e-con sets box-shadow: none and
   loads after this file, so it beat the single-class .tile rule. Every shadow
   here is therefore written as .elementor .tile, which outranks it. */

.tile--lime   { --accent-ink: var(--lime-ink);   }
.tile--tang   { --accent-ink: var(--tang-ink);   }
.tile--lagoon { --accent-ink: var(--lagoon-ink); }
.tile--ember  { --accent-ink: var(--ember-ink);  }

.elementor .tile { box-shadow: var(--sh-1); }

/* The coloured glow sits under a small neutral shadow, so the card keeps a
   defined edge and the colour reads as light rather than as a border. */
.elementor .tile:hover {
  transform: translateY(-5px);
  box-shadow: 0 2px 6px rgba(16,50,61,.08),
              0 13px 23px -10px var(--accent, var(--lagoon));
}
.tile:hover .tile-media img { transform: scale(1.05); }

/* No colour wash over the photo here. The recipe cards use one because the
   card is small and the tint is what identifies the meal; these photographs
   are large and carry the page, so they are left alone. */

/* The whole tile is the link, so the arrow answers a hover anywhere on the
   card rather than only on the words themselves. */
.tile .arrowlink { color: var(--accent-ink, var(--lagoon-ink)); }
.tile:hover .arrowlink::after { transform: translateX(4px); }

/* 39. The what's-on list on the Events page.

   Wider rows rather than a three-up grid: an event has a date, a time and a
   place to carry, which a narrow card cannot hold without wrapping badly. The
   photo takes a fixed column beside the text and collapses above it on a
   phone. The date sits on the photo so the day is readable while scanning. */
.ev-list { display: grid; gap: 20px; }

.ev-card {
  display: grid;
  grid-template-columns: 300px 1fr;
  align-items: stretch;
  overflow: hidden;
  border-radius: var(--r-lg);
  background: var(--surface);
  box-shadow: var(--sh-1);
  transition: transform .3s cubic-bezier(.22,.7,.3,1), box-shadow .3s ease;
}
.ev-card:hover {
  transform: translateY(-4px);
  box-shadow: 0 2px 6px rgba(16,50,61,.08),
              0 13px 23px -10px var(--ev, var(--lagoon));
}

/* One colour per kind of session, matching the three cards below. */
.ev-workshop { --ev: var(--lagoon);    --ev-ink: var(--lagoon-ink); }
.ev-seminar  { --ev: var(--tangerine); --ev-ink: var(--tang-ink);   }
.ev-cooking  { --ev: var(--lime);      --ev-ink: var(--lime-ink);   }

.ev-media { position: relative; overflow: hidden; background: var(--lagoon-wash); }
.ev-media img {
  width: 100%; height: 100%; object-fit: cover; display: block;
  transition: transform .6s cubic-bezier(.22,.7,.3,1);
}
.ev-card:hover .ev-media img { transform: scale(1.04); }

/* The date block. Lifted off the photo rather than printed on it, so it stays
   readable whatever the photo happens to be. */
.ev-when {
  position: absolute; left: 14px; top: 14px;
  margin: 0; padding: 8px 12px 7px;
  display: grid; justify-items: center; line-height: 1;
  border-radius: var(--r-sm);
  background: rgba(255,255,255,.94);
  -webkit-backdrop-filter: blur(8px); backdrop-filter: blur(8px);
  box-shadow: var(--sh-1);
  color: var(--ev-ink, var(--lagoon-ink));
}
.ev-day   { font-family: var(--font-display); font-weight: 700; font-size: 1.32rem; }
.ev-month { font-size: .7rem; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; margin-top: 3px; }

.ev-body { padding: 26px 30px 28px; display: flex; flex-direction: column; gap: 9px; }
.ev-kind {
  margin: 0;
  font-family: var(--font-display); font-weight: 600;
  font-size: .76rem; letter-spacing: .16em; text-transform: uppercase;
  color: var(--ev-ink, var(--lagoon-ink));
}
.ev-body h3 { font-size: 1.32rem; margin: 0; }
.ev-meta  { margin: 0; font-size: .92rem; color: var(--ink-2); font-weight: 500; }
.ev-blurb { margin: 0; font-size: .98rem; color: var(--ink-2); }
.ev-body .btn { align-self: flex-start; margin-top: 10px; }

@media (max-width: 760px) {
  .ev-card { grid-template-columns: 1fr; }
  .ev-media { aspect-ratio: 16 / 9; }
  .ev-body { padding: 22px 24px 26px; }
}
