/* ============================================================================
   BASE — identical on every Pittsburgh IT build. The visitor never sees any of it.
   Token NAMES are fixed; only the VALUES change per client. Everything below the
   token block is structural: the accessibility floor, the form skeleton, tap
   targets, the motion contract. Roughly 20 lines get rewritten per client and
   several hundred lines of quality are inherited.
   MOBILE FIRST — every rule here is the small-screen rule. Breakpoints add.
   ========================================================================== */
:root{
  --surface:#EFEEE9;
  --surface-2:#E4E1D8;
  --band:#1A1814;
  --band-ink:#F1F0EB;
  --band-ink-2:#ABA69B;
  --accent-on-band:#CFC9BC;
  --ink:#171612;
  --ink-2:#4E4B44;
  --ink-3:#5C5951;
  --accent:#232019;
  --accent-2:#3B372E;
  --accent-ink:#FFFFFF;
  --line:#D6D3CA;
  --maxw:1280px;
  --gutter:22px;
  --radius:0px;
  --font-display:'Cormorant Garamond',Georgia,'Times New Roman',serif;
  --font-body:Jost,system-ui,-apple-system,'Segoe UI',sans-serif;
}

*,*::before,*::after{box-sizing:border-box}
html{-webkit-text-size-adjust:100%;scroll-behavior:smooth}
@media(prefers-reduced-motion:reduce){html{scroll-behavior:auto}}
body{margin:0;background:var(--surface);color:var(--ink);
  font-family:var(--font-body);font-size:17px;line-height:1.62;
  -webkit-font-smoothing:antialiased;text-rendering:optimizeLegibility;
  overflow-x:hidden}
img,svg,video{max-width:100%;height:auto;display:block}
h1,h2,h3,h4{font-family:var(--font-display);margin:0;line-height:1.08;
  font-weight:500;letter-spacing:-.006em}
p{margin:0 0 1em}
a{color:inherit}
ul{margin:0;padding:0;list-style:none}

/* --- container ------------------------------------------------------------ */
.container{width:100%;max-width:var(--maxw);margin:0 auto;padding:0 var(--gutter)}
@media(min-width:760px){:root{--gutter:34px}}
@media(min-width:1180px){:root{--gutter:48px}}

/* --- accessibility floor -------------------------------------------------- */
.skip{position:absolute;left:-9999px;top:0;z-index:200;background:var(--accent);
  color:var(--accent-ink);padding:12px 18px;border-radius:0 0 var(--radius) 0;
  font-weight:700;text-decoration:none}
.skip:focus{left:0}
:focus-visible{outline:3px solid var(--accent);outline-offset:3px;border-radius:2px}
.vh{position:absolute;width:1px;height:1px;overflow:hidden;clip:rect(0 0 0 0);
  clip-path:inset(50%);white-space:nowrap}
/* honeypot: OFF-SCREEN, never display:none — a hidden field some bots skip,
   and a screen reader is told to leave it alone. */
.hp{position:absolute!important;left:-9999px;top:-9999px;width:1px;height:1px;
  opacity:0;pointer-events:none}

/* --- tap targets ---------------------------------------------------------- */
a,button,input,select,textarea,summary{font-family:inherit}
.btn,button,input[type=submit]{min-height:48px}
nav a,footer a{display:inline-block;min-height:24px}

/* --- button skeleton (templates restyle the skin, not the mechanics) ------- */
.btn{display:inline-flex;align-items:center;justify-content:center;gap:.55em;
  padding:14px 26px;border:1px solid transparent;border-radius:var(--radius);
  font-weight:650;font-size:16px;line-height:1.1;text-decoration:none;cursor:pointer;
  transition:transform .18s ease,background .18s ease,color .18s ease,border-color .18s ease,box-shadow .18s ease}
.btn:active{transform:translateY(1px)}
.btn-primary{background:var(--accent);color:var(--accent-ink);border-color:var(--accent)}
.btn-ghost{background:transparent;color:var(--ink);border-color:var(--line)}

/* --- form skeleton -------------------------------------------------------- */
.form{display:grid;gap:16px}
.field{display:grid;gap:7px}
.field label{font-size:12.5px;font-weight:700;letter-spacing:.09em;
  text-transform:uppercase;color:var(--ink-2)}
.field input,.field select,.field textarea{
  width:100%;min-height:50px;padding:13px 15px;border:1px solid var(--line);
  border-radius:var(--radius);background:var(--surface);color:var(--ink);
  font-size:16px;/* 16px stops iOS zooming the page on focus */
  font-family:inherit;transition:border-color .18s ease,box-shadow .18s ease}
.field textarea{min-height:140px;resize:vertical;line-height:1.55}
.field input:focus,.field select:focus,.field textarea:focus{
  outline:none;border-color:var(--accent);box-shadow:0 0 0 3px rgba(35,32,25,.22)}
.field ::placeholder{color:var(--ink-3);opacity:1}
.frow{display:grid;gap:16px}
@media(min-width:680px){.frow{grid-template-columns:1fr 1fr}}
.thanks{display:none;border:1px solid var(--line);border-radius:var(--radius);
  padding:28px;background:var(--surface-2)}
.thanks.show{display:block}
.thanks h3{font-size:24px;margin-bottom:10px}
.formerror{color:#232019;font-size:15px;font-weight:600;margin-top:10px}

/* --- MOTION CONTRACT ------------------------------------------------------
   Nothing starts hidden unless JavaScript has already run. The `js` class is set
   by an inline <head> script, and ONLY when prefers-reduced-motion is not set.
   No JS, blocked JS, old browser, or reduced motion => the page is simply visible.
   This is the inverse of how most sites do it, and it is why a script failure
   here cannot produce a blank page on a lead-generating site. */
html.js .reveal{opacity:0;transform:translateY(18px);
  transition:opacity .7s cubic-bezier(.22,.61,.36,1),transform .7s cubic-bezier(.22,.61,.36,1)}
html.js .reveal.in{opacity:1;transform:none}
html.js .reveal.d1{transition-delay:.08s}
html.js .reveal.d2{transition-delay:.16s}
html.js .reveal.d3{transition-delay:.24s}
@media(prefers-reduced-motion:reduce){
  html.js .reveal,html.js .reveal.in{opacity:1!important;transform:none!important;transition:none!important}
  *{animation-duration:.001ms!important;animation-iteration-count:1!important;
    transition-duration:.001ms!important}
}

/* --- nav skeleton --------------------------------------------------------- */
#nav{position:fixed;top:0;left:0;right:0;z-index:100;
  transition:background .25s ease,box-shadow .25s ease,border-color .25s ease}
.nav-inner{display:flex;align-items:center;justify-content:space-between;
  gap:16px;min-height:72px}
.navtoggle{display:inline-flex;align-items:center;justify-content:center;
  width:48px;height:48px;margin-right:-10px;background:none;border:0;
  color:inherit;cursor:pointer}
@media(min-width:940px){.navtoggle{display:none}}
.nav-links{display:none}
.nav-links.open{display:flex}
.nav-links{gap:0}
/* Desktop nav reset. Deliberately scoped to #nav so its specificity (1,1,0) beats any
   later `.nav-links{position:absolute…}` a template writes for its mobile drawer —
   equal specificity later in the file wins over a media query, which silently left the
   drawer stacked at the left edge on six of seven templates before this was scoped.
   It sets ONLY the structural properties that must not leak from mobile to desktop;
   gap, colour and type stay the template's business. */
@media(min-width:940px){
  #nav .nav-links,#nav .nav-links.open{display:flex;position:static;inset:auto;
    flex-direction:row;align-items:center;padding:0;margin:0;border:0;background:none;
    width:auto;height:auto;min-height:0;max-height:none;box-shadow:none;transform:none;
    visibility:visible;opacity:1;overflow:visible;
    gap:var(--nav-gap,32px)}
}
html.menu-open,html.menu-open body{overflow:hidden}

/* --- footer skeleton ------------------------------------------------------ */
footer a{text-decoration:none}
.credit{font-size:13.5px}
.credit a{text-decoration:underline;text-underline-offset:3px}

/* --- button rows ----------------------------------------------------------
   On a phone two CTAs sitting side by side at different intrinsic widths look
   accidental, and neither is a comfortable thumb target. They go full width until
   there is room for a row. Scoped as `.btnrow > .btn` (0,2,0) so a template's own
   `.btn{}` rule later in the file cannot silently undo it — the same cascade trap
   that left the desktop nav stacked. */
.btnrow{display:flex;flex-wrap:wrap;gap:12px}
.btnrow > .btn{flex:1 1 100%}
@media(min-width:560px){.btnrow > .btn{flex:0 0 auto}}

/* --- long-string guard ----------------------------------------------------
   A client email address or a compound word set in a heavy display face at
   20px uppercase does not wrap, and pushes a 390px page sideways. Found on the
   Ironworks contact page: dispatch@vantagemechanical.com forced the document to
   462px. Plumbing, so every template inherits the fix. */
/* Headings are deliberately NOT in this guard. break-word on a display heading
   shatters a word mid-syllable the moment its container is narrower than the word —
   it turned "Everything we make," into "Everyth / ing we / make," on Marquee. A
   heading that does not fit is a LAYOUT bug; fix the column, do not hyphenate it. */
h1,h2,h3,h4{overflow-wrap:normal;word-break:normal}
a[href^="mailto:"],a[href^="tel:"]{overflow-wrap:anywhere}
.crow span,.crow b,.cinfo span,address{overflow-wrap:anywhere}

/* --- utility -------------------------------------------------------------- */
.sec{padding:64px 0}
@media(min-width:760px){.sec{padding:96px 0}}
@media(min-width:1180px){.sec{padding:124px 0}}
.eyebrow{font-size:12px;font-weight:750;letter-spacing:.16em;text-transform:uppercase;
  color:var(--accent);margin:0 0 14px}
.lead{font-size:19px;line-height:1.6;color:var(--ink-2)}
@media(min-width:760px){.lead{font-size:21px}}


/* ============================================================
   TEMPLATE 09 — PLOT
   Concept: a catalogue, not a gallery. The photographs are left
   alone and every fact about a house is hung on a hairline rail
   beside them, in the same four cells, in the same order, every
   single time.

   SIGNATURE ELEMENT — THE RAIL.
   A hairline carrying a house's facts NEXT to its picture rather
   than on top of it. Four cells, always this order:
     1 the stage of the sale — and the stage is written INTO the
       word: ACTIVE stands on a live 2px rule, COMING on a dotted
       one (the rule is not there yet), SOLD is struck through.
     2 the street, and the neighbourhood under it
     3 what the house is — beds, baths, floor area, year
     4 what it costs, led by THE SCALE: four segments, filled from
       the left to the price band. The scale means the same thing
       everywhere it appears — on a plate, on a row of the
       neighbourhood index, and against a fee.
   Delete any part of it and a fact goes with it. Nothing is ever
   printed over a photograph, which is the whole discipline: a
   buyer is looking at houses, not at a website.

   NEAR-MONOCHROME, DELIBERATELY. There is no chromatic accent in
   this template. --accent is a deep warm neutral, so the CTA is a
   near-black CELL rather than a coloured button; every rule, tag
   and mark is ink or line; --radius is 0 and there is no shadow
   anywhere. All the colour on a page comes from the photographs.

   MOBILE FIRST — every base rule is the small-screen rule and
   every breakpoint below is min-width.
   ============================================================ */

:root{
  /* the rail's own measurements, so a new rail cannot drift out of
     the language: one gutter, one hairline, one label size. */
  --rail-gap:11px;
  --seg:7px;            /* one segment of the price scale        */
  --seg-gap:2px;
}

/* --- preview bar (demo builds only) ------------------------- */
.tplbar{background:var(--band);color:var(--band-ink-2);font-size:12.5px;
  letter-spacing:.02em;padding:9px 20px;text-align:center;position:relative;z-index:120}
.tplbar b{color:var(--band-ink);font-weight:500}

/* --- base.css resets ul but not ol; the twelve weeks and the
       "after you send it" ladder are both ordered lists -------- */
ol{margin:0;padding:0;list-style:none}

/* ============================================================
   THE SCALE — four segments, filled to the band.
   Drawn from ONE rule so a scale at a new size cannot drift: the
   track is four hairline segments, the fill is the same four
   segments in ink, clipped to the band's width. It is the only
   quantitative mark in the template and it always means price.
   ============================================================ */
.scale{display:inline-block;flex:0 0 auto;position:relative;height:7px;
  width:calc(var(--seg) * 4 + var(--seg-gap) * 3);vertical-align:1px;
  background:repeating-linear-gradient(90deg,
    var(--line) 0 var(--seg),transparent var(--seg) calc(var(--seg) + var(--seg-gap)))}
.scale::before{content:"";position:absolute;left:0;top:0;bottom:0;width:var(--fill,0);
  background:repeating-linear-gradient(90deg,
    var(--ink) 0 var(--seg),transparent var(--seg) calc(var(--seg) + var(--seg-gap)))}
.s1{--fill:7px}
.s2{--fill:16px}
.s3{--fill:25px}
.s4{--fill:34px}
.onband .scale{background:repeating-linear-gradient(90deg,
  rgba(241,240,235,.16) 0 var(--seg),transparent var(--seg) calc(var(--seg) + var(--seg-gap)))}
.onband .scale::before{background:repeating-linear-gradient(90deg,
  var(--accent-on-band) 0 var(--seg),transparent var(--seg) calc(var(--seg) + var(--seg-gap)))}

/* ============================================================
   THE RAIL — the caption that never touches the picture.
   ============================================================ */
.rail{display:grid;gap:var(--rail-gap);margin-top:14px;padding-top:13px;
  border-top:1px solid var(--ink);grid-template-columns:1fr auto;align-items:start}
.rst{grid-column:1;justify-self:start;position:relative;display:inline-block;
  font-size:10px;letter-spacing:.22em;text-transform:uppercase;font-weight:600;
  color:var(--ink);padding-bottom:5px}
/* THE STAGE IS THE TREATMENT, not a coloured dot. Three states,
   three things a rule can do to a word, all of them monochrome
   and all of them legible before you have read the word. */
.rst--active::after{content:"";position:absolute;left:0;right:0;bottom:0;
  height:2px;background:var(--ink)}
.rst--coming{color:var(--ink-3)}
.rst--coming::after{content:"";position:absolute;left:0;right:0;bottom:0;
  height:0;border-bottom:1px dotted var(--ink-3)}
.rst--sold{color:var(--ink-3)}
.rst--sold::after{content:"";position:absolute;left:-2px;right:-2px;top:43%;
  height:1px;background:var(--ink-3)}
.rwhere{grid-column:1;grid-row:2}
.rwhere b{display:block;font-family:var(--font-display);font-weight:600;
  font-size:clamp(21px,4.6vw,26px);line-height:1.14;letter-spacing:-.01em;color:var(--ink)}
.rwhere span{display:block;margin-top:3px;font-size:11px;letter-spacing:.17em;
  text-transform:uppercase;color:var(--ink-3)}
.rspec{grid-column:1;grid-row:3;font-size:13px;letter-spacing:.03em;color:var(--ink-2);
  font-variant-numeric:tabular-nums}
.rprice{grid-column:2;grid-row:1/3;justify-self:end;text-align:right;
  display:flex;flex-direction:column;align-items:flex-end;gap:7px}
.rprice b{font-family:var(--font-display);font-weight:600;font-size:clamp(20px,4.4vw,25px);
  line-height:1;color:var(--ink);font-variant-numeric:tabular-nums}
.plate{margin:0}
.pf{overflow:hidden;background:linear-gradient(152deg,#2A2721,var(--band))}
.pf img{width:100%;display:block;object-fit:cover;
  /* ONE grade for every photograph on the site. Barely a grade at
     all — the pictures are the only colour on the page and this
     template's whole argument is that they are the product. */
  filter:saturate(.92) contrast(1.05) brightness(1.01) sepia(.03)}
/* Every frame's aspect equals its asset's declared w/h, so nothing
   is cropped anywhere in this template. A new asset at a different
   aspect reintroduces cropping silently — check template.json. */
.pf--wide img{aspect-ratio:8/5}
.pf--tall img{aspect-ratio:4/5}
.pf--sq img{aspect-ratio:1/1}
.pf--land img{aspect-ratio:14/9}

/* ============================================================
   TYPE
   Cormorant Garamond does the headlines and the numbers; Jost
   does every label, every rail cell and the body. Cormorant is
   set at 500 and never 400 — it goes weak below about 26px.
   ============================================================ */
.h-xl{font-size:clamp(34px,8.2vw,64px);line-height:1.03;letter-spacing:-.012em}
.h-lg{font-size:clamp(29px,5.6vw,48px);line-height:1.06;letter-spacing:-.008em}
.h-md{font-size:clamp(23px,3.8vw,32px);line-height:1.14}
.measure{max-width:56ch}
.pre{white-space:pre-line}
.lead{font-size:17px;line-height:1.62;color:var(--ink-2)}
.fineprint{font-size:12.5px;color:var(--ink-3);margin:12px 0 0;max-width:52ch}
.eyebrow{font-size:10.5px;letter-spacing:.22em;font-weight:600;color:var(--ink-3);margin-bottom:16px}
.kicker{margin:0 0 14px;font-size:10.5px;font-weight:600;letter-spacing:.24em;
  text-transform:uppercase;color:var(--ink-3)}
.sec-tight{padding-top:0}
.stone{background:var(--surface-2)}
.onband{background:var(--band);color:var(--band-ink)}
.onband h2,.onband h3,.onband b{color:var(--band-ink)}
.onband .lead,.onband p{color:var(--band-ink-2)}
.onband .eyebrow,.onband .kicker{color:var(--accent-on-band)}
.plainlink{color:var(--ink);text-decoration:underline;text-underline-offset:5px;
  text-decoration-thickness:1px;font-size:13px;letter-spacing:.14em;
  text-transform:uppercase;font-weight:600}
.plainlink:hover{color:var(--ink-3)}

/* --- buttons: a cell, never a pill --------------------------- */
.btn{border-radius:0;padding:16px 26px;font-family:var(--font-body);font-weight:500;
  font-size:12.5px;letter-spacing:.18em;text-transform:uppercase}
.btn-primary:hover{background:var(--accent-2);border-color:var(--accent-2)}
.btn-line{background:transparent;color:var(--ink);border-color:var(--ink)}
.btn-line:hover{background:var(--ink);color:var(--surface)}
.onband .btn-primary{background:var(--band-ink);color:var(--band);border-color:var(--band-ink)}
.onband .btn-primary:hover{background:var(--accent-on-band);border-color:var(--accent-on-band)}
.onband .btn-line{color:var(--band-ink);border-color:var(--band-ink-2)}
.onband .btn-line:hover{background:var(--band-ink);color:var(--band);border-color:var(--band-ink)}

/* ============================================================
   NAV — THE CELL RAIL.
   The menu bar is built out of the same vocabulary as the rail
   under a photograph: ruled cells with NO gap between them,
   divided by vertical hairlines, and the last cell is a solid ink
   CTA flush to the bar rather than a button floating inside it.
   Nothing here is a gap-separated list of links, which is what
   the other eight bars are.

   On a phone the bar keeps the name and the toggle, and the menu
   opens IN FLOW as a two-by-two grid of ruled cells — the same
   grid the plates use — with the CTA as a full-width cell across
   the foot of it. It is never absolutely positioned: an absolute
   drawer is what leaked onto the desktop of six of the first
   seven templates.
   ============================================================ */
#nav{position:sticky;top:0;background:rgba(239,238,233,.90);
  backdrop-filter:saturate(140%) blur(10px);border-bottom:1px solid var(--line)}
#nav.scrolled{border-bottom-color:var(--ink-3)}
.nav-inner{flex-wrap:wrap;gap:0;min-height:62px;align-items:stretch}
.mark{display:flex;flex-direction:column;justify-content:center;gap:2px;
  text-decoration:none;color:var(--ink);min-width:0;order:1;margin-right:auto;
  padding:9px 0}
.markname{font-family:var(--font-display);font-weight:600;font-size:clamp(23px,5.6vw,29px);
  line-height:1;letter-spacing:-.012em;white-space:nowrap}
.marksub{font-size:9.5px;letter-spacing:.2em;text-transform:uppercase;color:var(--ink-3);
  white-space:nowrap}
.mark:hover .markname{color:var(--ink-2)}
.navtoggle{order:2;align-self:center}
.bars{display:block;width:22px}
.bars i{display:block;height:1px;background:var(--ink);margin:6px 0}
/* the drawer: in flow, full width, a ruled two-column grid */
.nav-links{order:3;flex:1 1 100%;gap:0;border-top:1px solid var(--line);
  grid-template-columns:1fr 1fr}
#nav .nav-links.open{display:grid}
.cell{display:flex;align-items:center;justify-content:flex-start;
  padding:17px 0;font-size:12px;letter-spacing:.18em;text-transform:uppercase;
  font-weight:500;color:var(--ink);text-decoration:none;min-height:56px;
  border-bottom:1px solid var(--line)}
.cell:nth-child(odd){border-right:1px solid var(--line);padding-right:14px}
.cell:nth-child(even){padding-left:16px}
.cell[aria-current]{color:var(--ink-3)}
.cell[aria-current]::before{content:"";width:6px;height:6px;background:var(--ink);
  margin-right:9px;flex:0 0 auto}
/* the CTA cell has to out-rank the nth-child cell rules above it,
   or the ink cell keeps the drawer's right-hand hairline and its
   asymmetric padding. Scoped to #nav for the specificity, not for
   the scoping. */
#nav .cell--cta{grid-column:1/-1;background:var(--accent);color:var(--accent-ink);
  justify-content:center;border:0;padding:19px 0;font-weight:500}
#nav .cell--cta:hover{background:var(--accent-2)}
@media(min-width:940px){
  .nav-inner{flex-wrap:nowrap;min-height:72px}
  .mark{padding:0}
  #nav .nav-links,#nav .nav-links.open{display:flex;align-self:stretch;gap:0}
  .cell{border-bottom:0;border-left:1px solid var(--line);border-right:0;
    padding:0 21px;min-height:0;font-size:11px;letter-spacing:.17em;color:var(--ink-2)}
  .cell:nth-child(odd),.cell:nth-child(even){padding:0 21px;border-right:0}
  .cell:hover{color:var(--ink)}
  .cell[aria-current]{color:var(--ink)}
  #nav .cell--cta{border-left:0;padding:0 26px;color:var(--accent-ink)}
  #nav .cell--cta:hover{color:var(--accent-ink)}
}

/* ============================================================
   HOME — HERO 7: THE PLATES ARE THE HERO.
   A short type block so the headline lands high, then the
   catalogue immediately underneath INSIDE THE SAME SECTION. The
   pictures are the argument, so they are the first thing after
   the sentence that introduces them.
   ============================================================ */
.hero-cat{padding:26px 0 0}
.hero-cat h1{max-width:12ch;margin-bottom:0}
.hero-cat .lead{max-width:50ch;margin-top:20px}
.hero-cat .btnrow{margin-top:24px}
@media(min-width:900px){
  .hero-cat{padding:44px 0 0}
  .hero-cat .herotop{display:grid;grid-template-columns:1.05fr .95fr;gap:56px;align-items:end}
  .hero-cat .lead{margin-top:0}
}

/* --- THE DRAWN MOMENT: the rail draws itself ----------------
   One drawn moment on the site, in the hero, and it is the
   signature element arriving: the hairline runs left to right and
   the tick drops onto it at the point where the first plate's
   price column starts. Gated behind html.js — no JS, blocked JS
   or reduced motion and the rail is simply already there. */
.drawrail{display:block;position:relative;width:100%;height:9px;margin:26px 0 0}
.drawrail i{position:absolute;bottom:0;background:var(--ink);display:block}
.drawrail .rl{left:0;right:0;height:1px;transform-origin:left center}
.drawrail .tk{left:74%;width:2px;height:9px;transform-origin:bottom center}
html.js .drawrail .rl{transform:scaleX(0);
  animation:drawx 1.05s cubic-bezier(.22,.61,.36,1) .3s 1 forwards}
html.js .drawrail .tk{transform:scaleY(0);
  animation:drawy .35s cubic-bezier(.22,.61,.36,1) 1.25s 1 forwards}
@keyframes drawx{to{transform:scaleX(1)}}
@keyframes drawy{to{transform:scaleY(1)}}

/* --- the state key: the legend, ABOVE the data --------------- */
.statekey{display:flex;flex-wrap:wrap;gap:10px 22px;margin:30px 0 0;padding:14px 0 0;
  border-top:1px solid var(--line);font-size:11.5px;color:var(--ink-3);align-items:baseline}
.statekey span{display:inline-flex;align-items:baseline;gap:9px}
.statekey .rst{padding-bottom:4px}

/* --- the plate grid ----------------------------------------- */
.plates{display:grid;gap:38px;margin-top:26px}
@media(min-width:640px){
  .plates{grid-template-columns:1fr 1fr;gap:26px 22px}
  .plates .plate--wide{grid-column:1/-1}
}
@media(min-width:1000px){.plates{gap:34px 30px}}

/* ============================================================
   THE INDEX — the neighbourhood table. The section this template
   is really for. A legend at the top that orients you before you
   read a word, then the areas grouped by WHAT THE HOUSES ARE,
   because that is what sets the price — not by an alphabet and
   not by a card count. Every row carries three axes at once:
   where (the area), when (the era of the stock) and how much
   (the scale, then the exact range). Hairlines, never boxes.
   ============================================================ */
.bandkey{display:grid;grid-template-columns:1fr 1fr;gap:0;margin:28px 0 0;
  border-top:1px solid var(--ink)}
.bandkey li{display:flex;align-items:center;gap:11px;padding:13px 0;
  border-bottom:1px solid var(--line);font-size:11.5px;letter-spacing:.08em;
  color:var(--ink-2);font-variant-numeric:tabular-nums}
.bandkey li:nth-child(odd){border-right:1px solid var(--line);padding-right:14px}
.bandkey li:nth-child(even){padding-left:16px}
.bandkeyh{margin:30px 0 0;font-size:10.5px;letter-spacing:.22em;text-transform:uppercase;
  font-weight:600;color:var(--ink-3)}
@media(min-width:760px){
  .bandkey{grid-template-columns:repeat(4,1fr)}
  .bandkey li{border-right:1px solid var(--line);padding:15px 18px}
  .bandkey li:first-child{padding-left:0}
  .bandkey li:last-child{border-right:0}
  .bandkey li:nth-child(odd),.bandkey li:nth-child(even){padding-left:18px}
  .bandkey li:first-child{padding-left:0}
}
.groups{margin-top:40px;display:grid;gap:38px}
.grp h3{font-size:clamp(22px,4vw,29px);margin-bottom:8px}
.grpline{margin:0;color:var(--ink-2);font-size:15.5px;max-width:52ch}
.arows{margin-top:16px;border-top:2px solid var(--ink)}
.arow{display:grid;grid-template-columns:1fr auto;gap:4px 18px;align-items:baseline;
  padding:14px 0;border-bottom:1px solid var(--line)}
.aname{grid-column:1;font-size:16.5px;color:var(--ink)}
.aera{grid-column:1;grid-row:2;justify-self:start;font-size:9.5px;letter-spacing:.17em;
  text-transform:uppercase;font-weight:600;color:var(--ink-3);
  border:1px solid var(--line);padding:3px 8px;margin-top:5px}
.arange{grid-column:2;grid-row:1;justify-self:end;font-family:var(--font-display);
  font-weight:600;font-size:18px;color:var(--ink);font-variant-numeric:tabular-nums;
  white-space:nowrap}
.ascale{grid-column:2;grid-row:2;justify-self:end;margin-top:11px}
.indexfoot{margin:30px 0 0;padding-left:18px;border-left:2px solid var(--ink);
  font-size:14.5px;line-height:1.65;color:var(--ink-2);max-width:62ch}
@media(min-width:820px){
  .groups{gap:46px}
  .arow{grid-template-columns:1fr 132px 190px;gap:0 26px;padding:15px 0}
  .aera{grid-column:2;grid-row:1;justify-self:start;margin:0}
  .arange{grid-column:3}
  .ascale{grid-column:3;grid-row:2;margin-top:8px}
}
@media(min-width:1080px){
  .groups{grid-template-columns:1fr;gap:52px}
  .arow{grid-template-columns:1fr 150px 120px 190px}
  .ascale{grid-column:3;grid-row:1;justify-self:start;align-self:center;margin:0}
  .arange{grid-column:4}
}

/* ============================================================
   THE FOUR THINGS — priced rows, and a hand-off to the fee sheet
   ============================================================ */
.offer{margin-top:30px;border-top:2px solid var(--ink)}
.orow{display:block;padding:22px 0;border-bottom:1px solid var(--line);
  text-decoration:none;color:inherit}
.orow h3{font-size:clamp(23px,4.4vw,30px);margin-bottom:8px;transition:color .2s ease}
.orow p{margin:0;color:var(--ink-2);font-size:15.5px;max-width:54ch}
.ofee{display:inline-flex;align-items:center;gap:11px;margin-top:12px;font-size:11px;
  letter-spacing:.18em;text-transform:uppercase;font-weight:600;color:var(--ink)}
.ofee::before,.itemfee::before{content:"";width:18px;height:1px;background:var(--ink);flex:0 0 auto}
.orow:hover h3{color:var(--ink-3)}
.offerfoot{margin:26px 0 0}
@media(min-width:820px){
  .orow{display:grid;grid-template-columns:1fr 200px;gap:6px 34px;align-items:baseline;padding:24px 0}
  .orow h3,.orow p{grid-column:1}
  .ofee{grid-column:2;grid-row:1/3;justify-self:end;margin:0}
}

/* --- the review slot ---------------------------------------- */
.saying{margin:0;max-width:34ch}
.saying blockquote{margin:0;font-family:var(--font-display);font-weight:500;
  font-size:clamp(25px,4.6vw,38px);line-height:1.22;letter-spacing:-.008em;
  padding-top:20px;border-top:2px solid var(--ink)}
.saying figcaption{margin-top:20px;font-size:10.5px;letter-spacing:.2em;
  text-transform:uppercase;font-weight:600;color:var(--ink-3)}
@media(min-width:900px){.saying{max-width:26ch;margin-left:auto}}

/* --- the closing band --------------------------------------- */
.close{padding:52px 0}
.closeh{font-size:clamp(28px,5.2vw,46px);line-height:1.06;letter-spacing:-.01em;
  margin-bottom:16px;max-width:16ch}
.closep{max-width:44ch;margin-bottom:28px}
.closetel{display:block;margin-top:22px;padding-top:20px;
  border-top:1px solid rgba(241,240,235,.16);font-family:var(--font-display);
  font-size:clamp(24px,4.4vw,32px);font-weight:600;color:var(--band-ink);
  text-decoration:none;font-variant-numeric:tabular-nums}
.closetel:hover{color:var(--accent-on-band)}
@media(min-width:900px){
  .close{padding:82px 0 76px}
  .closegrid{display:grid;grid-template-columns:1.1fr .9fr;gap:60px;align-items:end}
  .closetel{margin:0}
}

/* ============================================================
   FOOTER — THE COVERAGE LEDGER.
   Not a sitemap. The first thing in it is every neighbourhood on
   the books, drawn straight off the index above, so the footer
   restates the one fact that decides whether a visitor is in the
   right place at all. The contact block and the pages run under
   it as ruled cells in the same vocabulary as the nav.
   ============================================================ */
footer{background:var(--surface-2);border-top:1px solid var(--line);padding:44px 0 26px}
.fh{margin:0 0 14px;font-family:var(--font-body);font-size:10px;letter-spacing:.22em;
  text-transform:uppercase;font-weight:600;color:var(--ink-3)}
.areas{display:grid;grid-template-columns:1fr 1fr;gap:0;border-top:1px solid var(--ink)}
.areas li{padding:11px 0;border-bottom:1px solid var(--line);font-size:14px;color:var(--ink)}
.areas li:nth-child(odd){border-right:1px solid var(--line);padding-right:14px}
.areas li:nth-child(even){padding-left:16px}
.fblock{margin-top:36px;display:grid;gap:26px;padding-top:24px;border-top:1px solid var(--line)}
.fname{font-family:var(--font-display);font-size:26px;font-weight:600;margin:0 0 8px}
.fabout{margin:0;color:var(--ink-2);font-size:14.5px;max-width:48ch}
.fdl{margin:0;display:grid;gap:0}
.fdl > div{display:grid;grid-template-columns:76px 1fr;gap:16px;align-items:baseline;
  padding:10px 0;border-bottom:1px solid var(--line)}
.fdl > div:first-child{border-top:1px solid var(--line)}
.fdl dt{font-size:9.5px;letter-spacing:.18em;text-transform:uppercase;font-weight:600;color:var(--ink-3)}
.fdl dd{margin:0;font-size:14.5px;color:var(--ink);overflow-wrap:anywhere}
.fdl a{text-decoration:none}
.fdl a:hover{color:var(--ink-3)}
.fnav{display:flex;flex-wrap:wrap;gap:2px 24px;margin-top:28px;padding-top:18px;
  border-top:1px solid var(--line)}
.fnav a{padding:7px 0;font-size:11px;letter-spacing:.18em;text-transform:uppercase;
  font-weight:500;color:var(--ink)}
.fnav a:hover{color:var(--ink-3)}
.fbase{margin-top:24px;padding-top:16px;border-top:1px solid var(--line);
  display:flex;flex-wrap:wrap;gap:8px 24px;justify-content:space-between;
  font-size:12.5px;color:var(--ink-3)}
.fbase a{color:var(--ink-2)}
@media(min-width:700px){
  .areas{grid-template-columns:repeat(3,1fr)}
  .areas li{border-right:1px solid var(--line);padding:12px 16px}
  .areas li:nth-child(odd),.areas li:nth-child(even){padding:12px 16px;border-right:1px solid var(--line)}
  .areas li:nth-child(3n){border-right:0;padding-right:0}
  .areas li:nth-child(3n+1){padding-left:0}
}
@media(min-width:900px){
  .fblock{grid-template-columns:1.05fr .95fr;gap:56px;align-items:start}
}

/* ============================================================
   SERVICES — the reference page
   ============================================================ */

/* --- HERO 5: MOSAIC / COLLAGE -------------------------------
   Three frames at three different aspects lapped into an
   asymmetric block. THE TYPE IS FIRST IN SOURCE ORDER and the
   mosaic follows it: on one column a collage placed first stacks
   on top of the headline and pushes it under the fold, which is
   what happened to four of the original seven templates. On
   desktop the block sits beside the type and the tall frame drops
   below the wide one so the collage reads as three pictures, not
   as a row. Every frame carries its asset's own aspect, so
   nothing here crops either. */
.hero-mos{padding:26px 0 0}
.hero-mos h1{max-width:13ch}
.hero-mos .lead{max-width:48ch;margin-top:18px}
.hero-mos .btnrow{margin-top:26px}
.mos{display:grid;grid-template-columns:1fr 1fr;gap:12px;margin-top:30px}
/* A FRAME IS ONLY EVER AS TALL AS ITS PICTURE. .m1 spans two grid rows, and
   without this the grid stretched the frame past its 4:5 asset and the
   gradient behind the photograph rendered as a black block underneath it.
   Found by looking at the render at 390, not by measuring. */
.mos > *{align-self:start}
.mos .m1{grid-column:1;grid-row:1/3}
.mos .m2{grid-column:2;grid-row:1}
.mos .m3{grid-column:2;grid-row:2}
@media(min-width:900px){
  .hero-mos{padding:48px 0 0}
  .hero-mos .mosgrid{display:grid;grid-template-columns:.86fr 1.14fr;gap:54px;align-items:start}
  .mos{margin-top:0;gap:16px;align-content:start;max-width:560px;margin-left:auto}
  .mos .m1{grid-column:1;grid-row:1/3;align-self:start}
  .mos .m2{grid-column:2;grid-row:1}
  .mos .m3{grid-column:2;grid-row:2;margin-top:22px}
}

/* --- the four services in full ------------------------------- */
.item{padding:30px 0;border-top:1px solid var(--line)}
.item:first-child{border-top:0;padding-top:0}
.itemhd h2{font-size:clamp(25px,4.6vw,34px);margin-bottom:10px}
.itemfee{display:inline-flex;align-items:center;gap:11px;margin:0;font-size:11px;
  letter-spacing:.18em;text-transform:uppercase;font-weight:600;color:var(--ink)}
.itembd{margin-top:16px}
.itembd p{color:var(--ink-2);max-width:62ch;margin:0}
@media(min-width:900px){
  .item{display:grid;grid-template-columns:.72fr 1.28fr;gap:54px;align-items:start;padding:40px 0}
  .itembd{margin-top:0}
}

/* --- THE FEE SHEET ------------------------------------------- */
.fees{margin-top:26px;border-top:2px solid var(--ink)}
.feerow{display:grid;grid-template-columns:1fr auto;gap:5px 20px;align-items:baseline;
  padding:16px 0;border-bottom:1px solid var(--line)}
.feerow dt{grid-column:1;font-size:16.5px;color:var(--ink)}
.feerow .fd{grid-column:1;grid-row:2;margin:0;font-size:14px;color:var(--ink-2);max-width:56ch}
.feerow .fv{grid-column:2;grid-row:1/3;justify-self:end;margin:0;font-family:var(--font-display);
  font-weight:600;font-size:21px;color:var(--ink);font-variant-numeric:tabular-nums;white-space:nowrap}
.feenote{margin:26px 0 0;padding-left:18px;border-left:2px solid var(--ink);
  font-size:14.5px;line-height:1.65;color:var(--ink-2);max-width:64ch}
@media(min-width:820px){
  .feerow{grid-template-columns:.62fr 1fr 140px;gap:0 30px}
  .feerow .fd{grid-column:2;grid-row:1}
  .feerow .fv{grid-column:3;grid-row:1;font-size:23px}
}

/* --- THE TWELVE WEEKS ---------------------------------------- */
.run{margin-top:26px;border-top:1px solid var(--line)}
.runstep{display:grid;grid-template-columns:1fr;gap:7px;padding:20px 0;
  border-bottom:1px solid var(--line)}
.runw{font-size:10px;letter-spacing:.2em;text-transform:uppercase;font-weight:600;
  color:var(--ink-3);font-variant-numeric:tabular-nums}
.runstep h3{font-size:clamp(20px,3.6vw,25px)}
.runstep p{margin:0;color:var(--ink-2);font-size:15.5px;max-width:58ch}
@media(min-width:820px){
  .runstep{grid-template-columns:130px 1fr;gap:6px 34px;padding:22px 0}
  .runw{grid-column:1;grid-row:1;padding-top:6px}
  .runstep h3{grid-column:2;grid-row:1}
  .runstep p{grid-column:2;grid-row:2}
}

/* --- questions ----------------------------------------------- */
.asks{margin-top:24px;border-top:1px solid var(--line)}
.asks details{border-bottom:1px solid var(--line)}
.asks summary{list-style:none;cursor:pointer;position:relative;padding:18px 42px 18px 0;
  min-height:48px;font-family:var(--font-display);font-size:21px;font-weight:600;line-height:1.3}
.asks summary::-webkit-details-marker{display:none}
/* the marker is the rail's own mark: a hairline that gains a
   second stroke when the answer is open */
.asks summary::after{content:"";position:absolute;right:2px;top:29px;width:16px;height:1px;
  background:var(--ink)}
.asks summary::before{content:"";position:absolute;right:9.5px;top:21px;width:1px;height:17px;
  background:var(--ink);transform-origin:center;transition:transform .28s cubic-bezier(.22,.61,.36,1)}
.asks details[open] summary::before{transform:scaleY(0)}
.asks .a{margin:0;padding:0 0 22px;color:var(--ink-2);max-width:64ch;font-size:16px}

/* ============================================================
   ABOUT — HERO 2: SPLIT
   ============================================================ */
.hero-split{padding:26px 0 0}
.hsgrid{display:grid;gap:28px}
.hstxt h1{max-width:19ch}
.hstxt .lead{max-width:44ch;margin-top:18px}
@media(min-width:900px){
  .hero-split{padding:48px 0 0}
  .hsgrid{grid-template-columns:1.12fr .88fr;gap:54px;align-items:start}
}
.telling{max-width:62ch;margin-top:22px}
.telling p{color:var(--ink-2);font-size:17px}
.telling p:first-child{color:var(--ink)}
.telling p:last-child{margin-bottom:0}
.how{margin-top:24px;border-top:2px solid var(--ink)}
.how li{padding:20px 0;border-bottom:1px solid var(--line)}
.how h3{font-size:clamp(20px,3.6vw,25px);margin-bottom:7px}
.how p{margin:0;color:var(--ink-2);font-size:15.5px;max-width:56ch}
@media(min-width:820px){
  .how li{display:grid;grid-template-columns:.62fr 1fr;gap:30px;align-items:baseline;padding:22px 0}
  .how h3{margin:0}
}
/* THE AGENT, ONCE. Not a bought headshot — a signed note, set in
   the display face at a size that means it. The portrait frame is
   OPTIONAL and simply absent when a client has no photograph of
   their own, which is better than a stock one. */
.signed{margin-top:34px;padding-top:26px;border-top:2px solid var(--ink);
  display:grid;gap:22px}
.signedq{margin:0;font-family:var(--font-display);font-weight:500;
  font-size:clamp(24px,4.4vw,36px);line-height:1.2;letter-spacing:-.008em;max-width:22ch}
.signedwho{margin:0}
.signedwho b{display:block;font-family:var(--font-display);font-size:25px;font-weight:600;
  font-style:italic;letter-spacing:-.005em}
.signedwho span{display:block;margin-top:6px;font-size:10.5px;letter-spacing:.2em;
  text-transform:uppercase;color:var(--ink-3)}
@media(min-width:900px){
  .signed{grid-template-columns:1.15fr .85fr;gap:54px;align-items:end}
}

/* ============================================================
   CONTACT — HERO 4: TYPE + STAT BAND
   The band carries plain checkable facts. There is no production
   figure anywhere in this template and there must never be one.
   ============================================================ */
.hero-stat{padding:26px 0 0}
.hero-stat h1{max-width:11ch}
.hero-stat .lead{max-width:46ch;margin-top:18px}
.facts{margin-top:30px;background:var(--band);color:var(--band-ink)}
.facts dl{margin:0;display:grid;gap:0}
.facts dl > div{padding:18px 0;border-bottom:1px solid rgba(241,240,235,.16)}
.facts dl > div:last-child{border-bottom:0}
.facts dt{font-size:9.5px;letter-spacing:.2em;text-transform:uppercase;font-weight:600;
  color:var(--accent-on-band);margin-bottom:7px}
.facts dd{margin:0;font-family:var(--font-display);font-size:24px;font-weight:600;
  line-height:1.1;color:var(--band-ink)}
@media(min-width:820px){
  .hero-stat{padding:48px 0 0}
  .facts dl{grid-template-columns:repeat(3,minmax(0,1fr))}
  .facts dl > div{border-bottom:0;border-right:1px solid rgba(241,240,235,.16);
    padding:26px 30px}
  .facts dl > div:first-child{padding-left:0}
  .facts dl > div:last-child{border-right:0;padding-right:0}
}

/* --- the three ways in --------------------------------------- */
.reach{margin-top:24px;border-top:2px solid var(--ink)}
.reach li{border-bottom:1px solid var(--line)}
.reach a,.reach .rb{display:grid;grid-template-columns:1fr;gap:6px;padding:18px 0;
  text-decoration:none;color:var(--ink)}
.reach b{font-size:9.5px;letter-spacing:.2em;text-transform:uppercase;font-weight:600;
  color:var(--ink-3)}
.rv{font-family:var(--font-display);font-weight:600;font-size:clamp(21px,4vw,27px);
  line-height:1.24;letter-spacing:-.008em;overflow-wrap:anywhere}
.reach a:hover .rv{color:var(--ink-3)}
@media(min-width:820px){
  .reach a,.reach .rb{grid-template-columns:150px 1fr;gap:30px;align-items:baseline;padding:20px 0}
}

/* ============================================================
   THE FORM — THE BRIEF.
   The rail, run backwards. Instead of describing a house that
   exists it describes the one you want, in the same ruled cells:
   a tiny caps label in the left column and the answer filling the
   cell, no boxes, hairlines only. It opens on an EMPTY PLATE —
   an unfilled frame with the rail cells blank — because the house
   has not been found yet, and that is what the form is for.
   ============================================================ */
.fgrid{display:grid;gap:36px}
.fgrid > *{min-width:0}
.fcol > h2{margin-bottom:12px}
.fcol > .lead{max-width:46ch;margin-bottom:26px}
@media(min-width:960px){
  .fgrid{grid-template-columns:1.2fr .8fr;gap:60px;align-items:start}
}
.blank{margin:0 0 26px;max-width:380px}
.blankf{border:1px dashed var(--line);aspect-ratio:8/5;display:flex;align-items:center;
  justify-content:center;text-align:center}
.blankf span{font-size:10.5px;letter-spacing:.2em;text-transform:uppercase;color:var(--ink-3);
  max-width:22ch;line-height:1.7}
.blank .rail{border-top-color:var(--line)}
.blank .rline{display:block;height:1px;background:var(--line)}
.blank .rl1{grid-column:1;grid-row:1;width:70px}
.blank .rl2{grid-column:1;grid-row:2;width:100%;max-width:220px;height:2px}
.blank .rl3{grid-column:1;grid-row:3;width:60%;max-width:170px}
.blank .rl4{grid-column:2;grid-row:1/3;justify-self:end;width:78px;align-self:center}
/* the fields themselves: ruled cells, no boxes */
.brief{display:block}
.bline{display:grid;grid-template-columns:1fr;gap:5px;margin:0;padding:14px 0;
  border-bottom:1px solid var(--line)}
.bline label{font-size:9.5px;letter-spacing:.2em;text-transform:uppercase;font-weight:600;
  color:var(--ink-3);transition:color .2s ease}
.bline input,.bline select,.bline textarea{width:100%;min-width:0;min-height:44px;
  border:0;border-radius:0;background:transparent;color:var(--ink);padding:2px 0;
  font-family:var(--font-body);font-weight:400;font-size:17px;line-height:1.5}
.bline textarea{min-height:112px;resize:vertical;font-size:16px}
.bline input:focus,.bline select:focus,.bline textarea:focus{outline:none;box-shadow:none}
.bline:focus-within{border-bottom-color:var(--ink)}
.bline:focus-within label{color:var(--ink)}
.bline input::placeholder,.bline textarea::placeholder{color:var(--ink-3)}
.brief select{max-width:100%;text-overflow:ellipsis}
.bsend{width:100%;margin-top:26px}
.bthanks{border:0;border-top:2px solid var(--ink);border-radius:0;background:var(--surface);
  padding:26px 0 0}
.bthanks h3{font-size:28px;margin-bottom:12px}
.bthanks p{margin:0;color:var(--ink-2);max-width:52ch}
.thmark{display:block;margin:0 0 14px;font-size:10px;letter-spacing:.22em;
  text-transform:uppercase;font-weight:600;color:var(--ink)}
@media(min-width:640px){
  .bsend{width:auto;min-width:270px}
  .bline{grid-template-columns:170px 1fr;gap:18px;align-items:baseline;padding:16px 0}
  .bline label{padding-top:6px}
  .blineblock{grid-template-columns:1fr}
}

/* --- what happens after you send it -------------------------- */
.next{margin-top:6px;border-top:1px solid var(--line);counter-reset:nx}
.next li{padding:17px 0;border-bottom:1px solid var(--line);counter-increment:nx}
.next h3{font-size:18px;margin-bottom:6px}
.next h3::before{content:counter(nx) " — ";color:var(--ink-3);font-variant-numeric:tabular-nums}
.next p{margin:0;color:var(--ink-2);font-size:15px;max-width:46ch}

/* --- 404 ------------------------------------------------------ */
.nf{padding:66px 0 60px}
.nf h1{margin-bottom:18px;max-width:14ch}
.nf .lead{margin-bottom:28px;max-width:46ch}
@media(min-width:900px){.nf{padding:112px 0 100px}}

/* --- reduced motion ------------------------------------------ */
@media(prefers-reduced-motion:reduce){
  html.js .drawrail .rl,html.js .drawrail .tk{transform:none;animation:none}
  .asks summary::before{transition:none}
}
