/* ==========================================================================
   WINTEAM — SECTIONS
   The eight-part home sequence, then the inner pages.
   ========================================================================== */

/* ------------------------------------------------------- 01 · HERO */

.hero {
  position: relative;
  min-height: 100svh;
  display: flex;
  align-items: flex-end;
  overflow: clip;
}

/*  z-0, not a negative index: an in-flow block background paints above a
    negative-z descendant, which on the Next build made the video invisible. */
.hero__media {
  position: absolute;
  inset: 0;
  z-index: 0;
}

.hero__video {
  width: 100%;
  height: 100%;
  object-fit: cover;
  /* No scroll-linked transform on this layer. Compositing a moving video
     against a scrim is what made the picture shimmer; the fix was to leave
     the video alone and move only what sits over it. */
}

.hero__scrim {
  position: absolute;
  inset: 0;
  z-index: 1;
  background: linear-gradient(
    to bottom,
    color-mix(in oklab, var(--wt-ink-950) 55%, transparent) 0%,
    transparent 35%,
    transparent 55%,
    color-mix(in oklab, var(--wt-ink-950) 72%, transparent) 100%
  );
}

.hero__copy {
  position: relative;
  z-index: 2;
  width: 100%;
  padding-block-end: clamp(3rem, 8vh, 7rem);
}

.hero__headline {
  margin-block-start: clamp(1rem, 3vh, 2.5rem);
  max-width: 14ch;
}

.hero__foot {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 1rem var(--grid-gap);
  margin-block-start: clamp(2rem, 5vh, 4rem);
}

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

.hero__scroll-rule {
  display: block;
  width: 3rem;
  height: 1px;
  background-color: var(--line-strong);
  position: relative;
  overflow: hidden;
}

.hero__scroll-rule::after {
  content: "";
  position: absolute;
  inset-block: 0;
  inset-inline-start: 0;
  width: 40%;
  background-color: var(--content);
  animation: wt-scroll-cue 2.4s var(--ease-in-out-expo) infinite;
}

@keyframes wt-scroll-cue {
  0% { transform: translateX(-100%); }
  60%, 100% { transform: translateX(250%); }
}

/* --------------------------------------------------- 02 · MANIFESTO */

/*  The frame argument, made literally. The section opens as a narrow vertical
    slot cut through the surface; as the visitor scrolls it widens until the
    view fills the screen. The claim changes at the moment the slot stops
    being a window and starts being the world.

      We don't just make windows.  →  We frame the world outside.

    Built on a sticky viewport inside a tall section rather than a pin:
    pinning rewrites layout, and with Lenis driving the scroll a sticky
    element is both cheaper and immune to refresh-order bugs.              */

.manifesto {
  position: relative;
  height: 240vh;
  /*  How much of the surface still covers the view on each side when the
      section opens. Declared here rather than in the script so a narrow
      screen can start wider — at 375px, 38% either side leaves a 90px
      letterbox, which reads as a defect rather than a view. */
  --slot-start: 38%;

  /* Written by the runtime, from `--slot-start` down to zero. */
  --slot: var(--slot-start);
  --view-scale: 1.3;
  --eyebrow-opacity: 0;
}

.manifesto__pin {
  position: sticky;
  inset-block-start: 0;
  height: 100svh;
  overflow: clip;
}

.manifesto__view {
  position: absolute;
  inset: 0;
  clip-path: inset(0 var(--slot) 0 var(--slot));
}

.manifesto__scale {
  position: absolute;
  inset: 0;
  transform: scale(var(--view-scale));
  will-change: transform;
}

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

/*  Heavier than the hero's grade — the copy sits mid-frame here, over the
    brightest part of the picture.                                         */
.manifesto__grade {
  position: absolute;
  inset: 0;
  background: linear-gradient(
    to top,
    color-mix(in oklab, var(--wt-ink-950) 82%, transparent) 0%,
    color-mix(in oklab, var(--wt-ink-950) 55%, transparent) 45%,
    color-mix(in oklab, var(--wt-ink-950) 60%, transparent) 100%
  );
}

.manifesto__copy {
  position: relative;
  display: flex;
  flex-direction: column;
  justify-content: center;
  height: 100%;
}

/* Held back until the slot has opened enough to be read as one. */
.manifesto__eyebrow {
  opacity: var(--eyebrow-opacity);
  transition: opacity var(--duration-base) var(--ease-editorial);
}

.manifesto__lines {
  display: grid;
  margin-block-start: var(--space-block);
}

/* Both claims occupy the same cell, so the second rises into the space the
   first sinks out of. Both stay in the accessibility tree — they are one
   sentence, and a screen reader should hear the whole of it. */
.manifesto__line {
  grid-area: 1 / 1;
  max-width: 18ch;
  transition: opacity var(--duration-slow) var(--ease-editorial),
    transform var(--duration-slow) var(--ease-editorial);
}

.manifesto__line--after {
  opacity: 0;
  transform: translate3d(0, 1.5rem, 0);
}

.manifesto[data-phase="after"] .manifesto__line--before {
  opacity: 0;
  transform: translate3d(0, -1.5rem, 0);
}

.manifesto[data-phase="after"] .manifesto__line--after {
  opacity: 1;
  transform: none;
}

/* ----------------------------------------------------- 03 · ANATOMY */

/*  A tracking shot, not a dolly: the plate keeps a constant scale and moves
    sideways across the frame. Zooming it was tried and rejected — the parts
    lost their edges.                                                       */
.anatomy {
  position: relative;
  height: 240vh;
}

.anatomy__pin {
  position: sticky;
  inset-block-start: 0;
  height: 100svh;
  overflow: clip;
  display: flex;
  flex-direction: column;
}

.anatomy__frame {
  position: absolute;
  inset: 0;
  overflow: clip;
}

/*  Vignette, so the caption always has something to sit on. Bottom only —
    the copy lives at the foot of the frame, and washing the whole plate to
    protect it would be washing the thing the section is about.            */
.anatomy__vignette {
  position: absolute;
  inset: 0;
  pointer-events: none;
  background: linear-gradient(
    to top,
    color-mix(in oklab, var(--wt-ink-950) 92%, transparent) 0%,
    color-mix(in oklab, var(--wt-ink-950) 40%, transparent) 34%,
    transparent 62%
  );
}

/*  Width is set by the runtime from the frame height, because the drawing's
    content occupies only the middle 76% of the render: sizing by width left
    the tips of the parts outside the viewport top and bottom.

    `max-width: none` matters. The base rule caps every image at 100% of its
    container, which would clamp the plate back to the frame width and undo
    the sizing — and then the pan, which is computed from the width the
    runtime asked for, would travel the wrong distance.

    Vertical centring uses `translate` rather than `transform`, so the pan can
    own `transform` outright and the two never overwrite each other.        */
.anatomy__plate {
  position: absolute;
  inset-block-start: 50%;
  inset-inline-start: 0;
  translate: 0 -50%;
  height: auto;
  width: auto;
  max-width: none;
  will-change: transform;
}

/*  The caption sits at the foot of the frame: the part being named on the
    left, and an index of the six on the right that doubles as a progress
    read-out.                                                              */
.anatomy__caption {
  position: relative;
  z-index: 2;
  margin-block-start: auto;
  padding-block-end: var(--space-section-sm);
  display: flex;
  flex-direction: column;
  gap: 2rem;
}

@media (min-width: 48rem) {
  .anatomy__caption {
    flex-direction: row;
    align-items: flex-end;
    justify-content: space-between;
  }
}

.anatomy__steps {
  display: grid;
  margin-block-start: var(--space-block);
  max-width: var(--measure-text);
  min-height: 6rem;
}

.anatomy__step {
  grid-area: 1 / 1;
  pointer-events: none;
  opacity: 0;
  transform: translate3d(0, 14px, 0);
  transition: opacity var(--duration-base) var(--ease-editorial),
    transform var(--duration-base) var(--ease-editorial);
}

.anatomy__step[data-active="true"] {
  opacity: 1;
  transform: none;
}

.anatomy__index {
  display: flex;
  flex-shrink: 0;
  gap: 1.25rem;
}

@media (min-width: 48rem) {
  .anatomy__index {
    flex-direction: column;
    gap: 0.625rem;
  }
}

.anatomy__index li {
  display: flex;
  align-items: center;
  gap: 0.75rem;
  color: var(--content-subtle);
  transition: color var(--duration-fast) var(--ease-swift);
}

.anatomy__index li[data-active="true"] {
  color: var(--content);
}

/* The rule grows as its part comes up — the read-out, not decoration. */
.anatomy__index-rule {
  display: none;
  height: 1px;
  width: 0.75rem;
  background-color: var(--line-strong);
  transition: width var(--duration-base) var(--ease-editorial),
    background-color var(--duration-base) var(--ease-editorial);
}

@media (min-width: 48rem) {
  .anatomy__index-rule {
    display: block;
  }
}

.anatomy__index li[data-active="true"] .anatomy__index-rule {
  width: 2rem;
  background-color: var(--accent);
}

/* -------------------------------------------------- 04 · COLLECTION */

/*  Four series, one plate. Rather than four blocks all saying the same thing,
    the names are set as an index at display scale and the profile render and
    spec table swap underneath as you move between them.

    Hover selects on pointer devices, focus selects for keyboard, and without
    a script it stays a plain list with the first series shown.             */

.collection__layout {
  display: grid;
  gap: var(--space-block);
  margin-block-start: var(--space-block);
}

@media (min-width: 64rem) {
  .collection__layout {
    grid-template-columns: minmax(0, 7fr) minmax(0, 5fr);
    gap: var(--grid-gap);
  }

  .collection__detail {
    padding-inline-start: var(--space-block);
  }
}

.collection__index li {
  border-block-start: 1px solid var(--line);
}

.collection__index li:last-child {
  border-block-end: 1px solid var(--line);
}

.collection__pick {
  display: flex;
  width: 100%;
  align-items: baseline;
  gap: 1.25rem;
  padding-block: 1.5rem;
  text-align: start;
  background: none;
  border: 0;
}

@media (min-width: 48rem) {
  .collection__pick {
    gap: 2rem;
    padding-block: 2rem;
  }
}

.collection__number {
  width: 1.5rem;
  flex-shrink: 0;
}

.collection__name {
  flex: 1;
  color: var(--content-subtle);
  transition: color var(--duration-base) var(--ease-editorial),
    transform var(--duration-base) var(--ease-editorial);
}

.collection__pick[aria-pressed="true"] .collection__name {
  color: var(--content);
}

.collection__pick:hover .collection__name {
  transform: translateX(0.5rem);
}

.collection__summary {
  display: none;
  flex-shrink: 0;
  text-align: end;
}

@media (min-width: 40rem) {
  .collection__summary {
    display: block;
  }
}

/*  A dark plate inside the paper section, deliberately: the profile renders
    are white objects on transparency, and on paper they dissolve.
    `data-scheme` flips the tokens for this box alone.                      */
.collection__plate {
  position: relative;
  aspect-ratio: 4 / 5;
  width: 100%;
  overflow: clip;
  border-radius: var(--radius-xs);
  background-color: var(--surface);
}

.collection__render {
  position: absolute;
  inset: 0;
  display: grid;
  place-items: center;
  padding: var(--space-block);
  opacity: 0;
  transform: scale(1.04);
  transition: opacity var(--duration-base) var(--ease-editorial),
    transform var(--duration-base) var(--ease-editorial);
}

.collection__render[data-active="true"] {
  opacity: 1;
  transform: none;
}

.collection__render img {
  max-width: 100%;
  max-height: 100%;
  width: auto;
  height: auto;
  object-fit: contain;
}

.collection__body {
  margin-block-start: var(--space-block);
}

.collection__specs {
  margin-block-start: var(--space-block);
}

.collection__spec {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 1.5rem;
  border-block-start: 1px solid var(--line);
  padding-block: 0.75rem;
}

.collection__spec dd {
  text-align: end;
}

.collection__cta {
  border-block-start: 1px solid var(--line);
  padding-block-start: var(--space-block);
  margin-block-start: var(--space-block);
}

/* Only the chosen series' description, specs and link are shown. */
.collection__pane[hidden] {
  display: none;
}

/* ------------------------------------------------ 05 · CONFIGURATOR */

.configurator__layout {
  display: grid;
  gap: var(--space-block);
}

@media (min-width: 64rem) {
  .configurator__layout {
    grid-template-columns: minmax(0, 7fr) minmax(0, 5fr);
    gap: var(--grid-gap);
  }

  .configurator__controls {
    padding-inline-start: var(--space-block);
  }
}

.configurator__stage {
  background-color: var(--surface-raised);
  border-block: 1px solid var(--line);
  padding: var(--space-block) var(--gutter);
  display: grid;
  place-items: center;
}

.configurator__stage svg {
  width: 100%;
  max-width: 42rem;
  height: auto;
}

.configurator__controls {
  display: flex;
  flex-direction: column;
  gap: var(--space-block);
}

.option-group {
  border-block-start: 1px solid var(--line);
  padding-block-start: 1.5rem;
}

.option-group__options {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem;
  margin-block-start: 1rem;
}

.option {
  display: inline-flex;
  align-items: center;
  height: 2.5rem;
  padding-inline: 1rem;
  border: 1px solid var(--line-strong);
  border-radius: var(--radius-full);
  background: none;
  font-size: 0.875rem;
  color: var(--content-muted);
  transition: border-color var(--duration-fast) var(--ease-swift),
    background-color var(--duration-fast) var(--ease-swift),
    color var(--duration-fast) var(--ease-swift);
}

.option:hover:not([aria-disabled="true"]) {
  border-color: var(--content);
  color: var(--content);
}

.option[aria-current="true"] {
  border-color: var(--content);
  background-color: var(--content);
  color: var(--content-inverse);
}

/*  Not disabled by accident: this series cannot be built that way, so the
    option is rendered as text rather than a link.                         */
.option[aria-disabled="true"] {
  opacity: 0.3;
  cursor: not-allowed;
}

.option__swatch {
  display: inline-block;
  width: 0.75rem;
  height: 0.75rem;
  border-radius: var(--radius-full);
  border: 1px solid var(--line-strong);
  margin-inline-end: 0.6rem;
}

/* ---------------------------------------------------- 06 · PROJECTS */

/*  Not a grid. Each project is a full-width plate whose image sits in a frame
    that opens on hover — the same gesture as the hero window, at a smaller
    scale. Alternating alignment keeps the eye moving down the page rather
    than scanning across it.                                                */

.projects__list {
  display: flex;
  flex-direction: column;
  gap: var(--space-section-sm);
}

@media (min-width: 48rem) {
  .projects__item {
    width: 91.666%;
  }

  .projects__item:nth-child(even) {
    margin-inline-start: auto;
  }
}

/* The frame. Its padding collapses on hover, so the image grows into its own
   border — the window opening again. */
.projects__frame {
  position: relative;
  overflow: clip;
  border: 1px solid var(--line);
  padding: 0.625rem;
  transition: padding var(--duration-slow) var(--ease-editorial);
}

@media (min-width: 48rem) {
  .projects__frame {
    padding: 1rem;
  }
}

.projects__item:hover .projects__frame {
  padding: 0;
}

.projects__viewport {
  position: relative;
  aspect-ratio: 16 / 9;
  overflow: clip;
}

.projects__viewport img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  transition: transform var(--duration-slow) var(--ease-editorial);
}

.projects__item:hover .projects__viewport img {
  transform: scale(1.05);
}

.projects__caption {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 0.5rem 2rem;
  margin-block-start: 1.25rem;
}

.projects__title {
  display: flex;
  align-items: baseline;
  gap: 1rem;
}

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

.projects__closing {
  margin-block-start: var(--space-section-sm);
  max-width: var(--measure-text);
}

/* ---------------------------------------------- 07 · INSIDE/OUTSIDE */

/*  The whole product argument in one picture: a warm room, Dutch weather, and
    a single pane between them. The claim sits on the inside half, where the
    comfort is.

    The image is a sticky plate the copy scrolls over, rather than a split
    screen — a hard 50/50 divide would fight the photograph, which already has
    its own dividing line in the window frame.                              */

.inside-outside {
  position: relative;
}

.inside-outside__plate {
  position: sticky;
  inset-block-start: 0;
  height: 100svh;
  overflow: clip;
}

/*  `object-fit` needs a sized box, and a sticky element is not a positioned
    parent for an absolutely placed child. The wrapper is what gives it one. */
.inside-outside__media {
  position: absolute;
  inset: 0;
}

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

/*  Opacity only. The plate is sticky, and a scroll-linked translation on a
    pinned layer goes out of register with the page.

    The wash runs left to right because the claim sits on the left, over the
    inside of the room, and the weather on the right should stay legible as
    weather.                                                                */
.inside-outside__veil {
  position: absolute;
  inset: 0;
  opacity: var(--veil, 0.9);
  background: linear-gradient(
    to right,
    color-mix(in oklab, var(--wt-ink-950) 88%, transparent) 0%,
    /*  Held dark to 55%, which is where the comfort list ends. It used to
        thin from 45% onward, and the detail column — 13px, right-aligned —
        sat in the thin part: 2.5:1 against a lit pane at the moment the veil
        is lightest, which is also the moment the copy is centred on screen. */
    color-mix(in oklab, var(--wt-ink-950) 82%, transparent) 55%,
    color-mix(in oklab, var(--wt-ink-950) 25%, transparent) 100%
  );
}

/*  On a phone the copy is full width, so its right-hand end lands where the
    wash has thinned to 20% — measured at 1.6:1 against a bright pane, which
    is unreadable. There is no left half to protect here, so the gradient
    turns to run with the copy instead of across it.                        */
@media (max-width: 48rem) {
  .inside-outside__veil {
    background: linear-gradient(
      to bottom,
      color-mix(in oklab, var(--wt-ink-950) 45%, transparent) 0%,
      color-mix(in oklab, var(--wt-ink-950) 62%, transparent) 38%,
      color-mix(in oklab, var(--wt-ink-950) 88%, transparent) 100%
    );
  }
}

/*  Pulled back up over the sticky plate so the copy travels across the
    picture instead of following it.                                        */
.inside-outside__copy {
  position: relative;
  margin-block-start: -100svh;
  min-height: 180vh;
  display: flex;
  flex-direction: column;
  justify-content: center;
}

.inside-outside__comforts {
  margin-block-start: var(--space-block);
  max-width: var(--measure-text);
}

.inside-outside__comfort {
  border-block-start: 1px solid var(--line);
  display: flex;
  flex-direction: column;
  gap: 0.25rem;
  padding-block: 1.25rem;
}

@media (min-width: 40rem) {
  .inside-outside__comfort {
    flex-direction: row;
    align-items: baseline;
    justify-content: space-between;
    gap: 2rem;
  }

  .inside-outside__comfort dd {
    text-align: end;
  }
}

/* ----------------------------------------------------- 08 · CLOSING */

/*  The window opens one last time. Two leaves part as the section is scrolled
    through, revealing the view behind — the same gesture the visit began with,
    closing the loop, with the only thing we actually want them to do sitting
    in the opening.

    Deliberately not the page-level frame: that is a state machine for the
    whole visit, and driving it from a section that can be scrolled past in
    both directions would leave the chrome wherever the visitor stopped.
    Local leaves, local scroll.                                             */

.closing {
  position: relative;
  height: 260vh;
}

.closing__pin {
  position: sticky;
  inset-block-start: 0;
  height: 100svh;
  overflow: clip;
}

.closing__media {
  position: absolute;
  inset: 0;
}

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

/*  The mid stop is 45%, not the 35% the section was drawn with: the headline
    sits at about 0.43 of the frame, and 35% measured 2.96:1 against a lit
    window — just under the 3:1 a display line needs.                       */
.closing__grade {
  position: absolute;
  inset: 0;
  background: linear-gradient(
    to top,
    color-mix(in oklab, var(--wt-ink-950) 85%, transparent) 0%,
    color-mix(in oklab, var(--wt-ink-950) 45%, transparent) 55%,
    color-mix(in oklab, var(--wt-ink-950) 60%, transparent) 100%
  );
}

/* `--leaf` runs 0 (shut) to 1 (open), written by the runtime. */
.closing__leaf {
  position: absolute;
  inset-block: 0;
  width: 50%;
  background-color: var(--surface);
  will-change: transform;
}

.closing__leaf--left {
  inset-inline-start: 0;
  transform: translate3d(calc(var(--leaf, 0) * -100.5%), 0, 0);
}

.closing__leaf--right {
  inset-inline-end: 0;
  transform: translate3d(calc(var(--leaf, 0) * 100.5%), 0, 0);
}

/* The meeting stile, a hairline on the inner edge of each leaf. */
.closing__leaf::after {
  content: "";
  position: absolute;
  inset-block: 1.25rem;
  width: 1px;
  background-color: var(--line-strong);
}

.closing__leaf--left::after { inset-inline-end: 0; }
.closing__leaf--right::after { inset-inline-start: 0; }

.closing__copy {
  position: relative;
  display: flex;
  flex-direction: column;
  justify-content: center;
  height: 100%;
}

.closing__headline {
  max-width: 9ch;
  margin-block-start: var(--space-block);
}

.closing__actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 1rem;
  margin-block-start: var(--space-block);
  /* Held back until the leaves have parted enough to read behind them. */
  opacity: var(--closing-actions, 0);
  transition: opacity var(--duration-base) var(--ease-editorial);
}

/* ============================================== INNER PAGES ============== */

/*  Inner pages open under the fixed navigation rather than behind it. */
.page-head {
  padding-block-start: calc(var(--nav-h) + var(--space-section-sm));
  padding-block-end: var(--space-section-sm);
}

.page-head__title {
  margin-block-start: var(--space-block);
  max-width: 16ch;
}

.page-head__lead {
  margin-block-start: 1.5rem;
  max-width: 46ch;
}

/* ------------------------------------------------------------ Systems */

.systems__list {
  display: flex;
  flex-direction: column;
}

.systems__row {
  border-block-start: 1px solid var(--line);
  padding-block: clamp(2rem, 5vw, 4rem);
  display: grid;
  gap: var(--grid-gap);
}

.systems__row:last-child {
  border-block-end: 1px solid var(--line);
}

@media (min-width: 64rem) {
  .systems__row {
    grid-template-columns: minmax(0, 4fr) minmax(0, 5fr) minmax(0, 3fr);
    align-items: center;
  }
}

.systems__render {
  background-color: var(--surface-raised);
  padding: clamp(1rem, 2.5vw, 2rem);
  display: grid;
  place-items: center;
}

.systems__render img {
  max-height: 14rem;
  width: auto;
  object-fit: contain;
}

/* ---------------------------------------------------- Series detail */

.series__hero {
  display: grid;
  gap: var(--space-block);
  align-items: center;
}

@media (min-width: 64rem) {
  .series__hero {
    grid-template-columns: minmax(0, 6fr) minmax(0, 6fr);
    gap: var(--grid-gap);
  }
}

.series__render {
  background-color: var(--surface-raised);
  padding: clamp(1.5rem, 4vw, 3.5rem);
  display: grid;
  place-items: center;
}

.series__specs {
  display: grid;
  gap: 0;
}

.series__spec {
  display: flex;
  justify-content: space-between;
  gap: 1.5rem;
  padding-block: 0.9rem;
  border-block-start: 1px solid var(--line);
  font-size: var(--text-body-sm);
}

.series__spec:last-child {
  border-block-end: 1px solid var(--line);
}

.series__spec dt {
  color: var(--content-subtle);
}

.series__spec dd {
  text-align: end;
}

.series__foot {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: 1rem var(--grid-gap);
  align-items: center;
  border-block-start: 1px solid var(--line);
  padding-block-start: var(--space-block);
  margin-block-start: var(--space-block);
}

/* --------------------------------------------- Technical library */

.library__filters {
  display: flex;
  flex-wrap: wrap;
  gap: 0.5rem;
  padding-block: 1.25rem;
  border-block: 1px solid var(--line);
  position: sticky;
  inset-block-start: var(--nav-h-compact);
  z-index: var(--z-sticky);
  background-color: var(--surface);
}

.library__count {
  margin-block-start: 1.25rem;
  font-variant-numeric: tabular-nums;
}

.library__grid {
  display: grid;
  gap: var(--grid-gap);
  grid-template-columns: repeat(auto-fill, minmax(11rem, 1fr));
  margin-block-start: var(--space-block);
}

.drawing {
  display: flex;
  flex-direction: column;
  gap: 0.75rem;
  text-align: start;
  background: none;
  border: 0;
  padding: 0;
}

.drawing__plate {
  background-color: var(--surface-raised);
  border: 1px solid var(--line);
  aspect-ratio: 1;
  display: grid;
  place-items: center;
  padding: 0.75rem;
  transition: border-color var(--duration-fast) var(--ease-swift);
}

.drawing:hover .drawing__plate {
  border-color: var(--line-strong);
}

.drawing__plate img {
  max-width: 100%;
  max-height: 100%;
  width: auto;
  height: auto;
  object-fit: contain;
}

.drawing__code {
  font-variant-numeric: tabular-nums lining-nums;
}

.drawing__type {
  color: var(--content-muted);
  font-size: var(--text-caption);
}

.drawing[hidden] {
  display: none;
}

/* The lightbox. A real <dialog>, so Escape and the top layer come free. */
.lightbox {
  border: 0;
  padding: 0;
  max-width: min(90vw, 60rem);
  max-height: 90vh;
  width: 100%;
  background-color: var(--surface);
  color: var(--content);
}

.lightbox::backdrop {
  background-color: color-mix(in oklab, var(--wt-ink-950) 88%, transparent);
  backdrop-filter: blur(6px);
}

.lightbox__inner {
  display: grid;
  gap: var(--grid-gap);
  padding: clamp(1.25rem, 3vw, 2.5rem);
}

.lightbox__figure {
  background-color: var(--surface-raised);
  display: grid;
  place-items: center;
  padding: clamp(1rem, 3vw, 2.5rem);
  min-height: 40vh;
}

.lightbox__figure img {
  max-height: 55vh;
  width: auto;
  object-fit: contain;
}

.lightbox__bar {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: 0.75rem 1.5rem;
}

/* ---------------------------------------------------------- Contact */

.contact__layout {
  display: grid;
  gap: var(--space-block);
}

@media (min-width: 64rem) {
  .contact__layout {
    grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
    gap: calc(var(--grid-gap) * 2);
    align-items: start;
  }
}

.contact__rows {
  display: grid;
}

.contact__row {
  display: grid;
  gap: 0.35rem;
  padding-block: 1.1rem;
  border-block-start: 1px solid var(--line);
}

@media (min-width: 30rem) {
  .contact__row {
    grid-template-columns: 11rem minmax(0, 1fr);
    gap: 1rem;
  }
}

.contact__row:last-child {
  border-block-end: 1px solid var(--line);
}

.contact__row dt {
  font-size: var(--text-eyebrow);
  letter-spacing: var(--tracking-eyebrow);
  text-transform: uppercase;
  color: var(--content-subtle);
  padding-block-start: 0.2rem;
}

.contact__row dd a:hover {
  color: var(--accent);
}

.contact__brand {
  margin-block-start: var(--space-block);
  padding: clamp(1.25rem, 3vw, 2rem);
  border: 1px solid var(--line);
}

.enquiry {
  display: grid;
  gap: 1.75rem;
}

@media (min-width: 40rem) {
  .enquiry__pair {
    display: grid;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 1.75rem;
  }
}

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

/* --------------------------------------------------- Status pages */

.status-page {
  min-height: 100svh;
  display: grid;
  align-content: center;
}

.status-page__title {
  margin-block-start: var(--space-block);
  max-width: 16ch;
}

.status-page__body {
  margin-block-start: 1.5rem;
  max-width: 42ch;
}

.status-page__actions {
  margin-block-start: var(--space-block);
  display: flex;
  flex-wrap: wrap;
  gap: 0.75rem;
}
