/* ============================================================
   SERVICE DETAIL
   One stylesheet, six pages. Nothing here is per-service: the
   template is driven entirely by services-detail.json, so a new
   service is a new record, not a new file.

   The motion vocabulary is deliberately its own. The rest of the
   site rises, parallaxes and counts; this page *uncovers* — every
   entrance is a mask being drawn back off something that was
   already there, which is the one gesture the other pages do not
   use. Scroll depth is not needed for it: the hero plays on
   arrival, the rest plays as it is reached, through the same
   .reveal observer the whole site already runs.

   Fail-open, like everything else: every hidden state below is
   gated behind html.js-anim, so until the motion script has
   actually arrived the page renders as plain, complete HTML.
   ============================================================ */

:root{
  --svc-e:  cubic-bezier(.22, 1, .36, 1);      /* fast out, long settle */
  --svc-e2: cubic-bezier(.65, 0, .35, 1);
}

/* Each section below is a .reveal purely so the shared observer marks
   it .in as it is reached. The base .reveal fade would double up with
   the per-element motion inside, so it is cancelled here — the section
   itself never moves, only its contents. */
.svc-sec.reveal{ opacity:1; transform:none; transition:none; }

/* ---------------- breadcrumb ---------------- */
.svc-crumb{
  /* the nav is fixed and 97px tall on this breakpoint; clear it */
  max-width:var(--container); margin:0 auto; padding:124px var(--pad) 0;
  font-family:var(--f-mono); font-size:.7rem; letter-spacing:.18em;
  text-transform:uppercase; color:var(--ink-faint);
  display:flex; align-items:center; gap:10px; flex-wrap:wrap;
}
.svc-crumb a{ color:var(--ink-faint); text-decoration:none; transition:color .4s var(--svc-e); }
.svc-crumb a:hover{ color:var(--primer-bright); }
.svc-crumb .sep{ opacity:.4; }
.svc-crumb .here{ color:var(--ink-mute); }

/* ---------------- hero ---------------- */
.svc-hero{
  position:relative;
  margin-top:22px;
  height:clamp(360px, 58vh, 620px);
  overflow:hidden;
  border-top:1px solid var(--line);
  border-bottom:1px solid var(--line);
}
.svc-hero-media{ position:absolute; inset:0; overflow:hidden; }
.svc-hero-media img{
  width:100%; height:100%; object-fit:cover;
  filter:grayscale(52%) brightness(.62);
  transform-origin:50% 55%;
}
.svc-hero::after{
  content:''; position:absolute; inset:0; z-index:1; pointer-events:none;
  background:linear-gradient(0deg, rgba(11,12,12,.94) 4%, rgba(11,12,12,.55) 46%, rgba(11,12,12,.30) 100%);
}
.svc-hero-inner{
  position:absolute; inset:auto 0 0 0; z-index:2;
  max-width:var(--container); margin:0 auto;
  padding:0 var(--pad) clamp(28px, 5vh, 54px);
}
.svc-hero .svc-num{
  font-family:var(--f-mono); font-size:.72rem; letter-spacing:.32em;
  color:var(--primer-bright); display:block; margin-bottom:14px;
}
.svc-hero h1{
  font-family:var(--f-display); font-weight:800;
  font-size:clamp(2.2rem, 6vw, 4.6rem); line-height:1.02;
  letter-spacing:-.03em; text-transform:uppercase; color:var(--ink);
  max-width:18ch;
}
.svc-hero .svc-tag{
  margin-top:18px; color:var(--ink-mute); font-size:clamp(.95rem, 1.4vw, 1.08rem);
  line-height:1.6; max-width:52ch; text-wrap:pretty;
}
/* the drawn rule under the number */
.svc-hero .svc-rule{
  display:block; height:1px; width:min(240px, 42vw);
  background:var(--primer-bright); opacity:.55;
  margin:0 0 22px; transform-origin:0 50%;
}

/* ---------------- intro ---------------- */
.svc-intro{ padding:clamp(60px, 9vh, 110px) 0 0; }
.svc-intro .container{ max-width:var(--container); margin:0 auto; padding:0 var(--pad); }
.svc-intro-grid{
  display:grid; grid-template-columns:minmax(0,.34fr) minmax(0,.66fr); gap:clamp(28px, 5vw, 80px);
  align-items:start;
}
.svc-intro .eyebrow-rail{
  font-family:var(--f-mono); font-size:.7rem; letter-spacing:.24em;
  text-transform:uppercase; color:var(--ink-faint);
  border-top:1px solid var(--line); padding-top:18px;
}
.svc-intro-body p{
  color:var(--ink-mute); font-size:clamp(1rem, 1.5vw, 1.18rem); line-height:1.72;
  max-width:62ch; text-wrap:pretty;
}
.svc-intro-body p + p{ margin-top:20px; }
.svc-intro-body p:first-child{ color:var(--ink); }

/* ---------------- gallery ---------------- */
.svc-gallery{ padding:clamp(56px, 8vh, 96px) 0 0; }
.svc-gallery .container{ max-width:var(--container); margin:0 auto; padding:0 var(--pad); }
.svc-gallery-head{
  font-family:var(--f-mono); font-size:.7rem; letter-spacing:.24em;
  text-transform:uppercase; color:var(--ink-faint);
  border-top:1px solid var(--line); padding-top:18px; margin-bottom:26px;
  display:flex; justify-content:space-between; gap:20px; flex-wrap:wrap;
}
.svc-gallery-head .note{ letter-spacing:.1em; text-transform:none; opacity:.75; }
.svc-grid{
  display:grid; grid-template-columns:repeat(12, 1fr);
  gap:clamp(10px, 1.4vw, 18px);
  /* The row sets the height, not the frames. Leaving it to the content
     lets a tall photograph in a narrow slot stretch its whole row and
     the two frames stop sharing a baseline. */
  grid-auto-rows:clamp(240px, 30vw, 440px);
}
/* asymmetric on purpose: 7/5 then 5/7, so the eye travels */
.svc-shot:nth-child(1){ grid-column:span 7; }
.svc-shot:nth-child(2){ grid-column:span 5; }
.svc-shot:nth-child(3){ grid-column:span 5; }
.svc-shot:nth-child(4){ grid-column:span 7; }
.svc-shot{
  position:relative; overflow:hidden; background:var(--bg-panel);
  border:1px solid var(--line-soft);
}

.svc-shot img{
  width:100%; height:100%; object-fit:cover;
  filter:grayscale(38%) brightness(.86);
  transition:transform 1s var(--svc-e), filter .7s var(--svc-e);
}
.svc-shot:hover img{ transform:scale(1.045); filter:grayscale(0%) brightness(1); }
.svc-shot figcaption{
  position:absolute; left:0; right:0; bottom:0; z-index:2;
  padding:14px 16px;
  font-family:var(--f-mono); font-size:.68rem; letter-spacing:.08em;
  color:var(--ink-mute);
  background:linear-gradient(0deg, rgba(11,12,12,.9), rgba(11,12,12,0));
}

/* ---------------- what we deliver ---------------- */
.svc-deliver{ padding:clamp(60px, 9vh, 110px) 0 0; }
.svc-deliver .container{ max-width:var(--container); margin:0 auto; padding:0 var(--pad); }
.svc-deliver h2{
  font-family:var(--f-display); font-weight:700;
  font-size:clamp(1.7rem, 3.2vw, 2.7rem); text-transform:uppercase;
  letter-spacing:-.02em; margin-bottom:34px;
}
.svc-deliver-grid{
  display:grid; grid-template-columns:repeat(4, minmax(0,1fr));
  gap:clamp(18px, 2.4vw, 38px);
}
.svc-item{ position:relative; padding-top:22px; }
.svc-item::before{
  content:''; position:absolute; top:0; left:0; right:0; height:1px;
  background:var(--line); transform-origin:0 50%;
}
.svc-item .n{
  font-family:var(--f-mono); font-size:.72rem; letter-spacing:.2em;
  color:var(--primer-bright); display:block; margin-bottom:12px;
}
.svc-item h3{
  font-family:var(--f-display); font-weight:700; font-size:1.02rem;
  text-transform:uppercase; letter-spacing:-.005em; margin-bottom:9px;
}
.svc-item p{ color:var(--ink-mute); font-size:.9rem; line-height:1.6; text-wrap:pretty; }

/* ---------------- capabilities ---------------- */
.svc-caps{ padding:clamp(56px, 8vh, 96px) 0 0; }
.svc-caps .container{ max-width:var(--container); margin:0 auto; padding:0 var(--pad); }
.svc-caps .sb-label{
  font-family:var(--f-mono); font-size:.72rem; letter-spacing:.15em;
  text-transform:uppercase; color:var(--ink-faint);
  border-top:1px solid var(--line); padding-top:18px; margin-bottom:22px;
}
.svc-cap-list{ display:flex; flex-wrap:wrap; gap:12px; }
.svc-cap{
  border:1px solid var(--line); padding:11px 18px; border-radius:22px;
  font-family:var(--f-mono); font-size:.82rem; color:var(--ink-mute);
  transition:border-color .5s var(--svc-e), color .5s var(--svc-e);
}
.svc-cap b{ color:var(--ink); font-weight:500; }
.svc-cap:hover{ border-color:var(--primer); color:var(--ink); }

/* ---------------- cta + sibling nav ---------------- */
.svc-cta{
  margin-top:clamp(70px, 11vh, 130px);
  border-top:1px solid var(--line);
  background:var(--bg-panel);
}
.svc-cta .container{ max-width:var(--container); margin:0 auto; padding:clamp(48px, 7vh, 84px) var(--pad); }
.svc-cta h2{
  font-family:var(--f-display); font-weight:800;
  font-size:clamp(1.8rem, 4vw, 3rem); text-transform:uppercase;
  letter-spacing:-.025em; max-width:20ch;
}
.svc-cta p{ margin-top:16px; color:var(--ink-mute); max-width:56ch; line-height:1.65; }
.svc-cta .btn{ margin-top:28px; }

.svc-siblings{
  display:flex; justify-content:space-between; gap:20px; flex-wrap:wrap;
  border-top:1px solid var(--line); margin-top:clamp(40px, 6vh, 64px); padding-top:22px;
}
.svc-siblings a{
  color:var(--ink-mute); text-decoration:none;
  font-family:var(--f-mono); font-size:.72rem; letter-spacing:.16em; text-transform:uppercase;
  display:flex; align-items:center; gap:10px;
  transition:color .4s var(--svc-e);
}
.svc-siblings a:hover{ color:var(--ink); }
.svc-siblings a b{ font-weight:500; letter-spacing:.06em; }
.svc-siblings .all{ color:var(--ink-faint); }

/* ---------------- services listing: the rows are links now ---------------- */
a.service-row{ text-decoration:none; color:inherit; cursor:pointer; display:grid; }
a.service-row:focus-visible{ outline:1px solid var(--primer-bright); outline-offset:-2px; }

/* ============================================================
   MOTION
   Everything below is gated behind html.js-anim. The gesture is
   one idea repeated at four scales: a mask withdrawing.
   ============================================================ */

/* hero: the image is uncovered from the bottom up while it settles
   back from a slow push-in. The two run at different lengths on
   purpose, so the picture is still moving after the wipe finishes. */
html.js-anim .svc-hero.armed .svc-hero-media{ clip-path:inset(100% 0 0 0); }
html.js-anim .svc-hero.armed .svc-hero-media img{ transform:scale(1.16); }
html.js-anim .svc-hero.armed .svc-rule{ transform:scaleX(0); }
html.js-anim .svc-hero.armed .svc-num,
html.js-anim .svc-hero.armed h1,
html.js-anim .svc-hero.armed .svc-tag{ opacity:0; transform:translateY(26px); }

html.js-anim .svc-hero.armed.in .svc-hero-media{
  clip-path:inset(0 0 0 0);
  transition:clip-path 1150ms var(--svc-e);
}
html.js-anim .svc-hero.armed.in .svc-hero-media img{
  transform:scale(1);
  transition:transform 2400ms var(--svc-e);
}
html.js-anim .svc-hero.armed.in .svc-rule{
  transform:scaleX(1);
  transition:transform 900ms var(--svc-e) 620ms;
}
html.js-anim .svc-hero.armed.in .svc-num,
html.js-anim .svc-hero.armed.in h1,
html.js-anim .svc-hero.armed.in .svc-tag{
  opacity:1; transform:none;
  transition:opacity 760ms linear, transform 1000ms var(--svc-e);
}
html.js-anim .svc-hero.armed.in .svc-num{ transition-delay:420ms; }
html.js-anim .svc-hero.armed.in h1{ transition-delay:520ms; }
html.js-anim .svc-hero.armed.in .svc-tag{ transition-delay:660ms; }

/* intro: the rail draws, the paragraphs uncover downward */
html.js-anim .svc-intro .eyebrow-rail{ opacity:0; transform:translateY(14px); }
html.js-anim .svc-intro-body p{ opacity:0; transform:translateY(22px); }
html.js-anim .svc-intro.in .eyebrow-rail{
  opacity:1; transform:none;
  transition:opacity 600ms linear, transform 800ms var(--svc-e);
}
html.js-anim .svc-intro.in .svc-intro-body p{
  opacity:1; transform:none;
  transition:opacity 700ms linear calc(140ms + var(--i, 0) * 130ms),
             transform 950ms var(--svc-e) calc(140ms + var(--i, 0) * 130ms);
}

/* gallery: each frame is wiped open from the leading edge while the
   photograph inside slides the opposite way, so the image appears to
   have been there before the frame arrived */
html.js-anim .svc-gallery-head{ opacity:0; transform:translateY(12px); }
html.js-anim .svc-gallery.in .svc-gallery-head{
  opacity:1; transform:none;
  transition:opacity 600ms linear, transform 800ms var(--svc-e);
}
html.js-anim .svc-shot{ clip-path:inset(0 100% 0 0); }
html.js-anim .svc-shot img{ transform:translateX(9%) scale(1.06); }
html.js-anim .svc-shot figcaption{ opacity:0; }
html.js-anim .svc-shot:nth-child(even){ clip-path:inset(0 0 0 100%); }
html.js-anim .svc-shot:nth-child(even) img{ transform:translateX(-9%) scale(1.06); }

html.js-anim .svc-gallery.in .svc-shot{
  clip-path:inset(0 0 0 0);
  transition:clip-path 1000ms var(--svc-e) calc(var(--i, 0) * 140ms);
}
html.js-anim .svc-gallery.in .svc-shot img{
  transform:none;
  transition:transform 1300ms var(--svc-e) calc(var(--i, 0) * 140ms),
             filter .7s var(--svc-e);
}
html.js-anim .svc-gallery.in .svc-shot figcaption{
  opacity:1;
  transition:opacity 600ms linear calc(500ms + var(--i, 0) * 140ms);
}

/* deliver: the rule above each block draws across, then the text
   comes up under it — the block builds itself top-down */
html.js-anim .svc-deliver h2{ opacity:0; transform:translateY(20px); }
html.js-anim .svc-item::before{ transform:scaleX(0); }
html.js-anim .svc-item .n,
html.js-anim .svc-item h3,
html.js-anim .svc-item p{ opacity:0; transform:translateY(16px); }

html.js-anim .svc-deliver.in h2{
  opacity:1; transform:none;
  transition:opacity 650ms linear, transform 850ms var(--svc-e);
}
html.js-anim .svc-deliver.in .svc-item::before{
  transform:scaleX(1);
  transition:transform 720ms var(--svc-e) calc(120ms + var(--i, 0) * 110ms);
}
html.js-anim .svc-deliver.in .svc-item .n,
html.js-anim .svc-deliver.in .svc-item h3,
html.js-anim .svc-deliver.in .svc-item p{
  opacity:1; transform:none;
  transition:opacity 600ms linear var(--d, 0ms), transform 800ms var(--svc-e) var(--d, 0ms);
}
html.js-anim .svc-deliver.in .svc-item .n{ --d:calc(280ms + var(--i, 0) * 110ms); }
html.js-anim .svc-deliver.in .svc-item h3{ --d:calc(340ms + var(--i, 0) * 110ms); }
html.js-anim .svc-deliver.in .svc-item p{ --d:calc(400ms + var(--i, 0) * 110ms); }

/* capabilities: tight, quick, mechanical — a list being stamped */
html.js-anim .svc-caps .sb-label{ opacity:0; transform:translateY(10px); }
html.js-anim .svc-cap{ opacity:0; transform:translateY(12px) scale(.97); }
html.js-anim .svc-caps.in .sb-label{
  opacity:1; transform:none;
  transition:opacity 550ms linear, transform 700ms var(--svc-e);
}
html.js-anim .svc-caps.in .svc-cap{
  opacity:1; transform:none;
  transition:opacity 420ms linear calc(180ms + var(--i, 0) * 55ms),
             transform 560ms var(--svc-e2) calc(180ms + var(--i, 0) * 55ms),
             border-color .5s var(--svc-e), color .5s var(--svc-e);
}

/* cta */
html.js-anim .svc-cta .container > *{ opacity:0; transform:translateY(20px); }
html.js-anim .svc-cta.in .container > *{
  opacity:1; transform:none;
  transition:opacity 650ms linear calc(var(--i, 0) * 90ms),
             transform 900ms var(--svc-e) calc(var(--i, 0) * 90ms);
}

/* ---------------- narrow ---------------- */
@media (max-width:900px){
  .svc-crumb{ padding-top:calc(var(--nav-h, 68px) + 24px); }
  .svc-hero{ height:clamp(320px, 52vh, 480px); margin-top:14px; }
  .svc-grid{ grid-auto-rows:clamp(200px, 62vw, 340px); }
  .svc-intro-grid{ grid-template-columns:1fr; gap:22px; }
  .svc-deliver-grid{ grid-template-columns:1fr 1fr; }
  .svc-shot:nth-child(1),
  .svc-shot:nth-child(2),
  .svc-shot:nth-child(3),
  .svc-shot:nth-child(4){ grid-column:span 12; }

  .svc-siblings{ flex-direction:column; gap:14px; }
}
@media (max-width:560px){
  .svc-deliver-grid{ grid-template-columns:1fr; }
}

/* ---------------- reduced motion ---------------- */
@media (prefers-reduced-motion: reduce){
  html.js-anim .svc-hero.armed .svc-hero-media,
  html.js-anim .svc-shot{ clip-path:none !important; }
  html.js-anim .svc-hero.armed .svc-hero-media img,
  html.js-anim .svc-shot img,
  html.js-anim .svc-hero.armed .svc-rule,
  html.js-anim .svc-item::before{ transform:none !important; }
  html.js-anim .svc-hero.armed .svc-num,
  html.js-anim .svc-hero.armed h1,
  html.js-anim .svc-hero.armed .svc-tag,
  html.js-anim .svc-intro .eyebrow-rail,
  html.js-anim .svc-intro-body p,
  html.js-anim .svc-gallery-head,
  html.js-anim .svc-shot figcaption,
  html.js-anim .svc-deliver h2,
  html.js-anim .svc-item .n,
  html.js-anim .svc-item h3,
  html.js-anim .svc-item p,
  html.js-anim .svc-caps .sb-label,
  html.js-anim .svc-cap,
  html.js-anim .svc-cta .container > *{
    opacity:1 !important; transform:none !important; transition:none !important;
  }
}
