/* ══════════════════════════════════════════════════════════════════════════
   Thaisky-Digital — Construction Time-lapse
   Page layer. Colors, radii and shadows come from the Nocturne tokens as
   retuned in theme.css; the only values added here are page-scale rhythm
   steps the compact --space-* scale doesn't carry.

   Brand roles, following the logo's own structure:
     yellow (--color-accent, #fffc00)   the figure — links, kickers, focus,
                                        outlines, frames, hovers
     red    (--color-accent-2, step 600) the field — bars, marks, glows,
                                        active fills, the progress ramp

   The yellow is used as the flat brand value rather than a ramp step: at
   L 0.962 it sits above the top of the shared lightness scale, so there is
   no step that is it. The ramp is still there for tints and shades —
   --color-accent-100 carries the hovers, where "brighter" is not available
   above #fffc00 and the move has to be toward white instead.
   ══════════════════════════════════════════════════════════════════════ */

:root {
  /* Page-scale rhythm — the --space-* scale is interface-density (0.7x) and
     tops out at 22.4px, so section gutters get their own steps. */
  --gutter: 32px;
  --gap-lg: 48px;
  --gap-xl: 56px;
  --section-y: 80px;
  --shell: 1240px;

  /* Text on the dark ground, by role. Derived from --color-text so a token
     change carries through. */
  --text-strong: color-mix(in srgb, var(--color-text) 94%, transparent);
  --text-body:   color-mix(in srgb, var(--color-text) 86%, transparent);
  --text-muted:  color-mix(in srgb, var(--color-text) 74%, transparent);
  --text-faint:  color-mix(in srgb, var(--color-text) 62%, transparent);
  /* Things you click rest lower than things you read, so that coming
     forward on hover is a visible change. Reading text cannot use this —
     it has to be legible without a pointer, which phones do not have. */
  --text-interactive: color-mix(in srgb, var(--color-text) 66%, transparent);
  --hairline:    color-mix(in srgb, var(--color-text) 10%, transparent);

  --gallery-cols: 3;

  /* Height every client mark is drawn at. The tile is 176x78 with 15px
     padding, so the inner box is 146x48 — this must stay at or under 48,
     and 146 must stay above 2.86x it (the widest mark's ratio). */
  --logo-h: 48px;

  /* One number scales the page's type. Every font-size in this file is
     written as calc(Npx * var(--text-scale)), so the numbers stay readable
     as the design's own values and the multiplier is the only thing to
     touch. */
  --text-scale: 1.4;

  /* The header is chrome, not reading matter, and it sits on one line at a
     fixed height. Doubling it made the nav wrap mid-word, so it gets its
     own gentler multiplier. */
  --ui-scale: 1.25;

  /* Section headings sit between the two: at their own base sizes they are
     already the largest type on the page, so they do not need the full body
     multiplier to still read as headings. */
  --title-scale: 1.2;
}

/* The design system sets its own sizes on body and .btn; without these the
   buttons and base text would stay behind while everything else grew. */
body { font-size: calc(15px * var(--text-scale)); }
.btn { font-size: calc(14px * var(--text-scale)); }

/* — display face ────────────────────────────────────────────────────────
   "Construction Time-lapse" is set in Chakra Petch Bold Italic. Hemi Head
   426 was the original intent, but it is a commercial Typodermic release
   whose webfont licence is sold separately from the free desktop one, and
   this is the closest freely-licensed match: the same squared, slanted,
   flat-terminalled letterforms, and a real italic rather than a browser-
   faked slant. It also carries Thai, which none of the other candidates
   did — so the face stays available if headings ever go bilingual. */
.display {
  font-family: "Chakra Petch", "Inter", system-ui, sans-serif;
  font-weight: 700;
  font-style: italic;
}

body {
  font-family: "Inter", "Noto Sans Thai", system-ui, sans-serif;
  overflow-x: hidden;
}
h1, h2, h3, h4, h5, h6 { font-family: "Inter", "Noto Sans Thai", system-ui, sans-serif; }
a { color: var(--color-accent); text-decoration: none; }
a:hover { color: var(--color-accent-100); }

.shell { max-width: var(--shell); margin-inline: auto; }
.section { padding: var(--section-y) var(--gutter); }

.skip-link {
  position: absolute; left: var(--space-4); top: -60px; z-index: 80;
  padding: var(--space-2) var(--space-4); border-radius: var(--radius-md);
  background: var(--color-surface); box-shadow: var(--shadow-md);
  color: var(--color-text); transition: top 0.18s ease;
}
.skip-link:focus-visible { top: var(--space-4); }

/* — language ────────────────────────────────────────────────────────────
   Both languages ship in the document; the inactive one is hidden rather
   than swapped in, so nothing depends on JS to have content and both stay
   in the markup for indexing. Scoped to `body ...` so the rule can never
   match <html lang>, and the switcher's own buttons opt out — their labels
   are genuinely Thai and English and both must always be visible. */
html[data-lang="th"] body [lang="en"]:not(.lang-opt) { display: none; }
html[data-lang="en"] body [lang="th"]:not(.lang-opt) { display: none; }

.lang-switch {
  display: inline-flex; overflow: hidden; flex: none;
  border: 1px solid var(--color-divider); border-radius: var(--radius-md);
}
.lang-opt {
  padding: 5px 10px; font: inherit; font-size: calc(12px * var(--ui-scale)); letter-spacing: 0.06em;
  background: transparent; border: 0; color: var(--text-interactive); cursor: pointer;
  transition: background 0.18s ease, color 0.18s ease;
}
.lang-opt + .lang-opt { border-left: 1px solid var(--color-divider); }
.lang-opt:hover { background: color-mix(in srgb, var(--color-text) 8%, transparent); color: var(--color-text); }
.lang-opt:active { background: color-mix(in srgb, var(--color-text) 14%, transparent); }
.lang-opt.is-active { color: var(--color-accent); box-shadow: inset 0 0 0 1px var(--color-accent); }

/* — header ──────────────────────────────────────────────────────────────── */
.site-header {
  position: sticky; top: 0; z-index: 40;
  display: flex; align-items: center; justify-content: space-between;
  gap: var(--space-6); padding: var(--space-4) var(--gutter);
  background: color-mix(in srgb, var(--color-bg) 88%, transparent);
  backdrop-filter: blur(14px); -webkit-backdrop-filter: blur(14px);
  border-bottom: 1px solid var(--hairline);
}
.brand { display: flex; align-items: center; gap: var(--space-4); color: var(--color-text); }
.brand:hover { color: var(--color-text); }
/* The mark is the company logo itself: black ground, red disc, gold letters.
   .lighten drops its black straight into the page ground. */
.brand-mark {
  display: block; flex: none; width: 34px; height: 34px;
  border-radius: var(--radius-sm); overflow: hidden;
}
.brand-mark img { width: 100%; height: 100%; object-fit: cover; mix-blend-mode: lighten; }
.brand-name {
  font-size: calc(14px * var(--ui-scale)); font-weight: var(--font-heading-weight);
  letter-spacing: 0.12em; text-transform: uppercase;
}
.site-nav {
  display: flex; align-items: center; gap: var(--space-6);
  font-size: calc(13px * var(--ui-scale)); letter-spacing: 0.06em; text-transform: uppercase;
}
.site-nav > a { color: var(--text-interactive); }
.site-nav > a:hover { color: var(--color-accent-100); }
.nav-cta { font-size: calc(12px * var(--ui-scale)); letter-spacing: 0.08em; }
.nav-cta:hover { color: var(--color-accent); }

/* — hero ────────────────────────────────────────────────────────────────── */
.hero { position: relative; padding: 100px var(--gutter) var(--section-y); }
/* The logo's two colors as light rather than fill: a red bloom with a
   smaller gold one inside it, the way the mark reads at a glance. */
.hero-glow {
  position: absolute; top: -140px; left: -180px; width: 680px; height: 680px;
  border-radius: 50%; pointer-events: none;
  background:
    radial-gradient(circle at 42% 46%,
      color-mix(in srgb, var(--color-accent) 14%, transparent), transparent 42%),
    radial-gradient(circle,
      color-mix(in srgb, var(--color-accent-2) 22%, transparent), transparent 66%);
}
.hero-grid {
  position: relative;
  display: grid; grid-template-columns: minmax(0, 1.05fr) minmax(0, 0.85fr);
  gap: var(--gap-xl); align-items: start;
}
.eyebrow {
  display: flex; align-items: center; gap: var(--space-3);
  margin: 0 0 var(--space-8); font-size: calc(12px * var(--text-scale)); letter-spacing: 0.18em;
  text-transform: uppercase; color: var(--color-accent);
}
.eyebrow-rule {
  display: block; flex: none; width: 28px; height: 2px;
  background: linear-gradient(to right, var(--color-accent-2), var(--color-accent));
}
/* "Construction" is one unbreakable word 5.86x as wide as the type size, so
   past a certain size it runs straight out of the column — no wrapping can
   save it. The min() caps the heading at what the column can actually hold
   at each width, which is why doubling stops short here and nowhere else. */
.hero-title {
  font-size: min(calc(66px * var(--text-scale)), calc(9vw - 10px), 105px);
  line-height: 1.02; letter-spacing: -0.03em;
  margin: 0 0 var(--space-6);
}
.hero-subtitle {
  font-size: calc(22px * var(--text-scale)); font-weight: 400; letter-spacing: 0;
  color: color-mix(in srgb, var(--color-text) 72%, transparent);
  margin: 0 0 var(--space-8);
}
.hero-lede {
  font-size: calc(16px * var(--text-scale)); line-height: 1.85; color: var(--text-body);
  max-width: 56ch; margin: 0 0 var(--space-6); text-wrap: pretty;
}
.hero-actions { display: flex; flex-wrap: wrap; gap: var(--space-4); margin-top: var(--space-8); }
.btn-quiet { color: color-mix(in srgb, var(--color-text) 70%, transparent); }
.btn-quiet:hover { color: var(--color-accent-100); }

.pillars { list-style: none; display: grid; gap: var(--space-4); margin: 0; padding: var(--space-3) 0 0; }
.pillar {
  position: relative; overflow: hidden;
  background: var(--color-surface); border-radius: var(--radius-md);
  box-shadow: var(--shadow-sm);
  padding: var(--space-6) var(--space-6) var(--space-6) var(--space-8);
}
.pillar-bar {
  position: absolute; left: 0; top: var(--space-6); bottom: var(--space-6);
  width: 2px; background: var(--color-accent-2);
}
.pillar-kicker {
  margin: 0 0 var(--space-2); font-size: calc(12px * var(--text-scale)); letter-spacing: 0.14em;
  text-transform: uppercase; color: var(--color-accent);
}
.pillar-body { margin: 0; font-size: calc(14px * var(--text-scale)); line-height: 1.7; color: var(--text-body); }

/* — clients ─────────────────────────────────────────────────────────────── */
.clients { margin-top: 72px; padding-top: var(--space-8); border-top: 1px solid var(--hairline); }
.clients-head {
  display: flex; align-items: baseline; justify-content: space-between;
  flex-wrap: wrap; gap: var(--space-8); margin-bottom: var(--space-6);
}
.clients-title { margin: 0; font-size: calc(13px * var(--text-scale)); letter-spacing: 0.14em; text-transform: uppercase; color: var(--text-muted); }
.clients-count { font-size: calc(13px * var(--text-scale)); color: var(--text-faint); }
/* — client logos ───────────────────────────────────────────────────────
   The marks keep their own colours, which means keeping their white
   grounds too — so each one gets a white tile rather than being dropped
   into the page. The tiles are identical, and sized so that every mark is
   limited by the tile's height rather than its width: the widest of them
   (Le Menara, 2.86:1) still clears the inner width at full height, so all
   five render at exactly the same height. */
.logo-marquee {
  position: relative; overflow: hidden; margin-bottom: var(--space-8);
  /* fade the ends so logos enter and leave rather than being cut off */
  -webkit-mask-image: linear-gradient(to right, transparent, #000 60px, #000 calc(100% - 60px), transparent);
          mask-image: linear-gradient(to right, transparent, #000 60px, #000 calc(100% - 60px), transparent);
}
/* The spacing lives on the tiles, not as a flex gap: translateX(-50%) only
   lands on a seam if each half is exactly one tile-plus-gap times five. A
   `gap` would leave one fewer gap in each half and the loop would jump. */
.logo-track {
  display: flex; width: max-content;
  animation: logoMarquee 32s linear infinite;
}
/* Same courtesy the old carousel had: it stopped while you were looking. */
.logo-marquee:hover .logo-track { animation-play-state: paused; }
@keyframes logoMarquee { to { transform: translateX(-50%); } }

.logo {
  flex: none; width: 176px; height: 78px; padding: 15px; margin-right: 18px;
  display: flex; align-items: center; justify-content: center;
  background: #fff; border-radius: var(--radius-sm);
}
/* An explicit height, not a percentage: percentages here resolve against a
   box the browser treats as indefinite, so the marks kept being fitted by
   width and each came out a different height. Pinning the height and
   letting the width follow the aspect ratio is what actually makes all
   five the same size — the tile is wide enough that even the widest mark
   (Le Menara at 2.86:1) is never clipped. */
.logo img {
  height: var(--logo-h); width: auto; max-width: 100%; object-fit: contain;
}
.clients-list { margin: 0; font-size: calc(14px * var(--text-scale)); line-height: 1.9; color: var(--text-muted); max-width: 100ch; }

/* — shared section furniture ────────────────────────────────────────────── */
.kicker { margin: 0 0 var(--space-3); font-size: calc(13px * var(--text-scale)); letter-spacing: 0.14em; text-transform: uppercase; color: var(--color-accent); }
.section-title { margin: 0 0 var(--space-3); font-size: calc(38px * var(--title-scale)); letter-spacing: -0.02em; }
.section-lede { margin: 0 0 var(--gutter); color: var(--text-muted); max-width: 60ch; }
.section-head {
  display: flex; align-items: flex-end; justify-content: space-between;
  flex-wrap: wrap; gap: var(--space-8); margin-bottom: var(--space-8);
}
.section-head .section-title { margin-bottom: 0; }

/* — chips (filters and step tabs) ───────────────────────────────────────── */
.chips { display: flex; flex-wrap: wrap; gap: var(--space-3); }
.chip {
  display: inline-flex; align-items: center; gap: 6px; cursor: pointer;
  font: inherit; font-size: calc(13px * var(--text-scale)); letter-spacing: 0.04em;
  padding: 7px 14px; border-radius: var(--radius-md);
  background: transparent; color: var(--text-body);
  border: 1px solid color-mix(in srgb, var(--color-text) 16%, transparent);
  transition: background 0.18s ease, color 0.18s ease, border-color 0.18s ease;
}
.chip:hover { background: color-mix(in srgb, var(--color-text) 7%, transparent); color: var(--color-text); }
.chip:active { background: color-mix(in srgb, var(--color-text) 14%, transparent); }
/* Active state is the logo in miniature: yellow lettering on a red ground —
   so this one keeps the brand value rather than the near-white the other
   hover states moved to. */
.chip.is-active {
  background: color-mix(in srgb, var(--color-accent-2) 22%, transparent);
  border-color: var(--color-accent-2); color: var(--color-accent);
}
.chip.is-active:hover { background: color-mix(in srgb, var(--color-accent-2) 30%, transparent); }
.chip-stack { flex-direction: column; align-items: flex-start; gap: 2px; padding: 8px 14px; }
.step-num { font-size: calc(11px * var(--text-scale)); letter-spacing: 0.12em; opacity: 0.7; }
.step-short { font-size: calc(13px * var(--text-scale)); }

/* — gallery ─────────────────────────────────────────────────────────────── */
.gallery {
  display: grid; gap: var(--space-6);
  grid-template-columns: repeat(var(--gallery-cols), minmax(0, 1fr));
}
.video-card {
  display: block; text-align: left; padding: 0; cursor: pointer; border: 0;
  font: inherit; color: inherit; background: var(--color-surface);
  border-radius: var(--radius-md); overflow: hidden; box-shadow: var(--shadow-sm);
  transition: box-shadow 0.2s ease, transform 0.2s ease;
}
.video-card:hover { box-shadow: var(--shadow-md); transform: translateY(-2px); }
.video-card:active { transform: translateY(0); }
.video-card[hidden] { display: none; }
.video-thumb {
  position: relative; display: block; aspect-ratio: 16 / 9;
  overflow: hidden; background: var(--color-neutral-900);
}
.video-thumb img {
  width: 100%; height: 100%; object-fit: cover; opacity: 0.82;
  transition: opacity 0.2s ease, transform 0.35s ease;
}
.video-card:hover .video-thumb img { opacity: 1; transform: scale(1.03); }
.video-scrim {
  position: absolute; inset: 0;
  background: linear-gradient(to top, color-mix(in srgb, var(--color-bg) 88%, transparent), transparent 55%);
}
.video-badge { position: absolute; left: 14px; bottom: 14px; display: flex; align-items: center; gap: var(--space-3); }
/* Red ring, gold play mark — the disc and the letters. */
.play-dot {
  display: grid; place-items: center; width: 34px; height: 34px; border-radius: 50%;
  border: 1px solid var(--color-accent-2);
  background: color-mix(in srgb, var(--color-bg) 55%, transparent);
  transition: background 0.2s ease, border-color 0.2s ease;
}
.play-dot::before {
  content: ""; display: block; width: 0; height: 0; margin-left: 3px;
  border-left: 9px solid var(--color-accent);
  border-top: 6px solid transparent; border-bottom: 6px solid transparent;
}
.video-card:hover .play-dot { background: color-mix(in srgb, var(--color-accent-2) 55%, transparent); }
.video-tag { font-size: calc(12px * var(--text-scale)); letter-spacing: 0.1em; text-transform: uppercase; color: color-mix(in srgb, var(--color-text) 70%, transparent); }
.video-meta {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: var(--space-4); padding: 14px var(--space-6) var(--space-6);
}
/* Titles sit back in the same grey the nav links use and come forward on
   hover, so the row reads as a set of links rather than a wall of white.
   The trigger is the whole card, not the words — the card is the button. */
.video-title {
  font-size: calc(17px * var(--text-scale)); font-weight: var(--font-heading-weight);
  letter-spacing: -0.01em; color: var(--text-interactive);
  transition: color 0.18s ease;
}
.video-card:hover .video-title,
.video-card:focus-visible .video-title,
.video-card:active .video-title { color: var(--color-accent-100); }
.video-duration { font-size: calc(13px * var(--text-scale)); color: var(--text-muted); white-space: nowrap; }

/* — process ─────────────────────────────────────────────────────────────── */
.process {
  padding: var(--section-y) var(--gutter);
  background: linear-gradient(180deg,
    var(--color-bg), color-mix(in srgb, var(--color-accent-2) 7%, var(--color-bg)) 45%, var(--color-bg));
}
.step-tabs { display: flex; flex-wrap: wrap; gap: var(--space-3); margin-bottom: var(--space-8); }
.progress-track {
  height: 2px; border-radius: 1px; overflow: hidden;
  background: var(--hairline); margin-bottom: var(--gutter);
}
/* Red into gold — the gradient the logo disc itself runs. */
.progress-fill {
  height: 2px; width: 14.3%;
  background: linear-gradient(to right, var(--color-accent-2), var(--color-accent));
  transition: width 0.35s ease;
}
.step-panel {
  display: grid; grid-template-columns: minmax(0, 0.9fr) minmax(0, 1.1fr);
  gap: var(--gap-lg); align-items: start;
}
.step-panel[hidden] { display: none; }
.step-stage { margin: 0 0 var(--space-4); font-size: calc(12px * var(--text-scale)); letter-spacing: 0.16em; text-transform: uppercase; color: var(--color-accent); }
.step-title { margin: 0 0 var(--space-4); font-size: calc(34px * var(--title-scale)); letter-spacing: -0.02em; }
.step-note { margin: 0; color: var(--text-muted); font-size: calc(15px * var(--text-scale)); line-height: 1.8; }
.step-items {
  list-style: none; margin: 0; padding: 0;
  display: grid; gap: 1px; background: var(--hairline);
  border-radius: var(--radius-md); overflow: hidden; box-shadow: var(--shadow-sm);
}
.step-items li {
  display: flex; align-items: flex-start; gap: var(--space-4);
  background: var(--color-surface); padding: 14px var(--space-6);
  font-size: calc(15px * var(--text-scale)); line-height: 1.65; color: var(--text-strong);
}
.step-items li::before {
  content: ""; flex: none; margin-top: 8px; width: 5px; height: 5px;
  border-radius: 50%; background: var(--color-accent-2);
}

/* — capability ──────────────────────────────────────────────────────────
   The one light band on the page. The sketch renders are dark line work on
   white and are left at their own polarity — they read as drawings, which
   is the point — so the card carries the white ground with them and the
   type flips dark to suit. Each plate is framed in the brand gold, which
   is what holds the band to the rest of the page. */
.cap-grid { display: grid; grid-template-columns: repeat(auto-fit, minmax(300px, 1fr)); gap: var(--space-6); }
/* The frame sits on the outside of the white card, not around the photo:
   a border inside the card would have to hold its own against white, and
   on the outer edge it meets the black page instead. Deep red rather than
   the brand yellow — the yellow was doing the job of an outline, and this
   band is the one place the page turns light, so the frame reads better as
   the darker of the two brand colours. */
.cap-card {
  display: flex; flex-direction: column;
  border: 2px solid var(--color-accent-2-700);
  border-radius: var(--radius-md); padding: var(--space-3);
  background: var(--color-neutral-100);
  color: var(--color-neutral-900);
}
.cap-figure {
  height: 190px; flex: none; overflow: hidden; background: #fff;
  border-radius: var(--radius-sm);
}
.cap-figure img { width: 100%; height: 100%; object-fit: cover; }
/* The LINE code is a scannable target, not a photograph: contain rather
   than cover, so its quiet zone survives and readers keep locking on. */
.cap-figure--plate img { object-fit: contain; }
.cap-body { padding: var(--space-4) var(--space-2) var(--space-2); }
.cap-title {
  margin: 0 0 var(--space-2); font-size: calc(15px * var(--text-scale)); letter-spacing: 0.1em;
  text-transform: uppercase; color: var(--color-neutral-900);
}
.cap-text {
  margin: 0; font-size: calc(14px * var(--text-scale)); line-height: 1.75;
  color: color-mix(in srgb, var(--color-neutral-900) 82%, transparent);
}

/* — contact ─────────────────────────────────────────────────────────────── */
.contact {
  padding: var(--section-y) var(--gutter) 100px;
  background: color-mix(in srgb, var(--color-accent-2) 5%, var(--color-bg));
  border-top: 1px solid var(--hairline);
}
.contact-grid {
  display: grid; grid-template-columns: minmax(0, 0.85fr) minmax(0, 1.15fr);
  gap: var(--gap-lg); align-items: start;
}
.contact .section-title { margin-bottom: var(--space-8); }
.contact-list { display: grid; gap: var(--space-6); max-width: 44ch; }
.contact-label { margin: 0 0 var(--space-1); font-size: calc(12px * var(--text-scale)); letter-spacing: 0.14em; text-transform: uppercase; color: var(--text-faint); }
.contact-value { margin: 0; font-size: calc(15px * var(--text-scale)); line-height: 1.7; color: var(--text-strong); }
.contact-note { margin: var(--space-3) 0 0; font-size: calc(14px * var(--text-scale)); color: var(--text-muted); }
.map-frame { border-radius: var(--radius-md); overflow: hidden; box-shadow: var(--shadow-sm); }
.map-frame iframe {
  display: block; width: 100%; height: 420px; border: 0;
  filter: grayscale(0.6) invert(0.92) hue-rotate(185deg) brightness(0.95);
}

/* — footer ──────────────────────────────────────────────────────────────── */
.site-footer {
  padding: var(--space-8) var(--gutter);
  display: flex; flex-wrap: wrap; gap: var(--space-4);
  align-items: center; justify-content: space-between;
  border-top: 1px solid var(--hairline);
  font-size: calc(13px * var(--text-scale)); color: var(--text-faint);
}

/* — player ──────────────────────────────────────────────────────────────── */
@keyframes tsFade { from { opacity: 0; transform: translateY(10px); } to { opacity: 1; transform: none; } }

.player {
  position: fixed; inset: 0; z-index: 60;
  display: grid; place-items: center; padding: var(--gutter);
  background: color-mix(in srgb, var(--color-bg) 92%, transparent);
  backdrop-filter: blur(8px); -webkit-backdrop-filter: blur(8px);
  animation: tsFade 0.22s ease-out;
}
.player[hidden] { display: none; }
.player-panel { width: min(1100px, 100%); animation: tsFade 0.3s ease-out; }
.player-head {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: var(--space-8); margin-bottom: var(--space-4);
}
.player-tag { margin: 0 0 var(--space-1); font-size: calc(12px * var(--text-scale)); letter-spacing: 0.14em; text-transform: uppercase; color: var(--color-accent); }
.player-title { margin: 0; font-size: calc(26px * var(--title-scale)); }
/* Line 2 of the YouTube description, when there is one. */
.player-note {
  margin: var(--space-2) 0 0; max-width: 68ch;
  font-size: calc(14px * var(--text-scale)); line-height: 1.7; color: var(--text-muted);
}
.player-note[hidden] { display: none; }
.player-tag[hidden] { display: none; }
.player-stage {
  position: relative; aspect-ratio: 16 / 9;
  border-radius: var(--radius-md); overflow: hidden; box-shadow: var(--shadow-md);
  background: var(--color-neutral-900);
}
.player-stage iframe { position: absolute; inset: 0; width: 100%; height: 100%; border: 0; }
.player-foot {
  display: flex; align-items: center; justify-content: space-between;
  gap: var(--space-6); margin-top: var(--space-4);
}
.player-position { font-size: calc(13px * var(--text-scale)); color: var(--text-faint); }

body.is-locked { overflow: hidden; }

/* — responsive ──────────────────────────────────────────────────────────── */
@media (max-width: 1080px) {
  :root { --gallery-cols: 2; }
  .hero-title { font-size: min(calc(54px * var(--text-scale)), calc(9vw - 10px)); }
}

@media (max-width: 900px) {
  :root { --gutter: 24px; --gap-lg: 32px; --gap-xl: 40px; --section-y: 64px; }
  .hero { padding-top: 64px; }
  .hero-grid, .step-panel, .contact-grid { grid-template-columns: minmax(0, 1fr); }
  .hero-title { font-size: min(calc(46px * var(--text-scale)), calc(16vw - 8px)); }
  .hero-subtitle { font-size: calc(20px * var(--text-scale)); }
  .section-title { font-size: calc(32px * var(--title-scale)); }
  .step-title { font-size: calc(28px * var(--title-scale)); }
  .clients { margin-top: var(--gap-xl); }
  .map-frame iframe { height: 320px; }
}

@media (max-width: 680px) {
  :root { --gallery-cols: 1; --gutter: 20px; }
  .site-nav > a:not(.nav-cta) { display: none; }
  .site-nav { gap: var(--space-3); }
  .brand-name { display: none; }
  .hero-title { font-size: min(calc(36px * var(--text-scale)), calc(16vw - 8px)); }
  .hero-lede { font-size: calc(15px * var(--text-scale)); line-height: 1.8; }
  .section-title { font-size: calc(27px * var(--title-scale)); }
  .cap-grid { grid-template-columns: minmax(0, 1fr); }
  .player { padding: var(--space-6); }
  .player-title { font-size: calc(20px * var(--title-scale)); }
  .player-foot { gap: var(--space-3); }
  .player-position { order: 3; flex-basis: 100%; text-align: center; }
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important; animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important; scroll-behavior: auto !important;
  }
  .video-card:hover { transform: none; }
  .video-card:hover .video-thumb img { transform: none; }
  /* The blanket rule above would freeze the marquee at the end of its run,
     showing only the duplicate half. Stop it at the start and let the tiles
     wrap onto lines instead, so every logo is still visible standing still. */
  .logo-track { animation: none; transform: none; flex-wrap: wrap; width: 100%; }
  .logo-marquee { -webkit-mask-image: none; mask-image: none; }
  .logo-track > [aria-hidden="true"] { display: none; }
}
