/* ===========================================================================
   MC CONSTRUCTIONS, instant deck quote landing page.
   Built to web_research/paid-traffic-landing-pages/INSTANT_QUOTE_CALCULATOR_PAGE_GUIDE.md

   PALETTE MECHANISM (guide s11: "constrain the palette by any mechanism"):
   one accent plus opacity. Bronze is the only hue that acts. Navy and ink are
   structure. Green appears once, on success, and nowhere else. Every value is
   declared here and never picked on an element.

   TYPE: one family, Archivo. This is a tool, not an editorial page.
   Micro-label per s11: 11px / .18em / uppercase / 600.
   =========================================================================== */
:root{
  /* brand, from mcconstructionsvic.com.au */
  --navy:#021F59;
  --bronze:#A87E40;
  --gold:#C5A862;
  --bronze-ink:#7A5620;      /* same hue, darkened, AA-safe on paper at label sizes */

  /* neutrals toned off the brand. never pure white on pure black */
  --paper:#FBFAF8;
  --card:#FFFFFF;
  --sand:#F2EFE9;
  --sand-2:#E9E5DD;
  --tint:#FBF6EE;            /* bronze at low opacity, flattened */
  --line:#E2DED6;
  --line-2:#C8C1B4;
  --ink:#191713;
  --ink-2:#4B463D;
  --ink-3:#7A7367;
  --on-navy:#EEF0F6;
  --on-navy-2:#9AA6C4;
  --ok:#1E6B45;
  --bad:#8A2118;

  /* Google's own review amber. Scoped to the rating pill only, and part of the
     same platform-attribution exception as the four-colour G. Nothing else on
     the page may use it. */
  --star-gold:#FBBC04;

  /* the drawn marker colour. rough-notation composites with multiply, so this
     is the flattened value of the gold the CSS fallback paints. one value for
     every highlight on the page, per the one-accent rule above. */
  --mark-draw:#E3D5B4;

  /* 4px scale */
  --s1:4px; --s2:8px; --s3:12px; --s4:16px; --s5:20px; --s6:24px;
  --s7:32px; --s8:40px; --s9:56px; --s10:72px; --s11:96px;

  --ease:cubic-bezier(.2,.8,.2,1);
  --gutter:clamp(16px,4vw,48px);
}
*{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(--paper);color:var(--ink);
  font-family:"Archivo",system-ui,sans-serif;font-size:16px;line-height:1.55;
  -webkit-font-smoothing:antialiased;overflow-x:hidden;
}
img{max-width:100%;display:block}
a{color:inherit}
button{font-family:inherit}

/* ---------------- type ---------------- */
h1,h2,h3{margin:0;font-weight:700;letter-spacing:-.02em;line-height:1.1}
h1{
  /* the phone was clamping to the 30px floor because 5.4vw is tiny at 390px.
     Scaled off vw properly so it reads as a headline on a phone, not a label. */
  font-size:clamp(44px,11.2vw,74px);
  line-height:1.02;letter-spacing:-.035em;
}
h2{font-size:clamp(24px,3.4vw,36px)}
h3{font-size:clamp(17px,1.8vw,20px);letter-spacing:-.01em}
p{margin:0 0 var(--s4)}
p:last-child{margin-bottom:0}
.micro{
  display:block;font-size:11px;line-height:1.4;font-weight:600;
  text-transform:uppercase;letter-spacing:.18em;color:var(--bronze-ink);
}
.micro.on-dark{color:var(--gold)}
.lede{font-size:clamp(16px,1.4vw,18px);color:var(--ink-2);max-width:62ch}
.h2-gap{margin:var(--s4) 0 var(--s6)}
.gap-t{margin-top:var(--s4)}
.gap-t2{margin-top:var(--s7)}
.center{text-align:center}
.centered{margin-left:auto;margin-right:auto}
.note{margin-top:var(--s6);color:var(--ink-3)}

/* ---------------- layout ---------------- */
.wrap{max-width:1180px;margin:0 auto;padding:0 var(--gutter)}
.narrow{max-width:780px;margin:0 auto;padding:0 var(--gutter)}
section{padding:var(--s11) 0}
.navy{background:var(--navy);color:var(--on-navy)}
.navy .lede{color:var(--on-navy-2)}
.sandbg{background:var(--sand)}
.hr{height:1px;background:var(--line);border:0;margin:0}

/* ---------------- placeholder-rate banner ---------------- */
.ratebanner{
  background:var(--bronze);color:#fff;font-size:13px;font-weight:500;
  padding:var(--s3) var(--gutter);text-align:center;line-height:1.45;
}

/* ---------------- persistent bar. logo + phone, no nav (guide s4.1) ------- */
.bar{position:sticky;top:0;z-index:30;background:var(--ink);color:#fff}
.bar .in{
  max-width:1180px;margin:0 auto;padding:var(--s3) var(--gutter);
  display:flex;align-items:center;justify-content:space-between;gap:var(--s4);
}
.bar img{height:30px;width:auto}
.bar .tel{
  display:block;min-height:44px;text-align:right;text-decoration:none;
  font-weight:700;font-size:17px;color:var(--gold);letter-spacing:-.01em;
}
.bar .tel span{
  display:block;font-size:11px;font-weight:600;letter-spacing:.14em;
  text-transform:uppercase;color:#A9A296;
}

/* ---------------- hero ---------------- */
/* THE RATING PILL. Opens the page (Eden, 2026-08-19), sized to sit at roughly
   the width the service-area line used to occupy so the first line of the page
   keeps its old proportion.

   ⚠ PALETTE EXCEPTION, on purpose. Every other hue on this page is bronze at
   some opacity. Google's four-colour G is the one thing that is not, because it
   is the platform's own attribution mark and a recoloured G would be both less
   credible and against Google's brand terms. It is 15px, it appears once, and
   it is the only place this exception applies. */
.ratepill{
  display:inline-flex;align-items:center;gap:var(--s2);
  margin:0;padding:5px var(--s3) 5px var(--s2);
  background:var(--card);border:1px solid var(--line-2);border-radius:999px;
  font-size:12.5px;color:var(--ink-2);
  /* line-height 1 so the text's box hugs its glyphs. With the default 1.25 the
     box carried leading above and below, and centring the BOX left the words
     sitting visibly higher than the stars. */
  line-height:1;
}
.ratepill .gmark{width:15px;height:15px;flex:none}
/* Bigger, tighter and a true gold rather than the brand's muted one: Eden,
   2026-08-19. This is inside the same platform-attribution exception the G is:
   a Google rating pill reads as authentic in Google's own review amber, and
   the brand gold looked dull next to the four-colour G.

   The stroke is not an outline. It is the same colour as the fill, so it just
   fattens the shape and rounds the tips off, which is the "less pointy" part.
   The path itself is also blunter, see the note on .stars svg below. */
.ratepill .stars{display:flex;gap:0;flex:none}
.ratepill .stars svg{
  width:18px;height:18px;fill:var(--star-gold);
  stroke:var(--star-gold);stroke-width:1.5;stroke-linejoin:round;
}
.ratepill .ratetext{white-space:nowrap}
/* stepped back off full ink so the stars carry the emphasis, not the words */
.ratepill .ratetext b{font-weight:700;color:var(--ink-2)}
.ratepill .ratetext i{font-style:normal;color:var(--ink-3)}
/* the separator is a real character in the markup, not CSS generated content:
   a backslash-00b7 escape here rendered as mojibake in the browser */
.ratepill .ratetext em{font-style:normal;color:var(--line-2);margin:0 5px}

/* Closes the hero on the last line before the ground turns to sand. Sentence
   case rather than the uppercase micro-label, because these are claims to be
   read, not a label, and tracked uppercase would not fit two of them on a
   390px line. */
.trustline{
  display:flex;flex-wrap:wrap;gap:var(--s2) var(--s4);
  margin:var(--s4) 0 0;font-size:12px;line-height:1.35;color:var(--ink-2);
  /* a rule segments it off the hero rather than letting it float under the
     photo caption (Eden, 2026-08-19) */
  border-top:1px solid var(--line);padding-top:var(--s3);
}
.trustline span{display:inline-flex;align-items:center;gap:5px;white-space:nowrap}
.trustline svg{
  width:13px;height:13px;flex:none;fill:none;
  stroke:var(--bronze);stroke-width:3;stroke-linecap:round;stroke-linejoin:round;
}

.hero h1{margin:var(--s4) 0 var(--s6)}
.h-calc{margin-bottom:var(--s4)}
@media(min-width:980px){.h-calc{margin-bottom:0}}
.spec{list-style:none;margin:0 0 var(--s6);padding:0;display:grid;gap:var(--s3)}
.spec li{position:relative;padding-left:26px;font-size:15px;color:var(--ink-2)}
.spec li b{color:var(--ink);font-weight:600}
.spec li::before{
  content:"";position:absolute;left:2px;top:6px;width:11px;height:6px;
  border:2px solid var(--bronze);border-right:0;border-top:0;
  transform:rotate(-45deg);
}

/* proof pair */
/* Pulled up (Eden, 2026-08-19): the first proof should sit close under the
   number, not float a block below it. */
.proofs{display:grid;gap:var(--s4);margin-top:var(--s2)}
/* The before and after, FRAMED. Eden, 2026-09-13: "for the before and after,
   I want it in a frame."

   The frame is a real one: a mat of card colour with a hairline, the pair
   sitting inside it as a single object, and the caption printed under the mat
   the way a plate is captioned rather than floating as page text. The two
   source photos are different orientations, so both are locked to a common
   4:3 and object-position keeps the deck in frame instead of the sky. */
.ba{
  margin:0;padding:var(--s3);
  background:var(--card);border:1px solid var(--line-2);
  box-shadow:0 1px 0 rgba(0,0,0,.04);
}
.ba-pair{display:grid;grid-template-columns:1fr 1fr;gap:2px;background:var(--line-2)}
.ba-shot{margin:0;background:var(--card);position:relative;overflow:hidden}
.ba figcaption{
  margin-top:var(--s3);text-align:center;
  font-size:12.5px;color:var(--ink-3);line-height:1.4;
}
.ba img{width:100%;height:auto;aspect-ratio:4/3;object-fit:cover;display:block}
/* The before is landscape and the deck sits low in the frame; the after is
   portrait and the deck sits low too, with sky up top worth cropping out. */
.ba-shot:first-child img{object-position:50% 68%}
.ba-shot:last-child img{object-position:50% 72%}
.ba .tagm{
  position:absolute;left:0;top:0;background:var(--ink);color:#fff;
  font-size:11px;font-weight:600;letter-spacing:.16em;text-transform:uppercase;
  padding:3px var(--s2);
}
.ph{
  aspect-ratio:4/3;display:grid;place-items:center;align-content:center;
  text-align:center;padding:var(--s4);
  background:repeating-linear-gradient(45deg,var(--sand),var(--sand) 10px,var(--sand-2) 10px,var(--sand-2) 20px);
  color:var(--ink-3);font-size:12px;line-height:1.4;font-weight:600;
}
.ph code{font-size:11px;display:block;margin-top:var(--s1);color:var(--ink-2);font-weight:400}
/* The first proof after the number. A STRIP across the page, not a card:
   Eden, 2026-08-19. No background and no border, hairlines top and bottom, so
   it reads as a band rather than as another box competing with the six cards
   below it. Ordered ABOVE the before/after. */
/* The booking now opens with what it actually is. Eden, 2026-08-19: the
   screen read as though the button booked the build. */
.bookhead{margin-bottom:var(--s5);padding-bottom:var(--s4);border-bottom:1px solid var(--line);scroll-margin-top:var(--barh,56px)}
.bookhead h3{font-size:clamp(19px,4.8vw,23px);letter-spacing:-.02em;margin:0 0 var(--s2)}
.bookhead p{font-size:14px;line-height:1.5;color:var(--ink-2);margin:0}
.bookhead p b{color:var(--ink);font-weight:700}

/* The band. Borders live on the SECTION so the two lines run the full width
   of the viewport; the quote inside keeps the page's normal measure. The white
   is deliberate and is the only pure white ground on the page, which is what
   makes the band read as a held breath rather than another card. */
.proofband{
  background:#fff;
  border-top:1px solid var(--line-2);border-bottom:1px solid var(--line-2);
  margin-top:var(--s7);
}
.proofband{padding:0;margin-top:0}
.proofband .proofstrip{padding:var(--s5) 0}
.proofstrip{padding:var(--s4) 0 var(--s5)}
.proofstrip p{
  font-size:clamp(17px,4.6vw,21px);line-height:1.4;color:var(--ink);
  margin:0 0 var(--s4);font-weight:500;
}
/* Eden: the stars belong NEXT TO the initial, not stacked above the quote,
   and the Google attribution sits out to the side rather than under the name.
   That makes the bottom line read left to right as who said it, how they
   rated it, and where it came from. */
.proofstrip .by{display:flex;align-items:center;gap:var(--s3)}
.proofstrip .who{display:flex;flex-direction:column;gap:2px;min-width:0}
.proofstrip .who b{color:var(--ink);font-weight:600;font-size:13.5px;line-height:1.2}
.proofstrip .stars{display:flex;gap:0}
.proofstrip .stars svg{width:15px;height:15px;fill:var(--star-gold);stroke:var(--star-gold);stroke-width:1.5;stroke-linejoin:round}
.proofstrip .src{
  margin-left:auto;display:inline-flex;align-items:center;gap:5px;flex:none;
  color:var(--ink-3);font-size:12.5px;
}

/* ---- the shape question, at the BOTTOM of the size screen ---- */
.shapeask{margin:0 0 var(--s5);padding-top:var(--s4);border-top:1px solid var(--line)}

.quotecard{background:var(--card);border:1px solid var(--line);padding:var(--s5)}
.quotecard p{font-size:15px;color:var(--ink);margin-bottom:var(--s3)}
.quotecard .by{font-size:13px;color:var(--ink-3)}
.quotecard .by b{color:var(--ink);font-weight:600}

/* ---------------- the calculator ---------------- */
.calc{background:var(--card);border:1px solid var(--line-2);position:relative}
.calc-head{
  padding:var(--s5) var(--s5) 0;display:flex;justify-content:space-between;
  align-items:baseline;gap:var(--s3);
;scroll-margin-top:var(--barh,56px)}
.calc-body{padding:var(--s5);min-height:330px}
/* 3px was a hairline nobody noticed moving. 5px, a slower ease, and a short
   glow while it travels, so the answer you just gave visibly buys you
   something (Eden, 2026-09-15). */
.progress{height:5px;background:var(--line);margin:var(--s4) var(--s5) 0;border-radius:3px;overflow:hidden}
.progress i{
  display:block;height:100%;width:0;border-radius:3px;
  background:linear-gradient(90deg,var(--bronze),var(--gold));
  transition:width .62s cubic-bezier(.22,.9,.24,1), box-shadow .62s ease;
}
/* The glow rides the move: the class goes on for the length of the
   transition and comes off when it lands. */
.progress i.moving{box-shadow:0 0 10px 1px rgba(197,168,98,.85)}
@media (prefers-reduced-motion:reduce){.progress i{transition:none}.progress i.moving{box-shadow:none}}
.qtitle{font-size:clamp(19px,2.1vw,24px);font-weight:700;letter-spacing:-.02em;line-height:1.2;margin:var(--s2) 0}
.qhelp{font-size:14px;color:var(--ink-3);margin:0 0 var(--s5)}
.nojs{font-size:15px;color:var(--ink-2)}

/* tiles: real input hidden, selected state in CSS (guide s11) */
.tiles{display:grid;gap:var(--s2)}
.tiles.two{grid-template-columns:1fr 1fr}
.tile{position:relative;display:block}
.tile input{position:absolute;opacity:0;width:0;height:0}
.tile .face{
  display:flex;align-items:center;gap:var(--s3);
  min-height:56px;padding:var(--s3) var(--s4);
  border:1px solid var(--line-2);background:var(--card);
  font-size:16px;font-weight:600;cursor:pointer;
  transition:border-color .18s var(--ease),background .18s var(--ease);
}
.tile .face em{font-style:normal;flex:1;line-height:1.25}
.tile .face small{display:block;font-size:13px;font-weight:400;color:var(--ink-3);margin-top:2px}
.tile:hover .face{border-color:var(--ink-3)}
.tile input:focus-visible + .face{outline:2px solid var(--bronze);outline-offset:2px}
.tile input:checked + .face{border-color:var(--bronze);background:var(--tint);box-shadow:inset 3px 0 0 var(--bronze)}
/* 36px was a bullet, not a picture. Eden, 2026-09-13: the extras step should
   read visually rather than as a list of words, so the box and the drawing in
   it both grew. The tap target grows with it, which is the other reason. */
/* The tick on a multi-select tile. Keyed on :checked rather than an
   attribute, so nothing can lose a specificity fight with it the way
   hidden lost to display:inline-flex on the calculator toggle. */
.tile .pick{
  position:absolute;top:8px;right:8px;width:22px;height:22px;border-radius:50%;
  border:1px solid var(--line-2);background:var(--card);color:transparent;
  display:grid;place-items:center;font-size:12px;font-weight:700;line-height:1;
  transition:background .12s ease,border-color .12s ease,color .12s ease;
}
.tile input:checked + .face .pick{background:var(--bronze);border-color:var(--bronze);color:#fff}
/* The count sits ON the button, a circle at its top right corner, because a
   line of text under a button is not read (Eden, 2026-09-15). Zero is drawn
   with scale(0) rather than display:none so it animates in on the first pick
   and cannot be beaten by a display rule further down the file, which is the
   trap the calculator toggle fell into. */
.btn.hasbadge{position:relative;overflow:visible}
.btnbadge{
  position:absolute;top:-9px;right:-9px;min-width:24px;height:24px;padding:0 6px;
  border-radius:999px;background:var(--bronze);color:#fff;
  font-size:13px;font-weight:700;line-height:24px;text-align:center;
  box-shadow:0 0 0 2px var(--card);
  transform:scale(0);transition:transform .14s cubic-bezier(.2,.9,.3,1.3);
}
.btnbadge.on{transform:scale(1)}
.tile .ic{
  width:60px;height:60px;flex:none;border:1px solid var(--line);
  display:grid;place-items:center;color:var(--bronze-ink);font-size:11px;font-weight:700;
  background:var(--sand);
}
.calc-foot{
  display:flex;align-items:center;justify-content:space-between;gap:var(--s3);
  padding:var(--s4) var(--s5);border-top:1px solid var(--line);background:var(--card);
}
.back{
  background:none;border:0;color:var(--ink-2);font-size:14px;font-weight:600;
  cursor:pointer;min-height:44px;padding:0 var(--s2);flex:none;
}
.back:hover{color:var(--ink)}
.fud{font-size:13px;color:var(--ink-3);line-height:1.4;text-align:right;max-width:36ch;margin:0}

/* fields */
.field{margin-bottom:var(--s4)}
.field label{display:block;font-size:13px;font-weight:600;margin-bottom:var(--s1);color:var(--ink-2)}
.field input{
  width:100%;font-family:inherit;font-size:16px;   /* 16px floor, or iOS zooms */
  padding:var(--s3) var(--s4);min-height:48px;
  border:1px solid var(--line-2);background:var(--card);color:var(--ink);
}
.field input:focus{outline:2px solid var(--bronze);outline-offset:-1px}
.field .why{font-size:12.5px;color:var(--ink-3);margin-top:var(--s1)}
.err{color:var(--bad);font-size:13px;margin-top:var(--s2);display:none;font-weight:600}
.err.show{display:block}

/* buttons */
.btn{
  display:inline-flex;align-items:center;justify-content:center;text-align:center;
  min-height:52px;padding:0 var(--s7);border:0;cursor:pointer;
  font-size:16px;font-weight:700;letter-spacing:-.01em;text-decoration:none;
  transition:background .18s var(--ease),border-color .18s var(--ease);
}
.btn-primary{
  background:var(--bronze);color:#fff;width:100%;gap:10px;
  min-height:56px;font-size:17px;border-radius:3px;
  /* A bronze shadow rather than a grey one: a grey drop shadow under a warm
     button is the fastest way to make a page look like a template. */
  box-shadow:0 6px 16px rgba(138,90,43,.28);
  transition:background .18s var(--ease),box-shadow .18s var(--ease),transform .18s var(--ease);
}
.btn-primary:hover{background:#96702F;box-shadow:0 10px 22px rgba(138,90,43,.34);transform:translateY(-1px)}
.btn-primary:active{transform:translateY(0);box-shadow:0 4px 12px rgba(138,90,43,.3)}
/* The arrow moves, the button does not shout. */
.btn-go{display:inline-flex;transition:transform .18s var(--ease)}
.btn-go svg{
  width:17px;height:17px;fill:none;stroke:currentColor;stroke-width:2.4;
  stroke-linecap:round;stroke-linejoin:round;display:block;
}
.btn-primary:hover .btn-go{transform:translateX(4px)}
@media (prefers-reduced-motion:reduce){
  .btn-primary,.btn-go{transition:none}
  .btn-primary:hover{transform:none}
  .btn-primary:hover .btn-go{transform:none}
}
.btn-ghost{background:none;border:1px solid var(--line-2);color:var(--ink);width:100%}
.btn-ghost:hover{border-color:var(--ink)}
.closer-btn{max-width:380px;margin:0 auto}
.callnote{margin-top:var(--s5);font-size:15px;color:var(--ink-2)}
.callnote a{font-weight:700;color:var(--bronze-ink)}

/* ---------------- result screen ---------------- */
.band{background:var(--navy);color:var(--on-navy);padding:var(--s6) var(--s5);scroll-margin-top:var(--barh,56px)}
.range{font-size:clamp(28px,5.6vw,44px);font-weight:700;letter-spacing:-.03em;line-height:1.05;margin:var(--s2) 0 0}
.range small{display:block;font-size:13px;font-weight:500;letter-spacing:0;color:var(--on-navy-2);margin-top:var(--s3);line-height:1.5}
/* Border on TOP now: it sits under the details form rather than between the
   number and the form (2026-09-15). */
/* The asterisk line under the number. Small and quiet: it is a caveat, not a
   headline, and it has a matching note at the foot of the screen. */
.pstar{
  margin:var(--s3) 0 0;font-size:12px;line-height:1.45;
  color:rgba(255,255,255,.72);max-width:46ch;
}
.editpanel{padding:var(--s4) var(--s5);border-top:1px solid var(--line)}
/* Two columns, not a wrapping flex row. Four chips stacked nearly full
   width cost 241px between the number and the form, which is most of
   why the fields were off screen. Two up halves it. */
.chips{display:grid;grid-template-columns:1fr 1fr;gap:var(--s2);margin-top:var(--s3)}
.chip{
  display:inline-flex;flex-direction:column;justify-content:center;gap:2px;
  min-height:44px;padding:var(--s2) var(--s3);
  background:var(--sand);border:1px solid var(--line-2);
  font-size:14px;font-weight:600;cursor:pointer;color:var(--ink);text-align:left;
}
.chip:hover{border-color:var(--bronze);background:var(--tint)}
.chip u{text-decoration:none;color:var(--bronze-ink);font-size:11px;letter-spacing:.14em;text-transform:uppercase;font-weight:600}
.protect{padding:var(--s5);background:var(--sand);border-bottom:1px solid var(--line);font-size:14px;color:var(--ink-2);line-height:1.55}
.protect b{color:var(--ink)}

/* The trust stack that lands at the same moment as the number (funnel spec:
   half of priced prospects ask a trust question right after the price, so it
   is answered before it is asked). Same card language as the rest of the
   calculator, gold rule to mark it as the page's own emphasis. */
.resulttrust{padding:var(--s4) var(--s5);border-bottom:1px solid var(--line)}
.truststack{list-style:none;margin:0;padding:0}
.truststack li{
  position:relative;padding:5px 0 5px 26px;
  font-size:14px;color:var(--ink-2);line-height:1.45
}
.truststack li::before{
  content:"";position:absolute;left:2px;top:11px;width:12px;height:7px;
  border-left:2px solid var(--bronze);border-bottom:2px solid var(--bronze);
  transform:rotate(-45deg)
}
.truststack b{color:var(--ink)}
/* .dreamline was removed on 2026-09-13 with the paragraph it styled. */

/* thank-you page quote */
.tyquote{
  margin:var(--s6) 0 0;padding:var(--s4) var(--s5);border-left:3px solid var(--gold);
  background:var(--sand);font-size:15px;line-height:1.6;color:var(--ink)
}
.tyquote cite{display:block;margin-top:var(--s2);font-style:normal;font-size:12px;color:var(--ink-3)}
.cal{padding:var(--s5)}

/* The embedded booking page (spec section 8). Height is the whole question
   here: the frame cannot measure its own contents across an origin, so a short
   frame hides the calendar's own scrollbar behind the page's and a visitor on
   a phone ends up scrolling one inside the other. Tall enough that the
   dashboard's page fits, capped against the viewport so the frame never
   becomes a scroll trap taller than the screen. */
/* ---- the booking page (book.html), its own page since 2026-09-15 ---- */
.bookpage{max-width:1100px;padding-top:var(--s5);padding-bottom:var(--s8)}
.bookbar{display:grid;gap:var(--s2);margin-bottom:var(--s5)}
.bookbar .progress{margin:0}
.bookpage .bookhead{max-width:62ch;border-bottom:0;padding-bottom:0;margin-bottom:var(--s5)}
.bookpage .bookhead .qtitle{font-size:clamp(23px,5.4vw,34px);letter-spacing:-.02em;margin:0 0 var(--s3)}
.bookpage .bookhead .qhelp{font-size:16px;line-height:1.55;margin:0}
.booknote{
  margin:var(--s4) 0 0;padding:var(--s3) var(--s4);background:var(--tint);
  border-left:3px solid var(--bronze);font-size:14px;color:var(--ink-2);line-height:1.5;
}
/* The whole point of the page: the calendar gets the width. Taller here than
   it ever was in the card, and capped against the viewport so the frame never
   becomes a scroll trap taller than the screen. */
/* Taller than the viewport on purpose. The dashboard booking page does not
   tell us how tall it is, so the frame is a fixed box and anything longer than
   it scrolls INSIDE the box, which is the second scrollbar Eden saw. Until the
   booking page posts its height, the fix available on this side is to make the
   box tall enough that the calendar and the form fit inside it and only the
   page scrolls. Asked for on 2026-09-15. */
.bookstage .bookframe{height:1500px;min-height:1500px}
@media(max-width:760px){
  .bookstage .bookframe{height:1360px;min-height:1360px}
}
.bookstage .bookframe-help{margin:0 0 var(--s3)}
.bookpage .done{text-align:left}
.bookpage .done .tick{margin-left:0}
.bookframe-wrap{padding-bottom:var(--s4)}
.bookframe{
  display:block;width:100%;border:1px solid var(--line);background:var(--card);
  height:min(1180px, calc(100vh - 120px));min-height:620px;
}
.bookframe-help{margin:0 0 var(--s3);font-size:13px}
.bookframe-help a{color:var(--bronze-ink);font-weight:600}
.requal{font-size:14px;color:var(--ink-2);margin:0 0 var(--s5)}
.days{display:grid;grid-template-columns:repeat(auto-fill,minmax(92px,1fr));gap:var(--s2);margin-top:var(--s3)}
.day{border:1px solid var(--line-2);background:var(--card);cursor:pointer;padding:var(--s3) var(--s2);text-align:center;min-height:72px;font-family:inherit}
.day b{display:block;font-size:16px}
.day small{display:block;font-size:12px;color:var(--ink-3);margin-top:2px}
.day.sel{border-color:var(--bronze);background:var(--tint);box-shadow:inset 0 -3px 0 var(--bronze)}
.day.full{opacity:.45;cursor:not-allowed}
.day.full small{color:var(--bad)}
.slots{display:flex;flex-wrap:wrap;gap:var(--s2);margin-top:var(--s4)}
.slot{border:1px solid var(--line-2);background:var(--card);cursor:pointer;padding:var(--s3) var(--s4);min-height:44px;font-size:15px;font-weight:600;font-family:inherit}
.slot.sel{border-color:var(--bronze);background:var(--tint)}
.oos{padding:var(--s5);background:var(--tint);border:1px solid var(--bronze);margin:var(--s5)}
.oos h3{margin-bottom:var(--s2)}
.oos p{font-size:15px;color:var(--ink-2)}
.done{padding:var(--s8) var(--s5);text-align:center}
.done .tick{width:52px;height:52px;border-radius:50%;background:var(--ok);color:#fff;display:grid;place-items:center;margin:0 auto var(--s5);font-size:26px;font-weight:700}
.done ul{text-align:left;max-width:44ch;margin:var(--s6) auto 0;padding:0;list-style:none;display:grid;gap:var(--s3)}
.done li{position:relative;padding-left:22px;font-size:15px;color:var(--ink-2)}
.done li::before{content:"";position:absolute;left:0;top:10px;width:10px;height:1px;background:var(--bronze)}

/* thanks.html, the page the booking frame returns to. It reuses .done, which
   was built for a screen inside the calculator, so it only needs the few
   things a standalone page has that a screen does not: a width, room under
   the header, and headings between the lists. */
.thanks{max-width:720px;padding-bottom:var(--s8)}
.thanks .qtitle{font-size:clamp(24px,6vw,34px)}
.thanks-h2{font-size:20px;margin:var(--s8) 0 0;text-align:center}
.thanks-ref{font-size:13px;color:var(--ink-3);margin-top:var(--s2)}
.thanks-call{margin-top:var(--s8)}
/* Beats .done .tick{display:grid}. Without this the attribute is ignored
   and a cold visitor gets a confirmation tick for nothing. */
.done .tick[hidden]{display:none}
.thanks a{color:var(--bronze-ink);font-weight:600}

/* ---------------- content blocks ---------------- */
.cards{display:grid;gap:var(--s4)}
.c{background:var(--card);border:1px solid var(--line);padding:var(--s6)}
/* A photo the CUSTOMER attached to their own Google review, sitting on top of
   the review it belongs to (Eden, 2026-08-19). Bled to the card edges by
   cancelling the card's padding, so it reads as part of the card rather than
   as an image pasted inside one.

   These are the strongest proof on the page: they are not Marco's photography,
   they are what the person who paid him chose to photograph.

   ⚠ RIGHTS. Re-hosted from the listing. Same note as the profile pictures: for
   production the cleaner route is the Places API, which serves these under
   Google's own terms. Worth a minute of Marco's attention, they are his
   customers. */
.rvshot{
  margin:calc(var(--s6) * -1) calc(var(--s6) * -1) var(--s5);
  background:var(--sand);border-bottom:1px solid var(--line);
}
/* height:auto is load-bearing. The <img> carries width/height attributes
   (they stop the layout jumping while it loads), and a specified height
   beats aspect-ratio, which only applies when a dimension is auto. Without
   it this rendered 356x1050 and made the card 1431px tall. */
.rvshot img{display:block;width:100%;height:auto;aspect-ratio:4/3;object-fit:cover}
.rvshot figcaption{
  padding:6px var(--s6);font-size:11px;letter-spacing:.02em;color:var(--ink-3);
  background:var(--card);
}
.c p{font-size:15px;color:var(--ink-2);margin:0}
.c .who{margin-top:var(--s3);color:var(--ink);font-weight:600}
.c .n{
  display:block;font-size:11px;font-weight:600;letter-spacing:.18em;
  text-transform:uppercase;color:var(--bronze-ink);margin-bottom:var(--s3);
}
.steps{display:grid;gap:0;position:relative;margin-top:var(--s7)}
/* The track. It runs between the nodes rather than behind them, so it never
   shows through a node on a translucent ground, and it stops short of the
   last one because the last one is an arrival, not a step onward. */
.steps::before{
  content:'';position:absolute;left:21px;top:22px;bottom:64px;width:2px;
  background:linear-gradient(180deg,rgba(168,126,64,.2),rgba(168,126,64,.85));
}
.step{
  position:relative;display:grid;grid-template-columns:44px 1fr;gap:var(--s4);
  align-items:start;padding:var(--s4) 0;
}
.step .no{
  position:relative;z-index:1;
  width:44px;height:44px;border-radius:50%;border:1px solid var(--line-2);
  display:grid;place-items:center;
  font-weight:700;font-size:15px;color:var(--bronze-ink);background:var(--card);
}
.step h3{margin:0;font-size:17px;letter-spacing:-.01em}
.step p{font-size:15px;color:var(--ink-2);margin:var(--s1) 0 0;max-width:60ch}
/* Where the reader is standing right now: they have the estimate, it is the
   screen they just used. Saying so is what turns a list of six things into a
   position on a path. */
.step.here .no{background:var(--bronze);border-color:var(--bronze);color:#fff}
.step.here h3::after{
  content:'you are here';margin-left:var(--s3);font-size:10.5px;font-weight:700;
  letter-spacing:.14em;text-transform:uppercase;color:var(--bronze-ink);
  background:var(--tint);border:1px solid var(--gold);border-radius:999px;
  padding:2px 8px;white-space:nowrap;vertical-align:middle;
}
/* And the end of it, which is the thing they are actually buying. */
.step.arrive{
  background:var(--card);border:1px solid var(--line);border-radius:3px;
  padding:var(--s4);margin-top:var(--s3);
  box-shadow:0 1px 2px rgba(25,23,19,.04);
}
.step.arrive .no{background:var(--ink);border-color:var(--ink);color:#fff}
.alts{display:grid;gap:var(--s5)}
.alt{border-left:3px solid var(--bronze);padding:var(--s1) 0 var(--s1) var(--s5)}
.alt b{display:block;font-size:16px;margin-bottom:var(--s1)}
.alt p{font-size:15px;color:var(--ink-2);margin:0;max-width:68ch}
.gal{display:grid;gap:var(--s4)}
.gal figure{margin:0}
.gal img{width:100%;aspect-ratio:4/5;object-fit:cover;border:1px solid var(--line)}
.gal figcaption{font-size:11px;font-weight:600;letter-spacing:.16em;text-transform:uppercase;color:var(--ink-3);margin-top:var(--s2)}
.faq details{border-bottom:1px solid var(--line);padding:var(--s5) 0}
.faq summary{
  cursor:pointer;font-weight:700;font-size:17px;letter-spacing:-.01em;list-style:none;
  display:flex;justify-content:space-between;gap:var(--s4);min-height:44px;align-items:center;
}
.faq summary::-webkit-details-marker{display:none}
.faq summary::after{content:"+";color:var(--bronze);font-weight:700;font-size:22px;line-height:1}
/* A minus sign, not an en dash. The dash rule covers what the page draws,
   and a CSS escape is still a dash once it is on screen. */
.faq details[open] summary::after{content:"\2212"}
.faq p{margin:var(--s3) 0 0;font-size:15px;color:var(--ink-2);max-width:68ch}
.creds{display:grid;gap:var(--s4)}

footer{background:var(--ink);color:#A9A296;padding:var(--s10) 0 var(--s6);font-size:14px}
footer img{height:40px;margin-bottom:var(--s5)}
footer a{color:#A9A296}
footer a:hover{color:var(--gold)}
footer .fwide{max-width:54ch}
footer .legal{
  margin-top:var(--s7);padding-top:var(--s5);border-top:1px solid #2E2A24;
  font-size:12px;display:flex;flex-wrap:wrap;gap:var(--s3);justify-content:space-between;
}

/* ---------------- sticky mobile CTA. Guide s11, all four details. -------- */
.sticky{
  display:none;
  position:fixed;left:0;right:0;bottom:0;z-index:25;
  padding:10px var(--gutter) calc(10px + env(safe-area-inset-bottom));
  background:linear-gradient(to bottom,rgba(251,250,248,0),var(--paper) 40%);
}
.sticky .btn{width:100%}
@media(max-width:760px){
  .sticky{display:block}
  .sticky[hidden]{display:none}
  /* The spacer for the fixed CTA lives in the footer, not on body: body is
     paper and the footer is ink, so on body it read as a white strip hanging
     under a dark footer (Eden, 2026-09-15). */
  footer{padding-bottom:calc(var(--s6) + 80px)}
}

/* ---------------- reveal. JS-gated, reduced-motion safe. ----------------- */
.js .rv{opacity:0;transform:translateY(12px);transition:opacity .5s var(--ease),transform .5s var(--ease)}
.js .rv.in{opacity:1;transform:none}
@media (prefers-reduced-motion:reduce){
  .js .rv{opacity:1;transform:none;transition:none}
}

/* ---------------- breakpoints ---------------- */
@media(min-width:640px){
  .steps{grid-template-columns:repeat(2,1fr);gap:var(--s6)}
  .cards{grid-template-columns:1fr 1fr}
  .gal{grid-template-columns:repeat(3,1fr)}
  .creds{grid-template-columns:repeat(2,1fr)}
  .alts{grid-template-columns:1fr 1fr;gap:var(--s6) var(--s7)}
}
@media(min-width:980px){
  /* Desktop puts the calculator in its own column beside everything else.
     Mobile keeps DOM order: headline, calculator, then spec and proof. */

  /* One review per row (Eden, 2026-08-19). Was repeat(3,1fr). */
  .cards{grid-template-columns:1fr}
  /* A card carrying a customer photo goes two-up rather than stacking, or the
     photo alone would be 813px tall at this width. */
  .cards .c:has(.rvshot){
    display:grid;grid-template-columns:340px 1fr;column-gap:var(--s6);align-items:start;
    padding-left:0;
  }
  .cards .c:has(.rvshot) .rvshot{
    margin:calc(var(--s6) * -1) 0 calc(var(--s6) * -1) 0;
    grid-row:1 / span 20;align-self:stretch;
    border-bottom:0;border-right:1px solid var(--line);
    display:flex;flex-direction:column;
  }
  .cards .c:has(.rvshot) .rvshot img{flex:1 1 auto;height:100%;aspect-ratio:auto;min-height:220px}
  .cards .c:has(.rvshot) .rvshot figcaption{padding-left:var(--s6);padding-right:var(--s6)}
  /* The ghosted quote glyph is positioned against the card; with the photo
     occupying the left column it has to stay over the TEXT. */
  .cards .c:has(.rvshot) .qglyph{right:12px}
  /* .rtitle caps at 24ch, which was right for a 350px card in a three-column
     grid and is wrong at 1084px: the heading wrapped to three short lines while
     the review under it ran the full width. */
  .cards .rtitle{max-width:36ch;font-size:clamp(20px,1.7vw,25px)}
  .cards .c:has(.rvshot) .rtitle{max-width:28ch}
  /* the review body wants a readable measure, not the whole 1084px */
  .cards .c p{max-width:78ch}
  .creds{grid-template-columns:repeat(4,1fr)}
  .steps{grid-template-columns:repeat(3,1fr);gap:var(--s7) var(--s6)}  /* 6 steps, 2 clean rows */
  .step{grid-template-columns:1fr;gap:var(--s3)}
}

/* ---------------- visual tiles (guide s5.2) ------------------------------
   Size and height are scale diagrams, material is a set of board samples.
   Two per row on every viewport: one per row wastes the screen and pushes
   the later options under the fold, four per row drops the tap target. */
.tiles.visual{grid-template-columns:1fr 1fr;gap:var(--s2)}
.tile.vis .face{
  flex-direction:column;align-items:stretch;gap:0;
  min-height:0;padding:0;overflow:hidden;
}
.tile.vis .media{
  display:block;background:var(--sand);border-bottom:1px solid var(--line);
  aspect-ratio:4/3;overflow:hidden;
}
.tile.vis .media img{width:100%;height:100%;object-fit:cover}
.tile.vis .media.diagram{display:grid;place-items:center;padding:var(--s2);background:var(--card)}
.tile.vis .media.diagram svg{width:100%;height:100%}
.tile.vis .media.need{
  display:grid;place-items:center;text-align:center;padding:var(--s3);
  font-size:11px;font-weight:600;line-height:1.35;color:var(--ink-3);
  background:repeating-linear-gradient(45deg,var(--sand),var(--sand) 10px,var(--sand-2) 10px,var(--sand-2) 20px);
}
.tile.vis .face em{padding:var(--s3) var(--s3) var(--s4);font-size:15px}
.tile.vis .face em small{font-size:12.5px;line-height:1.4}
.tile.vis input:checked + .face{box-shadow:inset 0 0 0 2px var(--bronze)}
.tile.vis input:checked + .face .media{border-bottom-color:var(--bronze)}

/* extras keep the row shape, with a line glyph instead of a photo */
.tile .ic svg{width:40px;height:38px;display:block}
.tile .ic{background:var(--card)}

/* the suburb step needs to say what is covered BEFORE it asks */
.areahint{
  font-size:13px;color:var(--ink-2);background:var(--sand);
  border-left:3px solid var(--bronze);padding:var(--s3) var(--s4);margin:0 0 var(--s4);
  line-height:1.5;
}
.areahint b{color:var(--ink)}

/* review cards: the attribution sits under the quote, not above it */
/* Bumped 2026-09-13. The subhead used to be a supporting detail under the
   promise; it is now the line that carries the ANGLE, which is the emotional
   half of the headline under Willington's result-plus-feeling formula. A line
   doing that job cannot be set at caption size. */
.subhead{
  font-size:clamp(17px,1.8vw,22px);color:var(--ink-2);
  margin:0 0 var(--s6);max-width:46ch;line-height:1.45;
}

/* ---------------- step 1: two sliders with a live plan drawing ------------ */
.plan{
  background:var(--card);border:1px solid var(--line);
  padding:var(--s3);margin-bottom:var(--s4);
}
.plan svg{width:100%;height:auto;display:block}
/* ---- the plan follows you down the size screen (2026-08-19) ---------------
   Sticky under the site header. The workbench hit exactly this problem first
   and its lesson applies here: a sticky panel that is too tall swallows the
   controls underneath it. The workbench settled at 305px of 844; this one is
   capped so the drawing shrinks on a short viewport rather than pushing the
   sliders off screen. */
.planstick{
  position:sticky;top:var(--barh,56px);z-index:4;
  background:var(--card);padding-top:var(--s2);
  margin-left:calc(var(--s1) * -1);margin-right:calc(var(--s1) * -1);
  padding-left:var(--s1);padding-right:var(--s1);
}
.planstick .plan svg{max-height:168px;width:100%;display:block;margin:0 auto}
@media (min-width:760px){
  .planstick{position:static;padding:0;margin:0}
  .planstick .plan svg{max-height:none}
}

/* ---- shape question, size screen (2026-08-19) ------------------------------
   Sits ABOVE the drawing because it decides what the drawing is. Two options
   only: a rectangle covers squares too, and every other deck shape a homeowner
   describes is either an L or something the measure has to resolve anyway.
   Tap targets are the full tile, comfortably over the 44px minimum. */
.shapepick{display:grid;grid-template-columns:1fr 1fr;gap:var(--s2);margin-bottom:var(--s4)}
.shapeopt{
  display:flex;flex-direction:column;align-items:center;justify-content:center;gap:6px;
  min-height:76px;padding:var(--s3) var(--s2);
  background:var(--card);border:1px solid var(--line-2);border-radius:4px;
  font:inherit;color:var(--ink-2);cursor:pointer;text-align:center;
  transition:border-color .16s ease,background .16s ease;
}
.shapeopt b{font-size:13px;font-weight:600;line-height:1.2}
.shapeopt .shapeic{width:34px;height:29px;display:block}
.shapeopt:focus-visible{outline:2px solid var(--bronze);outline-offset:2px}
/* Repeating the class rather than relying on .shapeopt.is-on winning on source
   order. Three separate rules on this page have already been lost to a longer
   selector elsewhere in the file, and this one is a state that must never
   silently stop applying. */
.shapepick .shapeopt.is-on{
  border-color:var(--bronze);background:var(--sand);box-shadow:inset 0 0 0 1px var(--bronze);
}
.shapepick .shapeopt.is-on b{color:var(--ink)}

/* ---- the cut-out, only present for an L ---- */
.cutwrap{
  margin:0 0 var(--s5);padding:var(--s4) var(--s4) var(--s2);
  background:var(--sand);border-left:3px solid var(--bronze);
}
.cutwrap[hidden]{display:none}
.cutlede{margin:0 0 var(--s4);font-size:13px;line-height:1.45;color:var(--ink-2)}
.cutlede b{font-weight:700;color:var(--ink)}
.cutwrap .slider:last-child{margin-bottom:var(--s2)}

/* ---- anything coming up through the deck ---- */
.obst{margin:0 0 var(--s5);padding-top:var(--s4);border-top:1px solid var(--line)}
.obstq{display:block;font-size:13px;font-weight:600;color:var(--ink-2);margin-bottom:var(--s3)}
.obstq i{display:block;font-style:normal;font-weight:400;font-size:12px;color:var(--ink-3);margin-top:2px}
.obstrow{display:grid;grid-template-columns:repeat(4,1fr);gap:6px}
.obstopt{
  min-height:44px;padding:0 var(--s2);
  background:var(--card);border:1px solid var(--line-2);border-radius:4px;
  font:inherit;font-size:14px;font-weight:600;color:var(--ink-2);cursor:pointer;
  transition:border-color .16s ease,background .16s ease;
}
.obstopt:focus-visible{outline:2px solid var(--bronze);outline-offset:2px}
.obstrow .obstopt.is-on{
  border-color:var(--bronze);background:var(--sand);color:var(--ink);
  box-shadow:inset 0 0 0 1px var(--bronze);
}

.readout{
  display:flex;align-items:baseline;gap:var(--s2);
  padding:var(--s3) var(--s4);background:var(--sand);
  border-left:3px solid var(--bronze);margin-bottom:var(--s5);
}
.readout b{font-size:22px;font-weight:700;letter-spacing:-.02em;color:var(--ink)}
.readout span{font-size:12px;font-weight:600;letter-spacing:.14em;text-transform:uppercase;color:var(--ink-3)}
.slider{margin-bottom:var(--s5)}
.slider label{
  display:flex;justify-content:space-between;align-items:baseline;
  font-size:13px;font-weight:600;color:var(--ink-2);margin-bottom:var(--s2);
}
.slider label b{font-size:17px;color:var(--ink);font-weight:700}
.slider input[type=range]{
  -webkit-appearance:none;appearance:none;
  width:100%;height:44px;background:transparent;cursor:pointer;display:block;
}
.slider input[type=range]:focus{outline:none}
.slider input[type=range]:focus-visible{outline:2px solid var(--bronze);outline-offset:4px}
/* track */
.slider input[type=range]::-webkit-slider-runnable-track{
  height:4px;background:var(--line-2);border-radius:2px;
}
.slider input[type=range]::-moz-range-track{
  height:4px;background:var(--line-2);border-radius:2px;
}
/* thumb: 28px visual, sitting inside a 44px tall control */
.slider input[type=range]::-webkit-slider-thumb{
  -webkit-appearance:none;appearance:none;
  width:28px;height:28px;border-radius:50%;
  background:var(--bronze);border:3px solid var(--card);
  box-shadow:0 0 0 1px var(--line-2);
  margin-top:-12px;
}
.slider input[type=range]::-moz-range-thumb{
  width:28px;height:28px;border-radius:50%;
  background:var(--bronze);border:3px solid var(--card);
  box-shadow:0 0 0 1px var(--line-2);
}

/* review highlights: emphasis is ours, the words are theirs and unedited.
   Scoped to `mark` itself, not to .c, or any quote outside a review card
   falls back to the browser's default highlighter yellow. */
mark{
  background:linear-gradient(to bottom,transparent 58%,rgba(168,126,64,.28) 58%);
  color:inherit;font-weight:600;padding:0 1px;
}
/* Once highlights.js has loaded AND the library is present it adds .rn to
   <html> and takes the flat gradient away, because from that point the marker
   is drawn instead. If either script fails the gradient above still ships, so
   the page is never left with unhighlighted phrases. */
.rn mark{background:none}

/* .no-rn is opted out of the drawn marker (see highlights.js). On the
   calculator title it is an UNDERLINE rather than a highlight (Eden,
   2026-08-19): at 30px a filled band competes with the hero's marker two
   hundred pixels above it, and the rule reads as emphasis without becoming a
   second highlighter on the same screen.

   Declared on `mark.no-rn` rather than under `.rn`, so it looks the same
   whether or not the highlight script ever loads. */
mark.no-rn{
  background:none;
  text-decoration:underline;
  text-decoration-color:var(--gold);
  text-decoration-thickness:3px;
  text-underline-offset:6px;
}

/* .hl-flat is the OTHER way to opt out: no drawn marker, but the flat
   highlight rather than the underline. The proof strip needs this. It is a
   quote, so it should look like the other quoted highlights on the page, and
   it sits directly under the calculator title, which already owns the gold
   underline. Two gold underlines one screen apart is the same defect the
   underline was introduced to fix.

   Specificity: three classes deep on purpose. `mark.no-rn` above is (0,2,0)
   and would otherwise keep the underline. This file has lost three separate
   rules to exactly that, so the count is deliberate. */
mark.no-rn.hl-flat{
  background:linear-gradient(to bottom,transparent 58%,rgba(168,126,64,.28) 58%);
  text-decoration:none;
}

/* The scannable heading on each review. Eden, 2026-08-19: the reviews were a
   wall of paragraphs and nothing carried at a glance. Every heading is a
   sentence lifted WORD FOR WORD out of the review printed underneath it, in
   quotes, and the full review is still there unedited. The body's highlight
   moved to a different phrase so the same words are not emphasised twice. */
.rtitle{
  font-size:clamp(18px,2vw,21px);line-height:1.25;letter-spacing:-.02em;
  margin:0 0 var(--s3);max-width:24ch;
}
.cards .c p{font-size:14.5px;color:var(--ink-2);line-height:1.6}

/* the platform mark next to the attribution line */
.gmark-sm{width:12px;height:12px;flex:none;vertical-align:-2px;margin-right:5px}

/* ---------------- review profile pictures --------------------------------
   Guide s4.2 slot 4 wants a named review WITH a photo and the platform named.
   The slot is real: drop a src on the img inside .avatar and the monogram is
   replaced automatically. Until then it shows initials taken from the
   reviewer's actual name, which is honest, rather than a stock face or a
   generic silhouette, which would not be. */
/* ---------------- review card lift ---------------------------------------
   Ported from the R Dhillon & Co home page's "What we do" three-pillar band,
   which Eden pointed at. The mechanism is theirs and it is better than the
   binary hover/not-hover this first shipped as:

   ONE custom property, --glow, from 0 to 1, drives the border tint, a large
   soft halo, the lift and a very slight scale together. On a mouse, :hover
   sets it to 1. On a touch screen there is no hover, so cards.js sets it
   CONTINUOUSLY to how centred the card is in the viewport, which is why the
   phone version reads as a card easing into focus rather than snapping on.

   Under prefers-reduced-motion cards.js sets a flat 0.32 and nothing moves,
   which is also what the Dhillon build does. */
.cards .c{
  --glow:0;
  border-color:color-mix(in srgb,var(--bronze) calc(var(--glow) * 38%),var(--line));
  box-shadow:
    0 1px 3px rgba(25,23,19,.04),
    0 0 52px 2px color-mix(in srgb,rgba(168,126,64,.5) calc(var(--glow) * 55%),transparent);
  transition:box-shadow .35s var(--ease),border-color .35s var(--ease),
             transform .35s var(--ease);
}
/* Transform is handed over only once the entrance reveal has finished, because
   `.js .rv.in{transform:none}` is THREE classes deep and beats anything
   shorter, so the selector below repeats `.c` to reach three as well.
   This trap has bitten twice on this page. What makes it hard to see: the
   shadow and the border DO apply and only the transform loses, so the card
   reacts to hover without moving, which reads as a subtle animation rather
   than a bug. If a lift stops working here, count the classes first. */
.cards .c.c-live{      /* .c twice ON PURPOSE: see the note above */
  transform:translateY(calc(var(--glow) * -9px)) scale(calc(1 + var(--glow) * .014));
  will-change:transform;
}
@media (hover:hover) and (pointer:fine){
  .cards .c:hover{--glow:1}
}
@media (prefers-reduced-motion:reduce){
  .cards .c,.cards .c.c-live{transition:none;transform:none;will-change:auto}
}

.avatar{
  position:relative;flex:none;
  width:40px;height:40px;border-radius:50%;
  display:grid;place-items:center;overflow:hidden;
  background:var(--sand);border:1px solid var(--line-2);
}
.avatar img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover}
.avatar img[hidden]{display:none}
.avatar b{
  font-size:13px;font-weight:700;letter-spacing:.04em;color:var(--bronze-ink);
}
.byline{
  display:flex;align-items:center;gap:var(--s3);
  margin-top:auto;padding-top:var(--s5);
}
.byline .who{margin:0;padding:0;color:var(--ink);font-weight:600;font-size:15px}
.c .byline + .n{margin:var(--s2) 0 0}
.quotecard .by{display:flex;align-items:center;gap:var(--s3)}
.quotecard .by small{display:block;color:var(--ink-3);font-size:12.5px;margin-top:1px}

/* a tile that is an opt-out rather than a choice: full width, no media */
.tiles.visual .tile.full{grid-column:1 / -1}
.tile.vis.full .face{flex-direction:row;align-items:center;min-height:56px;padding:var(--s3) var(--s4)}
.tile.vis.full .face em{padding:0;font-size:16px}

/* ---------------- hero: the 30-second claim, and the face ---------------- */
.hl-big{
  /* nowrap so the highlight never splits "30" from "seconds" across a line */
  white-space:nowrap;
  background:linear-gradient(to bottom,transparent 62%,rgba(197,168,98,.45) 62%);
  color:inherit;padding:0 2px;
  /* pull the following full stop back flush; the 2px is highlight bleed, not a space */
  margin-right:-2px;
}
.rn .hl-big{background:none}
.meet{
  display:flex;align-items:center;gap:var(--s4);
  padding:var(--s3) 0 0;margin:0 0 var(--s6);
}
.meet .face{
  flex:none;width:72px;height:72px;border-radius:50%;overflow:hidden;
  object-fit:cover;object-position:50% 30%;
  background:var(--sand);border:1px solid var(--line-2);
  box-shadow:0 1px 0 rgba(0,0,0,.04);
}
.meet .facehold{
  flex:none;width:72px;height:72px;border-radius:50%;overflow:hidden;
  display:grid;place-items:center;align-content:center;text-align:center;
  font-size:9.5px;font-weight:600;line-height:1.25;color:var(--ink-3);
  background:repeating-linear-gradient(45deg,var(--sand),var(--sand) 7px,var(--sand-2) 7px,var(--sand-2) 14px);
  border:1px solid var(--line-2);padding:var(--s1);
}
.facehold em{display:block;font-style:normal;font-weight:400;font-size:8.5px;opacity:.8}
.meet-txt b{display:block;font-size:16px;font-weight:700;letter-spacing:-.01em}
.meet-txt span{display:block;font-size:14px;color:var(--ink-2);line-height:1.45}

/* ---------------- reviews: a real heading ---------------- */
.revhead{margin-top:var(--s9)}
/* The star path is blunter than the usual one everywhere it appears, not just
   in the pill: the golden-ratio inner radius most star glyphs use (~0.38 of the
   outer) is what makes them read as spiky. This one is 0.52, so the points are
   chunkier. One shape on the page, so the pill and the proof block agree. */
.revhead .stars{display:flex;gap:3px;margin-bottom:var(--s3)}
.revhead .stars svg{width:22px;height:22px;fill:var(--bronze)}
.revhead h2{font-size:clamp(24px,3.4vw,36px);margin-bottom:var(--s2)}
.revhead p{font-size:15px;color:var(--ink-2);margin:0}

/* ---------------- why Marco -----------------------------------------------
   Eden, 2026-08-19: the sections below the fold read flatter than the top, and
   he wanted a "why pick us" beat with more photography, smaller and framed
   differently.

   This ABSORBS the old three-photo "Recent work" gallery rather than sitting
   next to it, because two photo sections back to back is the same stutter he
   flagged in the proof block. All six of his job photos are in here now,
   square and small, where three ran large before.

   It deliberately does NOT repeat the credibility band underneath: that block
   carries the checkable guarantees, this one carries what the page had nowhere
   else to say. */
.why{background:var(--card);border-top:1px solid var(--line)}
.whyshots{
  display:flex;flex-wrap:wrap;justify-content:center;gap:2px;
  margin:var(--s5) 0 0;
}
.whyshots figure{flex:0 0 calc((100% - 4px) / 3)}
.whyshots figure{margin:0;position:relative;overflow:hidden;background:var(--sand)}
.whyshots img{
  width:100%;aspect-ratio:1/1;object-fit:cover;display:block;
  transition:transform .5s var(--ease);
}
@media (hover:hover) and (pointer:fine){
  .whyshots figure:hover img{transform:scale(1.05)}
}
@media (prefers-reduced-motion:reduce){
  .whyshots img{transition:none}
  .whyshots figure:hover img{transform:none}
}
.whyshots figcaption{
  position:absolute;left:0;right:0;bottom:0;
  font-size:9.5px;font-weight:600;letter-spacing:.1em;text-transform:uppercase;
  color:#fff;padding:16px var(--s2) 5px;
  background:linear-gradient(to top,rgba(12,11,9,.75),transparent);
}
.whypoints{display:grid;gap:var(--s5);margin-top:var(--s7)}
.whypoint{display:grid;grid-template-columns:auto 1fr;gap:var(--s3);align-items:start}
.whypoint>svg{
  width:20px;height:20px;margin-top:3px;fill:none;
  stroke:var(--bronze);stroke-width:1.6;stroke-linecap:round;stroke-linejoin:round;
}
.whypoint b{display:block;font-size:16px;letter-spacing:-.01em;margin-bottom:3px}
.whypoint em{display:block;font-style:normal;font-size:14.5px;color:var(--ink-2);line-height:1.6}
.whyfoot{margin-top:var(--s6);font-size:13px;color:var(--ink-3)}
@media(min-width:760px){
  .whyshots figure{flex-basis:calc((100% - 10px) / 6)}
  .whypoints{grid-template-columns:1fr 1fr;gap:var(--s6) var(--s7)}
}

/* ---------------- credibility band, calm version -------------------------
   Was navy with a striped board texture behind gold icons: busy, and this is
   the block a nervous buyer reads slowest. Now the page's own card system on
   the light ground. The only flourish is a large ghosted numeral behind each
   card, which gives the grid rhythm without adding noise. */
.creds-band{background:var(--sand);border-top:1px solid var(--line)}
.creds{display:grid;gap:var(--s4);counter-reset:cred}
.cred{
  counter-increment:cred;
  position:relative;overflow:hidden;
  background:var(--card);border:1px solid var(--line);
  padding:var(--s6);
  transition:border-color .3s var(--ease);
}
@media (hover:hover) and (pointer:fine){
  .cred:hover{border-color:var(--line-2)}
}
/* The ghosted numeral behind each card is gone (Eden, 2026-09-15: this strip
   could do with better design). It was 74px of 4.5 percent ink that read as a
   smudge at any size and gave the grid no rhythm it did not already have.
   The icon carries the card instead, on a tinted disc so it reads as an object
   rather than a stray drawing, and the top rule ties the four together. */
.cred{border-top:3px solid var(--bronze)}
.cred-ic{
  display:grid;place-items:center;width:52px;height:52px;border-radius:50%;
  background:var(--tint);border:1px solid var(--gold);margin-bottom:var(--s4);
}
.cred-ic svg{
  width:26px;height:26px;fill:none;
  stroke:var(--bronze-ink);stroke-width:1.6;stroke-linecap:round;stroke-linejoin:round;
}
.cred b{display:block;font-size:17px;font-weight:700;letter-spacing:-.01em;margin-bottom:var(--s2);color:var(--ink)}
.cred-sub{display:block;font-size:14px;color:var(--ink-2);line-height:1.55;max-width:34ch}

/* ---------------- hero, restructured -------------------------------------
   Headline across the top, then Marco full-length against the credibility
   case, then a cue into the calculator. */
.hero{padding:var(--s8) 0 var(--s7)}
.hero-top{max-width:none}
.hero-top .subhead{max-width:44ch}
.hero-split{
  display:grid;gap:var(--s6);align-items:end;
  margin-top:var(--s7);
}
.hero-cred .micro{margin-bottom:var(--s3)}
.cred-name{
  font-size:clamp(20px,2.6vw,28px);line-height:1.15;margin:0 0 var(--s4);
  letter-spacing:-.02em;max-width:18ch;
}
.cred-lede{font-size:15.5px;color:var(--ink-2);line-height:1.6;margin:0 0 var(--s5);max-width:46ch}
.hero-cred .spec{margin:0}

/* the figure. Sits on a warm ground so a transparent cut-out has something
   to stand on, with a soft ellipse under him instead of a hard edge. */
.hero-figure{
  margin:0;position:relative;align-self:end;
  display:flex;flex-direction:column;align-items:center;
}
.hero-figure::before{
  content:"";position:absolute;left:50%;bottom:52px;transform:translateX(-50%);
  width:min(320px,82%);height:min(320px,82%);border-radius:50%;
  background:radial-gradient(circle at 50% 50%,rgba(168,126,64,.20),rgba(168,126,64,0) 68%);
}
.hero-figure img{
  position:relative;width:100%;max-width:340px;height:auto;
  display:block;
}
.hero-figure figcaption{
  position:relative;margin-top:var(--s3);text-align:center;
  padding-top:var(--s3);border-top:1px solid var(--line);width:min(340px,100%);
}
.hero-figure figcaption b{display:block;font-size:17px;font-weight:700;letter-spacing:-.01em}
.hero-figure figcaption span{display:block;font-size:12.5px;color:var(--ink-3)}

/* scroll cue */
.scrollcue{
  display:inline-flex;align-items:center;gap:var(--s3);
  margin-top:var(--s7);min-height:52px;padding:0 var(--s6) 0 var(--s6);
  background:var(--bronze);color:#fff;text-decoration:none;
  font-size:16px;font-weight:700;letter-spacing:-.01em;
  transition:background .2s var(--ease);
}
.scrollcue:hover{background:#96702F}
.scrollcue svg{
  width:20px;height:20px;fill:none;stroke:currentColor;stroke-width:2;
  stroke-linecap:round;stroke-linejoin:round;
  animation:cue 2.2s var(--ease) infinite;
}
@keyframes cue{0%,100%{transform:translateY(0)}50%{transform:translateY(4px)}}
@media (prefers-reduced-motion:reduce){.scrollcue svg{animation:none}}

/* the calculator now owns its own section */
.calcwrap{padding:var(--s9) 0;background:var(--sand);border-top:1px solid var(--line)}
.calc-grid{display:grid;gap:var(--s7)}
/* Opens the calculator band. Eden, 2026-08-19: there was no title at all, so
   the sand band just started and a card appeared, and nothing told a visitor
   that the thing worth scrolling to was down here. This is now what peeks in
   under the hero on a phone, in place of the card's own head row. */
.calchead{margin:0 0 var(--s5)}
/* Bigger and louder than a section heading, because it is the one instruction
   on the page and it is what a visitor sees peeking under the hero (Eden,
   2026-08-19). It outranks every other h2 here on purpose. Affordable now that
   the sticky CTA no longer occupies the bottom 72px of the first view. */
.calchead h2{
  font-size:clamp(30px,7.8vw,44px);line-height:1.06;letter-spacing:-.03em;
}
/* no max-width on the phone: at 18ch the title broke after "quote" and the
   sticky CTA sliced the orphaned "here." in half. It fits one line at 390px. */
.calchead h2{margin:var(--s2) 0 0}
@media(min-width:760px){.calchead h2{max-width:15ch}}
.calchead p{margin:var(--s2) 0 0;font-size:14.5px;color:var(--ink-2);max-width:46ch}

@media(min-width:760px){
  .hero-split{grid-template-columns:1fr auto;gap:var(--s8);align-items:end}
  .hero-figure img{max-width:380px}
}
@media(min-width:980px){
  /* Eden, 2026-08-19: "I don't know why the title has to be so left-centered,
     it can take up the full width." 16ch capped it at 704px on a 1440 screen,
     so it wrapped to two lines and left the whole right of the first view
     empty above Marco. It runs one line across the top now. */
  .hero-top h1{max-width:24ch}
  .hero-top .subhead{max-width:52ch}
  .hero-split{grid-template-columns:1.1fr .9fr;gap:var(--s9);align-items:center}
  .hero-figure img{max-width:380px}
  .hero{padding-bottom:var(--s6)}
  .calc-grid{grid-template-columns:1fr 1fr;gap:var(--s9);align-items:start}
}

/* ---------------- MOBILE HERO: one compact view ---------------------------
   Everything above the calculator has to fit a phone screen with the first
   step of the calculator peeking into view underneath it, so the visitor can
   see there is a tool without being told. That budget is tight, so the split
   runs two-up on the phone as well: short credibility on the left, a small
   body shot on the right. */
/* Tightened one step on the 4px scale when the rating pill took the opening
   slot (2026-08-19). The pill is 28px tall against the 15px text line it
   replaced, and the first view had one pixel of slack, so the 13px it added
   put the calculator's head row behind the sticky button at 390x644. These
   four reductions buy 20px back and leave real clearance instead of one pixel.
   Desktop is untouched: the 760px block resets all of them. */
/* Tightened again when the service area moved to the hero's last line
   (2026-08-19). The line is 14px and its margin is 12, and the first view had
   7px of clearance, so it had to be paid for. Everything below is one step
   down the 4px scale, mobile only: the 760px block resets all of it. */
.hero{padding:var(--s5) 0 var(--s2)}
.hero h1{margin:var(--s2) 0 var(--s4)}
.trustline{margin-top:var(--s2);padding-top:var(--s2)}
.hero-top .subhead{margin-bottom:0}
.hero-split{
  grid-template-columns:1fr 116px;
  gap:var(--s4);
  align-items:center;
  margin-top:var(--s3);
}
.hero-cred .micro{margin-bottom:var(--s2)}
.cred-name{font-size:19px;line-height:1.2;margin:0 0 var(--s2);max-width:none}
/* Taper: the lede is capped so its longest line lands INSIDE the heading's
   longest line above it (Eden, 2026-08-19). Measured at 390px the heading
   runs 169px and the lede was running 218px, so the block widened as it
   went down instead of narrowing. */
.cred-lede{font-size:14px;line-height:1.5;margin:0;max-width:23ch}
.hero-cred .spec{display:none}          /* the same facts sit in the navy band below */

.hero-figure img{max-width:116px}
.hero-figure::before{bottom:34px;width:120%;height:120%}
/* the figure is the taller of the two hero columns, so this gap is what sets
   the split's height. One step down on each buys the first view 8px. */
.hero-figure figcaption{
  margin-top:var(--s1);padding-top:var(--s1);width:100%;
}
.hero-figure figcaption b{font-size:13px}
.hero-figure figcaption span{display:none}   /* the org name is already in the header */

.scrollcue[hidden]{display:none}
.calcwrap{padding:var(--s4) 0 var(--s9)}

@media(min-width:760px){
  .hero{padding:var(--s8) 0 var(--s7)}
  .hero h1{margin:var(--s3) 0 var(--s5)}
  .hero-split{grid-template-columns:1fr auto;gap:var(--s8);align-items:end;margin-top:var(--s7)}
  .hero-cred .spec{display:grid}
  .cred-name{font-size:clamp(22px,2.6vw,28px);margin-bottom:var(--s4);max-width:18ch}
  .cred-lede{font-size:15.5px;margin-bottom:var(--s5);max-width:28ch}
  /* Trimmed from 340 so the whole hero clears a short desktop viewport. The
     figure is the only element here big enough to pay for it: every gap in
     this hero is already at or near its designed minimum. */
  .hero-figure img{max-width:300px}
  .hero-figure::before{bottom:52px;width:min(320px,82%);height:min(320px,82%)}
  .hero-figure figcaption{margin-top:var(--s3);padding-top:var(--s3);width:min(340px,100%)}
  .hero-figure figcaption b{font-size:17px}
  .hero-figure figcaption span{display:block;font-size:12.5px}
  .scrollcue[hidden]{display:inline-flex}
  .calcwrap{padding:var(--s9) 0}
}

@media(min-width:980px){
  /* The figure is far taller than the credibility column, so bottom-aligning
     the two on a wide screen left a dead gap under the subhead. Top-align the
     text and let the figure run past it. */
  .hero-split{grid-template-columns:1.05fr .95fr;gap:var(--s9);align-items:start}
  /* ⚠ THIS is the rule that wins, not the identical-looking pair in the
     earlier 980px block. Two @media(min-width:980px) blocks declare
     .hero-top h1 max-width, same specificity, so SOURCE ORDER decides and this
     one is later. Editing the other one changes nothing, which is exactly how
     this file has burned three previous passes.

     Eden, 2026-08-19: the title should take the full width. 16ch pinned it to
     704px on a 1440 screen, so it wrapped to two lines and left the right half
     of the first view empty. */
  .hero-top h1{max-width:24ch}
  .hero-top .subhead{max-width:52ch}
}

/* Permit flag on the result. VIC: over 800mm, or attached to the house, needs
   a building permit. Gold-ruled so it reads as a condition of the number above
   rather than as a warning about it. */
.permit{
  padding:var(--s5);background:var(--card);border-bottom:1px solid var(--line);
  border-left:3px solid var(--gold);
  font-size:14px;color:var(--ink-2);line-height:1.55
}
.permit b{color:var(--ink)}

/* ---------------- what moves the price ---------------------------------- */
/* THE FIVE DRIVERS. Cards on the sand ground, each with a drawing of its own
   mechanism. Rebuilt 2026-09-15 (Eden: actual boxes, and it is bland).
   The old version was a bare number, a heading and a paragraph on the page
   background, five times, which skims as a wall. */
.drivers{display:grid;gap:var(--s4)}
.driver{
  background:var(--card);border:1px solid var(--line);border-radius:3px;
  padding:var(--s5);box-shadow:0 1px 2px rgba(25,23,19,.04);
  display:block;
}
.driver .dnum{
  display:inline-block;font-size:11px;font-weight:700;letter-spacing:.18em;
  color:var(--bronze-ink);margin:0 0 var(--s3);
}
/* The drawings. Three stroke weights, bronze on card, never filled except
   the three board swatches which are the point of that one. */
.dfig{display:block;width:88px;height:55px;margin:0 0 var(--s3)}
.dfig path,.dfig rect,.dfig circle{fill:none;stroke:var(--bronze);stroke-width:2;stroke-linecap:round;stroke-linejoin:round}
.dfig .thin{stroke-width:1.4;stroke:var(--line-2)}
.dfig .ghost{stroke:var(--line-2);stroke-width:1.4;stroke-dasharray:3 3}
.dfig .fill-1{fill:#B5703A;stroke:none}
.dfig .fill-2{fill:#9C9A93;stroke:none}
.dfig .fill-3{fill:#5A3C25;stroke:none}
.driver h3{margin:0;font-size:18px;letter-spacing:-.01em}
.driver p{margin:var(--s2) 0 0;font-size:15px;color:var(--ink-2);line-height:1.6}
.driver p em{font-style:italic;color:var(--ink)}

/* The scale. Flat fills, no gradient, one accent, and the caption carries the
   claim so the bars are never the only thing saying it. */
.dscale{display:grid;gap:var(--s2);margin-top:var(--s4);padding-top:var(--s4);border-top:1px solid var(--line)}
.dsrow{display:grid;grid-template-columns:76px 1fr;align-items:center;gap:var(--s3)}
.dsrow b{font-size:12px;font-weight:700;letter-spacing:.04em;color:var(--ink-2)}
.dsrow i{display:block;height:10px;background:var(--sand-2);border-radius:2px;overflow:hidden}
.dsrow s{display:block;height:100%;background:var(--bronze);text-decoration:none}
.dscap{font-size:12px;color:var(--ink-3);margin-top:var(--s1)}
/* The old flat list rules lived here. They were a two column grid with the
   number in its own track and a border-top per row, and they were still
   winning by source order over the card rules above. Removed 2026-09-15. */
.driver-foot{
  margin-top:var(--s7);padding:var(--s5);background:var(--card);
  border-left:3px solid var(--bronze);
  font-size:15px;color:var(--ink-2);line-height:1.6;max-width:70ch;
}
@media(min-width:760px){
  .drivers{grid-template-columns:1fr 1fr;gap:var(--s4)}
  /* Five drivers in a two-column grid leaves an orphan on the last row.
     The fifth spans instead. Same orphan the six-step section hit on a
     five-column grid on 08-18: check the count against the columns any
     time an item is added to a grid on this page. */
  .drivers .driver:last-child{grid-column:1 / -1}
}

/* reviews now sit directly under the calculator, so they open the page's
   depth rather than closing it. Top margin comes from the section, not the
   old in-flow spacing. */
.reviews-first .revhead{margin-top:0}


/* ---------------- review cards: more to look at --------------------------
   A star row and a quote glyph per card. The stars are factual: his Google
   rating is 5.0 and every review shown is a five. The glyph is decoration,
   kept low-contrast so it reads as texture rather than as a graphic. */
/* Matched to the hero pill: bigger, gold, and blunted with a same-colour
   stroke rather than left as thin bronze points (Eden, 2026-08-19). */
.cardstars{display:flex;gap:0;margin-bottom:var(--s3)}
.cardstars svg{
  width:19px;height:19px;fill:var(--star-gold);
  stroke:var(--star-gold);stroke-width:1.5;stroke-linejoin:round;
}
.revhead .stars svg{
  fill:var(--star-gold);stroke:var(--star-gold);stroke-width:1.2;stroke-linejoin:round;
}
.revhead .stars{gap:0}
.c{position:relative;overflow:hidden}
.qglyph{
  position:absolute;top:-14px;right:6px;
  font-family:Georgia,serif;font-size:96px;line-height:1;
  color:var(--bronze);opacity:.10;pointer-events:none;
}
.c > p:first-of-type{position:relative}


/* ---------------- who this is for ----------------------------------------
   Eden, 2026-08-19. Reuses the .cred card outright so it cannot drift from
   the credibility band's look. The ghosted numeral is suppressed: these are
   three audiences, not three ranked steps, and the band above already spends
   that device. Three columns from 760 up, because three short cards fit and
   a 2+1 grid would leave an orphan. */
/* Category images, approved 2026-08-19. Bled to the card edges by cancelling
   its padding, same as the customer review photos.

   ⚠ These are the ONLY images on this page that are not photographs of real
   work, and there is deliberately no deck in any of them. Two review cards now
   carry real customer photos of Marco's decks; a generated deck sitting near
   those would mean a visitor cannot tell which is real, and the real ones are
   the strongest proof on the page. These are about the person, not the product.

   height:auto is load-bearing here for the same reason it is on .rvshot: the
   img carries width/height attributes and a specified height beats
   aspect-ratio, which only applies when a dimension is auto. */
.credshot{
  margin:calc(var(--s6) * -1) calc(var(--s6) * -1) var(--s5);
  background:var(--sand);border-bottom:1px solid var(--line);
}
.credshot img{display:block;width:100%;height:auto;aspect-ratio:4/3;object-fit:cover}

/* Label and value pairs inside a card. The first version of the board
   comparison used <b>Upkeep.</b><br> and the label came out the same size
   as the answer, so a card that is four short facts read as four headings
   with fragments under them. The label is now small caps and quiet, the
   answer is the thing you read. */
/* The verification link. Quiet, because the claim is the sentence and this
   is the receipt for it, not a call to action competing with the one CTA. */
.verifylink{
  display:inline-block;margin-top:2px;font-size:13px;font-weight:600;
  color:var(--bronze-ink);text-decoration:underline;text-underline-offset:2px;
}
.speclist{list-style:none;margin:var(--s4) 0 0;padding:0;display:grid;gap:var(--s3)}
.speclist li{font-size:15px;line-height:1.5;color:var(--ink-2)}
.speclist li b{
  display:block;font-size:11px;letter-spacing:.09em;text-transform:uppercase;
  font-weight:700;color:var(--ink-3);margin-bottom:2px;
}
.foryou{display:grid;gap:var(--s4);margin-top:var(--s7)}
.foryou .cred::after{content:none}
@media(min-width:760px){
  .foryou{grid-template-columns:repeat(3,1fr)}
}


/* ---------------- lead magnet sections, 2026-08-19 ------------------------
   Four sections built from Marco's own "Deck Blueprint" PDF. Each one reuses
   an existing device where one fitted (.whypoints for the pain points) and
   only introduces new CSS where the content genuinely needed a new shape:
   a comparison table, a numbered chain and a ruled checklist.

   Grounds alternate deliberately. Running order of backgrounds through the
   lower page is now sand, paper, card, sand, paper, card, sand, so no two
   adjacent sections share a ground. */

/* 7. pain */
.painband{background:var(--card);border-top:1px solid var(--line)}
/* PROBLEM, ARROW, FIX. Lifted in spirit from the fix-list on the Ryder local
   SEO page, which Eden pointed at, and rebuilt in this page's palette and
   scale: no gradients on the panels, one accent, hairlines rather than the
   big soft shadows that page uses.

   The arrow sits ON the seam between the two halves at wide widths, and
   turns to point DOWN when the row stacks, because an arrow pointing right
   at something that is now underneath it is worse than no arrow. */
.fixlist{display:grid;gap:var(--s4);margin-top:var(--s7)}
.fixrow{
  position:relative;display:grid;grid-template-columns:1fr;
  background:var(--card);border:1px solid var(--line);border-radius:3px;
  overflow:hidden;box-shadow:0 1px 2px rgba(25,23,19,.04);
}
.fixproblem{padding:var(--s5)}
.fixproblem h3{margin:0 0 var(--s2);font-size:17px;letter-spacing:-.01em;color:var(--ink)}
.fixproblem p{margin:0;font-size:14.5px;line-height:1.55;color:var(--ink-2)}
.fixfix{
  padding:var(--s5);background:var(--tint);border-top:1px solid var(--gold);
  display:grid;gap:var(--s2);align-content:center;
}
.fixtag{
  justify-self:start;display:inline-block;font-size:10px;font-weight:700;
  letter-spacing:.14em;text-transform:uppercase;color:#fff;background:var(--bronze);
  border-radius:999px;padding:4px 10px;
}
.fixfix p{margin:0;font-size:15px;line-height:1.5;color:var(--ink);font-weight:500}
.fixseam{
  position:absolute;left:50%;top:auto;bottom:auto;
  display:none;place-items:center;width:38px;height:38px;border-radius:50%;
  background:var(--bronze);color:#fff;box-shadow:0 0 0 5px var(--card);z-index:2;
}
.fixseam svg{
  width:17px;height:17px;fill:none;stroke:currentColor;stroke-width:2.2;
  stroke-linecap:round;stroke-linejoin:round;
}
@media(min-width:860px){
  .fixrow{grid-template-columns:1fr 1fr;align-items:stretch}
  .fixproblem{padding-right:var(--s8)}
  .fixfix{border-top:0;border-left:1px solid var(--gold);padding-left:var(--s8)}
  .fixseam{display:grid;top:50%;transform:translate(-50%,-50%)}
}
/* Centred 2026-09-15 (Eden): "maybe just make that centred". The measure stays
   capped at 30ch so it keeps its shape; auto margins centre the block itself
   rather than only the text inside it, which is the bit that actually looked
   off against the ruled rows above it. */
.pull{margin:var(--s8) 0 0;padding:var(--s6) 0 0;border-top:1px solid var(--line);
  text-align:center}
.pull p{
  font-size:clamp(19px,2.4vw,26px);line-height:1.35;letter-spacing:-.02em;
  color:var(--ink);margin:0 auto var(--s3);max-width:30ch;
}
.pull cite{display:block;font-style:normal;font-size:13px;color:var(--ink-3)}

/* 9. everything included */
.included{background:var(--paper)}
.inclist{list-style:none;margin:var(--s7) 0 0;padding:0;display:grid;gap:var(--s5)}
/* Eight items now rather than five, so they read as a checklist in two
   columns on a wide screen instead of one very long ladder. */
.inclist li{
  position:relative;padding-left:var(--s7);
}
@media(min-width:760px){
  .inclist{grid-template-columns:1fr 1fr;gap:var(--s5) var(--s7)}
}
.inclist li::before{
  content:"";position:absolute;left:0;top:2px;width:18px;height:18px;
  background:var(--bronze);
  -webkit-mask:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'><path d='M4 12.5l5 5L20 6.5' fill='none' stroke='black' stroke-width='2.6' stroke-linecap='round' stroke-linejoin='round'/></svg>") no-repeat center/contain;
  mask:url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'><path d='M4 12.5l5 5L20 6.5' fill='none' stroke='black' stroke-width='2.6' stroke-linecap='round' stroke-linejoin='round'/></svg>") no-repeat center/contain;
}
.inclist b{display:block;font-size:16.5px;letter-spacing:-.01em;margin-bottom:3px}
.inclist span{display:block;font-size:14.5px;color:var(--ink-2);line-height:1.6;max-width:44ch}

/* 11. permit table and approval chain */
.ptable{margin-top:var(--s7);background:var(--card);border:1px solid var(--line)}
.prow{display:grid;grid-template-columns:.72fr 1fr 1fr;border-top:1px solid var(--line)}
.prow:first-child{border-top:0}
.prow>span{padding:var(--s4) var(--s3);font-size:13.5px;line-height:1.4;color:var(--ink-2)}
.prow>span+span{border-left:1px solid var(--line)}
.phead{background:var(--sand)}
.phead>span{
  font-size:10.5px;font-weight:700;letter-spacing:.1em;text-transform:uppercase;color:var(--ink-3);
}
/* these three repeat .prow> on purpose. .prow>span already sets a colour at
   (0,1,1); a bare .pno is (0,1,0) and silently loses. Same trap as the
   .js .rv.in transform one recorded further up this file. */
.prow>.pk{font-weight:700;color:var(--ink)}
.prow>.pno{color:var(--ok)}
.prow>.pyes{color:var(--bad)}
.pnote{margin:var(--s5) 0 0;font-size:14.5px;color:var(--ink-2);line-height:1.6;max-width:62ch}
.pnote b{color:var(--ink)}
/* THE SPLIT. Your jobs against his, side by side. It is the only thing in
   this section that argues on a skim, so it comes first and it is the only
   thing here with a filled panel. */
.split{display:grid;gap:var(--s4);margin-top:var(--s7)}
.splitcol{
  background:var(--card);border:1px solid var(--line);border-radius:3px;
  padding:var(--s5);box-shadow:0 1px 2px rgba(25,23,19,.04);
}
.splitcol.him{background:var(--tint);border-color:var(--gold)}
.splittag{
  display:inline-block;font-size:11px;font-weight:700;letter-spacing:.16em;
  text-transform:uppercase;color:var(--ink-3);margin-bottom:var(--s3);
}
.splitcol.him .splittag{color:var(--bronze-ink)}
.splitcol ul{list-style:none;margin:0;padding:0;display:grid;gap:var(--s3)}
.splitcol li{
  position:relative;padding-left:26px;font-size:15px;line-height:1.5;color:var(--ink-2);
}
/* A tick for his list, a dash for yours: the shape says who is doing the
   work before a word is read. */
.splitcol li::before{
  content:'';position:absolute;left:4px;top:.62em;width:10px;height:2px;
  background:var(--line-2);border-radius:2px;
}
.splitcol.him li::before{
  content:'';left:2px;top:.34em;width:6px;height:11px;background:none;
  border:solid var(--bronze);border-width:0 2px 2px 0;transform:rotate(45deg);border-radius:0;
}
.splitfoot{
  margin:var(--s4) 0 0;padding-top:var(--s3);border-top:1px solid var(--line);
  font-size:13px;color:var(--ink-3);line-height:1.5;
}
@media(min-width:760px){
  .split{grid-template-columns:1fr 1.15fr;gap:var(--s5);align-items:start}
}

/* The standalone permit offer. It is the only price in this section, so it
   gets the bronze rule that the page uses for a figure worth stopping on. */
.permitoffer{
  margin:var(--s5) 0 0;padding:var(--s4) var(--s5);background:var(--card);
  border:1px solid var(--line);border-left:3px solid var(--bronze);border-radius:3px;
  font-size:15px;line-height:1.6;color:var(--ink-2);max-width:70ch;
}
.permitoffer b{color:var(--ink)}
.chain-h{margin:var(--s10) 0 0;font-size:clamp(19px,2.2vw,24px);letter-spacing:-.02em}
.chain{list-style:none;margin:var(--s6) 0 0;padding:0;display:grid;gap:0}
/* A RAIL, not a bordered list. The numbers are nodes on a line that runs down
   through them, which is what makes seven rows read as one process rather
   than seven separate requirements. The line intensifies downward, because a
   track that gets stronger as it goes implies progress toward something. */
.chain.rail{position:relative;padding-left:0}
.chain.rail::before{
  content:'';position:absolute;left:15px;top:14px;bottom:26px;width:2px;
  background:linear-gradient(180deg,rgba(168,126,64,.25),var(--bronze));
}
.chain li{
  position:relative;display:grid;grid-template-columns:32px 1fr;gap:var(--s4);
  align-items:baseline;padding:var(--s3) 0;border:0;
}
.chain b{
  position:relative;z-index:1;width:32px;height:32px;border-radius:50%;
  display:grid;place-items:center;background:var(--card);
  border:1px solid var(--line-2);color:var(--bronze-ink);
  font-size:11px;font-weight:700;letter-spacing:.02em;
  font-variant-numeric:tabular-nums;
}
/* The last node is the one the visitor actually wants, so it is filled. */
.chain li.done b{background:var(--bronze);border-color:var(--bronze);color:#fff}
.chain li.done span{color:var(--ink);font-weight:600}
.chain span{font-size:15px;color:var(--ink-2);line-height:1.45}
.chain-note{margin:var(--s5) 0 0;font-size:15.5px;color:var(--ink);line-height:1.6;max-width:52ch}

/* 12. five checks */
.checks{background:var(--card);border-top:1px solid var(--line)}
.checklist{margin-top:var(--s7);border-top:1px solid var(--line)}
.checkitem{
  display:grid;grid-template-columns:auto 1fr;gap:var(--s4);align-items:start;
  padding:var(--s5) 0;border-bottom:1px solid var(--line);
}
.checkitem>svg{
  width:22px;height:22px;flex:none;fill:none;stroke:var(--bronze);
  stroke-width:1.5;stroke-linecap:round;stroke-linejoin:round;margin-top:1px;
}
.checkitem b{display:block;font-size:16.5px;letter-spacing:-.01em;margin-bottom:3px}
.checkitem p{margin:0;font-size:14.5px;color:var(--ink-2);line-height:1.6;max-width:62ch}

@media(min-width:760px){
  .inclist{grid-template-columns:1fr 1fr;gap:var(--s6) var(--s7)}
  .prow>span{padding:var(--s5) var(--s5);font-size:15px}
  .chain li{grid-template-columns:52px 1fr;padding:var(--s4) 0}
  .chain span{font-size:16px}
  .checkitem{grid-template-columns:auto 1fr;gap:var(--s5)}
}


/* ---------------- calculator workbench, 2026-08-19 ------------------------
   The "all at once" view. Demo only: the stepped calculator is still what the
   page ships with and none of its rules changed.

   Layout inverts between widths on purpose. On a phone the drawing is STUCK
   to the top and the controls scroll under your thumb, which is the whole
   point: you are meant to watch the deck change while you tap. On desktop
   there is room for both, so the controls take the left and the drawing sits
   sticky on the right where a plan drawing belongs. */

.ct-btn{
  font:inherit;font-size:13px;font-weight:600;letter-spacing:-.01em;
  padding:9px var(--s5);min-height:40px;border:0;cursor:pointer;
  background:var(--card);color:var(--ink-2);transition:background .2s var(--ease),color .2s var(--ease);
}
.ct-btn:hover{color:var(--ink)}
.ct-btn.is-on{background:var(--ink);color:#fff}

.wb{grid-column:1 / -1;background:var(--card);border:1px solid var(--line)}
.wb-grid{display:grid}

.wb-vis{
  position:sticky;top:var(--barh,56px);z-index:6;
  /* ⚠ This was --sand, and planBuild() paints the drawing's own ground rect
     #F2EFE9, which IS --sand. Identical values, so the drawing surface
     disappeared into the panel and the deck floated on nothing. The section
     band behind it is --sand too, so the panel had no edge either.

     This is the third time on this page: .calc-foot was --sand on a --sand
     band and the card's bottom edge vanished the same way. When a panel looks
     like it has no edges, compare its background against BOTH the thing behind
     it and the thing drawn inside it. */
  background:var(--card);border-bottom:1px solid var(--line);
  padding:var(--s4) var(--s4) var(--s5);
}
.wb-draw svg{display:block;width:100%;height:auto;max-height:30vh}
.wb-price{
  margin-top:var(--s3);display:flex;align-items:baseline;justify-content:space-between;
  gap:var(--s3);flex-wrap:wrap;
}
.wb-plabel{
  display:block;font-size:10.5px;font-weight:700;letter-spacing:.12em;
  text-transform:uppercase;color:var(--ink-3);
}
.wb-range{
  margin:0;font-size:clamp(20px,5.2vw,28px);font-weight:700;
  letter-spacing:-.03em;line-height:1.1;color:var(--ink);
}
.wb-range em{font-style:normal;font-weight:400;font-size:.6em;color:var(--ink-3)}
/* The breakdown lives at the top of the CONTROLS column, not in the sticky
   one. See the note in workbench.js: pinning it ate half a 390px viewport. */
.wb-detail{margin:0 0 var(--s5);padding-bottom:var(--s5);border-bottom:1px solid var(--line)}
.wb-break{margin:0;font-size:13px}
.wb-break div{display:flex;justify-content:space-between;gap:var(--s4);padding:3px 0}
.wb-break dt{color:var(--ink-3);margin:0}
.wb-break dd{margin:0;color:var(--ink-2);font-variant-numeric:tabular-nums;white-space:nowrap}
.wb-warn{
  margin:var(--s3) 0 0;padding-top:var(--s3);border-top:1px solid var(--line);
  font-size:12px;line-height:1.5;color:var(--ink-2);
}
.wb-controls{padding-top:var(--s5)}
.wb-warn b{color:var(--bad)}

.wb-controls{padding:var(--s5) var(--s4) var(--s6)}
.wb-field{padding:0 0 var(--s5);margin-bottom:var(--s5);border-bottom:1px solid var(--line)}
.wb-field:last-of-type{border-bottom:0;margin-bottom:0}
.wb-lab{
  display:block;font-size:11px;font-weight:700;letter-spacing:.1em;text-transform:uppercase;
  color:var(--ink-3);margin-bottom:var(--s2);
}
.wb-lab b{color:var(--ink);font-size:14px;letter-spacing:0;text-transform:none}
.wb-field input[type=range]{
  -webkit-appearance:none;appearance:none;width:100%;height:34px;background:none;
  margin:0 0 var(--s4);cursor:pointer;
}
.wb-field input[type=range]::-webkit-slider-runnable-track{height:3px;background:var(--line-2)}
.wb-field input[type=range]::-moz-range-track{height:3px;background:var(--line-2)}
.wb-field input[type=range]::-webkit-slider-thumb{
  -webkit-appearance:none;appearance:none;width:26px;height:26px;border-radius:50%;
  background:var(--bronze);border:2px solid #fff;box-shadow:0 1px 4px rgba(0,0,0,.25);margin-top:-11.5px;
}
.wb-field input[type=range]::-moz-range-thumb{
  width:26px;height:26px;border-radius:50%;background:var(--bronze);
  border:2px solid #fff;box-shadow:0 1px 4px rgba(0,0,0,.25);
}
.wb-chips{display:flex;flex-wrap:wrap;gap:var(--s2)}
.wb-chip{
  font:inherit;font-size:13.5px;padding:10px var(--s4);min-height:44px;
  background:var(--card);border:1px solid var(--line-2);color:var(--ink-2);cursor:pointer;
  transition:border-color .2s var(--ease),background .2s var(--ease),color .2s var(--ease);
}
.wb-chip:hover{border-color:var(--ink)}
.wb-chip.is-on{background:var(--ink);border-color:var(--ink);color:#fff}
.wb-text{
  width:100%;font:inherit;font-size:16px;padding:12px var(--s3);
  background:var(--card);border:1px solid var(--line-2);color:var(--ink);
}
.wb-text:focus{outline:2px solid var(--bronze);outline-offset:1px}
.wb-area{margin:var(--s3) 0 0;font-size:13.5px;line-height:1.5;color:var(--ink-2)}
.wb-area .ok{color:var(--ok)}
.wb-area .no{color:var(--bad)}
.wb-foot{margin:var(--s6) 0 0;font-size:12.5px;line-height:1.55;color:var(--ink-3)}

@media(min-width:980px){
  /* The sand ground is painted on the GRID, not on the sticky panel. A sticky
     element is shorter than the column it sits in, so colouring the panel left
     the right half of the section going white halfway down and reading as an
     unfinished block. The gradient hard-stops at the column boundary. */
  .wb-grid{
    grid-template-columns:1fr 1fr;align-items:start;
    background:linear-gradient(to right,var(--card) 50%,var(--sand) 50%);
  }
  .wb-vis{
    order:2;position:sticky;top:var(--s7);background:none;
    border-bottom:0;border-left:1px solid var(--line);
    padding:var(--s6);
  }
  .wb-draw svg{max-height:none}
  .wb-price{display:block}
  .wb-range{margin-top:var(--s1)}
  .wb-controls{order:1;padding:var(--s6)}
}
@media (prefers-reduced-motion:reduce){
  .ct-btn,.wb-chip{transition:none}
}


/* ---- the full bleed work strip ----------------------------------------
   Eden wants the best five unskippable. Each shot is 85vh so it cannot be
   taken in at a glance, and the sliver of the next one showing underneath is
   what tells a thumb to keep going.

   object-position sits at 55% rather than centre: these are phone photos of
   backyards and the sky is almost always the top third, so a dead centre crop
   spends the frame on cloud. */
.showcase{margin-top:var(--s7)}
.shots{display:grid;gap:0;margin-top:var(--s4)}
.shot + .shot{border-top:1px solid var(--line-2)}
.shot{margin:0;position:relative;overflow:hidden;background:var(--sand)}
.shot img{
  display:block;width:100%;height:85vh;min-height:420px;max-height:900px;
  object-fit:cover;object-position:50% 55%;
}
.shot figcaption{
  position:absolute;left:0;right:0;bottom:0;
  padding:var(--s6) var(--s4) var(--s3);
  background:linear-gradient(to top,rgba(0,0,0,.55),rgba(0,0,0,0));
}
.shot figcaption span{
  color:#fff;font-size:13px;font-weight:500;letter-spacing:.01em;
  text-shadow:0 1px 3px rgba(0,0,0,.5);
}
@media (max-width:640px){
  /* On a phone 85vh is most of the screen already, and a min-height fights
     the small landscape case rather than helping it. */
  .shot img{height:72vh;min-height:340px}
}

/* ---- the full review wall ---------------------------------------------
   Twenty four reviews instead of six hand picked ones. The argument for
   showing all of them is that a curated six reads as a curated six; a whole
   listing, including the wordless five stars, reads as a whole listing. */
.rphotos{
  display:grid;grid-template-columns:1fr 1fr;gap:2px;
  margin:var(--s4) 0 0;background:var(--line-2);
}
/* One photo gets the whole width rather than sitting in a half-empty row. */
.rphotos-one{grid-template-columns:1fr}
.rphotos img{
  width:100%;height:auto;aspect-ratio:4/3;object-fit:cover;display:block;
  background:var(--sand);
}
.rby{display:flex;align-items:center;gap:var(--s3);margin-top:var(--s4)}
.ravatar{
  position:relative;flex:none;width:34px;height:34px;border-radius:50%;
  overflow:hidden;background:var(--sand-2);
  display:grid;place-items:center;
}
.ravatar img{position:absolute;inset:0;width:100%;height:100%;object-fit:cover}
/* The initials sit UNDER the avatar, so a Google image that fails to load or
   is withheld leaves something readable rather than a grey hole. */
.ravatar b{font-size:12px;font-weight:700;color:var(--ink-3);letter-spacing:.02em}
.rwho{display:flex;flex-direction:column;gap:1px;min-width:0}
.rwho b{font-size:13.5px;font-weight:600;color:var(--ink);line-height:1.2}
.rwho em{font-style:normal;font-size:12px;color:var(--ink-3)}

.rmore-head{
  margin:var(--s7) 0 var(--s4);font-size:clamp(15px,1.4vw,17px);
  font-weight:600;color:var(--ink-2);
}
.rchips{
  list-style:none;margin:0;padding:0;
  display:grid;gap:1px;background:var(--line-2);
  border:1px solid var(--line-2);
  grid-template-columns:repeat(auto-fill,minmax(200px,1fr));
}
.rchip{
  display:flex;align-items:center;gap:var(--s3);
  padding:var(--s3) var(--s4);background:var(--card);
}
.cardstars-sm svg{width:12px;height:12px}

.rattr{margin-top:var(--s2);font-size:12.5px;color:var(--ink-3)}
.rattr b{color:var(--ink-2);font-weight:600}
.c p+p{margin-top:var(--s2)}


/* The before and after, now standing on its own under the review band. Capped
   rather than full bleed: a pair of 4:3 crops stretched across a desktop is
   two letterboxes, and the point of the pair is that you can hold both in one
   glance. */
.basection{padding:var(--s7) 0 0}
.basection .ba{max-width:760px;margin:0 auto}

@media (max-width:640px){
  /* Two 4:3 crops side by side on a 390px phone is 165px each, which is too
     small to read a transformation in. Stacked they are full width, and the
     Before and After tags carry the comparison the adjacency used to. */
  .ba-pair{grid-template-columns:1fr}
}


/* ---- Eden's pass, 2026-09-13 ------------------------------------------- */

/* 5/5 sits beside the stars and never drops under them. Not bold: the heading
   is the only bold thing on a card. */
.ratedas{display:flex;align-items:center;gap:var(--s2);flex-wrap:nowrap}
.ratedas span[aria-hidden]{font-size:12.5px;font-weight:400;color:var(--ink-3)}
.ratedas-sm span[aria-hidden]{font-size:11.5px}

/* Google sits bottom right of the card, on its own line under the name so it
   cannot be squeezed by a long one. */
.rby{flex-wrap:wrap}
.rsrc{margin-left:auto}

/* The two sections either side of the work strip were carrying the page's
   default 96px of section padding on top of their own margins, which is the
   white gap Eden kept hitting. */
.showcase{margin-top:0;padding:var(--s9) 0 0}
.why{padding-top:var(--s8)}

.gprofile-wrap{margin-top:var(--s5)}
.gprofile{
  display:inline-flex;align-items:center;gap:var(--s3);
  padding:var(--s3) var(--s5);
  border:1px solid var(--line);background:var(--card);
  color:var(--ink);text-decoration:none;font-weight:600;font-size:15px;
  transition:border-color .2s var(--ease),background .2s var(--ease);
}
.gprofile:hover{border-color:var(--ink-3);background:var(--sand)}
.gprofile i{font-style:normal;color:var(--ink-3)}
.gprofile .gmark{width:18px;height:18px;flex:none}


/* The CTA lands on the calculator's heading, not on the card, so a visitor
   arrives reading what the thing is rather than staring at step one with no
   context. The offset clears the sticky site header. */
#calcstart{scroll-margin-top:72px}


/* ---- the material step -------------------------------------------------
   Three choices in a two column grid left one tile sitting alone beside a
   hole, which is the "weird wide gap" Eden was looking at. On a phone they
   become one per row, image left and words right, so every row is the same
   shape and the whole step is readable without scrolling past a 293px tall
   photograph three times. Three across once there is room for it. */
.tiles.materials{grid-template-columns:1fr}
.tiles.materials .tile.vis .face{flex-direction:row;align-items:stretch}
.tiles.materials .tile.vis .media{
  flex:0 0 116px;aspect-ratio:1/1;border-bottom:0;border-right:1px solid var(--line);
}
.tiles.materials .tile.vis .face em{
  padding:var(--s3) var(--s4);display:flex;flex-direction:column;justify-content:center;
}
.tiles.materials .tile.full .face{flex-direction:row}

/* Dot points, because Eden is right that people read them and skip sentences. */
.tbul{list-style:none;margin:var(--s2) 0 0;padding:0;display:grid;gap:2px}
.tbul li{
  position:relative;padding-left:14px;font-size:12.5px;line-height:1.45;
  color:var(--ink-2);font-weight:400;
}
.tbul li::before{
  content:"";position:absolute;left:3px;top:.55em;
  width:4px;height:4px;border-radius:50%;background:var(--bronze);
}

/* Unused since 2026-09-13: the premium tile carries a board photo now.
   The swatch path stays in tiles() and here in case a material ever needs
   colours instead of a picture. */
.media.swatch{display:flex;flex-direction:column;background:var(--card)}
.media.swatch i{flex:1;display:block}

@media(min-width:640px){
  .tiles.materials{grid-template-columns:repeat(3,1fr)}
  .tiles.materials .tile.vis .face{flex-direction:column}
  .tiles.materials .tile.vis .media{
    flex:none;aspect-ratio:4/3;border-right:0;border-bottom:1px solid var(--line);
  }
  .tiles.materials .tile.full{grid-column:1 / -1}
}

/* The band's heading was 18px against a 17.94px body, so the thing meant to
   lead was the same size as what it was leading. In the band the heading is
   the feature and the quote is the support, which is the reverse of a card. */
.proofband .rtitle{
  font-size:clamp(23px,5.8vw,31px);max-width:20ch;
  margin-bottom:var(--s4);
}
.proofband .proofstrip p{font-size:clamp(15px,3.7vw,17px);font-weight:400}

/* Review photos one per row on a phone. Two across made each of them 153px,
   which is too small to see what you are being shown, and Eden read the result
   as an image that had been cut out rather than a photo of a deck. Full card
   width is 308px on a 390px phone. Two across only once the card is wide
   enough to carry it. */
.rphotos{grid-template-columns:1fr}
@media(min-width:760px){
  .rphotos{grid-template-columns:1fr 1fr}
  .rphotos-one{grid-template-columns:1fr}
}

/* THE 6PX. .cardstars carries margin-bottom:var(--s3) from when it was a block
   of stars sitting above a quote. Inside a flex row with align-items:center
   that margin is part of the box, so the stars' visual centre sat half the
   margin above the text's. Measured at exactly 6px, which is half of 12. */
.ratedas .cardstars{margin-bottom:0;align-items:center;line-height:0}
.ratedas{line-height:1}
.ratedas span[aria-hidden]{line-height:1;display:inline-block}

/* The Google mark hard right in a chip. rwho has to be allowed to absorb the
   free space, or margin-left:auto on the mark has nothing to push against. */
.rchip a{align-items:center}
.rchip .rwho{flex:1 1 auto;min-width:0}
.rchip .gmark-sm{margin-left:auto;flex:none}

/* The chip's link was computing as display:block, so as a flex item of the
   chip it shrank to its content, 118px inside a 356px row, and margin-left:auto
   on the Google mark had no free space to push against. The chip is a plain
   block now and the link is the flex row that fills it. */
.rchip{display:block;padding:0}
.rchip a{
  display:flex;align-items:center;gap:var(--s3);width:100%;
  padding:var(--s3) var(--s4);
}

/* The captions under the five big shots. Eden asked for these bigger and I
   missed it the first time. */
.shot figcaption{padding:var(--s7) var(--s5) var(--s4)}
.shot figcaption span{font-size:clamp(15px,2.6vw,19px);font-weight:600}


/* The permit table's header row was var(--sand), and the table sits inside a
   section whose ground is var(--sand), so on a white table the header read as
   a hole punched back through to the page behind it. A dark header row is
   already the page's language for a label: it is what .tagm does on the before
   and after. */
/* Eden, 2026-09-15: he does not want plain text sitting on a dark ground.
   The header keeps the dark row, because that is already this page's
   language for a label, and the two column labels became pills on it, which
   is the same glass-label device used on the before and after. */
.phead{background:var(--ink)}
.prow.phead>span{color:#fff;padding-top:var(--s3);padding-bottom:var(--s3)}
.prow.phead>span+span{
  background:rgba(255,255,255,.08);border-left-color:rgba(255,255,255,.18);
}
.prow.phead>span+span+span{background:rgba(197,168,98,.16)}
.prow.phead>span+span{border-left-color:rgba(255,255,255,.18)}

/* The repeated CTA. Same button, same words, same destination as the sticky
   bar: this is ONE call to action appearing more than once, not a second one,
   which is what canon forbids. It earns its place mainly on desktop, where the
   sticky bar does not exist and a visitor who has just read twenty four
   reviews would otherwise have to scroll hunting for the way back. */
.ctaback{text-align:center;padding:var(--s8) 0 0}
.ctaback .btn{min-width:min(320px,100%)}
.ctaback .cta-sub{
  display:block;margin-top:var(--s3);font-size:13px;color:var(--ink-3);
}
@media(min-width:760px){
  /* On a phone the sticky bar is already on screen, so an inline button right
     above it is the same button twice in one glance. */
  .ctaback{padding-top:var(--s9)}
}
