/* ==================================================================
   SCALING AFRICA — Editorial Stylesheet
   ------------------------------------------------------------------
   Table of contents:
   0. Local fonts
   1. Design tokens
   2. Reset & base
   3. Layout utilities
   4. Type utilities
   5. Buttons & links
   6. Header & navigation
   7. Hero
   8. The African Paradox
   9. About the book
   10. What's inside (table of contents)
   11. Author
   12. Reviews
   13. Interest form
   14. Purchase CTA
   15. Footer
   16. Image fallback placeholders
   17. Scroll reveal & motion
   18. Responsive adjustments
   19. "Coming Soon" modal
   ================================================================== */

/* ---------- 0. Local fonts ----------
   Ambit is the book's own display typeface (matches the cover
   treatment) — self-hosted from /assets/fonts. Only Regular and Bold
   are supplied, so the display type scale below uses just those two
   weights. */
@font-face {
  font-family: "Ambit";
  src: url("../assets/fonts/Ambit-Regular.otf") format("opentype");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}

@font-face {
  font-family: "Ambit";
  src: url("../assets/fonts/Ambit-Bold.otf") format("opentype");
  font-weight: 700;
  font-style: normal;
  font-display: swap;
}

/* ---------- 1. Design tokens ----------
   Accent green (#7CBD3F) and ink navy (#041C36) are sampled directly
   from the real book cover, so the site reads as one product with it.
   --color-accent is a deepened, AA-contrast-safe working shade for
   text/borders on light backgrounds; --color-accent-vivid is the true
   cover green, reserved for large fills, icons, and dark-background use
   where its contrast is verified to hold up. */
:root {
  /* Color */
  --color-bg: #f7f6f1;
  --color-bg-alt: #ecebe2;
  --color-surface: #fffefb;
  --color-ink: #0a1d30;
  --color-ink-soft: #47576a;
  --color-ink-faint: #7c8998;
  --color-line: rgba(4, 28, 54, 0.12);
  --color-line-strong: rgba(4, 28, 54, 0.22);
  --color-accent: #4e7a22;
  --color-accent-dark: #3a5c19;
  --color-accent-soft: #9fcb6c;
  --color-accent-vivid: #7cbd3f;
  --color-dark-bg: #071726;
  --color-dark-surface: #102a42;
  --color-dark-ink: #f6f2ea;
  --color-dark-ink-soft: rgba(246, 242, 234, 0.68);
  --color-dark-line: rgba(246, 242, 234, 0.16);
  --color-amazon-orange: #ff9900;
  --color-amazon-orange-dark: #e88a00;
  --color-amazon-ink: #131a22;

  /* Type */
  --font-display: "Ambit", "Century Gothic", "Futura", -apple-system,
    sans-serif;
  --font-sans: "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI",
    Helvetica, Arial, sans-serif;

  /* Layout */
  --container-max: 1320px;
  --container-pad: clamp(1.25rem, 4vw, 3.5rem);
  --radius-sm: 2px;
  --radius-md: 4px;

  /* Motion */
  --ease-editorial: cubic-bezier(0.22, 1, 0.36, 1);
  --dur-base: 0.6s;
}

/* ---------- 2. Reset & base ---------- */
*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  scroll-behavior: smooth;
}

@media (prefers-reduced-motion: reduce) {
  html {
    scroll-behavior: auto;
  }
  *,
  *::before,
  *::after {
    animation-duration: 0.001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.001ms !important;
    scroll-behavior: auto !important;
  }
}

body {
  margin: 0;
  background: var(--color-bg);
  color: var(--color-ink);
  font-family: var(--font-sans);
  font-size: 16px;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  text-rendering: optimizeLegibility;
  /* Safety net for any section that deliberately bleeds an image past
     its column (see .about-book__image). Deliberately on <body>, not
     on the section itself: overflow other than "visible" on ANY other
     ancestor turns that ancestor into the scrolling container that
     position:sticky descendants resolve against, breaking their
     stickiness — body/html doesn't have this problem since the
     document scroll IS the root scrolling context regardless. */
  overflow-x: hidden;
}

img {
  max-width: 100%;
  height: auto;
  display: block;
}

a {
  color: inherit;
  text-decoration: none;
}

button {
  font: inherit;
  color: inherit;
  background: none;
  border: 0;
  cursor: pointer;
}

ul {
  list-style: none;
  margin: 0;
  padding: 0;
}

h1,
h2,
h3,
h4,
p,
figure {
  margin: 0;
}

input,
select,
textarea {
  font: inherit;
  color: inherit;
}

.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;
}

.skip-link {
  position: fixed;
  top: -100%;
  left: 1rem;
  z-index: 1000;
  background: var(--color-ink);
  color: var(--color-bg);
  padding: 0.75rem 1.25rem;
  border-radius: var(--radius-sm);
  font-size: 0.875rem;
  transition: top 0.2s var(--ease-editorial);
}

.skip-link:focus {
  top: 1rem;
}

:focus-visible {
  outline: 2px solid var(--color-accent);
  outline-offset: 3px;
}

/* ---------- 3. Layout utilities ---------- */
.container {
  max-width: var(--container-max);
  margin-inline: auto;
  padding-inline: var(--container-pad);
}

section {
  position: relative;
}

.section-pad {
  padding-block: clamp(4.5rem, 9vw, 8.5rem);
}

.section-pad-tight {
  padding-block: clamp(3rem, 6vw, 5.5rem);
}

.grid-split {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: clamp(2.5rem, 6vw, 6rem);
  align-items: center;
}

.grid-split--reverse .grid-split__visual {
  order: 2;
}

/* ---------- 4. Type utilities ---------- */
.eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 0.6em;
  font-family: var(--font-sans);
  font-size: 0.75rem;
  font-weight: 600;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--color-accent);
}

.eyebrow::before {
  content: "";
  width: 1.75em;
  height: 1px;
  background: currentColor;
}

.heading-display {
  font-family: var(--font-display);
  font-weight: 700;
  line-height: 1.06;
  letter-spacing: -0.01em;
  font-size: clamp(2.5rem, 5.2vw, 4.5rem);
}

.heading-lg {
  font-family: var(--font-display);
  font-weight: 700;
  line-height: 1.12;
  letter-spacing: -0.01em;
  font-size: clamp(2rem, 3.6vw, 3.1rem);
}

.heading-md {
  font-family: var(--font-display);
  font-weight: 700;
  line-height: 1.2;
  font-size: clamp(1.4rem, 2vw, 1.85rem);
}

.body-lg {
  font-size: clamp(1.05rem, 1.4vw, 1.25rem);
  line-height: 1.7;
  color: var(--color-ink-soft);
}

.body-base {
  font-size: 1rem;
  line-height: 1.7;
  color: var(--color-ink-soft);
}

.text-center {
  text-align: center;
}

.section-intro {
  max-width: 46rem;
}

.section-intro--center {
  margin-inline: auto;
  text-align: center;
}

.section-head {
  display: flex;
  flex-direction: column;
  gap: 1.1rem;
  margin-bottom: clamp(2.5rem, 5vw, 4rem);
}

/* ---------- 5. Buttons & links ---------- */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.6rem;
  padding: 0.95rem 1.9rem;
  font-family: var(--font-sans);
  font-size: 0.95rem;
  font-weight: 600;
  letter-spacing: 0.01em;
  border-radius: var(--radius-sm);
  border: 1px solid transparent;
  white-space: nowrap;
  transition: background-color 0.25s var(--ease-editorial),
    color 0.25s var(--ease-editorial), border-color 0.25s var(--ease-editorial),
    transform 0.25s var(--ease-editorial);
}

.btn:hover {
  transform: translateY(-1px);
}

.btn:active {
  transform: translateY(0) scale(0.98);
  transition-duration: 0.1s;
}

.btn--primary {
  background: var(--color-ink);
  color: var(--color-bg);
}

.btn--primary:hover {
  background: var(--color-accent-dark);
}

.btn--secondary {
  background: transparent;
  border-color: var(--color-line-strong);
  color: var(--color-ink);
}

.btn--secondary:hover {
  border-color: var(--color-ink);
}

/* The final purchase CTA only — every other "Buy the Book" button
   stays the site's normal btn--primary. --color-amazon-orange is
   Amazon's own brand orange. .btn__icon--amazon traces the real
   Amazon wordmark (see assets/brand/amazon-logo-full-color.svg) but
   flattens it to one currentColor, since the logo's usual orange
   smile would disappear against this button's orange background. */
.btn--amazon {
  background: var(--color-amazon-orange);
  color: var(--color-amazon-ink);
}

.btn--amazon:hover {
  background: var(--color-amazon-orange-dark);
}

.btn__icon {
  width: 1.15em;
  height: 1.15em;
  flex-shrink: 0;
}

.btn__icon--amazon {
  width: 4.8em;
  height: 1.45em; /* matches the icon-amazon symbol's 603:182 viewBox ratio */
  flex-shrink: 0;
}

.btn--small {
  padding: 0.65rem 1.35rem;
  font-size: 0.85rem;
}

.btn--block {
  width: 100%;
}

.text-link {
  display: inline-flex;
  align-items: center;
  gap: 0.4rem;
  font-weight: 600;
  font-size: 0.95rem;
  border-bottom: 1px solid var(--color-line-strong);
  padding-bottom: 0.15rem;
  transition: border-color 0.25s var(--ease-editorial),
    color 0.25s var(--ease-editorial);
}

.text-link:hover {
  color: var(--color-accent);
  border-color: var(--color-accent);
}

.text-link__arrow {
  display: inline-block;
  transition: transform 0.25s var(--ease-editorial);
}

.text-link:hover .text-link__arrow {
  transform: translateX(3px);
}

/* ---------- 6. Header & navigation ---------- */
.site-header {
  position: sticky;
  top: 0;
  z-index: 100;
  background: rgba(247, 246, 241, 0.86);
  backdrop-filter: saturate(140%) blur(10px);
  -webkit-backdrop-filter: saturate(140%) blur(10px);
  border-bottom: 1px solid transparent;
  transition: border-color 0.3s var(--ease-editorial),
    box-shadow 0.3s var(--ease-editorial);
}

.site-header--scrolled {
  border-color: var(--color-line);
  box-shadow: 0 8px 24px -20px rgba(23, 20, 15, 0.35);
}

.header__inner {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1.5rem;
  padding-block: 1.15rem;
}

.wordmark {
  display: inline-flex;
  align-items: center;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 1.15rem;
  letter-spacing: 0.02em;
  text-decoration: none;
  white-space: nowrap;
}

/* The header uses the real wordmark artwork (assets/brand/); the
   footer keeps styled text since the artwork's navy half disappears
   against the footer's dark background. */
.wordmark img {
  height: 26px;
  width: auto;
  display: block;
}

.nav {
  display: none;
}

.nav ul {
  display: flex;
  gap: clamp(1.25rem, 2vw, 2.25rem);
}

.nav a {
  position: relative;
  display: inline-block;
  font-size: 0.92rem;
  font-weight: 500;
  text-decoration: none;
  color: var(--color-ink-soft);
  transition: color 0.2s var(--ease-editorial);
}

.nav a::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  bottom: -4px;
  height: 1px;
  background: currentColor;
  transform: scaleX(0);
  transform-origin: left;
  transition: transform 0.25s var(--ease-editorial);
}

.nav a:hover {
  color: var(--color-ink);
}

.nav a:hover::after {
  transform: scaleX(1);
}

.header__actions {
  display: flex;
  align-items: center;
  gap: 0.75rem;
}

.header__actions .btn {
  display: none;
}

.menu-toggle {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 2.5rem;
  height: 2.5rem;
}

.menu-toggle__bars,
.menu-toggle__bars::before,
.menu-toggle__bars::after {
  display: block;
  width: 22px;
  height: 1.5px;
  background: var(--color-ink);
  position: relative;
  transition: transform 0.25s var(--ease-editorial);
}

.menu-toggle__bars::before,
.menu-toggle__bars::after {
  content: "";
  position: absolute;
  left: 0;
}

.menu-toggle__bars::before {
  top: -7px;
}

.menu-toggle__bars::after {
  top: 7px;
}

.menu-toggle[aria-expanded="true"] .menu-toggle__bars {
  background: transparent;
}

.menu-toggle[aria-expanded="true"] .menu-toggle__bars::before {
  top: 0;
  transform: rotate(45deg);
}

.menu-toggle[aria-expanded="true"] .menu-toggle__bars::after {
  top: 0;
  transform: rotate(-45deg);
}

.mobile-nav {
  display: grid;
  grid-template-rows: 0fr;
  border-top: 1px solid var(--color-line);
  background: var(--color-bg);
  opacity: 0;
  transition: grid-template-rows 0.3s var(--ease-editorial),
    opacity 0.25s var(--ease-editorial);
}

.mobile-nav--open {
  grid-template-rows: 1fr;
  opacity: 1;
}

.mobile-nav__inner {
  min-height: 0;
  overflow: hidden;
  padding: 1.5rem var(--container-pad) 2rem;
  display: flex;
  flex-direction: column;
  gap: 1.5rem;
}

.mobile-nav ul {
  display: flex;
  flex-direction: column;
  gap: 1.1rem;
}

.mobile-nav a {
  font-family: var(--font-display);
  font-size: 1.3rem;
  text-decoration: none;
}

body.nav-open,
body.modal-open {
  overflow: hidden;
}

/* ---------- 7. Hero ---------- */
.hero {
  padding-block: clamp(3rem, 7vw, 5.5rem) clamp(4rem, 8vw, 7rem);
  overflow: hidden;
}

.hero__inner {
  display: grid;
  grid-template-columns: 1.05fr 1fr;
  gap: clamp(2.5rem, 6vw, 5rem);
  align-items: center;
}

.hero__copy {
  max-width: 34rem;
}

.hero__eyebrow {
  margin-bottom: 1.5rem;
}

.hero__heading {
  margin-bottom: 1.75rem;
}

.hero__lede {
  margin-bottom: 2.5rem;
}

.hero__actions {
  display: flex;
  flex-wrap: wrap;
  gap: 1rem;
  align-items: center;
}

.hero__visual {
  position: relative;
  display: flex;
  align-items: center;
  justify-content: flex-start;
}

/* Decorative world-dot-map, seated behind the cover. Oversized and
   softened so it reads as ambient texture rather than competing
   with the book — .hero has overflow:hidden to keep it contained. */
.hero__map {
  position: absolute;
  z-index: 1;
  top: 50%;
  left: 50%;
  width: 165%;
  max-width: 900px;
  transform: translate(-50%, -50%);
  opacity: 0.16;
  pointer-events: none;
}

.hero__map img {
  width: 100%;
}

/* Default (safe, no-JS-required) sizing: fill the column's width,
   height follows the image's own aspect ratio. */
.hero__book-primary {
  position: relative;
  z-index: 2;
  width: 100%;
}

.hero__book-primary img {
  width: 100%;
  height: auto;
  display: block;
}

/* Once main.js has measured the copy column and set an explicit pixel
   height on .hero__visual (see initHeroHeightMatch), switch to sizing
   by height instead, so the cover matches the headline-to-buttons
   block exactly. A CSS-only version of this is not reliable: a grid
   row sized "auto" can't resolve a percentage-height image without
   first knowing the row's height, which is exactly what it's trying
   to compute — browsers fall back to the image's natural size while
   solving that, inflating the whole row to match. flex-shrink:0 and
   no max-width stop the browser from squashing the width back down
   (which would distort the image) to fit the column; any overflow
   grows rightward, away from the text, and .hero's own
   overflow:hidden clips it cleanly if it reaches the section edge. */
.hero__visual--matched .hero__book-primary {
  height: 100%;
  width: auto;
  flex-shrink: 0;
  margin-left: -9rem;
}

.hero__visual--matched .hero__book-primary img {
  height: 100%;
  width: auto;
}

/* ---------- 8. The African Paradox ---------- */
.paradox {
  background: var(--color-bg-alt);
  border-block: 1px solid var(--color-line);
  overflow: hidden;
}

.paradox__head {
  max-width: 54rem;
  margin-bottom: clamp(3rem, 6vw, 4.5rem);
}

.paradox__headline {
  margin-top: 1rem;
}

.paradox__body-grid {
  display: grid;
  grid-template-columns: 1.15fr 0.85fr;
  gap: clamp(2.5rem, 6vw, 5rem);
  align-items: start;
}

.paradox__copy p + p {
  margin-top: 1.25rem;
}

.paradox__emphasis {
  margin: 1.75rem 0;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(1.15rem, 1.8vw, 1.4rem);
  color: var(--color-ink);
}

.paradox__quote-col {
  position: relative;
  padding-top: 0.5rem;
}

.paradox__watermark {
  position: absolute;
  top: -2.5rem;
  right: -0.5rem;
  z-index: 0;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(4rem, 11vw, 8rem);
  line-height: 1;
  letter-spacing: -0.02em;
  color: rgba(4, 28, 54, 0.05);
  white-space: nowrap;
  user-select: none;
  pointer-events: none;
}

.paradox__quote {
  position: relative;
  z-index: 1;
  margin: 0;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(1.5rem, 2.6vw, 2rem);
  line-height: 1.35;
  color: var(--color-ink);
}

.paradox__quote-mark {
  display: inline-block;
  margin-right: 0.1em;
  font-size: 1.3em;
  line-height: 0;
  vertical-align: -0.32em;
  color: var(--color-accent);
}

.paradox__closing {
  position: relative;
  z-index: 1;
  margin-top: 1.75rem;
  padding-top: 1.5rem;
  border-top: 1px solid var(--color-line-strong);
  font-size: 0.95rem;
  font-style: italic;
  color: var(--color-ink-faint);
}

/* ---------- 9. About the book ---------- */
/* The enlarged image below is clipped at the page edge by body's
   overflow-x:hidden (see the body rule), not by overflow here — any
   overflow value other than "visible" on THIS section would turn it
   into the scrolling container that .about-book__visual's sticky
   position resolves against instead of the page, breaking it. */

/* Top-aligned (not the grid-split default of centered) so the sticky
   image starts flush with the top of the copy column instead of
   jumping there partway through the scroll. */
.about-book .grid-split {
  align-items: start;
}

.about-book__visual {
  position: relative;
  display: flex;
  align-items: flex-start;
  justify-content: flex-end;
}

/* Book stays in view while the (now considerably longer) copy column
   scrolls past it — same pattern as .interest__intro. Desktop
   two-column layout only; mobile stacks them in one column, where a
   pinned image would just eat into limited screen space. */
@media (min-width: 961px) {
  .about-book__visual {
    position: sticky;
    top: 6rem;
  }
}

.about-book__image {
  position: relative;
  width: 128%;
  max-width: 128%;
  flex-shrink: 0;
}

.about-book__image img {
  width: 100%;
  border-radius: 2px;
}

.about-book__copy .heading-display {
  margin: 1rem 0 1.5rem;
}

.about-book__copy p + p {
  margin-top: 1.1rem;
}

.pull-quote {
  margin-top: 2.25rem;
  padding-left: 1.5rem;
  border-left: 2px solid var(--color-accent);
  font-family: var(--font-display);
  font-size: clamp(1.25rem, 1.8vw, 1.55rem);
  font-weight: 700;
  line-height: 1.4;
  color: var(--color-ink);
}

/* ---------- 10. What's inside (table of contents) ---------- */
.toc {
  background: var(--color-surface);
}

.toc-scroll {
  display: flex;
  align-items: center;
  gap: 1rem;
}

.toc-scroll__track {
  display: flex;
  gap: clamp(2.5rem, 5vw, 4rem);
  overflow-x: auto;
  scroll-snap-type: x proximity;
  scroll-behavior: smooth;
  padding-block: clamp(1rem, 2vw, 1.5rem);
  scrollbar-width: none;
  -ms-overflow-style: none;
}

.toc-scroll__track::-webkit-scrollbar {
  display: none;
}

.toc-part {
  flex: 0 0 auto;
  width: min(85vw, 480px);
  scroll-snap-align: start;
}

.toc-part__number {
  display: block;
  font-family: var(--font-display);
  font-weight: 700;
  font-size: clamp(2.25rem, 4.5vw, 3rem);
  line-height: 1;
  color: var(--color-line-strong);
  margin-bottom: 1rem;
}

.toc-part__label {
  margin-bottom: 0.6rem;
}

.toc-part h3 {
  margin-bottom: 0.75rem;
}

/* Nav buttons flank the track — reuse the same circular icon-button
   treatment as .captcha__refresh for a consistent system. Touch users
   can just swipe, so these step aside below the swipe-first breakpoint
   rather than eating into card width on small screens. */
.toc-scroll__nav {
  flex-shrink: 0;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 2.85rem;
  height: 2.85rem;
  border-radius: 50%;
  border: 1px solid var(--color-line-strong);
  background: var(--color-surface);
  color: var(--color-ink-soft);
  transition: border-color 0.2s var(--ease-editorial),
    color 0.2s var(--ease-editorial), opacity 0.2s var(--ease-editorial);
}

.toc-scroll__nav:hover {
  border-color: var(--color-ink);
  color: var(--color-ink);
}

.toc-scroll__nav:disabled {
  opacity: 0.35;
  pointer-events: none;
}

.toc-scroll__nav .btn__icon {
  width: 1.1em;
  height: 1.1em;
}

@media (max-width: 720px) {
  .toc-scroll__nav {
    display: none;
  }
}

/* ---------- 11. Author ---------- */
.author {
  background: var(--color-bg-alt);
}

.author__visual {
  position: relative;
}

.author__frame {
  position: relative;
  aspect-ratio: 1080 / 1350; /* matches author-main.png */
  overflow: hidden;
  border-radius: var(--radius-md);
  background: var(--color-surface);
}

.author__frame img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.author__copy .heading-lg {
  margin: 1rem 0 0.4rem;
  text-transform: uppercase;
  letter-spacing: 0.01em;
}

.author__role {
  font-size: 0.95rem;
  color: var(--color-ink-faint);
  font-style: italic;
  margin-bottom: 1.5rem;
}

.author__bio p + p {
  margin-top: 1.1rem;
}

.author__cta {
  margin-top: 2rem;
}

/* ---------- 12. Reviews ---------- */
.reviews {
  background: var(--color-surface);
}

.reviews-grid {
  display: grid;
  grid-template-columns: repeat(2, 1fr);
  gap: clamp(1.5rem, 3vw, 2rem);
}

.review-card {
  padding: clamp(1.75rem, 3vw, 2.25rem);
  background: var(--color-bg);
  border: 1px solid var(--color-line);
  border-radius: var(--radius-md);
  display: flex;
  flex-direction: column;
  gap: 1.5rem;
}

.review-card__mark {
  font-family: var(--font-display);
  font-weight: 700;
  font-size: 2.5rem;
  line-height: 1;
  color: var(--color-accent-soft);
}

.review-card__quote {
  font-family: var(--font-display);
  font-size: 1.1rem;
  line-height: 1.55;
  color: var(--color-ink);
}

.review-card__meta {
  margin-top: auto;
  padding-top: 1.25rem;
  border-top: 1px solid var(--color-line);
}

.review-card__name {
  font-weight: 600;
  font-size: 0.95rem;
}

.review-card__role {
  font-size: 0.85rem;
  color: var(--color-ink-faint);
}

/* ---------- 13. Interest form ---------- */
.interest {
  background: var(--color-bg-alt);
}

.interest__inner {
  display: grid;
  grid-template-columns: 0.85fr 1.15fr;
  gap: clamp(2.5rem, 5vw, 5rem);
  align-items: start;
}

.interest__intro .heading-lg {
  margin: 1rem 0 1.25rem;
}

/* Sidebar stays in view while the (usually taller) form scrolls past —
   desktop two-column layout only; mobile stacks them in one column,
   where a pinned intro would just eat into limited screen space. */
@media (min-width: 961px) {
  .interest__intro {
    position: sticky;
    top: 6rem;
  }
}

.form-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  column-gap: 1.5rem;
  row-gap: 2rem;
}

.form-field {
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
}

.form-field--full {
  grid-column: 1 / -1;
}

.form-field label {
  font-size: 0.85rem;
  font-weight: 600;
  color: var(--color-ink);
}

.form-field .optional {
  font-weight: 400;
  color: var(--color-ink-faint);
}

.form-field input,
.form-field select,
.form-field textarea {
  width: 100%;
  padding: 0.85rem 1rem;
  background: var(--color-surface);
  border: 1px solid var(--color-line-strong);
  border-radius: var(--radius-sm);
  font-size: 0.95rem;
  transition: border-color 0.2s var(--ease-editorial);
}

/* Text inputs and the native <select> render at slightly different
   heights even with identical padding/font-size — an explicit height
   on every single-line control (plus the buttons beside them) keeps
   the whole row lining up exactly instead of by coincidence. */
.form-field input:not([type="checkbox"]):not([type="radio"]),
.form-field select {
  height: 3.375rem;
}

.form-field input:focus,
.form-field select:focus,
.form-field textarea:focus {
  border-color: var(--color-ink);
}

.form-field textarea {
  resize: none;
  min-height: 6rem;
}

.form-counter {
  align-self: flex-end;
  font-size: 0.78rem;
  color: var(--color-ink-faint);
  transition: color 0.2s var(--ease-editorial);
}

.form-counter.is-at-limit {
  color: var(--color-accent);
}

/* Self-built captcha (see initCaptcha in main.js) */
.captcha__code {
  display: inline-flex;
  align-self: flex-start;
  gap: 0.3em;
  padding: 0.4rem 0.75rem;
  background: var(--color-bg-alt);
  border: 1px dashed var(--color-line-strong);
  border-radius: var(--radius-sm);
  font-family: ui-monospace, "SF Mono", Menlo, monospace;
  font-weight: 700;
  font-size: 1.1rem;
  letter-spacing: 0.05em;
  color: var(--color-ink);
  user-select: none;
  opacity: 1;
  transition: opacity 0.14s var(--ease-editorial);
}

.captcha__code.is-refreshing {
  opacity: 0;
}

.captcha__code span {
  display: inline-block;
}

.captcha__row {
  display: flex;
  gap: 0.6rem;
}

.captcha__row input {
  flex: 1;
}

.captcha__refresh {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 2.85rem;
  height: 3.375rem;
  flex-shrink: 0;
  border: 1px solid var(--color-line-strong);
  border-radius: var(--radius-sm);
  background: var(--color-surface);
  color: var(--color-ink-soft);
  transition: border-color 0.2s var(--ease-editorial),
    color 0.2s var(--ease-editorial);
}

.captcha__refresh:hover {
  border-color: var(--color-ink);
  color: var(--color-ink);
}

.captcha__refresh .btn__icon {
  width: 1.1em;
  height: 1.1em;
  transition: transform 0.4s var(--ease-editorial);
}

.captcha__refresh.is-spinning .btn__icon {
  transform: rotate(180deg);
}

.form-field [aria-invalid="true"] {
  border-color: #a13d2b;
}

.form-error {
  font-size: 0.82rem;
  color: #a13d2b;
  min-height: 1.1em;
}

/* Sits beside the captcha field, same grid row — bottom-aligned so the
   button lines up with the captcha's input rather than its label. */
/* form-actions mirrors the captcha field's own label+row structure —
   the spacer keeps the button lined up with the captcha input rather
   than with the label above it. */
.form-actions {
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
}

.form-actions__spacer {
  font-size: 0.85rem;
}

.form-submit {
  position: relative;
  width: 100%;
  height: 3.375rem;
}

.form-submit[data-loading="true"] {
  opacity: 0.85;
  cursor: progress;
  color: transparent;
}

.form-submit[data-loading="true"]::after {
  content: "";
  position: absolute;
  top: 50%;
  left: 50%;
  width: 1.1rem;
  height: 1.1rem;
  margin: -0.55rem 0 0 -0.55rem;
  border: 2px solid rgba(247, 246, 241, 0.35);
  border-top-color: var(--color-bg);
  border-radius: 50%;
  animation: form-submit-spin 0.7s linear infinite;
}

@keyframes form-submit-spin {
  to {
    transform: rotate(360deg);
  }
}

.form-status {
  margin-top: 1.25rem;
  font-size: 0.9rem;
  min-height: 1.3em;
}

.form-status[data-state="success"] {
  color: #3a6b3f;
}

.form-status[data-state="error"] {
  color: #a13d2b;
}

.form-status[data-state="loading"] {
  color: var(--color-ink-faint);
}

.form-privacy {
  margin-top: 0.35rem;
  font-size: 0.82rem;
  color: var(--color-ink-faint);
  max-width: 34rem;
}

/* ---------- 14. Purchase CTA ---------- */
.purchase-cta {
  background: var(--color-dark-bg);
  color: var(--color-dark-ink);
  overflow: hidden;
}

.purchase-cta__inner {
  display: grid;
  grid-template-columns: 1.1fr 0.9fr;
  gap: clamp(2.5rem, 6vw, 5rem);
  align-items: center;
}

.purchase-cta__eyebrow {
  color: var(--color-accent-vivid);
}

.purchase-cta__eyebrow::before {
  background: var(--color-accent-vivid);
}

.purchase-cta .heading-display {
  color: var(--color-dark-ink);
  margin: 1.25rem 0 1.5rem;
}

.purchase-cta__lede {
  color: var(--color-dark-ink-soft);
  margin-bottom: 2.5rem;
  max-width: 32rem;
}

.purchase-cta__actions {
  display: flex;
  flex-wrap: wrap;
  gap: 1rem;
}

.purchase-cta__visual {
  position: relative;
  display: flex;
  align-items: center;
  justify-content: center;
}

.purchase-cta__image {
  position: relative;
  width: 100%;
}

.purchase-cta__image img {
  width: 100%;
  border-radius: 2px;
}

/* ---------- 15. Footer ---------- */
.site-footer {
  background: var(--color-ink);
  color: rgba(247, 244, 238, 0.72);
  padding-block: clamp(3rem, 6vw, 4.5rem) 2rem;
}

.footer__top {
  display: flex;
  justify-content: space-between;
  gap: 3rem;
  flex-wrap: wrap;
  padding-bottom: clamp(2.5rem, 5vw, 3.5rem);
  border-bottom: 1px solid rgba(247, 244, 238, 0.14);
  margin-bottom: 1.75rem;
}

.footer__brand .wordmark {
  color: var(--color-bg);
}

.footer__tagline {
  margin-top: 0.75rem;
  max-width: 22rem;
  font-size: 0.92rem;
  color: rgba(247, 244, 238, 0.6);
}

.footer__nav ul {
  display: flex;
  flex-wrap: wrap;
  gap: 1.5rem 2rem;
}

.footer__nav a {
  text-decoration: none;
  font-size: 0.92rem;
  color: rgba(247, 244, 238, 0.72);
  transition: color 0.2s var(--ease-editorial);
}

.footer__nav a:hover {
  color: var(--color-bg);
}

.footer__bottom {
  display: flex;
  justify-content: space-between;
  align-items: center;
  flex-wrap: wrap;
  gap: 1rem;
  font-size: 0.82rem;
  color: rgba(247, 244, 238, 0.5);
}

.footer__social {
  display: flex;
  gap: 1.25rem;
}

.footer__social-link {
  text-decoration: none;
  color: rgba(247, 244, 238, 0.72);
  font-size: 0.82rem;
  transition: color 0.2s var(--ease-editorial);
}

.footer__social-link:hover {
  color: var(--color-bg);
}

/* ---------- 16. Image fallback placeholders ---------- */
[data-fallback-label] {
  position: relative;
}

[data-fallback-label].is-missing {
  display: flex;
  align-items: center;
  justify-content: center;
  background: repeating-linear-gradient(
    135deg,
    rgba(23, 20, 15, 0.04),
    rgba(23, 20, 15, 0.04) 10px,
    rgba(23, 20, 15, 0.07) 10px,
    rgba(23, 20, 15, 0.07) 20px
  );
  border: 1px dashed var(--color-line-strong);
  min-height: 220px;
  border-radius: var(--radius-md);
}

[data-fallback-label].is-missing::before {
  content: "SA";
  font-family: var(--font-display);
  font-size: 1.5rem;
  color: var(--color-ink-faint);
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -140%);
}

[data-fallback-label].is-missing::after {
  content: attr(data-fallback-label);
  font-size: 0.78rem;
  color: var(--color-ink-faint);
  text-align: center;
  max-width: 80%;
  padding: 0 1rem;
}

.purchase-cta [data-fallback-label].is-missing,
[data-fallback-label].is-missing.is-on-dark {
  background: repeating-linear-gradient(
    135deg,
    rgba(246, 242, 234, 0.05),
    rgba(246, 242, 234, 0.05) 10px,
    rgba(246, 242, 234, 0.08) 10px,
    rgba(246, 242, 234, 0.08) 20px
  );
  border-color: var(--color-dark-line);
}

.purchase-cta [data-fallback-label].is-missing::before,
[data-fallback-label].is-missing.is-on-dark::before,
.purchase-cta [data-fallback-label].is-missing::after,
[data-fallback-label].is-missing.is-on-dark::after {
  color: var(--color-dark-ink-soft);
}

/* ---------- 17. Scroll reveal & motion ----------
   Progressive enhancement: [data-reveal] elements are only ever hidden
   once the "js" class confirms main.js is running and will be the one
   to reveal them. If JS is blocked, slow, or errors, content is never
   hidden in the first place — it just renders normally, unanimated. */
.js [data-reveal] {
  opacity: 0;
  transform: translateY(22px);
  transition: opacity 0.8s var(--ease-editorial),
    transform 0.8s var(--ease-editorial);
}

.js [data-reveal].is-visible {
  opacity: 1;
  transform: translateY(0);
}

/* The fade variant never gets a transform at all, in either state —
   not even the visually-identity translateY(0) above, since ANY
   non-"none" transform value (matrix or otherwise) makes an element
   establish its own containing block, which silently breaks
   position:sticky on itself or on any descendant. Used on
   .interest__intro, which needs to stick while its section scrolls. */
.js [data-reveal="fade"],
.js [data-reveal="fade"].is-visible {
  transform: none;
}

/* The stagger variant (hero copy) doesn't hide or animate itself —
   it's only there so its is-visible class can drive a small cascade
   through its own children below, each on its own delay, instead of
   the whole block arriving as one flat block on page load. */
.js [data-reveal="stagger"],
.js [data-reveal="stagger"].is-visible {
  opacity: 1;
  transform: none;
}

.js [data-reveal="stagger"] .hero__heading,
.js [data-reveal="stagger"] .hero__lede,
.js [data-reveal="stagger"] .hero__actions {
  opacity: 0;
  transform: translateY(14px);
  transition: opacity 0.6s var(--ease-editorial),
    transform 0.6s var(--ease-editorial);
}

.js [data-reveal="stagger"].is-visible .hero__heading {
  opacity: 1;
  transform: none;
  transition-delay: 0.05s;
}

.js [data-reveal="stagger"].is-visible .hero__lede {
  opacity: 1;
  transform: none;
  transition-delay: 0.18s;
}

.js [data-reveal="stagger"].is-visible .hero__actions {
  opacity: 1;
  transform: none;
  transition-delay: 0.3s;
}

@media (prefers-reduced-motion: reduce) {
  .js [data-reveal="stagger"] .hero__heading,
  .js [data-reveal="stagger"] .hero__lede,
  .js [data-reveal="stagger"] .hero__actions {
    opacity: 1;
    transform: none;
    transition: none;
  }

  .js [data-reveal] {
    opacity: 1;
    transform: none;
    transition: none;
  }
}

/* ---------- 18. Responsive adjustments ---------- */
@media (min-width: 900px) {
  .nav {
    display: block;
  }

  .header__actions .btn {
    display: inline-flex;
  }

  .menu-toggle {
    display: none;
  }

  .mobile-nav {
    display: none;
  }
}

@media (max-width: 1080px) {
  .pillars {
    grid-template-columns: repeat(2, 1fr);
  }

  .reviews-grid {
    grid-template-columns: 1fr;
    max-width: 34rem;
    margin-inline: auto;
  }
}

@media (max-width: 960px) {
  .hero__inner,
  .grid-split,
  .interest__inner,
  .purchase-cta__inner,
  .paradox__body-grid {
    grid-template-columns: 1fr;
  }

  .paradox__watermark {
    top: -1.5rem;
  }

  .grid-split__visual,
  .grid-split--reverse .grid-split__visual {
    order: -1;
  }

  .hero__copy {
    max-width: none;
  }

  .interest__intro {
    max-width: none;
  }

  .purchase-cta__visual {
    order: -1;
  }
}

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

  .form-submit {
    width: 100%;
    min-width: 0;
  }

  .footer__top {
    flex-direction: column;
  }

  .footer__bottom {
    flex-direction: column;
    align-items: flex-start;
  }
}

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

  .hero__actions {
    flex-direction: column;
    align-items: stretch;
  }

  .hero__actions .btn {
    width: 100%;
  }
}

/* ---------- 19. "Coming Soon" modal ----------
   Shown instead of navigating to Amazon while AMAZON_BOOK_URL is a
   placeholder — see initAmazonModal in main.js. */
.modal {
  position: fixed;
  inset: 0;
  z-index: 300;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 1.5rem;
}

.modal[hidden] {
  display: none;
}

.modal__backdrop {
  position: absolute;
  inset: 0;
  background: rgba(4, 28, 54, 0.6);
  opacity: 0;
  transition: opacity 0.25s var(--ease-editorial);
}

.modal--open .modal__backdrop {
  opacity: 1;
}

.modal__dialog {
  position: relative;
  z-index: 1;
  display: grid;
  grid-template-columns: 0.85fr 1.15fr;
  gap: clamp(1.5rem, 4vw, 2.75rem);
  width: 100%;
  max-width: 720px;
  max-height: 90vh;
  overflow-y: auto;
  background: var(--color-bg);
  border-radius: var(--radius-md);
  padding: clamp(1.75rem, 4vw, 2.75rem);
  box-shadow: 0 40px 80px -20px rgba(4, 28, 54, 0.4);
  opacity: 0;
  transform: translateY(16px) scale(0.98);
  transition: opacity 0.3s var(--ease-editorial),
    transform 0.3s var(--ease-editorial);
}

.modal--open .modal__dialog {
  opacity: 1;
  transform: translateY(0) scale(1);
}

@media (prefers-reduced-motion: reduce) {
  .modal__backdrop,
  .modal__dialog {
    transition: none;
  }
}

.modal__close {
  position: absolute;
  top: 1rem;
  right: 1rem;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 2.25rem;
  height: 2.25rem;
  border-radius: 50%;
  color: var(--color-ink-soft);
  transition: background-color 0.2s var(--ease-editorial),
    color 0.2s var(--ease-editorial);
}

.modal__close:hover {
  background: var(--color-bg-alt);
  color: var(--color-ink);
}

.modal__close .btn__icon {
  width: 1.1em;
  height: 1.1em;
}

.modal__visual {
  display: flex;
  align-items: center;
  justify-content: center;
}

.modal__visual img {
  width: 100%;
  max-width: 200px;
  border-radius: 3px;
  box-shadow: 0 24px 48px -16px rgba(4, 28, 54, 0.3);
}

.modal__copy {
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 0.9rem;
  padding-top: 1.5rem;
}

.modal__copy .heading-lg {
  font-size: clamp(1.5rem, 3vw, 2rem);
}

@media (max-width: 640px) {
  .modal__dialog {
    grid-template-columns: 1fr;
    text-align: center;
  }

  .modal__visual img {
    max-width: 150px;
  }

  .modal__copy {
    padding-top: 0;
    align-items: center;
  }
}
