/* ═══════════════════════════════════════════════════
   Likolihle Moses — Professional Chef
   Palette drawn from cool-blue impasto: deep petrol
   navy, ice, cream, apricot.
   ═══════════════════════════════════════════════════ */

:root {
  --ink:      #08131f;
  --ink-2:    #0d1e2f;
  --deep:     #123047;
  --blue:     #2f6d94;
  --blue-lt:  #6fa6c4;
  --ice:      #c9dce8;
  --cream:    #f4efe7;
  --apricot:  #e8a87c;
  /* Sampled from the gold veining in the abstracts (#fdb629), muted so it
     sits beside the apricot as a metallic rather than competing with it. */
  --gold:     #d9a441;
  --rule:     rgba(201, 220, 232, .16);

  --serif: "Fraunces", Georgia, serif;
  --sans:  "Inter", -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;

  --pad: clamp(1.5rem, 5vw, 6rem);
  --maxw: 1240px;
  --ease: cubic-bezier(.2, .7, .2, 1);
  /* Motion curves. --spring is a settle with no overshoot (headings, reveals);
     --pop carries a little overshoot for things that should feel alive. */
  --spring: cubic-bezier(.16, 1, .3, 1);
  --pop:    cubic-bezier(.34, 1.56, .64, 1);
}

*, *::before, *::after { box-sizing: border-box; }

html { scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
}

body {
  margin: 0;
  background: var(--ink);
  color: var(--cream);
  font-family: var(--sans);
  font-weight: 300;
  font-size: clamp(1rem, .95rem + .2vw, 1.0625rem);
  line-height: 1.75;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

img { max-width: 100%; display: block; }

::selection { background: var(--apricot); color: var(--ink); }

.skip {
  position: absolute; left: -9999px; top: 0; z-index: 100;
  background: var(--apricot); color: var(--ink);
  padding: .75rem 1.25rem; font-weight: 600;
}
.skip:focus { left: 0; }

:focus-visible {
  outline: 2px solid var(--apricot);
  outline-offset: 3px;
}

/* ─────────── Shared type ─────────── */

.eyebrow {
  font-size: .6875rem;
  letter-spacing: .22em;
  text-transform: uppercase;
  font-weight: 500;
  color: var(--blue-lt);
  margin: 0 0 1.25rem;
}

h1, h2, h3 {
  font-family: var(--serif);
  font-weight: 400;
  line-height: 1.04;
  letter-spacing: -.02em;
  margin: 0;
}

h2 em, h1 em {
  font-style: italic;
  font-weight: 300;
  color: var(--apricot);
}

/* ─────────── Nav ─────────── */

.nav {
  position: fixed; inset: 0 0 auto 0; z-index: 50;
  display: flex; align-items: center; gap: 2rem;
  padding: 1.1rem var(--pad);
  transition: background .4s var(--ease), backdrop-filter .4s var(--ease),
              padding .4s var(--ease), border-color .4s var(--ease);
  border-bottom: 1px solid transparent;
}
.nav.is-stuck {
  background: rgba(8, 19, 31, .82);
  backdrop-filter: blur(14px);
  -webkit-backdrop-filter: blur(14px);
  border-bottom-color: var(--rule);
  padding-block: .7rem;
}

.nav__mark {
  font-family: var(--serif);
  font-size: 1.0625rem;
  letter-spacing: .06em;
  color: var(--cream);
  text-decoration: none;
  border: 1px solid var(--rule);
  width: 2.5rem; height: 2.5rem;
  display: grid; place-items: center;
  border-radius: 50%;
  flex: none;
  transition: border-color .3s var(--ease), color .3s var(--ease);
}
.nav__mark:hover { border-color: var(--apricot); color: var(--apricot); }

.nav__links {
  display: flex; gap: 1.75rem;
  margin-inline: auto;
}
.nav__links a {
  color: var(--ice);
  text-decoration: none;
  font-size: .8125rem;
  letter-spacing: .08em;
  text-transform: uppercase;
  font-weight: 400;
  opacity: .75;
  position: relative;
  transition: opacity .3s var(--ease), color .3s var(--ease);
}
.nav__links a::after {
  content: ""; position: absolute; left: 0; bottom: -5px;
  width: 100%; height: 1px; background: var(--apricot);
  transform: scaleX(0); transform-origin: right;
  transition: transform .35s var(--ease);
}
.nav__links a:hover { opacity: 1; color: var(--cream); }
.nav__links a:hover::after { transform: scaleX(1); transform-origin: left; }

.nav__cta {
  flex: none;
  font-size: .75rem; letter-spacing: .1em; text-transform: uppercase;
  font-weight: 500;
  color: var(--ink); background: var(--apricot);
  padding: .6rem 1.15rem; border-radius: 999px;
  text-decoration: none;
  transition: transform .3s var(--ease), background .3s var(--ease);
}
.nav__cta:hover {
  background: var(--cream);
  transform: translate(var(--mx, 0px), calc(var(--my, 0px) - 2px));
}

@media (max-width: 900px) {
  .nav__links { display: none; }
  .nav__cta { margin-left: auto; }
}

/* ─────────── Hero ─────────── */

.hero {
  position: relative;
  min-height: 100svh;
  display: grid;
  grid-template-columns: 1fr 1fr;
  align-items: center;
  gap: clamp(2rem, 5vw, 5rem);
  padding: 8rem var(--pad) 5rem;
  max-width: var(--maxw);
  margin-inline: auto;
}

/* The portrait's blue studio backdrop bleeds into the page.
   Full-bleed: constraining this to the hero's max-width box clips the
   radials and leaves visible vertical seams at the container edges. */
.hero::before {
  content: "";
  position: absolute;
  top: 0; bottom: 0;
  left: 50%;
  width: 100vw;
  transform: translateX(-50%);
  background:
    radial-gradient(60% 55% at 72% 42%, rgba(47, 109, 148, .45), transparent 70%),
    radial-gradient(45% 45% at 18% 88%, rgba(18, 48, 71, .5), transparent 70%);
  pointer-events: none;
  z-index: -1;
}

/* Painterly wash beneath the glow — brushwork left sharp so the impasto
   reads. Saturation is held down at build time instead: colour, not
   sharpness, is what smears the navy into mud. Masked at the bottom so it
   dissolves into the stat band rather than ending on a seam. */
.hero__art {
  position: absolute;
  top: -12%; bottom: -12%;          /* overscan: room to drift without gapping */
  left: 50%;
  width: 100vw;
  margin-left: -50vw;
  background: url("/images/art-hero.jpg") center / cover no-repeat;
  opacity: .46;
  pointer-events: none;
  z-index: -2;
  -webkit-mask-image: linear-gradient(to bottom, #000 50%, transparent 92%);
          mask-image: linear-gradient(to bottom, #000 50%, transparent 92%);
}

/* Framed as a photograph rather than bled into the page.
   A radial feather was tried and abandoned: the toque touches the top edge
   and the red stole reaches the sides, so any mask tight enough to dissolve
   the light studio backdrop also eats the subject. Sizing is width-only and
   capped against svh so the frame stays inside the fold. */
.hero__portrait {
  position: relative;
  order: 2;
  justify-self: center;
  max-width: min(25rem, 46svh);
  width: 100%;
  border-radius: 4px;
  overflow: hidden;
  box-shadow:
    0 0 0 1px rgba(201, 220, 232, .14),
    0 40px 80px -20px rgba(0, 0, 0, .7);
  animation: floatIn 1.4s var(--ease) both;
}
.hero__portrait img {
  width: 100%;
  filter: saturate(.82) contrast(1.04);
}

@keyframes floatIn {
  from { opacity: 0; transform: translateY(24px) scale(.98); }
  to   { opacity: 1; transform: none; }
}

/* Hero copy now sits over visible brushwork rather than flat navy. */
.hero__copy {
  order: 1;
  max-width: 34rem;
  text-shadow: 0 2px 18px rgba(8, 19, 31, .85);
}

.hero h1 {
  font-size: clamp(3.25rem, 8.5vw, 6.5rem);
  margin-bottom: 1.5rem;
}

.hero__role {
  font-size: .8125rem;
  letter-spacing: .16em;
  text-transform: uppercase;
  color: var(--ice);
  margin: 0 0 2rem;
  padding-top: 1.5rem;
  border-top: 1px solid var(--rule);
}

.hero__lede {
  font-size: clamp(1.0625rem, 1rem + .35vw, 1.25rem);
  color: rgba(244, 239, 231, .82);
  margin: 0 0 2.5rem;
  max-width: 30rem;
}

.hero__actions { display: flex; gap: .875rem; flex-wrap: wrap; }

.btn {
  display: inline-block;
  padding: .9rem 1.75rem;
  border-radius: 999px;
  font-size: .8125rem;
  letter-spacing: .1em;
  text-transform: uppercase;
  font-weight: 500;
  text-decoration: none;
  transition: transform .3s var(--ease), background .3s var(--ease),
              color .3s var(--ease), border-color .3s var(--ease);
}
/* Hover lift folds into the magnetic offset — a bare translateY here would
   overwrite it and kill the pull entirely. */
.btn--solid { background: var(--apricot); color: var(--ink); }
.btn--solid:hover {
  background: var(--cream);
  transform: translate(var(--mx, 0px), calc(var(--my, 0px) - 2px));
}
.btn--ghost { border: 1px solid var(--rule); color: var(--cream); }
.btn--ghost:hover {
  border-color: var(--apricot); color: var(--apricot);
  transform: translate(var(--mx, 0px), calc(var(--my, 0px) - 2px));
}

.hero__scroll {
  position: absolute;
  bottom: 2rem; left: 50%; transform: translateX(-50%);
  width: 1px; height: 3.5rem;
  background: var(--rule);
  overflow: hidden;
}
.hero__scroll span {
  position: absolute; inset: 0;
  background: var(--apricot);
  animation: scrollHint 2.4s var(--ease) infinite;
}
@keyframes scrollHint {
  0%   { transform: translateY(-100%); }
  60%, 100% { transform: translateY(100%); }
}

@media (max-width: 880px) {
  .hero {
    grid-template-columns: 1fr;
    text-align: left;
    padding-top: 6rem;
    min-height: auto;
    gap: 1rem;
  }
  /* Keep the portrait from swallowing the first screen and pushing his
     name below the fold — the name has to land in the first view. */
  .hero__portrait { order: 1; max-width: min(17rem, 34svh); justify-self: start; }
  .hero__copy { order: 2; }
  .hero__scroll { display: none; }
  .hero h1 { font-size: clamp(3rem, 15vw, 4.5rem); }
}

/* ─────────── Stat band ─────────── */

.band {
  position: relative;
  border-block: 1px solid var(--rule);
  background: var(--ink-2);
  overflow: hidden;
}
/* Brush texture under the numbers — enough to feel like canvas, not enough
   to compete with them. */
.band::before {
  content: "";
  position: absolute;
  inset: 0;
  background: url("/images/art-band.jpg") center / cover no-repeat;
  opacity: .42;
  pointer-events: none;
}
/* Light scrim: enough to keep pale labels legible over the warm passages of
   the painting, not enough to flatten the brushwork back out. */
.band::after {
  content: "";
  position: absolute;
  inset: 0;
  background: rgba(8, 19, 31, .34);
  pointer-events: none;
}
.band__inner {
  position: relative;
  max-width: var(--maxw);
  margin-inline: auto;
  padding: clamp(2.5rem, 5vw, 4rem) var(--pad);
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: clamp(1.5rem, 4vw, 3rem);
}
.stat { display: flex; flex-direction: column; gap: .6rem; }
/* Text sitting directly on the painting carries its own shadow rather than
   forcing a heavier scrim over the art. */
.stat__fig, .stat__label { text-shadow: 0 1px 14px rgba(8, 19, 31, .95); }
.stat__fig {
  font-family: var(--serif);
  font-size: clamp(2.5rem, 5vw, 3.75rem);
  line-height: 1;
  color: var(--cream);
  letter-spacing: -.03em;
}
.stat__fig em {
  font-style: normal;
  color: var(--blue-lt);
  font-size: .5em;
}
.stat__label {
  font-size: .875rem;
  color: rgba(201, 220, 232, .88);
  line-height: 1.55;
  max-width: 20rem;
}
@media (max-width: 780px) {
  .band__inner { grid-template-columns: 1fr; }
}

/* ─────────── Section shell ─────────── */

.section {
  max-width: var(--maxw);
  margin-inline: auto;
  padding: clamp(4.5rem, 11vw, 9rem) var(--pad);
}
.section--alt {
  max-width: none;
  background: var(--ink-2);
  border-block: 1px solid var(--rule);
}
.section--alt > * { max-width: var(--maxw); margin-inline: auto; }

/* The nav is fixed, so an anchor jump would otherwise land the heading
   underneath it. Clears the stuck nav plus a little breathing room. */
section[id], .chapter[id] { scroll-margin-top: 5.5rem; }

.section__head { margin-bottom: clamp(2.5rem, 5vw, 4rem); }
.section__head h2 { font-size: clamp(2.25rem, 5.5vw, 4rem); }
.section__note {
  margin: 1.25rem 0 0;
  font-size: .9375rem;
  color: rgba(201, 220, 232, .6);
  font-style: italic;
  max-width: 32rem;
}

/* ─────────── About ─────────── */

.prose { max-width: 46rem; }
.prose p {
  font-size: clamp(1.0625rem, 1rem + .3vw, 1.1875rem);
  color: rgba(244, 239, 231, .8);
  margin: 0 0 1.5rem;
}
.prose strong { color: var(--cream); font-weight: 500; }

.facts {
  margin: 3rem 0 0;
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(11rem, 1fr));
  gap: 1.75rem 2rem;
  padding-top: 2.5rem;
  border-top: 1px solid var(--rule);
}
.facts div { display: flex; flex-direction: column; gap: .4rem; }
.facts dt {
  font-size: .6875rem; letter-spacing: .16em; text-transform: uppercase;
  color: var(--blue-lt); font-weight: 500;
}
.facts dd { margin: 0; font-size: .9375rem; color: var(--cream); line-height: 1.5; }

/* ─────────── Pull quote ─────────── */

.quote {
  position: relative;
  padding: clamp(5rem, 12vw, 9rem) var(--pad);
  isolation: isolate;
  overflow: hidden;
}
.quote::before {
  content: "";
  position: absolute; inset: 0;
  background-image: var(--tex);
  background-size: cover;
  background-position: center;
  opacity: .45;
  filter: saturate(.7);
  z-index: -2;
}
.quote::after {
  content: "";
  position: absolute; inset: 0;
  background: linear-gradient(180deg, var(--ink), rgba(8, 19, 31, .55) 50%, var(--ink));
  z-index: -1;
}
.quote blockquote {
  margin: 0 auto;
  max-width: 46rem;
  text-align: center;
}
.quote p {
  font-family: var(--serif);
  font-style: italic;
  font-weight: 300;
  font-size: clamp(1.5rem, 4vw, 2.75rem);
  line-height: 1.28;
  letter-spacing: -.02em;
  margin: 0 0 1.75rem;
  color: var(--cream);
}
.quote cite {
  font-style: normal;
  font-size: .75rem;
  letter-spacing: .2em;
  text-transform: uppercase;
  color: var(--apricot);
}

/* ─────────── Cards (training) ─────────── */

.cards {
  display: grid;
  grid-template-columns: 1.4fr 1fr 1fr;
  gap: 1.25rem;
}
/* Three across is too tight below ~1100px, so the Capsicum card — the one
   carrying the scorebar — takes the full width and the other two pair up
   beneath it rather than all three squeezing. */
@media (max-width: 1100px) {
  .cards { grid-template-columns: 1fr 1fr; }
  .card--hero { grid-column: 1 / -1; }
}
@media (max-width: 880px) {
  .cards { grid-template-columns: 1fr; }
  .card--hero { grid-column: auto; }
}

.card {
  border: 1px solid var(--rule);
  border-radius: 3px;
  padding: clamp(1.75rem, 3.5vw, 2.75rem);
  background: linear-gradient(160deg, rgba(47, 109, 148, .08), transparent 60%);
  transition: border-color .4s var(--ease), transform .4s var(--ease);
}
.card:hover { border-color: rgba(232, 168, 124, .45); transform: translateY(-3px); }

/* The Capsicum card carries his strongest credential, so it gets the gold
   veining — used exactly once on the page, kept crisp (not blurred) because
   the metallic lines are the whole point, and a gold hairline on top. */
.card--hero {
  position: relative;
  overflow: hidden;
  border-top: 1px solid rgba(217, 164, 65, .5);
  background: linear-gradient(160deg, rgba(47, 109, 148, .18), transparent 65%);
}
/* Gold veining isolated from the painting onto pure black, then screened:
   black contributes nothing, so only the metal glows through. Dropping the
   painting in whole just muddied the card with colour blobs — the veins
   were never legible at this size. */
.card--hero::before {
  content: "";
  position: absolute;
  inset: 0;
  background: url("/images/art-veins.jpg") center / cover no-repeat;
  mix-blend-mode: screen;
  opacity: .55;
  pointer-events: none;
  /* Weight the veining toward the outer edge so it never sits behind the
     left-aligned text. */
  -webkit-mask-image: linear-gradient(105deg, transparent 28%, #000 95%);
          mask-image: linear-gradient(105deg, transparent 28%, #000 95%);
}
.card--hero > * { position: relative; }
.card--hero:hover { border-color: rgba(217, 164, 65, .6); }

.card__date {
  font-size: .6875rem; letter-spacing: .16em; text-transform: uppercase;
  color: var(--blue-lt); margin: 0 0 1rem; font-weight: 500;
}
.card h3 {
  font-size: clamp(1.375rem, 2.5vw, 1.75rem);
  margin-bottom: .5rem;
}
.card__org {
  margin: 0 0 1.25rem;
  color: var(--apricot);
  font-size: .9375rem;
  letter-spacing: .02em;
}
.card__body {
  margin: 0;
  color: rgba(244, 239, 231, .74);
  font-size: .9375rem;
  line-height: 1.7;
}

.scorebar { display: block; margin-top: 2rem; }
.scorebar__fill {
  display: block;
  height: 3px;
  background: var(--rule);
  border-radius: 999px;
  position: relative;
  overflow: hidden;
}
.scorebar__fill::after {
  content: "";
  position: absolute; inset: 0 auto 0 0;
  width: 88.2%; /* 15 of 17 */
  background: linear-gradient(90deg, var(--blue), var(--gold));
  border-radius: 999px;
  transform-origin: left;
  transition: transform 1.5s var(--ease) .2s;
}
.js .scorebar__fill::after { transform: scaleX(0); }
.js .card.is-in .scorebar__fill::after { transform: scaleX(1); }
.scorebar__note {
  display: block;
  margin-top: .85rem;
  font-size: .75rem;
  letter-spacing: .1em;
  text-transform: uppercase;
  color: var(--blue-lt);
}

/* ─────────── Timeline ─────────── */

.timeline { list-style: none; margin: 0; padding: 0; }

.tl {
  display: grid;
  grid-template-columns: 14rem 1fr;
  gap: clamp(1rem, 4vw, 3rem);
  padding: clamp(1.75rem, 3.5vw, 2.5rem) 0;
  border-top: 1px solid var(--rule);
  position: relative;
}
.tl:last-child { border-bottom: 1px solid var(--rule); }

.tl::before {
  content: "";
  position: absolute;
  left: 0; top: -1px;
  width: 100%; height: 1px;
  background: var(--apricot);
  transition: width .8s var(--ease);
}
.js .tl::before { width: 0; }
.js .tl.is-in::before { width: 100%; }

.tl__meta { display: flex; flex-direction: column; gap: .75rem; align-items: flex-start; }
.tl__date {
  font-size: .8125rem;
  letter-spacing: .1em;
  text-transform: uppercase;
  color: var(--ice);
  font-weight: 400;
}
.tl__tag {
  font-size: .625rem;
  letter-spacing: .14em;
  text-transform: uppercase;
  font-weight: 600;
  color: var(--ink);
  background: var(--apricot);
  padding: .3rem .7rem;
  border-radius: 999px;
}
.tl__body h3 { font-size: clamp(1.375rem, 2.6vw, 1.875rem); margin-bottom: .4rem; }
.tl__org {
  margin: 0 0 1rem;
  color: var(--apricot);
  font-size: .9375rem;
}
.tl__body p:last-child {
  margin: 0;
  color: rgba(244, 239, 231, .74);
  font-size: .9375rem;
  line-height: 1.7;
  max-width: 42rem;
}
.tl--now .tl__body h3 { color: var(--cream); }

@media (max-width: 780px) {
  .tl { grid-template-columns: 1fr; }
  .tl__meta { flex-direction: row; align-items: center; gap: 1rem; }
}

/* ─────────── Dishes ─────────── */

.dishes {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(20rem, 100%), 1fr));
  gap: clamp(1.25rem, 3vw, 2.5rem);
}
.dish { margin: 0; }
/* Square: one photo is a tall close-up, the other a landscape dish shot.
   A landscape slot centre-cropped the pizza into abstract toppings; square
   suits both and the source files are cropped to match, so cover() has
   nothing left to throw away. */
.dish__img {
  overflow: hidden;
  border-radius: 3px;
  border: 1px solid var(--rule);
  aspect-ratio: 1 / 1;
  background: var(--ink-2);
}
.dish__img img {
  width: 100%; height: 100%;
  object-fit: cover;
  transition: transform 1s var(--ease), filter .6s var(--ease);
  filter: saturate(.92);
}
.dish:hover .dish__img img { transform: scale(1.05); filter: saturate(1.05); }

.dish figcaption { padding-top: 1.5rem; }
.dish h3 { font-size: 1.375rem; margin-bottom: .5rem; }
.dish figcaption p {
  margin: 0;
  font-size: .9375rem;
  color: rgba(244, 239, 231, .7);
  line-height: 1.65;
  max-width: 26rem;
}

/* ─────── The book — chapters ─────── */

.chapter {
  position: relative;                 /* anchors the rail arrows */
  margin-bottom: clamp(3.5rem, 7vw, 6rem);
}
.chapter:last-of-type { margin-bottom: 0; }

.chapter__head {
  max-width: 44rem;
  margin-bottom: clamp(1.5rem, 3vw, 2.25rem);
  padding-right: 7rem;                /* keeps long headings clear of the arrows */
}
.chapter__label {
  display: flex;
  align-items: center;
  gap: .875rem;
  font-size: .6875rem;
  letter-spacing: .22em;
  text-transform: uppercase;
  font-weight: 500;
  color: var(--blue-lt);
  margin: 0 0 1rem;
}
/* Rule runs out from the label to fill whatever width is left. */
.chapter__label::after {
  content: "";
  flex: 1;
  height: 1px;
  background: var(--rule);
}
.chapter__count { color: rgba(201, 220, 232, .45); letter-spacing: .14em; }

.chapter__head h3 {
  font-family: var(--serif);
  font-weight: 400;
  font-size: clamp(1.75rem, 3.6vw, 2.75rem);
  line-height: 1.05;
  letter-spacing: -.02em;
  margin: 0 0 1rem;
  color: var(--cream);
}
.chapter__head h3 em { font-style: italic; font-weight: 300; color: var(--apricot); }

.chapter__lead {
  margin: 0;
  font-size: .9375rem;
  line-height: 1.7;
  color: rgba(244, 239, 231, .7);
}

/* ─────── The book — scroll rails ─────── */

/* The track breaks out of the centred column to the full viewport width, so
   the row runs off the edge of the screen instead of stopping at a margin —
   that overflowing card is what tells you there is more to scroll. Left
   padding re-aligns the first card with the heading above it. */
.rail__track {
  /* Inset that re-aligns the first card with the heading above it. */
  --rail-inset: max(var(--pad), calc((100vw - var(--maxw)) / 2));
  display: flex;
  gap: clamp(.875rem, 1.6vw, 1.5rem);
  list-style: none;
  margin: 0 calc(50% - 50vw);
  width: 100vw;
  padding: .5rem var(--rail-inset);
  /* Snap points ignore padding unless this is set — without it the browser
     snaps the first card flush to the screen edge on load, knocking the row
     out of line with the heading and leaving the rail pre-scrolled. */
  scroll-padding-inline: var(--rail-inset);
  overflow-x: auto;
  overscroll-behavior-x: contain;
  scroll-snap-type: x proximity;
  scroll-behavior: smooth;
  -webkit-overflow-scrolling: touch;
  scrollbar-width: none;              /* arrows and the cut-off card carry the affordance */
}
.rail__track::-webkit-scrollbar { display: none; }
.rail__track:focus-visible { outline: 2px solid var(--apricot); outline-offset: -2px; }

@media (prefers-reduced-motion: reduce) {
  .rail__track { scroll-behavior: auto; }
}

.plate {
  flex: 0 0 clamp(13.5rem, 20vw, 17rem);
  scroll-snap-align: start;
  display: flex;
  flex-direction: column;
}

.plate__btn {
  display: block;
  width: 100%;
  padding: 0;
  border: 1px solid var(--rule);
  border-radius: 3px;
  overflow: hidden;
  background: var(--ink-2);
  cursor: zoom-in;
  position: relative;
  aspect-ratio: 4 / 5;
  transition: border-color .4s var(--ease);
}
.plate__btn img {
  width: 100%; height: 100%;
  object-fit: cover;
  filter: saturate(.92);
  transition: transform 1s var(--ease), filter .6s var(--ease);
}
.plate:hover .plate__btn,
.plate__btn:focus-visible { border-color: rgba(232, 168, 124, .5); }
.plate:hover .plate__btn img,
.plate__btn:focus-visible img { transform: scale(1.05); filter: saturate(1.05); }

.plate__zoom {
  position: absolute;
  top: .625rem; right: .625rem;
  width: 1.75rem; height: 1.75rem;
  border-radius: 50%;
  background: rgba(8, 19, 31, .72);
  backdrop-filter: blur(4px);
  -webkit-backdrop-filter: blur(4px);
  opacity: 0;
  transform: scale(.8);
  transition: opacity .3s var(--ease), transform .3s var(--pop);
}
.plate__zoom::before, .plate__zoom::after {
  content: "";
  position: absolute;
  top: 50%; left: 50%;
  background: var(--cream);
  transform: translate(-50%, -50%);
}
.plate__zoom::before { width: .625rem; height: 1px; }
.plate__zoom::after  { width: 1px; height: .625rem; }
.plate:hover .plate__zoom,
.plate__btn:focus-visible .plate__zoom { opacity: 1; transform: scale(1); }

.plate__text { padding-top: 1rem; }
.plate__num {
  font-family: var(--serif);
  font-size: .8125rem;
  letter-spacing: .1em;
  color: var(--blue-lt);
  margin: 0 0 .35rem;
  font-variant-numeric: tabular-nums;
}
.plate__text h4 {
  font-family: var(--serif);
  font-weight: 400;
  font-size: 1.0625rem;
  line-height: 1.25;
  letter-spacing: -.01em;
  color: var(--cream);
  margin: 0 0 .4rem;
}
.plate__desc {
  margin: 0;
  font-size: .8125rem;
  line-height: 1.55;
  color: rgba(244, 239, 231, .6);
}

/* Arrows sit level with the chapter heading rather than over the photographs,
   so they never cover the work. */
.rail__nav {
  position: absolute;
  top: 0;
  right: 0;
  width: 2.75rem; height: 2.75rem;
  border: 1px solid var(--rule);
  border-radius: 50%;
  background: transparent;
  cursor: pointer;
  transition: border-color .3s var(--ease), background .3s var(--ease),
              opacity .3s var(--ease);
}
.rail__nav--prev { right: 3.25rem; }
.rail__nav::before {
  content: "";
  position: absolute;
  top: 50%; left: 50%;
  width: .5rem; height: .5rem;
  border-top: 1px solid var(--cream);
  border-right: 1px solid var(--cream);
}
.rail__nav--prev::before { transform: translate(-30%, -50%) rotate(-135deg); }
.rail__nav--next::before { transform: translate(-70%, -50%) rotate(45deg); }
.rail__nav:hover:not(:disabled) {
  border-color: var(--apricot);
  background: rgba(232, 168, 124, .08);
}
.rail__nav:hover:not(:disabled)::before { border-color: var(--apricot); }
.rail__nav:disabled { opacity: .25; cursor: default; }

/* Touch devices swipe; the arrows would only take up room. */
@media (max-width: 700px) {
  .rail__nav { display: none; }
  .chapter__head { padding-right: 0; }
}

/* ─────────── Lightbox ─────────── */

.lb {
  position: fixed;
  inset: 0;
  z-index: 90;
  display: grid;
  place-items: center;
  padding: clamp(1rem, 4vw, 3rem);
  background: rgba(4, 10, 17, .93);
  backdrop-filter: blur(10px);
  -webkit-backdrop-filter: blur(10px);
  animation: lbIn .3s var(--ease);
}
.lb[hidden] { display: none; }
@keyframes lbIn { from { opacity: 0; } to { opacity: 1; } }

.lb__stage {
  margin: 0;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 1.1rem;
  max-width: 100%;
}
.lb__stage img {
  max-width: min(100%, 60rem);
  max-height: 76svh;
  width: auto;
  border-radius: 3px;
  box-shadow: 0 40px 90px -25px rgba(0, 0, 0, .85);
  animation: lbPop .4s var(--spring);
}
@keyframes lbPop {
  from { opacity: 0; transform: scale(.97); }
  to   { opacity: 1; transform: none; }
}
.lb__stage figcaption {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: .5rem;
  text-align: center;
}
.lb__cap {
  font-family: var(--serif);
  font-size: clamp(1rem, .95rem + .4vw, 1.25rem);
  color: var(--cream);
}
.lb__count {
  font-size: .6875rem;
  letter-spacing: .2em;
  text-transform: uppercase;
  color: var(--blue-lt);
  font-variant-numeric: tabular-nums;
}

.lb__close, .lb__nav {
  position: absolute;
  border: 1px solid var(--rule);
  background: rgba(8, 19, 31, .6);
  border-radius: 50%;
  cursor: pointer;
  transition: border-color .3s var(--ease), background .3s var(--ease),
              transform .3s var(--ease);
}
.lb__close:hover, .lb__nav:hover {
  border-color: var(--apricot);
  background: rgba(8, 19, 31, .85);
}

.lb__close {
  top: clamp(1rem, 3vw, 2rem);
  right: clamp(1rem, 3vw, 2rem);
  width: 2.75rem; height: 2.75rem;
}
.lb__close::before, .lb__close::after {
  content: "";
  position: absolute;
  top: 50%; left: 50%;
  width: 1rem; height: 1px;
  background: var(--cream);
}
.lb__close::before { transform: translate(-50%, -50%) rotate(45deg); }
.lb__close::after  { transform: translate(-50%, -50%) rotate(-45deg); }
.lb__close:hover::before, .lb__close:hover::after { background: var(--apricot); }

.lb__nav {
  top: 50%;
  width: 3rem; height: 3rem;
  transform: translateY(-50%);
}
/* Chevron drawn from two borders of a rotated square. */
.lb__nav::before {
  content: "";
  position: absolute;
  top: 50%; left: 50%;
  width: .6rem; height: .6rem;
  border-top: 1px solid var(--cream);
  border-right: 1px solid var(--cream);
}
.lb__nav:hover::before { border-color: var(--apricot); }
.lb__nav--prev { left: clamp(.5rem, 2.5vw, 2rem); }
.lb__nav--prev::before { transform: translate(-30%, -50%) rotate(-135deg); }
.lb__nav--next { right: clamp(.5rem, 2.5vw, 2rem); }
.lb__nav--next::before { transform: translate(-70%, -50%) rotate(45deg); }
.lb__nav:hover { transform: translateY(-50%) scale(1.06); }

@media (max-width: 640px) {
  .lb__nav { top: auto; bottom: clamp(1rem, 4vw, 2rem); transform: none; }
  .lb__nav:hover { transform: scale(1.06); }
  .lb__stage img { max-height: 62svh; }
}

/* Scroll lock while the viewer is open. */
body.lb-open { overflow: hidden; }

/* ─────────── Skills ─────────── */

.skills {
  list-style: none;
  margin: 0; padding: 0;
  display: flex;
  flex-wrap: wrap;
  gap: .75rem;
}
.skills li {
  border: 1px solid var(--rule);
  border-radius: 999px;
  padding: .7rem 1.4rem;
  font-size: .875rem;
  letter-spacing: .02em;
  color: var(--ice);
  transition: border-color .35s var(--ease), color .35s var(--ease),
              background .35s var(--ease), transform .35s var(--ease);
}
.skills li:hover {
  border-color: var(--apricot);
  color: var(--apricot);
  background: rgba(232, 168, 124, .07);
  transform: translateY(-2px);
}

/* ─────────── Beyond ─────────── */

.beyond {
  position: relative;
  padding: clamp(4.5rem, 11vw, 8rem) var(--pad);
  isolation: isolate;
  overflow: hidden;
  border-block: 1px solid var(--rule);
}
.beyond::before {
  content: "";
  position: absolute; inset: 0;
  background-image: var(--tex);
  background-size: cover;
  background-position: center;
  opacity: .4;
  z-index: -2;
}
.beyond::after {
  content: "";
  position: absolute; inset: 0;
  background: linear-gradient(90deg, var(--ink) 15%, rgba(8, 19, 31, .7));
  z-index: -1;
}
.beyond__inner {
  max-width: var(--maxw);
  margin-inline: auto;
  text-shadow: 0 2px 16px rgba(8, 19, 31, .8);
}
.beyond h2 { font-size: clamp(2rem, 4.5vw, 3rem); margin-bottom: 1.75rem; }
.beyond p {
  max-width: 44rem;
  margin: 0;
  font-size: clamp(1.0625rem, 1rem + .3vw, 1.1875rem);
  color: rgba(244, 239, 231, .82);
}

/* ─────────── Contact ─────────── */

/* Closes the page on the same wash it opens with. Full-bleed and faded from
   the top so it lifts out of the preceding section rather than starting on
   a hard line. */
.contact { position: relative; }
.contact::before {
  content: "";
  position: absolute;
  top: 0; bottom: 0;
  left: 50%;
  width: 100vw;
  transform: translateX(-50%);
  background: url("/images/art-hero.jpg") center / cover no-repeat;
  opacity: .4;
  pointer-events: none;
  z-index: -1;
  -webkit-mask-image: linear-gradient(to bottom, transparent 0%, #000 45%);
          mask-image: linear-gradient(to bottom, transparent 0%, #000 45%);
}
.contact > * { position: relative; }

.contact__grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(15rem, 100%), 1fr));
  gap: 1rem;
}
.ccard {
  display: flex;
  flex-direction: column;
  gap: .6rem;
  padding: 1.75rem;
  border: 1px solid var(--rule);
  border-radius: 3px;
  text-decoration: none;
  /* Tinted glass — these sit over the painterly wash, so they need a
     backdrop of their own to stay readable. */
  background: rgba(8, 19, 31, .55);
  backdrop-filter: blur(6px);
  -webkit-backdrop-filter: blur(6px);
  transition: border-color .35s var(--ease), transform .35s var(--ease),
              background .35s var(--ease);
}
.ccard:hover {
  border-color: var(--apricot);
  transform: translateY(-3px);
  background: rgba(8, 19, 31, .72);
}
.ccard__label {
  font-size: .6875rem; letter-spacing: .16em; text-transform: uppercase;
  color: var(--blue-lt); font-weight: 500;
}
.ccard__value {
  font-family: var(--serif);
  font-size: 1.0625rem;
  color: var(--cream);
  word-break: break-word;
  transition: color .35s var(--ease);
}
.ccard:hover .ccard__value { color: var(--apricot); }

.refs {
  margin: 3rem 0 0;
  padding-top: 2rem;
  border-top: 1px solid var(--rule);
  font-size: .9375rem;
  color: rgba(201, 220, 232, .68);
  max-width: 44rem;
}
.refs strong { color: var(--cream); font-weight: 500; }

/* ─────────── Footer ─────────── */

.foot {
  border-top: 1px solid var(--rule);
  background: var(--ink-2);
  padding: clamp(2.5rem, 5vw, 3.5rem) var(--pad);
  text-align: center;
}
.foot__name {
  font-family: var(--serif);
  font-size: 1.5rem;
  margin: 0 0 .5rem;
  color: var(--cream);
}
.foot__meta {
  margin: 0;
  font-size: .75rem;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: rgba(201, 220, 232, .55);
}

/* ─────────── Reveal ─────────── */

/* Only hide when JS is live to un-hide it. No JS = plain, readable page. */
.js .reveal {
  opacity: 0;
  transform: translateY(26px);
  transition: opacity 1s var(--spring), transform 1s var(--spring);
  will-change: transform, opacity;
}
.js .reveal.is-in { opacity: 1; transform: none; }
.js .reveal.is-in { will-change: auto; }

/* ─────────── Motion layer ─────────── */

/* Scroll progress rail */
.progress {
  position: fixed;
  top: 0; left: 0; right: 0;
  height: 2px;
  z-index: 60;
  background: transparent;
  pointer-events: none;
}
.progress span {
  display: block;
  height: 100%;
  width: 100%;
  transform: scaleX(0);
  transform-origin: left;
  background: linear-gradient(90deg, var(--blue), var(--apricot), var(--gold));
}
html:not(.js) .progress { display: none; }

/* Headings wipe up behind their own baseline. The clip lives on an inner
   wrapper span injected by JS — never on the observed heading itself, or the
   IntersectionObserver sees zero area and the reveal deadlocks.
   Gated on .js so without scripting the text simply sits there, visible. */
.mask { display: block; }
.js .mask {
  clip-path: inset(-.25em 0 105% 0);
  transform: translateY(.14em);
  transition: clip-path 1.15s var(--spring), transform 1.15s var(--spring);
}
.js .mask.is-in {
  clip-path: inset(-.25em 0 -.25em 0);
  transform: none;
}

/* Parallax targets are moved by JS via a custom property, so the transform
   stays composited and nothing triggers layout. */
.js [data-speed] { will-change: transform; }

/* Buttons lean toward the cursor (magnetic), driven by JS vars. */
.btn, .nav__cta {
  transform: translate(var(--mx, 0px), var(--my, 0px));
}
.btn:hover, .nav__cta:hover { transition: transform .18s var(--ease); }

.stat__fig [data-count] { font-variant-numeric: tabular-nums; }

@media (prefers-reduced-motion: reduce) {
  .reveal { opacity: 1; transform: none; transition: none; }
  .hero__portrait img { animation: none; }
  .hero__scroll span { animation: none; }
  .scorebar__fill::after { transform: scaleX(1); transition: none; }
  .tl::before { transition: none; }
  *, *::before, *::after {
    animation-duration: .001ms !important;
    transition-duration: .001ms !important;
  }
}
