/* =============================================================================
   All 4 One Farms
   main.css is the only stylesheet on the site. No build step, no inline styles.
   If you need a component that is not here, add it to the section where it
   belongs. Section banners below are for code navigation only.

   01  Fonts
   02  Tokens
   03  Reset and base
   04  Type
   05  Layout primitives
   06  Header and navigation
   07  Buttons, links, marks
   08  Photography: bands, scrims, pairings
   09  Dark band
   10  Reviews
   11  Clock timeline
   12  Dialogs, inbox frame
   13  Forms, chips
   14  Calendar
   15  Details / FAQ
   16  Prose (journal)
   17  Rate table
   18  Footer
   19  Motion and reveals
   20  Print
   21  Framing: how a photograph is held on the page
   22  Social marks
   23  Journal
   24  Gallery, scroll story
============================================================================= */

/* -----------------------------------------------------------------------------
   01  Fonts
   Phase-one stand-ins. Swapping in the licensed families is a file drop plus
   the src line; the family names stay "Venue Serif" and "Venue Sans".
----------------------------------------------------------------------------- */

@font-face {
  font-family: "Venue Serif";
  src: url("../fonts/quinela-400.woff2") format("woff2");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Venue Serif";
  src: url("../fonts/quinela-400italic.woff2") format("woff2");
  font-weight: 400;
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: "Venue Serif";
  src: url("../fonts/quinela-500.woff2") format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Venue Serif";
  src: url("../fonts/quinela-500italic.woff2") format("woff2");
  font-weight: 500;
  font-style: italic;
  font-display: swap;
}

@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-400.woff2") format("woff2");
  font-weight: 400;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-400italic.woff2") format("woff2");
  font-weight: 400;
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-500.woff2") format("woff2");
  font-weight: 500;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-500italic.woff2") format("woff2");
  font-weight: 500;
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-600.woff2") format("woff2");
  font-weight: 600;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-600italic.woff2") format("woff2");
  font-weight: 600;
  font-style: italic;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-700.woff2") format("woff2");
  font-weight: 700;
  font-style: normal;
  font-display: swap;
}
@font-face {
  font-family: "Venue Sans";
  src: url("../fonts/parson-700italic.woff2") format("woff2");
  font-weight: 700;
  font-style: italic;
  font-display: swap;
}

/* -----------------------------------------------------------------------------
   02  Tokens
----------------------------------------------------------------------------- */

:root {
  /* Palette */
  --cream: #f4eee3;
  --linen: #fbf8f2;
  --ink: #1c1a16;
  --muted: #5f5a50;
  --hairline: #e3dccd;
  --pine: #1e3a2f;
  --pine-deep: #132520;
  --brass: #9c7c46;
  --brass-text: #7f6533;
  --brass-light: #c9ae7a;
  --on-dark: #f4eee3;
  --on-dark-muted: #b9b2a3;

  /* Type families */
  --font-display: "Venue Serif", "Iowan Old Style", "Palatino Linotype", Georgia, serif;
  --font-body: "Venue Sans", "Helvetica Neue", Arial, sans-serif;

  /* Type scale, desktop / mobile per the brief */
  --t-h1: clamp(2.5rem, 1.2rem + 5.8vw, 4.5rem);
  --t-h2: clamp(2rem, 1.1rem + 2.8vw, 3rem);
  --t-h3: clamp(1.5rem, 1.15rem + 0.95vw, 1.875rem);
  --t-lead: clamp(1.125rem, 1.02rem + 0.32vw, 1.3125rem);
  --t-body: clamp(1rem, 0.965rem + 0.11vw, 1.0625rem);
  --t-small: 0.875rem;
  --t-label: 0.75rem;

  /* Layout */
  --wrap: 1320px;
  --gutter: clamp(1.5rem, 4vw, 3.5rem);
  --section-y: clamp(4.5rem, 2.5rem + 5vw, 7rem);
  --measure: 64ch;
  --radius-pill: 999px;

  /* Scrims. The hero photograph has a blown white sky behind the nav and bright
     grass behind the headline, so both scrims are sized for the worst case: they
     hold at least 0.68 alpha everywhere cream text actually sits, which keeps
     cream at 4.5:1 or better even if the pixel underneath were pure white. */
  --scrim-top: linear-gradient(to bottom, rgba(19, 37, 32, 0.74) 0px, rgba(19, 37, 32, 0.68) 92px, rgba(19, 37, 32, 0.3) 175px, rgba(19, 37, 32, 0) 265px);
  --scrim-bottom: linear-gradient(to top, rgba(19, 37, 32, 0.88) 0px, rgba(19, 37, 32, 0.82) 200px, rgba(19, 37, 32, 0.74) 440px, rgba(19, 37, 32, 0.7) 560px, rgba(19, 37, 32, 0.36) 680px, rgba(19, 37, 32, 0.1) 780px, rgba(19, 37, 32, 0) 900px);

  /* Motion */
  --ease: cubic-bezier(0.2, 0.6, 0.2, 1);
}

/* -----------------------------------------------------------------------------
   03  Reset and base
----------------------------------------------------------------------------- */

*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  -webkit-text-size-adjust: 100%;
  scroll-behavior: smooth;
  scroll-padding-top: 6rem;
}

body {
  margin: 0;
  background: var(--cream);
  color: var(--ink);
  font-family: var(--font-body);
  font-size: var(--t-body);
  line-height: 1.6;
  font-weight: 400;
  overflow-x: hidden;
  -webkit-font-smoothing: antialiased;
}

h1,
h2,
h3,
h4,
p,
figure,
blockquote,
ul,
ol,
dl,
dd {
  margin: 0;
}

ul,
ol {
  padding: 0;
  list-style: none;
}

img,
picture,
video,
svg {
  display: block;
  max-width: 100%;
}

img {
  height: auto;
}

a {
  color: inherit;
}

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

hr {
  border: 0;
  border-top: 1px solid var(--hairline);
  margin: 0;
}

:focus-visible {
  outline: 2px solid var(--brass);
  outline-offset: 2px;
}

.skip-link {
  position: absolute;
  left: 0.75rem;
  top: -6rem;
  z-index: 100;
  background: var(--pine);
  color: var(--on-dark);
  padding: 0.75rem 1.25rem;
  border-radius: 0 0 4px 4px;
  font-size: var(--t-small);
  font-weight: 600;
  transition: top 0.18s var(--ease);
}

.skip-link:focus {
  top: 0;
}

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

/* -----------------------------------------------------------------------------
   04  Type
----------------------------------------------------------------------------- */

h1,
h2,
h3,
.display {
  font-family: var(--font-display);
  font-weight: 400;
  color: var(--ink);
  letter-spacing: -0.012em;
  text-wrap: balance;
}

h1,
.h1 {
  font-size: var(--t-h1);
  line-height: 1.02;
}

h2,
.h2 {
  font-size: var(--t-h2);
  line-height: 1.08;
}

h3,
.h3 {
  font-size: var(--t-h3);
  line-height: 1.18;
}

h1 em,
h2 em,
h3 em,
.h1 em,
.h2 em,
.h3 em {
  font-style: italic;
}

p {
  max-width: var(--measure);
}

.lead {
  font-size: var(--t-lead);
  line-height: 1.5;
  color: var(--ink);
}

.serif-body {
  font-family: var(--font-display);
  font-size: var(--t-lead);
  line-height: 1.55;
}

.small {
  font-size: var(--t-small);
  line-height: 1.55;
}

.muted {
  color: var(--muted);
}

.stack > * + * {
  margin-top: 1.25rem;
}

.stack-tight > * + * {
  margin-top: 0.5rem;
}

.stack-wide > * + * {
  margin-top: 2rem;
}

/* -----------------------------------------------------------------------------
   05  Layout primitives
----------------------------------------------------------------------------- */

.wrap {
  width: 100%;
  max-width: var(--wrap);
  margin-inline: auto;
  padding-inline: var(--gutter);
}

.wrap--narrow {
  max-width: 860px;
}

.section {
  padding-block: var(--section-y);
}

.section--tight {
  padding-block: clamp(3rem, 1.5rem + 4vw, 4.5rem);
}

.section--flush-top {
  padding-top: 0;
}

.section-head {
  max-width: 46ch;
}

.section-head h2 {
  margin-bottom: 1rem;
}

/* Hairline rules stand in for boxes. Never wrap a section in a card. */
.rule {
  border-top: 1px solid var(--hairline);
  margin-block: clamp(2.5rem, 4vw, 4rem);
}

.rule--short {
  width: 88px;
  border-top: 1px solid var(--brass);
  margin-block: 1.5rem;
}

.rule--on-dark {
  border-top-color: rgba(244, 238, 227, 0.22);
}

.grid {
  display: grid;
  gap: clamp(1.5rem, 3vw, 2.75rem);
}

@media (min-width: 768px) {
  .grid--2 {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

/* -----------------------------------------------------------------------------
   06  Header and navigation
----------------------------------------------------------------------------- */

.site-header {
  position: sticky;
  top: 0;
  z-index: 60;
  background: var(--cream);
  border-bottom: 1px solid var(--hairline);
  transition: background 0.25s var(--ease), border-color 0.25s var(--ease), color 0.25s var(--ease);
}

/* Home only. The header floats over the hero until the sentinel scrolls out. */
body.hero-page .site-header {
  position: fixed;
  left: 0;
  right: 0;
  background: transparent;
  border-bottom-color: transparent;
  color: var(--on-dark);
}

body.hero-page .site-header.is-solid {
  background: var(--cream);
  border-bottom-color: var(--hairline);
  color: var(--ink);
}

/* While the header floats over the hero, its two actions have to read against a
   photograph, so they take the on-dark treatment until the header goes solid. */
@media (min-width: 960px) {
  body.hero-page .site-header:not(.is-solid) .site-nav__actions .btn--primary {
    background: var(--cream);
    border-color: var(--cream);
    color: var(--pine);
  }

  body.hero-page .site-header:not(.is-solid) .site-nav__actions .btn--primary:hover {
    background: var(--on-dark-muted);
    border-color: var(--on-dark-muted);
    color: var(--pine-deep);
  }

  body.hero-page .site-header:not(.is-solid) .site-nav__actions .link {
    text-decoration-color: var(--brass-light);
  }

  body.hero-page .site-header:not(.is-solid) .site-nav__actions .link:hover {
    color: var(--brass-light);
    text-decoration-color: var(--brass-light);
  }
}

.site-header__inner {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1.5rem;
  min-height: 82px;
}

.wordmark {
  font-family: var(--font-display);
  font-size: 1.5rem;
  line-height: 1;
  letter-spacing: -0.01em;
  text-decoration: none;
  white-space: nowrap;
  flex: 0 0 auto;
}

.wordmark__four {
  font-style: italic;
}

.site-nav {
  display: flex;
  align-items: center;
  gap: clamp(1.25rem, 2vw, 2.25rem);
  margin-left: auto;
}

.site-nav__list {
  display: flex;
  align-items: center;
  gap: clamp(1.1rem, 1.8vw, 1.9rem);
}

.site-nav__list a {
  font-size: 0.875rem;
  font-weight: 500;
  letter-spacing: 0.005em;
  text-decoration: none;
  padding-block: 0.4rem;
  border-bottom: 1px solid transparent;
  white-space: nowrap;
}

.site-nav__list a:hover,
.site-nav__list a[aria-current="page"] {
  border-bottom-color: currentColor;
}

.site-nav__actions {
  display: flex;
  align-items: center;
  gap: clamp(1rem, 1.6vw, 1.5rem);
}

.nav-toggle {
  display: none;
  align-items: center;
  gap: 0.6rem;
  background: none;
  border: 0;
  padding: 0.6rem 0;
  cursor: pointer;
  font-size: var(--t-small);
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: inherit;
}

.nav-toggle__bars {
  display: block;
  position: relative;
  width: 22px;
  height: 9px;
}

.nav-toggle__bars::before,
.nav-toggle__bars::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  height: 1px;
  background: currentColor;
  transition: transform 0.22s var(--ease);
}

.nav-toggle__bars::before {
  top: 0;
}

.nav-toggle__bars::after {
  bottom: 0;
}

.nav-toggle[aria-expanded="true"] .nav-toggle__bars::before {
  transform: translateY(4px) rotate(45deg);
}

.nav-toggle[aria-expanded="true"] .nav-toggle__bars::after {
  transform: translateY(-4px) rotate(-45deg);
}

@media (max-width: 959px) {
  .nav-toggle {
    display: inline-flex;
  }

  /* The drawer is a child of the header, so the wordmark and the close control
     are lifted above it rather than the drawer being pushed below the header.
     While it is open the header goes transparent with cream text, because the
     pine drawer is what sits behind those two things. */
  .wordmark,
  .nav-toggle {
    position: relative;
    z-index: 60;
  }

  body.nav-open .site-header,
  body.nav-open.hero-page .site-header.is-solid {
    background: transparent;
    border-bottom-color: transparent;
    color: var(--on-dark);
  }

  .site-nav {
    position: fixed;
    inset: 0;
    z-index: 55;
    flex-direction: column;
    align-items: flex-start;
    justify-content: center;
    gap: 0;
    background: var(--pine);
    color: var(--on-dark);
    padding: 6rem var(--gutter) 3rem;
    transform: translateY(-100%);
    visibility: hidden;
    transition: transform 0.3s var(--ease), visibility 0.3s var(--ease);
    overflow-y: auto;
  }

  .site-nav.is-open {
    transform: translateY(0);
    visibility: visible;
  }

  .site-nav__list {
    flex-direction: column;
    align-items: flex-start;
    gap: 0;
    width: 100%;
  }

  .site-nav__list li {
    width: 100%;
    border-bottom: 1px solid rgba(244, 238, 227, 0.18);
  }

  .site-nav__list a {
    display: block;
    font-family: var(--font-display);
    font-size: 1.75rem;
    font-weight: 400;
    padding-block: 0.85rem;
    border-bottom: 0;
  }

  .site-nav__actions {
    flex-direction: column;
    align-items: flex-start;
    gap: 1.5rem;
    margin-top: 2.25rem;
  }

  .site-nav__actions .link {
    color: var(--on-dark);
    text-decoration-color: var(--brass-light);
  }

  .site-nav__actions .btn--primary {
    background: var(--cream);
    color: var(--pine);
    border-color: var(--cream);
  }

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

/* -----------------------------------------------------------------------------
   07  Buttons, links, marks
----------------------------------------------------------------------------- */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: 48px;
  padding: 0.75rem 1.75rem;
  border-radius: var(--radius-pill);
  border: 1px solid var(--pine);
  background: var(--pine);
  color: var(--on-dark);
  font-size: 0.9375rem;
  font-weight: 600;
  letter-spacing: 0.005em;
  text-decoration: none;
  cursor: pointer;
  text-align: center;
  transition: background 0.2s var(--ease), color 0.2s var(--ease), border-color 0.2s var(--ease);
}

.btn--primary:hover {
  background: var(--pine-deep);
  border-color: var(--pine-deep);
}

.btn--secondary {
  background: transparent;
  color: var(--pine);
}

.btn--secondary:hover {
  background: var(--pine);
  color: var(--on-dark);
}

/* On pine bands and over photographs. */
.btn--on-dark {
  background: var(--cream);
  border-color: var(--cream);
  color: var(--pine);
}

.btn--on-dark:hover {
  background: var(--on-dark-muted);
  border-color: var(--on-dark-muted);
  color: var(--pine-deep);
}

.btn--ghost-dark {
  background: transparent;
  border-color: var(--cream);
  color: var(--cream);
}

.btn--ghost-dark:hover {
  background: var(--cream);
  color: var(--pine);
}

.btn[disabled],
.btn[aria-disabled="true"] {
  opacity: 0.45;
  cursor: not-allowed;
}

.btn-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 0.875rem 1.25rem;
}

/* Text links: hairline brass underline, text goes pine on hover. No arrows. */
.link {
  color: inherit;
  text-decoration: underline;
  text-decoration-color: var(--brass-text);
  text-decoration-thickness: 1px;
  text-underline-offset: 0.32em;
  font-weight: 500;
  transition: color 0.18s var(--ease), text-decoration-color 0.18s var(--ease);
}

.link:hover {
  color: var(--pine);
  text-decoration-color: var(--pine);
}

.link--on-dark {
  color: var(--on-dark);
  text-decoration-color: var(--brass-light);
}

.link--on-dark:hover {
  color: var(--brass-light);
  text-decoration-color: var(--brass-light);
}

/* Eyebrow. Three per page maximum, hero included. */
.eyebrow {
  display: block;
  font-family: var(--font-body);
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--brass-text);
  margin-bottom: 1.25rem;
}

.eyebrow--on-dark,
.on-dark .eyebrow {
  color: var(--brass-light);
}

/* Brass dot list marker. The only list mark on the site. */
.dot-list li {
  position: relative;
  padding-left: 1.4rem;
  margin-bottom: 0.6rem;
}

.dot-list li::before {
  content: "";
  position: absolute;
  left: 0;
  top: 0.72em;
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--brass);
}

.on-dark .dot-list li::before {
  background: var(--brass-light);
}

.col-list {
  columns: 1;
}

@media (min-width: 768px) {
  .col-list {
    columns: 2;
    column-gap: clamp(2rem, 4vw, 4rem);
  }

  .col-list li {
    break-inside: avoid;
  }
}

/* -----------------------------------------------------------------------------
   08  Photography: bands, scrims, pairings
----------------------------------------------------------------------------- */

.bleed {
  position: relative;
  width: 100%;
}

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

/* Hero */
.hero {
  position: relative;
  min-height: 100vh;
  min-height: 100svh;
  display: flex;
  align-items: flex-end;
  overflow: hidden;
  background: var(--pine-deep);
  color: var(--on-dark);
}

.hero__media {
  position: absolute;
  inset: 0;
  z-index: 0;
}

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

/* Both scrims must sit above .hero__media. Without the z-index the ::before
   would paint underneath the photograph, because it precedes the media in the
   box tree, and the header would lose its contrast against a bright sky. */
.hero::before,
.hero::after {
  content: "";
  position: absolute;
  left: 0;
  right: 0;
  z-index: 1;
  pointer-events: none;
}

.hero::before {
  top: 0;
  height: 265px;
  background: var(--scrim-top);
}

.hero::after {
  bottom: 0;
  height: 100%;
  background: var(--scrim-bottom);
}

.hero__inner {
  position: relative;
  z-index: 2;
  width: 100%;
  padding-block: clamp(3.5rem, 7vh, 6rem);
}

.hero h1 {
  color: var(--on-dark);
  max-width: 15ch;
}

.hero__sub {
  font-size: var(--t-lead);
  line-height: 1.45;
  color: var(--on-dark);
  max-width: 42ch;
  margin-top: 1.5rem;
}

.hero__note {
  font-size: var(--t-small);
  color: var(--on-dark);
  margin-top: 1.5rem;
  max-width: 46ch;
}

.hero .btn-row {
  margin-top: 2rem;
}

/* Text over a photograph is cream, never brass. Brass-light is only safe on a
   flat pine band, where it measures 5.77:1. */
.hero .eyebrow,
.photo-band .eyebrow {
  color: var(--on-dark);
}

/* Reduced-height hero strip for inner pages. */
.hero--strip {
  min-height: 0;
  height: clamp(340px, 46vh, 480px);
}

.hero--strip h1 {
  max-width: 20ch;
}

/* Sentinel the header watches to decide transparent or solid. */
.header-sentinel {
  position: absolute;
  top: 0;
  left: 0;
  width: 1px;
  height: 78vh;
  pointer-events: none;
}

/* Full-bleed photo band with a cream panel sitting on it. */
.photo-band {
  position: relative;
  isolation: isolate;
  display: grid;
  align-items: center;
  min-height: clamp(460px, 62vh, 640px);
  overflow: hidden;
}

.photo-band__media {
  position: absolute;
  inset: 0;
  z-index: -2;
}

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

.photo-band::before {
  content: "";
  position: absolute;
  inset: 0;
  z-index: -1;
  background: linear-gradient(to right, rgba(19, 37, 32, 0.55) 0%, rgba(19, 37, 32, 0.2) 60%, rgba(19, 37, 32, 0.1) 100%);
}

.photo-band__panel {
  background: var(--cream);
  padding: clamp(2rem, 4vw, 3.25rem);
  max-width: 560px;
  border-top: 2px solid var(--brass);
}

.photo-band__panel > * + * {
  margin-top: 1.25rem;
}

.photo-band__panel .btn-row {
  margin-top: 1.75rem;
}

/* Asymmetric pairing: photo 7 columns, text 5. */
.pair {
  display: grid;
  gap: clamp(1.75rem, 3vw, 3.25rem);
  align-items: center;
}

/* Two pairings in one section breathe like two sections would. */
.pair + .pair {
  margin-top: clamp(3.5rem, 7vw, 6.5rem);
}

.pair__media img {
  width: 100%;
  height: auto;
}

.pair__body > * + * {
  margin-top: 1.25rem;
}

@media (min-width: 900px) {
  .pair {
    grid-template-columns: repeat(12, minmax(0, 1fr));
    gap: clamp(2rem, 4vw, 4.5rem);
  }

  .pair__media {
    grid-column: 1 / span 7;
  }

  .pair__body {
    grid-column: 8 / span 5;
  }

  .pair--flip .pair__media {
    grid-column: 6 / span 7;
    grid-row: 1;
  }

  .pair--flip .pair__body {
    grid-column: 1 / span 5;
    grid-row: 1;
  }
}

/* Editorial spread: photos at deliberately different sizes, no card grid. */
.spread {
  display: grid;
  gap: clamp(2.25rem, 4vw, 3.5rem);
}

@media (min-width: 800px) {
  .spread {
    grid-template-columns: repeat(12, minmax(0, 1fr));
    row-gap: clamp(3rem, 6vw, 5.5rem);
  }

  .spread__item:nth-child(1) {
    grid-column: 1 / span 7;
  }

  .spread__item:nth-child(2) {
    grid-column: 9 / span 4;
    align-self: end;
    padding-bottom: 2rem;
  }

  .spread__item:nth-child(3) {
    grid-column: 1 / span 4;
    padding-top: 2rem;
  }

  .spread__item:nth-child(4) {
    grid-column: 6 / span 7;
  }
}

.spread__item h3 {
  margin-top: 1.5rem;
}

.spread__item h3 a {
  text-decoration: none;
  border-bottom: 1px solid transparent;
}

.spread__item h3 a:hover {
  border-bottom-color: var(--brass);
}

.spread__item p {
  margin-top: 0.65rem;
  color: var(--muted);
  max-width: 38ch;
}

figure {
  margin: 0;
}

figcaption {
  font-size: var(--t-small);
  color: var(--muted);
  margin-top: 0.75rem;
}

/* -----------------------------------------------------------------------------
   09  Dark band
----------------------------------------------------------------------------- */

.band-dark {
  background: var(--pine);
  color: var(--on-dark);
}

.band-dark h1,
.band-dark h2,
.band-dark h3 {
  color: var(--on-dark);
}

.band-dark .muted,
.band-dark .lead.muted {
  color: var(--on-dark-muted);
}

.band-deep {
  background: var(--pine-deep);
  color: var(--on-dark);
}

/* -----------------------------------------------------------------------------
   10  Reviews
----------------------------------------------------------------------------- */

.review-spread {
  display: grid;
  gap: clamp(2.5rem, 5vw, 4rem);
}

@media (min-width: 900px) {
  .review-spread {
    grid-template-columns: repeat(12, minmax(0, 1fr));
    align-items: start;
  }

  .review-spread__quotes {
    grid-column: 1 / span 7;
  }

  .review-spread__media {
    grid-column: 9 / span 4;
    position: sticky;
    top: 7rem;
  }
}

.review {
  padding-block: clamp(1.75rem, 3vw, 2.5rem);
  border-top: 1px solid var(--hairline);
}

.review:first-child {
  border-top: 0;
  padding-top: 0;
}

.review blockquote {
  font-family: var(--font-display);
  font-size: clamp(1.375rem, 0.9rem + 1.7vw, 1.875rem);
  line-height: 1.32;
  letter-spacing: -0.01em;
  max-width: 30ch;
}

.review figcaption {
  margin-top: 1rem;
  font-size: var(--t-small);
  font-weight: 500;
  color: var(--muted);
  letter-spacing: 0.02em;
}

.rating-line {
  font-size: var(--t-lead);
  font-family: var(--font-display);
  margin-bottom: 2rem;
}

/* -----------------------------------------------------------------------------
   11  Clock timeline
   Steps are marked by a time of day, never by a decorative ordinal number.
----------------------------------------------------------------------------- */

.clockline {
  display: grid;
  gap: 0;
  margin-top: 2.5rem;
  counter-reset: none;
}

.clockline__step {
  display: grid;
  gap: 0.35rem 2rem;
  padding-block: clamp(1.25rem, 2.5vw, 1.75rem);
  border-top: 1px solid rgba(244, 238, 227, 0.22);
}

.clockline__step:last-child {
  border-bottom: 1px solid rgba(244, 238, 227, 0.22);
}

.clockline__time {
  font-family: var(--font-body);
  font-size: var(--t-small);
  font-weight: 600;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--brass-light);
  white-space: nowrap;
  padding-top: 0.35rem;
}

.clockline__title {
  font-family: var(--font-display);
  font-size: clamp(1.25rem, 0.9rem + 1.1vw, 1.625rem);
  line-height: 1.2;
}

.clockline__body {
  color: var(--on-dark-muted);
  font-size: var(--t-body);
  max-width: 56ch;
  margin-top: 0.4rem;
}

@media (min-width: 720px) {
  .clockline__step {
    grid-template-columns: 108px minmax(0, 1fr);
  }

  .clockline__time {
    grid-row: 1 / span 2;
  }
}

/* Light-ground variant for /weddings and /tour. */
.clockline--light .clockline__step {
  border-top-color: var(--hairline);
}

.clockline--light .clockline__step:last-child {
  border-bottom-color: var(--hairline);
}

.clockline--light .clockline__time {
  color: var(--brass-text);
}

.clockline--light .clockline__body {
  color: var(--muted);
}

/* -----------------------------------------------------------------------------
   12  Dialogs, inbox frame
----------------------------------------------------------------------------- */

dialog.dialog {
  width: min(920px, calc(100vw - 2rem));
  max-height: calc(100vh - 3rem);
  padding: 0;
  border: 0;
  border-radius: 2px;
  background: var(--cream);
  color: var(--ink);
  overflow: auto;
}

dialog.dialog::backdrop {
  background: rgba(19, 37, 32, 0.7);
}

.dialog__head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 1.5rem;
  padding: clamp(1.25rem, 3vw, 1.75rem) clamp(1.25rem, 3vw, 2rem);
  border-bottom: 1px solid var(--hairline);
}

.dialog__title {
  font-family: var(--font-display);
  font-size: 1.375rem;
  line-height: 1.2;
}

.dialog__body {
  padding: clamp(1.25rem, 3vw, 2rem);
}

.dialog__body--flush {
  padding: 0;
}

.dialog__close {
  flex: 0 0 auto;
  background: none;
  border: 1px solid var(--hairline);
  border-radius: var(--radius-pill);
  min-height: 40px;
  padding: 0.35rem 1.1rem;
  font-size: var(--t-small);
  font-weight: 600;
  cursor: pointer;
  color: var(--muted);
}

.dialog__close:hover {
  border-color: var(--pine);
  color: var(--pine);
}

.dialog__foot {
  padding: 0 clamp(1.25rem, 3vw, 2rem) clamp(1.25rem, 3vw, 2rem);
}

/* Map embed. The iframe is injected on first open and blanked on close. */
.map-frame {
  width: 100%;
  aspect-ratio: 16 / 10;
  background: var(--hairline);
}

.map-frame iframe {
  display: block;
  width: 100%;
  height: 100%;
  border: 0;
}

/* Mock inbox. Used by the inquiry result and the pricing guide capture. */
.inbox-frame__label {
  display: block;
  font-size: var(--t-small);
  font-weight: 600;
  letter-spacing: 0.02em;
  color: var(--muted);
  background: var(--cream);
  border: 1px solid var(--hairline);
  border-bottom: 0;
  padding: 0.7rem 1rem;
}

.inbox-frame {
  background: var(--linen);
  border: 1px solid var(--hairline);
}

.inbox-frame__meta {
  padding: 1rem 1.25rem;
  border-bottom: 1px solid var(--hairline);
  font-size: var(--t-small);
  line-height: 1.7;
}

.inbox-frame__row {
  display: flex;
  gap: 0.6rem;
}

.inbox-frame__key {
  flex: 0 0 4.25rem;
  color: var(--muted);
}

.inbox-frame__value {
  min-width: 0;
  word-break: break-word;
}

.inbox-frame__subject {
  font-weight: 600;
}

.inbox-frame__body {
  padding: clamp(1.25rem, 3vw, 1.75rem);
  font-size: var(--t-body);
  line-height: 1.65;
}

.inbox-frame__body > * + * {
  margin-top: 1rem;
}

.inbox-frame__body p {
  max-width: 60ch;
}

/* -----------------------------------------------------------------------------
   13  Forms, chips
----------------------------------------------------------------------------- */

.field {
  display: block;
  margin-bottom: 1.25rem;
}

.field__label {
  display: block;
  font-size: var(--t-small);
  font-weight: 600;
  margin-bottom: 0.5rem;
}

.field__hint {
  display: block;
  font-size: var(--t-small);
  color: var(--muted);
  margin-bottom: 0.5rem;
}

.input,
.select,
.textarea {
  display: block;
  width: 100%;
  min-height: 48px;
  padding: 0.7rem 0.9rem;
  background: var(--linen);
  border: 1px solid var(--hairline);
  border-radius: 2px;
  font-size: 1rem;
  line-height: 1.4;
  color: var(--ink);
  transition: border-color 0.18s var(--ease), box-shadow 0.18s var(--ease);
}

.textarea {
  min-height: 132px;
  resize: vertical;
}

.select {
  appearance: none;
  background-image: linear-gradient(45deg, transparent 50%, var(--muted) 50%),
    linear-gradient(135deg, var(--muted) 50%, transparent 50%);
  background-position: calc(100% - 20px) calc(50% + 1px), calc(100% - 14px) calc(50% + 1px);
  background-size: 6px 6px, 6px 6px;
  background-repeat: no-repeat;
  padding-right: 2.75rem;
}

.input:focus,
.select:focus,
.textarea:focus {
  outline: none;
  border-color: var(--pine);
  box-shadow: inset 0 0 0 1px var(--pine);
}

.input:focus-visible,
.select:focus-visible,
.textarea:focus-visible {
  outline: 2px solid var(--brass);
  outline-offset: 2px;
}

.field__error {
  display: block;
  font-size: var(--t-small);
  color: var(--ink);
  margin-top: 0.5rem;
}

.field__error:empty {
  display: none;
}

.honeypot {
  position: absolute;
  left: -9999px;
  width: 1px;
  height: 1px;
  overflow: hidden;
}

fieldset {
  border: 0;
  padding: 0;
  margin: 0 0 2rem;
  min-width: 0;
}

legend {
  padding: 0;
  font-family: var(--font-display);
  font-size: var(--t-h3);
  line-height: 1.2;
  margin-bottom: 1.25rem;
}

.form-panel {
  background: var(--linen);
  border-top: 2px solid var(--brass);
  padding: clamp(1.5rem, 4vw, 3rem);
}

.form-grid {
  display: grid;
  gap: 0 1.25rem;
}

@media (min-width: 640px) {
  .form-grid--2 {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

/* Chips */
.chip-group {
  display: flex;
  flex-wrap: wrap;
  gap: 0.6rem;
}

.chip {
  display: inline-flex;
  align-items: center;
  min-height: 44px;
  padding: 0.55rem 1.1rem;
  border: 1px solid var(--hairline);
  border-radius: var(--radius-pill);
  background: var(--linen);
  color: var(--ink);
  font-size: 0.9375rem;
  font-weight: 500;
  cursor: pointer;
  transition: background 0.16s var(--ease), border-color 0.16s var(--ease), color 0.16s var(--ease);
}

.chip:hover {
  border-color: var(--pine);
}

.chip[aria-pressed="true"] {
  background: var(--pine);
  border-color: var(--pine);
  color: var(--on-dark);
}

.chip[disabled] {
  opacity: 0.4;
  cursor: not-allowed;
}

/* Named progress line. Steps are words, never numbers. */
.progress-line {
  display: flex;
  flex-wrap: wrap;
  gap: 0.35rem 1.35rem;
  padding-bottom: 1rem;
  border-bottom: 1px solid var(--brass);
  margin-bottom: 2rem;
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
}

.progress-line__step[aria-current="step"] {
  color: var(--brass-text);
}

.progress-line__step.is-done {
  color: var(--pine);
}

/* -----------------------------------------------------------------------------
   14  Calendar
----------------------------------------------------------------------------- */

.cal {
  width: 100%;
}

.cal__head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  margin-bottom: 1.25rem;
}

.cal__month {
  font-family: var(--font-display);
  font-size: var(--t-h3);
  line-height: 1.2;
}

.cal__nav {
  display: flex;
  gap: 0.5rem;
}

.cal__nav button {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  border: 1px solid var(--hairline);
  border-radius: 50%;
  background: var(--linen);
  cursor: pointer;
  color: var(--ink);
}

.cal__nav button:hover:not([disabled]) {
  border-color: var(--pine);
}

.cal__nav button[disabled] {
  opacity: 0.35;
  cursor: not-allowed;
}

.cal__nav svg {
  width: 14px;
  height: 14px;
}

.cal__weekdays,
.cal__grid {
  display: grid;
  grid-template-columns: repeat(7, minmax(0, 1fr));
  gap: 4px;
}

.cal__weekdays {
  margin-bottom: 6px;
}

.cal__weekdays span {
  text-align: center;
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--muted);
  padding-block: 0.35rem;
}

.cal__day {
  position: relative;
  aspect-ratio: 1 / 1;
  min-height: 44px;
  display: flex;
  align-items: center;
  justify-content: center;
  border: 1px solid var(--hairline);
  border-radius: 2px;
  background: var(--linen);
  color: var(--ink);
  font-size: 0.9375rem;
  font-variant-numeric: tabular-nums;
  cursor: pointer;
  transition: background 0.15s var(--ease), border-color 0.15s var(--ease), color 0.15s var(--ease);
}

.cal__day--empty {
  border-color: transparent;
  background: transparent;
  cursor: default;
}

.cal__day--open::after {
  content: "";
  position: absolute;
  bottom: 7px;
  left: 50%;
  transform: translateX(-50%);
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--brass);
}

.cal__day:hover:not([disabled]) {
  border-color: var(--pine);
}

.cal__day[aria-pressed="true"] {
  background: var(--pine);
  border-color: var(--pine);
  color: var(--on-dark);
}

.cal__day[aria-pressed="true"]::after {
  background: var(--brass-light);
}

.cal__day[disabled] {
  color: var(--muted);
  opacity: 0.45;
  background: transparent;
  cursor: not-allowed;
}

.cal__legend {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  margin-top: 1rem;
  font-size: var(--t-small);
  color: var(--muted);
}

.cal__legend::before {
  content: "";
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--brass);
  flex: 0 0 auto;
}

/* -----------------------------------------------------------------------------
   15  Details / FAQ
----------------------------------------------------------------------------- */

.faq-group + .faq-group {
  margin-top: clamp(2.5rem, 4vw, 3.5rem);
}

.faq-group__title {
  font-size: var(--t-h3);
  padding-bottom: 0.75rem;
  border-bottom: 1px solid var(--brass);
  margin-bottom: 0.5rem;
}

details.qa {
  border-bottom: 1px solid var(--hairline);
}

details.qa > summary {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 1.5rem;
  list-style: none;
  cursor: pointer;
  padding-block: 1.1rem;
  font-family: var(--font-display);
  font-size: clamp(1.125rem, 0.95rem + 0.55vw, 1.375rem);
  line-height: 1.3;
}

details.qa > summary::-webkit-details-marker {
  display: none;
}

details.qa > summary::after {
  content: "";
  flex: 0 0 auto;
  width: 13px;
  height: 13px;
  margin-top: 0.35em;
  border-right: 1px solid var(--brass);
  border-bottom: 1px solid var(--brass);
  transform: rotate(45deg) translate(-2px, -2px);
  transition: transform 0.2s var(--ease);
}

details.qa[open] > summary::after {
  transform: rotate(225deg) translate(-2px, -2px);
}

details.qa > summary:hover {
  color: var(--pine);
}

.qa__body {
  padding-bottom: 1.5rem;
  max-width: var(--measure);
  color: var(--muted);
}

.qa__body > * + * {
  margin-top: 0.9rem;
}

/* -----------------------------------------------------------------------------
   16  Prose (journal)
----------------------------------------------------------------------------- */

.prose {
  font-family: var(--font-display);
  font-size: 1.1875rem;
  line-height: 1.68;
  color: var(--ink);
  max-width: var(--measure);
}

.prose > * + * {
  margin-top: 1.4rem;
}

.prose h2 {
  font-size: clamp(1.5rem, 1.1rem + 1.3vw, 1.875rem);
  margin-top: 2.75rem;
  line-height: 1.2;
}

.prose h3 {
  font-size: 1.375rem;
  margin-top: 2.25rem;
}

.prose p {
  max-width: none;
}

.prose ul {
  padding-left: 0;
}

.prose ul li {
  position: relative;
  padding-left: 1.4rem;
  margin-bottom: 0.6rem;
}

.prose ul li::before {
  content: "";
  position: absolute;
  left: 0;
  top: 0.75em;
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--brass);
}

.prose a {
  text-decoration: underline;
  text-decoration-color: var(--brass-text);
  text-underline-offset: 0.24em;
}

.prose a:hover {
  color: var(--pine);
}

.prose blockquote {
  font-size: clamp(1.375rem, 1rem + 1.2vw, 1.75rem);
  line-height: 1.3;
  font-style: italic;
  border-left: 2px solid var(--brass);
  padding-left: clamp(1rem, 3vw, 1.75rem);
  margin-block: 2.25rem;
}

.post-meta {
  font-family: var(--font-body);
  font-size: var(--t-small);
  letter-spacing: 0.02em;
  color: var(--muted);
}

.post-list {
  display: grid;
  gap: clamp(2rem, 4vw, 3rem);
}

.post-list__item {
  padding-top: clamp(1.75rem, 3vw, 2.25rem);
  border-top: 1px solid var(--hairline);
  display: grid;
  gap: 1.25rem;
}

@media (min-width: 760px) {
  .post-list__item {
    grid-template-columns: 220px minmax(0, 1fr);
    gap: clamp(1.75rem, 3vw, 2.75rem);
    align-items: start;
  }
}

.post-list__item h3 a {
  text-decoration: none;
  border-bottom: 1px solid transparent;
}

.post-list__item h3 a:hover {
  border-bottom-color: var(--brass);
}

.post-list__item p {
  color: var(--muted);
  margin-top: 0.6rem;
}

/* -----------------------------------------------------------------------------
   17  Rate table
   Prices are typography, not cards.
----------------------------------------------------------------------------- */

.rate-table {
  width: 100%;
  border-collapse: collapse;
  text-align: left;
}

.rate-table caption {
  text-align: left;
  font-size: var(--t-small);
  color: var(--muted);
  padding-bottom: 1rem;
}

.rate-table th,
.rate-table td {
  padding: 1.1rem 1rem 1.1rem 0;
  border-bottom: 1px solid var(--hairline);
  vertical-align: baseline;
}

.rate-table thead th {
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
  padding-bottom: 0.75rem;
  border-bottom-color: var(--brass);
}

.rate-table tbody th {
  font-family: var(--font-display);
  font-size: var(--t-h3);
  font-weight: 400;
  line-height: 1.2;
  width: 40%;
}

.rate-table .rate-table__price {
  font-family: var(--font-display);
  font-size: clamp(1.5rem, 1.1rem + 1.3vw, 1.875rem);
  white-space: nowrap;
  text-align: right;
}

.rate-table .rate-table__note {
  display: block;
  font-family: var(--font-body);
  font-size: var(--t-small);
  color: var(--muted);
  margin-top: 0.35rem;
  white-space: normal;
}

.rate-table--compact tbody th {
  font-family: var(--font-body);
  font-size: var(--t-body);
  font-weight: 500;
}

.rate-table--compact th,
.rate-table--compact td {
  padding-block: 0.85rem;
}

.rate-table--compact .rate-table__price {
  font-family: var(--font-body);
  font-size: var(--t-body);
  font-weight: 500;
}

@media (max-width: 599px) {
  .rate-table tbody th,
  .rate-table .rate-table__price {
    display: block;
    width: auto;
    text-align: left;
    border-bottom: 0;
    padding-bottom: 0.35rem;
  }

  .rate-table tbody td:last-child {
    padding-top: 0;
  }
}

/* -----------------------------------------------------------------------------
   18  Footer
----------------------------------------------------------------------------- */

.site-footer {
  background: var(--pine-deep);
  color: var(--on-dark);
  padding-block: clamp(3.5rem, 6vw, 5.5rem) 2.5rem;
}

.site-footer a {
  color: var(--on-dark);
}

.site-footer__top {
  display: grid;
  gap: clamp(2.5rem, 5vw, 4rem);
}

@media (min-width: 860px) {
  .site-footer__top {
    grid-template-columns: minmax(0, 1.2fr) minmax(0, 1fr) minmax(0, 1fr);
  }
}

.site-footer .wordmark {
  font-size: 1.75rem;
  display: inline-block;
  margin-bottom: 1.25rem;
}

.site-footer__blurb {
  color: var(--on-dark-muted);
  max-width: 34ch;
  margin-bottom: 1.75rem;
}

.site-footer__contact {
  display: grid;
  gap: 0.6rem;
  font-size: var(--t-body);
}

.site-footer__socials {
  display: flex;
  flex-wrap: wrap;
  gap: 0.35rem 1.25rem;
  margin-top: 1.5rem;
}

.site-footer__col h2 {
  font-family: var(--font-body);
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  color: var(--brass-light);
  margin-bottom: 1.1rem;
}

.site-footer__col li {
  margin-bottom: 0.6rem;
}

.site-footer__col a {
  text-decoration: none;
  border-bottom: 1px solid transparent;
}

.site-footer__col a:hover {
  border-bottom-color: var(--brass-light);
}

.site-footer__bottom {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: 0.75rem 2rem;
  margin-top: clamp(2.5rem, 5vw, 4rem);
  padding-top: 1.75rem;
  border-top: 1px solid rgba(244, 238, 227, 0.22);
  font-size: var(--t-small);
  color: var(--on-dark-muted);
}

.site-footer__bottom a {
  color: var(--on-dark-muted);
}

.site-footer__bottom a:hover {
  color: var(--on-dark);
}

.address-button {
  background: none;
  border: 0;
  padding: 0;
  text-align: left;
  cursor: pointer;
  color: inherit;
  font: inherit;
  text-decoration: underline;
  text-decoration-color: var(--brass-light);
  text-underline-offset: 0.3em;
}

.address-button:hover {
  color: var(--brass-light);
}

/* -----------------------------------------------------------------------------
   19  Motion and reveals
   Reveals only exist when JS is on and the visitor has not asked for less
   motion. Without the "js" class every .reveal renders at rest.
----------------------------------------------------------------------------- */

@media (prefers-reduced-motion: no-preference) {
  .js .reveal {
    opacity: 0;
    transform: translateY(16px);
    transition: opacity 0.7s var(--ease), transform 0.7s var(--ease);
  }

  .js .reveal.is-visible {
    opacity: 1;
    transform: none;
  }

  .js .reveal-delay-1 {
    transition-delay: 0.09s;
  }

  .js .reveal-delay-2 {
    transition-delay: 0.18s;
  }

  .js .reveal-delay-3 {
    transition-delay: 0.27s;
  }

  .hero__media img {
    animation: hero-settle 6s var(--ease) forwards;
  }

  @keyframes hero-settle {
    from {
      transform: scale(1.04);
    }
    to {
      transform: scale(1);
    }
  }
}

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

/* -----------------------------------------------------------------------------
   20  Print
   .print-page is the pricing guide, written to survive a home printer.
----------------------------------------------------------------------------- */

@media print {
  .site-header,
  .site-footer,
  .skip-link,
  .nav-toggle,
  .site-nav,
  dialog,
  .no-print {
    display: none !important;
  }

  body {
    background: #fff;
    color: #000;
    font-size: 11pt;
  }

  .print-page {
    padding: 0;
  }

  .print-page .section {
    padding-block: 0 0.6cm;
    break-inside: avoid;
  }

  .print-page h1 {
    font-size: 26pt;
  }

  .print-page h2 {
    font-size: 16pt;
    margin-top: 0.6cm;
  }

  .print-page h3 {
    font-size: 13pt;
  }

  .print-page .wrap {
    max-width: none;
    padding-inline: 0;
  }

  .print-page img,
  .print-page .photo-band,
  .print-page .hero {
    display: none;
  }

  .print-page a {
    text-decoration: none;
    color: #000;
  }

  .rate-table th,
  .rate-table td {
    border-bottom: 1px solid #999;
  }

  .print-only {
    display: block !important;
  }
}

.print-only {
  display: none;
}


/* -----------------------------------------------------------------------------
   21  Framing: how a photograph is held on the page
   A photograph dropped flat on the ground reads as a template. Each context
   holds its image a different way, the way a printed album does: an offset
   hairline behind the paired photos, a mat around the large spread images,
   an arch over the small portrait crops, a double rule on the cream panels.
   All of it is CSS, so every page picks it up without a markup change.
----------------------------------------------------------------------------- */

/* Paired photos: a single brass hairline set down and out behind the image,
   like a print lifted a quarter inch off its mount. Flipped pairs mirror it. */
.pair__media {
  position: relative;
  isolation: isolate;
}

.pair__media::before {
  content: "";
  position: absolute;
  inset: 14px -14px -14px 14px;
  border: 1px solid var(--brass);
  opacity: 0.55;
  z-index: -1;
  pointer-events: none;
}

.pair--flip .pair__media::before {
  inset: 14px 14px -14px -14px;
}

/* Two photos in one media column: the second sits smaller, offset, over the
   frame line, and the hairline belongs to the first. */
.pair__media img + img {
  width: 58%;
  margin-top: -18%;
  margin-left: auto;
  position: relative;
  z-index: 1;
  padding: 8px;
  background: var(--cream);
}

.pair--flip .pair__media img + img {
  margin-left: 0;
  margin-right: auto;
}

@media (max-width: 899px) {
  .pair__media::before,
  .pair--flip .pair__media::before {
    inset: 10px -10px -10px 10px;
  }

  .pair--flip .pair__media::before {
    inset: 10px 10px -10px -10px;
  }
}

/* The editorial spread: the two large photographs sit in a linen mat with a
   hairline edge; the two small ones become portrait arches, which is the one
   place the site borrows from wedding stationery. */
.spread__item:nth-child(1) img,
.spread__item:nth-child(4) img {
  padding: 12px;
  background: var(--linen);
  border: 1px solid var(--hairline);
}

.spread__item:nth-child(2) img,
.spread__item:nth-child(3) img {
  aspect-ratio: 4 / 5;
  object-fit: cover;
  border-radius: 999px 999px 0 0;
}

/* The sticky review photograph is the same arch, so the two portraits on the
   home page rhyme. */
.review-spread__media img {
  aspect-ratio: 4 / 5;
  object-fit: cover;
  border-radius: 999px 999px 0 0;
}

/* Journal list: small square prints in a narrow mat. */
.post-list__item img {
  aspect-ratio: 1 / 1;
  object-fit: cover;
  padding: 6px;
  background: var(--linen);
  border: 1px solid var(--hairline);
}

/* Cream panels over a photograph: a double rule, the way an invitation is
   printed, instead of a flat box with a coloured lid. */
.photo-band__panel {
  border-top: 0;
  position: relative;
  box-shadow: inset 0 0 0 1px rgba(156, 124, 70, 0.6);
}

.photo-band__panel::before {
  content: "";
  position: absolute;
  inset: 7px;
  border: 1px solid rgba(156, 124, 70, 0.32);
  pointer-events: none;
}

/* Journal post hero figure: a hairline under the caption, so the photograph
   and its caption read as one object. */
.prose figure > img + figcaption,
.post-figure figcaption {
  padding-bottom: 0.9rem;
  border-bottom: 1px solid var(--hairline);
}

/* -----------------------------------------------------------------------------
   22  Social marks
   The real marks, drawn inline, circled in a hairline. Text stays for
   screen readers only.
----------------------------------------------------------------------------- */

.site-footer__socials {
  gap: 0.75rem;
}

.site-footer__socials a {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 42px;
  height: 42px;
  border: 1px solid rgba(244, 238, 227, 0.28);
  border-radius: 50%;
  color: var(--on-dark);
  text-decoration: none;
  border-bottom-width: 1px;
  transition: border-color 0.2s ease, color 0.2s ease, transform 0.2s ease;
}

.site-footer__socials a:hover,
.site-footer__socials a:focus-visible {
  border-color: var(--brass-light);
  color: var(--brass-light);
  transform: translateY(-1px);
}

.site-footer__socials svg {
  width: 18px;
  height: 18px;
  display: block;
}

@media (prefers-reduced-motion: reduce) {
  .site-footer__socials a {
    transition: none;
  }

  .site-footer__socials a:hover {
    transform: none;
  }
}

/* -----------------------------------------------------------------------------
   23  Journal
   The journal is set as a print quarterly. The type carries it: cards hold no
   photographs at all, the cover story is the only image on the index, and the
   air between things is doing the same job a wide margin does on paper. Only
   the tokens and the scale above are used here. Nothing is boxed.
----------------------------------------------------------------------------- */

/* The cover story. One photograph, full width, then the title block set as a
   masthead: the headline wide on the left, the deck and the dateline in a
   narrow rail on the right, both hung from one hairline. */
.cover-story {
  margin-bottom: var(--section-y);
}

.cover-story__media {
  margin-bottom: clamp(1.5rem, 3vw, 2.5rem);
  aspect-ratio: 3 / 2;
}

/* On a wide screen the cover photograph is cropped to a band rather than run
   at its native 3:2, so the masthead underneath is still on the first screen. */
@media (min-width: 760px) {
  .cover-story__media {
    aspect-ratio: 21 / 9;
  }
}

.cover-story__body {
  border-top: 1px solid var(--hairline);
  padding-top: clamp(1.5rem, 2.5vw, 2.25rem);
  display: grid;
  gap: clamp(1.25rem, 3vw, 2.5rem);
}

@media (min-width: 900px) {
  .cover-story__body {
    grid-template-columns: minmax(0, 7fr) minmax(0, 4fr);
    gap: clamp(2rem, 4vw, 4rem);
  }
}

.cover-story__title {
  font-size: clamp(2.125rem, 1.15rem + 3.5vw, 3.5rem);
  line-height: 1.04;
}

.cover-story__title a,
.card-text__title a,
.article-footer__next a,
.article-footer__list a {
  text-decoration: none;
  border-bottom: 1px solid transparent;
}

.cover-story__title a:hover,
.card-text__title a:hover,
.article-footer__next a:hover,
.article-footer__list a:hover {
  border-bottom-color: var(--brass);
}

.cover-story__rail > * + * {
  margin-top: 1rem;
}

/* A section of the index: heading, one line of description, then the cards. */
.journal-section + .journal-section {
  margin-top: var(--section-y);
}

.journal-section__head {
  max-width: 46ch;
  margin-bottom: clamp(1.75rem, 3.5vw, 2.75rem);
}

.journal-section__head h2 {
  margin-bottom: 0.75rem;
}

.journal-section__cards {
  display: grid;
  gap: clamp(1.75rem, 3vw, 2.5rem) clamp(2rem, 4vw, 3.5rem);
}

@media (min-width: 620px) {
  .journal-section__cards {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

@media (min-width: 1080px) {
  .journal-section__cards {
    grid-template-columns: repeat(3, minmax(0, 1fr));
  }
}

/* The typographic card. A hairline, a title, a sentence, a dateline. The rule
   picks up brass on hover, which is the whole of the interaction. */
.card-text {
  border-top: 1px solid var(--hairline);
  padding-top: clamp(1rem, 2vw, 1.375rem);
  transition: border-top-color 0.2s var(--ease);
}

.card-text:hover {
  border-top-color: var(--brass);
}

.card-text__title {
  font-size: clamp(1.1875rem, 1.05rem + 0.45vw, 1.375rem);
  line-height: 1.24;
}

.card-text__standfirst {
  margin-top: 0.6rem;
  color: var(--muted);
  max-width: 42ch;
}

.card-text .post-meta {
  margin-top: 0.85rem;
}

/* The for-vendors strip that closes the index. */
.journal-strip {
  border-top: 1px solid var(--hairline);
  border-bottom: 1px solid var(--hairline);
  padding-block: clamp(2rem, 4vw, 3rem);
  display: grid;
  gap: clamp(1.25rem, 3vw, 2.5rem);
}

@media (min-width: 820px) {
  .journal-strip {
    grid-template-columns: minmax(0, 7fr) minmax(0, 5fr);
    align-items: end;
  }
}

/* The head of an article: section label, wide serif headline, deck, dateline,
   and for the imported pieces the line saying where they first ran. */
.article-head {
  border-bottom: 1px solid var(--hairline);
  padding-bottom: clamp(1.5rem, 2.5vw, 2rem);
}

.article-head h1 {
  font-size: clamp(2.125rem, 1.35rem + 3.1vw, 3.5rem);
}

.article-head .standfirst {
  margin-top: clamp(1.25rem, 2vw, 1.75rem);
}

.article-head__meta {
  margin-top: clamp(1.25rem, 2vw, 1.75rem);
}

.article-head__source {
  margin-top: 0.5rem;
}

a.eyebrow {
  display: inline-block;
  text-decoration: none;
  border-bottom: 1px solid transparent;
}

a.eyebrow:hover {
  border-bottom-color: var(--brass);
}

/* The deck. Sans against the serif headline, so the two do not compete. */
.standfirst {
  font-family: var(--font-body);
  font-size: var(--t-lead);
  line-height: 1.5;
  color: var(--ink);
  max-width: 52ch;
}

/* Drop cap on the opening paragraph. Ink, not brass: brass fails on cream. */
.prose > p.dropcap::first-letter {
  float: left;
  font-size: 3.85em;
  line-height: 0.8;
  padding-right: 0.08em;
  padding-top: 0.02em;
  color: var(--ink);
}

@media (max-width: 519px) {
  .prose > p.dropcap::first-letter {
    font-size: 3.1em;
  }
}

/* The pull quote. Ruled above and below rather than fenced on one side, which
   is how a printed page holds a quote pulled out of its own column. */
.prose .pullquote {
  border-left: 0;
  border-top: 1px solid var(--brass);
  border-bottom: 1px solid var(--hairline);
  padding: clamp(1.5rem, 3vw, 2.25rem) 0;
  margin-block: clamp(2.5rem, 4vw, 3.5rem);
  font-size: clamp(1.5rem, 1.05rem + 1.5vw, 2.125rem);
  line-height: 1.26;
}

/* What every piece ends on: the next one in its section, then two more from the
   same section, then the date check. */
.article-footer {
  border-top: 1px solid var(--hairline);
}

.article-footer__inner {
  padding-block: clamp(2.25rem, 4vw, 3.25rem);
  display: grid;
  gap: clamp(1.75rem, 3.5vw, 3rem);
}

@media (min-width: 760px) {
  .article-footer__inner {
    grid-template-columns: minmax(0, 6fr) minmax(0, 5fr);
    gap: clamp(2rem, 5vw, 4rem);
  }
}

.article-footer__label {
  font-family: var(--font-body);
  font-size: var(--t-small);
  color: var(--muted);
  margin-bottom: 0.7rem;
}

.article-footer__next a {
  font-family: var(--font-display);
  font-size: clamp(1.375rem, 1.1rem + 0.9vw, 1.75rem);
  line-height: 1.22;
  display: inline-block;
}

.article-footer__list a {
  font-family: var(--font-display);
  font-size: 1.125rem;
  line-height: 1.35;
  display: inline-block;
}

.article-footer__list li + li {
  margin-top: 0.7rem;
}

.article-footer__all {
  margin-top: 1.25rem;
}


/* -----------------------------------------------------------------------------
   24  Gallery, scroll story
   /gallery is a walk through the property, not a filtered grid. Four chapters
   with sticky heads, frames on a 12 column editorial grid whose shapes are
   fixed by nth-child so a season sort can move photographs between slots
   without breaking the composition, two detail film strips between chapters,
   and the lightbox. This block replaces the old page-scoped gallery.css, so
   /gallery loads main.css alone like every other page.

   Every piece of motion here sits inside prefers-reduced-motion: no-preference.
   Without JavaScript the page is the plain document order and every frame is
   still a link to its 1600 file.
----------------------------------------------------------------------------- */

:root {
  /* The sticky stack: solid header, then the chapter index under it. */
  --gal-header: 83px;
  --gal-index: 3.5rem;
  --frame-gap: clamp(0.5rem, 1.1vw, 1rem);
  /* The media box is inset by this much top and bottom, so a depth lane can
     travel without ever showing an edge inside the frame. */
  --lane-room: 30px;
  --lane-1: 24px;
  --lane-2: 14px;
  --lane-3: 7px;
}

/* --- Title block ----------------------------------------------------------- */

.gallery-head h1 {
  margin-bottom: 1rem;
}

/* --- Chapter index --------------------------------------------------------- */

.chapter-index {
  position: sticky;
  top: var(--gal-header);
  z-index: 40;
  background: var(--cream);
  border-top: 1px solid var(--hairline);
  border-bottom: 1px solid var(--hairline);
}

.chapter-index__list {
  display: flex;
  align-items: stretch;
  gap: clamp(1.25rem, 3vw, 2.75rem);
  overflow-x: auto;
  scrollbar-width: none;
  min-height: var(--gal-index);
}

.chapter-index__list::-webkit-scrollbar {
  display: none;
}

.chapter-index__link {
  display: inline-flex;
  align-items: center;
  gap: 0.5rem;
  white-space: nowrap;
  padding-block: 1rem;
  border-bottom: 2px solid transparent;
  font-size: var(--t-small);
  font-weight: 500;
  color: var(--muted);
  text-decoration: none;
  transition: color 0.2s var(--ease), border-color 0.2s var(--ease);
}

.chapter-index__link:hover {
  color: var(--ink);
}

.chapter-index__link[aria-current="true"] {
  color: var(--ink);
  border-bottom-color: var(--brass);
}

.chapter-index__count {
  font-size: var(--t-label);
  font-variant-numeric: tabular-nums;
  color: var(--brass-text);
}

/* --- Season sort ----------------------------------------------------------- */

.season-sort {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.5rem clamp(1rem, 2.5vw, 1.75rem);
  margin-top: clamp(2.25rem, 4vw, 3.25rem);
}

.season-sort[hidden] {
  display: none;
}

.season-sort__label {
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
}

.season-sort__set {
  display: flex;
  flex-wrap: wrap;
  gap: 0.35rem clamp(0.9rem, 2vw, 1.5rem);
}

/* Typographic, not a pill. The mark is a brass rule under the chosen season. */
.season-sort__option {
  appearance: none;
  background: none;
  border: 0;
  border-bottom: 1px solid transparent;
  padding: 0.35rem 0;
  font-family: var(--font-display);
  font-size: 1.125rem;
  line-height: 1.2;
  color: var(--muted);
  cursor: pointer;
  transition: color 0.18s var(--ease), border-color 0.18s var(--ease);
}

.season-sort__option:hover {
  color: var(--ink);
}

.season-sort__option[aria-pressed="true"] {
  color: var(--ink);
  border-bottom-color: var(--brass);
  font-style: italic;
}

/* The hairline under the count is the lid on the whole story, so this line
   opts out of the 64ch body measure and runs the full content width. */
.gallery-count {
  max-width: none;
  margin-top: 1rem;
  padding-bottom: clamp(1.5rem, 3vw, 2.25rem);
  border-bottom: 1px solid var(--hairline);
  font-size: var(--t-small);
  color: var(--muted);
}

/* --- Chapters -------------------------------------------------------------- */

.chapter {
  padding-block: clamp(3rem, 5.5vw, 5rem);
  scroll-margin-top: calc(var(--gal-header) + var(--gal-index));
}

.chapter__head {
  margin-bottom: clamp(1.5rem, 3vw, 2.25rem);
}

.chapter__title {
  font-size: var(--t-h2);
  line-height: 1.05;
}

.chapter__tally {
  margin-top: 1rem;
  font-size: var(--t-label);
  font-weight: 600;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--muted);
  font-variant-numeric: tabular-nums;
}

.chapter__note {
  margin-top: 0.75rem;
  max-width: 34ch;
  font-family: var(--font-display);
  font-size: var(--t-lead);
  line-height: 1.4;
  color: var(--ink);
}

@media (min-width: 900px) {
  .chapter__layout {
    display: grid;
    grid-template-columns: minmax(0, 3fr) minmax(0, 9fr);
    gap: clamp(2rem, 4vw, 3.5rem);
    align-items: start;
  }

  .chapter__head {
    position: sticky;
    top: calc(var(--gal-header) + var(--gal-index) + 2.5rem);
    margin-bottom: 0;
  }
}

/* --- The frame grid --------------------------------------------------------
   Sizes belong to the slot, not to the photograph. Every shape below is set by
   nth-child, so when the season sort reorders the frames inside a chapter the
   pattern of wide, tall and small holds and only the pictures move.
--------------------------------------------------------------------------- */

.chapter__frames {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--frame-gap);
}

/* clip, not hidden. A hidden box is a scroll container, and a scroll container
   is the scrollport that view() inside it measures against, which would pin
   every depth lane at the middle of its range and kill the parallax outright.
   hidden stays underneath as the fallback for engines without clip. */
.frame {
  position: relative;
  display: block;
  overflow: hidden;
  overflow: clip;
  background: var(--hairline);
  color: inherit;
  text-decoration: none;
  grid-column: span 2;
  aspect-ratio: 3 / 2;
  transition: opacity 0.5s var(--ease);
}

.frame__media {
  position: absolute;
  inset: calc(var(--lane-room) * -1) 0;
}

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

.frame:focus-visible {
  outline: 2px solid var(--brass);
  outline-offset: 3px;
}

/* The season sort dims what it did not pull forward. Nothing is removed. */
.frame.is-dimmed {
  opacity: 0.55;
}

/* Mobile: a single column with the occasional pair, fixed per chapter. */
.chapter--oaks .frame:nth-child(4),
.chapter--oaks .frame:nth-child(5),
.chapter--oaks .frame:nth-child(7),
.chapter--oaks .frame:nth-child(8),
.chapter--barn .frame:nth-child(3),
.chapter--barn .frame:nth-child(4),
.chapter--manor .frame:nth-child(2),
.chapter--manor .frame:nth-child(3),
.chapter--suites .frame:nth-child(2),
.chapter--suites .frame:nth-child(3) {
  grid-column: span 1;
  aspect-ratio: 4 / 5;
}

@media (min-width: 900px) {
  .chapter__frames {
    grid-template-columns: repeat(12, minmax(0, 1fr));
  }

  /* The oaks: a full width opener, then wide and tall trading sides. */
  .chapter--oaks .frame:nth-child(1) { grid-column: span 12; aspect-ratio: 16 / 9; }
  .chapter--oaks .frame:nth-child(2) { grid-column: span 7; aspect-ratio: 3 / 2; }
  .chapter--oaks .frame:nth-child(3) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--oaks .frame:nth-child(4) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--oaks .frame:nth-child(5) { grid-column: span 7; aspect-ratio: 3 / 2; }
  .chapter--oaks .frame:nth-child(6) { grid-column: span 7; aspect-ratio: 3 / 2; }
  .chapter--oaks .frame:nth-child(7) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--oaks .frame:nth-child(8) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--oaks .frame:nth-child(9) { grid-column: span 7; aspect-ratio: 3 / 2; }

  /* The barn: wide and tall, a band of three squares, then the mirror. */
  .chapter--barn .frame:nth-child(1) { grid-column: span 7; aspect-ratio: 3 / 2; }
  .chapter--barn .frame:nth-child(2) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--barn .frame:nth-child(3) { grid-column: span 4; aspect-ratio: 1 / 1; }
  .chapter--barn .frame:nth-child(4) { grid-column: span 4; aspect-ratio: 1 / 1; }
  .chapter--barn .frame:nth-child(5) { grid-column: span 4; aspect-ratio: 1 / 1; }
  .chapter--barn .frame:nth-child(6) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--barn .frame:nth-child(7) { grid-column: span 7; aspect-ratio: 3 / 2; }

  /* The two short chapters open full width so three frames still compose. */
  .chapter--manor .frame:nth-child(1) { grid-column: span 12; aspect-ratio: 16 / 9; }
  .chapter--manor .frame:nth-child(2) { grid-column: span 7; aspect-ratio: 3 / 2; }
  .chapter--manor .frame:nth-child(3) { grid-column: span 5; aspect-ratio: 4 / 5; }

  .chapter--suites .frame:nth-child(1) { grid-column: span 12; aspect-ratio: 16 / 9; }
  .chapter--suites .frame:nth-child(2) { grid-column: span 5; aspect-ratio: 4 / 5; }
  .chapter--suites .frame:nth-child(3) { grid-column: span 7; aspect-ratio: 3 / 2; }

  /* A tall frame sets its row's height, so the wide one beside it leaves air.
     Rows that read wide then tall hang their air below; rows that read tall
     then wide hang it above. The alternation is what makes the difference look
     like a decision instead of an accident. */
  .chapter__frames {
    align-items: start;
  }

  .chapter--oaks .frame:nth-child(5),
  .chapter--oaks .frame:nth-child(9),
  .chapter--barn .frame:nth-child(7),
  .chapter--suites .frame:nth-child(3) {
    align-self: end;
  }
}

/* --- Film strips ----------------------------------------------------------- */

.strip {
  padding-block: clamp(1.5rem, 3vw, 2.5rem);
}

.strip__rail {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: 62%;
  gap: var(--frame-gap);
  overflow-x: auto;
  scroll-snap-type: x mandatory;
  scroll-padding-inline: var(--gutter);
  padding-inline: var(--gutter);
  scrollbar-width: none;
}

.strip__rail::-webkit-scrollbar {
  display: none;
}

.strip .frame {
  scroll-snap-align: center;
  aspect-ratio: 4 / 5;
  grid-column: auto;
}

@media (min-width: 900px) {
  /* clip, not hidden: a hidden box is still a scroll container, so tabbing to
     the frame at the clipped end would shunt the whole reel sideways. */
  .strip {
    overflow: clip;
  }

  /* Wider than the band and hung past both edges, so the slide below travels
     8 percent of the viewport without ever bringing an end into view. */
  .strip__rail {
    grid-auto-flow: row;
    grid-template-columns: repeat(5, minmax(0, 1fr));
    width: 118%;
    overflow: visible;
    padding-inline: 0;
    margin-left: -8%;
  }
}

/* --- Lightbox --------------------------------------------------------------
   Markup and keyboard handling are unchanged. The element selector beats
   the shared dialog.dialog width rule in section 12.
--------------------------------------------------------------------------- */

dialog.lightbox {
  width: min(1180px, calc(100vw - 2rem));
}

.lightbox__stage {
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--pine-deep);
  touch-action: pan-y;
  overflow: hidden;
}

.lightbox__stage img {
  display: block;
  width: 100%;
  height: auto;
  max-height: calc(100vh - 17rem);
  object-fit: contain;
  border-radius: 0;
  user-select: none;
  -webkit-user-drag: none;
}

.lightbox__foot {
  display: flex;
  align-items: center;
  gap: 1rem;
  padding-top: clamp(1rem, 2vw, 1.25rem);
}

.lightbox__caption {
  flex: 1 1 auto;
  min-width: 0;
  max-width: none;
  margin: 0;
  text-align: center;
  font-size: var(--t-small);
  line-height: 1.5;
  color: var(--muted);
}

.lightbox__nav {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  border: 1px solid var(--hairline);
  border-radius: var(--radius-pill);
  background: var(--linen);
  color: var(--pine);
  cursor: pointer;
  transition: border-color 0.16s var(--ease), background 0.16s var(--ease);
}

.lightbox__nav:hover {
  border-color: var(--pine);
  background: var(--cream);
}

.lightbox__nav svg {
  display: block;
}

/* The clone that flies back to its thumbnail when the lightbox closes. It is
   built, animated and removed by gallery.js, and only when motion is allowed. */
.lightbox-ghost {
  position: fixed;
  z-index: 90;
  margin: 0;
  object-fit: contain;
  pointer-events: none;
}

/* --- Hover, pointer devices only -------------------------------------------
   A touch device gets neither the scale nor the caption.
--------------------------------------------------------------------------- */

.frame__caption {
  display: none;
}

@media (hover: hover) and (pointer: fine) {
  .frame__caption {
    display: -webkit-box;
    -webkit-line-clamp: 2;
    line-clamp: 2;
    -webkit-box-orient: vertical;
    position: absolute;
    left: 0;
    right: 0;
    bottom: 0;
    overflow: hidden;
    padding: 2.5rem 1rem 0.85rem;
    font-size: var(--t-small);
    line-height: 1.35;
    color: var(--on-dark);
    background: linear-gradient(to top, rgba(19, 37, 32, 0.9) 0%, rgba(19, 37, 32, 0.8) 64%, rgba(19, 37, 32, 0) 100%);
    opacity: 0;
  }

  .frame:hover .frame__caption,
  .frame:focus-visible .frame__caption {
    opacity: 1;
  }

  /* The rise is the only part that moves, so it lives behind the guard and a
     visitor who asked for less motion simply gets the caption, no travel. */
  @media (prefers-reduced-motion: no-preference) {
    .frame__media img {
      transition: transform 0.7s var(--ease);
    }

    .frame:hover .frame__media img,
    .frame:focus-visible .frame__media img {
      transform: scale(1.03);
    }

    .frame__caption {
      transform: translateY(101%);
      transition: transform 0.5s var(--ease), opacity 0.5s var(--ease);
    }

    .frame:hover .frame__caption,
    .frame:focus-visible .frame__caption {
      transform: none;
    }
  }
}

/* --- Depth lanes and the sliding strips -------------------------------------
   Scroll driven animations where the browser has them. Deeper lanes move less.
   The media box is inset by --lane-room top and bottom, so a lane never pulls a
   frame off its slot or shows an edge. Where view() is missing, the frames keep
   the ordinary .reveal stagger and nothing drifts. The sitewide reduced motion
   block cannot switch a view() animation off, because such an animation takes
   its progress from the timeline and ignores animation-duration, so both rules
   below carry their own no-preference guard.
--------------------------------------------------------------------------- */

@supports (animation-timeline: view()) {
  @media (prefers-reduced-motion: no-preference) {
    .js .frame[data-depth] .frame__media {
      animation: lane-drift linear both;
      animation-timeline: view();
      animation-range: cover 0% cover 100%;
    }

    .js .frame[data-depth="1"] .frame__media { --lane: var(--lane-1); }
    .js .frame[data-depth="2"] .frame__media { --lane: var(--lane-2); }
    .js .frame[data-depth="3"] .frame__media { --lane: var(--lane-3); }

    @keyframes lane-drift {
      from { transform: translate3d(0, var(--lane), 0); }
      to { transform: translate3d(0, calc(var(--lane) * -1), 0); }
    }
  }

  @media (prefers-reduced-motion: no-preference) and (min-width: 900px) {
    .js .strip__rail {
      animation: strip-slide linear both;
      animation-timeline: view();
      animation-range: cover 0% cover 100%;
    }

    .js .strip--reverse .strip__rail {
      animation-name: strip-slide-back;
    }

    @keyframes strip-slide {
      from { transform: translate3d(0, 0, 0); }
      to { transform: translate3d(-7%, 0, 0); }
    }

    @keyframes strip-slide-back {
      from { transform: translate3d(-7%, 0, 0); }
      to { transform: translate3d(0, 0, 0); }
    }
  }
}

/* The season sort's FLIP sets the inverted transform from script; this is what
   plays it back to rest. Under reduced motion the sitewide duration override in
   section 19 collapses it, so every frame lands in its new slot at once. */
.frame.is-flipping {
  transition: transform 0.5s var(--ease);
}

/* --- Centred opening: title, chapter index, season sort ------------------- */

.gallery-head {
  text-align: center;
  margin-inline: auto;
}

.gallery-head .lead {
  margin-inline: auto;
}

.chapter-index__list {
  justify-content: safe center;
}

.season-sort {
  justify-content: center;
  text-align: center;
}

.season-sort__set {
  justify-content: center;
}

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