/* ==========================================================================
   DISTILO
   --------------------------------------------------------------------------
   One stylesheet, no build step. Root-relative paths, clean URLs.

   Distilo's brand (brand book in "Distilo - FULL BRANDING"): the logo on
   its black background. Black, white and true grays carry the page; the
   lime green is the only colour and is used sparingly (the logo, the main
   button, the current page, a handful of marks), never as body text and
   never on white. Headlines are a condensed bold in capitals.

   The secondary colours are used the way the brand book uses them, as
   solid surfaces: the dark gray as the footer and the homepage's problem
   panel (the business card's charcoal back), the light gray as a third
   section ground (.on-gray), and the soft lime as one full colour block
   per page, the closing call to action.

   Sections flip between the dark ground and a paper ground by adding
   .on-paper, which re-points the semantic variables below. Every
   component reads those semantic variables, never the raw palette, so
   the same markup works on either ground without a second rule.
   ========================================================================== */

:root{
  /* raw palette */
  --ink:        #000000;
  --ink-2:      #0E0E0E;
  --ink-3:      #383838;   /* brand secondary dark gray */
  --gray:       #E3E3E3;   /* brand secondary light gray */
  --paper:      #FFFFFF;
  --paper-2:    #F5F5F5;
  --cream:      #FFFFFF;
  --green:      #6EF600;   /* brand primary */
  --green-soft: #9BF651;   /* brand secondary, hovers */
  --green-wash: rgba(110,246,0,.10);

  /* semantic, re-pointed by .on-paper */
  --bg:        var(--ink);
  --bg-raise:  var(--ink-2);
  --bg-sink:   #000000;
  --fg:        var(--cream);
  --fg-soft:   rgba(255,255,255,.68);
  --fg-faint:  rgba(255,255,255,.56);
  --rule:      rgba(255,255,255,.14);
  --rule-firm: var(--ink-3);
  --accent:    var(--green);
  --accent-fg: #000000;
  --accent-wash: var(--green-wash);
  /* Hover fill for outline buttons. */
  --hover-fill: var(--ink-3);
  /* Status: lime for good, soft pink to watch, rose for bad (rose instead
     of red sits beside the brand lime and stays apart for color blindness). */
  --good:  var(--green);
  --watch: #FF9EB5;
  --bad:   #FF3B6B;

  /* Free stand-ins for the brand's faces: Barlow Condensed for Akko Pro
     Bold Condensed (headlines), Inter for Helvetica Now (copy). */
  --display: "Barlow Condensed", "Arial Narrow", sans-serif;
  --body:    "Inter", "Helvetica Neue", Helvetica, Arial, sans-serif;
  --mono:    "JetBrains Mono", ui-monospace, SFMono-Regular, Menlo, monospace;

  --wrap: 1180px;
  --gut:  clamp(20px, 5vw, 44px);
  --r:    4px;
  --r-lg: 6px;
  --nav-h: 68px;
}

.on-paper{
  --bg:        var(--paper);
  --bg-raise:  var(--paper-2);
  --bg-sink:   #E3E3E3;
  --fg:        #000000;
  --fg-soft:   rgba(0,0,0,.68);
  --fg-faint:  rgba(0,0,0,.60);
  --rule:      rgba(0,0,0,.13);
  --rule-firm: rgba(0,0,0,.30);
  /* Lime is unreadable on white, so on paper the accent is ink. */
  --accent:    #000000;
  --accent-fg: #FFFFFF;
  --accent-wash: rgba(0,0,0,.05);
  --hover-fill: var(--gray);
  --good:  #357A00;
  --watch: #C2416A;
  --bad:   #D6194F;
}

/* The brand's light gray as a third ground, so a page can run black,
   white and gray. Add alongside .on-paper; everything else is the same. */
.on-paper.on-gray{
  --bg:        var(--gray);
  --bg-raise:  #FFFFFF;
  --bg-sink:   #D4D4D4;
  --rule:      rgba(0,0,0,.14);
  --hover-fill: #FFFFFF;
}

*,*::before,*::after{ box-sizing:border-box; }

html{
  color-scheme: dark;
  scroll-behavior: smooth;
  /* every in-page anchor has to clear the fixed masthead */
  scroll-padding-top: calc(var(--nav-h) + 16px);
  -webkit-text-size-adjust: 100%;
}

body{
  margin:0;
  background: var(--ink);
  color: var(--cream);
  font-family: var(--body);
  font-size: 17px;
  line-height: 1.65;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  overflow-x: hidden;
}

img,svg{ max-width:100%; display:block; }
a{ color: inherit; }

h1,h2,h3,h4{
  font-family: var(--display);
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0;
  line-height: 1.02;
  margin: 0;
  text-wrap: balance;
}
h1{ font-size: clamp(2.55rem, 7vw, 5rem); }
h2{ font-size: clamp(1.95rem, 4.4vw, 3.15rem); }
h3{ font-size: clamp(1.25rem, 2.4vw, 1.65rem); }
/* Small headings read as copy, not as headlines. */
h4{ font-family: var(--body); text-transform:none; font-size: 1.02rem; font-weight:600; letter-spacing:-0.01em; }
p{ margin: 0; }

::selection{ background: var(--green); color:#000; }

:focus-visible{
  outline: 2px solid var(--accent);
  outline-offset: 3px;
  border-radius: 2px;
}

.skip-link{
  position:absolute; left:-9999px; top:0; z-index:200;
  background: var(--green); color:#000;
  padding:.7rem 1.1rem; font-weight:600; font-size:.9rem;
  text-decoration:none; border-radius:0 0 var(--r) 0;
}
.skip-link:focus{ left:0; }

@media (prefers-reduced-motion: reduce){
  html{ scroll-behavior:auto; }
  *,*::before,*::after{
    animation-duration:.01ms !important;
    animation-iteration-count:1 !important;
    transition-duration:.01ms !important;
  }
}

/* ---- layout primitives -------------------------------------------------- */

.wrap{ width:100%; max-width: var(--wrap); margin-inline:auto; padding-inline: var(--gut); }
.wrap--narrow{ max-width: 780px; }

.section{
  background: var(--bg);
  color: var(--fg);
  padding: clamp(4.5rem, 9vw, 7.5rem) 0;
  position: relative;
}
.section--tight{ padding: clamp(3rem, 6vw, 5rem) 0; }
.section--edge{ border-top:1px solid var(--rule); }

/* Section heading block. No kicker line above it: the heading carries
   itself, and a lede paragraph under it does the rest. */
.head{ max-width: 46ch; margin-bottom: clamp(2.25rem, 4vw, 3.5rem); }
.head--wide{ max-width: 62ch; }
.head p{ color: var(--fg-soft); margin-top: 1rem; font-size: 1.06rem; }
.head--split{ max-width:none; display:grid; gap:1.25rem; align-items:end; }
@media (min-width: 880px){
  .head--split{ grid-template-columns: minmax(0,1.15fr) minmax(0,1fr); gap:3rem; }
  .head--split p{ margin-top:0; padding-bottom:.35rem; }
}

.lede{ font-size: clamp(1.05rem, 1.6vw, 1.22rem); line-height:1.7; color: var(--fg-soft); }
.prose p + p{ margin-top: 1.05rem; }
.prose{ color: var(--fg-soft); }
.prose strong{ color: var(--fg); font-weight:600; }

.accent{ color: var(--accent); }
em.accent{ font-style: normal; }

/* A small monospace meta line. Used for numbers, keys and field labels,
   never as a kicker sitting above a heading. */
.meta{
  font-family: var(--mono);
  font-size: .72rem;
  font-weight: 500;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--fg-faint);
}

/* ---- buttons ------------------------------------------------------------ */

.btn{
  display:inline-flex; align-items:center; justify-content:center; gap:.55rem;
  font-family: var(--body);
  font-size: .96rem; font-weight:600; line-height:1;
  padding: .95rem 1.5rem;
  border-radius: var(--r);
  border:1px solid transparent;
  text-decoration:none; cursor:pointer;
  transition: background .18s ease, color .18s ease, border-color .18s ease, transform .18s ease;
}
.btn svg{ width:17px; height:17px; flex:none; }
.btn--solid{ background: var(--accent); color: var(--accent-fg); }
.btn--solid:hover{ background: var(--green-soft); color:#000; }
.on-paper .btn--solid:hover{ background:#383838; color:#fff; }
.btn--line{ border-color: var(--rule-firm); color: var(--fg); }
.btn--line:hover{ border-color: var(--fg); background: var(--hover-fill); }
.btn--sm{ padding:.62rem 1.1rem; font-size:.875rem; }
.btn:active{ transform: translateY(1px); }

/* An inline text link that reads as a link without a permanent underline
   fighting the type. */
.tlink{
  display:inline-flex; align-items:center; gap:.45rem;
  font-weight:600; font-size:.94rem; color: var(--accent);
  text-decoration:none;
  border-bottom:1px solid transparent;
  padding-bottom:1px;
  transition: border-color .18s ease;
}
.tlink svg{ width:15px; height:15px; transition: transform .2s ease; }
.tlink:hover{ border-bottom-color: currentColor; }
.tlink:hover svg{ transform: translateX(3px); }

/* ---- masthead ----------------------------------------------------------- */
/* Structure and the two Safari fixes come from component-library's
   navbar.html: prefixed sticky (some Safari builds silently ignore the
   unprefixed value), and position:fixed rather than sticky below the
   breakpoint (iOS Safari measures a sticky offset against a stale
   viewport height mid address-bar animation and parks the bar off
   screen until you scroll the other way). */

.masthead{
  position: -webkit-sticky;
  position: sticky;
  top:0; z-index:100;
  background: rgba(0,0,0,.82);
  backdrop-filter: blur(14px) saturate(140%);
  -webkit-backdrop-filter: blur(14px) saturate(140%);
  border-bottom:1px solid var(--rule);
}
.masthead__row{
  display:flex; align-items:center; justify-content:space-between; gap:1.25rem;
  min-height: var(--nav-h);
  padding-block:.75rem;
}
/* The brand logo (assets/logo.svg: green mark, white wordmark), drawn for
   the black ground. */
.wordmark{ display:inline-flex; align-items:center; flex:none; }
.wordmark img{ height:30px; width:auto; }

.masthead__nav{ display:none; align-items:center; gap:1.6rem; }
.masthead__nav a{
  font-size:.94rem; font-weight:500; color: rgba(255,255,255,.70);
  text-decoration:none; padding-block:.3rem;
  border-bottom:2px solid transparent;
  transition: color .18s ease;
}
.masthead__nav a:hover{ color: var(--cream); }
.masthead__nav a[aria-current="page"]{ color: var(--cream); border-bottom-color: var(--green); }

.masthead__actions{ display:flex; align-items:center; gap:.6rem; }
.masthead__toggle{
  display:inline-flex; align-items:center; justify-content:center;
  width:42px; height:42px; margin-right:-8px;
  background:none; border:none; color: var(--cream); cursor:pointer;
}

/* Mobile panel: the grid-row trick from navbar.html. It animates to
   whatever height the content actually is, stays in normal flow (so it
   can never render in the wrong place), and carries max-height
   alongside grid-template-rows because the grid track alone is not a
   hard clip mid-transition and content can otherwise poke past the
   collapsing edge for a frame. */
.masthead__panel{
  display:grid; grid-template-rows:0fr;
  max-height:0; opacity:0; visibility:hidden; pointer-events:none;
  overflow:hidden;
  transition: grid-template-rows .38s cubic-bezier(.16,1,.3,1),
              max-height .38s cubic-bezier(.16,1,.3,1),
              opacity .2s ease, visibility 0s linear .38s;
}
.masthead.is-open .masthead__panel{
  grid-template-rows:1fr; max-height:30rem;
  opacity:1; visibility:visible; pointer-events:auto;
  transition: grid-template-rows .38s cubic-bezier(.16,1,.3,1),
              max-height .38s cubic-bezier(.16,1,.3,1),
              opacity .25s ease .05s, visibility 0s linear 0s;
}
.masthead__panel-inner{
  display:flex; flex-direction:column;
  overflow-x:hidden; overflow-y:auto; -webkit-overflow-scrolling:touch;
  min-height:0;
  padding: .25rem var(--gut) 1.4rem;
  border-top:1px solid var(--rule);
  border-bottom:1px solid var(--rule-firm);
  background: var(--ink);
  box-shadow: 0 22px 34px -18px rgba(0,0,0,.9);
}
.masthead__panel-inner a{
  font-family: var(--display); font-weight:700; font-size:1.5rem;
  text-transform:uppercase; letter-spacing:.01em; color: rgba(255,255,255,.78);
  text-decoration:none; padding:.85rem 0;
  border-bottom:1px solid var(--rule);
}
.masthead__panel-inner a[aria-current="page"]{ color: var(--green); }
.masthead__panel-inner .btn{ margin-top:1.35rem; font-family: var(--body); font-size:1rem; }

@media (min-width: 960px){
  .masthead__nav{ display:flex; }
  .masthead__toggle{ display:none; }
  .masthead__panel{ display:none; }
}
@media (max-width: 959px){
  .masthead{ position: fixed; left:0; right:0; }
  .masthead__actions .btn{ display:none; }
}

/* ---- hero --------------------------------------------------------------- */

.hero{
  position:relative;
  padding-top: clamp(4rem, 9vw, 7rem);
  padding-bottom: clamp(3rem, 6vw, 5rem);
  overflow:hidden;
  border-bottom:1px solid var(--rule);
}
.hero > .wrap{ position:relative; }
.hero__grid{ display:grid; gap: clamp(2.5rem, 5vw, 4.5rem); align-items:start; }
@media (min-width: 980px){
  .hero__grid{ grid-template-columns: minmax(0, 1.35fr) minmax(320px, .85fr); }
}
.hero h1{ line-height:1.12; }
.hero h1 em{ font-style:normal; color: var(--green); }
.hero__lede{ margin-top: 1.6rem; max-width: 48ch; }
.hero__actions{ display:flex; flex-wrap:wrap; gap:.75rem; margin-top: 2.1rem; }
@media (max-width: 420px){
  .hero__actions{ display:grid; }
  .hero__actions .btn{ width:100%; }
}

/* The spec sheet standing in for the usual hero illustration. Real
   information, set like a datasheet, instead of a decorative mockup. */
.spec{
  border:1px solid var(--rule);
  border-radius: var(--r-lg);
  background: linear-gradient(180deg, rgba(255,255,255,.035), transparent 60%);
}
.spec__row{
  display:grid; grid-template-columns: 8.5rem minmax(0,1fr);
  gap:1rem; align-items:baseline;
  padding: 1rem 1.25rem;
  border-bottom:1px solid var(--rule);
}
.spec__row:last-child{ border-bottom:none; }
.spec__row dt{ font-family: var(--mono); font-size:.68rem; letter-spacing:.1em; text-transform:uppercase; color: var(--fg-faint); }
.spec__row dd{ margin:0; font-size:.94rem; color: var(--fg); }
@media (max-width: 460px){
  .spec__row{ grid-template-columns:1fr; gap:.2rem; padding:.8rem 1.05rem; }
}

/* Hairline fact strip under the hero. */
.facts{
  display:grid; gap:1.75rem;
  margin-top: clamp(3rem, 5vw, 4.25rem);
  padding-top: 1.9rem;
  border-top:1px solid var(--rule);
}
@media (min-width: 620px){ .facts{ grid-template-columns: repeat(3, 1fr); gap:2.5rem; } }
.facts__n{ font-family: var(--display); font-weight:700; font-size: clamp(2.1rem,4vw,2.8rem); line-height:1; }
.facts__n span{ color: var(--green); }
.facts__l{ margin-top:.45rem; font-size:.88rem; color: var(--fg-faint); }

/* Shorter banner for inner pages. */
.pagehead{
  padding: clamp(3.5rem, 7vw, 5.5rem) 0 clamp(2.5rem, 5vw, 4rem);
  border-bottom:1px solid var(--rule);
  position:relative; overflow:hidden;
}
.pagehead > .wrap{ position:relative; }
.pagehead .lede{ margin-top:1.35rem; max-width:56ch; }

/* ---- service index ------------------------------------------------------- */
/* Ruled rows rather than a grid of identical cards, and deliberately not
   numbered: an ordinal in front of every item is a tell, and the rules
   already group the list. The title carries it instead, set large enough
   to read as a statement rather than a table cell. */

.index{ border-top:1px solid var(--rule-firm); }
.index__row{
  display:grid; gap:.5rem 3rem;
  padding: 1.75rem 0;
  border-bottom:1px solid var(--rule);
  position:relative;
  transition: padding-left .25s ease;
}
@media (min-width: 800px){
  .index__row{
    grid-template-columns: minmax(0, .85fr) minmax(0, 1.15fr);
    align-items:baseline;
    padding-block: 2.4rem;
  }
}
.index__row h3{
  font-family: var(--display); font-weight:700;
  font-size: clamp(1.45rem, 2.9vw, 2.15rem);
}
.index__row p{ color: var(--fg-soft); font-size:.98rem; max-width: 54ch; }
.index__row::after{
  content:""; position:absolute; left:0; bottom:-1px; height:1px; width:0;
  background: var(--accent);
  transition: width .35s cubic-bezier(.16,1,.3,1);
}
.index__row:hover::after{ width:100%; }
@media (min-width: 800px){ .index__row:hover{ padding-left:.75rem; } }

/* ---- pitch (mockup-first) ------------------------------------------------ */

.pitch{ display:grid; gap: clamp(2rem, 4vw, 3.5rem); align-items:start; }
@media (min-width: 900px){ .pitch{ grid-template-columns: minmax(0,1fr) minmax(0,1fr); gap:5rem; } }
.pitch__body p{ font-size:1.06rem; }
.pitch__body p + p{ margin-top:1.1rem; }

/* Ruled list with a small tick, used where a card grid would be lazy. */
.ticks{ display:flex; flex-direction:column; }
.ticks li{
  display:grid; grid-template-columns: 1.35rem minmax(0,1fr); gap:.85rem;
  padding: 1.05rem 0;
  border-bottom:1px solid var(--rule);
  font-size:.98rem; color: var(--fg-soft);
}
.ticks li:first-child{ border-top:1px solid var(--rule); }
.ticks svg{ width:17px; height:17px; margin-top:.32rem; color: var(--accent); flex:none; }
.ticks strong{ color: var(--fg); font-weight:600; }
.ticks ul, .ticks{ list-style:none; margin:0; padding:0; }

/* ---- process ------------------------------------------------------------ */
/* A connected rail rather than five boxes. On desktop the line runs
   horizontally through the markers; on mobile it runs down the left. */

.steps{ list-style:none; margin:0; padding:0; display:grid; gap:0; }
@media (min-width: 900px){
  .steps{ grid-template-columns: repeat(5, 1fr); gap: 1.75rem; }
}
.step{ position:relative; padding: 0 0 1.7rem 2.25rem; }
.step:last-child{ padding-bottom:0; }
.step::before{
  content:""; position:absolute; left:5px; top:1.35rem; bottom:-.4rem; width:1px;
  background: var(--rule);
}
.step:last-child::before{ display:none; }
.step__dot{
  position:absolute; left:0; top:.42rem;
  width:11px; height:11px; border-radius:50%;
  border:1px solid var(--accent); background: var(--bg);
}
.step.is-first .step__dot{ background: var(--accent); }
.step h3{ font-size:1.22rem; letter-spacing:.01em; margin-bottom:.4rem; }
.step p{ font-size:.92rem; color: var(--fg-soft); line-height:1.6; }
@media (min-width: 900px){
  .step{ padding: 1.9rem 0 0 0; }
  .step::before{ left:11px; right:-1.75rem; top:5px; bottom:auto; width:auto; height:1px; }
  .step:last-child::before{ display:none; }
  .step__dot{ top:0; left:0; }
}

/* ---- audience: ruled inline list, not a fourth card grid ----------------- */

.who{ display:grid; gap:0; border-top:1px solid var(--rule); }
@media (min-width: 760px){ .who{ grid-template-columns:1fr 1fr; column-gap:3.5rem; } }
.who__item{ padding:1.4rem 0; border-bottom:1px solid var(--rule); }
.who__item h3{ font-size:1.18rem; letter-spacing:.01em; margin-bottom:.3rem; }
.who__item p{ font-size:.92rem; color: var(--fg-soft); line-height:1.6; }

/* ---- spec table (what's included) --------------------------------------- */

.table{ width:100%; border-collapse:collapse; font-size:.95rem; }
.table th, .table td{ text-align:left; padding:1rem .85rem; border-bottom:1px solid var(--rule); vertical-align:top; }
.table th{
  font-family: var(--mono); font-weight:500; font-size:.7rem;
  letter-spacing:.1em; text-transform:uppercase; color: var(--fg-faint);
  border-bottom:1px solid var(--rule-firm);
}
.table td:first-child{ font-weight:600; color: var(--fg); white-space:nowrap; }
.table td:last-child{ color: var(--fg-soft); }
.table tr:last-child td{ border-bottom:none; }
.table__scroll{ overflow-x:auto; -webkit-overflow-scrolling:touch; }
.table__scroll table{ min-width: 34rem; }

/* ---- FAQ (native details, no JS) ---------------------------------------- */

.faq{ border-top:1px solid var(--rule-firm); }
.faq details{ border-bottom:1px solid var(--rule); }
.faq summary{
  display:flex; align-items:flex-start; justify-content:space-between; gap:1.5rem;
  padding:1.35rem 0; cursor:pointer; list-style:none;
  font-family: var(--body); font-weight:600; font-size:1.06rem; letter-spacing:-0.01em;
  color: var(--fg);
}
.faq summary::-webkit-details-marker{ display:none; }
.faq summary::after{
  content:""; flex:none; width:15px; height:15px; margin-top:.42rem;
  background: currentColor; color: var(--accent);
  -webkit-mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M11 5h2v14h-2z'/%3E%3Cpath d='M5 11h14v2H5z'/%3E%3C/svg%3E") center/contain no-repeat;
  mask: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24'%3E%3Cpath d='M11 5h2v14h-2z'/%3E%3Cpath d='M5 11h14v2H5z'/%3E%3C/svg%3E") center/contain no-repeat;
  transition: transform .4s cubic-bezier(.4,0,.2,1);
}
/* .is-closing is set by site.js while the answer animates shut, so the icon
   turns back with it rather than when it finishes. */
.faq details[open]:not(.is-closing) summary::after{ transform: rotate(45deg); }
@media (prefers-reduced-motion: reduce){ .faq summary::after{ transition:none; } }
.faq details p{ padding-bottom:1.35rem; color: var(--fg-soft); font-size:.98rem; max-width:70ch; }
.faq details p + p{ padding-bottom:1.35rem; margin-top:-.5rem; }

/* ---- contact ------------------------------------------------------------ */

.contact{ display:grid; gap: clamp(2.5rem, 5vw, 4rem); align-items:start; }
@media (min-width: 900px){ .contact{ grid-template-columns: minmax(0,.85fr) minmax(0,1.15fr); gap:4.5rem; } }

.iconrow{
  display:flex; align-items:flex-start; gap:.75rem;
  padding:.95rem 0; border-bottom:1px solid var(--rule);
  font-size:.96rem; color: var(--fg-soft); text-decoration:none;
}
.iconrow:first-of-type{ border-top:1px solid var(--rule); }
.iconrow svg{ width:18px; height:18px; margin-top:.2rem; color: var(--fg-faint); flex:none; transition: color .18s ease; }
a.iconrow:hover{ color: var(--fg); }
a.iconrow:hover svg{ color: var(--green); }
.on-paper a.iconrow:hover svg{ color: #000; }

.form{
  background: var(--bg-raise);
  border:1px solid var(--rule);
  border-radius: var(--r-lg);
  padding: clamp(1.35rem, 3vw, 2.25rem);
}
.field{ display:flex; flex-direction:column; gap:.45rem; margin-bottom:1rem; }
.field label{
  font-family: var(--mono); font-size:.68rem; font-weight:500;
  letter-spacing:.1em; text-transform:uppercase; color: var(--fg-faint);
}
.field input, .field select, .field textarea{
  width:100%; font-family: var(--body); font-size:1rem; line-height:1.5;
  color: var(--fg); background: var(--bg);
  border:1px solid var(--rule); border-radius: var(--r);
  padding:.78rem .95rem;
  outline:none;
  transition: border-color .18s ease, box-shadow .18s ease;
  appearance:none; -webkit-appearance:none;
}
.field input::placeholder, .field textarea::placeholder{ color: var(--fg-faint); }
.field input:focus, .field select:focus, .field textarea:focus{
  border-color: var(--accent);
  box-shadow: 0 0 0 3px var(--accent-wash);
}
.field textarea{ resize:vertical; min-height:8.5rem; }
.field select{
  padding-right:2.6rem; cursor:pointer;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8'%3E%3Cpath fill='%23A3A3A3' d='M1 1.5 6 6.5l5-5'/%3E%3C/svg%3E");
  background-repeat:no-repeat; background-position:right 1rem center;
}
.field select option{ background: var(--ink-2); color: var(--cream); }
.field-pair{ display:grid; gap:0 1rem; }
@media (min-width: 480px){ .field-pair{ grid-template-columns:1fr 1fr; } }
.form .btn{ width:100%; margin-top:.4rem; }
.form__status{ margin-top:.9rem; font-size:.9rem; color: var(--fg-soft); text-align:center; }
.form__status:empty{ display:none; }
.form__status[data-tone="watch"]{ color: var(--watch); }
.form__status[data-tone="bad"]{ color: var(--bad); }
.form__done{ padding:.25rem 0; }
/* Honeypot. Off-screen rather than display:none so a bot that filters on
   display:none still sees a fillable field. */
.hp{ position:absolute; left:-9999px; width:1px; height:1px; overflow:hidden; }

/* ---- closing call to action --------------------------------------------- */

/* A block of the brand's soft lime, like the brand book's full lime pages:
   black type, a black button, and the brand pattern (the mark, repeated,
   from the brand kit) fading in from the right. */
.cta{
  position:relative; overflow:hidden;
  background: var(--green-soft);
  color: #000;
  padding: clamp(3.25rem, 6vw, 5rem) 0;
}
.cta::before{
  content:""; position:absolute; inset:0; pointer-events:none;
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='99.8 19.9 354.1 354.1' width='96' height='96'%3E%3Cg fill='black' fill-opacity='.07'%3E%3Cpath d='M 320.04 248.01 L 226.93 248.01 L 226.93 157.16 L 271.04 157.16 C 273.10 157.16 275.14 157.29 277.15 157.54 C 292.30 159.42 305.30 168.21 312.89 180.67 C 317.43 188.10 320.04 196.83 320.04 206.17 Z M 325.89 111.54 L 166.23 111.54 L 166.23 246.32 C 192.58 246.32 213.94 267.67 213.94 294.01 L 373.58 294.01 L 373.58 159.23 C 347.24 159.23 325.89 137.87 325.89 111.54'/%3E%3Cpath d='M 339.83 99.85 L 387.53 99.85 L 387.53 147.55 C 361.19 147.55 339.83 126.19 339.83 99.85'/%3E%3C/g%3E%3C/svg%3E");
  background-size:96px 96px;
  -webkit-mask-image: linear-gradient(to left, #000 0%, transparent 75%);
          mask-image: linear-gradient(to left, #000 0%, transparent 75%);
}
.cta > .wrap{ position:relative; }
.cta__inner{ display:grid; gap:1.75rem; align-items:center; }
@media (min-width: 820px){
  .cta__inner{ grid-template-columns: minmax(0,1fr) auto; gap:3rem; }
}
.cta h2{ color: #000; max-width:20ch; }
.cta p{ margin-top:.85rem; color: rgba(0,0,0,.74); font-size:1.02rem; max-width:48ch; }
.cta .btn{ background: #000; color: #fff; border-color: #000; white-space:nowrap; }
.cta .btn:hover{ background: var(--ink-3); border-color: var(--ink-3); color: #fff; }
.cta :focus-visible{ outline-color: #000; }

/* ---- footer ------------------------------------------------------------- */

/* The brand's dark gray, like the charcoal back of the business card. */
.site-footer{
  background: var(--ink-3);
  --rule: rgba(255,255,255,.16);
  padding: clamp(3rem, 5vw, 4.25rem) 0 1.75rem;
  color: var(--cream);
}
.site-footer__top{ display:grid; gap:2.5rem; padding-bottom:2.5rem; border-bottom:1px solid var(--rule); }
@media (min-width: 780px){
  .site-footer__top{ grid-template-columns: minmax(0,1.4fr) repeat(2, minmax(0,1fr)); gap:3rem; }
}
.site-footer__blurb{ margin-top:1rem; font-size:.94rem; color: rgba(255,255,255,.72); max-width:34ch; }
.site-footer .foot-h{
  font-family: var(--mono); font-weight:500; font-size:.68rem;
  letter-spacing:.12em; text-transform:uppercase;
  color: rgba(255,255,255,.7); margin:0 0 1rem;
}
.site-footer ul{ list-style:none; margin:0; padding:0; display:flex; flex-direction:column; gap:.7rem; }
.site-footer ul a{ font-size:.94rem; color: rgba(255,255,255,.82); text-decoration:none; }
.site-footer ul a:hover{ color: var(--green); }
.site-footer .iconrow{ border:none; padding:.28rem 0; font-size:.92rem; }
.site-footer .iconrow:first-of-type{ border-top:none; }
.site-footer__bottom{
  display:flex; flex-wrap:wrap; align-items:center; justify-content:space-between;
  gap:.75rem 1.5rem; padding-top:1.5rem;
}
.site-footer__bottom p{ font-size:.8rem; color: rgba(255,255,255,.7); }
.site-footer__bottom span{ font-family: var(--mono); font-size:.72rem; letter-spacing:.06em; color: rgba(255,255,255,.66); }

/* ---- scroll reveal ------------------------------------------------------- */
/* Opt-in with data-reveal. JS adds .is-in; if JS never runs, the
   no-js-safe default below leaves everything visible. */

[data-reveal]{ opacity:1; }
.js [data-reveal]{ opacity:0; transform: translateY(14px); transition: opacity .6s ease, transform .6s cubic-bezier(.16,1,.3,1); }
.js [data-reveal].is-in{ opacity:1; transform:none; }
@media (prefers-reduced-motion: reduce){
  .js [data-reveal]{ opacity:1; transform:none; }
}
@media print{
  .js [data-reveal]{ opacity:1 !important; transform:none !important; }
}

/* ---- 404 ---------------------------------------------------------------- */
.notfound{ min-height: 68vh; display:flex; align-items:center; }

/* ==========================================================================
   FLAIR
   --------------------------------------------------------------------------
   The site's visual language is already drafting-and-print: a hairline grid
   behind the hero, hairline rules everywhere, monospace keys. Everything
   below extends that rather than decorating over it, so the flourishes read
   as the same idea rather than as ornament borrowed from elsewhere.

   All of it fails open. Anything using an entrance animation animates *to*
   its resting state with animation-fill-mode: forwards, and the global
   prefers-reduced-motion rule near the top of this file shortens rather than
   cancels those animations, so a reduced-motion visitor lands on the final
   state immediately instead of on a blank page.
   ========================================================================== */

/* ---- pen stroke under the accent word -----------------------------------
   One marker stroke under the word, drawn as a filled shape: tapered at both
   ends, thickest in the middle, rising slightly to the right and running a
   little past the word's end, with a lighter second pass where the pen goes
   over itself. It inks in left to right after the headline lands. One
   stroke, not a scribble: it should read as someone underlining the word
   once, by hand.

   ONLY PUT THIS ON A SINGLE WORD. It's an inline-block, so a phrase would
   never wrap, and the stroke is sized to one word's width. */
.uline{ position:relative; display:inline-block; white-space:nowrap; }
.uline::after{
  content:""; position:absolute; pointer-events:none;
  left:-.04em; right:-.1em; bottom:-.13em; height:.27em;
  background: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 400 28' preserveAspectRatio='none'%3E%3Cpath fill='%236EF600' fill-opacity='.93' d='M5 15C60 12.5 130 11 205 10.5C275 10 340 9.5 394 8C399 8 400 13 395 13.6C340 15.5 275 17.5 205 19C130 20.5 62 21.5 9 22.4C2 22.5 1 15.6 5 15Z'/%3E%3Cpath fill='%239BF651' fill-opacity='.5' d='M30 16.5C100 13.8 180 12.6 260 12.4C318 12.2 362 11.6 386 11L387 13C352 14.6 292 15.8 232 16.8C162 17.8 96 18.8 32 19.8Z'/%3E%3C/svg%3E") no-repeat 0 0 / 100% 100%;
  transform: rotate(-.6deg); transform-origin: left center;
  clip-path: inset(0 100% 0 0);
  animation: pen-draw .65s cubic-bezier(.5,.05,.3,1) .7s forwards;
}
@keyframes pen-draw{ to{ clip-path: inset(0 0 0 0); } }

/* ---- hero entrance -------------------------------------------------------
   Low amplitude and quick. The point is that the page arrives rather than
   snaps, not that anything performs. */
@keyframes rise{ from{ opacity:0; transform: translateY(13px); } to{ opacity:1; transform:none; } }
.hero h1, .hero__lede, .hero .hero__actions, .hero .spec, .hero .facts,
.pagehead h1, .pagehead .lede, .pagehead .hero__actions{
  opacity:0;
  animation: rise .72s cubic-bezier(.16,1,.3,1) forwards;
}
.hero h1,        .pagehead h1{ animation-delay:.04s; }
.hero__lede,     .pagehead .lede{ animation-delay:.15s; }
.hero .hero__actions, .pagehead .hero__actions{ animation-delay:.26s; }
.hero .spec{ animation-delay:.34s; }
.hero .facts{ animation-delay:.44s; }

/* ---- measuring rule above each section heading ---------------------------
   Draws across as the section arrives. Defaults to full width so a page
   with no JS shows a plain static rule rather than nothing. */
.head--split{ position:relative; padding-top:1.7rem; }
.head--split::before{
  content:""; position:absolute; top:0; left:0; height:1px; width:100%;
  background: var(--rule-firm);
}

.section > .wrap{ position:relative; z-index:1; }

/* ---- micro-interactions --------------------------------------------------
   The text links already nudge their arrow on hover; the buttons should
   agree with them, and a service row should acknowledge the pointer with
   more than a rule sweep. */
.btn svg{ transition: transform .2s ease; }
.btn:hover svg{ transform: translateX(3px); }
.index__row h3{ transition: color .25s ease; }
.index__row:hover h3{ color: var(--accent); }

/* Three steps instead of five (the homepage). */
@media (min-width: 900px){
  .steps--3{ grid-template-columns: repeat(3, 1fr); }
}
/* A row whose heading is a link: the whole row is the link, and the row's
   own hover rule marks it. */
.index__row h3 a{ color:inherit; text-decoration:none; }
.index__row h3 a::before{ content:""; position:absolute; inset:0; }
.index__row h3 a:focus-visible{ outline:none; }
.index__row:has(h3 a:focus-visible){ outline:2px solid var(--accent); outline-offset:4px; }

/* The homepage's problem/fix panel as a solid charcoal card on the black
   hero. */
.hero .spec{ background: var(--ink-3); border-color: transparent; }
.hero .spec .spec__row{ border-color: rgba(255,255,255,.12); }
.hero .spec dt{ color: rgba(255,255,255,.72); }

/* ---- labels ---------------------------------------------------------------
   Labels in the body face and sentence case. Small monospace capitals on
   every label, table head and footer heading read as a template. */
.meta, .spec__row dt, .table th, .field label, .site-footer .foot-h,
.site-footer__bottom span{
  font-family: var(--body); text-transform:none; letter-spacing:0;
}
.table th{ font-size:.85rem; font-weight:600; }
.field label{ font-size:.88rem; font-weight:600; color: var(--fg); }
.site-footer .foot-h{ font-size:.9rem; font-weight:600; color:#fff; }
.site-footer__bottom span{ font-size:.8rem; }

/* ---- heading beside paragraphs --------------------------------------------
   For "how it works": a heading and a few plain paragraphs, instead of
   another row of steps. */
.split{ display:grid; gap:1.25rem 4rem; }
@media (min-width: 900px){
  .split{ grid-template-columns: minmax(0,.8fr) minmax(0,1.2fr); align-items:start; }
}
.split .prose{ font-size:1.06rem; line-height:1.7; max-width:60ch; }
.split .prose p:first-child{ color: var(--fg); }

/* The homepage hero is one column now. */
.hero__copy{ max-width: 54rem; }

/* ---- more grounds -----------------------------------------------------------
   The brand's dark gray and soft lime as whole sections, so a page can run
   through black, white, light gray, dark gray and lime instead of
   alternating two. Same idea as .on-paper: re-point the semantic variables
   and every component follows. */
.on-charcoal{
  --bg:        var(--ink-3);
  --bg-raise:  #2E2E2E;
  --bg-sink:   #2A2A2A;
  --fg:        #FFFFFF;
  --fg-soft:   rgba(255,255,255,.78);
  --fg-faint:  rgba(255,255,255,.68);
  --rule:      rgba(255,255,255,.17);
  --rule-firm: rgba(255,255,255,.36);
  --hover-fill: #454545;
}
.on-lime{
  --bg:        var(--green-soft);
  --bg-raise:  #B9F98A;
  --bg-sink:   #8BE640;
  --fg:        #000000;
  --fg-soft:   rgba(0,0,0,.78);
  --fg-faint:  rgba(0,0,0,.68);
  --rule:      rgba(0,0,0,.16);
  --rule-firm: rgba(0,0,0,.42);
  --accent:    #000000;
  --accent-fg: #FFFFFF;
  --accent-wash: rgba(0,0,0,.06);
  --hover-fill: rgba(0,0,0,.08);
  --good:      #1F5200;
}
.on-lime ::selection{ background:#000; color: var(--green-soft); }

/* Closing band variants, so the lime band isn't the same on every page:
   black with the green button (the logo on its black background), or white. */
.cta--dark{ background: var(--ink); color:#fff; }
.cta--dark::before{ filter: invert(1); }
.cta--dark h2{ color:#fff; }
.cta--dark p{ color: rgba(255,255,255,.72); }
.cta--dark .btn{ background: var(--green); color:#000; border-color: var(--green); }
.cta--dark .btn:hover{ background: var(--green-soft); border-color: var(--green-soft); color:#000; }
.cta--dark :focus-visible{ outline-color: var(--green); }
.cta--paper{ background: var(--paper); }

/* ---- two colour panels (homepage "What we build") ----------------------- */
.duo{ display:grid; gap:1rem; }
@media (min-width: 800px){ .duo{ grid-template-columns: 1fr 1fr; gap:1.25rem; } }
.duo__panel{
  display:flex; flex-direction:column; justify-content:space-between; gap:2.5rem;
  min-height: 19rem;
  padding: clamp(1.75rem, 3.5vw, 2.75rem);
  border-radius: var(--r-lg);
  background: var(--bg); color: var(--fg);
  text-decoration:none;
  transition: transform .2s ease;
}
.duo__panel:hover{ transform: translateY(-3px); }
.duo__panel h3{ font-size: clamp(2rem, 4vw, 3rem); }
.duo__panel p{ margin-top:1rem; color: var(--fg-soft); font-size:1.02rem; line-height:1.65; max-width:42ch; }
.duo__more{ display:inline-flex; align-items:center; gap:.5rem; font-weight:600; font-size:.95rem; }
.duo__more svg{ width:17px; height:17px; transition: transform .2s ease; }
.duo__panel:hover .duo__more svg{ transform: translateX(3px); }
.duo__panel.on-charcoal .duo__more{ color: var(--green); }
.duo__panel:focus-visible{ outline:2px solid #000; outline-offset:3px; }
@media (prefers-reduced-motion: reduce){ .duo__panel, .duo__more svg{ transition:none; } }

/* ---- contact form: optional fields and errors ----------------------------- */
.field__optional{ font-weight:400; color: var(--fg-faint); }
.field__error{ margin:0; font-size:.85rem; color: var(--bad); }
.field__error:empty{ display:none; }
.field input[aria-invalid="true"]{ border-color: var(--bad); }

/* ---- contact form: sent ----------------------------------------------------
   Once a message goes through, the form's card turns into the logo's black
   ground: a lime check, a white heading, and the phone number in lime. The
   green stays to the one mark and the one link. */
.form.is-done{
  background: var(--ink); border-color: var(--ink); color:#fff;
  padding: clamp(2rem, 4.5vw, 3.25rem);
}
.form__done-mark{
  display:inline-flex; align-items:center; justify-content:center;
  width:3.25rem; height:3.25rem; border-radius:50%;
  background: var(--green); color:#000; margin-bottom:1.6rem;
}
.form__done-mark svg{ width:1.6rem; height:1.6rem; }
.form__done h3{ font-size: clamp(1.75rem, 3.4vw, 2.4rem); color:#fff; margin-bottom:.75rem; }
.form__done p{ color: rgba(255,255,255,.74); font-size:1rem; line-height:1.65; max-width:36ch; }
.form__done .form__done-call{ margin-top:1.4rem; padding-top:1.4rem; border-top:1px solid rgba(255,255,255,.14); }
.form__done-call a{ color: var(--green); font-weight:600; text-decoration:none; white-space:nowrap; }
.form__done-call a:hover{ text-decoration:underline; }
.form__done:focus{ outline:none; }
/* Side by side with "What happens next", the sent card runs the full height
   of that column, its message centred. */
@media (min-width: 900px){
  .contact > .form.is-done{ align-self:stretch; display:flex; flex-direction:column; justify-content:center; }
}

/* ==========================================================================
   Motion from the brand (2026-10-20): the logo's corner tab on hover, the
   closing band's pattern drifting, and a still header between pages.
   ========================================================================== */

/* ---- corner tab ------------------------------------------------------------
   The quarter-circle from the logo's top-right corner tucks into place on
   hover, on the homepage's colour panels and on the main buttons. Each tab
   takes its button's own colour. */
.duo__panel{ position:relative; overflow:hidden; }
.duo__panel::before{
  content:""; position:absolute; top:1.1rem; right:1.1rem;
  width:1.7rem; height:1.7rem; border-bottom-left-radius:100%;
  background: var(--green);
  transform: scale(0); transform-origin: top right;
  transition: transform .4s cubic-bezier(.3,1.5,.5,1);
}
.duo__panel.on-lime::before{ background:#000; }
.duo__panel:hover::before, .duo__panel:focus-visible::before{ transform: scale(1); }

.btn{ position:relative; }
.btn--solid{ --btn-tab: var(--accent); }
.btn--line{ --btn-tab: var(--fg); }
.cta .btn{ --btn-tab: #000; }
.cta--dark .btn{ --btn-tab: var(--green); }
.btn--solid::after, .btn--line::after, .cta .btn::after{
  content:""; position:absolute; top:-.55rem; right:-.55rem;
  width:.8rem; height:.8rem; border-bottom-left-radius:100%;
  background: var(--btn-tab);
  transform: scale(0); transform-origin: top right;
  transition: transform .35s cubic-bezier(.3,1.5,.5,1);
  pointer-events:none;
}
.btn--solid:hover::after, .btn--line:hover::after, .cta .btn:hover::after,
.btn--solid:focus-visible::after, .btn--line:focus-visible::after, .cta .btn:focus-visible::after{ transform: scale(1); }

/* ---- pattern drift -------------------------------------------------------
   The logo marks behind the closing band move slowly (one tile, 96px, per
   48 seconds, so the loop is seamless). */
.cta::before{ animation: cta-drift 48s linear infinite; }
@keyframes cta-drift{ to{ background-position: 96px -96px; } }

/* ---- page changes ----------------------------------------------------------
   Moving between pages, the header stays put and the page fades over.
   Browsers without cross-page view transitions just change pages. */
@view-transition{ navigation: auto; }
.masthead{ view-transition-name: masthead; }
::view-transition-old(root){ animation: vt-out .2s ease both; }
::view-transition-new(root){ animation: vt-in .35s cubic-bezier(.2,.7,.3,1) both; }
@keyframes vt-out{ to{ opacity:0; } }
@keyframes vt-in{ from{ opacity:0; transform: translateY(10px); } }

@media (prefers-reduced-motion: reduce){
  .cta::before{ animation:none; }
  .duo__panel::before, .btn::after{ transition:none; }
  ::view-transition-group(*), ::view-transition-old(*), ::view-transition-new(*){ animation:none !important; }
}

/* ---- services on the homepage ------------------------------------------------
   The two colour panels list each service, linking to its row on that
   service's page. The panel is no longer one big link, so it doesn't lift;
   the corner tab still tucks in on hover. */
.duo__panel{ transition:none; }
.duo__panel:hover{ transform:none; }
.duo__panel h3 a{ color:inherit; text-decoration:none; }
.duo__panel h3 a:hover{ text-decoration:underline; text-decoration-thickness:.06em; text-underline-offset:.12em; }
.duo__list{ list-style:none; margin:1.6rem 0 0; padding:0; border-top:1px solid var(--rule); }
.duo__list a{
  display:flex; align-items:center; justify-content:space-between; gap:1rem;
  padding:.8rem 0; border-bottom:1px solid var(--rule);
  color: var(--fg); font-weight:600; text-decoration:none;
}
.duo__list a svg{ width:16px; height:16px; flex:none; opacity:.55; transition: transform .2s ease, opacity .2s ease; }
.duo__list a:hover svg, .duo__list a:focus-visible svg{ transform: translateX(3px); opacity:1; }
.duo__panel.on-charcoal .duo__list a:hover{ color: var(--green); }
.duo__panel.on-lime .duo__list a:hover{ text-decoration:underline; text-underline-offset:.2em; }
.duo__more{ color: var(--fg); text-decoration:none; }
.duo__more:hover{ text-decoration:underline; text-underline-offset:.2em; }
.duo__panel:focus-within::before{ transform: scale(1); }
@media (prefers-reduced-motion: reduce){ .duo__list a svg{ transition:none; } }

/* ---- drawings ---------------------------------------------------------------
   Simple line drawings in the brand colours (assets/art/): a website and a
   dashboard, each with the logo's corner tab. Decorative, so alt="". The
   bars and chart lines grow in once, inside the SVG files themselves. */
.hero__layout{ display:grid; gap:2.75rem; align-items:center; }
@media (min-width: 980px){ .hero__layout{ grid-template-columns: minmax(0,1.2fr) minmax(0,.8fr); gap:3.5rem; } }
.hero__art{ display:block; width:100%; max-width:440px; height:auto; justify-self:end; }
@media (max-width: 979px){ .hero__art{ max-width:320px; justify-self:start; } }

.pagehead__layout{ display:grid; gap:2rem; align-items:center; }
@media (min-width: 980px){ .pagehead__layout{ grid-template-columns: minmax(0,1.15fr) minmax(0,.85fr); gap:3.5rem; } }
.pagehead__art{ display:block; width:100%; max-width:400px; height:auto; justify-self:end; }
@media (max-width: 979px){ .pagehead__art{ display:none; } }

.duo__art{ display:block; width:150px; height:auto; margin-bottom:1.6rem; }

/* ---- what's included (Web design) ---------------------------------------
   A drawing of a site with numbered markers (assets/art/included.svg) and a
   matching numbered list, in place of a table. */
.features{ display:grid; gap:2.5rem; align-items:center; }
@media (min-width: 900px){ .features{ grid-template-columns: minmax(0,1.2fr) minmax(0,.8fr); gap:4rem; } }
.features__art{ display:block; width:100%; height:auto; }
.features__list{ list-style:none; margin:0; padding:0; display:grid; gap:1.4rem; }
.features__list li{ display:grid; grid-template-columns:auto minmax(0,1fr); gap:1rem; align-items:start; }
.features__n{
  display:inline-flex; align-items:center; justify-content:center;
  width:2rem; height:2rem; border-radius:50%;
  background: var(--green); color:#000; border:2px solid #000;
  font-family: var(--display); font-weight:700; font-size:1.1rem; line-height:1;
}
.features__list h3{ font-size:1.25rem; margin:.15rem 0 .3rem; }
.features__list p{ color: var(--fg-soft); font-size:.97rem; line-height:1.6; }

/* ---- add-ons (Web design) -------------------------------------------------
   Four columns of drawing, name and a line, on the black ground, separated
   by a rule rather than boxed. */
.addons{ display:grid; gap:2.5rem 2rem; border-top:1px solid var(--rule); padding-top:2.5rem; }
@media (min-width: 640px){ .addons{ grid-template-columns: repeat(2, minmax(0,1fr)); } }
@media (min-width: 1050px){ .addons{ grid-template-columns: repeat(4, minmax(0,1fr)); } }
.addon img{ display:block; width:110px; height:auto; margin-bottom:1.2rem; }
.addon h3{ font-size:1.3rem; margin-bottom:.45rem; }
.addon p{ color: var(--fg-soft); font-size:.97rem; line-height:1.6; max-width:30ch; }
/* Tiled .addons (tools on /solutions/, add-ons on /web-design/): four loose tiles, each drawing centred
   in its own tile so drawings of different widths still line up. The
   charcoal quarter circle in each corner is the logo's corner tab.
   Two across on phones rather than four tall tiles stacked. */
.addons--tiles{ grid-template-columns: repeat(2, minmax(0,1fr)); gap:.9rem; border-top:0; padding-top:0; }
@media (min-width: 1050px){ .addons--tiles{ grid-template-columns: repeat(4, minmax(0,1fr)); gap:1.1rem; } }
.addons--tiles .addon{
  position:relative; overflow:hidden; text-align:center;
  background:#1a1a1a; border:1px solid var(--rule); border-radius:12px;
  padding:2rem 1.25rem 1.75rem;
}
.addons--tiles .addon::before{
  content:""; position:absolute; top:0; right:0; width:30px; height:30px;
  background:#383838; border-bottom-left-radius:100%;
}
.addons--tiles .addon img{ margin:0 auto 1.3rem; }
.addons--tiles .addon p{ margin-inline:auto; max-width:24ch; }
@media (max-width: 639px){
  /* one per row, drawing beside the text, so a sentence of copy isn't
     squeezed into half the screen */
  .addons--tiles{ grid-template-columns:minmax(0,1fr); gap:.75rem; }
  .addons--tiles .addon{
    display:grid; grid-template-columns:84px minmax(0,1fr); grid-template-rows:auto auto;
    column-gap:1.1rem; align-items:center; text-align:left; padding:1.2rem 1.6rem 1.2rem 1.1rem;
  }
  .addons--tiles .addon::before{ width:22px; height:22px; }
  .addons--tiles .addon img{ grid-row:1 / 3; width:84px; margin:0; }
  .addons--tiles .addon h3{ font-size:1.15rem; margin-bottom:.25rem; align-self:end; }
  .addons--tiles .addon p{ font-size:.9rem; margin:0; max-width:none; align-self:start; overflow-wrap:anywhere; }
}

/* ---- taps ---------------------------------------------------------------------
   No double-tap zoom anywhere. manipulation keeps pinch-to-zoom (people need
   it) and only turns off double-tap zoom, which also removes the short delay
   Safari waits on every tap to see whether a second one is coming. It goes on
   every element, not just html, because iOS Safari does not always carry it
   down to a tap on plain text; site.js backs it up. The form fields are 1rem
   (16px) because iOS also zooms in on focus for any field smaller than that. */
*, *::before, *::after{ touch-action: manipulation; }

/* ---- menu button --------------------------------------------------------------
   One icon of three lines. Opening, the outer lines slide to the middle and
   then turn into an X while the middle one fades; closing runs the same
   steps backwards, so it never snaps between two drawings. */
.masthead__bars{ position:relative; display:block; width:22px; height:16px; }
.masthead__bars span{
  position:absolute; left:0; width:100%; height:2px; border-radius:2px; background: currentColor;
  transition: translate .18s cubic-bezier(.4,0,.2,1) .18s, rotate .18s cubic-bezier(.4,0,.2,1) 0s, opacity .12s ease .18s;
}
.masthead__bars span:nth-child(1){ top:0; }
.masthead__bars span:nth-child(2){ top:7px; }
.masthead__bars span:nth-child(3){ top:14px; }
.masthead.is-open .masthead__bars span{
  transition: translate .18s cubic-bezier(.4,0,.2,1) 0s, rotate .18s cubic-bezier(.4,0,.2,1) .18s, opacity .12s ease 0s;
}
.masthead.is-open .masthead__bars span:nth-child(1){ translate: 0 7px; rotate: 45deg; }
.masthead.is-open .masthead__bars span:nth-child(2){ opacity:0; }
.masthead.is-open .masthead__bars span:nth-child(3){ translate: 0 -7px; rotate: -45deg; }

/* The menu's links ease in one after another as the panel opens. */
@keyframes nav-item-in{ from{ opacity:0; transform: translateY(-10px); } }
.masthead.is-open .masthead__panel-inner > *{ animation: nav-item-in .5s cubic-bezier(.32,.72,0,1) .04s both; }
.masthead.is-open .masthead__panel-inner > :nth-child(2){ animation-delay:.08s; }
.masthead.is-open .masthead__panel-inner > :nth-child(3){ animation-delay:.12s; }
.masthead.is-open .masthead__panel-inner > :nth-child(4){ animation-delay:.16s; }
.masthead.is-open .masthead__panel-inner > :nth-child(5){ animation-delay:.2s; }
.masthead.is-open .masthead__panel-inner > :nth-child(6){ animation-delay:.24s; }

/* With JS, site.js animates the panel's height (to its real height, on a
   soft curve, reversible mid-way), so these are just the resting states.
   .is-moving keeps it visible while it slides shut. */
@media (max-width: 959px){
  .js .masthead__panel{
    display:block; height:0; max-height:none; overflow:hidden;
    opacity:1; visibility:hidden; pointer-events:none; transition:none;
  }
  .js .masthead.is-open .masthead__panel{ height:auto; max-height:none; visibility:visible; pointer-events:auto; transition:none; }
  .js .masthead__panel.is-moving{ visibility:visible; }
}
@media (prefers-reduced-motion: reduce){
  .masthead__bars span, .masthead.is-open .masthead__bars span{ transition:none; }
  .masthead.is-open .masthead__panel-inner > *{ animation:none; }
}

/* The menu's "Start a project" is a button, not one of the menu's links:
   black text in normal case like every other lime button (the link rule
   above was turning it white and uppercase on lime). */
.masthead__panel-inner a.btn{
  color:#000; text-transform:none; letter-spacing:0;
  font-family: var(--body); font-weight:600; font-size:1rem;
  padding:.95rem 1.5rem; border-bottom:0;
}
.masthead__panel-inner a.btn:hover{ color:#000; }

/* ---- drawings on tablets and phones -----------------------------------------
   From 720px (every iPad, either way up) the first section puts the text and
   its drawing side by side on all three pages, the drawing filling its
   column, with the headline a size down so the two fit together. Below that
   (phones) the drawing sits under the text at a comfortable size, on every
   page rather than only the homepage. */
@media (min-width: 720px) and (max-width: 979px){
  .hero__layout, .pagehead__layout{ grid-template-columns: minmax(0,1.05fr) minmax(0,.95fr); gap:2.25rem; }
  .hero__art, .pagehead__art{ display:block; max-width:100%; justify-self:end; }
  .hero h1, .pagehead h1{ font-size: clamp(2.3rem, 5.2vw, 3rem); }
  .hero__lede, .pagehead .lede{ font-size:1.02rem; }
}
@media (max-width: 719px){
  .hero__art, .pagehead__art{ display:block; width:100%; max-width:380px; justify-self:start; margin-top:.25rem; }
}

/* ---- contact: what happens next ---------------------------------------------
   The three steps as the site's numbered lime circles, joined by one thin
   line, then the direct contact details in their own charcoal card beside
   the white form. No check marks, no rules between items. */
.next__title{ font-size: clamp(1.4rem, 2.6vw, 1.85rem); }
.next__steps{ list-style:none; margin:1.75rem 0 0; padding:0; display:grid; gap:1.6rem; }
.next__steps li{ position:relative; display:grid; grid-template-columns:auto minmax(0,1fr); gap:1rem; align-items:start; }
.next__steps li:not(:last-child)::before{
  content:""; position:absolute; left:calc(1rem - 1px); top:2.15rem; bottom:-1.45rem; width:2px;
  background: var(--rule-firm);
}
.next__steps p{ margin:.32rem 0 0; color: var(--fg); font-size:1.02rem; line-height:1.6; }

.direct{
  margin-top:2.5rem; padding: 1.6rem 1.75rem;
  border-radius: var(--r-lg); background: var(--ink-3); color:#fff;
}
.direct h3{ font-size:1.25rem; color:#fff; margin:0 0 1.1rem; }
.direct__list{ list-style:none; margin:0; padding:0; display:grid; gap:.9rem; }
.direct__list li, .direct__list a{ display:flex; align-items:center; gap:.75rem; color: rgba(255,255,255,.86); font-size:.98rem; text-decoration:none; }
.direct__list a{ font-weight:600; color:#fff; }
.direct__list a:hover{ color: var(--green); }
.direct__list svg{ width:18px; height:18px; flex:none; color: var(--green); }
.direct :focus-visible{ outline-color: var(--green); }

/* ---- questions your data can answer (/solutions/) ----------------------
   Each question is the heading and a small dashboard below draws the
   answer. Side by side on tablets, three across on desktop. */
.asks{ display:grid; gap:2.5rem; border-top:1px solid var(--rule); padding-top:2.5rem; }
.ask img{ display:block; width:100%; max-width:420px; height:auto; border-radius:10px; }
.ask h3{ font-size:1.5rem; line-height:1.08; margin:1.3rem 0 .55rem; }
.ask p{ color: var(--fg-soft); font-size:.97rem; line-height:1.6; max-width:34ch; }
@media (min-width: 600px) and (max-width: 979px){
  .ask{ display:grid; grid-template-columns: minmax(0,260px) minmax(0,1fr); gap:1.75rem; align-items:center; }
  .ask h3{ margin-top:0; }
}
@media (min-width: 980px){ .asks{ grid-template-columns: repeat(3, minmax(0,1fr)); gap:2.25rem; } }

/* ---- how a project runs (/solutions/) ----------------------------------
   Three numbered stops on a line: down the left on phones, across the
   top from tablet width up. */
.route{ list-style:none; margin:0; padding:0; display:grid; gap:2.5rem; border-top:1px solid var(--rule); padding-top:2.5rem; }
.route li{ position:relative; display:grid; grid-template-columns:2.6rem minmax(0,1fr); gap:1.25rem; align-content:start; }
.route__num{
  position:relative; z-index:1; width:2.6rem; height:2.6rem; border-radius:50%;
  display:grid; place-items:center; background: var(--fg); color:#6EF600;
  font-family: var(--display); font-weight:700; font-size:1.3rem; line-height:1;
}
.route li:not(:last-child)::before{
  content:""; position:absolute; left:calc(1.3rem - 1px); top:2.6rem; bottom:-2.5rem; width:2px; background: var(--fg);
}
.route img{ display:block; width:120px; height:auto; margin-bottom:1rem; }
.route h3{ margin-bottom:.45rem; }
.route p{ color: var(--fg-soft); font-size:.97rem; line-height:1.6; max-width:32ch; }
@media (min-width: 720px){
  .route{ grid-template-columns: repeat(3, minmax(0,1fr)); gap:2rem; }
  .route li{ grid-template-columns:minmax(0,1fr); gap:1.5rem; justify-items:center; text-align:center; }
  .route img, .route p{ margin-inline:auto; }
  /* centre of this stop to centre of the next: one column plus the gap */
  .route li:not(:last-child)::before{ left:calc(50% + 1.3rem); right:calc(-50% - .7rem); top:calc(1.3rem - 1px); bottom:auto; width:auto; height:2px; }
}

/* ---- why we do this (/about/) ------------------------------------------
   Josh's paragraph as written, centred, with a drawing for each of the
   three problems it names underneath. */
.why{ display:grid; justify-items:center; text-align:center; gap:1.75rem; }
.why__row{ display:grid; justify-items:center; gap:2.5rem; }
.why__row p{ font-size:1.18rem; line-height:1.7; max-width:52ch; color: var(--fg); }
.why__ills{ display:grid; grid-template-columns: repeat(3, minmax(0,1fr)); gap:.9rem; width:100%; max-width:600px; }
.why__ills img{ display:block; width:100%; height:auto; border-radius:10px; }

/* ---- reduce stress (home) ----------------------------------------------
   The three paragraphs as a .route on the charcoal ground, with the rail
   in lime, under a centred heading on wider screens. */
.calm{ display:grid; gap:2.5rem; }
.calm h2{ text-wrap:balance; }
.calm .route{ border-top:0; padding-top:0; }
.calm .route__num{ background:#000; }
.calm .route li:not(:last-child)::before{ background: var(--green); }
.calm .route p{ color: var(--fg); font-size:1.02rem; }
@media (min-width: 720px){
  .calm{ gap:3.25rem; }
  .calm h2{ text-align:center; max-width:24ch; margin-inline:auto; }
}
/* Phones: every .route (home and both service pages) is the same centred
   steps stacked, with a short connector in the gap between one step and
   the next number instead of a side rail. */
@media (max-width: 719px){
  .calm h2, .head:has(+ .route) h2{ text-align:center; margin-inline:auto; }
  .route{ gap:3.5rem; }
  .route li{ grid-template-columns:minmax(0,1fr); justify-items:center; text-align:center; gap:1rem; }
  .route img{ margin:0 auto .8rem; }
  .route p{ margin-inline:auto; max-width:30ch; }
  .route li:not(:last-child)::before{ left:calc(50% - 1px); right:auto; top:calc(100% + .75rem); bottom:auto; width:2px; height:2rem; }
}

/* ---- service rows with icons (/web-design/, /solutions/) ---------------
   A small lime line icon in a black square beside each name; the square
   flips to lime on hover along with the row's existing slide and rule. */
.index--icons h3{ display:flex; align-items:center; gap:1rem; }
.index__icon{
  flex:none; display:grid; place-items:center; width:2.8rem; height:2.8rem;
  border-radius:10px; background:#000; color: var(--green);
  transition: background-color .25s ease, color .25s ease;
}
.index__icon svg{ width:1.8rem; height:1.8rem; }
.index--icons .index__row:hover .index__icon{ background: var(--green); color:#000; }
@media (min-width: 800px){ .index--icons .index__row{ align-items:center; } }
