/**
 * Site header.
 *
 * Design: 94px white bar (16 + 62 + 16). Nav links 20/30 at #2B2B2B separated by
 * 48px slots holding a 12px accent dot. The logo sits in a 293x198 white box that
 * starts inside the bar and overlaps the hero below it.
 *
 * @package lawncareknox
 */

.site-header {
	position: relative;
	z-index: 10;
	background-color: var(--color-white);
	padding-block: var(--sp-16);
}

.site-header--sticky {
	position: sticky;
	top: 0;
}

.site-header__inner {
	position: relative;
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	min-height: 62px;
}

/* --- Logo box: absolute so it can overlap the hero without adding height. --- */
.site-header__brand {
	position: absolute;
	top: 0;
	left: var(--container-gutter);
	z-index: 2;
}

.site-header__logo {
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	-webkit-box-pack: center;
	    -ms-flex-pack: center;
	        justify-content: center;
	width: 293px;
	height: 198px;
	background-color: var(--color-white);
	border-radius: var(--radius);
	overflow: hidden;
	padding: 24px;
}

.site-header__logo img {
	width: 100%;
	height: 100%;
	-o-object-fit: contain;
	   object-fit: contain;
}

/* --- Nav + actions group.
   In Figma this is a fixed 955px box (nav 600 + 145 + button 210) pinned to the
   right edge of the 1440 content box, so the gap below is the design value. --- */
.site-header__nav-wrap {
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	-webkit-box-pack: end;
	    -ms-flex-pack: end;
	        justify-content: flex-end;
	gap: 145px;
	margin-left: auto;
}

.nav-menu {
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	gap: var(--sp-10);
}

.nav-menu > li {
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	gap: var(--sp-10);
	position: relative;
}


.nav-menu a {
	font-size: 20px;
	line-height: 30px;
	letter-spacing: -0.02em;
	font-weight: 400;
	color: var(--color-text);
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	gap: var(--sp-10);
}

.nav-menu a:hover,
.nav-menu .current-menu-item > a {
	color: var(--color-primary);
}

/* Accent dot between top-level items: a 48px slot with a 12px ring and a 4px
   core, matching the design's 10px nav gap on either side. */
.nav-menu > li + li::before {
	content: "";
	-webkit-box-flex: 0;
	    -ms-flex: 0 0 48px;
	        flex: 0 0 48px;
		width: 48px;
	height: 48px;
	background-image: radial-gradient(circle at center, var(--color-accent) 0 2px, transparent 2px),
		radial-gradient(circle at center, rgba(151, 175, 144, 0.25) 0 6px, transparent 6px);
	background-repeat: no-repeat;
	background-position: center;
}

/*
 * Dropdown chevron on items that have children.
 *
 * MASKED, not a background-image. chevron-down.svg is a single #2B2B2B stroke on
 * transparent, so using its alpha as a mask and painting through
 * `background-color: currentColor` renders the identical glyph at rest (the link
 * colour IS #2B2B2B = --color-text) while making the colour token-driven. That is
 * what lets the chevron follow the link into every state — :hover and the
 * current/ancestor states below — from one asset instead of a second tinted file.
 * Verified pixel-identical to the previous background-image at 1920.
 */
.nav-menu > li.menu-item-has-children > a::after {
	content: "";
	width: 24px;
	height: 24px;
	-webkit-box-flex: 0;
	    -ms-flex: 0 0 24px;
	        flex: 0 0 24px;
	background-color: currentColor;
	-webkit-mask: url("../images/icons/chevron-down.svg") no-repeat center / 24px 24px;
	mask: url("../images/icons/chevron-down.svg") no-repeat center / 24px 24px;
	-webkit-transition: var(--transition);
	transition: var(--transition);
}

.nav-menu > li.menu-item-has-children:hover > a::after {
	-webkit-transform: rotate(180deg);
	    -ms-transform: rotate(180deg);
	        transform: rotate(180deg);
}

/*
 * Active parent. `.nav-menu .current-menu-item > a` above already recolours the
 * link (and therefore the chevron) for the current page itself, but WordPress
 * marks a parent of the current page with .current-menu-ancestor /
 * .current-menu-parent, which nothing covered — so a dropdown parent whose child
 * is the current page rendered its chevron in the resting colour. Added as its
 * own rule rather than by editing the resting colour rule above.
 *
 * On the front page the current item is "Home", which has no children, so this
 * selector matches nothing here and the header render is unchanged.
 */
.nav-menu > li.current-menu-ancestor > a,
.nav-menu > li.current-menu-parent > a {
	color: var(--color-primary);
}

/* ==========================================================================
   Sub menu
   ==========================================================================
   The panel is new UI — the Figma file never shows the dropdown open — so it is
   built out of devices that already exist in this design rather than a new look:
   the nav's own accent dot, the project's list-separator hairline, the shared
   8px radius and the project's one elevation shadow.

   Everything in this block is only ever seen in the :hover / :focus-within
   state: the panel is `opacity: 0; visibility: hidden` at rest and
   `position: absolute`, so it contributes nothing to the resting header — no
   paint and no layout. The closed nav row is byte-identical to before.
   ========================================================================== */

/*
 * The nav accent dot, as one definition: a 12px rgba(151,175,144,0.25) ring with
 * a 4px solid --color-accent core, drawn as two concentric radial-gradients
 * (2px and 6px radii). This is the exact construction of the separator dot in
 * `.nav-menu > li + li::before` above, so the submenu bullet and the nav
 * separator read as the same device.
 *
 * The separator rule above deliberately still carries its own copy instead of
 * consuming this token: the resting desktop header is under a hard no-change
 * rule this pass, and rewriting a rule that paints at rest is not worth the
 * risk for a cosmetic refactor. Fold it in on the next pass that is allowed to
 * touch desktop.
 */
:root {
	--nav-dot: radial-gradient(circle at center, var(--color-accent) 0 2px, transparent 2px),
		radial-gradient(circle at center, rgba(151, 175, 144, 0.25) 0 6px, transparent 6px);
}

.nav-menu .sub-menu {
	position: absolute;
	top: 100%;
	left: 0;
	min-width: 240px;
	background-color: var(--color-white);
	-webkit-box-shadow: 0 30px 80px 0 rgba(0, 0, 0, 0.08);
	        box-shadow: 0 30px 80px 0 rgba(0, 0, 0, 0.08);
	border: 1px solid var(--color-border-light);
	/* Every other surface in this design is 8px. `0` is what made the panel read
	   as foreign. */
	border-radius: var(--radius);
	/* padding: var(--sp-16) 0; */
	opacity: 0;
	visibility: hidden;
	-webkit-transform: translateY(var(--sp-10));
	    -ms-transform: translateY(var(--sp-10));
	        transform: translateY(var(--sp-10));
	-webkit-transition: var(--transition);
	transition: var(--transition);
	z-index: 20;
	overflow: hidden;
}

.nav-menu > li:hover > .sub-menu,
.nav-menu > li:focus-within > .sub-menu {
	opacity: 1;
	visibility: visible;
	-webkit-transform: translateY(0);
	    -ms-transform: translateY(0);
	        transform: translateY(0);
}

.nav-menu .sub-menu li {
	display: block;
}

/*
 * Hairline BETWEEN items only — `li + li` puts a rule above every item except
 * the first, so there is none above the first and none below the last.
 *
 * --color-hairline (rgba(43,43,43,0.2)) rather than --color-border-light
 * (#C3C3C3), for two reasons:
 *   1. Role. --color-hairline is already this project's separator between items
 *      of a list — it is the rule between rows of the Service Areas area-list.
 *      #C3C3C3 is structural section chrome (the full-bleed rules and card edges
 *      in the cards section), which is a different job.
 *   2. It reads correctly against white. Over #FFFFFF it composites to ~#D4D4D4,
 *      lighter than the panel's own #C3C3C3 border, so the frame stays dominant
 *      and the internal rules sit below it in the hierarchy. At #C3C3C3 the
 *      internal rules would match the frame exactly and the panel would read as
 *      a table rather than a menu.
 *
 * Drawn as an inset box-shadow, per the convention used everywhere else in this
 * theme, so the rules cost no layout height and the panel stays 166px.
 */
.nav-menu .sub-menu li + li {
	-webkit-box-shadow: inset 0 1px 0 0 var(--color-hairline);
	        box-shadow: inset 0 1px 0 0 var(--color-hairline);
}

.nav-menu .sub-menu a {
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	gap: var(--sp-10);
	padding: var(--sp-8) var(--sp-24);
	font-size: 18px;
	line-height: 28px;
	white-space: nowrap;
	/* Anchors the sweep below, clips it to the row, and makes the row its own
	   stacking context so the sweep can sit behind the text and the dot.
	   All three are inert at rest — the panel is hidden and the sweep is
	   scaled to 0. */
	position: relative;
	overflow: hidden;
	z-index: 0;
}

/*
 * THE HOVER SWEEP — background enters from the LEFT rather than fading in.
 *
 * Drawn as its own layer instead of animating `background-color`, because a
 * colour cannot be animated directionally. `transform: scaleX()` from a
 * `left center` origin gives the wipe, runs on the compositor, and costs no
 * layout. `z-index: -1` inside the row's own stacking context puts it above the
 * row's (transparent) background but below the label and the accent dot, so the
 * dot is never covered.
 *
 * `::after` is used because `::before` is already the dot.
 */
.nav-menu .sub-menu a::after {
	content: "";
	position: absolute;
	inset: 0;
	z-index: -1;
	background-color: var(--color-secondary);
	-webkit-transform: scaleX(0);
	    -ms-transform: scaleX(0);
	        transform: scaleX(0);
	-webkit-transform-origin: left center;
	    -ms-transform-origin: left center;
	        transform-origin: left center;
	-webkit-transition: -webkit-transform 0.3s ease;
	transition: -webkit-transform 0.3s ease;
	transition: transform 0.3s ease;
	transition: transform 0.3s ease, -webkit-transform 0.3s ease;
}

.nav-menu .sub-menu a:hover::after,
.nav-menu .sub-menu a:focus-visible::after,
.nav-menu .sub-menu .current-menu-item > a::after {
	-webkit-transform: scaleX(1);
	    -ms-transform: scaleX(1);
	        transform: scaleX(1);
}

/* A directional wipe is exactly the kind of motion this preference asks to drop.
   The fill still appears — it just arrives instantly. Not width-scoped, because
   the sweep itself is not: it runs in the desktop dropdown and in the mobile
   accordion alike. */
@media (prefers-reduced-motion: reduce) {
	.nav-menu .sub-menu a::after {
		-webkit-transition: none;
		transition: none;
	}
}

/* The accent dot, to the left of every item. 12x12 box, and the gradient radii
   are absolute, so it is the 12px ring + 4px core at native size. */
.nav-menu .sub-menu a::before {
	content: "";
	-webkit-box-flex: 0;
	    -ms-flex: 0 0 12px;
	        flex: 0 0 12px;
	width: 12px;
	height: 12px;
	background-image: var(--nav-dot);
	background-repeat: no-repeat;
	background-position: center;
}

/*
 * Hover FOREGROUND. The background is the swept ::after layer above.
 *
 * This used to be --color-bg-light (#EFFFF5, a near-white mint) behind
 * --color-primary (#7C9A74, sage). Two low-contrast values against each other on
 * a white panel: the row barely separated from the panel and the label barely
 * separated from the row, so hovering read as the item going DULL rather than
 * becoming active. Measured contrast was ~2.0:1, under the 4.5:1 minimum.
 *
 * Now the sweep fills the row with --color-secondary (#2F5D3A, the theme's deep
 * green) and the label flips to white — ~8.9:1, and the same "solid fill, white
 * label" language `.btn-outline:hover` already uses. No new colour is introduced.
 *
 * The dot is deliberately left alone: it is #97AF90 sage on the deep green, which
 * still reads clearly, and its gradient radii are absolute so restyling it would
 * mean a second asset for no gain.
 */
.nav-menu .sub-menu a:hover,
.nav-menu .sub-menu a:focus-visible,
.nav-menu .sub-menu .current-menu-item > a {
	color: var(--color-white);
}

.site-header__actions {
	display: -webkit-box;
	display: -ms-flexbox;
	display: flex;
	-webkit-box-align: center;
	    -ms-flex-align: center;
	        align-items: center;
	gap: var(--sp-16);
}

/* Optional secondary header button. Per decision D8 this field is mandated by the
   brief's Theme Options list but the design has no slot for it, so it renders
   only when the client populates it. Sized to match the 62px phone button beside
   it so the bar height never changes. */
.btn--header-cta {
	min-height: 62px;
}

/* --- Mobile toggles (hidden on desktop). --- */
.menu-toggle,
.menu-close {
	display: none;
}

.site-header__overlay {
	display: none;
}

/* ==========================================================================
   Responsive
   ========================================================================== */

@media (max-width: 1600px) {
	.site-header__nav-wrap {
		gap: var(--sp-80);
	}
}

@media (max-width: 1360px) {
	.site-header__nav-wrap {
		gap: var(--sp-48);
	}

	.nav-menu > li + li::before {
		-webkit-box-flex: 0;
		    -ms-flex: 0 0 var(--sp-24);
		        flex: 0 0 var(--sp-24);
				width: var(--sp-24);
		height: var(--sp-24);
	}

	.site-header__logo {
		width: 240px;
		height: 162px;
	}
}

@media (max-width: 1200px) {
	.nav-menu a {
		font-size: 18px;
		/* em so the line box tracks the font-size instead of being frozen px. */
		line-height: 1.556em;
		/* Stepping the negative tracking toward 0 as the screen narrows: -0.02em
		   flatters 20px, but it closes 18px up and reads cramped. */
		letter-spacing: -0.01em;
	}

	.site-header__nav-wrap {
		gap: var(--sp-32);
	}
}

/*
 * The dropdown panel's own responsive step.
 *
 * Bounded at BOTH ends on purpose. The desktop dropdown only exists above 999 —
 * at 999 and below the same <ul> becomes the stacked accordion inside the
 * off-canvas panel, which has its own type and padding — so a plain
 * `max-width: 1200px` block would leak this step into the mobile menu and
 * shrink rows that are meant to be 48px tap targets. `min-width: 1000px` is the
 * same boundary js/site.js uses for isDesktop(), so CSS and JS agree.
 *
 * 17px holds the 28px line box exactly (17 x 1.647 = 28.0), matching how
 * .btn__label takes its 1200 step in global.css, so the glyphs shrink without
 * the line box moving. The row padding is what actually tightens the list:
 * 8 -> 4 takes each row from 44px to 36px.
 */
@media (max-width: 1200px) and (min-width: 1000px) {
	.nav-menu .sub-menu {
		min-width: 220px;
		padding: var(--sp-10) 0;
	}

	.nav-menu .sub-menu a {
		font-size: 17px;
		line-height: 1.647em;
		letter-spacing: -0.01em;
		padding: var(--sp-4) var(--sp-16);
		gap: var(--sp-8);
	}
	.site-header__logo {
    width: 220px;
    height: 152px;
}
}

/* --- Hamburger: slides in right-to-left with a full-screen overlay. --- */
@media (max-width: 999px) {
	/*
	 * .site-header is position:relative + z-index:10, so it opens its own
	 * stacking context. That means .site-header__nav-wrap's z-index:999 only
	 * orders the panel INSIDE the header — the header itself still competes
	 * with .site-header__overlay (a sibling of <header>, z-index:998) at level
	 * 10, so the overlay painted over the whole panel and swallowed every
	 * pointer event: no nav link and no close (x) was clickable.
	 * Lifting the header above the overlay fixes it without touching the
	 * panel, the overlay or the JS. The overlay still dims and still catches
	 * outside clicks over everything below the header bar.
	 */
	.site-header {
		z-index: 9999;
	}

	.site-header__inner {
		-webkit-box-pack: end;
		    -ms-flex-pack: end;
		        justify-content: flex-end;
	}

	/* The logo is the brand mark and it was collapsing at small widths. Sized up
	   through here / 767 / 640 / 479 instead of down. 293:198 is the design's
	   box ratio, held exactly at every step. */
	.site-header__logo {
		width: 200px;
		height: 135px;
		padding: 20px;
	}

	/* ==================================================================
	   Menu toggle — and, when open, the close (x) in the same position
	   ==================================================================
	   One control, two states. A sage 48px tile on the shared 8px radius,
	   using the same fill and the same hover colour as the header's phone
	   button so it belongs to the header rather than to the panel.

	   z-index 1000 is load-bearing. .site-header is z-index 999 at this
	   breakpoint and so opens a stacking context; .site-header__nav-wrap is
	   z-index 999 INSIDE it. Anything below that paints under the panel, so
	   the old z-index:2 toggle disappeared the moment the panel slid in —
	   which is exactly why a separate .menu-close existed. At 1000 the tile
	   stays on top of the panel, in place, and becomes the close.
	   ================================================================== */
	.menu-toggle {
		display: -webkit-box;
		display: -ms-flexbox;
		display: flex;
		-webkit-box-orient: vertical;
		-webkit-box-direction: normal;
		    -ms-flex-direction: column;
		        flex-direction: column;
		-webkit-box-align: center;
		    -ms-flex-align: center;
		        align-items: center;
		-webkit-box-pack: center;
		    -ms-flex-pack: center;
		        justify-content: center;
		gap: var(--sp-4);
		width: 48px;
		height: 48px;
		margin-left: auto;
		padding: 0;
		border-radius: var(--radius);
		background-color: var(--color-primary);
		-webkit-transition: var(--transition);
		transition: var(--transition);
		position: relative;
		z-index: 1000;
	}
.nav-menu > .menu-item-has-children {
    display: block !important;
}
	.menu-toggle:hover,
	.menu-toggle:focus-visible {
		background-color: var(--color-secondary);
	}

	.menu-toggle__bar {
		display: block;
		width: 20px;
		height: 2px;
		background-color: var(--color-white);
		-webkit-transition: var(--transition);
		transition: var(--transition);
	}

	/*
	 * Hamburger -> x. Three 2px bars with 4px gaps stack 14px tall inside the
	 * 48px tile, so the bar centres are 6px apart: the outer two travel exactly
	 * 6px to meet on the centre line, then rotate.
	 */
	.menu-toggle.is-open {
		background-color: var(--color-secondary);
	}

	.menu-toggle.is-open .menu-toggle__bar:nth-child(1) {
		-webkit-transform: translateY(6px) rotate(45deg);
		    -ms-transform: translateY(6px) rotate(45deg);
		        transform: translateY(6px) rotate(45deg);
	}

	.menu-toggle.is-open .menu-toggle__bar:nth-child(2) {
		opacity: 0;
		-webkit-transform: scaleX(0);
		    -ms-transform: scaleX(0);
		        transform: scaleX(0);
	}

	.menu-toggle.is-open .menu-toggle__bar:nth-child(3) {
		-webkit-transform: translateY(-6px) rotate(-45deg);
		    -ms-transform: translateY(-6px) rotate(-45deg);
		        transform: translateY(-6px) rotate(-45deg);
	}

	/*
	 * The panel's own x is gone: the toggle above IS the close now, in the same
	 * position, so a second x inside the panel would be a duplicate control.
	 * The element stays in the markup (no PHP change) and stays reachable by
	 * nothing — JS drives the toggle instead.
	 */
	.menu-close {
		display: none;
	}

	.site-header__nav-wrap {
		position: fixed;
		top: 0;
		right: 0;
		bottom: 0;
		width: min(360px, 85vw);
		background-color: var(--color-white);
		-webkit-box-orient: vertical;
		-webkit-box-direction: normal;
		    -ms-flex-direction: column;
		        flex-direction: column;
		-webkit-box-align: start;
		    -ms-flex-align: start;
		        align-items: flex-start;
		-webkit-box-pack: start;
		    -ms-flex-pack: start;
		        justify-content: flex-start;
		gap: var(--sp-32);
		/* padding-top clears the 48px toggle tile (y 23..71) with room to spare. */
		padding: var(--sp-80) var(--sp-24) var(--sp-40);
		overflow-y: auto;
		-webkit-transform: translateX(100%);
		    -ms-transform: translateX(100%);
		        transform: translateX(100%);
		-webkit-transition: -webkit-transform 0.3s ease;
		transition: -webkit-transform 0.3s ease;
		transition: transform 0.3s ease;
		transition: transform 0.3s ease, -webkit-transform 0.3s ease;
		z-index: 999;
		margin-left: 0;
	}

	.site-header__nav-wrap.is-open {
		-webkit-transform: translateX(0);
		    -ms-transform: translateX(0);
		        transform: translateX(0);
	}

	.main-navigation {
		width: 100%;
	}

	/*
	 * Rows carry their own 48px height now (28px line box + 10px top and
	 * bottom), so the list gap drops from 16 to 4 — the old 16 on top of
	 * zero-padding rows was both a small tap target and a loose list.
	 */
	.nav-menu {
		-webkit-box-orient: vertical;
		-webkit-box-direction: normal;
		    -ms-flex-direction: column;
		        flex-direction: column;
		-webkit-box-align: start;
		    -ms-flex-align: start;
		        align-items: flex-start;
		gap: var(--sp-4);
		width: 100%;
	}

	.nav-menu > li {
		-webkit-box-orient: vertical;
		-webkit-box-direction: normal;
		    -ms-flex-direction: column;
		        flex-direction: column;
		-webkit-box-align: start;
		    -ms-flex-align: start;
		        align-items: flex-start;
		width: 100%;
	}

	.nav-menu > li > a {
		width: 100%;
		padding-block: var(--sp-10);
		font-size: 20px;
		line-height: 1.4em;
		font-weight: 500;
	}

	/* No decorative dots in the stacked mobile menu. */
	.nav-menu > li + li::before {
		display: none;
	}

	/* ==================================================================
	   Submenu: tap-to-expand accordion, driven by the arrow only
	   ==================================================================
	   Hover is not a mobile input, so the panel no longer opens on hover here.
	   The chevron becomes a real 48px button (injected by js/site.js only at
	   this breakpoint) sitting in the row's top-right, and the parent stays a
	   plain link — so a tap on "Land Care" navigates and only a tap on the
	   arrow expands.

	   Animated with max-height + overflow:hidden. NOT min-height: animating
	   min-height was already proven on this project to shove everything below
	   it down mid-transition; max-height on a box that is 0 at rest cannot,
	   because the row's own height is what is being clipped.
	   ================================================================== */
	.nav-menu > li.menu-item-has-children > a {
		/* Reserve the arrow's 48px so long labels never run under it. */
		padding-right: var(--sp-48);
	}

	/* The pseudo-chevron is decorative and untappable — the button below
	   carries the real one. */
	.nav-menu > li.menu-item-has-children > a::after {
		display: none;
	}

	.nav-submenu-toggle {
		position: absolute;
		top: 0;
		right: 0;
		display: -webkit-box;
		display: -ms-flexbox;
		display: flex;
		-webkit-box-align: center;
		    -ms-flex-align: center;
		        align-items: center;
		-webkit-box-pack: center;
		    -ms-flex-pack: center;
		        justify-content: center;
		width: 48px;
		height: 48px;
		padding: 0;
		border-radius: var(--radius);
		background-color: transparent;
		-webkit-transition: var(--transition);
		transition: var(--transition);
	}

	.nav-submenu-toggle::before {
		content: "";
		width: 24px;
		height: 24px;
		background-color: var(--color-text);
		-webkit-mask: url("../images/icons/chevron-down.svg") no-repeat center / 24px 24px;
		mask: url("../images/icons/chevron-down.svg") no-repeat center / 24px 24px;
		-webkit-transition: var(--transition);
		transition: var(--transition);
	}

	.nav-submenu-toggle:hover,
	.nav-submenu-toggle:focus-visible {
		background-color: var(--color-bg-light);
	}

	.nav-submenu-toggle:hover::before,
	.nav-submenu-toggle[aria-expanded="true"]::before {
		background-color: var(--color-primary);
	}

	.nav-submenu-toggle[aria-expanded="true"]::before {
		-webkit-transform: rotate(180deg);
		    -ms-transform: rotate(180deg);
		        transform: rotate(180deg);
	}

	.nav-menu .sub-menu {
		position: static;
		opacity: 1;
		visibility: visible;
		-webkit-transform: none;
		    -ms-transform: none;
		        transform: none;
		-webkit-box-shadow: none;
		        box-shadow: none;
		border: 0;
		border-radius: 0;
		background-color: transparent;
		/* padding: 0 0 0 var(--sp-16); */
		min-width: 0;
		width: 100%;
		/* Collapsed. js/site.js sets max-height to the measured scrollHeight to
		   open, and back to 0 to close. */
		max-height: 0;
		overflow: hidden;
		-webkit-transition: max-height 0.3s ease;
		transition: max-height 0.3s ease;
	}

	/* The desktop panel is revealed on hover; here it is revealed only by the
	   arrow, so hover must not open it. */
	.nav-menu > li:hover > .sub-menu,
	.nav-menu > li:focus-within > .sub-menu {
		-webkit-transform: none;
		    -ms-transform: none;
		        transform: none;
	}

	.nav-menu .sub-menu a {
		padding: var(--sp-8) var(--sp-16);
		white-space: normal;
	}

	/* The dot and the hairlines carry over from the desktop panel — in an
	   indented accordion the dot reads as the list marker and the rules
	   separate the rows, which is the same job they do open on desktop. */

	.site-header__actions {
		-webkit-box-orient: vertical;
		-webkit-box-direction: normal;
		    -ms-flex-direction: column;
		        flex-direction: column;
		-webkit-box-align: stretch;
		    -ms-flex-align: stretch;
		        align-items: stretch;
		width: 100%;
	}

	.site-header__actions .btn {
		-webkit-box-pack: center;
		    -ms-flex-pack: center;
		        justify-content: center;
	}

	.site-header__overlay {
		display: block;
		position: fixed;
		inset: 0;
		background-color: rgba(0, 0, 0, 0.5);
		opacity: 0;
		visibility: hidden;
		-webkit-transition: var(--transition);
		transition: var(--transition);
		z-index: 998;
	}

	.site-header__overlay.is-visible {
		opacity: 1;
		visibility: visible;
	}

	/*
	 * KEPT, BUT IT IS NOT WHAT LOCKS THE SCROLL — see the html rule below. On its own
	 * this only clips the body box's own overflow, which changes nothing here because
	 * body is already as tall as its content.
	 */
html.menu-open,
body.menu-open {
    overflow: hidden;
    touch-action: none;
}
body.menu-open {
	position: fixed;
	width: 100%;
	left: 0;
	right: 0;
}
	/*
	 * `body.menu-open { overflow: hidden }` removes the vertical scrollbar, which
	 * widens the viewport the instant the panel opens. Measured: the document
	 * client width went 360 -> 375 on open at a 375px viewport, so the whole
	 * header shifted 15px right and the toggle tile visibly jumped at the exact
	 * moment it is supposed to read as the SAME control becoming the close.
	 *
	 * `scrollbar-gutter: stable` ALONE DOES NOT FIX THIS, which is worth
	 * recording: the property only applies to an actual scroll container, and
	 * html here computes `overflow-y: visible` — the scrollbar comes from
	 * viewport propagation, not from html being a scroller. Verified in place:
	 * scrollbar-gutter computed `stable`, CSS.supports true, and the 15px shift
	 * still happened. Making html an explicit scroll container is what actually
	 * holds the width constant across both states.
	 *
	 * Costs nothing on a real phone, where the scrollbar is an overlay.
	 */
	html {
		overflow-y: scroll;
		scrollbar-gutter: stable;
	}

	/*
	 * AND THE SCROLL LOCK HAS TO LAND HERE TOO, FOR THE SAME REASON THE RULE ABOVE
	 * EXISTS. This is the one thing that rule quietly broke.
	 *
	 * `body.menu-open { overflow: hidden }` only ever worked by viewport propagation:
	 * the body's overflow is propagated to the viewport, but ONLY while the root
	 * element's own overflow is `visible`. Making html an explicit scroll container
	 * to stop the 15px header jump ended that propagation, so from then on the
	 * body rule clipped nothing and the page scrolled behind the open panel.
	 * Measured at a 375px viewport with the panel open: body overflow computed
	 * `hidden`, and window.scrollY still went to 900 on scrollTo and 1500 after a
	 * wheel gesture.
	 *
	 * NO WIDTH COMPENSATION IS NEEDED HERE, and that is worth stating because it looks
	 * like it should be. `hidden` is still a scroll container, so `scrollbar-gutter:
	 * stable` above keeps reserving the gutter and the content box stays exactly the
	 * width it was: measured 360 in both states at a 375px viewport, with the header
	 * and the container edges unmoved. (`documentElement.clientWidth` does report
	 * 360 -> 375 across the change, but that counts the reserved gutter as content
	 * area — it is not a layout shift. Adding padding to "correct" it was measured to
	 * shrink the real content box to 345, i.e. it caused the very jump it was meant
	 * to prevent.)
	 *
	 * `position: fixed` on the body — the usual scroll-lock idiom — is deliberately
	 * NOT used: `.site-header--sticky` is `position: sticky`, and sticky needs a
	 * scrolling ancestor, so taking the body out of flow would break the sticky
	 * header. Locking the root leaves the whole document in flow.
	 *
	 * The one cost is that making the root non-scrollable clamps its scroll offset to
	 * 0, so openMenu()/closeMenu() in js/site.js record the offset and put it back.
	 */
	html:has(body.menu-open) {
		overflow-y: hidden;
	}
}

/* Anyone who has asked for less motion gets both state changes instantly.
   Scoped to this breakpoint so the desktop dropdown is untouched. */
@media (prefers-reduced-motion: reduce) and (max-width: 999px) {
	.site-header__nav-wrap,
	.menu-toggle,
	.menu-toggle__bar,
	.nav-submenu-toggle,
	.nav-submenu-toggle::before,
	.nav-menu .sub-menu {
		-webkit-transition: none;
		transition: none;
	}
}

@media (max-width: 767px) {
	.site-header__logo {
		width: 180px;
		height: 122px;
		padding: 15px;
	}

	.site-header__nav-wrap {
		gap: var(--sp-24);
		padding: var(--sp-80) var(--sp-16) var(--sp-32);
	}

	.nav-menu > li > a {
		font-size: 18px;
		line-height: 1.556em;
		letter-spacing: 0;
	}

	.nav-menu .sub-menu a {
		letter-spacing: 0;
	}
	.site-header {
	padding-block: 10px;
}
}



@media (max-width: 479px) {
	.site-header__logo {
		width: 170px;
		height: 118px;
	}
}