/* Pitch site, Operating Bureau brand.
   Warm cream ground, black type, one yellow accent. No top bar: the headline
   is the first thing on the page, nothing sits above it competing. */

.backlink{display:inline-block;margin:22px 0 0 max(16px,var(--gutter));
  font-family:var(--font-label);font-size:.6875rem;letter-spacing:.14em;
  text-transform:uppercase;opacity:.5;text-decoration:none}
.backlink:hover{opacity:.85}

/* ---- hero wordmark: a quiet identity mark, not a bar. No background, no
   border, no nav beside it, no button. If it ever grows any of those it has
   become the bar this page deliberately doesn't have, see build/design.md ---- */
.hero__mark{display:block;font-family:var(--font-label);font-size:.75rem;
  letter-spacing:.16em;text-transform:uppercase;opacity:.6;margin:0 0 clamp(20px,3vw,32px)}

/* ---- hero: headline first, video staged, their world scattered round it ---- */
.hero{padding-block:clamp(44px,6vw,84px) clamp(36px,5vw,68px);position:relative;overflow:hidden}
.hero__head{max-width:27ch;margin:0 auto;padding-bottom:.12em}
.hero__sub{margin-top:1.6rem;max-width:50ch;margin-inline:auto;font-size:1.0625rem;opacity:.78}

/* stage: the video, with their real photographs floating around it */
.hero__stage{position:relative;margin:clamp(30px,4.5vw,54px) auto 0;max-width:1120px}
.hero__video{position:relative;z-index:2;margin-inline:auto;max-width:780px;
  border-radius:var(--r-lg);overflow:hidden;background:#0d0c0a;aspect-ratio:16/9;
  box-shadow:0 30px 80px rgba(40,30,10,.20),0 2px 0 rgba(0,0,0,.04)}
.hero__video iframe{position:absolute;inset:0;width:100%;height:100%;border:0}

.scatter{position:absolute;inset:0;z-index:1;pointer-events:none}
/* Entrance drifts each photograph in from outside its resting spot (--dx/--dy,
   set per item in initHeroStage() as a vector away from the video's centre)
   rather than fading up in place: it reads as photographs settling into a
   composition instead of a row of thumbnails switching on, and the slight
   overshoot in the easing curve (past 1, back to 1) is what keeps the settle
   from looking mechanical. prefers-reduced-motion still wins outright, see
   base.css's global transition:none override. */
.scatter__item{position:absolute;width:var(--w,150px);
  border-radius:var(--rad,14px);overflow:hidden;background:var(--ob-mist);
  box-shadow:0 14px 34px rgba(40,30,10,.18);
  transform:translate(var(--dx,0),var(--dy,0)) rotate(calc(var(--r,0deg) * 2.4)) scale(.7);
  opacity:0}
.scatter__item img{width:100%;height:100%;object-fit:cover;display:block;aspect-ratio:var(--ar,4/5)}
.scatter__item--round{border-radius:50%}
.scatter__item--round img{aspect-ratio:1/1}
.js .scatter__item{transition:opacity 640ms var(--ease) var(--d,0ms),
  transform 900ms cubic-bezier(.24,1.16,.32,1) var(--d,0ms)}
.is-lit .scatter__item{opacity:1;transform:translate(0,0) rotate(var(--r,0deg)) scale(1)}
/* A slow, barely-there float once landed keeps the composition from going
   inert: a few seconds of drift per item, offset so they never move in sync. */
.is-lit .scatter__item{animation:scatter-float var(--float-dur,7s) ease-in-out var(--d,0ms) infinite}
@keyframes scatter-float{
  0%,100%{translate:0 0}
  50%{translate:0 -7px}
}

/* below the video */
.hero__cta{margin-top:clamp(24px,3.5vw,38px);display:flex;gap:1rem;flex-wrap:wrap;
  align-items:center;justify-content:center}
.hero__meta{font-family:var(--font-label);font-size:.6875rem;letter-spacing:.14em;
  text-transform:uppercase;opacity:.55;width:100%}

/* mobile: the scatter would collide with everything, so it becomes a row of
   thumbs under the video instead of vanishing. The research still shows. */
.hero__strip{display:none;gap:10px;justify-content:center;flex-wrap:wrap;
  margin-top:22px}
.hero__strip img{width:62px;height:78px;object-fit:cover;border-radius:10px;
  box-shadow:0 6px 16px rgba(40,30,10,.16)}

/* Too little gutter left of the video for a photograph to read: main.js's
   placeScatter() measures the real gap and sets this, rather than relying on a
   width breakpoint that cannot know how wide the video actually rendered. The
   thumb strip takes over. */
.hero.is-cramped .scatter{display:none}
.hero.is-cramped .hero__strip{display:flex}

@media(max-width:900px){
  .scatter{display:none}
  .hero__strip{display:flex}
}

/* ---- deliverable groups ---- */
.group{padding-block:clamp(48px,6vw,88px)}
.group + .group{border-top:1px solid var(--ob-line)}
.group__label{font-family:var(--font-label);font-size:.6875rem;letter-spacing:.18em;
  text-transform:uppercase;opacity:.55;margin-bottom:.75rem}
.group__title{margin-bottom:.6rem}
.group__sub{max-width:48ch;margin:0 auto clamp(28px,3.5vw,44px);opacity:.75;font-size:.9875rem}

/* browser-chrome preview of a real page */
.frames{display:grid;gap:18px;grid-template-columns:1fr;margin-bottom:clamp(24px,3vw,36px)}
@media(min-width:760px){.frames--3{grid-template-columns:repeat(3,1fr)}
  .frames--2{grid-template-columns:repeat(2,1fr)}}
/* a lone frame is a feature shot, not a full-bleed band */
.frames--1{max-width:760px;margin-inline:auto}
.frames--1 .frame__shot{aspect-ratio:16/10}
.cards--1{max-width:420px;margin-inline:auto}
.frame{border-radius:var(--r);overflow:hidden;background:var(--ob-paper);
  box-shadow:0 1px 0 rgba(0,0,0,.08),0 14px 34px rgba(0,0,0,.10);text-align:left}
a.frame{display:block;text-decoration:none;color:inherit;cursor:pointer;
  transition:transform var(--dur-fast) var(--ease),box-shadow var(--dur-fast) var(--ease)}
a.frame:hover{transform:translateY(-3px);box-shadow:0 1px 0 rgba(0,0,0,.08),0 20px 44px rgba(0,0,0,.13)}
.frame__bar{display:flex;align-items:center;gap:8px;padding:9px 12px;
  background:var(--ob-mist);border-bottom:1px solid var(--ob-line)}
.frame__dots{display:flex;gap:5px;flex:0 0 auto}
.frame__dots i{width:9px;height:9px;border-radius:50%;background:rgba(0,0,0,.16);display:block}
.frame__url{flex:1;background:var(--ob-paper);border-radius:var(--r-pill);
  padding:4px 10px;font-size:.6875rem;color:rgba(0,0,0,.5);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.frame__shot{aspect-ratio:4/3;overflow:hidden;background:var(--ob-mist);position:relative}
.frame__shot img{width:100%;height:100%;object-fit:cover;object-position:top center}

/* the numbered cards under each group */
.cards{display:grid;gap:16px;grid-template-columns:1fr}
@media(min-width:760px){.cards--3{grid-template-columns:repeat(3,1fr)}
  .cards--2{grid-template-columns:repeat(2,1fr)}}
.card{display:block;text-decoration:none;background:var(--ob-paper);
  border-radius:var(--r);padding:22px 20px;text-align:center;
  box-shadow:0 1px 0 rgba(0,0,0,.06),0 6px 18px rgba(0,0,0,.06);
  transition:transform var(--dur-fast) var(--ease),box-shadow var(--dur-fast) var(--ease)}
.card:hover{transform:translateY(-3px);box-shadow:0 1px 0 rgba(0,0,0,.06),0 16px 34px rgba(0,0,0,.11)}
.card__n{font-family:var(--font-label);font-size:.625rem;letter-spacing:.18em;
  text-transform:uppercase;opacity:.5;display:block;margin-bottom:.6rem}
.card__title{font-family:var(--font-display);font-size:1.1875rem;color:var(--ob-black);
  margin:0 0 .4rem}
.card__desc{font-size:.9375rem;margin:0;opacity:.78;max-width:34ch;margin-inline:auto}
.card__open{margin-top:.9rem;display:inline-block;font-family:var(--font-label);
  font-size:.625rem;letter-spacing:.14em;text-transform:uppercase;
  border-bottom:2px solid var(--ob-accent);padding-bottom:2px}

/* ---- .dcard: frame and card fused into one clickable unit, only where a
   group's frame count matches its card count 1:1 (today, just "The funnel").
   Everywhere else the frames-row-then-cards-grid layout stays as it is;
   click behaviour is lightbox-uniform across both, see build/design.md ---- */
.dcards{display:grid;gap:18px;grid-template-columns:1fr}
@media(min-width:760px){.dcards--3{grid-template-columns:repeat(3,1fr)}
  .dcards--2{grid-template-columns:repeat(2,1fr)}}
.dcard{display:block;text-decoration:none;text-align:left;background:var(--ob-paper);
  border-radius:var(--r);overflow:hidden;
  box-shadow:0 1px 0 rgba(0,0,0,.08),0 14px 34px rgba(0,0,0,.10);
  transition:transform var(--dur-fast) var(--ease),box-shadow var(--dur-fast) var(--ease)}
.dcard:hover{transform:translateY(-3px);box-shadow:0 1px 0 rgba(0,0,0,.08),0 20px 44px rgba(0,0,0,.13)}
.dcard .frame__bar{margin:0}
.dcard .frame__shot{aspect-ratio:16/10}
.dcard__body{padding:18px 20px 22px}
.dcard__n{font-family:var(--font-label);font-size:.625rem;letter-spacing:.18em;
  text-transform:uppercase;opacity:.5;display:block;margin-bottom:.5rem}
.dcard__title{font-family:var(--font-display);font-size:1.1875rem;color:var(--ob-black);margin:0 0 .35rem}
.dcard__desc{font-size:.9375rem;margin:0;opacity:.78}

/* ---- case studies: real ones, or the authority line, never fabricated ---- */
.cases{display:grid;gap:20px;grid-template-columns:1fr;margin-top:clamp(24px,3vw,36px)}
@media(min-width:640px){.cases{grid-template-columns:repeat(2,1fr)}}
.case{text-align:left}
.case .vid,.case .swap{margin-bottom:0}
/* Two tiers. The lead carries the figure at display size, the sub carries the
   supporting record. One flat grey paragraph buried the best line on the page. */
.authority{max-width:56ch;margin-inline:auto;text-align:center}
.authority__lead{font-family:var(--font-display);
  font-size:clamp(1.375rem,1.05rem + 1.35vw,1.9375rem);line-height:1.22;
  letter-spacing:-.01em;color:var(--ob-black);margin:0 0 .85rem}
.authority__sub{font-size:1.0625rem;line-height:1.55;opacity:.72;margin:0;
  max-width:48ch;margin-inline:auto}

/* Scoped to #case-studies only (index.html's client-results grid, and
   booked.html's reused copy of the same component): the caption is a bold,
   centered heading ABOVE the video rather than base.css's default small,
   left-aligned line below it. main.js's caseHtml() already renders the
   figcaption before the media for this reason. Booked.html's separate
   "Three quick answers" FAQ figures share the .case/.vid__cap classes but
   sit outside #case-studies, so they keep the base.css default untouched. */
#case-studies .vid__cap{order:-1;margin-top:0;margin-bottom:.6rem;text-align:center;
  font-weight:700;font-size:1.0625rem;opacity:1;color:var(--ob-black)}
#case-studies .case{display:flex;flex-direction:column;text-align:center}

/* ---- preview lightbox: every deliverable opens in place, never a
   navigation away from the pitch site, see build/design.md ---- */
.lightbox{position:fixed;inset:0;z-index:80;display:flex;align-items:center;
  justify-content:center;padding:clamp(14px,4vw,48px);
  background:rgba(20,16,8,.72);backdrop-filter:blur(2px)}
.lightbox[hidden]{display:none}
.lightbox__panel{position:relative;width:100%;max-width:1100px;height:min(84vh,900px);
  background:var(--ob-paper);border-radius:var(--r-lg);overflow:hidden;
  box-shadow:0 30px 80px rgba(0,0,0,.4);display:flex;flex-direction:column}
.lightbox__bar{display:flex;align-items:center;gap:12px;padding:12px 16px;
  background:var(--ob-mist);border-bottom:1px solid var(--ob-line);flex:0 0 auto}
.lightbox__url{flex:1;font-family:var(--font-label);font-size:.6875rem;
  letter-spacing:.04em;opacity:.6;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.lightbox__hint{font-family:var(--font-label);font-size:.625rem;letter-spacing:.04em;
  opacity:.45;flex:0 0 auto;white-space:nowrap}
@media(max-width:640px){.lightbox__hint{display:none}}
.lightbox__open{font-family:var(--font-label);font-size:.6875rem;letter-spacing:.1em;
  text-transform:uppercase;text-decoration:none;color:var(--ob-black);opacity:.7;flex:0 0 auto}
.lightbox__open:hover{opacity:1}
.lightbox__close{flex:0 0 auto;width:26px;height:26px;border-radius:50%;border:0;
  background:rgba(0,0,0,.08);cursor:pointer;font-size:1rem;line-height:1;color:var(--ob-ink)}
.lightbox__close:hover{background:rgba(0,0,0,.16)}
.lightbox__frame{flex:1;border:0;width:100%;background:#fff}
.lightbox__nav{position:absolute;top:50%;translate:0 -50%;z-index:2;width:38px;height:38px;
  border-radius:50%;border:0;cursor:pointer;background:rgba(255,255,255,.92);
  box-shadow:0 4px 16px rgba(0,0,0,.24);display:flex;align-items:center;justify-content:center}
.lightbox__nav--prev{left:clamp(-8px,-2vw,10px)}
.lightbox__nav--next{right:clamp(-8px,-2vw,10px)}
.lightbox__nav svg{width:18px;height:18px;stroke:#262626;fill:none;stroke-width:2;
  stroke-linecap:round;stroke-linejoin:round}
@media(max-width:640px){.lightbox__nav{display:none}}

/* ---- calendar ---- */
.cal{border-radius:var(--r-lg);background:var(--ob-paper);min-height:718px;
  margin:clamp(24px,3vw,36px) auto 0;overflow:hidden;max-width:960px;
  box-shadow:0 1px 0 rgba(0,0,0,.06),0 18px 50px rgba(0,0,0,.10)}

/* ---- floating book-a-call pill ---- */
.sticky-cta{position:fixed;right:clamp(14px,2.4vw,26px);bottom:clamp(14px,2.4vw,26px);
  z-index:50;opacity:0;transform:translateY(14px);pointer-events:none;
  transition:opacity var(--dur) var(--ease),transform var(--dur) var(--ease)}
.sticky-cta.is-on{opacity:1;transform:none;pointer-events:auto}
.sticky-cta .btn{display:inline-flex;align-items:center;gap:.5rem;
  box-shadow:0 10px 30px rgba(40,30,10,.24)}
.sticky-cta .btn::before{content:"";width:7px;height:7px;border-radius:50%;
  background:var(--ob-black);opacity:.55;flex:0 0 auto}
@media(prefers-reduced-motion:reduce){.sticky-cta{transition:none}}
