/* ============================================================
   AI & Automation: colour treatment
   Layered over the shared tech-lp.css, which stays byte-identical to the
   reference LP. This page owns one hue: #B488F2.

   THEMED   background and accent surfaces: the hero background and glows, the
            .hl-underline highlight band, the "I need to" selector, the Juicebox
            column of the comparison table, accent text and the section
            flourishes. Plus the kaleidoscope sweep (--grad-brand): the nav
            slogan, the gradient CTA button, the .grad-text heading word and the
            seven header anchors all open on this page's hue and run rightwards
            through the rest of the service wheel.
   BASELINE  only the arrow circle on the white CTA buttons, which is a solid
            fill rather than a gradient.
   ============================================================ */

:root {
  --accent: #B488F2;
  --accent-soft: rgba(180,136,242,0.16);
  --accent-line: rgba(180,136,242,0.45);
  /* secondary is a lighter tint of the same hue, not a second colour, so
     text links and feed hovers stay on the page's one hue */
  --accent-2: #C9A9F6;
  --accent-2-soft: rgba(201,169,246,0.16);
  --accent-2-line: rgba(201,169,246,0.5);
  --blue-deep: #1D1840;

  /* The kaleidoscope sweep. Opens on this page's hue and runs rightwards
     through the rest of the service wheel, wrapping past the cyan end back to
     magenta so the sweep is full-range wherever it starts. The base sheet
     derives this from --accent/--accent-2, which would give a flat two-stop
     ramp; this replaces it with all six stops, rotated to lead on the page hue.
     Drives the nav slogan, the gradient CTA button and .grad-text together. */
  --grad-brand: linear-gradient(100deg, #B488F2 0%, #A097EF 20%, #8CA6EC 40%, #77B5E9 60%, #63C4E6 80%, #C77DEA 100%);
}

/* ---------- ambient glows (hard-coded rgba in the base sheet) ---------- */
.hero-glow { background: radial-gradient(circle, rgba(140,107,232,0.3), rgba(140,107,232,0.06) 42%, transparent 70%); }
.hero-glow.two { background: radial-gradient(circle, rgba(180,136,242,0.22), transparent 70%); }
#why-us::before { background: radial-gradient(circle, rgba(140,107,232,0.16), transparent 68%); }
#insights::before { background: radial-gradient(circle, rgba(140,107,232,0.14), transparent 68%); }
.testi-glow { background: radial-gradient(circle, rgba(180,136,242,0.16), transparent 70%); }
.cta-glow { background: radial-gradient(circle, rgba(140,107,232,0.22), transparent 68%); }
.cs-quote { background: rgba(180,136,242,0.07); }


/* ---------- baseline brand furniture ----------
   The arrow circle on the white CTA buttons is a solid fill rather than a
   gradient, so it stays on the baseline accent; it is pinned here because the
   base sheet paints it with --accent. */
.btn--white.btn--lg .arr, .btn--white.btn--full .arr { background: #B488F2; }

/* ---------- cross-sell cards: colour follows the service, not the position ----------
   The base sheet tints these by :nth-child, which would recolour a service every
   time a page reorders the row. These class rules land later at equal specificity,
   so a service keeps its hue on every page in the set. */
.svc-card.svc--webdev { --svc: #C77DEA; --svc-soft: rgba(199,125,234,0.16); --svc-line: rgba(199,125,234,0.5); }
.svc-card.svc--ai { --svc: #B488F2; --svc-soft: rgba(180,136,242,0.16); --svc-line: rgba(180,136,242,0.5); }
.svc-card.svc--brand { --svc: #A097EF; --svc-soft: rgba(160,151,239,0.16); --svc-line: rgba(160,151,239,0.5); }
.svc-card.svc--growth { --svc: #8CA6EC; --svc-soft: rgba(140,166,236,0.16); --svc-line: rgba(140,166,236,0.5); }
.svc-card.svc--systems { --svc: #77B5E9; --svc-soft: rgba(119,181,233,0.16); --svc-line: rgba(119,181,233,0.5); }
.svc-card.svc--design { --svc: #63C4E6; --svc-soft: rgba(99,196,230,0.16); --svc-line: rgba(99,196,230,0.5); }

/* ============================================================
   Modules added for the expansion set (not in the reference LP)
   ============================================================ */

/* Hero trust strip. Same mechanic as the .team-mini row further down the page:
   a tight cluster on the left, two short lines of type beside it. Kept to one
   row at desktop so it clears the fold under the hero CTA. */
.hero-proof {
  display: flex; align-items: center; flex-wrap: wrap; gap: 12px 18px;
  margin-top: 22px; padding-top: 18px; border-top: 1px solid var(--line);
}
.hero-proof .hp-label { font-size: 10.5px; letter-spacing: 0.1em; text-transform: uppercase; color: var(--fg-mute); flex: none; }
.hero-proof .hp-badges { display: flex; flex-wrap: wrap; gap: 7px; }
.hero-proof .hp-badge {
  font-size: 10.5px; line-height: 1; letter-spacing: 0.05em; text-transform: uppercase;
  color: var(--accent); background: var(--accent-soft); border: 1px solid var(--accent-line);
  border-radius: var(--r-pill); padding: 6px 10px;
}
.hero-proof .hp-logos { display: flex; align-items: center; gap: 18px; flex: none; }
.hero-proof .hp-logos img { height: 18px; width: auto; opacity: 0.5; transition: opacity 180ms var(--ease); }
.hero-proof .hp-logos img:hover { opacity: 0.85; }
.hero-proof .hp-txt { flex: 1 1 250px; min-width: 0; font-size: 12.5px; line-height: 1.4; color: var(--fg-dim); }
.hero-proof .hp-txt b { display: block; color: var(--fg); font-weight: 600; }
@media (max-width: 1080px){ .hero-proof .hp-txt { flex-basis: 100%; } }
@media (max-width: 620px){
  .hero-proof { gap: 10px 14px; margin-top: 18px; padding-top: 14px; }
  .hero-proof .hp-logos { gap: 14px; }
  .hero-proof .hp-logos img { height: 16px; }
  .hero-proof .hp-txt { font-size: 12px; }
}

/* The intent echo is a single line with the link inline, so the stacked link's
   top margin would otherwise add height to the row. */
.intent-echo .echo-link { margin-top: 0; }

/* Tighter hero rhythm at desktop only, so the trust row clears the fold on a
   standard 1440-wide screen without touching the mobile stack. */
@media (min-width: 1081px){
  .hero h1 { margin: 14px 0 20px; }
  .hero-sub { margin-bottom: 22px; }
  .intent { margin: 18px 0 22px; }
  .intent-echo { margin-top: 14px; }
  .hero-cta { margin-top: 22px; }
}

/* Case card without a shipped image yet: an accent-tinted plate rather than a
   grey box, so a placeholder still reads as part of the page. */
.case-img.is-ph { background: linear-gradient(150deg, var(--accent-soft) 0%, rgba(250,250,250,0.02) 70%); }
.case-img.is-ph .ph-label { font-size: 12.5px; }

/* ---------- header anchors: eight samples of the same sweep ----------
   The nav gained an About link, so the ramp is recalculated across eight stops
   rather than extended by one. Link 1 is still the page hue and link 8 still
   lands on the far end of the rotated wheel; the base sheet declares only seven
   stops, so nth-child(8) exists here alone.

   The eight are spread over the wheel's four real hue transitions, with the
   wrap (cyan back to magenta) collapsed to a hard step. Sampling the CSS
   gradient evenly instead would put two links inside that wrap, where the
   interpolation goes muddy, and the pair comes back near-identical. */
.nav-links a:nth-child(1), .nav-menu a:nth-child(1) { color: #B488F2; }
.nav-links a:nth-child(2), .nav-menu a:nth-child(2) { color: #A792F0; }
.nav-links a:nth-child(3), .nav-menu a:nth-child(3) { color: #999CEE; }
.nav-links a:nth-child(4), .nav-menu a:nth-child(4) { color: #8CA6EC; }
.nav-links a:nth-child(5), .nav-menu a:nth-child(5) { color: #7EB0EA; }
.nav-links a:nth-child(6), .nav-menu a:nth-child(6) { color: #70BAE8; }
.nav-links a:nth-child(7), .nav-menu a:nth-child(7) { color: #63C4E6; }
.nav-links a:nth-child(8), .nav-menu a:nth-child(8) { color: #C77DEA; }
.nav-links a.is-active { color: var(--fg); }

/* An eighth link adds ~70px the base sheet did not budget for. Rather than move
   its 1240px cut-off up and lose the section nav on a 1280 screen, the gap
   tightens through the band where the row would otherwise crowd the phone
   number: 205px of slack at 1440, and 55px at the 1240 boundary. */
.nav-links { gap: 21px; }
@media (max-width: 1359px){ .nav-links { gap: 14px; } }

/* ---------- hero: content centred in the first screen ----------
   The base sheet pads the hero 20px above and 96px below, and the left column
   adds another 29px of its own. Measured at 1440x900 that put 58px between the
   nav and the first line of hero copy and 202px between the bottom of the hero
   and the fold: three and a half times as much air underneath as above.

   Fixed by height rather than by numbers, since the right figure depends on how
   tall the content runs. The hero is given the first screen as a minimum and
   centres its content in it, so whatever space is left over is split evenly top
   and bottom. The padding below is the floor, taking over on short viewports and
   on pages whose hero outgrows the screen, where there is no slack to split.
   dvh so a phone's collapsing URL bar does not shift the centre. */
.hero {
  display: flex; align-items: center;
  min-height: calc(100vh - var(--nav-h, 66px));
  min-height: calc(100dvh - var(--nav-h, 66px));
  padding-top: clamp(16px, 1.8vw, 28px);
  padding-bottom: clamp(16px, 1.8vw, 28px);
}
.hero > .wrap { width: 100%; }
@media (max-width: 620px){
  .hero { --nav-h: 50px; padding-top: clamp(24px, 5vw, 32px); padding-bottom: clamp(24px, 5vw, 32px); }
}

/* ---------- About Juicebox ----------
   A row rather than a section: hairline top and bottom, and about half the
   vertical padding of .section, so it introduces the agency between the stat
   bar and the comparison table without competing with either. */
.about { padding: clamp(46px, 5vw, 72px) 0; border-top: 1px solid var(--line); border-bottom: 1px solid var(--line); }
/* Land the anchor on the eyebrow, not on the section border. Same mechanic the
   base sheet gives .section[id]: a negative scroll-margin that cancels the
   section's own top padding, so #about arrives cropped tight to the eyebrow and
   the row and the photograph share the screen instead of the padding taking a
   slice of it. .about is not .section, so it needs its own copy with its own
   (smaller) padding value. */
#about { scroll-margin-top: calc(-1 * clamp(46px, 5vw, 72px)); }
/* Bottom-aligned, so the ledger's last row sits on the same line as the "Meet
   the people you'd work with" link rather than floating off the top of a column
   it never fills. The statement column is the taller of the two at most desktop
   widths, so end-alignment drops the ledger; around 1090 the ledger wins by a
   few pixels and starts fractionally above the eyebrow instead, which is not
   visible at that margin. */
.about-row { display: grid; grid-template-columns: minmax(0, 1.15fr) minmax(0, 1fr); gap: clamp(40px, 5vw, 78px); align-items: end; }
.about-say .eyebrow { margin-bottom: 18px; }
.about-say h2 { font-size: clamp(26px, 2.7vw, 36px); line-height: 1.16; max-width: 28ch; }
.about-p { margin: 18px 0 0; font-size: 15.5px; line-height: 1.65; color: var(--fg-dim); max-width: 52ch; }
.about-link { display: inline-flex; margin-top: 20px; font-size: 15px; }

/* The facts read as a ledger: a hairline per row, the term in the display face,
   the gloss beside it. No boxes, so the row stays quiet.

   The grid is on the list rather than on each item, with the items set to
   display: contents, so one max-content column serves all four terms: they line
   up with each other and give the rest of the width back to the values. Four
   separate per-item grids cannot do that, which is why the term column had been
   pinned to a guessed 9.5rem and was starving the values at 1024. */
.about-facts {
  margin: 0; padding: 0; list-style: none;
  display: grid; grid-template-columns: max-content minmax(0, 1fr); column-gap: 24px;
}
.about-facts li { display: contents; }
.about-facts b, .about-facts span { padding: 15px 0; border-top: 1px solid var(--line); }
.about-facts li:first-child b, .about-facts li:first-child span { padding-top: 0; border-top: 0; }
.about-facts li:last-child b, .about-facts li:last-child span { padding-bottom: 0; }
.about-facts b {
  font-family: var(--font-display); font-weight: 500; font-size: 17px; line-height: 1.25;
  color: var(--fg); letter-spacing: -0.005em; white-space: nowrap;
}
.about-facts span { font-size: 13.5px; line-height: 1.5; color: var(--fg-dim); }

/* Stacks at the same 1080px line the rest of the suite treats as the end of
   desktop, rather than holding two columns down to 900 where the values were
   breaking to three and four lines. */
@media (max-width: 1080px){
  .about-row { grid-template-columns: 1fr; gap: 32px; }
  .about-say h2 { max-width: 26ch; }
}
@media (max-width: 560px){
  .about-facts { grid-template-columns: 1fr; column-gap: 0; }
  .about-facts b { padding-bottom: 3px; white-space: normal; }
  .about-facts span { border-top: 0; padding-top: 0; }
  .about-facts li:last-child b { padding-bottom: 3px; }
}

/* ---------- the team photograph ----------
   Full-bleed at the foot of the About row, so the section closes on the agency
   itself rather than on a list of facts. Three crops, art-directed rather than
   resolution-switched: the 2.33 ultrawide reads as a band on desktop, the 1.91
   covers tablet, and the 1.33 keeps forty faces legible on a phone, where the
   ultrawide would render them about 40px tall. The grade is deliberately light
   -- the photograph is a bright late-afternoon exposure and the page is dark, so
   it needs settling, not dimming. */
.about-shot { margin: clamp(38px, 4vw, 58px) 0 0; padding: 0; }
.about-shot picture { display: block; }
.about-shot img {
  display: block; width: 100%;
  height: clamp(230px, min(27vw, 44vh), 430px);
  object-fit: cover; object-position: 50% 48%;
  filter: saturate(0.94) contrast(1.02) brightness(0.94);
}
.about-shot figcaption {
  margin-top: 14px;
  font-size: 12.5px; line-height: 1.5; letter-spacing: 0.02em; color: var(--fg-mute);
}

/* ---------- the lead form as a mobile lightbox ----------
   Rides the .cs-* shell already on the page, so there is no second modal
   implementation: same backdrop, scroll lock and escape handling as the case
   study, team and insights lightboxes. These rules mirror the ones variant B
   carries in layout.css, which index.html does not load. */
.lead-modal .cs-dialog { max-width: 560px; }
.lead-modal .cs-scroll { max-height: 90vh; }
.lead-modal .lead { background: transparent; border: 0; border-radius: 0; padding: 30px 30px 32px; }
.lead-modal .lead-title { font-size: 25px; }
.lead-modal .lead-sub { font-size: 14px; }
@media (max-width: 620px){
  .lead-modal .cs-dialog, .lead-modal .cs-scroll { max-height: calc(100dvh - 28px); }
  .lead-modal .lead { padding: 24px 18px 26px; }
}

/* Collapse the hero's form column once the form has actually been moved out.
   Gated on .lead-modal-ready (set by tech-lp.js) rather than on the media query
   alone, so a no-JS visitor keeps the inline form instead of losing it. */
@media (max-width: 1080px){
  .lead-modal-ready .hero-grid > aside { display: none; }
  .lead-modal-ready .hero-grid { gap: 0; }
}

/* Taking the form out of the mobile hero also takes away its ask, so the hero
   CTA row gains a primary button in its place. Hidden at desktop, where the
   form is right there. It is .btn--white, not .btn--grad, so the existing
   work/team A/B selector still matches the button it was written for. */
.hero-cta .lead-cta-m { display: none; }
@media (max-width: 1080px){
  .lead-modal-ready .hero-cta { flex-wrap: wrap; }
  .lead-modal-ready .hero-cta .lead-cta-m { display: inline-flex; }
}

/* Short desktop viewports: pull the section in so the row and the photograph
   share the screen instead of the caption sliding under the fold. The photo
   height already carries a 44vh term for the same reason. Below roughly 800px
   of viewport the two cannot both fit whole -- the row alone is ~310px and a
   band thin enough to make room stops reading as a photograph -- so this closes
   most of the gap rather than all of it. The scroll-margin is restated because
   it has to keep cancelling whatever the padding currently is. */
@media (min-width: 1081px) and (max-height: 820px){
  .about { padding: clamp(28px, 3vw, 40px) 0; }
  #about { scroll-margin-top: calc(-1 * clamp(28px, 3vw, 40px)); }
  .about-shot { margin-top: clamp(24px, 2.6vw, 34px); }
}

/* ---------- mobile navigation ----------
   Two swaps, at two different widths, because they solve two different things.

   The hamburger appears at 1240px, the exact width where the base sheet hides
   the inline section links. Between 1081 and 1240 the page previously had no
   section navigation at all; now it has the sheet.

   The nav's consult button hands over to a floating one at 1080px, matching
   where the lead form itself becomes a modal, so on a phone the bar carries
   wayfinding and the floating button carries the ask. */
.nav-burger {
  display: none; align-items: center; justify-content: space-between; gap: 10px;
  min-width: 122px; height: 38px; padding: 0 12px; flex: none;
  background: transparent; border: 1px solid var(--line-2, var(--line)); border-radius: var(--r-pill);
  cursor: pointer; transition: border-color 180ms var(--ease), background 180ms var(--ease);
}
.nav-burger:hover { border-color: var(--accent-line); }
/* The word crossfades rather than cutting, and the button is wide enough for the
   longest section name so the nav does not twitch on every swap. */
.nb-label {
  font-family: var(--font-body); font-size: 11px; font-weight: 600;
  letter-spacing: 0.12em; text-transform: uppercase; white-space: nowrap;
  color: var(--fg-dim); transition: opacity 150ms var(--ease);
}
.nb-label.is-swapping { opacity: 0; }
.nav-burger.is-open .nb-label,
.nav-burger:hover .nb-label { color: var(--fg); }
@media (prefers-reduced-motion: reduce){ .nb-label { transition: none; } }
.nb-bars { display: block; width: 17px; height: 11px; position: relative; }
.nb-bars i {
  position: absolute; left: 0; right: 0; height: 1.5px; border-radius: 2px; background: var(--fg);
  transition: transform 220ms var(--ease), opacity 160ms var(--ease);
}
.nb-bars i:nth-child(1) { top: 0; }
.nb-bars i:nth-child(2) { top: 4.75px; }
.nb-bars i:nth-child(3) { top: 9.5px; }
.nav-burger.is-open .nb-bars i:nth-child(1) { transform: translateY(4.75px) rotate(45deg); }
.nav-burger.is-open .nb-bars i:nth-child(2) { opacity: 0; }
.nav-burger.is-open .nb-bars i:nth-child(3) { transform: translateY(-4.75px) rotate(-45deg); }

.nav-menu {
  display: none;
  border-top: 1px solid var(--line);
  background: rgba(12,13,16,0.97);
  -webkit-backdrop-filter: saturate(140%) blur(10px);
  backdrop-filter: saturate(140%) blur(10px);
}
.nav-menu.is-open { display: block; }
.nav-menu > .wrap { padding-top: 14px; padding-bottom: 18px; }
.nav-menu-links {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); column-gap: 24px;
  font-family: var(--font-display); font-size: 16px; font-weight: 700; letter-spacing: -0.008em;
}
.nav-menu-links a { padding: 12px 0; border-bottom: 1px solid var(--line); }
.nav-menu-links a:hover { opacity: 0.75; }
.nm-phone {
  display: inline-flex; align-items: center; gap: 8px; margin-top: 16px;
  font-size: 13.5px; color: var(--fg-dim);
}
.nm-phone .dot { color: var(--accent); font-size: 9px; }
@media (max-width: 1240px){ .nav-burger { display: inline-flex; } }
@media (max-width: 359px){ .nav-menu-links { grid-template-columns: 1fr; } }

/* Floating ask. z-index sits above the sticky nav (60) and below the lightboxes
   (120), so an open modal covers it without needing to be told to. */
.cta-float {
  display: none; position: fixed; right: 16px; bottom: 16px; z-index: 70;
  align-items: center; gap: 10px;
  padding: 13px 20px; border-radius: var(--r-pill);
  font-family: var(--font-body); font-size: 15px; font-weight: 500; line-height: 1;
  color: var(--ink); background: var(--white);
  box-shadow: 0 14px 34px -10px rgba(0,0,0,0.7);
  opacity: 0; transform: translateY(14px); pointer-events: none;
  transition: opacity 260ms var(--ease), transform 260ms var(--ease);
}
.cta-float.is-on { opacity: 1; transform: none; pointer-events: auto; }
@media (max-width: 1080px){
  .nav-cta { display: none; }
  .cta-float { display: inline-flex; }
}
@media (max-width: 500px){
  /* the phone number has dropped out by here, so the burger takes the slack */
  .nav-burger { margin-left: auto; }
  .cta-float { right: 12px; bottom: 12px; padding: 12px 17px; font-size: 14.5px; }
}
@media (prefers-reduced-motion: reduce){
  .cta-float { transition: none; }
  .nb-bars i { transition: none; }
}

/* ---------- hero eyebrow: one line on every phone ----------
   Below 620px the base sheet hides .eyebrow-tail, so only the first half shows
   -- but at 13px the longest of the six ('For established Australian brands')
   measures 321px against 233px of usable width on a 320px screen, and broke to
   two lines on most phones.

   Sized from that measurement rather than guessed: the eyebrow sits inside
   .wrap (28px of padding each side at every mobile width) less the 26px rule
   and its 12px gap. Measured, not modelled: the usable width is 100vw - 94px,
   and the offset here is 98 to leave 4px of slack. A first pass used 87 and
   overflowed the longest string by 7px at 320 -- invisible, because nowrap will
   happily run type past the edge rather than admit it does not fit. 321px of
   type scales in at 0.0405px per available pixel; the floor of 8.9px is what a
   320px screen needs, and 430px and wider gets the full 13px back.

   nowrap makes the single line a guarantee rather than an expectation. The
   constant is tied to the longest eyebrow currently in the set: re-measure it if
   a page gets a longer one, or the line will overflow instead of wrapping. */
@media (max-width: 620px){
  .hero .eyebrow {
    font-size: clamp(8.9px, calc((100vw - 98px) * 0.0405), 13px);
    white-space: nowrap;
  }
}

/* ---------- stat bar on mobile: full bleed, two by two ----------
   The base sheet drops the bar to a single column under 480px, which turned four
   compact proof points into four full-width rows and a lot of scrolling. Two by
   two keeps them readable as a set.

   Full bleed too: .proof-grid IS the .wrap, so its 28px of padding was insetting
   cells that already carry 20px of their own. Dropping it lets the hairlines
   reach both screen edges and gives the numbers back the width, while the text
   inside stays inset by the cell padding. */
@media (max-width: 620px){
  .proof-grid {
    grid-template-columns: repeat(2, 1fr);
    max-width: none; padding-left: 0; padding-right: 0;
  }
  .proof-cell { padding: 22px 20px; }
  /* Two up, the cell is 50vw less its 20px of padding each side. Four of the six
     pages carry a worded stat rather than a figure -- 'Since 2005' is the widest
     at 162px against a 120px cell on a 320px screen -- so the number is sized
     from that rather than set flat, and scales back up to the base 32px by the
     time there is room for it. */
  .proof-cell .num { font-size: clamp(21px, calc((50vw - 40px) / 5.6), 32px); }
  .proof-cell .lbl { margin-top: 10px; font-size: 13px; }
  .proof-cell .src { margin-top: 8px; }
}

/* One hairline between the two, not two: .about closes on a border and .proof
   opens on one, and they are now neighbours. */
.about + .proof { border-top: 0; }
