/** Shopify CDN: Minification failed

Line 125:19 Unexpected "{"
Line 125:28 Expected ":"
Line 133:19 Unexpected "{"
Line 133:28 Expected ":"
Line 141:19 Unexpected "{"
Line 141:28 Expected ":"
Line 150:19 Unexpected "{"
Line 150:28 Expected ":"
Line 156:19 Unexpected "{"
Line 156:28 Expected ":"
... and 92 more hidden warnings

**/
/* SHOPIFY_STYLESHEETS_VERSION: 1.0 */


/* CSS from section stylesheet tags */
/* START_SECTION:footer (INDEX:11) */
/* ---- payment marks ------------------------------------------------------
   Centred in the band between the menu columns and the wordmark. Card marks
   keep their own colours - the networks' guidelines do not allow
   recolouring or desaturating them, so only scale and a resting opacity are
   ours to set. */
.sh-ftr__pay { display: flex; justify-content: center; }

.sh-ftr__pay .payment-icon-list {
  display: flex; flex-wrap: wrap; align-items: center; justify-content: center;
  gap: 10px; list-style: none; margin: 0; padding: 0;
}
.sh-ftr__pay .payment-icon-list li { margin: 0; line-height: 0; }
.sh-ftr__pay .payment-icon {
  display: block; height: 24px; width: auto; opacity: .66;
  transition: opacity .4s var(--sh-ease, ease);
}
.sh-ftr__pay .payment-icon-list li:hover .payment-icon { opacity: 1; }

/* ---- oversized wordmark ------------------------------------------------
   Full size, at the merchant's opacity. Static: no clip-path, no transform,
   no script, so it can never reserve height it then fails to fill. */
.sh-ftr__wordmark { opacity: var(--sh-ftr-wm-o, .26); }
.sh-ftr__wordmark img {
  display: block; width: 100%;
  height: auto;   /* real artwork at its own 3065:369 ratio - never distorted */
}

/* ==========================================================================
   HEIGHT COMPACTION
   Vertical spacing only. Original in assets/spicy-footer.css, then each pass:

     footer top padding      180 -> 112 -> 74 -> 54
     above the menu columns  140 ->  88 -> 58 -> 37
     brand col: contact       32 ->  32 -> 18 -> 13
     brand col: newsletter    44 ->  44 -> 22 -> 15
     brand col: social        44 ->  44 -> 20 -> 13
     above the payment row    84 ->  52 -> 36 -> 26
     above the wordmark       84 ->  52 -> 36 -> 26
     above the copyright     150 ->  26 -> 18 -> 13
     footer bottom padding    52 ->  34 -> 24 -> 17

   Deliberately NOT touched, because each would cross from spacing into
   design or brand:
     - .sh-ftr__mark's bottom margin: the brand book's clear zone (half the
       mark's width). It is a minimum, not slack.
     - the wordmark artwork's height: fixed at 12% of container width by the
       3065x369 logotype ratio, so shrinking it means rescaling the logo.
     - .sh-ftr__statement: type size.

   assets/spicy-footer.css is shared and read-only, so every override below
   is written to outrank its original on SPECIFICITY rather than load order
   (section stylesheets and theme assets are separate files and their order
   is not something this section can depend on):
     footer.sh-ftr        - element + class beats the bare .sh-ftr
     .sh-ftr__inner > ... - two classes beat one
   ========================================================================== */

/* Left/right padding stays on the original shorthand's var(--sh-gutter),
   which is why only the block sides are named here. */
footer.sh-ftr {
  padding-top: clamp(34px, 4.2vw, 56px);
  padding-bottom: clamp(12px, 1.3vw, 18px);
}

.sh-ftr__inner > .sh-ftr__grid { margin-top: clamp(24px, 2.9vw, 40px); }

/* Column gap only - the desktop track definition is untouched, so the number
   and arrangement of columns is exactly as before. */
@media (min-width: 1040px) {
  .sh-ftr__inner > .sh-ftr__grid--mega { gap: clamp(28px, 2.6vw, 44px); }
}

/* The brand column is the tallest, so it sets the grid's height - but only
   down to ~314px, where the Customer Service column takes over as the floor.
   These are already close to that floor; trimming them further buys nothing. */
.sh-ftr__inner .sh-ftr__col--brand .sh-ftr__contact { margin-top: clamp(10px, 1.1vw, 14px); }
.sh-ftr__inner .sh-ftr__form { margin-top: clamp(11px, 1.2vw, 16px); }
.sh-ftr__inner .sh-ftr__social { margin-top: clamp(10px, 1.1vw, 14px); }

.sh-ftr__inner > .sh-ftr__pay,
.sh-ftr__inner > .sh-ftr__wordmark { margin-top: clamp(17px, 2vw, 27px); }

/* .sh-ftr__bottom carries margin-top: clamp(80px, 10vw, 150px) from
   spicy-footer.css, sized for when the copyright sat directly under the menu
   columns. With the wordmark now between them that gap stranded the wordmark
   in an empty band. Closed up here, but ONLY when a wordmark actually
   precedes the rule, so the original spacing still applies if it is off. */
.sh-ftr__wordmark + .sh-ftr__bottom { margin-top: clamp(8px, 1vw, 13px); }

/* Mobile: same stacking order, same breakpoint, same elements - these are
   the identical spacers scaled by the same proportion as desktop. */
@media (max-width: 620px) {
  .sh-ftr__pay .payment-icon { height: 20px; }
  .sh-ftr__inner > .sh-ftr__pay,
  .sh-ftr__inner > .sh-ftr__wordmark { margin-top: clamp(16px, 4vw, 24px); }
  .sh-ftr__wordmark + .sh-ftr__bottom { margin-top: clamp(8px, 2.4vw, 14px); }
}

@media (prefers-reduced-motion: reduce) {
  .sh-ftr__pay .payment-icon { transition: none; }
}
/* END_SECTION:footer */

/* START_SECTION:product (INDEX:17) */
#ProductTemplate--{{ section.id }}.sh-pdp {
  --pdp-maxw: 1520px;
  background-color: var(--sh-ground);
  /* padding-BOTTOM only. Top padding is the theme's business: it is what
     clears the header, and this ID selector would override it outright. */
  padding-bottom: var(--sh-section-y);
}

#ProductTemplate--{{ section.id }}.sh-pdp .wrapper {
  max-width: var(--pdp-maxw);
}

/* ---- the two-column stage -----------------------------------------------
   The theme's own grid (.product-single__wrapper), re-cut to an asymmetric
   split with real air between the columns, and the gallery held in place
   while the details column scrolls past it. */
#ProductTemplate--{{ section.id }} .product-single__wrapper {
  display: grid;
  grid-template-columns: minmax(0, 1.28fr) minmax(0, 1fr);
  gap: clamp(40px, 5vw, 96px);
  align-items: start;
}

/* Sticky offset is generous enough to clear the header when the gallery
   pins, for the same reason as above. */
#ProductTemplate--{{ section.id }} .product-single__gallery {
  position: sticky;
  top: clamp(90px, 12vh, 150px);
}

/* the media frame: no border, no shadow - the photograph is the ornament */
#ProductTemplate--{{ section.id }} .product-single__media,
#ProductTemplate--{{ section.id }} .product-single__media-slide {
  background-color: var(--sh-ground-alt);
  border-radius: 0;
}

#ProductTemplate--{{ section.id }} .product-single__thumbnails {
  margin-top: clamp(14px, 1.6vw, 22px);
  gap: 8px;
}

#ProductTemplate--{{ section.id }} .product-single__thumbnails .product-single__thumbnail {
  border-radius: 0;
  border-color: var(--sh-line);
  opacity: 0.55;
  transition: opacity 0.4s var(--sh-ease), border-color 0.4s var(--sh-ease);
}

#ProductTemplate--{{ section.id }} .product-single__thumbnails .product-single__thumbnail:hover,
#ProductTemplate--{{ section.id }} .product-single__thumbnails .product-single__thumbnail.is-active,
#ProductTemplate--{{ section.id }} .product-single__thumbnails [aria-current="true"] {
  opacity: 1;
  border-color: var(--sh-ink);
}

/* ---- the details column ------------------------------------------------ */
#ProductTemplate--{{ section.id }} .product-single__details {
  max-width: 44rem;
}

#ProductTemplate--{{ section.id }} .product__subheading,
#ProductTemplate--{{ section.id }} .product-single__details .breadcrumbs {
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-eyebrow);
  font-weight: var(--sh-fw-medium);
  letter-spacing: var(--sh-ls-eyebrow);
  text-transform: uppercase;
  color: var(--sh-ink-muted);
  margin-bottom: var(--sh-s-4);
}

#ProductTemplate--{{ section.id }} .product__title {
  font-family: var(--sh-font-display);
  font-weight: 400;
  font-size: clamp(1.9rem, 3.2vw, 3rem);
  line-height: 1.08;
  letter-spacing: -0.012em;
  color: var(--sh-ink);
  max-width: 20ch;
}

#ProductTemplate--{{ section.id }} .product__title-and-price {
  padding-bottom: clamp(20px, 2.4vw, 30px);
  margin-bottom: clamp(20px, 2.4vw, 30px);
  border-bottom: 1px solid var(--sh-line);
}

/* Price: quiet by design. The enquire state's colour is left completely
   alone - that rule lives in spicy-product.css and must keep deciding it. */
#ProductTemplate--{{ section.id }} .product__price-and-badge {
  margin-top: var(--sh-s-4);
}

#ProductTemplate--{{ section.id }} [data-product-price] {
  font-family: var(--sh-font-body);
  font-size: 1.15rem;
  font-weight: var(--sh-fw-regular);
  letter-spacing: 0.01em;
}

#ProductTemplate--{{ section.id }} .product__price--compare {
  color: var(--sh-ink-faint);
  font-weight: var(--sh-fw-regular);
}

/* ---- variant selectors --------------------------------------------------
   Both control shapes the theme can render - inline swatches/boxes, or the
   popout dropdown - moved to the same hairline register. */
#ProductTemplate--{{ section.id }} .product__selectors,
#ProductTemplate--{{ section.id }} .product__form > .selector-wrapper {
  margin-bottom: clamp(18px, 2vw, 26px);
}

#ProductTemplate--{{ section.id }} .selector-wrapper label,
#ProductTemplate--{{ section.id }} .product__selectors label {
  font-family: var(--sh-font-body);
  font-size: 0.68rem;
  font-weight: var(--sh-fw-medium);
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--sh-ink-muted);
}

#ProductTemplate--{{ section.id }} .swatch__input + label,
#ProductTemplate--{{ section.id }} .radio__input + label {
  border-radius: 0;
  border-color: var(--sh-line-strong);
  color: var(--sh-ink);
}

#ProductTemplate--{{ section.id }} .swatch__input:checked + label,
#ProductTemplate--{{ section.id }} .radio__input:checked + label {
  border-color: var(--sh-ink);
  background-color: var(--sh-ink);
  color: var(--sh-ground);
}

#ProductTemplate--{{ section.id }} .select-popout {
  border-radius: 0;
}

#ProductTemplate--{{ section.id }} .select-popout__toggle,
#ProductTemplate--{{ section.id }} [data-popout-toggle] {
  border-radius: 0;
  border-color: var(--sh-line-strong);
  font-family: var(--sh-font-body);
  letter-spacing: 0.02em;
}

/* ---- quantity ----------------------------------------------------------- */
#ProductTemplate--{{ section.id }} .quantity-selector {
  border-radius: 0;
  border-color: var(--sh-line-strong);
}

/* ---- the buy button -----------------------------------------------------
   Full width, no radius, wide tracking. The enquire variant's rouge fill
   (product__submit__enquire) is untouched; only shape and type are shared. */
#ProductTemplate--{{ section.id }} .product__form .btn--submit {
  width: 100%;
  min-height: 3.4rem;
  border-radius: 0;
  font-family: var(--sh-font-body);
  font-size: 0.78rem;
  font-weight: var(--sh-fw-medium);
  letter-spacing: 0.18em;
  text-transform: uppercase;
}

#ProductTemplate--{{ section.id }} .product__form .btn--submit.product__submit__add:not(.product__submit__enquire) {
  background-color: var(--sh-ink);
  border-color: var(--sh-ink);
  color: var(--sh-ground);
  transition: background-color 0.4s var(--sh-ease), border-color 0.4s var(--sh-ease);
}

#ProductTemplate--{{ section.id }} .product__form .btn--submit.product__submit__add:not(.product__submit__enquire):hover {
  background-color: var(--sh-accent);
  border-color: var(--sh-accent);
}

/* ---- description -------------------------------------------------------- */
#ProductTemplate--{{ section.id }} .product__description {
  margin-top: clamp(28px, 3vw, 44px);
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-small);
  font-weight: var(--sh-fw-light);
  line-height: 1.75;
  color: var(--sh-ink-muted);
  max-width: 42ch;
}

/* ---- accordions ---------------------------------------------------------
   The hairline-divided register used across the rest of the site. */
#ProductTemplate--{{ section.id }} .product__accordions {
  margin-top: clamp(32px, 3.4vw, 52px);
  border-top: 1px solid var(--sh-line);
}

#ProductTemplate--{{ section.id }} .product__accordion {
  border-bottom: 1px solid var(--sh-line);
}

#ProductTemplate--{{ section.id }} .product__accordion .product__accordion-title,
#ProductTemplate--{{ section.id }} .product__accordion summary {
  font-family: var(--sh-font-body);
  font-size: 0.72rem;
  font-weight: var(--sh-fw-medium);
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--sh-ink);
  padding-block: clamp(16px, 1.8vw, 22px);
}

#ProductTemplate--{{ section.id }} .product__accordion-content,
#ProductTemplate--{{ section.id }} .product__accordion .rte {
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-small);
  color: var(--sh-ink-muted);
  line-height: 1.7;
  padding-bottom: clamp(16px, 1.8vw, 22px);
}

/* ---- responsive ---------------------------------------------------------
   Below the point the two columns can breathe, the gallery stops sticking
   and stacks above the details, in document order. */
@media (max-width: 899px) {
  #ProductTemplate--{{ section.id }} .product-single__wrapper {
    grid-template-columns: 1fr;
    gap: clamp(28px, 6vw, 44px);
  }

  #ProductTemplate--{{ section.id }} .product-single__gallery {
    position: static;
  }

  #ProductTemplate--{{ section.id }} .product-single__details {
    max-width: none;
  }
}

@media (prefers-reduced-motion: reduce) {
  #ProductTemplate--{{ section.id }} * { transition: none !important; }
}
/* END_SECTION:product */

/* START_SECTION:related-products (INDEX:18) */
#RelatedProducts--{{ section.id }}.sh-related {
  padding-block: var(--sh-section-y);
  border-top: 1px solid var(--sh-line);
}

#RelatedProducts--{{ section.id }} .featured-collection__title {
  margin-bottom: clamp(32px, 4.4vw, 56px);
}

#RelatedProducts--{{ section.id }} .featured-collection__title hr {
  display: none;
}

#RelatedProducts--{{ section.id }} .sh-related__eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 0.7rem;
  margin: 0 0 var(--sh-s-4);
}

#RelatedProducts--{{ section.id }} .featured-collection__heading {
  font-family: var(--sh-font-display);
  font-weight: 400;
  font-size: clamp(1.6rem, 2.6vw, 2.3rem);
  letter-spacing: -0.012em;
  color: var(--sh-ink);
  margin: 0;
}

@media (prefers-reduced-motion: reduce) {
  #RelatedProducts--{{ section.id }} * { transition: none !important; }
}
/* END_SECTION:related-products */

/* START_SECTION:spicy-assurances (INDEX:55) */
/* ==========================================================================
   ASSURANCES
   Type-led, hairline-divided, generously spaced. No fills, no pills, no
   rounded containers - the restraint is the design. Motion is confined to
   three things: a numeral that counts and warms, a rule that draws itself,
   and a glow that follows the pointer - each one earns its keep instead of
   decorating.
   ========================================================================== */
.sh-marks {
  position: relative;
  isolation: isolate; /* keeps the z-index:-1 photo/scrim inside this section, not sunk behind the previous one */
  background-color: var(--sh-ground);
  padding-block: var(--sh-section-y);
}

/* The photograph and its scrim sit behind the section's own ::before-based
   grid glow (z-index 0 there), so both are pinned to z-index -1 and stack
   in document order: photo first, scrim on top of it. */
.sh-marks__bg {
  position: absolute; inset: 0; z-index: -1;
  overflow: hidden;
}
.sh-marks__bg img {
  display: block; width: 100%; height: 100%; object-fit: cover; object-position: center;
}
.sh-marks__scrim {
  position: absolute; inset: 0; z-index: -1;
  background: rgba(6, 5, 4, var(--sh-marks-dim, 0.65));
}

/* With a photograph behind it, the hairline grid's own cell backgrounds
   would otherwise paint over it - so each cell drops its ground fill and
   picks up a faint frosted line instead, keeping the divider legible
   without hiding the room. */
.sh-marks--photo .sh-marks__grid { background-color: rgba(242, 241, 237, 0.16); }
.sh-marks--photo .sh-marks__item { background-color: transparent; }
.sh-marks--photo .sh-marks__bar { background: rgba(242, 241, 237, 0.22); }

.sh-marks__head { margin-bottom: clamp(36px, 5vw, 64px); }

.sh-marks__eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 0.7rem;
  margin: 0 0 var(--sh-s-4);
}

.sh-marks__heading { margin: 0; max-width: 22ch; }

/* The hairline grid: the container paints the rule colour, each cell paints
   its own ground on top, so a 1px gap becomes a divider that only ever
   appears BETWEEN cells - and reflows correctly at every breakpoint with no
   extra elements and no border bookkeeping. */
.sh-marks__grid {
  display: grid;
  grid-template-columns: repeat(var(--sh-marks-cols, 4), minmax(0, 1fr));
  gap: 1px;
  background-color: var(--sh-line);
  border-block: 1px solid var(--sh-line);
}

.sh-marks__item {
  position: relative;
  overflow: hidden;
  background-color: var(--sh-ground);
  padding: clamp(28px, 3.4vw, 52px) clamp(20px, 2.4vw, 40px);
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  isolation: isolate;
}

/* The spotlight: a soft glow that tracks the pointer inside the column it's
   in, set by JS via --mx/--my as plain percentages. Felt, not seen - it
   never reaches full opacity, and never leaves its own column. */
.sh-marks__item::before {
  content: '';
  position: absolute;
  inset: 0;
  z-index: 0;
  opacity: 0;
  background: radial-gradient(
    280px circle at var(--mx, 50%) var(--my, 50%),
    var(--sh-accent-glow, rgba(133, 23, 25, 0.10)),
    transparent 70%
  );
  transition: opacity 0.5s var(--sh-ease);
  pointer-events: none;
}
.sh-inverse .sh-marks__item::before { --sh-accent-glow: rgba(179, 68, 72, 0.16); }
.sh-marks__item:hover::before,
.sh-marks__item:focus-within::before { opacity: 1; }

.sh-marks__item > * { position: relative; z-index: 1; }

/* The oversized index numeral: watermark-faint at rest, so it reads as
   texture rather than a number until a visitor's attention actually lands
   on the column. */
.sh-marks__num {
  display: block;
  font-family: var(--sh-font-display);
  font-size: clamp(2.6rem, 4.2vw, 4.4rem);
  line-height: 1;
  font-variant-numeric: tabular-nums;
  letter-spacing: -0.02em;
  color: var(--sh-ink);
  opacity: 0.09;
  margin-bottom: clamp(10px, 1.4vw, 18px);
  transition: opacity 0.5s var(--sh-ease), color 0.5s var(--sh-ease), transform 0.5s var(--sh-ease);
}
.sh-marks__item:hover .sh-marks__num,
.sh-marks__item:focus-within .sh-marks__num {
  opacity: 0.9;
  color: var(--sh-accent);
  transform: translateY(-2px);
}

/* the brand's signature device, doing the work an icon would otherwise do */
.sh-marks__dot {
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background-color: var(--sh-accent);
  margin-bottom: clamp(18px, 2vw, 28px);
  flex: 0 0 auto;
}

.sh-marks__icon {
  display: block;
  margin-bottom: clamp(14px, 1.6vw, 22px);
  color: var(--sh-ink-faint);
}

/* height-driven so the theme's mixed icon viewBoxes keep their proportions */
.sh-marks__icon svg {
  display: block;
  height: 19px;
  width: auto;
  fill: currentColor;
}

.sh-marks__label {
  margin: 0;
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-eyebrow);
  font-weight: var(--sh-fw-medium);
  letter-spacing: var(--sh-ls-eyebrow);
  text-transform: uppercase;
  color: var(--sh-ink);
  transition: transform 0.4s var(--sh-ease);
}
.sh-marks__item:hover .sh-marks__label,
.sh-marks__item:focus-within .sh-marks__label { transform: translateX(3px); }

/* The rule that draws itself: 0 width until the column reveals, then grows
   to full - the same "progress rule" language as the Vispring chapter,
   reused rather than reinvented. */
.sh-marks__bar {
  display: block;
  width: 100%;
  height: 1px;
  margin: clamp(14px, 1.6vw, 20px) 0 0;
  background: var(--sh-line-strong);
  position: relative;
  overflow: hidden;
}
.sh-marks__bar::after {
  content: '';
  position: absolute; inset: 0;
  background: var(--sh-accent);
  transform: scaleX(0);
  transform-origin: 0 50%;
  transition: transform 0.9s var(--sh-ease);
}
[data-sh-reveal].is-inview .sh-marks__bar::after { transform: scaleX(1); }

.sh-marks__text {
  margin: clamp(12px, 1.4vw, 18px) 0 0;
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-small);
  font-weight: var(--sh-fw-light);
  line-height: 1.65;
  color: var(--sh-ink-muted);
  max-width: 28ch;
  text-wrap: pretty;
}

/* ---- responsive ---------------------------------------------------------
   Columns collapse rather than squeeze: four marks at desktop, two on a
   tablet, one on a phone. The hairline grid follows automatically. */
@media (max-width: 1023px) {
  .sh-marks__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

@media (max-width: 599px) {
  .sh-marks__grid { grid-template-columns: minmax(0, 1fr); }
  .sh-marks__item { padding-inline: 0; }
  .sh-marks__text { max-width: none; }
  /* No pointer on touch: skip the spotlight and simply show the numeral in
     its warm state once the column has revealed, so mobile still reads as
     considered rather than as "the hover effect that never fires". */
  .sh-marks__item::before { display: none; }
  [data-sh-reveal].is-inview .sh-marks__num { opacity: 0.9; color: var(--sh-accent); }
}

/* Reduced motion is already handled globally for [data-sh-reveal]; this
   clears the stagger and the bar/numeral transitions, which would otherwise
   still be honoured, and shows every column in its finished state at once. */
@media (prefers-reduced-motion: reduce) {
  .sh-marks__item { transition-delay: 0ms !important; }
  .sh-marks__bar::after { transition: none !important; transform: scaleX(1) !important; }
  .sh-marks__num { transition: none !important; }
}
/* END_SECTION:spicy-assurances */

/* START_SECTION:spicy-brand-marquee (INDEX:56) */
.sh-marquee {
  padding-block: clamp(30px, 4.4vw, 62px);
  background-color: var(--sh-ground);
  overflow: hidden;
}

.mq__head { margin-bottom: clamp(18px, 2.4vw, 32px); }
.mq__eyebrow { display: inline-flex; align-items: center; gap: 0.7rem; }

/* The window fades the line out at both edges instead of letting it hit a
   hard vertical cut, which is what separates a marquee from a ticker. */
.mq__window {
  position: relative;
  overflow: hidden;
  -webkit-mask-image: linear-gradient(to right, transparent 0, #000 9%, #000 91%, transparent 100%);
          mask-image: linear-gradient(to right, transparent 0, #000 9%, #000 91%, transparent 100%);
}

.mq__track {
  display: flex;
  width: max-content;
  animation: mq-run var(--mq-dur, 48s) linear infinite;
  will-change: transform;
}

/* Pausing on hover is not decoration: the line is the only place these names
   appear, and a visitor who wants to read one should be able to stop it. */
.mq__window:hover .mq__track,
.mq__window:focus-within .mq__track { animation-play-state: paused; }

@keyframes mq-run {
  from { transform: translate3d(0, 0, 0); }
  to   { transform: translate3d(-50%, 0, 0); }
}

.mq__copy {
  display: flex;
  align-items: center;
  list-style: none;
  margin: 0;
  padding: 0;
  flex: 0 0 auto;
}

.mq__item { display: inline-flex; align-items: center; flex: 0 0 auto; }

.mq__name {
  font-family: var(--sh-font-display);
  font-size: clamp(1.5rem, 3.4vw, 2.9rem);
  font-weight: var(--sh-fw-semi);
  line-height: 1.1;
  letter-spacing: -0.014em;
  color: var(--sh-ink);
  white-space: nowrap;
}

.mq__sep {
  width: 7px;
  height: 7px;
  margin-inline: clamp(20px, 2.6vw, 46px);
}

/* Reduced motion: the names still have to be readable, so the line stops
   running and wraps into a plain centred list rather than sitting frozen
   mid-scroll with half of it cut off. */
@media (prefers-reduced-motion: reduce) {
  .mq__window { -webkit-mask-image: none; mask-image: none; }
  .mq__track { animation: none; width: 100%; }
  .mq__copy:last-child { display: none; }
  .mq__copy {
    flex-wrap: wrap;
    justify-content: center;
    row-gap: var(--sh-s-3);
    padding-inline: var(--sh-gutter);
  }
  .mq__name { font-size: clamp(1.1rem, 2.2vw, 1.6rem); }
}
/* END_SECTION:spicy-brand-marquee */

/* START_SECTION:spicy-brands (INDEX:57) */
.sh-brands__rail { scroll-padding-inline: var(--sh-gutter); }

.sh-chapter { width: clamp(240px, 30vw, 400px); }

.sh-chapter__link { display: block; text-decoration: none; color: inherit; }

.sh-chapter__foot { padding-top: var(--sh-s-5); }

.sh-chapter__foot .sh-index { display: block; margin-bottom: var(--sh-s-4); }

/* One tone, always. The filter flattens whatever the manufacturer supplied
   to a single value so the rail reads as one editorial system. */
.sh-chapter__logo-img {
  display: block;
  width: auto;
  max-width: 160px;
  max-height: 34px;
  object-fit: contain;
  object-position: left center;
}

.sh-chapter__logo--ink .sh-chapter__logo-img { filter: brightness(0) saturate(100%); opacity: .78; }
.sh-chapter__logo--light .sh-chapter__logo-img { filter: brightness(0) invert(1); opacity: .82; }

.sh-chapter__name {
  font-family: var(--sh-font-display);
  font-size: var(--sh-fs-h3);
  font-weight: var(--sh-fw-medium);
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--sh-ink);
  margin: 0;
}

.sh-chapter__note { margin: var(--sh-s-3) 0 0; max-width: 28ch; }

.sh-brands__hint { margin-top: var(--sh-s-6); color: var(--sh-ink-faint); }

/* The rail is focusable so it can be scrolled from the keyboard; give that
   focus a visible home rather than an outline around the whole viewport. */
.sh-brands__rail:focus-visible { outline: 2px solid var(--sh-accent); outline-offset: -4px; }

/* --------------------------------------------------------------------------
   DESKTOP — the four sit together

   Below this width the rail is the right answer: four cards cannot be read
   side by side on a phone without shrinking each one to a thumbnail, and a
   thumb swipe is the natural gesture there. Above it, a rail is the wrong
   answer for exactly four items — the fourth hides off the edge and the set
   stops reading as a considered shortlist.

   Matched to the header's own 1000px breakpoint so the page changes
   behaviour once, not twice. The max-width and gutter mirror .sh-wrap so the
   first card's left edge lands on the same line as the heading above it.
   -------------------------------------------------------------------------- */
@media (min-width: 1000px) {
  .sh-brands__rail {
    display: grid;
    grid-template-columns: repeat(4, minmax(0, 1fr));
    gap: clamp(18px, 2vw, 36px);
    overflow: visible;
    scroll-snap-type: none;
    max-width: var(--sh-maxw, 1280px);
    margin-inline: auto;
    padding-inline: var(--sh-gutter);
    padding-bottom: 0;
  }

  /* The rail sized each card; the grid tracks do it now. */
  .sh-chapter { width: auto; }

  /* Nothing scrolls here any more, so the invitation to scroll would be a
     lie. */
  .sh-brands__hint { display: none; }
}
/* END_SECTION:spicy-brands */

/* START_SECTION:spicy-collection-hero (INDEX:58) */
.shc { background-color: var(--sh-ground, #f7f5f1); color: var(--sh-ink, #292421); }

.shc__inner {
  max-width: var(--sh-maxw, 1280px);
  margin-inline: auto;
  padding-inline: var(--sh-gutter, 5vw);
}

/* ---- type ----------------------------------------------------------------
   Two columns on desktop so the title has a shoulder to sit against rather
   than floating in the middle of a wide empty band — which is what made the
   original header read as unfinished space rather than as air. */
.shc--type .shc__inner { padding-block: clamp(46px, 8vh, 104px) clamp(30px, 5vh, 60px); }

@media (min-width: 900px) {
  .shc--type .shc__inner {
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    gap: clamp(32px, 5vw, 96px);
    align-items: end;
  }
  .shc--type .shc__title { margin-bottom: 0; }
}

/* ---- split / split-left --------------------------------------------------- */
.shc--split .shc__inner,
.shc--split-left .shc__inner {
  padding-block: clamp(40px, 6vh, 84px) clamp(30px, 5vh, 60px);
  display: grid;
  gap: clamp(28px, 4vw, 72px);
  align-items: center;
}

@media (min-width: 900px) {
  .shc--split .shc__inner      { grid-template-columns: minmax(0, .54fr) minmax(0, .46fr); }
  .shc--split-left .shc__inner { grid-template-columns: minmax(0, .46fr) minmax(0, .54fr); }
  .shc--split-left .shc__media { order: 1; }
  .shc--split-left .shc__words { order: 2; }

  /* A portrait photograph is taller than the words beside it; capping the
     height keeps the two columns in conversation instead of letting the
     picture run away down the page. */
  .shc--split .shc__fig,
  .shc--split-left .shc__fig { max-height: 78svh; }
}

/* ---- duo ------------------------------------------------------------------
   Deliberately unequal and offset. A matched pair reads as a gallery grid;
   an unequal one reads as art direction. */
.shc--duo .shc__inner {
  padding-block: clamp(40px, 6vh, 84px) clamp(30px, 5vh, 60px);
  display: grid;
  gap: clamp(28px, 4vw, 64px);
  align-items: center;
}

@media (min-width: 900px) {
  .shc--duo .shc__inner { grid-template-columns: minmax(0, .42fr) minmax(0, .58fr); }
  .shc--duo .shc__media {
    display: grid;
    grid-template-columns: 1.25fr .75fr;
    gap: clamp(14px, 1.6vw, 26px);
    align-items: end;
  }
  .shc--duo .shc__fig { max-height: 74svh; }
  .shc--duo .shc__fig--second { margin-bottom: clamp(20px, 4vw, 56px); }
}

@media (max-width: 899px) {
  .shc--duo .shc__media { display: grid; grid-template-columns: 1.2fr .8fr; gap: 10px; align-items: end; }
}

/* ---- frame ---------------------------------------------------------------
   Centred and inset. The quietest image layout — for objects where a wide
   crop would misrepresent how big the thing actually is. */
.shc--frame .shc__inner {
  padding-block: clamp(44px, 7vh, 96px) clamp(30px, 5vh, 60px);
  text-align: center;
  display: grid;
  justify-items: center;
  gap: clamp(28px, 4vw, 56px);
}
.shc--frame .shc__lede { margin-inline: auto; }
.shc--frame .shc__media { width: min(100%, 720px); }
.shc--frame .shc__fig { max-height: 76svh; }

/* ---- cinematic ------------------------------------------------------------ */
.shc--cinematic .shc__inner {
  max-width: none;
  padding-inline: 0;
  padding-block: 0;
  position: relative;
}
.shc__fig--bleed { min-height: 46svh; }

@media (max-width: 899px) {
  .shc__fig--bleed { aspect-ratio: 4 / 5 !important; min-height: 0; }
}

.shc__fig--bleed::after {
  content: '';
  position: absolute;
  inset: 0;
  background:
    linear-gradient(to right, rgba(8,7,6,.66) 0%, rgba(8,7,6,.22) 48%, rgba(8,7,6,0) 76%),
    linear-gradient(to top, rgba(8,7,6,.52) 0%, rgba(8,7,6,0) 46%);
}

.shc--cinematic .shc__words {
  position: absolute;
  z-index: 2;
  left: 0; right: 0; bottom: 0;
  max-width: var(--sh-maxw, 1280px);
  margin-inline: auto;
  padding: clamp(24px, 4vw, 64px) var(--sh-gutter, 5vw);
  color: #f4efe9;
}
.shc--cinematic .shc__eyebrow { color: rgba(244,239,233,.72); }
.shc--cinematic .shc__lede    { color: rgba(244,239,233,.88); }
.shc--cinematic .shc__count   { color: rgba(244,239,233,.62); }

/* ---- shared --------------------------------------------------------------- */
.shc__eyebrow {
  display: inline-flex; align-items: center; gap: .6rem;
  margin: 0 0 clamp(14px, 1.6vw, 22px);
  font-family: var(--sh-font-body, sans-serif);
  font-size: .62rem; font-weight: 400; letter-spacing: .26em;
  text-transform: uppercase; color: var(--sh-ink-faint, #9a9088);
}
.shc__dot { width: 4px; height: 4px; border-radius: 50%; background-color: var(--sh-accent, #851719); flex: none; }

/* Restrained on purpose. Oversized type is the commonest way a page tries to
   look expensive and instead looks loud. */
.shc__title {
  font-family: var(--sh-font-display, serif);
  font-weight: 400;
  font-size: clamp(1.9rem, 3.6vw, 3.4rem);
  line-height: 1.04; letter-spacing: -.014em;
  margin: 0 0 clamp(16px, 2vw, 26px);
}

.shc__lede {
  max-width: 52ch;
  font-family: var(--sh-font-body, sans-serif);
  font-size: clamp(.95rem, 1.05vw, 1.08rem);
  font-weight: 300; line-height: 1.68;
  color: var(--sh-ink-muted, #6b625b);
}
.shc__lede p { margin: 0 0 .8em; }
.shc__lede p:last-child { margin-bottom: 0; }

.shc__count {
  margin: clamp(20px, 2.4vw, 32px) 0 0;
  font-family: var(--sh-font-body, sans-serif);
  font-size: .62rem; font-weight: 400; letter-spacing: .22em;
  text-transform: uppercase; color: var(--sh-ink-faint, #9a9088);
  font-variant-numeric: tabular-nums;
}

.shc__fig {
  position: relative; margin: 0; overflow: hidden;
  background-color: var(--sh-ground-alt, #efe9e2);
}
.shc__img { display: block; width: 100%; height: 100%; object-fit: cover; }

/* ---- entrance ------------------------------------------------------------
   `both` holds the from-state before the animation runs, so nothing flashes;
   removing the animation under reduced motion leaves the element in its
   natural, visible state. There is no configuration in which this hides
   content permanently.

   The picture is uncovered rather than faded — a photograph that fades in
   reads as a slow connection, one that is uncovered reads as intent — and
   settles from 1.04 over 1.6s, slow enough to be felt rather than watched. */
@keyframes shc-rise    { from { opacity: 0; transform: translateY(14px); } }
@keyframes shc-uncover { from { clip-path: inset(0 0 100% 0); } }
@keyframes shc-settle  { from { transform: scale(1.04); } }

.shc__eyebrow { animation: shc-rise 800ms cubic-bezier(.22,.61,.36,1) both; }
.shc__title   { animation: shc-rise 800ms cubic-bezier(.22,.61,.36,1) 80ms both; }
.shc__lede    { animation: shc-rise 800ms cubic-bezier(.22,.61,.36,1) 160ms both; }
.shc__count   { animation: shc-rise 800ms cubic-bezier(.22,.61,.36,1) 240ms both; }

.shc__fig         { animation: shc-uncover 1000ms cubic-bezier(.22,.61,.36,1) 120ms both; }
.shc__fig--second { animation-delay: 300ms; }
.shc__img         { animation: shc-settle 1600ms cubic-bezier(.22,.61,.36,1) 120ms both; }

@media (prefers-reduced-motion: reduce) {
  .shc__eyebrow, .shc__title, .shc__lede, .shc__count,
  .shc__fig, .shc__fig--second, .shc__img { animation: none; }
}

@media (max-width: 899px) {
  .shc--split .shc__media, .shc--split-left .shc__media { order: 2; }
  .shc--split .shc__words, .shc--split-left .shc__words { order: 1; }
  .shc--split .shc__fig, .shc--split-left .shc__fig,
  .shc--frame .shc__fig, .shc--duo .shc__fig { max-height: 62svh; }
  .shc--cinematic .shc__words { position: static; color: inherit; padding-inline: var(--sh-gutter, 5vw); padding-block: clamp(22px, 4vh, 40px); }
  .shc--cinematic .shc__eyebrow { color: var(--sh-ink-faint, #9a9088); }
  .shc--cinematic .shc__lede { color: var(--sh-ink-muted, #6b625b); }
  .shc--cinematic .shc__count { color: var(--sh-ink-faint, #9a9088); }
  .shc__fig--bleed::after { display: none; }
}
/* END_SECTION:spicy-collection-hero */

/* START_SECTION:spicy-collections (INDEX:59) */
.sh-colls__grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: clamp(40px, 5vw, 72px) var(--sh-gutter);
}

@media (min-width: 700px) {
  .sh-colls__grid { grid-template-columns: repeat(2, 1fr); }
}

@media (min-width: 1100px) {
  .sh-colls__grid { grid-template-columns: repeat(3, 1fr); }
  /* The centre column drops. One offset, applied consistently, gives the
     grid a rhythm without any card needing to be a special case. */
  .sh-colls__grid > *:nth-child(3n + 2) { margin-top: clamp(32px, 6vw, 104px); }
}

.sh-card {
  display: block;
  text-decoration: none;
  color: inherit;
  position: relative;
}

.sh-card__veil { opacity: 0; transition: opacity var(--sh-dur-hover) var(--sh-ease); }

.sh-card__foot {
  display: flex;
  align-items: baseline;
  gap: var(--sh-s-4);
  padding-top: var(--sh-s-5);
}

.sh-card__index { flex: 0 0 auto; }

.sh-card__title {
  flex: 1 1 auto;
  margin: 0;
  transition: transform var(--sh-dur-hover) var(--sh-ease);
}

/* The rouge dot as the hover state. It is the same device as the scroll
   indicator and the logo — one mark, used consistently, rather than a new
   arrow or underline invented for this component. */
.sh-card__dot {
  flex: 0 0 auto;
  align-self: center;
  opacity: 0;
  transform: translateX(-6px);
  transition:
    opacity var(--sh-dur-hover) var(--sh-ease),
    transform var(--sh-dur-hover) var(--sh-ease);
}

.sh-card__rule {
  display: block;
  height: 1px;
  margin-top: var(--sh-s-4);
  background-color: var(--sh-line);
  position: relative;
}

.sh-card__rule::after {
  content: '';
  position: absolute;
  inset: 0;
  background-color: var(--sh-ink);
  transform: scaleX(0);
  transform-origin: left center;
  transition: transform 0.7s var(--sh-ease);
}

.sh-card__note { margin: var(--sh-s-4) 0 0; max-width: 30ch; }

@media (hover: hover) {
  .sh-card:hover .sh-card__title,
  .sh-card:focus-visible .sh-card__title { transform: translateX(6px); }

  .sh-card:hover .sh-card__dot,
  .sh-card:focus-visible .sh-card__dot { opacity: 1; transform: translateX(0); }

  .sh-card:hover .sh-card__rule::after,
  .sh-card:focus-visible .sh-card__rule::after { transform: scaleX(1); }

  .sh-card:hover .sh-card__veil,
  .sh-card:focus-visible .sh-card__veil { opacity: 1; }
}
/* END_SECTION:spicy-collections */

/* START_SECTION:spicy-contact (INDEX:60) */
/* ==========================================================================
   SPICY HOME — CONTACT
   Two rooms, one line of light between them. Underline inputs, not boxes —
   the same restrained vocabulary as .sh-link and .sh-rule elsewhere.
   ========================================================================== */
.sh-contact { position: relative; }

.sh-contact__grid {
  display: grid;
  grid-template-columns: minmax(0, 0.94fr) minmax(0, 1fr);
  min-height: 100vh; min-height: 100svh;
}
@media (max-width: 900px) {
  .sh-contact__grid { grid-template-columns: 1fr; min-height: 0; }
}

.sh-contact__panel { position: relative; display: flex; flex-direction: column; }
.sh-contact__panel--info { justify-content: space-between; background-color: var(--sh-ground); color: var(--sh-ink); }
.sh-contact__panel--form { background-color: var(--sh-c-ivory); justify-content: center; }

.sh-contact__panel-inner {
  padding: clamp(56px, 8vw, 110px) var(--sh-gutter);
  width: 100%; max-width: 560px;
}
.sh-contact__panel--info .sh-contact__panel-inner { margin-left: auto; }
.sh-contact__panel--form .sh-contact__panel-inner { margin-right: auto; }

.sh-contact__marker { display: inline-flex; align-items: center; gap: 0.7rem; margin-bottom: var(--sh-s-5); }
.sh-contact__heading { max-width: 14ch; }
.sh-contact__lede { margin: var(--sh-s-5) 0 0; color: var(--sh-ink-muted); max-width: 42ch; }

.sh-contact__particulars {
  list-style: none; margin: clamp(40px, 6vw, 64px) 0 0; padding: 0;
  border-top: 1px solid var(--sh-line);
}
.sh-contact__particulars li {
  display: flex; align-items: baseline; gap: var(--sh-s-5);
  padding: clamp(16px, 2.2vw, 22px) 0;
  border-bottom: 1px solid var(--sh-line);
}
.sh-contact__p-label { flex: 0 0 auto; width: 6.5em; }
.sh-contact__p-value { font-family: var(--sh-font-body); font-size: var(--sh-fs-body); color: var(--sh-ink); }

.sh-contact__directions { margin-top: clamp(28px, 4vw, 44px); align-self: flex-start; }

.sh-contact__panel-img { position: relative; width: 100%; aspect-ratio: 16 / 9; overflow: hidden; }
.sh-contact__panel-img img { display: block; width: 100%; height: 100%; object-fit: cover; }

.sh-contact__form-mark { color: var(--sh-accent); }
.sh-contact__form-lede { margin: var(--sh-s-3) 0 0; color: var(--sh-ink-muted); max-width: 40ch; }

.sh-contact__form { margin-top: clamp(36px, 5vw, 52px); }
.sh-contact__row { display: grid; grid-template-columns: 1fr 1fr; gap: 0 var(--sh-s-5); }
@media (max-width: 560px) { .sh-contact__row { grid-template-columns: 1fr; } }

.sh-contact__field { margin-top: var(--sh-s-6); }
.sh-contact__row .sh-contact__field { margin-top: var(--sh-s-6); }

.sh-contact__label {
  display: block; font-family: var(--sh-font-body); font-size: var(--sh-fs-eyebrow);
  letter-spacing: var(--sh-ls-eyebrow); text-transform: uppercase; color: var(--sh-ink-muted);
  margin-bottom: var(--sh-s-3);
}
.sh-contact__optional { text-transform: none; letter-spacing: 0; opacity: 0.7; }

.sh-contact__input {
  width: 100%; display: block; font-family: var(--sh-font-body); font-size: var(--sh-fs-body);
  color: var(--sh-ink); background: transparent; border: 0; border-bottom: 1px solid var(--sh-line-strong);
  padding: 0.6em 0.1em; border-radius: 0;
  transition: border-color var(--sh-dur-hover) var(--sh-ease);
}
.sh-contact__input::placeholder { color: var(--sh-ink-faint); }
.sh-contact__input:focus { outline: none; border-bottom-color: var(--sh-accent); }
.sh-contact__input--area { resize: vertical; min-height: 3.4em; line-height: var(--sh-lh-body); }

.sh-contact__submit { margin-top: clamp(32px, 4.5vw, 48px); width: 100%; }
@media (min-width: 561px) { .sh-contact__submit { width: auto; min-width: 220px; } }

.sh-contact__notice {
  margin-top: clamp(28px, 4vw, 40px); padding: var(--sh-s-5); border: 1px solid var(--sh-line-strong);
}
.sh-contact__notice--success { border-color: var(--sh-accent); }
.sh-contact__notice--error { border-color: var(--sh-c-rouge); background: rgba(133, 23, 25, 0.06); }
.sh-contact__notice p { margin: 0; }
/* END_SECTION:spicy-contact */

/* START_SECTION:spicy-hero (INDEX:61) */
.sh-hero {
  position: relative;
  min-height: var(--sh-hero-h, 90vh);
  display: flex;
  align-items: flex-end;
  overflow: hidden;
  isolation: isolate;
  background-color: var(--sh-c-black);
}

.sh-hero--centre { text-align: center; }

/* Two nested layers: the outer one is moved by the parallax system, the
   inner one holds the slow drift. Combining both on one element would mean
   two systems fighting over the same transform. */
.sh-hero__media { position: absolute; inset: -8% 0; z-index: 0; }
.sh-hero__drift { width: 100%; height: 100%; }
.sh-hero__media .sh-media { width: 100%; height: 100%; }

.sh-hero__veil { z-index: 1; opacity: var(--sh-veil-o, 1); }

.sh-hero__inner {
  position: relative;
  z-index: 2;
  width: 100%;
  padding-top: clamp(96px, 20vh, 200px);
  padding-bottom: clamp(64px, 10vh, 128px);
}

.sh-hero__seq { display: flex; flex-direction: column; align-items: flex-start; gap: var(--sh-s-5); }
.sh-hero--centre .sh-hero__seq { align-items: center; }

.sh-hero__symbol-img,
.sh-hero__wordmark-img { display: block; width: var(--sh-w); height: auto; }

.sh-hero__symbol { margin-bottom: var(--sh-s-2); }
.sh-hero__wordmark { margin-bottom: var(--sh-s-3); }

.sh-hero__eyebrow { display: inline-flex; align-items: center; gap: .7rem; color: var(--sh-c-ivory); }
.sh-hero__eyebrow .sh-dot { background-color: var(--sh-c-rouge-light); }

.sh-hero__heading { color: var(--sh-c-white); max-width: 17ch; }
.sh-hero--centre .sh-hero__heading { margin-inline: auto; }

.sh-hero__text { color: rgba(242, 241, 237, .78); max-width: 46ch; margin: 0; }
.sh-hero--centre .sh-hero__text { margin-inline: auto; }

.sh-hero__actions {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--sh-s-6);
  margin-top: var(--sh-s-2);
}

.sh-hero__btn { color: var(--sh-c-ivory); border-color: rgba(242, 241, 237, .45); }
.sh-hero__btn:hover,
.sh-hero__btn:focus-visible { border-color: var(--sh-c-ivory); background-color: transparent; color: var(--sh-c-white); }
.sh-hero__link { color: rgba(242, 241, 237, .82); font-size: var(--sh-fs-small); }
.sh-hero__link:hover { color: var(--sh-c-white); }

/* --------------------------------------------------------------------------
   THE ARRIVAL
   Held at rest, then released one element at a time. Each element carries its
   own --sh-t delay from the template, so the rhythm is editable without
   touching this file.
   -------------------------------------------------------------------------- */

.sh-hero--seq .sh-hero__seq > *,
.sh-hero--seq .sh-hero__cue { opacity: 0; }

.sh-hero--seq .sh-hero__seq > * { transform: translateY(20px); }
.sh-hero--seq .sh-hero__symbol { filter: blur(8px); }

.sh-hero--seq.is-sequenced .sh-hero__seq > * {
  animation: sh-hero-rise 1.5s var(--sh-ease) var(--sh-t, 0s) forwards;
}

.sh-hero--seq.is-sequenced .sh-hero__symbol {
  animation: sh-hero-focus 1.8s var(--sh-ease) var(--sh-t, 0s) forwards;
}

/* The headline wipes up through a mask instead of fading. It is the one
   moment in the hero that behaves differently, which is what makes it read
   as the headline. */
.sh-hero--seq .sh-hero__heading { clip-path: inset(0 0 108% 0); transform: none; }
.sh-hero--seq.is-sequenced .sh-hero__heading {
  animation: sh-hero-wipe 1.7s var(--sh-ease-inout) var(--sh-t, 0s) forwards;
}

.sh-hero--seq.is-sequenced .sh-hero__cue {
  animation: sh-hero-fade 1.2s var(--sh-ease) var(--sh-t, 0s) forwards;
}

.sh-hero--seq.is-sequenced .sh-hero__drift {
  animation: sh-hero-drift 22s var(--sh-ease-inout) forwards;
}

/* No JavaScript, theme editor, or reduced motion: everything already placed. */
html:not(.sh-js) .sh-hero--seq .sh-hero__seq > *,
html:not(.sh-js) .sh-hero--seq .sh-hero__cue,
.sh-hero--seq.is-instant .sh-hero__seq > *,
.sh-hero--seq.is-instant .sh-hero__cue {
  opacity: 1;
  transform: none;
  filter: none;
  clip-path: none;
  animation: none;
}

@keyframes sh-hero-rise {
  from { opacity: 0; transform: translateY(20px); }
  to   { opacity: 1; transform: translateY(0); }
}

@keyframes sh-hero-focus {
  from { opacity: 0; transform: translateY(20px); filter: blur(8px); }
  to   { opacity: 1; transform: translateY(0); filter: blur(0); }
}

@keyframes sh-hero-wipe {
  from { opacity: 1; clip-path: inset(0 0 108% 0); }
  to   { opacity: 1; clip-path: inset(0 0 -12% 0); }
}

@keyframes sh-hero-fade {
  to { opacity: 1; }
}

/* A very slow settle on the film. 1.06 to 1 across 22 seconds is barely
   perceptible, which is the intention - it reads as depth, not as an effect. */
@keyframes sh-hero-drift {
  from { transform: scale(1.06); }
  to   { transform: scale(1); }
}

/* --------------------------------------------------------------------------
   SCROLL CUE - a slow rouge line. The only repeating motion in the hero.
   -------------------------------------------------------------------------- */

.sh-hero__cue {
  position: absolute;
  z-index: 2;
  bottom: 0;
  left: 50%;
  transform: translateX(-50%);
  width: 1px;
  height: clamp(48px, 7vh, 84px);
  background-color: rgba(242, 241, 237, .22);
  overflow: hidden;
}

.sh-hero__cue-line {
  position: absolute;
  inset: 0;
  background-color: var(--sh-c-rouge-light);
  animation: sh-cue 3.2s var(--sh-ease-inout) infinite;
}

@keyframes sh-cue {
  0%   { transform: translateY(-100%); }
  55%  { transform: translateY(100%); }
  100% { transform: translateY(100%); }
}

@media (max-width: 768px) {
  .sh-hero { min-height: var(--sh-hero-h-sm, 80vh); align-items: flex-end; }
  .sh-hero__media { inset: 0; }
  .sh-hero__inner { padding-top: clamp(80px, 16vh, 140px); }
  .sh-hero__actions { gap: var(--sh-s-4); }
  .sh-hero__btn { width: 100%; }
}

@media (prefers-reduced-motion: reduce) {
  .sh-hero--seq .sh-hero__seq > *,
  .sh-hero--seq .sh-hero__cue {
    opacity: 1;
    transform: none;
    filter: none;
    clip-path: none;
    animation: none;
  }
  .sh-hero__drift { animation: none; }
  .sh-hero__cue-line { animation: none; transform: none; }
}
/* END_SECTION:spicy-hero */

/* START_SECTION:spicy-home-immersive-footer (INDEX:62) */
/* ==========================================================================
   SPICY HOME — IMMERSIVE BRAND FOOTER
   Every rule below is scoped to .spicy-home-immersive-footer. Nothing here
   selects an element type, a shared class, or anything outside this block.
   ========================================================================== */
.spicy-home-immersive-footer {
  --spicy-footer-ground: #000000;
  --spicy-footer-ink: #f2f1ed;
  --spicy-footer-accent: #851719;
  --spicy-footer-height: 88svh;
  --spicy-footer-font-display: 'Afacad', ui-sans-serif, -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
  --spicy-footer-font-body: 'Jost', ui-sans-serif, -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
  --spicy-footer-gutter: clamp(20px, 4vw, 56px);

  /* progress (0-1) and drift (-1..1) are written by the script each frame */
  --spicy-footer-p: 1;
  --spicy-footer-drift: 0;

  position: relative;
  display: flex;
  align-items: center;
  justify-content: center;
  min-height: var(--spicy-footer-height);
  padding: clamp(72px, 12vh, 150px) var(--spicy-footer-gutter) clamp(48px, 8vh, 96px);
  background-color: var(--spicy-footer-ground);
  color: var(--spicy-footer-ink);
  /* the wordmark and ring are deliberately oversized; this is what
     guarantees they can never produce a horizontal scrollbar */
  overflow: hidden;
  isolation: isolate;
}

/* -- layer 1 · atmosphere -------------------------------------------------- */
.spicy-home-immersive-footer .spicy-home-immersive-footer__background {
  position: absolute;
  inset: -10% -5%;
  z-index: 0;
  pointer-events: none;
  background:
    radial-gradient(46% 44% at 50% 58%, rgba(133, 23, 25, 0.14), transparent 68%),
    radial-gradient(60% 52% at 22% 22%, rgba(184, 164, 145, 0.09), transparent 72%);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__ring {
  position: absolute;
  left: 50%;
  top: 52%;
  width: min(128vw, 1500px);
  aspect-ratio: 1;
  margin-left: min(-64vw, -750px);
  margin-top: min(-64vw, -750px);
  border: 1px solid rgba(242, 241, 237, 0.055);
  border-radius: 50%;
}

/* -- layout ---------------------------------------------------------------- */
.spicy-home-immersive-footer .spicy-home-immersive-footer__inner {
  position: relative;
  z-index: 1;
  width: 100%;
  max-width: 1600px;
  display: flex;
  flex-direction: column;
  align-items: center;
  text-align: center;
}

/* -- eyebrow --------------------------------------------------------------- */
.spicy-home-immersive-footer .spicy-home-immersive-footer__eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 0.7rem;
  margin: 0 0 clamp(20px, 3vh, 36px);
  font-family: var(--spicy-footer-font-body);
  font-size: clamp(0.62rem, 0.72vw, 0.72rem);
  font-weight: 500;
  letter-spacing: 0.24em;
  text-transform: uppercase;
  color: rgba(242, 241, 237, 0.42);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__eyebrow-dot {
  width: 4px;
  height: 4px;
  border-radius: 50%;
  background: var(--spicy-footer-accent);
  flex: 0 0 auto;
}

/* -- layer 2 · the wordmark ------------------------------------------------
   Sized so the lockup spans most of the viewport width at every breakpoint,
   which is what makes it read as a brand statement rather than a heading. */
.spicy-home-immersive-footer .spicy-home-immersive-footer__wordmark {
  display: flex;
  align-items: baseline;
  justify-content: center;
  flex-wrap: nowrap;
  gap: 0.22em;
  margin: 0;
  font-family: var(--spicy-footer-font-display);
  font-weight: 400;
  font-size: clamp(2.6rem, 18.4vw, 22rem);
  line-height: 0.86;
  letter-spacing: -0.005em;
  text-transform: uppercase;
  color: var(--spicy-footer-ink);
  white-space: nowrap;
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__word { display: inline-block; }

.spicy-home-immersive-footer .spicy-home-immersive-footer__dot {
  display: inline-block;
  width: 0.1em;
  height: 0.1em;
  margin-left: 0.05em;
  border-radius: 50%;
  background: var(--spicy-footer-accent);
  vertical-align: baseline;
}

/* -- layer 3 · supporting line --------------------------------------------- */
.spicy-home-immersive-footer .spicy-home-immersive-footer__content {
  margin-top: clamp(26px, 4.5vh, 52px);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: clamp(16px, 2.4vh, 26px);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__tagline {
  margin: 0;
  max-width: 34ch;
  font-family: var(--spicy-footer-font-body);
  font-size: clamp(0.9rem, 1.05vw, 1.02rem);
  font-weight: 300;
  line-height: 1.65;
  color: rgba(242, 241, 237, 0.58);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__links {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: clamp(18px, 2.4vw, 34px);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__links-item { margin: 0; }

.spicy-home-immersive-footer .spicy-home-immersive-footer__link {
  position: relative;
  display: inline-block;
  /* comfortably tappable without changing the visual rhythm */
  padding: 6px 2px;
  font-family: var(--spicy-footer-font-body);
  font-size: clamp(0.68rem, 0.78vw, 0.76rem);
  font-weight: 500;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  text-decoration: none;
  color: rgba(242, 241, 237, 0.72);
  transition: color 0.4s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__link::after {
  content: '';
  position: absolute;
  left: 2px;
  right: 2px;
  bottom: 0;
  height: 1px;
  background: var(--spicy-footer-accent);
  transform: scaleX(0);
  transform-origin: right center;
  transition: transform 0.4s cubic-bezier(0.22, 0.61, 0.36, 1);
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__link:hover,
.spicy-home-immersive-footer .spicy-home-immersive-footer__link:focus-visible { color: var(--spicy-footer-ink); }

.spicy-home-immersive-footer .spicy-home-immersive-footer__link:hover::after,
.spicy-home-immersive-footer .spicy-home-immersive-footer__link:focus-visible::after {
  transform: scaleX(1);
  transform-origin: left center;
}

.spicy-home-immersive-footer .spicy-home-immersive-footer__note {
  margin: 0;
  font-family: var(--spicy-footer-font-body);
  font-size: clamp(0.62rem, 0.72vw, 0.72rem);
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: rgba(242, 241, 237, 0.3);
}

/* ==========================================================================
   THE SCROLL-DRIVEN STATE
   Applied only once the script has taken over, so the default rendering above
   is already the finished composition. No JS, no motion — but never a blank
   or half-built footer.
   ========================================================================== */
.spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__wordmark {
  opacity: var(--spicy-footer-p);
  transform:
    translate3d(0, calc((1 - var(--spicy-footer-p)) * 72px + var(--spicy-footer-drift) * 10px), 0)
    scale(calc(0.93 + var(--spicy-footer-p) * 0.07));
  /* resolves to exactly 0 at rest, so the finished wordmark is perfectly sharp */
  filter: blur(calc((1 - var(--spicy-footer-p)) * 5px));
  will-change: opacity, transform, filter;
}

/* the layers move at different rates — this is what reads as depth */
.spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__background {
  transform: translate3d(0, calc(var(--spicy-footer-drift) * -34px), 0);
  will-change: transform;
}

.spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__eyebrow {
  opacity: var(--spicy-footer-p);
  transform: translate3d(0, calc((1 - var(--spicy-footer-p)) * 26px), 0);
  will-change: opacity, transform;
}

.spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__content {
  /* trails the wordmark slightly, so the statement lands first */
  opacity: clamp(0, calc(var(--spicy-footer-p) * 1.5 - 0.5), 1);
  transform: translate3d(0, calc((1 - var(--spicy-footer-p)) * 40px + var(--spicy-footer-drift) * 18px), 0);
  will-change: opacity, transform;
}

/* ==========================================================================
   RESPONSIVE
   Mobile is not a smaller desktop: the lockup stacks to keep its scale, and
   the parallax distances come down so nothing feels loose on a small screen.
   ========================================================================== */
@media (max-width: 640px) {
  .spicy-home-immersive-footer {
    --spicy-footer-height: 76svh;
    padding-top: clamp(60px, 10vh, 110px);
  }

  .spicy-home-immersive-footer .spicy-home-immersive-footer__wordmark {
    flex-direction: column;
    align-items: center;
    gap: 0;
    font-size: clamp(3.4rem, 34vw, 9rem);
    line-height: 0.92;
  }

  .spicy-home-immersive-footer .spicy-home-immersive-footer__ring {
    width: 150vw;
    margin-left: -75vw;
    margin-top: -75vw;
  }

  /* shorter travel, no blur cost on mobile GPUs */
  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__wordmark {
    transform:
      translate3d(0, calc((1 - var(--spicy-footer-p)) * 40px), 0)
      scale(calc(0.96 + var(--spicy-footer-p) * 0.04));
    filter: none;
  }

  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__background {
    transform: translate3d(0, calc(var(--spicy-footer-drift) * -14px), 0);
  }

  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__content {
    transform: translate3d(0, calc((1 - var(--spicy-footer-p)) * 22px), 0);
  }
}

/* ==========================================================================
   REDUCED MOTION
   No parallax, no travel, no blur, no stagger. The composition still arrives,
   and remains completely functional.
   ========================================================================== */
@media (prefers-reduced-motion: reduce) {
  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__wordmark,
  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__eyebrow,
  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__content,
  .spicy-home-immersive-footer[data-spicy-footer-state='live'] .spicy-home-immersive-footer__background {
    opacity: 1;
    transform: none;
    filter: none;
    will-change: auto;
  }

  .spicy-home-immersive-footer .spicy-home-immersive-footer__link,
  .spicy-home-immersive-footer .spicy-home-immersive-footer__link::after { transition: none; }
}
/* END_SECTION:spicy-home-immersive-footer */

/* START_SECTION:spicy-journal (INDEX:63) */
.sh-lead {
  display: grid;
  grid-template-columns: 1fr;
  gap: clamp(28px, 4vw, 64px);
  text-decoration: none;
  color: inherit;
  align-items: center;
}

@media (min-width: 900px) {
  .sh-lead { grid-template-columns: 1.5fr 1fr; gap: clamp(48px, 6vw, 96px); }
}

.sh-lead__figure { margin: 0; }
.sh-lead__date { margin: 0 0 var(--sh-s-4); color: var(--sh-ink-faint); }
.sh-lead__title { margin: 0; }
.sh-lead__excerpt { margin: var(--sh-s-5) 0 0; color: var(--sh-ink-muted); max-width: 42ch; }
.sh-lead__cue { display: inline-block; margin-top: var(--sh-s-6); font-size: var(--sh-fs-small); }

@media (hover: hover) {
  .sh-lead:hover .sh-lead__cue::after,
  .sh-lead:focus-visible .sh-lead__cue::after { transform: scaleX(1); transform-origin: left center; }
}

/* --------------------------------------------------------------------------
   THE LIST — hairlines only. Date, title, and the rouge dot on hover.
   -------------------------------------------------------------------------- */

.sh-journal__list {
  list-style: none;
  margin: clamp(48px, 7vw, 104px) 0 0;
  padding: 0;
  border-top: 1px solid var(--sh-line);
}

.sh-entry { border-bottom: 1px solid var(--sh-line); }

.sh-entry__link {
  display: flex;
  align-items: baseline;
  gap: var(--sh-s-5);
  padding: var(--sh-s-6) 0;
  text-decoration: none;
  color: inherit;
}

.sh-entry__date { flex: 0 0 auto; min-width: 10ch; color: var(--sh-ink-faint); }

.sh-entry__title {
  flex: 1 1 auto;
  transition: transform var(--sh-dur-hover) var(--sh-ease);
}

.sh-entry__dot {
  flex: 0 0 auto;
  opacity: 0;
  transform: translateX(-6px);
  transition:
    opacity var(--sh-dur-hover) var(--sh-ease),
    transform var(--sh-dur-hover) var(--sh-ease);
}

@media (hover: hover) {
  .sh-entry__link:hover .sh-entry__title,
  .sh-entry__link:focus-visible .sh-entry__title { transform: translateX(8px); }
  .sh-entry__link:hover .sh-entry__dot,
  .sh-entry__link:focus-visible .sh-entry__dot { opacity: 1; transform: translateX(0); }
}

@media (max-width: 620px) {
  .sh-entry__link { flex-wrap: wrap; gap: var(--sh-s-2); }
  .sh-entry__date { min-width: 0; flex: 1 0 100%; }
}

.sh-journal__empty { color: var(--sh-ink-faint); }
/* END_SECTION:spicy-journal */

/* START_SECTION:spicy-philosophy (INDEX:64) */
.sh-philos__spread {
  display: grid;
  grid-template-columns: 1fr;
  gap: clamp(40px, 6vw, 96px);
  align-items: start;
}

@media (min-width: 900px) {
  .sh-philos__spread {
    grid-template-columns: 1fr 0.86fr;
    gap: clamp(56px, 8vw, 140px);
  }
  /* The photograph sits lower than the type it accompanies. The mismatch is
     what stops the spread reading as a two-column template. */
  .sh-philos__figure { margin-top: clamp(40px, 7vw, 120px); }
}

.sh-philos__eyebrow { display: inline-flex; align-items: center; gap: .7rem; margin-bottom: var(--sh-s-6); }

.sh-philos__heading { max-width: 15ch; }

.sh-philos__body {
  margin-top: var(--sh-s-6);
  color: var(--sh-ink-muted);
  max-width: 48ch;
}

.sh-philos__body > * + * { margin-top: var(--sh-s-4); }
.sh-philos__body p { margin: 0; }

.sh-philos__link { display: inline-block; margin-top: var(--sh-s-6); }

.sh-philos__figure { margin: 0; }
.sh-philos__caption { margin-top: var(--sh-s-4); max-width: 34ch; }

/* --------------------------------------------------------------------------
   PRINCIPLES — a ruled list, not a row of cards.
   Hairlines only. Cards would add borders, shadows and corners the brand
   does not use.
   -------------------------------------------------------------------------- */

.sh-philos__principles {
  list-style: none;
  margin: clamp(56px, 9vw, 130px) 0 0;
  padding: 0;
  display: grid;
  grid-template-columns: 1fr;
  gap: 0;
  border-top: 1px solid var(--sh-line);
}

.sh-philos__principle {
  padding: var(--sh-s-6) 0;
  border-bottom: 1px solid var(--sh-line);
}

@media (min-width: 760px) {
  .sh-philos__principles {
    grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
    gap: 0 clamp(28px, 4vw, 72px);
  }
  .sh-philos__principle { padding: var(--sh-s-7) 0; }
}

.sh-philos__label { margin-bottom: var(--sh-s-4); color: var(--sh-ink-faint); }

.sh-philos__text {
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-body);
  line-height: var(--sh-lh-body);
  color: var(--sh-ink);
  margin: 0;
  max-width: 34ch;
}
/* END_SECTION:spicy-philosophy */

/* START_SECTION:spicy-projects (INDEX:65) */
.sh-projects { padding-block: var(--sh-section-y); background-color: var(--sh-ground); }

.sh-projects__head { margin-bottom: clamp(40px, 6vw, 88px); }
.sh-projects__heading { max-width: 18ch; }

.sh-panel + .sh-panel { margin-top: clamp(48px, 8vw, 128px); }

.sh-panel__media {
  position: relative;
  height: var(--sh-panel-h, 78vh);
  overflow: hidden;
  background-color: var(--sh-c-espresso);
}

.sh-panel__media .sh-media { position: absolute; inset: -6% 0; height: 112%; }

.sh-panel__captionwrap { margin-top: var(--sh-s-6); }

.sh-panel__caption {
  display: grid;
  gap: var(--sh-s-3);
  max-width: 42ch;
}

/* The caption sits under the image rather than on it. Type over photography
   needs a scrim, and a scrim over good photography is a compromise. */
.sh-panel--right .sh-panel__caption { margin-left: auto; text-align: left; }
.sh-panel--centre .sh-panel__caption { margin-inline: auto; text-align: center; }

.sh-panel__title { margin: 0; }
.sh-panel__note { margin: 0; }
.sh-panel__link { justify-self: start; margin-top: var(--sh-s-2); }
.sh-panel--centre .sh-panel__link { justify-self: center; }
.sh-panel--right .sh-panel__link { justify-self: start; }

@media (max-width: 768px) {
  .sh-panel__media { height: 62vh; }
  .sh-panel--right .sh-panel__caption,
  .sh-panel--centre .sh-panel__caption { margin-left: 0; margin-inline: 0; text-align: left; }
}
/* END_SECTION:spicy-projects */

/* START_SECTION:spicy-sofas (INDEX:66) */
/* ==========================================================================
   FEATURED SOFAS
   ========================================================================== */
.sh-sofas {
  position: relative;
  background-color: var(--sh-ground);
  /* No overflow here. position:sticky inside would stop working. */
}

.sh-sofas__track {
  position: relative;
  height: 100svh;   /* JS replaces this with the measured travel */
}

.sh-sofas__stage {
  position: sticky;
  top: 0;
  height: 100vh;
  height: 100svh;
  overflow: hidden;          /* safe: the sticky element itself, not an ancestor */
  display: flex;
  flex-direction: column;
  justify-content: center;
  padding-block: clamp(56px, 8vh, 104px);
}

/* ---- the wall ----------------------------------------------------------- */
.sh-sofas__head {
  flex: 0 0 auto;
  padding-inline: var(--sh-gutter);
  margin-bottom: clamp(28px, 4.5vh, 60px);
}

.sh-sofas__eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 0.7rem;
  margin: 0 0 var(--sh-s-4);
}

.sh-sofas__heading { margin: 0; max-width: 20ch; }

/* ---- the rail ------------------------------------------------------------ */
.sh-sofas__viewport {
  flex: 1 1 auto;
  min-height: 0;
  display: flex;
  align-items: center;
}

.sh-sofas__rail {
  --sh-sofas-x: 0px;
  display: flex;
  align-items: flex-start;
  gap: clamp(18px, 2.4vw, 44px);
  padding-inline: var(--sh-gutter);
  will-change: transform;
  transform: translate3d(var(--sh-sofas-x), 0, 0);
}

.sh-sofas__panel {
  flex: 0 0 auto;
  width: auto;
  display: flex;
  flex-direction: column;
  text-decoration: none;
  color: inherit;
}

/* ==========================================================================
   THE FRAME - it has no shape of its own.

   Every panel is the same HEIGHT and takes its width from --sh-ar, the
   photograph's real aspect ratio, printed by Liquid. The image then fills
   it exactly: nothing is cropped, and no panel is ever visible behind the
   picture.

   Both tidier-looking alternatives were tried and are wrong:

     - A fixed ratio with `object-fit: cover` crops whatever does not fit.
       On a wide sofa photograph in a portrait frame that removed both arms;
       the customer was shown half the thing being sold.
     - A fixed ratio with `object-fit: contain` keeps the whole picture but
       letterboxes it, and the bars are the frame's own background - which
       is the white ground that had to come out.

   A uniform grid can have one of the two. Only a per-image ratio has
   neither, and the varied widths read as editorial rather than untidy.
   ========================================================================== */
.sh-sofas__frame {
  position: relative;
  display: block;
  height: clamp(230px, 52svh, 620px);
  aspect-ratio: var(--sh-ar, 1);
  width: auto;
  overflow: hidden;
  background-color: transparent;
}

/* `cover` is safe here precisely because the frame is already the image's
   own shape - there is nothing to crop. No transform: the frame no longer
   carries any bleed, so drifting the image would expose its edge. The rail
   itself supplies the movement. */
.sh-sofas__img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: center;
  display: block;
}

/* ---- caption ------------------------------------------------------------- */
.sh-sofas__caption {
  display: grid;
  grid-template-columns: auto 1fr;
  align-items: baseline;
  column-gap: clamp(12px, 1.4vw, 22px);
  padding-top: clamp(14px, 1.8vw, 24px);
}

.sh-sofas__index {
  font-family: var(--sh-font-body);
  font-size: 0.62rem;
  font-weight: 400;
  letter-spacing: 0.24em;
  color: var(--sh-ink-faint);
  font-variant-numeric: tabular-nums;
}

.sh-sofas__name {
  font-family: var(--sh-font-display);
  font-size: clamp(1.05rem, 1.5vw, 1.4rem);
  font-weight: 400;
  line-height: 1.2;
  color: var(--sh-ink);
  transition: color 0.4s var(--sh-ease);
}

.sh-sofas__meta {
  grid-column: 2;
  font-family: var(--sh-font-body);
  font-size: 0.68rem;
  font-weight: 400;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--sh-ink-muted);
  margin-top: 6px;
}

.sh-sofas__panel:hover .sh-sofas__name,
.sh-sofas__panel:focus-visible .sh-sofas__name { color: var(--sh-accent); }

.sh-sofas__empty {
  font-family: var(--sh-font-body);
  color: var(--sh-ink-muted);
  padding-block: var(--sh-s-8);
}

/* ---- progress ------------------------------------------------------------ */
.sh-sofas__rule {
  flex: 0 0 auto;
  margin: clamp(24px, 4vh, 52px) var(--sh-gutter) 0;
  height: 1px;
  background: var(--sh-line);
}

.sh-sofas__rule i {
  display: block;
  height: 100%;
  background: var(--sh-accent);
  transform: scaleX(0);
  transform-origin: 0 50%;
  will-change: transform;
}

/* ==========================================================================
   MOBILE - a real gesture, not a hijacked one.
   ========================================================================== */
@media (max-width: 767px) {
  .sh-sofas__track { height: auto !important; }

  .sh-sofas__stage {
    position: static;
    height: auto;
    overflow: visible;
    padding-block: var(--sh-section-y);
  }

  .sh-sofas__viewport { display: block; }

  .sh-sofas__rail {
    transform: none !important;
    overflow-x: auto;
    overscroll-behavior-x: contain;
    scroll-snap-type: x mandatory;
    -webkit-overflow-scrolling: touch;
    scrollbar-width: none;
    padding-bottom: 4px;
  }

  .sh-sofas__rail::-webkit-scrollbar { display: none; }

  .sh-sofas__panel {
    width: 78vw;
    scroll-snap-align: center;
  }

  /* width-driven on a phone; the ratio still comes from the photograph, so
     the height follows it and nothing is cropped or padded. */
  .sh-sofas__frame { height: auto; width: 100%; }

  .sh-sofas__rule { display: none; }
}

/* ==========================================================================
   REDUCED MOTION - a conventional grid. Everything present, nothing moves.
   ========================================================================== */
@media (prefers-reduced-motion: reduce) {
  .sh-sofas__track { height: auto !important; }

  .sh-sofas__stage {
    position: static;
    height: auto;
    overflow: visible;
    padding-block: var(--sh-section-y);
  }

  .sh-sofas__viewport { display: block; }

  .sh-sofas__rail {
    transform: none !important;
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
    overflow: visible;
    max-width: var(--sh-maxw);
    margin-inline: auto;
  }

  .sh-sofas__panel { width: auto; }
  .sh-sofas__frame { height: auto; width: 100%; }
  .sh-sofas__rule { display: none; }
}
/* END_SECTION:spicy-sofas */

/* START_SECTION:spicy-story (INDEX:67) */
.sh-story {
  background-color: var(--sh-ground);
  color: var(--sh-ink);
  padding-block: clamp(60px, 9vh, 130px) clamp(80px, 12vh, 180px);
  overflow-x: clip;
}

.sh-story__open {
  max-width: var(--sh-maxw);
  margin-inline: auto;
  padding-inline: var(--sh-gutter);
  padding-block: clamp(40px, 9vh, 120px) clamp(60px, 12vh, 150px);
}

.sh-story__eyebrow { display: inline-flex; align-items: center; gap: .7rem; margin: 0 0 var(--sh-s-5); }

.sh-story__title {
  font-family: var(--sh-font-display);
  font-weight: 400;
  font-size: clamp(2.1rem, 5.4vw, 5rem);
  line-height: 1.02;
  letter-spacing: -.018em;
  max-width: 17ch;
  margin: 0;
}

.sh-story__lede {
  margin: clamp(24px, 3vw, 40px) 0 0;
  max-width: 52ch;
  font-family: var(--sh-font-body);
  font-size: clamp(1rem, 1.15vw, 1.2rem);
  font-weight: 300;
  line-height: 1.65;
  color: var(--sh-ink-muted);
}

.sh-story__ch {
  position: relative;
  max-width: var(--sh-maxw);
  margin-inline: auto;
  padding-inline: var(--sh-gutter);
  padding-block: clamp(48px, 9vh, 120px);
  display: grid;
  gap: clamp(28px, 4vw, 72px);
  align-items: center;
}

/* The year is a watermark behind the type, not a label. Decorative, so it is
   aria-hidden — the date is already in the words. */
.sh-story__year {
  display: block;
  font-family: var(--sh-font-display);
  font-size: clamp(3.4rem, 9vw, 8.5rem);
  font-weight: 400;
  line-height: .82;
  letter-spacing: -.03em;
  color: var(--sh-ink);
  opacity: .09;
  margin-bottom: clamp(-30px, -2.6vw, -14px);
  pointer-events: none;
}

.sh-story__ch-eyebrow {
  font-family: var(--sh-font-body);
  font-size: .64rem;
  font-weight: 400;
  letter-spacing: .26em;
  text-transform: uppercase;
  color: var(--sh-ink-faint);
  margin: 0 0 var(--sh-s-4);
}

.sh-story__ch-title {
  font-family: var(--sh-font-display);
  font-weight: 400;
  font-size: clamp(1.7rem, 3.4vw, 3.3rem);
  line-height: 1.06;
  letter-spacing: -.012em;
  margin: 0;
}

.sh-story__body {
  margin-top: clamp(16px, 1.8vw, 26px);
  max-width: 46ch;
  font-family: var(--sh-font-body);
  font-size: clamp(.95rem, 1.05vw, 1.09rem);
  font-weight: 300;
  line-height: 1.7;
  color: var(--sh-ink-muted);
}
.sh-story__body p { margin: 0 0 1em; }
.sh-story__body p:last-child { margin-bottom: 0; }

.sh-story__media { position: relative; display: grid; }

.sh-story__fig {
  position: relative;
  margin: 0;
  overflow: hidden;
  background-color: var(--sh-ground-alt);
}

.sh-story__img {
  display: block;
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: center;
}

@media (min-width: 768px) {
  .sh-story__ch--left  { grid-template-columns: minmax(0, 1.05fr) minmax(0, .95fr); }
  .sh-story__ch--right { grid-template-columns: minmax(0, .95fr) minmax(0, 1.05fr); }

  .sh-story__ch--left  .sh-story__media { order: 1; }
  .sh-story__ch--left  .sh-story__words { order: 2; }
  .sh-story__ch--right .sh-story__media { order: 2; }
  .sh-story__ch--right .sh-story__words { order: 1; }

  .sh-story__ch--left .sh-story__fig,
  .sh-story__ch--right .sh-story__fig { aspect-ratio: 4 / 5; }

  /* Deliberately unequal. A matched pair reads as a gallery grid; an unequal
     one reads as art direction. */
  .sh-story__ch--pair { grid-template-columns: minmax(0, 1.15fr) minmax(0, .85fr); }
  .sh-story__ch--pair .sh-story__media {
    grid-template-columns: 1fr 1fr;
    align-items: end;
    gap: clamp(14px, 2vw, 30px);
  }
  .sh-story__ch--pair .sh-story__fig { aspect-ratio: 3 / 4; }
  .sh-story__ch--pair .sh-story__fig--second {
    aspect-ratio: 1 / 1;
    margin-bottom: clamp(24px, 5vw, 70px);
  }

  .sh-story__ch--detail { grid-template-columns: minmax(0, .38fr) minmax(0, .62fr); }
  .sh-story__ch--detail .sh-story__fig { aspect-ratio: 1 / 1; }

  .sh-story__ch--type { grid-template-columns: minmax(0, .18fr) minmax(0, .62fr); }
  .sh-story__ch--type .sh-story__words { grid-column: 2; }
}

.sh-story__ch--full {
  max-width: none;
  padding-inline: 0;
  padding-block: clamp(60px, 10vh, 140px);
  display: block;
}

.sh-story__ch--full .sh-story__fig { aspect-ratio: 21 / 9; min-height: 62svh; }
.sh-story__ch--full .sh-story__media { position: relative; }

.sh-story__ch--full .sh-story__fig::after {
  content: '';
  position: absolute;
  inset: 0;
  background:
    linear-gradient(to right, rgba(8,7,6,.72) 0%, rgba(8,7,6,.28) 46%, rgba(8,7,6,0) 74%),
    linear-gradient(to top, rgba(8,7,6,.44) 0%, rgba(8,7,6,0) 42%);
}

.sh-story__ch--full .sh-story__words {
  position: absolute;
  z-index: 2;
  left: 0; right: 0; bottom: 0;
  max-width: var(--sh-maxw);
  margin-inline: auto;
  padding: clamp(28px, 5vw, 76px) var(--sh-gutter);
  color: var(--sh-c-ivory, #f4efe9);
}

.sh-story__ch--full .sh-story__year { color: #fff; opacity: .22; }
.sh-story__ch--full .sh-story__ch-eyebrow { color: rgba(244,239,233,.72); }
.sh-story__ch--full .sh-story__body { color: rgba(244,239,233,.86); max-width: 44ch; }

.sh-story__ch--type .sh-story__ch-title { font-size: clamp(1.9rem, 4.2vw, 4rem); max-width: 18ch; }
.sh-story__ch--type .sh-story__body { font-size: clamp(1rem, 1.2vw, 1.24rem); max-width: 44ch; }

.sh-story__end {
  max-width: var(--sh-maxw);
  margin-inline: auto;
  padding-inline: var(--sh-gutter);
  padding-top: clamp(30px, 5vh, 60px);
}

.sh-story__cta {
  display: inline-flex;
  align-items: center;
  gap: clamp(12px, 1.1vw, 20px);
  padding-bottom: 7px;
  font-family: var(--sh-font-body);
  font-size: clamp(11px, .86vw, 13px);
  font-weight: 400;
  letter-spacing: .22em;
  text-transform: uppercase;
  color: var(--sh-ink);
  text-decoration: none;
  border-bottom: 1px solid currentColor;
  transition: opacity .3s var(--sh-ease);
}
.sh-story__cta svg { width: 28px; height: 8px; flex: none; overflow: visible; transition: transform .5s var(--sh-ease); }
.sh-story__cta:hover { opacity: .68; }
.sh-story__cta:hover svg { transform: translateX(7px); }

/* ==========================================================================
   REVEALS — armed by JS, never by CSS alone.

   Every hidden state below is scoped to `.sh-story.is-armed`, a class added
   by assets/spicy-story.js. Without that script the page is simply visible.
   This is not defensive tidiness: the first version hid everything in CSS and
   shipped a completely blank story page when the observer did not fire.
   ========================================================================== */

/* The mask uncovers the frame; the photograph settles 1.06 -> 1. No fade on
   the image itself — a photograph that fades in reads as a slow connection,
   one that is uncovered reads as intent. */
.sh-story.is-armed [data-sh-mask] {
  clip-path: inset(0 0 100% 0);
  transition: clip-path 1.25s var(--sh-ease);
}
.sh-story.is-armed [data-sh-mask] .sh-story__img {
  transform: scale(1.06);
  transition: transform 1.8s var(--sh-ease);
}
.sh-story [data-sh-mask].is-in { clip-path: inset(0 0 0 0); }
.sh-story [data-sh-mask].is-in .sh-story__img { transform: scale(1); }

.sh-story.is-armed [data-sh-reveal] {
  opacity: 0;
  transform: translateY(16px);
  transition: opacity .9s var(--sh-ease), transform .9s var(--sh-ease);
}
.sh-story [data-sh-reveal].is-in { opacity: 1; transform: none; }
.sh-story .sh-story__year[data-sh-reveal].is-in { opacity: .09; }
.sh-story__ch--full .sh-story__year[data-sh-reveal].is-in { opacity: .22; }

@media (max-width: 767px) {
  .sh-story__ch { grid-template-columns: 1fr; }
  .sh-story__media { order: 1 !important; }
  .sh-story__words { order: 2 !important; }
  .sh-story__fig { aspect-ratio: 4 / 5; }
  .sh-story__ch--pair .sh-story__media { grid-template-columns: 1fr 1fr; gap: 12px; }
  .sh-story__ch--pair .sh-story__fig--second { margin-bottom: 0; }
  .sh-story__ch--full .sh-story__fig { aspect-ratio: 4 / 5; min-height: 0; }
  .sh-story__ch--full .sh-story__words { position: static; color: inherit; padding-inline: var(--sh-gutter); }
  .sh-story__ch--full .sh-story__ch-eyebrow { color: var(--sh-ink-faint); }
  .sh-story__ch--full .sh-story__body { color: var(--sh-ink-muted); }
  .sh-story__ch--full .sh-story__year { color: var(--sh-ink); }
  .sh-story__ch--full .sh-story__year[data-sh-reveal].is-in { opacity: .09; }
  .sh-story__ch--full .sh-story__fig::after { display: none; }
}

@media (prefers-reduced-motion: reduce) {
  .sh-story.is-armed [data-sh-mask],
  .sh-story.is-armed [data-sh-mask] .sh-story__img,
  .sh-story.is-armed [data-sh-reveal] {
    clip-path: none;
    opacity: 1;
    transform: none;
    transition: none;
  }
  .sh-story .sh-story__year[data-sh-reveal] { opacity: .09; }
}
/* END_SECTION:spicy-story */

/* START_SECTION:spicy-testimonials (INDEX:68) */
/* Tighter than --sh-section-y: this is a proof band, not a chapter. */
.tq {
  padding-block: clamp(34px, 4.6vw, 62px);
  background-color: var(--sh-ground);
  overflow: hidden;
}

/* ---- the band ------------------------------------------------------------
   Heading, score and CTA share one row on desktop and stack on small
   screens, which is what keeps the whole section under half a screen. */
.tq__band {
  display: flex;
  flex-wrap: wrap;
  align-items: flex-end;
  justify-content: space-between;
  gap: var(--sh-s-5) var(--sh-s-6);
}

.tq__eyebrow { display: inline-flex; align-items: center; gap: 0.7rem; }
.tq__heading { margin-top: var(--sh-s-3); max-width: 20ch; }

.tq__score { display: flex; align-items: center; gap: var(--sh-s-4); }

.tq__score-num {
  font-family: var(--sh-font-display);
  font-size: clamp(2rem, 3.4vw, 2.9rem);
  font-weight: var(--sh-fw-regular);
  line-height: 1;
  letter-spacing: var(--sh-ls-display);
  color: var(--sh-ink);
}

.tq__score-right { display: flex; flex-direction: column; gap: 5px; }

.tq__stars { display: inline-flex; gap: 3px; }
.tq__stars svg { width: 16px; height: 16px; fill: var(--sh-accent); }
.tq__stars--sm svg { width: 13px; height: 13px; }

.tq__score-meta {
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-small);
  color: var(--sh-ink-muted);
}

.tq__cta-icon {
  width: 14px; height: 14px;
  fill: none; stroke: currentColor; stroke-width: 1.4;
  stroke-linecap: round; stroke-linejoin: round;
}

/* ---- the rail ------------------------------------------------------------
   Native horizontal scrolling by default: keyboard, trackpad and touch all
   behave correctly and it costs no JavaScript. JS only upgrades this to the
   scroll-driven version where that is a good idea. */
.tq__viewport {
  margin-top: clamp(24px, 3.2vw, 42px);
  overflow-x: auto;
  overflow-y: hidden;
  scrollbar-width: none;
  -webkit-overflow-scrolling: touch;
  scroll-snap-type: x proximity;
}

.tq__viewport::-webkit-scrollbar { display: none; }
.tq__viewport:focus-visible { outline: 2px solid var(--sh-accent); outline-offset: 4px; }

.tq__rail {
  display: flex;
  gap: var(--sh-s-6);
  list-style: none;
  margin: 0;
  padding-inline: var(--sh-gutter);
  width: max-content;
}

.tq__cell {
  flex: 0 0 auto;
  width: clamp(255px, 26vw, 340px);
  scroll-snap-align: start;
}

.tq__card {
  margin: 0;
  padding-top: var(--sh-s-4);
  border-top: 1px solid var(--sh-line);
  height: 100%;
}

/* Capped at six lines so one long review cannot set the height of the whole
   band — the reason this section came out taller than the screen. The words
   are never altered, only how many are shown before the card ends, and the
   full text is one click away on Google. Every card then occupies the same
   height and the rail reads as a row rather than a ragged skyline. */
.tq__text {
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-small);
  font-weight: var(--sh-fw-light);
  line-height: 1.62;
  letter-spacing: var(--sh-ls-body);
  color: var(--sh-ink-muted);
  margin: var(--sh-s-4) 0 0;
  text-wrap: pretty;
  display: -webkit-box;
  -webkit-line-clamp: 6;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

.tq__by {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 0.5rem;
  margin-top: var(--sh-s-4);
  font-family: var(--sh-font-body);
  font-size: var(--sh-fs-eyebrow);
  font-weight: var(--sh-fw-medium);
  letter-spacing: var(--sh-ls-eyebrow);
  text-transform: uppercase;
}

.tq__by-name { color: var(--sh-ink); }
.tq__by-sep,
.tq__by-date { color: var(--sh-ink-faint); }

.tq__foot { margin-top: clamp(22px, 2.8vw, 36px); }
.tq__read { font-size: var(--sh-fs-small); letter-spacing: 0.04em; }

/* ---- scroll-driven mode --------------------------------------------------
   Added by JS only. Native scrolling is switched off here because the two
   would fight each other for the same axis; JS owns the offset instead. */
.tq.is-driven .tq__viewport {
  overflow: hidden;
  scroll-snap-type: none;
}

.tq.is-driven .tq__rail {
  transform: translate3d(var(--tq-x, 0px), 0, 0);
  will-change: transform;
}

@media (max-width: 640px) {
  .tq__band { align-items: flex-start; }
  .tq__cta { width: 100%; }
  .tq__cell { width: min(78vw, 320px); }
}

@media (prefers-reduced-motion: reduce) {
  .tq.is-driven .tq__rail { transform: none; }
  .tq.is-driven .tq__viewport { overflow-x: auto; }
}
/* END_SECTION:spicy-testimonials */

/* START_SECTION:spicy-vispring (INDEX:69) */
/* ==========================================================================
   SPICY HOME x VISPRING
   One dark room, eight chapters. Sizes come from the token scale rather than
   being invented here: on this brand, confidence comes from space, not size.
   ========================================================================== */
.sh-vis {
  position: relative;
  background-color: var(--sh-ground);
  /* No overflow rule here. position:sticky inside would stop working. */
}

.sh-vis__h { max-width: 18ch; margin-top: var(--sh-s-5); }
.sh-vis__prose { margin: var(--sh-s-5) 0 0; color: var(--sh-ink-muted); max-width: 46ch; }
.sh-vis__prose > * + * { margin-top: var(--sh-s-4); }
.sh-vis__prose p { margin: 0; }
.sh-vis__marker { display: inline-flex; align-items: center; gap: 0.7rem; margin-bottom: var(--sh-s-5); }

/* -- 01 introduction ------------------------------------------------------ */
.sh-vis__intro { padding-block: var(--sh-section-y) clamp(32px, 5vw, 64px); }
.sh-vis__intro-logo {
  display: block;
  width: clamp(64px, 7vw, 104px);
  height: auto;
  margin-bottom: clamp(24px, 3.4vw, 40px);
  opacity: 0.92;
}
.sh-vis__heading { max-width: 16ch; }
.sh-vis__lede { margin: var(--sh-s-5) 0 0; color: var(--sh-ink-muted); max-width: 42ch; }

/* -- 02 the assembly -------------------------------------------------------
   Shots stack in document order; each arrives by the transition declared on
   it. No transform of any kind is applied to a photograph on this stage: no
   scale, no pan, no Ken Burns. Any scale would resample the image and cost
   sharpness, and a drifting room would contradict the whole idea that the
   room is locked and only the bed changes. */
.sh-vis__track { position: relative; height: var(--vis-track, 320vh); }

.sh-vis__stage {
  position: sticky; top: 0;
  height: 100vh; height: 100svh;
  overflow: hidden;          /* safe: the sticky element itself, not an ancestor */
  isolation: isolate;
  background: #0b0908;
}

.sh-vis__frame {
  position: absolute; inset: 0; z-index: 1; display: block;
  will-change: opacity, clip-path;
}
.sh-vis__frame-img { display: block; width: 100%; height: 100%; object-fit: cover; }

/* --reveal is registered so the sweep interpolates as a real number rather
   than a string swap; unregistered it would step instead of glide. */
@property --reveal { syntax: '<number>'; inherits: false; initial-value: 1; }

/* The assembly sweep: a hard-edged geometric boundary, gently raked, rising
   from the foot of the bed toward the headboard so the base reads as being
   built up. At --reveal:1 the boundary has cleared the top of the frame, so
   the whole bed including the headboard always finishes fully uncovered.
   Used only between a measured locked pair, where every pixel outside the bed
   is identical and this boundary is therefore invisible wherever it crosses
   the room. Nothing is feathered, masked or blurred. */
.sh-vis__frame[data-vis-mode="wipe"] {
  clip-path: polygon(
    0    calc(100% - var(--reveal, 1) * 112%),
    100% calc(107% - var(--reveal, 1) * 112%),
    100% 100%,
    0    100%
  );
}

/* No JS: show every shot unclipped so the finished bed reads, rather than a
   half-built stack. */
html:not(.sh-js) .sh-vis__frame { opacity: 1 !important; clip-path: none !important; }

/* The warm stage light, in CSS so the GPU never pays for a post pass — and so
   nothing on this page is ever blurred to fake depth. */
.sh-vis__stage::before {
  content: ''; position: absolute; inset: 0; z-index: 0;
  background:
    radial-gradient(58% 48% at 60% 32%, rgba(255, 198, 128, 0.08), transparent 70%),
    radial-gradient(70% 58% at 38% 82%, rgba(184, 164, 145, 0.06), transparent 72%);
}

.sh-vis__veil {
  position: absolute; inset: 0; z-index: 3; pointer-events: none;
  background:
    radial-gradient(116% 86% at 50% 44%, transparent 52%, rgba(0, 0, 0, 0.38) 100%),
    linear-gradient(0deg, rgba(4, 3, 3, 0.80) 0%, rgba(4, 3, 3, 0.22) 28%, transparent 54%);
}

.sh-vis__beats { position: absolute; left: 0; right: 0; bottom: clamp(38px, 7vh, 88px); z-index: 4; pointer-events: none; }
.sh-vis__beat { position: absolute; bottom: 0; left: var(--sh-gutter); right: var(--sh-gutter); opacity: 0; visibility: hidden; }
.sh-vis__beat-label { color: var(--sh-accent); margin: 0; }
.sh-vis__beat-note {
  font-family: var(--sh-font-display);
  font-size: clamp(1.5rem, 3.1vw, 2.6rem);
  line-height: 1.12; letter-spacing: var(--sh-ls-heading);
  color: var(--sh-ink); margin: var(--sh-s-3) 0 0; max-width: 22ch; text-wrap: balance;
  text-shadow: 0 2px 24px rgba(0, 0, 0, 0.45);
}
.sh-vis__cue {
  position: absolute; right: var(--sh-gutter); bottom: clamp(38px, 7vh, 88px); z-index: 4; margin: 0;
  font-family: var(--sh-font-body); font-size: var(--sh-fs-eyebrow);
  letter-spacing: var(--sh-ls-eyebrow); text-transform: uppercase;
  color: var(--sh-ink-faint); pointer-events: none;
}
@media (max-width: 767px) { .sh-vis__cue { display: none; } }

/* The rouge progress rule — the signature accent, marking position, nothing else. */
.sh-vis__rule { position: absolute; left: 0; right: 0; bottom: 0; z-index: 5; height: 2px; background: rgba(242, 241, 237, 0.14); }
.sh-vis__rule i {
  display: block; height: 100%; background: var(--sh-accent);
  transform: scaleX(0); transform-origin: 0 50%; will-change: transform;
}

/* -- 03 look inside ------------------------------------------------------- */
.sh-vis__inside { padding-block: clamp(80px, 13vw, 170px); }
.sh-vis__inside-grid {
  display: grid; grid-template-columns: minmax(0, 0.86fr) minmax(0, 1fr);
  gap: clamp(36px, 6vw, 96px); align-items: center;
}
@media (max-width: 900px) { .sh-vis__inside-grid { grid-template-columns: 1fr; } }

.sh-vis__xsec { position: relative; margin: 0; }
.sh-vis__xsec img { display: block; width: 100%; height: auto; border: 1px solid var(--sh-line); }

/* Layer callouts. Percentages track the real strata in the photograph. */
.sh-vis__call { position: absolute; left: 0; display: flex; align-items: center; gap: 12px; pointer-events: none; }
.sh-vis__call i { flex: 0 0 auto; width: clamp(26px, 4vw, 58px); height: 1px; background: var(--sh-accent); }
.sh-vis__call b {
  font-family: var(--sh-font-body); font-weight: var(--sh-fw-medium);
  font-size: clamp(9.5px, 0.78vw, 11px); letter-spacing: 0.18em; text-transform: uppercase;
  color: var(--sh-ink); background: rgba(8, 6, 5, 0.84); padding: 7px 12px;
  border: 1px solid var(--sh-line); white-space: nowrap;
}
@media (max-width: 560px) { .sh-vis__call b { white-space: normal; max-width: 46vw; } }

/* -- 04 craftsmanship ----------------------------------------------------- */
.sh-vis__bleed { position: relative; margin: 0; height: min(108svh, 1040px); overflow: hidden; }
.sh-vis__bleed-img { position: absolute; inset: -12% 0; }
.sh-vis__bleed-img img { width: 100%; height: 100%; object-fit: cover; }
.sh-vis__bleed-scrim {
  position: absolute; inset: 0;
  background: linear-gradient(180deg, rgba(4, 3, 3, 0.62), rgba(4, 3, 3, 0.18) 42%, rgba(4, 3, 3, 0.88));
}
.sh-vis__bleed-cap { position: absolute; left: 0; right: 0; bottom: 0; padding-bottom: clamp(48px, 8vw, 110px); }

.sh-vis__duo {
  display: grid; grid-template-columns: 1fr 1fr; gap: 1px;
  background: var(--sh-line); border: 1px solid var(--sh-line);
  margin-block: clamp(80px, 13vw, 170px);
}
@media (max-width: 800px) { .sh-vis__duo { grid-template-columns: 1fr; } }
.sh-vis__duo figure { margin: 0; background: var(--sh-ground-alt); overflow: hidden; }
.sh-vis__duo img {
  display: block; width: 100%; aspect-ratio: 4 / 3; object-fit: cover;
  transition: transform 1.2s var(--sh-ease);
}
.sh-vis__duo figure:hover img { transform: scale(1.03); }
.sh-vis__duo figcaption { padding: clamp(20px, 2.4vw, 34px); display: flex; flex-direction: column; gap: 6px; }
.sh-vis__nm { font-family: var(--sh-font-display); font-size: clamp(1.15rem, 1.7vw, 1.5rem); color: var(--sh-ink); }

/* -- 05 heritage ---------------------------------------------------------- */
.sh-vis__heritage { padding-block: clamp(80px, 13vw, 170px); border-top: 1px solid var(--sh-line); }
.sh-vis__years {
  display: grid; grid-template-columns: 1fr 1fr; gap: 1px;
  background: var(--sh-line); border: 1px solid var(--sh-line);
  margin-top: clamp(44px, 7vw, 90px);
}
@media (max-width: 800px) { .sh-vis__years { grid-template-columns: 1fr; } }
.sh-vis__year { margin: 0; background: var(--sh-ground-alt); }
.sh-vis__year-img { overflow: hidden; }
.sh-vis__year img {
  display: block; width: 100%; aspect-ratio: 16 / 11; object-fit: cover;
  /* archival grade — a filter on a real photograph, never a blur */
  filter: saturate(0.26) contrast(1.05) brightness(0.92);
  transition: filter 0.9s var(--sh-ease), transform 1.2s var(--sh-ease);
}
.sh-vis__year:hover img { filter: saturate(0.62) contrast(1.02) brightness(0.98); }
.sh-vis__year figcaption { padding: clamp(20px, 2.4vw, 34px); }
.sh-vis__yr { display: block; font-family: var(--sh-font-display); font-size: clamp(1.8rem, 3vw, 2.6rem); line-height: 1; color: var(--sh-ink); }
.sh-vis__yrtx { display: block; margin-top: 10px; font-size: var(--sh-fs-small); line-height: 1.55; color: var(--sh-ink-muted); max-width: 40ch; }

.sh-vis__milestone {
  display: flex; align-items: baseline; gap: clamp(16px, 2.4vw, 32px); flex-wrap: wrap;
  margin: clamp(44px, 7vw, 90px) 0 0; padding-top: clamp(28px, 4vw, 52px);
  border-top: 1px solid var(--sh-line);
}
.sh-vis__milestone-k { font-family: var(--sh-font-display); font-size: clamp(3rem, 9vw, 7rem); line-height: 0.9; color: var(--sh-ink); }
.sh-vis__milestone-v { font-family: var(--sh-font-body); font-size: var(--sh-fs-body); letter-spacing: 0.06em; color: var(--sh-ink-muted); max-width: 30ch; }

/* -- 06 the facts --------------------------------------------------------- */
.sh-vis__facts {
  display: grid; grid-template-columns: repeat(3, 1fr); gap: 1px;
  background: var(--sh-line); border: 1px solid var(--sh-line);
  margin-bottom: clamp(80px, 13vw, 170px);
}
@media (max-width: 900px) { .sh-vis__facts { grid-template-columns: repeat(2, 1fr); } }
@media (max-width: 520px) { .sh-vis__facts { grid-template-columns: 1fr; } }
.sh-vis__fact {
  background: var(--sh-ground-alt); padding: clamp(26px, 3vw, 46px) clamp(20px, 2.4vw, 34px);
  min-height: clamp(150px, 17vw, 210px); display: flex; flex-direction: column; justify-content: space-between; gap: var(--sh-s-5);
  transition: background var(--sh-dur-hover) var(--sh-ease);
}
.sh-vis__fact:hover { background: #121010; }
.sh-vis__fact-k { font-family: var(--sh-font-display); font-size: clamp(1.7rem, 3vw, 2.6rem); line-height: 1; color: var(--sh-ink); }
.sh-vis__fact-v { color: var(--sh-ink-faint); }

/* -- 07 Spicy Home x Vispring ---------------------------------------------
   The panel itself, its optional background photograph and the scrim that
   keeps the type legible over it all live in
   snippets/spicy-vispring-pair.liquid. Only the type sits here. */
.sh-vis__pair { padding-block: clamp(80px, 13vw, 170px); border-top: 1px solid var(--sh-line); text-align: center; }
.sh-vis__logo { width: clamp(120px, 14vw, 190px); height: auto; margin: 0 auto clamp(26px, 4vw, 46px); opacity: 0.92; }
.sh-vis__pair .sh-vis__marker { justify-content: center; }
.sh-vis__pair-h { max-width: 20ch; margin-inline: auto; }
.sh-vis__pair .sh-vis__prose { margin-inline: auto; }

/* -- 08 the invitation ---------------------------------------------------- */
.sh-vis__cta { padding-block: clamp(70px, 11vw, 150px); border-top: 1px solid var(--sh-line); text-align: center; }
.sh-vis__cta-h { max-width: 14ch; margin-inline: auto; }
.sh-vis__cta .sh-vis__prose { margin-inline: auto; }
.sh-vis__actions {
  display: flex; flex-wrap: wrap; align-items: center; justify-content: center;
  gap: clamp(20px, 3vw, 40px); margin-top: clamp(34px, 5vw, 60px);
}
.sh-vis__btn { color: var(--sh-ink); border-color: var(--sh-line-strong); }
.sh-vis__btn:hover, .sh-vis__btn:focus-visible { border-color: var(--sh-ink); }

/* -- reduced motion --------------------------------------------------------
   The bed is shown once, fully assembled, and the closing caption shown.
   Nothing scrolls, nothing is missing. */
@media (prefers-reduced-motion: reduce) {
  .sh-vis__track { height: 100svh; }
  .sh-vis__cue { display: none; }
  .sh-vis__duo figure:hover img,
  .sh-vis__year:hover img { transform: none; }
}
/* END_SECTION:spicy-vispring */