:root {
  --ink: #14201c;
  --ink-2: #33423d;
  --muted: #6a736f;
  --faint: #98a09c;
  --rule: #e4e0d7;
  --rule-soft: #efece5;
  --bg: #fbfaf7;
  --panel: #fff;
  --accent: #14375a;
  --accent-hi: #1d4c77;
  --accent-2: #c9a24d;
  --soft: #eaf0f6;
  --warn: #8a5f18;
  --warn-bg: #fdf6e6;
  --bad: #96401d;
  --bad-bg: #fceee8;
  --r: 12px;
  --r-lg: 16px;
  --shadow: 0 1px 2px rgba(20,32,28,.05), 0 4px 16px rgba(20,32,28,.05);
  --shadow-lift: 0 2px 4px rgba(20,32,28,.06), 0 12px 32px rgba(20,32,28,.09);
  --measure: 68ch;
}

* { box-sizing: border-box; }

body {
  margin: 0;
  font: 16px/1.6 -apple-system, BlinkMacSystemFont, "Segoe UI", Helvetica, Arial, sans-serif;
  color: var(--ink);
  background: var(--bg);
  -webkit-font-smoothing: antialiased;
}
a { color: var(--accent); }

/* ---------------------------------------------------------------- chrome */
header.site {
  display: flex; flex-wrap: wrap; align-items: center; gap: .4rem 1.1rem;
  padding: .95rem 1.5rem; border-bottom: 1px solid var(--rule); background: var(--panel);
}
.brand {
  display: inline-flex; align-items: center; gap: .5rem;
  text-decoration: none; color: var(--accent);
}
.logo { width: 26px; height: 26px; flex: none; }
.wordmark { font-weight: 800; font-size: 1.22rem; letter-spacing: -.025em; color: var(--ink); }
.tag { color: var(--muted); font-size: .87rem; }

main { max-width: 800px; margin: 0 auto; padding: 2.2rem 1.5rem 4rem; }
section.wide { max-width: 1000px; margin: 0 auto; }

footer.site { border-top: 1px solid var(--rule); padding: 1.5rem; background: var(--panel); }
footer.site p { max-width: 800px; margin: 0 auto; color: var(--muted); font-size: .8rem; }

/* ------------------------------------------------------------- typography */
h1 { font-size: 1.95rem; line-height: 1.22; letter-spacing: -.02em; margin: 0 0 .5rem; }
h2 { font-size: 1.16rem; letter-spacing: -.01em; margin: 2.2rem 0 .6rem; }
h3 { font-size: 1rem; margin: 0; }
.lede { font-size: 1.07rem; color: #3a4441; }
.eyebrow { font-size: .78rem; text-transform: uppercase; letter-spacing: .07em;
  color: var(--muted); margin: 0 0 .25rem; }
.fine, .hint, .dim { color: var(--muted); font-size: .85rem; }
.hint { margin: .3rem 0 0; }
.legal { margin-top: 2.5rem; padding-top: 1.2rem; border-top: 1px solid var(--rule); }
.bullets li { margin-bottom: .42rem; }
.bullets.flags li::marker { color: var(--warn); }
.bullets.numbered li { margin-bottom: .55rem; }

/* -------------------------------------------------------------- home page */
.hero { margin-bottom: 2rem; }
.cards { display: grid; gap: 1rem; grid-template-columns: repeat(auto-fit, minmax(250px, 1fr)); }
.card {
  display: block; padding: 1.35rem; background: var(--panel); border: 1px solid var(--rule);
  border-radius: var(--r); text-decoration: none; color: inherit; transition: .16s;
}
a.card:hover { border-color: var(--accent); transform: translateY(-2px);
  box-shadow: 0 6px 22px rgba(22,33,29,.07); }
.card h2 { margin: 0 0 .4rem; font-size: 1.08rem; }
.card p { margin: 0 0 .85rem; color: var(--muted); font-size: .9rem; }
.card-soon { opacity: .62; }
.go { color: var(--accent); font-weight: 600; font-size: .9rem; }
.go.dim { color: var(--muted); }
.how ol { padding-left: 1.15rem; }
.how li { margin-bottom: .55rem; }

/* ------------------------------------------------------------------ forms */
.form fieldset {
  border: 1px solid var(--rule); border-radius: var(--r);
  padding: 1.3rem 1.4rem; margin: 0 0 1.3rem; background: var(--panel);
}
legend { font-weight: 700; padding: 0 .45rem; display: flex; align-items: center; gap: .5rem; }
.step {
  display: inline-grid; place-items: center; width: 1.45rem; height: 1.45rem;
  background: var(--accent); color: #fff; border-radius: 50%; font-size: .78rem;
}
.field { margin-bottom: 1.05rem; }
.field > label { display: block; font-weight: 600; font-size: .93rem; margin-bottom: .32rem; }
.req { color: var(--warn); }
.grid2 { display: grid; gap: 0 1rem; grid-template-columns: repeat(auto-fit, minmax(220px, 1fr)); }
input[type=text], input[type=email], input[type=tel], input[type=number], select, textarea {
  width: 100%; padding: .62rem .7rem; font: inherit; font-size: .95rem;
  border: 1px solid var(--rule); border-radius: 8px; background: #fff; color: var(--ink);
}
input:focus, select:focus, textarea:focus, .dropzone:focus-visible {
  outline: 3px solid var(--soft); border-color: var(--accent);
}
.checks { display: flex; flex-wrap: wrap; gap: .45rem; }
.check {
  display: inline-flex; align-items: center; gap: .4rem; font-size: .9rem;
  padding: .34rem .7rem; border: 1px solid var(--rule); border-radius: 20px;
  background: #fff; cursor: pointer;
}
.check:has(input:checked) { border-color: var(--accent); background: var(--soft); font-weight: 600; }

button, .primary {
  display: inline-block; padding: .72rem 1.35rem; font: inherit; font-weight: 600;
  background: var(--accent); color: #fff; border: 0; border-radius: 8px;
  cursor: pointer; text-decoration: none; text-align: center;
}
button:hover, .primary:hover { filter: brightness(1.09); }
button:disabled { opacity: .72; cursor: progress; filter: none; }
.primary.big { width: 100%; padding: .9rem 1.4rem; font-size: 1.02rem; }
.primary.ghost { background: transparent; color: var(--accent); border: 1.5px solid var(--accent); }
.working { position: relative; }
.form.inline { display: flex; flex-wrap: wrap; align-items: end; gap: .6rem; margin: 1rem 0; }
.form.inline label { font-size: .85rem; font-weight: 600; }
.form.inline input { width: auto; min-width: 220px; }

/* ------------------------------------------------------------ file upload */
.dropzone {
  border: 2px dashed var(--rule); border-radius: var(--r); padding: 2rem 1rem;
  text-align: center; cursor: pointer; background: #fcfbf9; transition: .15s;
}
.dropzone:hover, .dropzone.over { border-color: var(--accent); background: var(--soft); }
.dz-icon { width: 30px; height: 30px; color: var(--accent); margin-bottom: .3rem; }
.dz-main { margin: 0; font-weight: 600; font-size: .96rem; }
.dz-main .link { color: var(--accent); text-decoration: underline; }
.dz-sub { margin: .2rem 0 0; color: var(--muted); font-size: .82rem; }

.thumbs { display: grid; gap: .6rem; margin-top: .9rem;
  grid-template-columns: repeat(auto-fill, minmax(108px, 1fr)); }
.thumb { position: relative; margin: 0; border-radius: 9px; overflow: hidden;
  border: 1px solid var(--rule); background: #fff; }
.thumb img { display: block; width: 100%; height: 92px; object-fit: cover; }
.thumb figcaption { font-size: .7rem; color: var(--muted); padding: .2rem .4rem; }
.thumb-x {
  position: absolute; top: 4px; right: 4px; width: 22px; height: 22px; padding: 0;
  border-radius: 50%; background: rgba(22,33,29,.72); color: #fff;
  font-size: 15px; line-height: 1; display: grid; place-items: center;
}
.thumbs.static .thumb img { height: 120px; }

.shotlist { margin-top: 1.1rem; padding: .9rem 1.1rem; background: var(--soft);
  border-radius: 9px; font-size: .88rem; }
.shotlist-h { margin: 0 0 .45rem; font-weight: 600; }
.shotlist ol { margin: 0; padding-left: 1.15rem; }
.shotlist li { margin-bottom: .28rem; }

/* --------------------------------------------------------- estimate: head */
.est-head { display: flex; flex-wrap: wrap; gap: 1rem; align-items: start;
  justify-content: space-between; margin-bottom: 1.2rem; }
.est-head h1 { font-size: 1.6rem; margin: 0 0 .2rem; }
.conf-badge { font-size: .76rem; font-weight: 700; text-transform: uppercase;
  letter-spacing: .05em; padding: .3rem .65rem; border-radius: 20px; background: var(--soft);
  color: var(--accent); white-space: nowrap; }
.conf-badge.conf-low { background: var(--warn-bg); color: var(--warn); }

.rangebox {
  display: flex; flex-wrap: wrap; gap: 1.6rem 2.5rem;
  background: var(--soft); border-radius: var(--r); padding: 1.4rem 1.6rem;
}
.rangebox .label { display: block; font-size: .76rem; text-transform: uppercase;
  letter-spacing: .06em; color: var(--muted); margin-bottom: .1rem; }
.range { font-size: 1.4rem; font-weight: 700; letter-spacing: -.02em; }
.likely { font-size: 2.15rem; font-weight: 800; color: var(--accent); letter-spacing: -.03em;
  display: block; line-height: 1.1; }

.rangebar { margin: 1.1rem 0 .3rem; }
.rb-track { position: relative; height: 8px; border-radius: 5px;
  background: linear-gradient(90deg, var(--accent-2), var(--accent)); }
.rb-dot { position: absolute; top: 50%; width: 17px; height: 17px; border-radius: 50%;
  background: #fff; border: 4px solid var(--accent); transform: translate(-50%, -50%); }
.rb-ends { display: flex; justify-content: space-between; font-size: .78rem;
  color: var(--muted); margin-top: .35rem; }
.conf { font-size: .89rem; color: var(--muted); }
.conf-low { color: var(--warn); }

/* ------------------------------------------------------ estimate: paywall */
.paywall { margin: 2rem 0; padding: 1.5rem 1.6rem; background: var(--panel);
  border: 1.5px solid var(--accent); border-radius: var(--r); }
.paywall h2 { margin-top: 0; }
.preview-blur { filter: blur(4px); opacity: .5; user-select: none; pointer-events: none;
  margin-bottom: 1rem; }
.pv-row { display: flex; justify-content: space-between; padding: .42rem 0;
  border-bottom: 1px solid var(--rule); font-size: .9rem; }
.ticks { list-style: none; padding: 0; margin: 0 0 1.2rem; }
.ticks li { padding-left: 1.5rem; position: relative; margin-bottom: .42rem; font-size: .93rem; }
.ticks li::before { content: "✓"; position: absolute; left: 0; color: var(--accent); font-weight: 700; }

/* -------------------------------------------------- estimate: composition */
.compbar { display: flex; height: 34px; border-radius: 8px; overflow: hidden; margin: .5rem 0 .7rem; }
.cb-seg { height: 100%; }
.cb-mat { background: var(--accent); }
.cb-lab { background: var(--accent-2); }
.cb-op  { background: #c9b896; }
.cb-con { background: #ddd6c8; }
.complegend { display: flex; flex-wrap: wrap; gap: .5rem 1.3rem; font-size: .86rem; }
.cl { display: inline-flex; align-items: center; gap: .38rem; }
.cl i { width: 11px; height: 11px; border-radius: 3px; display: inline-block; }

/* -------------------------------------------------- estimate: line items */
.phase { border: 1px solid var(--rule); border-radius: var(--r); background: var(--panel);
  margin-bottom: .9rem; overflow: hidden; }
.phase-head { display: flex; justify-content: space-between; align-items: center;
  padding: .75rem 1.05rem; background: #f6f4f0; border-bottom: 1px solid var(--rule); }
.phase-total { font-weight: 700; }
table.lines { width: 100%; border-collapse: collapse; font-size: .88rem; }
table.lines th { text-align: right; font-size: .72rem; text-transform: uppercase;
  letter-spacing: .05em; color: var(--muted); padding: .5rem 1.05rem; font-weight: 600; }
table.lines th:first-child { text-align: left; }
table.lines td { padding: .6rem 1.05rem; border-top: 1px solid var(--rule); vertical-align: top; }
table.lines .num { text-align: right; white-space: nowrap; }
table.lines .strong { font-weight: 700; }
.ln-desc { display: block; }
.ln-why { display: block; color: var(--muted); font-size: .8rem; margin-top: .15rem; }

table.totals { width: 100%; max-width: 460px; margin: 1.1rem 0 0 auto;
  border-collapse: collapse; font-size: .92rem; }
table.totals td { padding: .42rem 0; }
table.totals .num { text-align: right; }
table.totals .grand td { border-top: 2px solid var(--ink); font-weight: 800;
  font-size: 1.12rem; padding-top: .6rem; }

table.answers { width: 100%; border-collapse: collapse; font-size: .89rem; }
table.answers th { text-align: left; font-weight: 600; color: var(--muted); width: 38%;
  padding: .45rem .6rem .45rem 0; border-bottom: 1px solid var(--rule); vertical-align: top; }
table.answers td { padding: .45rem 0; border-bottom: 1px solid var(--rule); }

.actions { display: flex; flex-wrap: wrap; align-items: center; gap: .8rem;
  margin: 2rem 0 0; padding-top: 1.3rem; border-top: 1px solid var(--rule); }

/* ------------------------------------------------------------- notices */
.notice { padding: .9rem 1.1rem; background: #fff8e8; border: 1px solid #e6d3a3;
  border-radius: var(--r); margin-bottom: 1.4rem; font-size: .93rem; }
.warnbox { background: var(--warn-bg); border-color: #e0b3a0; }

/* --------------------------------------------------------------- admin */
table.grid, table.mini { width: 100%; border-collapse: collapse; margin: .8rem 0 1.4rem; font-size: .88rem; }
table.grid th, table.grid td, table.mini th, table.mini td {
  text-align: left; padding: .5rem .55rem; border-bottom: 1px solid var(--rule); vertical-align: top; }
table.grid th { font-size: .76rem; text-transform: uppercase; letter-spacing: .04em; color: var(--muted); }
.row-review { background: #fff8e8; }
.pill { display: inline-block; padding: .12rem .55rem; border-radius: 20px;
  font-size: .73rem; font-weight: 600; background: #eee; }
.pill-needs_review { background: #fdf0cf; }
.pill-approved { background: var(--soft); color: var(--accent); }
.pill-paid { background: #d9ede4; color: var(--accent); }
.pill-failed { background: var(--warn-bg); color: var(--warn); }
.calib { background: var(--panel); border: 1px solid var(--rule);
  border-radius: var(--r); padding: 1rem 1.2rem; margin-bottom: 1.5rem; }
.warn { color: var(--warn); font-weight: 600; }
.ok { color: var(--accent); font-weight: 600; }
.mono { font-family: ui-monospace, SFMono-Regular, Menlo, monospace; font-size: .8rem; }

@media (max-width: 620px) {
  main { padding: 1.5rem 1rem 3rem; }
  h1 { font-size: 1.5rem; }
  .est-head h1 { font-size: 1.28rem; }
  .likely { font-size: 1.8rem; }
  .rangebox { gap: 1rem 1.6rem; padding: 1.1rem 1.2rem; }
  .phase-head, table.lines td, table.lines th { padding-left: .7rem; padding-right: .7rem; }
  table.lines { font-size: .82rem; }
  .tag { display: none; }
}

/* ------------------------------------------------------- service picker */
.proptypes { display: grid; gap: .6rem; grid-template-columns: repeat(auto-fit, minmax(200px, 1fr)); }
.proptype, .svc {
  display: flex; gap: .6rem; align-items: flex-start; cursor: pointer;
  padding: .8rem .9rem; border: 1.5px solid var(--rule); border-radius: 10px;
  background: #fff; transition: .13s;
}
.proptype:hover, .svc:hover { border-color: var(--accent-2); }
.proptype:has(input:checked), .svc:has(input:checked) {
  border-color: var(--accent); background: var(--soft);
}
.proptype input, .svc input { margin-top: .18rem; flex: none; accent-color: var(--accent); }
.pt-body, .svc-body { display: flex; flex-direction: column; gap: .1rem; }
.pt-body strong, .svc-body strong { font-size: .95rem; }
.pt-body em, .svc-body em { font-style: normal; color: var(--muted); font-size: .82rem; line-height: 1.4; }

.svc-cat { margin-bottom: 1.4rem; }
.svc-cat[hidden] { display: none; }
.svc-cat-h { font-size: .78rem; text-transform: uppercase; letter-spacing: .07em;
  color: var(--muted); margin: 0 0 .55rem; font-weight: 700; }
.svc-grid { display: grid; gap: .6rem; grid-template-columns: repeat(auto-fit, minmax(240px, 1fr)); }

.sticky-bar {
  position: sticky; bottom: 0; z-index: 5;
  display: flex; align-items: center; justify-content: space-between; gap: 1rem;
  padding: .85rem 1rem; margin: 0 -1rem;
  background: rgba(250,249,246,.94); backdrop-filter: blur(8px);
  border-top: 1px solid var(--rule);
}
.count { font-weight: 600; font-size: .92rem; }

/* ------------------------------------------------------- working overlay */
.overlay {
  position: fixed; inset: 0; z-index: 50; display: grid; place-items: center;
  padding: 1.5rem; background: rgba(250,249,246,.93); backdrop-filter: blur(6px);
}
.ov-card { max-width: 400px; text-align: center; }
.ov-spin {
  width: 42px; height: 42px; margin: 0 auto 1.1rem; border-radius: 50%;
  border: 3px solid var(--soft); border-top-color: var(--accent);
  animation: ov-rot .9s linear infinite;
}
@keyframes ov-rot { to { transform: rotate(360deg); } }
.ov-stage { font-size: 1.06rem; font-weight: 600; margin: 0 0 .9rem; min-height: 1.6em; }
.ov-bar { height: 5px; border-radius: 4px; background: var(--soft); overflow: hidden; }
.ov-bar i {
  display: block; width: 38%; height: 100%; border-radius: 4px;
  background: linear-gradient(90deg, var(--accent-2), var(--accent));
  animation: ov-slide 1.5s ease-in-out infinite;
}
@keyframes ov-slide {
  0% { transform: translateX(-105%); }
  100% { transform: translateX(280%); }
}
.ov-note { color: var(--muted); font-size: .85rem; margin: .9rem 0 0; line-height: 1.5; }

@media (prefers-reduced-motion: reduce) {
  .ov-spin, .ov-bar i { animation: none; }
  .ov-bar i { width: 100%; }
}


/* ----------------------------------------------------- guided shot capture */
.shot-progress { display: flex; align-items: center; gap: .8rem; margin-bottom: 1.1rem; }
.sp-bar { flex: 1; height: 7px; border-radius: 5px; background: var(--soft); overflow: hidden; }
.sp-bar i { display: block; height: 100%; border-radius: 5px; background: var(--accent-2);
  transition: width .3s ease; }
.sp-bar i.sp-full { background: var(--accent); }
.sp-text { font-size: .82rem; font-weight: 600; color: var(--muted); white-space: nowrap; }

.shots { display: grid; gap: .8rem; grid-template-columns: repeat(auto-fit, minmax(268px, 1fr)); }
.shot {
  border: 1.5px solid var(--rule); border-radius: var(--r); padding: .95rem 1rem;
  background: #fff; transition: .15s;
}
.shot-req { border-left: 3px solid var(--accent-2); }
.shot-done { border-color: var(--accent); background: var(--soft); }
.shot-done.shot-req { border-left-color: var(--accent); }
.shot-head { display: flex; align-items: baseline; justify-content: space-between;
  gap: .5rem; margin-bottom: .3rem; }
.shot-title { font-weight: 700; font-size: .93rem; line-height: 1.3; }
.badge-req, .badge-opt { font-size: .66rem; font-weight: 700; text-transform: uppercase;
  letter-spacing: .05em; padding: .15rem .45rem; border-radius: 20px; white-space: nowrap; }
.badge-req { background: var(--accent); color: #fff; }
.badge-opt { background: var(--soft); color: var(--muted); }
.shot-why { margin: 0 0 .3rem; font-size: .82rem; color: var(--muted); line-height: 1.45; }
.shot-hint { margin: 0 0 .5rem; font-size: .78rem; color: var(--muted);
  padding-left: .6rem; border-left: 2px solid var(--rule); font-style: italic; }
.shot-slot:not(:empty) { display: grid; gap: .45rem; margin: .6rem 0;
  grid-template-columns: repeat(auto-fill, minmax(74px, 1fr)); }
.shot-slot .thumb img, .shot-slot .thumb video {
  display: block; width: 100%; height: 66px; object-fit: cover; background: #000;
}
.thumb-tag { position: absolute; bottom: 20px; left: 4px; font-size: .6rem; font-weight: 700;
  text-transform: uppercase; letter-spacing: .05em; background: rgba(22,33,29,.78);
  color: #fff; padding: .1rem .3rem; border-radius: 3px; }
.shot-add {
  display: flex; align-items: center; justify-content: center; gap: .45rem;
  padding: .55rem .7rem; border: 1.5px dashed var(--rule); border-radius: 8px;
  font-size: .86rem; font-weight: 600; color: var(--accent); cursor: pointer;
  background: #fcfbf9; transition: .13s;
}
.shot-add:hover { border-color: var(--accent); background: var(--soft); }
.shot-add svg { width: 17px; height: 17px; flex: none; }
.missing-shots { margin-bottom: 1rem; }

@media (max-width: 620px) { .shots { grid-template-columns: 1fr; } }

/* ------------------------------------------------- captured shots, on the estimate */
.shotgrid { display: grid; gap: .7rem; margin-top: .8rem;
  grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); }
.shotcard { margin: 0; border: 1px solid var(--rule); border-radius: 9px;
  overflow: hidden; background: #fff; }
.shotcard img { display: block; width: 100%; height: 108px; object-fit: cover; background: #000; }
.shotcard figcaption { padding: .4rem .55rem; font-size: .74rem; line-height: 1.35;
  color: var(--muted); }
.kind-tag { display: inline-block; margin-left: .25rem; font-size: .62rem; font-weight: 700;
  text-transform: uppercase; letter-spacing: .04em; background: var(--soft);
  color: var(--accent); padding: .06rem .3rem; border-radius: 3px; }

/* =============================================================================
   POLISH LAYER
   Overrides the base above. A homeowner deciding whether to hand us $30,000 of
   their project reads polish as competence — so this is typography, rhythm and
   restraint, not decoration.
   ========================================================================== */

body { font-size: 16px; -moz-osx-font-smoothing: grayscale; }
p { max-width: var(--measure); }
a:hover { color: var(--accent-hi); }
::selection { background: var(--accent-2); color: var(--ink); }
::placeholder { color: var(--faint); }

/* Sticky header — the brand stays with you through a long form. */
header.site { position: sticky; top: 0; z-index: 20;
  background: rgba(255,255,255,.88); backdrop-filter: saturate(1.4) blur(10px);
  padding: .9rem clamp(1rem, 4vw, 2rem); }
main { max-width: 820px; padding: clamp(1.5rem, 4vw, 3rem) clamp(1rem, 4vw, 2rem) 5rem; }
footer.site { padding: 2rem clamp(1rem, 4vw, 2rem); }
footer.site p { color: var(--faint); font-size: .79rem; max-width: 820px; }

/* Fluid type: reads well on a phone in someone's kitchen and on a desktop. */
h1 { font-size: clamp(1.7rem, 4.2vw, 2.35rem); line-height: 1.15;
  letter-spacing: -.032em; font-weight: 800; }
h2 { font-size: clamp(1.08rem, 2.2vw, 1.25rem); letter-spacing: -.018em;
  margin: 2.4rem 0 .65rem; font-weight: 700; }
.lede { font-size: clamp(1rem, 2.1vw, 1.1rem); color: var(--ink-2); line-height: 1.62; }
.eyebrow { letter-spacing: .1em; color: var(--faint); font-weight: 700; font-size: .74rem; }
.fine, .hint { color: var(--muted); }
.legal { color: var(--faint); margin-top: 3rem; }
.bullets { max-width: var(--measure); }
.bullets.flags li::marker { color: var(--bad); }

/* Numbers are money — align them. */
.range, .likely, .phase-total, .rb-ends,
table.lines .num, table.totals { font-variant-numeric: tabular-nums; }

/* Depth instead of hairlines everywhere. */
.form fieldset, .phase, .shotcard { box-shadow: var(--shadow); }
a.card:hover { border-color: var(--accent-2); box-shadow: var(--shadow-lift); }
.proptype:hover, .svc:hover { box-shadow: var(--shadow); }
.proptype:has(input:checked), .svc:has(input:checked) {
  box-shadow: inset 0 0 0 1px var(--accent); }

button, .primary { font-weight: 700; border-radius: 9px;
  box-shadow: 0 1px 2px rgba(20,32,28,.12);
  transition: background .14s, transform .08s, box-shadow .14s; }
button:hover, .primary:hover { background: var(--accent-hi); box-shadow: var(--shadow-lift);
  filter: none; }
button:active, .primary:active { transform: translateY(1px); }
button:disabled { opacity: .55; cursor: not-allowed; transform: none; box-shadow: none; }
.primary.ghost:hover { background: var(--soft); }
input:focus, select:focus, textarea:focus, .dropzone:focus-visible {
  outline: none; border-color: var(--accent); box-shadow: 0 0 0 3px var(--soft); }

/* The number itself — the moment the whole product is judged on. */
.rangebox { background: linear-gradient(160deg, var(--soft), #f7faf8);
  border: 1px solid var(--rule-soft); border-radius: var(--r-lg);
  padding: 1.5rem 1.7rem; }
.rangebox .label { letter-spacing: .09em; font-weight: 700; font-size: .72rem; }
.likely { font-size: clamp(1.9rem, 5vw, 2.3rem); letter-spacing: -.035em; font-weight: 800; }
.rb-dot { box-shadow: 0 1px 4px rgba(20,32,28,.2); }
.paywall { border-radius: var(--r-lg); box-shadow: var(--shadow-lift); padding: 1.6rem 1.7rem; }
.compbar { box-shadow: inset 0 0 0 1px rgba(20,32,28,.05); border-radius: 9px; }
.cb-op { background: #cbbb96; }
.cb-con { background: #e0d9c9; }
.phase-head { background: #f8f6f2; }
table.lines td { border-top: 1px solid var(--rule-soft); }
.ln-why { color: var(--faint); line-height: 1.45; }

.conf-badge { letter-spacing: .08em; font-weight: 800; padding: .32rem .7rem; }
.badge-req, .badge-opt { font-weight: 800; letter-spacing: .07em; }
.badge-opt { background: var(--rule-soft); color: var(--faint); }
.shot-req { border-left: 0; box-shadow: inset 3px 0 0 var(--accent-2); }
.shot-done.shot-req { box-shadow: inset 3px 0 0 var(--accent); }
.sp-bar i { transition: width .35s cubic-bezier(.4,0,.2,1); }

/* ---------------------------------------------------------------- trust */
.trustbar { display: flex; flex-wrap: wrap; gap: .5rem 1.7rem; margin: 1.7rem 0 0;
  padding-top: 1.3rem; border-top: 1px solid var(--rule-soft); }
.trustbar span { display: inline-flex; align-items: center; gap: .42rem;
  font-size: .84rem; color: var(--muted); }
.trustbar svg { width: 15px; height: 15px; color: var(--accent); flex: none; }

.paysafe { display: flex; flex-wrap: wrap; gap: .4rem 1.3rem; margin-top: 1rem;
  font-size: .78rem; color: var(--faint); }
.paysafe span { display: inline-flex; align-items: center; gap: .32rem; }
.paysafe svg { width: 13px; height: 13px; }

section.centre { text-align: center; }
section.centre p { margin-left: auto; margin-right: auto; }
.spin-lg { width: 44px; height: 44px; margin: 1.6rem auto; border-radius: 50%;
  border: 3px solid var(--soft); border-top-color: var(--accent);
  animation: ov-rot .9s linear infinite; }

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: .01ms !important; transition-duration: .01ms !important;
  }
  .ov-bar i { width: 100%; }
}
.hint-block { margin-bottom: 1rem; }
.sp-bar i { width: 0; }

/* ============================================================ hero drawing
   A floor plan that draws itself.

   Every stroke in the SVG carries pathLength="1", which normalises paths of
   very different real lengths to a single unit. That lets one dash rule drive
   the whole drawing at an even rate — no measuring each path, and no
   JavaScript, which the CSP would refuse anyway.

   It draws once, on arrival, and then holds still. A loop was the wrong
   instinct here: a set of drawings is a finished thing, and something that
   keeps redrawing itself reads as decoration rather than as work.
   ------------------------------------------------------------------------ */

.hero {
  display: grid;
  grid-template-columns: minmax(0, 1.02fr) minmax(0, .98fr);
  gap: clamp(1.5rem, 4vw, 3.25rem);
  align-items: center;
  padding: clamp(1.5rem, 3.5vw, 2.75rem) 0 clamp(.75rem, 2vw, 1.5rem);
}

.hero-copy h1 { margin-top: 0; }

/* Block, not flex. With both the still image and the canvas as flex items the
   image's intrinsic width squeezed the canvas towards zero, and a canvas with
   no width can never size its buffer or draw — an invisible scene with nothing
   in any console to explain it. Only one of the two is ever displayed, so they
   never needed to share a row. */
.hero-art { position: relative; display: block; }

/* The canvas the house is drawn on. A fixed aspect keeps the hero from
   jumping while WebGL starts up. */
.house-still {
  display: block; width: 100%; max-width: 540px; height: auto; margin-inline: auto;
}

/* The `hidden` attribute sets display:none from the browser's own stylesheet,
   which any author `display` rule beats — so `.house3d { display: block }`
   quietly un-hid the canvas. Both then sat side by side in the flex row and
   shoved the picture off to the left. Restate it here so hidden means hidden. */
.house-still[hidden], .house3d[hidden] { display: none; }

.house3d {
  display: block;
  margin-inline: auto;
  width: 100%;
  max-width: 540px;
  aspect-ratio: 5 / 4;
  height: auto;
}

/* The contact shadow is drawn in WebGL now, from the house's own
   geometry, so it turns as the house turns. */

/* The plan now sits under the words, full width, as a drawing on the page
   rather than an illustration beside a headline. */
.plan-strip {
  margin: clamp(.5rem, 2vw, 1.25rem) 0 clamp(1rem, 2.5vw, 1.75rem);
  padding-top: clamp(1rem, 2.5vw, 1.5rem);
  border-top: 1px solid var(--rule-soft);
  display: flex;
  justify-content: center;
}

.bp { width: 100%; max-width: 620px; height: auto; overflow: visible; }

/* --- the ink ------------------------------------------------------------ */
.bp path, .bp circle { stroke-linecap: round; stroke-linejoin: round; fill: none; }

.bp-grid path      { stroke: var(--rule-soft); stroke-width: 1; }
.bp-wall path      { stroke: var(--accent);    stroke-width: 3.2; }
.bp-wall .bp-wall-in { stroke-width: 1.4; opacity: .5; }
.bp-door path      { stroke: var(--accent-hi); stroke-width: 1.6; }
.bp-win path       { stroke: var(--accent);    stroke-width: 2.4; }
.bp-fix path,
.bp-fix circle     { stroke: var(--muted);     stroke-width: 1.5; }
.bp-dim path       { stroke: var(--faint);     stroke-width: 1.2; }

.bp-text text {
  font: 600 10px/1 -apple-system, BlinkMacSystemFont, "Segoe UI", Helvetica, Arial, sans-serif;
  fill: var(--muted);
  letter-spacing: .08em;
}
.bp-text .bp-room { font-size: 10.5px; letter-spacing: .16em; fill: var(--accent); }
.bp-text .bp-note { font-size: 8.5px; letter-spacing: .22em; fill: var(--faint); }

/* --- the drawing itself ------------------------------------------------- */
.bp path, .bp circle {
  stroke-dasharray: 1;
  stroke-dashoffset: 1;
  animation: draw 1s cubic-bezier(.4,.05,.2,1) forwards;
}
@keyframes draw { to { stroke-dashoffset: 0; } }

/* Trades arrive in the order a drawing is actually built up. */
.bp-grid path { animation-duration: 1.4s; animation-delay: .05s; opacity: .9; }
.bp-wall path { animation-delay: .45s; }
.bp-wall.bp-2 path { animation-delay: 1.05s; }
.bp-win  path { animation-delay: 1.35s; }
.bp-door path { animation-delay: 1.5s; }
.bp-fix  path,
.bp-fix  circle { animation-delay: 1.75s; animation-duration: .8s; }
.bp-dim  path { animation-delay: 2.15s; animation-duration: .6s; }
.bp-dim.bp-2 path { animation-delay: 2.35s; }

/* Text can't be drawn, so it is set down once its line is in place. */
.bp-text text { opacity: 0; animation: ink-in .5s ease-out 2.55s forwards; }
@keyframes ink-in { to { opacity: 1; } }

@media (max-width: 860px) {
  .hero { grid-template-columns: 1fr; gap: .75rem; padding-top: .75rem; }
  .hero-art { order: -1; }
  .house3d, .house-still { max-width: 360px; margin: 0 auto; }
  .bp { max-width: 100%; }
  .plan-strip { margin-top: .25rem; }
}

/* A finished drawing, with none of the performance. */
@media (prefers-reduced-motion: reduce) {
  .bp path, .bp circle { stroke-dashoffset: 0; animation: none; }
  .bp-text text { opacity: 1; animation: none; }
}

/* ========================================================== polish pass
   The page worked but read like a form with a heading on top. These rules
   give it depth and a sense of craft without touching the flow: the customer
   still lands on the same question, in the same place, one scroll shorter.
   -------------------------------------------------------------------- */

/* A warm field of light behind the hero, so the page isn't a flat sheet. */
body {
  background:
    radial-gradient(1100px 520px at 78% -8%, #eef4f1 0%, transparent 62%),
    radial-gradient(760px 420px at 5% 4%, #f7f4ec 0%, transparent 58%),
    var(--bg);
  /* Deliberately not background-attachment: fixed. A fixed gradient repaints
     the whole viewport on every scroll frame; iOS Safari in particular drops
     frames and sometimes paints nothing at all. The gradient lives at the top
     of the page anyway, which is the only place it is doing any work. */
  background-repeat: no-repeat;
}

h1 { font-size: clamp(2rem, 4.6vw, 2.9rem); letter-spacing: -.033em; }
.hero .lede { max-width: 46ch; }

/* The hero was leaving a canyon of empty space above the first question. */
.hero { padding-bottom: clamp(.75rem, 2vw, 1.5rem); }
.hero + .trustbar { margin-top: .6rem; padding-top: 1.1rem; }

/* Trust marks as pills — they were floating text an eye skated over. */
.trustbar { gap: .55rem .7rem; border-top: 0; }
.trustbar span {
  padding: .42rem .8rem;
  background: var(--panel);
  border: 1px solid var(--rule-soft);
  border-radius: 999px;
  box-shadow: 0 1px 2px rgba(20,32,28,.04);
}

/* Question cards: lift them off the page and mark the active one. */
fieldset {
  background: var(--panel);
  border: 1px solid var(--rule-soft) !important;
  border-radius: var(--r-lg);
  box-shadow: var(--shadow);
  transition: box-shadow .25s ease;
}
fieldset:focus-within { box-shadow: var(--shadow-lift); }

.step { box-shadow: 0 2px 6px rgba(20,55,90,.32); }

/* Choice tiles: a real hover, and a selected state you can see at a glance. */
.proptype, .svc {
  transition: border-color .16s ease, box-shadow .16s ease, transform .16s ease;
}
.proptype:hover, .svc:hover {
  border-color: var(--accent-2);
  box-shadow: 0 2px 4px rgba(20,32,28,.05), 0 8px 20px rgba(20,32,28,.07);
  transform: translateY(-1px);
}
.proptype:has(input:checked), .svc:has(input:checked) {
  box-shadow: 0 0 0 1px var(--accent), 0 6px 18px rgba(20,55,90,.14);
}

/* The button that carries the whole funnel. */
button, .primary {
  border-radius: 10px;
  box-shadow: 0 1px 2px rgba(20,32,28,.12), 0 6px 16px rgba(20,55,90,.18);
  transition: transform .14s ease, box-shadow .18s ease, filter .18s ease;
}
button:hover:not(:disabled), .primary:hover {
  transform: translateY(-1px);
  box-shadow: 0 2px 4px rgba(20,32,28,.14), 0 10px 26px rgba(20,55,90,.24);
}
button:active:not(:disabled) { transform: translateY(0); }
button:disabled { box-shadow: none; }

/* Keyboard users get a visible, branded focus ring rather than the default. */
:where(a, button, input, select, textarea, summary):focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
  border-radius: 6px;
}

.sticky-bar { box-shadow: 0 -6px 20px rgba(20,32,28,.06); }

/* The header carries the brand; give it the same lift as the cards. */
header.site { box-shadow: 0 1px 0 rgba(20,32,28,.04), 0 4px 18px rgba(20,32,28,.03); }

@media (prefers-reduced-motion: reduce) {
  .proptype, .svc, button, .primary { transition: none; }
  .proptype:hover, .svc:hover, button:hover, .primary:hover { transform: none; }
}

/* ===================================================== typographic voice
   Headings and figures in a serif; everything you interact with stays sans.

   This is the one idea worth taking from the Stitch pass. A serif reads as a
   document — a survey, a valuation, something a professional prepared — and
   that is exactly the claim this product makes. All-sans read like a web form,
   which is what it looked like.

   System faces only, no webfont: the CSP forbids external font hosts, and a
   downloaded font would delay the headline on a phone for no gain. Every
   platform in this stack ships something good.
   -------------------------------------------------------------------- */

:root {
  --serif: ui-serif, "Iowan Old Style", "Palatino Linotype", Palatino,
           "Book Antiqua", Georgia, "Times New Roman", serif;
}

h1, h2, .est-head h1, .money-big, .range-fig {
  font-family: var(--serif);
  font-weight: 600;
  letter-spacing: -.015em;
}

h1 { line-height: 1.12; }

/* Small-caps labels above a figure, the way a valuation sets them. */
.eyebrow {
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Helvetica, Arial, sans-serif;
  text-transform: uppercase;
  letter-spacing: .12em;
  font-size: .7rem;
  font-weight: 700;
}

/* Money is the thing the customer came for — set it like it matters, and in
   tabular figures so the digits line up down a column of line items. */
.money, .amount, td.num, .line-amt {
  font-variant-numeric: tabular-nums;
}


/* The brand lockup, supplied as artwork rather than drawn in CSS. Sized by
   height so it keeps its proportions wherever the header lands. */
.brand .lockup { height: 30px; width: auto; display: block; }
@media (max-width: 620px) { .brand .lockup { height: 25px; } }

/* ====================================================== landing & the choice
   The front door holds one idea and one button; the choice page holds two
   doors. Both were one crowded page before, which meant a first-time visitor
   met a twenty-item checklist before knowing what the thing was.
   -------------------------------------------------------------------- */

.start-cta { margin: clamp(1.5rem, 4vw, 2.5rem) 0 1rem; text-align: center; }
.start-cta .primary.big { display: inline-block; width: auto; min-width: 260px; }
.start-cta .fine { margin-top: .7rem; }

.centred { text-align: center; }
.choose-h1 { text-align: center; margin-top: .5rem; }
.back-link { margin-top: 1.75rem; }

/* The figures. Fixed aspect so the page doesn't jump while WebGL starts. */
.choose-art {
  position: relative;
  display: block;                 /* not flex: see .hero-art below */
  margin: clamp(.5rem, 2vw, 1.25rem) auto 0;
}
.pair-still, .pair3d {
  display: block; width: 100%; max-width: 620px; height: auto;
  margin-inline: auto;
  aspect-ratio: 15 / 8;
}
.pair-still[hidden], .pair3d[hidden] { display: none; }

/* Two doors, side by side, equal weight. */
.doors {
  display: grid; grid-template-columns: 1fr 1fr;
  gap: clamp(.75rem, 2vw, 1.25rem);
  margin: clamp(1.25rem, 3vw, 2rem) 0 .5rem;
}

.door {
  display: flex; flex-direction: column; gap: .35rem;
  padding: clamp(1.1rem, 2.5vw, 1.6rem);
  background: var(--panel);
  border: 1px solid var(--rule);
  border-radius: var(--r-lg);
  box-shadow: var(--shadow);
  text-decoration: none; color: var(--ink);
  transition: transform .16s ease, box-shadow .18s ease, border-color .16s ease;
}
.door:hover { transform: translateY(-2px); border-color: var(--accent-2); box-shadow: var(--shadow-lift); }
.door-tag {
  font-size: .72rem; font-weight: 700; letter-spacing: .12em;
  text-transform: uppercase; color: var(--accent);
}
.door strong { font-size: 1.05rem; line-height: 1.3; }
.door em { font-style: normal; color: var(--muted); font-size: .88rem; line-height: 1.5; }
.door-go { margin-top: .5rem; font-weight: 600; color: var(--accent); font-size: .92rem; }
.door-primary { border-color: var(--accent); }
.door-primary .door-tag { color: var(--accent-hi); }

@media (max-width: 620px) {
  .doors { grid-template-columns: 1fr; }
  .pair-still, .pair3d { max-width: 100%; }
  .start-cta .primary.big { width: 100%; }
}

@media (prefers-reduced-motion: reduce) {
  .door, .door:hover { transition: none; transform: none; }
}
