/* candice — custom rules theme.json can't express.
   Kept intentionally small; grouped by concern. */

/* ---------------------------------------------------------------------------
   Global text rendering — match production's lighter type on macOS/WebKit.
   The browser default (subpixel smoothing) renders every heading and paragraph
   noticeably darker/heavier than the live site, which antialiases. NOTE:
   Questrial ships a single weight (400) — Google Fonts has no 500 — so a "500"
   only relabels the text, it can't render heavier glyphs. The real weight gap
   vs production was this smoothing, not the font-weight number.
--------------------------------------------------------------------------- */
body {
	-webkit-font-smoothing: antialiased;
	-moz-osx-font-smoothing: grayscale;
}

/* ---------------------------------------------------------------------------
   Depth system — the one elevation language for the site.

   The rule is compositional, not decorative: **page-width bands stay flat**
   (colour, whitespace and section rhythm separate them) and only discrete
   content objects lift off the page — event cards, article cards, the podcast
   banner, the About portrait. Nothing else gets a shadow. If a new component
   needs elevation, reach for a token here rather than inventing a value.

   Shadows are tinted with the brand navy, never neutral grey: a grey shadow
   over the cream bands reads muddy and cold, a navy-tinted one stays warm.
   Every shadow is short-offset and tight-blur so cards read as *paper on a
   page* rather than UI floating in space.

   Values come from the owner's spec. Note the navy used for tinting is
   #1E2851 (30,40,81) — one step off the theme.json `navy` token #212951
   (33,41,81). At these alphas the two are indistinguishable; the tokens below
   are kept literal so they match the spec exactly.
--------------------------------------------------------------------------- */
:root {
	/* ---------------------------------------------------------------------
	   Background system — three levels, deliberately restrained:

	     white page  <  light warm panel  <  stronger cream band

	   The first three alias existing tokens rather than repeating their
	   values, so there is still one source of truth per colour: the band
	   cream and the navy live in theme.json (where the block editor and the
	   `has-*-background-color` classes read them), and only the two values
	   that had no token — the panel fill and the hairline — are defined here.

	   `--color-navy` is the theme's #212951, not the #1E2851 the spec quotes:
	   3 points apart and indistinguishable, and adding a second navy would
	   put two nearly-identical blues into the system. The tint colour in
	   `--color-subtle-border` stays literal because it matches the elevation
	   tokens below, which are all built on rgba(30, 40, 81, …).
	--------------------------------------------------------------------- */
	--color-navy: var(--wp--preset--color--navy);
	--color-page-background: var(--wp--preset--color--white);
	--color-band-cream: var(--wp--preset--color--cream);
	--color-panel-background: #FBF7F2;
	--color-subtle-border: rgba(30, 40, 81, .06);

	/* Hairline that defines a card's edge where the shadow alone is too soft. */
	--candice-edge: 1px solid rgba(30, 40, 81, .08);

	--candice-elev-card: 0 6px 18px rgba(30, 40, 81, .07);   /* cards at rest   */
	--candice-elev-hover: 0 10px 26px rgba(30, 40, 81, .11); /* cards on hover  */
	--candice-elev-quiet: 0 4px 14px rgba(30, 40, 81, .06);  /* images          */
	--candice-elev-card-sm: 0 4px 12px rgba(30, 40, 81, .06);/* cards ≤781px    */

	/* One step above the card tier, for a page's single focal object (currently
	   the Meet Candy film). Two stops on purpose: a tight contact shadow to
	   seat it plus a wide soft one for lift, which reads as depth where a
	   single large blur reads as grey fog. Reach for this only when one element
	   is meant to carry the whole page's elevation — bands stay flat. */
	--candice-elev-focal:
		0 4px 10px rgba(30, 40, 81, .08),
		0 18px 40px rgba(30, 40, 81, .10);
	--candice-elev-focal-sm:
		0 3px 8px rgba(30, 40, 81, .07),
		0 10px 24px rgba(30, 40, 81, .09);

	/* Square corners throughout — matches the buttons and the editorial feel. */
	--candice-card-radius: 0;

	/* The brand's hard offset shadow — a printed-stationery device, not part of
	   the soft elevation scale above. One value so every primary button carries
	   the same block. Was three different sizes in two blues (12px #bcd3e6,
	   6px #b5d5db, 6px #dfdfdf); the owner picked the "View Posts" treatment.
	   The event-card CTA (--dfdfdf grey) is intentionally still separate. */
	--candice-btn-offset: 6px 6px 0 0 #b5d5db;

	--candice-lift: translateY(-2px);
	--candice-ease: 200ms cubic-bezier(.2, .6, .3, 1);

	/* Form controls carry a stronger hairline than --candice-edge on purpose.
	   A white field on the cream band is only ~1.09:1 against its surround, so
	   the border *is* the control boundary and has to clear WCAG 1.4.11's 3:1.
	   .55 navy measures ~3.5:1 on white and ~3.1:1 on cream; .08 would be
	   ~1.1:1 and effectively invisible. */
	--candice-field-edge: 1px solid rgba(30, 40, 81, .55);
}

/* ---------------------------------------------------------------------------
   Header + navigation
   Design: logo left · hamburger (center) · social right.
   Nav is ALWAYS an overlay (hamburger at every width), sliding in from the
   right as a cream panel. Mobile hides the social icons.
--------------------------------------------------------------------------- */
/* Flush top-level stacking — remove WP's default 1.5rem block-gap between
   the header, main content, and footer. */
.wp-site-blocks > * {
	margin-block-start: 0;
}
.wp-site-blocks {
	overflow-x: clip;
}

/* Keep the whole page — including the hero — in a single 1200px column that
   lines up with the header. The templates nest global padding twice; drop the
   inner one so content isn't double-inset (which had pushed the hero narrower
   and offset from the header). */
.entry-content.has-global-padding {
	padding-left: 0;
	padding-right: 0;
}

/* ---------------------------------------------------------------------------
   Vertical rhythm (home)
   Every boundary between the homepage's sections is 80px of white — one value,
   applied once. Before this the gaps measured 99 / 99 / 74 / 49 / 75px, which
   was never a decision: it was WordPress's default 24px block gap landing on
   top of five sections whose paddings had each been tuned in isolation.

   The 24px gap is dropped here and each section's own padding carries the
   rhythm instead. That padding lives in `.rebuild-src/home-content.html`,
   because block padding is an inline style no selector can beat (§4f.2).

   Two paddings are deliberately NOT on the 80px grid — they sit *inside* a
   coloured band rather than between sections, and the band's art depends on
   them:
     .candice-hero     40px      tuned to the corner motifs
     .candice-events   100/150   the 150 is what gives the bottom lattice room
                                 to clear the last card

   Scoped to `.home` so other routes keep their own spacing. Three classes, to
   beat core's `:root :where(.is-layout-constrained) > *` (0,2,0), which is
   printed after this stylesheet (§4f.1).
--------------------------------------------------------------------------- */
.home .entry-content > .wp-block-group {
	margin-block-start: 0;
}

/* ---------------------------------------------------------------------------
   Mobile page gutter — one value, owner's call.

   The bands had each been given their own horizontal padding, so scrolling a
   phone stepped the text edge in and out: hero 40 · events 50 · newsletter 38 ·
   footer 15 · meet-video 15, against the global 20 that About, the podcast
   banner, Blog, the page heroes and the Wall/Blog bodies already used. This
   token is that global 20 — the inset the owner picked off the About section —
   and every band below now references it instead of its own number.

   Vertical padding is untouched: it carries Home's 80px section rhythm (see the
   comment above) and is a separate decision.

   Several of these bands write their padding as a block inline style, which no
   ordinary selector can outrank — hence `!important` at those call sites (§4f.2,
   same as the events rule that was already doing this).
--------------------------------------------------------------------------- */
:root {
	--candice-gutter-m: 20px;
}

.candice-header {
	background: #fff;
}

/* The header rides along at the top of every route. `sticky` rather than
   `fixed`: it keeps the bar in normal flow, so nothing below has to be pushed
   down by a hand-maintained header-height offset (and the block editor, which
   loads this same stylesheet, keeps rendering the template part in place).
   Every template puts the part in `.wp-site-blocks > header`; the one route
   without it (page-no-header) is unaffected.

   The wrapper's height is pinned to --candice-header-h and the white bar sits
   inside it. That split is what lets the bar compact on scroll without the page
   lurching: the wrapper's flow height never changes, so nothing below it ever
   moves, and the bar's own resize can't reflow anything outside the header.
   The strip the shrinking bar vacates is transparent, so content scrolls
   through it — hence pointer-events: none there, re-armed on the bar itself,
   so links passing under the compacted bar stay clickable. */
.wp-site-blocks > header {
	position: sticky;
	top: 0;
	z-index: 100;
	height: var(--candice-header-h);
	pointer-events: none;
}
.candice-header {
	/* min-height, not height: also squares up ≤340px, where the logo is
	   width-constrained and the bar would otherwise sit ~9px short of the
	   wrapper and leave a seam above a cream hero. */
	min-height: var(--candice-header-h);
	pointer-events: auto;
}
/* The admin bar is itself fixed at the top for logged-in users; below 783px
   core switches it to absolute so it scrolls away, and the offset goes back to 0. */
.admin-bar .wp-site-blocks > header {
	top: 32px;
}
@media (max-width: 782px) {
	.admin-bar .wp-site-blocks > header {
		top: 0;
	}
}

/* Scrolled state, over the page's first 6rem: the bar compacts 108px → 68px and
   a whisper of a shadow fades in. The shadow earns its keep — the bar is white
   and so is much of the copy, so without a boundary scrolled headings clip
   mid-glyph and read as a rendering fault rather than as content passing
   behind. Both are driven by the scroll timeline, so the bar is full-size and
   perfectly flat at rest and no JS or scroll listener is involved; browsers
   without scroll-driven animations just keep the full-size bar. */
@supports (animation-timeline: scroll()) {
	.candice-header,
	.candice-header__bar,
	.candice-header__bar > .candice-logo img {
		animation-timing-function: linear;
		animation-fill-mode: both;
		animation-timeline: scroll();
		animation-range: 0 6rem;
	}
	.candice-header {
		animation-name: candice-header-lift, candice-header-compact;
	}
	.candice-header__bar {
		animation-name: candice-bar-compact;
	}
	/* Beats the block's inline width:140px — animation declarations outrank the
	   style attribute in the cascade. */
	.candice-header__bar > .candice-logo img {
		animation-name: candice-logo-compact;
	}

	@keyframes candice-header-lift {
		from {
			box-shadow: 0 1px 0 rgba(33, 41, 81, 0), 0 6px 16px rgba(33, 41, 81, 0);
		}
		to {
			box-shadow: 0 1px 0 rgba(33, 41, 81, 0.07), 0 6px 16px rgba(33, 41, 81, 0.06);
		}
	}
	@keyframes candice-header-compact {
		from {
			min-height: var(--candice-header-h);
		}
		to {
			min-height: var(--candice-header-compact-h);
		}
	}
	@keyframes candice-bar-compact {
		from {
			padding-top: 1rem;
			padding-bottom: 1rem;
		}
		to {
			padding-top: 0.5rem;
			padding-bottom: 0.5rem;
		}
	}
	@keyframes candice-logo-compact {
		from {
			width: 140px;
		}
		to {
			width: 96px;
		}
	}

	/* Reduced motion keeps the shadow (it's a boundary cue, not movement) but
	   holds the bar at full size — a header that resizes under you is exactly
	   the sort of scroll-linked effect the preference is asking us to drop. */
	@media (prefers-reduced-motion: reduce) {
		.candice-header {
			animation-name: candice-header-lift;
		}
		.candice-header__bar,
		.candice-header__bar > .candice-logo img {
			animation-name: none;
		}
	}
}

/* In-page jumps (`#newsletter` from the nav and the footer) would otherwise land
   underneath the sticky bar. --candice-header-h is the at-rest bar (76px logo +
   2 × 1rem padding); --candice-header-compact-h is what it settles to once
   scrolled (96px logo + 2 × 0.5rem). An anchor jump always lands well past the
   6rem compaction range, so it clears the *compact* bar — but the offset only
   narrows to that where the compaction actually runs; everywhere else it stays
   on the full height, so a target can never end up hidden behind the bar. */
:root {
	--candice-header-h: 108px;
	--candice-header-compact-h: 68px;
	--candice-anchor-offset: var(--candice-header-h);
}
@supports (animation-timeline: scroll()) {
	@media (prefers-reduced-motion: no-preference) {
		:root {
			--candice-anchor-offset: var(--candice-header-compact-h);
		}
	}
}
[id] {
	scroll-margin-top: calc(var(--candice-anchor-offset) + 1rem);
}

/* Header layout: logo far-left · Display Menu centred · hamburger far-right.
   Grid (1fr auto 1fr) keeps the centre menu truly centred regardless of the
   logo/hamburger widths. */
.candice-header__bar.is-layout-flex {
	display: grid;
	grid-template-columns: 1fr auto 1fr;
	align-items: center;
	gap: 1rem;
}
.candice-header__bar > .candice-logo {
	justify-self: start;
	margin: 0;
}
.candice-header__bar > .candice-display-nav {
	justify-self: center;
}
.candice-header__bar > .candice-nav {
	justify-self: end;
	grid-column: 3;
}
.candice-display-nav .wp-block-navigation-item__content {
	position: relative;
	color: var(--wp--preset--color--navy);
	font-weight: 400;
}
/* Luxurious hover: a fine underline drawn in from the centre — no colour
   change, no layout shift. */
.candice-display-nav .wp-block-navigation-item__content::after {
	content: "";
	position: absolute;
	left: 0;
	right: 0;
	bottom: -0.35rem;
	height: 1px;
	background: currentColor;
	transform: scaleX(0);
	transform-origin: center;
	transition: transform 0.4s cubic-bezier(0.19, 1, 0.22, 1);
}
.candice-display-nav .wp-block-navigation-item__content:hover::after,
.candice-display-nav .current-menu-item .wp-block-navigation-item__content::after {
	transform: scaleX(1);
}
/* Below this width the centre menu would crowd the logo + hamburger, so hide
   it — everything is still reachable from the Primary hamburger. */
@media (max-width: 860px) {
	.candice-header__bar > .candice-display-nav {
		display: none;
	}
}

/* The hamburger (Navigation "open" button) */
.candice-header .wp-block-navigation__responsive-container-open,
.candice-header .wp-block-navigation__responsive-container-close {
	color: var(--wp--preset--color--navy);
}
.candice-header .wp-block-navigation__responsive-container-open svg,
.candice-header .wp-block-navigation__responsive-container-close svg {
	fill: currentColor;
	width: 28px;
	height: 28px;
}

/* Horizontal desktop menu items */
.candice-nav {
	font-family: var(--wp--preset--font-family--inter);
}
/* Submenu parents are <button>s — stop the global navy button style leaking in */
.candice-nav .wp-block-navigation-item__content,
.candice-nav button.wp-block-navigation-item__content,
.candice-nav .wp-block-navigation-submenu__toggle {
	background-color: transparent !important;
	border: 0;
	box-shadow: none;
	padding-left: 0;
	padding-right: 0;
	color: var(--wp--preset--color--navy);
}
.candice-nav .wp-block-navigation-item__content {
	color: var(--wp--preset--color--navy);
	font-weight: 500;
}
.candice-nav .wp-block-navigation-item__content:hover,
.candice-nav .wp-block-navigation-item.current-menu-item .wp-block-navigation-item__content {
	color: var(--wp--preset--color--red);
}
.candice-nav .wp-block-navigation__submenu-container {
	background: #fff;
	box-shadow: 0 10px 30px rgba(33, 41, 81, 0.15);
	border: 0;
}

/* Social icons — navy circular */
.candice-social .wp-block-social-links {
	gap: 0.5rem;
}
.candice-social .wp-social-link {
	background: var(--wp--preset--color--navy);
	color: #fff;
}
@media (max-width: 767px) {
	.candice-social {
		display: none;
	}
}

/* Overlay nav → right-hand cream panel (override core full-screen overlay) */
.wp-block-navigation__responsive-container.is-menu-open {
	background-color: var(--wp--preset--color--cream);
	inset: 0 0 0 auto;
	width: fit-content;
	max-width: 85vw;
	padding: 3.5rem 2.5rem;
	box-shadow: -12px 0 40px rgba(33, 41, 81, 0.18);
}
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-close {
	color: var(--wp--preset--color--navy);
}
/* Let the panel size to the longest menu item (+ the padding above) */
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content,
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation {
	width: max-content;
	max-width: 100%;
}
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation__responsive-container-content {
	align-items: flex-start;
	justify-content: flex-start;
	margin-top: 2rem;
}
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item__content {
	position: relative;
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 1.35rem;
	color: var(--wp--preset--color--navy);
}
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item__content::after {
	content: "";
	position: absolute;
	left: 0;
	bottom: -0.2rem;
	width: 100%;
	height: 1px;
	background: currentColor;
	transform: scaleX(0);
	transform-origin: left;
	transition: transform 0.35s cubic-bezier(0.19, 1, 0.22, 1);
}
.wp-block-navigation__responsive-container.is-menu-open .wp-block-navigation-item__content:hover::after {
	transform: scaleX(1);
}

/* ---------------------------------------------------------------------------
   Buttons — navy with a pale-blue offset shadow (the "ORDER YOUR COPY" style)
--------------------------------------------------------------------------- */
/* Matched to the "View Posts" button (.candice-blog__btn) — the owner's chosen
   reference for every primary CTA. Everything here restates that button: the
   theme.json defaults (Inter 500 at `medium`, 0.9rem 2rem padding) rendered
   these noticeably larger and heavier, and the offset block was twice the size
   in a different blue. `line-height: 1em` + `nowrap` are what keep the button
   the same 47px tall whatever the label. */
.candice-btn-offset .wp-block-button__link,
.wp-block-button.candice-btn-offset .wp-block-button__link {
	padding: 16px 25px;
	border-radius: 0;
	background: var(--wp--preset--color--navy);
	color: #fff;
	font-size: 15px;
	font-weight: 400;
	line-height: 1em;
	text-transform: uppercase;
	white-space: nowrap;
	box-shadow: var(--candice-btn-offset);
	transition: box-shadow 0.15s ease;
}
/* theme.json turns buttons red on hover; these clear the offset block instead
   and hold the navy, which is what "View Posts" does. */
.candice-btn-offset .wp-block-button__link:hover {
	background: var(--wp--preset--color--navy);
	color: #fff;
	box-shadow: none;
	transform: none;
}

/* ---------------------------------------------------------------------------
   Geometric motifs (hero + section corners). Absolute, decorative, aria-hidden.
--------------------------------------------------------------------------- */
.candice-motif {
	position: absolute;
	z-index: 0;
	pointer-events: none;
	max-width: 40%;
	height: auto;
}
.candice-motif--tl {
	top: 0;
	left: 0;
}
.candice-motif--br {
	right: 0;
	bottom: 0;
}
.candice-has-motifs {
	position: relative;
	overflow: hidden;
}
.candice-has-motifs > *:not(.candice-motif) {
	position: relative;
	z-index: 1;
}

/* hero1 (tall) is sized by HEIGHT to match hero2's WIDTH, so both motifs
   have the same "length" and read as a balanced pair. */
.candice-hero .candice-motif--tl {
	height: clamp(225px, 45vw, 570px);
	width: auto;
	max-width: none;
	top: 0;
	left: 0;
}
.candice-hero .candice-motif--br {
	width: clamp(150px, 30vw, 380px);
	right: 0;
	bottom: 0;
}

/* Hero balance: columns top-aligned and starting level (no stray widget
   margins), book cover trimmed so it doesn't overpower, and a deliberate
   vertical rhythm in the centre column. No fixed heights anywhere. */
.candice-hero .wp-block-columns {
	align-items: flex-start;
	margin-block-start: 0;
	margin-block-end: 0;
}
.candice-hero .wp-block-column > :first-child {
	margin-top: 0;
}
.candice-hero figure.wp-block-image {
	margin-top: 0;
	margin-bottom: 0;
}
.candice-hero__book img {
	max-width: 95%;
	height: auto;
	margin-inline: auto;
	display: block;
}
.candice-hero__text > * {
	margin-top: 0;
	margin-bottom: 0;
}
.candice-hero__text > * + * {
	margin-top: 1.15rem;
}
.candice-hero__text h1 {
	margin-top: 0.4rem;
}
.candice-hero__eyebrow,
.candice-hero__text h1 {
	font-weight: 500;
}
.candice-hero__text .wp-block-buttons {
	margin-top: 1.9rem;
}
/* Portrait caption sits close under the headshot */
.candice-hero__portrait > p {
	margin-top: 0.5rem;
}
/* Left-align the body paragraphs; the eyebrow and heading stay centred.
   `:not(.candice-hero__release)` is deliberately kept even though the release-
   date paragraph was removed from the hero (the book is out; the "September,
   2025" line had gone stale). It no longer excludes anything, but `:not()`
   counts toward specificity (§4f.8) — dropping it would take this rule from
   (0,3,1) to (0,2,1) and change which declarations win. Leave it. */
.candice-hero__text p:not(.candice-hero__eyebrow):not(.candice-hero__release) {
	text-align: left;
	line-height: 1.5;
}

/* ≤1099px: drop the portrait; book + text share the width; release date and
   button align left. Below 782px the columns stack (WordPress default). */
@media (max-width: 1099px) {
	.candice-hero__portrait {
		display: none;
	}
	.candice-hero .candice-motif--br {
		display: none;
	}
	/* hero1 locked to the top; sized in vw so it scales with the book as the
	   screen narrows, keeping their bottoms roughly aligned. */
	.candice-hero .candice-motif--tl {
		top: 0;
		height: 49vw;
	}
	.candice-hero__book {
		align-self: flex-start !important;
	}
	.candice-hero__text .wp-block-buttons {
		justify-content: flex-start !important;
	}
}
/* The hero's 40px was tuned to the corner motifs, but --tl is anchored to the
   band's own left edge, not to the padding, so narrowing the gutter moves the
   copy away from it rather than into it. Verified: no collision at 320–767. */
@media (max-width: 767px) {
	.candice-hero {
		padding-left: var(--candice-gutter-m) !important;
		padding-right: var(--candice-gutter-m) !important;
	}
}
/* ≤781 core stacks the two hero columns, at which point the text column's own
   20px is no longer a gutter between book and copy — it just doubles up on the
   band's padding and insets the hero copy further than anything else on the
   page. Zeroed here rather than removed from the block, because it is still
   doing its job at 782+. Inline block padding, so !important (§4f.2). */
@media (max-width: 781px) {
	.candice-hero__text {
		padding-left: 0 !important;
		padding-right: 0 !important;
	}
}
@media (min-width: 782px) and (max-width: 1099px) {
	.candice-hero__book {
		flex-basis: 40% !important;
	}
	.candice-hero__text {
		flex-basis: 60% !important;
	}
}
/* ≤781px the columns stack. Cream-background sections stretch to the page
   edges, the book becomes full-width, and hero1 grows to keep its bottom near
   the book's bottom. */
@media (max-width: 781px) {
	.entry-content > .has-cream-background-color {
		margin-left: calc(50% - 50vw) !important;
		margin-right: calc(50% - 50vw) !important;
		max-width: 100vw !important;
		width: 100vw;
	}
	/* hero1 ≈ 80% of the (full-width) book image's height */
	.candice-hero .candice-motif--tl {
		height: calc(116vw - 93px);
	}
}
/* ---------------------------------------------------------------------------
   About Me — values transcribed EXACTLY from the production Elementor data
   (.rebuild-src/page-129-elementor.json, the pre-rebuild live site), so this
   section matches candicemorrowauthor.com rather than an eyeballed approximation.
   Production breakpoints are Elementor's: tablet ≤1024px, mobile ≤767px.

   Reference (desktop / tablet):
     columns      50% / 50%, no gap; L padding-right 40 (30); R padding-left 40 (30)
     eyebrow      Noto Serif 15px italic 400, navy
     title        Questrial 48px (32) w500, line-height 55px (40), word-spacing 10px, centred
     subhead      Questrial 22px (20) normal, centred
     photo        width 100%, no margin
     motif        width 60% (75%), left, margin-top -20px, padding-left 40px
     lead         Noto Serif 20px (17) italic 400, line-height 1.8, navy
     body         Inter 16px (15) 400, line-height 1.8, rgba(0,0,0,.69)
     button       margin-top 20px, padding 16px 25px, left (centred on mobile)
--------------------------------------------------------------------------- */
.candice-about .wp-block-columns {
	align-items: flex-start;
	gap: 0;
}
.candice-about__left {
	padding-right: 40px;
}
.candice-about__right {
	padding-left: 40px;
}

/* Eyebrow — Noto Serif 15 italic */
.candice-about__eyebrow {
	margin-top: 0;
	margin-bottom: 20px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 15px;
	font-style: italic;
	font-weight: 400;
	line-height: 1.4;
}

/* Title — Questrial 48/55, weight 500, word-spacing 10px */
.candice-about__title {
	margin-top: 0;
	margin-bottom: 20px;
	color: var(--wp--preset--color--heading);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 48px;
	font-weight: 500;
	line-height: 55px;
	word-spacing: 10px;
}

/* Subhead — Questrial 22, upright (production sets no italic) */
.candice-about__subhead {
	margin-top: 0;
	margin-bottom: 20px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 22px;
	font-style: normal;
	font-weight: 400;
	line-height: 1.4;
}

.candice-about-photo {
	margin-top: 0;
	margin-bottom: 0;
}
/* Image-only elevation, and the quietest step in the system — the portrait sits
   on plain white with no frame of its own, so it needs just enough shadow to
   read as a photograph laid on the page. The *section* stays flat: composition
   and whitespace separate About from its neighbours, not a card. */
.candice-about-photo img {
	width: 100%;
	height: auto;
	display: block;
	box-shadow: var(--candice-elev-quiet);
}

/* Decorative navy lattice — sits flush under the photo, inset 40px from the
   left. (Production used margin-top:-20px; owner prefers 0.) */
.candice-about-motif {
	margin-top: 0;
	margin-bottom: 0;
	padding-left: 40px;
}
.candice-about-motif img {
	width: 60%;
	height: auto;
	display: block;
}

/* Lead-in — Noto Serif 20 italic, navy. Line-height tightened to 1.5 (owner's
   call); production was 1.8. */
.candice-about-lead {
	margin-top: 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 20px;
	font-style: italic;
	font-weight: 400;
	line-height: 1.5;
}

/* Body copy — Inter 16, line-height 1.5 (production was 1.8) */
.candice-about__right > p:not(.candice-about-lead) {
	font-size: 16px;
	font-weight: 400;
	line-height: 1.5;
}

/* CTA — left-aligned under the story, 20px above it */
.candice-about-cta {
	justify-content: flex-start;
	margin-top: 20px;
}
.candice-about-cta .wp-block-button__link {
	padding: 16px 25px;
}

/* Tablet (Elementor ≤1024px) */
@media (max-width: 1024px) {
	.candice-about__left {
		padding-right: 30px;
	}
	.candice-about__right {
		padding-left: 30px;
	}
	.candice-about__title {
		font-size: 32px;
		line-height: 40px;
	}
	.candice-about__subhead {
		font-size: 20px;
	}
	.candice-about-motif img {
		width: 75%;
	}
	.candice-about-lead {
		font-size: 17px;
	}
	.candice-about__right > p:not(.candice-about-lead) {
		font-size: 15px;
	}
}

/* Stacked (WP stacks columns at ≤781px; production's mobile rules are ≤767px) */
@media (max-width: 781px) {
	.candice-about__left {
		padding-right: 0;
		padding-bottom: 30px;
	}
	.candice-about__right {
		padding-left: 0;
	}
	/* The lattice is a desktop/tablet flourish — the mobile comp runs the photo
	   straight into the story text. */
	.candice-about-motif {
		display: none;
	}
	/* Production centres the CTA on mobile. Core's own
	   .is-content-justification-left wins on specificity, so match it. */
	.candice-about__right .wp-block-buttons.candice-about-cta.is-content-justification-left {
		justify-content: center;
	}
}

/* Simple centered page hero (Wall, Contact, etc.) */
.candice-page-hero {
	text-align: center;
}
.candice-page-hero .candice-motif--tl {
	width: clamp(120px, 18vw, 210px);
	top: 0;
	left: 0;
}
.candice-page-hero .candice-motif--br {
	width: clamp(120px, 18vw, 210px);
	right: 0;
	bottom: 0;
}

/* ---------------------------------------------------------------------------
   Page hero, lattice variant — Meet Candy, The Wall, Contact, Blog
   The archived Elementor data for Meet Candy (revision 1723) has no hero at
   all — the live hero was added after that snapshot — so per §2a the owner's
   production screenshots are the source of truth here. Values:

     motif pair   corner-hero-top-mobile.png (ink flush to its TOP edge) +
                  hero2.png (ink flush to its BOTTOM edge). They are drawn as a
                  matched top-left / bottom-right set, which is why the old
                  corner-3 / corner-4 pair read wrong. Same pair the archived
                  "Wall Hero Section" template (post 1497) uses.
     motif width  25% of the band. Production (post 1497, and the comps at
                  29.3–29.6%) ran these at 30%; the owner has since dialled
                  them back to 25% so the corners read lighter.
     h1           kit global 12d28b3 → Questrial 52 / 48 / 42px, lh 1.2em,
                  weight 500, navy. (Questrial ships one weight — see §4f.6.)

   Meet Candy, Contact and Blog are title-only — Blog's standfirst was dropped
   at the owner's request on 2026-07-31. The Wall is the only route that still
   carries one under the h1, so it is the only place the `> p` rule below
   applies and the only band that runs taller than the 262px the other three
   settle at. The same padding applies either way; the band simply grows.

   Padding was originally 168/132px, sized off the 30% motif so the copy always
   cleared the corner art. At the owner's direction it is now a flat 100px on
   desktop and tablet, which is the deliberate look rather than a derived
   value: at 25% the motif is 11% of the band's width tall (846/372 aspect), so
   on a wide band the art still runs slightly taller than the padding. The h1
   is centred and the motifs are cornered, so they pass each other; only a
   standfirst long enough to fill the band would come close. The 767px stop
   below stays motif-derived, because there the band is full-bleed and the
   motifs widen to 36% — a flat 100px would put the h1 inside the art.
--------------------------------------------------------------------------- */
.candice-page-hero.candice-page-hero--lattice {
	/* Width of each corner lattice as a share of the band. Declared on the
	   section rather than on the pseudo-elements so the flush-edge offsets
	   below can be derived from it — change this one value and they follow. */
	--candice-motif-w: 25%;
	padding-top: 100px;
	padding-bottom: 100px;
	/* The band carries no side padding of its own once it goes full-bleed, so a
	   short centred h1 looked fine but The Wall's standfirst ran to the very
	   edge of the screen. Set it explicitly rather than relying on the layout
	   support. The motifs are anchored to the band edges and are unaffected. */
	padding-inline: max(20px, 5vw);
}
.candice-page-hero--lattice > h1 {
	margin: 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 52px;
	font-weight: 500;
	line-height: 1.2em;
}
/* Drawn as pseudo-elements rather than <img> in the page content. Two reasons:
   they are purely decorative (nothing for a screen reader to skip past), and
   WordPress's layout-support filter was grafting `has-global-padding
   is-layout-constrained …` onto the *second* raw <img> inside the group
   instead of onto the <section>, which padded the motif and left the section
   unconstrained. No raw tags in the block, no misplaced classes. */
.candice-page-hero--lattice::before,
.candice-page-hero--lattice::after {
	content: "";
	position: absolute;
	z-index: 0;
	width: var(--candice-motif-w);
	aspect-ratio: 846 / 372;
	background-repeat: no-repeat;
	background-size: 100% 100%;
	pointer-events: none;
}
/* Both PNGs sit flush to the band edge they are anchored to *vertically* — the
   top art has zero transparent rows above it, the bottom art zero below. Their
   outer *horizontal* edges are not: each carries 10px of empty pixels out of
   846 (1.182%), which rendered as a 4px sliver of cream between the lattice
   and the side of the band. Pull each one out by exactly that fraction so the
   ink lands on the edge. The offset is a share of the motif's own width, and
   `left`/`right` percentages resolve against the same containing block that
   `width` does, so `--candice-motif-w * -0.01182` is the correct nudge at any
   width — including the 36% mobile stop. `.candice-has-motifs` already sets
   overflow:hidden, so the empty pixels are clipped rather than widening the
   band. Change these only if the source art is recropped. */
.candice-page-hero--lattice::before {
	top: 0;
	left: calc(var(--candice-motif-w) * -0.01182);
	background-image: url("/wp-content/uploads/2024/11/corner-hero-top-mobile.png");
}
.candice-page-hero--lattice::after {
	right: calc(var(--candice-motif-w) * -0.01182);
	bottom: 0;
	background-image: url("/wp-content/uploads/2024/11/hero2.png");
}
/* Standfirst under the h1 — The Wall only. (This used to name Acknowledgement
   too; that page was dropped in the rebuild, and the retired URL is handled by
   the redirect in the deploy runbook §5.9a.) Production sets this as
   an h4 taking the kit's h4 global 3a607be — Questrial 24/24/22, w500, navy —
   with the widget adding italic and a 30px line-height. Questrial has no italic
   face, so this is a synthesised oblique; production does the same thing, since
   it loads the same single-weight family. */
.candice-page-hero--lattice > p {
	margin: 18px 0 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 24px;
	font-style: italic;
	font-weight: 500;
	line-height: 30px;
}

/* No padding override here — tablet keeps the 100px set above. The old 132px
   stop existed to clear the 30% motif; at 25% the art is short enough that the
   band reads better without the tablet bump, and stepping *up* from a 100px
   desktop would have inverted the scale anyway. */
@media (max-width: 1024px) {
	.candice-page-hero--lattice > h1 {
		font-size: 48px;
	}
	.candice-page-hero--lattice > p {
		font-size: 24px;
	}
}
/* The band runs edge to edge on a phone. On page routes that already comes from
   `.entry-content > .has-cream-background-color` (§4f.1, same 781px stop — keep
   the two in step), but the blog index is rendered by `home.html`, which has no
   post-content wrapper: its hero is a direct child of <main>, so that selector
   never reaches it and the band stayed inset while every other route bled. Name
   the hero itself. The lattice's own `padding-inline` keeps the copy off the
   screen edge once it goes full width. */
@media (max-width: 781px) {
	.candice-page-hero--lattice {
		margin-left: calc(50% - 50vw) !important;
		margin-right: calc(50% - 50vw) !important;
		max-width: 100vw !important;
		width: 100vw;
	}
}
@media (max-width: 767px) {
	/* The band is full-bleed here, so the motif is 36vw wide → 15.83vw tall
	   (36 ÷ 2.2742). A flat 82px clears that on a phone but not at 767, where
	   the art is 121px tall and the h1 lands inside it. 18vw stays above the
	   motif all the way up, and max() keeps the phone value at the 82px the
	   comps show. */
	.candice-page-hero.candice-page-hero--lattice {
		padding-top: max(82px, 18vw);
		padding-bottom: max(82px, 18vw);
	}
	.candice-page-hero--lattice > h1 {
		font-size: 42px;
	}
	.candice-page-hero--lattice > p {
		font-size: 22px;
		line-height: 1.35;
	}
	/* The comps run the lattices wider on a phone (36–38% of the band). Set the
	   variable, not `width`, so the flush-edge offsets scale with it. */
	.candice-page-hero.candice-page-hero--lattice {
		--candice-motif-w: 36%;
	}
}

/* ---------------------------------------------------------------------------
   Meet Candy — "A Note From Candy" video band
   Full-bleed warm band → floating card → copy on the left, the vertical film
   on the right. The film is 9:16 (Vimeo reports 240×426); the old 16/9 frame
   pillarboxed it and threw away ~68% of the picture area to black bars.
--------------------------------------------------------------------------- */
.candice-meet-video {
	width: 100vw;
	max-width: 100vw !important;
	margin-left: calc(50% - 50vw) !important;
	margin-right: calc(50% - 50vw) !important;
	position: relative;
	/* 2.5rem between sections, matching the Wall's `.candice-wall__invite`
	   margin. The band's padding *is* the gap (the card sits inside it), so
	   both stops are set here — and core's 1.5rem block gap above the section
	   has to be zeroed or the top reads 24px larger than the bottom. That rule
	   is `:root :where(.is-layout-constrained) > * + *`, (0,2,0) and printed
	   after the theme sheet, hence !important — same reason as the full-bleed
	   margins above (§4f.1). */
	--meet-pad-t: 2.5rem;
	--meet-pad-b: 2.5rem;
	margin-top: 0 !important;
	padding: var(--meet-pad-t) 20px var(--meet-pad-b);
	background: #fff;
	/* Corner lattices reach from behind the card out to the hero band's edge.
	   The hero is the 1200-capped content column (root padding is 5vw a side),
	   the card is centred on the same axis, so the overhang each side is half
	   their difference — computed rather than hard-coded so it tracks at every
	   width. */
	/* The card tracks the hero band: min(1200, 90vw) is the content column
	   (root padding is 5vw a side). On a phone the hero itself goes full-bleed
	   but 90vw still resolves to an inset value, so the card keeps a margin
	   rather than running edge to edge. */
	--meet-hero-w: min(1200px, 90vw);
	--meet-card-w: var(--meet-hero-w);
	--meet-video-w: 400px;
}
/* The panel level of the background system (§2b): lighter than the hero band,
   so it stays warm and on-brand but reads as a surface on white rather than a
   second cream slab. Was a one-off #FCF7EF — within a point of the token, and
   folded into it so the site carries one panel colour, not three. Square
   corners like the rest of the site. */
.candice-meet-card {
	max-width: var(--meet-card-w);
	margin-inline: auto !important;
	padding: 64px;
	gap: 40px;
	align-items: center;
	background: var(--color-panel-background);
	/* Editorial panel, not a floating card: no shadow, just colour + a navy
	   hairline to hold the edge now that the shadow is gone. Elevation on this
	   page belongs to the film alone (see .candice-video) — the same hierarchy
	   the homepage uses, where bands are flat and only discrete objects (event
	   cards, buttons, the podcast banner) lift.

	   Matted frame, same construction as the Wall's `.candice-wall__invite`: a
	   9px white border reads as a mount against the white band, and the
	   hairline is an `outline` pulled back onto the border box's outer edge, so
	   it sits 9px *outside* the panel rather than hugging it. Border-box sizing
	   means the outline — not the panel fill — is what aligns with the hero
	   band. Fill, mount and hairline all come from the §2b background system,
	   the same three tokens the Wall invite and the Contact panel use. */
	border: 9px solid var(--color-page-background);
	outline: 1px solid var(--color-subtle-border);
	outline-offset: -1px;
}
/* Was nudged down 40px so the copy cleared the lattice's lower-left tip. The
   100px under the rule (below) now does that job and more — it pushes the copy
   well past the lattice's bottom edge — so the column sits at true centre and
   the eyebrow + wordmark ride 40px higher. `position: relative` stays as the
   anchor if the nudge is ever wanted back; re-run the collision sweep in §4g if
   the rule's margin or the lattice's size changes. */
.candice-meet-card > .candice-meet-card__text {
	position: relative;
	top: 0;
	flex-basis: 55% !important;
	align-self: center;
	padding-left: 20px;
}
/* Positioning context for the lattice. With `align-items: center` on the card
   this column shrinks to the film's height, so the pseudo-element can be
   placed against the film's own top-left corner. */
.candice-meet-card > .candice-meet-card__media {
	position: relative;
	flex-basis: 45% !important;
}
/* corner-1 set against the top-left of the film, filling the gutter between
   the copy and the film. It lives on the column, not on .candice-video — that
   keeps `overflow: hidden` on the film, which the poster's hover zoom needs,
   and the column shrinks to exactly the film's height (`align-items: center`
   on the card) so `top` is measured from the film's own top edge. */
.candice-meet-card__media::before {
	content: "";
	position: absolute;
	z-index: 0;
	top: 40px;
	/* Anchored to the FILM's left edge, not the column's. min(--meet-video-w,
	   100%) is the film's real width: it is capped at --meet-video-w but
	   shrinks with the column, and below ~1150 the column is the narrower of
	   the two. Anchoring to the column instead (`left: -100px`) drifts from 98%
	   to 67% visible across the range, because column and film scale
	   differently. Tucking 24px behind the film leaves 126px of 150px showing —
	   84% — and that holds at every width. */
	right: calc(min(var(--meet-video-w), 100%) - 24px);
	width: 150px;
	aspect-ratio: 372 / 846;
	background: url("/wp-content/uploads/2024/11/corner-1.png") no-repeat 0 0 / 100% 100%;
	opacity: .9;
	pointer-events: none;
}
/* Film sits flush with the card's inner right edge, so the air between the
   copy and the film is a deliberate gutter — which is where the lattice goes. */
.candice-meet-card__media .candice-video {
	margin-right: 0;
	margin-left: auto;
}
.candice-meet__eyebrow {
	margin: 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 15px;
	font-weight: 400;
	letter-spacing: .3em;
	line-height: 1.4;
	text-transform: uppercase;
}
/* The wordmark is the brand's own lettering, so it's the logo asset rather
   than a script webfont. alt="Candy" gives the h2 its accessible name. */
.candice-meet__heading {
	margin: 14px 0 0;
	line-height: 0;
}
.candice-meet__heading img {
	width: 150px;
	max-width: 100%;
	height: auto;
}
/* core/separator caps itself at 100px via
   `.wp-block-separator:not(.is-style-wide):not(.is-style-dots)` — the two
   :not()s count as classes, so that selector is (0,3,0) and needs three
   classes here to beat it, not two. Same trap as §4f.1. */
.candice-meet-card__text hr.candice-meet__rule.wp-block-separator {
	width: 256px;
	max-width: 100%;
	height: 2px;
	/* Eyebrow → wordmark → rule → copy → link should read as one editorial
	   column. The 100px that used to sit here pushed the copy clear of the
	   lattice, but the lattice now tucks behind the film, so the gap is back to
	   a normal paragraph interval and the visual path holds. */
	margin: 24px 0 32px;
	border: 0;
	opacity: 1;
	background: #B8985E;
}
/* Cap the measure — the card is now hero-wide, and 55% of it is far past a
   comfortable reading line. */
.candice-meet__copy {
	margin: 22px 0 0;
	max-width: 46ch;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--inter);
	font-size: 16px;
	font-weight: 400;
	line-height: 1.5;
}
.candice-meet__copy em {
	font-style: italic;
}
/* CTA reads as a link, not a slab button — the arrow is CSS so it stays out of
   the accessible name and can slide on hover. */
.candice-meet__cta {
	margin: 26px 0 0;
}
.candice-meet__cta a {
	position: relative;
	display: inline-block;
	padding-bottom: 3px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 17px;
	line-height: 1.4;
	text-decoration: none;
}
/* Same focus ring the newsletter and Wall controls use. */
.candice-meet__cta a:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 3px;
}
.candice-meet__cta a::after {
	content: "\2192";
	/* Second declaration gives the glyph empty alt text so it stays out of the
	   link's accessible name; browsers without the `content / alt` syntax keep
	   the first declaration and still draw the arrow. */
	content: "\2192" / "";
	display: inline-block;
	margin-left: 8px;
	transition: transform .25s ease;
}
.candice-meet__cta a::before {
	content: "";
	position: absolute;
	right: 0;
	bottom: 0;
	left: 0;
	height: 1px;
	background: #B8985E;
	transform: scaleX(1);
	transform-origin: left;
	transition: transform .3s ease;
}
.candice-meet__cta a:hover::after,
.candice-meet__cta a:focus-visible::after {
	transform: translateX(5px);
}
.candice-meet__cta a:hover::before {
	transform: scaleX(0);
	transform-origin: right;
}
@media (prefers-reduced-motion: reduce) {
	.candice-meet__cta a::after,
	.candice-meet__cta a::before {
		transition: none;
	}
}

/* --- the film itself ---------------------------------------------------- */
.candice-video {
	position: relative;
	z-index: 1;
	width: 100%;
	max-width: var(--meet-video-w, 400px);
	margin-inline: auto;
	aspect-ratio: var(--candice-video-ratio, 9 / 16);
	overflow: hidden;
	background: #11162c;
	/* The page's single elevated object — see --candice-elev-focal in :root. */
	box-shadow: var(--candice-elev-focal);
}
.candice-video iframe {
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
	border: 0;
}
/* Poster + play control. A real <button>, so Enter/Space work and the label is
   announced; the player iframe is only injected once it's pressed. */
.candice-video__play {
	position: absolute;
	inset: 0;
	display: block;
	width: 100%;
	padding: 0;
	border: 0;
	background: none;
	cursor: pointer;
	-webkit-appearance: none;
	appearance: none;
}
.candice-video__poster {
	display: block;
	width: 100%;
	height: 100%;
	object-fit: cover;
	transition: transform .5s ease, filter .5s ease;
}
.candice-video__play::after {
	content: "";
	position: absolute;
	inset: 0;
	background: linear-gradient(180deg, rgba(17, 22, 44, .05) 0%, rgba(17, 22, 44, .10) 45%, rgba(17, 22, 44, .55) 100%);
	transition: opacity .4s ease;
}
.candice-video__icon {
	position: absolute;
	top: 50%;
	left: 50%;
	z-index: 2;
	width: 76px;
	height: 76px;
	transform: translate(-50%, -50%);
	border-radius: 50%;
	background: rgba(250, 241, 226, .94);
	box-shadow: 0 6px 20px rgba(17, 22, 44, .35);
	transition: transform .3s ease, background-color .3s ease;
}
/* Navy triangle, nudged right so it reads centred inside the circle. */
.candice-video__icon::before {
	content: "";
	position: absolute;
	top: 50%;
	left: 50%;
	width: 0;
	height: 0;
	transform: translate(-38%, -50%);
	border-left: 22px solid var(--wp--preset--color--navy);
	border-top: 13px solid transparent;
	border-bottom: 13px solid transparent;
}
.candice-video__label {
	position: absolute;
	width: 1px;
	height: 1px;
	margin: -1px;
	padding: 0;
	overflow: hidden;
	clip: rect(0 0 0 0);
	clip-path: inset(50%);
	white-space: nowrap;
	border: 0;
}
.candice-video__time {
	position: absolute;
	right: 12px;
	bottom: 12px;
	z-index: 2;
	padding: 4px 9px;
	border-radius: 3px;
	background: rgba(17, 22, 44, .8);
	color: #fff;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 12px;
	line-height: 1.3;
	letter-spacing: .04em;
}
.candice-video__play:hover .candice-video__poster,
.candice-video__play:focus-visible .candice-video__poster {
	transform: scale(1.03);
	filter: brightness(1.04);
}
.candice-video__play:hover .candice-video__icon,
.candice-video__play:focus-visible .candice-video__icon {
	background: #FAF1E2;
	transform: translate(-50%, -50%) scale(1.08);
}
.candice-video__play:focus-visible {
	outline: 3px solid var(--wp--preset--color--navy);
	outline-offset: -3px;
}
.candice-video noscript iframe {
	position: absolute;
	inset: 0;
	width: 100%;
	height: 100%;
	border: 0;
}
@media (prefers-reduced-motion: reduce) {
	.candice-video__poster,
	.candice-video__icon {
		transition: none;
	}
	.candice-video__play:hover .candice-video__poster,
	.candice-video__play:focus-visible .candice-video__poster {
		transform: none;
	}
}

@media (max-width: 1024px) {
	.candice-meet-video {
		--meet-video-w: 410px;
	}
	.candice-meet-card {
		padding: 44px;
		gap: 28px;
	}
	/* With the lattice gone below 1100 the gutter is free, so the columns go
	   50/50 and the film takes the width — ~44% of the card, which is as large
	   as it gets before the copy's measure drops below ~50 characters. */
	.candice-meet-card > .candice-meet-card__text {
		flex-basis: 50% !important;
		padding-left: 0;
	}
	.candice-meet-card > .candice-meet-card__media {
		flex-basis: 50% !important;
	}
}
/* Below this the card is too narrow for the lattice to sit in the gutter
   without crossing into the copy — that collision is horizontal, so no vertical
   nudge fixes it; the art is dropped rather than shrunk.

   The cutoff is measured, not guessed, and it is a direct function of how much
   art is exposed. What has to fit inside the card's content box is
   copy + lattice-exposed + film; the copy is capped at 46ch and the film is
   flush right, so the split between the columns does not change the sum.
   Swept 960–1400 in 10px steps against the ink box of every text element:

       exposed 126px (width 150)  → clear from 1280
       exposed 109px (width 130)  → clear from 1160
       exposed  92px (width 110)  → clear from 1060

   At the owner's 150px the art needs ≥1280. Shrink it to lower the cutoff. */
@media (max-width: 1279px) {
	.candice-meet-card__media::before {
		display: none;
	}
	/* (The `top: 0` that used to live here is now the base value — the copy sits
	   at true centre at every width.) */
}
/* ≤781px core stacks the columns; centre the copy over the film. */
@media (max-width: 781px) {
	.candice-meet-video {
		padding: var(--meet-pad-t) var(--candice-gutter-m) var(--meet-pad-b);
	}
	/* (The lattice is already gone below 1100.) Stacked, so the film re-centres
	   in its full-width column and grows as large as it can while the whole
	   9:16 frame still fits on screen. `width: 100%` caps it to the card, this
	   caps it to the viewport height — whichever is smaller wins. */
	.candice-meet-card__media .candice-video {
		margin-inline: auto;
		max-width: calc(78vh * 9 / 16);
	}
	.candice-meet-card {
		padding: 36px 24px 40px;
		gap: 30px;
		text-align: center;
	}
	/* Lighter lift on a small screen — the same shadow reads heavy once the
	   film is a large share of the viewport. */
	.candice-meet-card__media .candice-video {
		box-shadow: var(--candice-elev-focal-sm);
	}
	.candice-meet-card > .candice-meet-card__text {
		flex-basis: 100% !important;
	}
	.candice-meet-card > .candice-meet-card__media {
		flex-basis: 100% !important;
	}
	/* Stacked, so the 100px is dropped: centred copy directly under the wordmark
	   reads as one block, and on a phone that gap is dead scrolling. */
	.candice-meet-card__text hr.candice-meet__rule.wp-block-separator {
		margin-inline: auto;
		margin-bottom: 0;
	}
	/* The card centres its contents, but that is meant for the heading group —
	   eyebrow, wordmark, rule. Running text reads left-aligned everywhere else
	   on the site (same call as `.candice-hero__text p` at mobile), so the copy
	   and its CTA opt out. `margin-inline: 0` goes with it: left-aligned text
	   inside an auto-centred block would start well short of the card's content
	   edge once the 46ch cap binds on the wider stacked widths. */
	.candice-meet__copy,
	.candice-meet__cta {
		margin-inline: 0;
		text-align: left;
	}
	.candice-video__icon {
		width: 64px;
		height: 64px;
	}
}
/* svh is the viewport height with the mobile browser's chrome *expanded*, so
   it's the honest "will this fit right now" number; vh above is the fallback.
   Written as a separate @supports block rather than a second declaration on a
   custom property, because an unsupported unit inside a custom property is
   only invalid at computed-value time — it would blow away max-width entirely
   instead of falling back to the previous line. */
@supports (height: 1svh) {
	@media (max-width: 781px) {
		.candice-meet-card__media .candice-video {
			max-width: calc(78svh * 9 / 16);
		}
	}
}

/* ---------------------------------------------------------------------------
   Podcast banner — "Behind the Bruises"
   A stand-alone section between About and Events. The artwork has its own
   baked-in type, so there is no text to style here — the rules only size it,
   reserve its aspect box (no CLS while it lazy-loads), and make the whole
   banner a single tap target for the podcast channel.

   Art-directed, NOT merely resized: the owner supplies two crops, and the
   <picture> in home-content.html switches between them at 781px — WordPress's
   column-stacking breakpoint, so the banner goes portrait in step with the
   rest of Home rather than at the 767px used elsewhere (§4f.3) —

     >=782px   behind-the-bruises-{1280,2560}.webp   2560×500 wide strip
     <=781px   behind-the-bruises-mobile-854.webp     854×1500 stacked

   which is why aspect-ratio has to be re-declared at the breakpoint below. A
   single ratio would letterbox or squash whichever crop it doesn't match.

   All three files are built by .rebuild-src/build-podcast-banner.py, which
   also warms the wide crop's neutral-grey edge bands toward the cream token —
   rebuild with that script, not with cwebp by hand, or the tint is lost.
--------------------------------------------------------------------------- */
.candice-podcast-banner__img {
	margin: 0;
}
.candice-podcast-banner__img a {
	display: block;
}
.candice-podcast-banner__img img {
	display: block;
	width: 100%;
	height: auto;
	/* Intrinsic ratio, so the strip holds its height before the file lands */
	aspect-ratio: 2560 / 500;
	/* Same resting elevation as the cards. This was a neutral-grey shadow —
	   the one piece of depth on the page that sat outside the system. */
	box-shadow: var(--candice-elev-card);
	transition: transform var(--candice-ease), box-shadow var(--candice-ease);
}
/* The banner carries no affordance of its own (its "Subscribe" is painted on),
   so hover/focus have to come from here: the standard card lift, plus an
   explicit navy ring for keyboard users. */
.candice-podcast-banner__img a:hover img,
.candice-podcast-banner__img a:focus-visible img {
	transform: var(--candice-lift);
	box-shadow: var(--candice-elev-hover);
}
.candice-podcast-banner__img a:focus-visible {
	outline: 3px solid var(--wp--preset--color--navy);
	outline-offset: -3px;
}
/* Mobile crop — same breakpoint as the <picture> source, so the reserved box
   matches the file the browser actually picks. 781px, not the usual 767px:
   this is where WordPress stacks columns, so the banner flips to its portrait
   crop in step with the rest of Home rather than one breakpoint later. */
@media (max-width: 781px) {
	.candice-podcast-banner__img img {
		aspect-ratio: 854 / 1500;
	}
}
/* Reduced-motion is handled once for every lifted object, at the end of this
   file — see "Depth system — reduced motion". */

/* ---------------------------------------------------------------------------
   Events — "Speaking Engagements"
   Values transcribed from the production Elementor data + its global kit
   (page-129-elementor.json + uploads/elementor/css/post-388.css, kit 388),
   so this matches candicemorrowauthor.com rather than an approximation.
   Elementor breakpoints: tablet ≤1024px, mobile ≤767px.

   Resolved globals used here:
     colors    primary #212951 · text #000000B0 · cream #FAF1E2
     type 9cd366b (card title)  Questrial 26/24px w400 lh 1.3em
     type 202a1a5 (day number)  Questrial 59/56px w500
     type 6db22bd (month)       Inter 15px w400 lh 1.2em
     type text   (time/place)   Inter 16/15px w400 lh 1.8em
     type accent (button)       Inter 15/14px w400 lh 1em UPPERCASE
     type cf25776 (section h2)  Questrial 40/35/32px w400 lh 1.4em
--------------------------------------------------------------------------- */
/* The band's own padding is authored inline on the block (the section lives in
   Home's post content, not in a template), so evening it up has to happen here
   and needs !important to outrank the style attribute. It was 100px top /
   150px bottom; the owner asked for it level, and 100px is the value the top
   already used and the one the page heroes settled on. The bottom-left lattice
   is anchored to the band's bottom edge and sits behind the cards, so it rides
   up with the shorter band rather than being clipped. */
.candice-events {
	padding-bottom: 100px !important;
}
/* The 10px top margin drops the whole heading group — eyebrow and title move
   together, so their own 10px gap is unchanged. It exists for one place: the
   ~660–767px band, where the centred title runs closest to the top-right
   lattice's lower tail. Everywhere else it is 10px of extra air at the top of
   a 100px-padded band, i.e. invisible. Owner's call. */
.candice-events__eyebrow {
	margin: 10px 0 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 15px;
	font-style: italic;
	font-weight: 400;
}
.candice-events__title {
	margin: 10px 0 50px;
	padding-right: 40%;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 40px;
	font-weight: 400;
	line-height: 1.4em;
}
/* Decorative lattices: top-right and bottom-left of the cream band */
.candice-events .candice-motif--events-tr {
	top: 0;
	right: 3px;
	width: 40%;
	height: auto;
	max-width: none;
}
.candice-events .candice-motif--events-bl {
	left: 0;
	bottom: 0;
	width: 40%;
	height: auto;
	max-width: none;
}

/* The card list — cards are 1100px wide, 40px apart */
.candice-events-list {
	max-width: 1100px;
	margin-inline: auto;
}
/* The cards are the elevated objects here — the cream band behind them stays
   flat. Depth comes from the shared tokens (top of file) so these read as the
   same object as the article cards below. */
.candice-event {
	max-width: 1100px;
	margin: 40px auto 0;
	padding: 30px 0;
	background: #fff;
	border: var(--candice-edge);
	border-radius: var(--candice-card-radius);
	box-shadow: var(--candice-elev-card);
	transition: transform var(--candice-ease), box-shadow var(--candice-ease);
	align-items: center !important;
	flex-wrap: nowrap;
	gap: 0 !important;
}
/* :focus-within so keyboard users tabbing to the CTA get the same feedback as
   a mouse hover, not just the button's own focus ring. */
.candice-event:hover,
.candice-event:focus-within {
	transform: var(--candice-lift);
	box-shadow: var(--candice-elev-hover);
}

/* Date — olive rule on the right. NOTE: the archived Elementor data sets this
   panel to cream (#FAF1E2), but current production (owner's screenshots) shows
   it white like the rest of the card, so it stays transparent here. */
.candice-event__date {
	flex: 0 0 15%;
	align-self: stretch;
	display: flex;
	flex-direction: column;
	justify-content: center;
	padding: 10px 20px;
	border-right: 1px solid #538914;
	text-align: center;
}
.candice-event__day {
	margin: 0 0 5px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 59px;
	font-weight: 500;
	line-height: 1;
}
.candice-event__month {
	margin: 0;
	color: rgba(0, 0, 0, 0.69);
	font-size: 15px;
	font-weight: 400;
	line-height: 1.2em;
}

/* Info column */
.candice-event__info {
	flex: 1 1 55%;
	padding: 0 20px;
}
/* Elementor spaces stacked widgets 20px apart; the two icon rows sit 6px apart
   (icon-list space_between). */
.candice-event__info > * {
	margin-top: 0;
	margin-bottom: 0;
}
.candice-event__info > * + * {
	margin-top: 20px;
}
.candice-event__title {
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 26px;
	font-weight: 400;
	line-height: 1.3em;
}
.candice-event__desc,
.candice-event__host {
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 22px;
	font-weight: 400;
	line-height: 1.3em;
}
.candice-event__host a {
	color: inherit;
}
/* Time + location: Inter, with the icon drawn as a masked SVG so no icon font
   is needed. Icon 15px, 8px gap to the text, 6px between the two rows. */
.candice-event__time,
.candice-event__place {
	display: flex;
	align-items: center;
	gap: 8px;
	color: rgba(0, 0, 0, 0.69);
	font-size: 16px;
	font-weight: 400;
	line-height: 1.8em;
}
.candice-event__place {
	margin-top: 6px !important;
}
.candice-event__time::before,
.candice-event__place::before {
	content: "";
	flex: 0 0 auto;
	width: 15px;
	height: 15px;
	background-color: var(--wp--preset--color--navy);
	-webkit-mask-repeat: no-repeat;
	mask-repeat: no-repeat;
	-webkit-mask-position: center;
	mask-position: center;
	-webkit-mask-size: contain;
	mask-size: contain;
}
.candice-event__time::before {
	-webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 512 512'%3E%3Cpath d='M256 8C119 8 8 119 8 256s111 248 248 248 248-111 248-248S393 8 256 8zm57.1 350.1L224.9 294c-3.1-2.3-4.9-5.9-4.9-9.7V116c0-6.6 5.4-12 12-12h48c6.6 0 12 5.4 12 12v137.7l63.5 46.2c5.4 3.9 6.5 11.4 2.6 16.8l-28.2 38.8c-3.9 5.3-11.4 6.5-16.8 2.6z'/%3E%3C/svg%3E");
	mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 512 512'%3E%3Cpath d='M256 8C119 8 8 119 8 256s111 248 248 248 248-111 248-248S393 8 256 8zm57.1 350.1L224.9 294c-3.1-2.3-4.9-5.9-4.9-9.7V116c0-6.6 5.4-12 12-12h48c6.6 0 12 5.4 12 12v137.7l63.5 46.2c5.4 3.9 6.5 11.4 2.6 16.8l-28.2 38.8c-3.9 5.3-11.4 6.5-16.8 2.6z'/%3E%3C/svg%3E");
}
.candice-event__place::before {
	-webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 384 512'%3E%3Cpath d='M172.268 501.67C26.97 291.031 0 269.413 0 192 0 85.961 85.961 0 192 0s192 85.961 192 192c0 77.413-26.97 99.031-172.268 309.67-9.535 13.774-29.93 13.773-39.464 0zM192 272c44.183 0 80-35.817 80-80s-35.817-80-80-80-80 35.817-80 80 35.817 80 80 80z'/%3E%3C/svg%3E");
	mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 384 512'%3E%3Cpath d='M172.268 501.67C26.97 291.031 0 269.413 0 192 0 85.961 85.961 0 192 0s192 85.961 192 192c0 77.413-26.97 99.031-172.268 309.67-9.535 13.774-29.93 13.773-39.464 0zM192 272c44.183 0 80-35.817 80-80s-35.817-80-80-80-80 35.817-80 80 35.817 80 80 80z'/%3E%3C/svg%3E");
}
.candice-event__place a {
	color: inherit;
}

/* CTA — full-width navy button with a hard grey offset shadow */
/* Child selector needed: core's `:root :where(.is-layout-flex) > *` resets the
   margin at equal specificity and is printed after the theme stylesheet. */
.candice-event > .candice-event__cta {
	flex: 0 0 30%;
	margin: 0 50px 0 20px;
}
.candice-event__cta .wp-block-buttons {
	margin: 0;
}
.candice-event__btn {
	width: 100%;
}
.candice-event__btn .wp-block-button__link {
	display: block;
	width: 100%;
	padding: 16px 25px;
	border-radius: 0;
	background: var(--wp--preset--color--navy);
	color: #fff;
	font-size: 15px;
	font-weight: 400;
	line-height: 1em;
	text-align: center;
	text-transform: uppercase;
	box-shadow: 6px 6px 0 0 #dfdfdf;
	transition: box-shadow 0.15s ease;
}
.candice-event__btn .wp-block-button__link:hover {
	box-shadow: none;
}

/* Tablet ≤1024: the button drops to its own full-width row */
@media (max-width: 1024px) {
	.candice-event {
		flex-wrap: wrap;
		padding: 30px;
	}
	.candice-event__date {
		flex: 0 0 30%;
		padding: 10px;
	}
	.candice-event__day {
		font-size: 56px;
	}
	.candice-event__info {
		flex: 1 1 70%;
		padding: 0 0 0 30px;
	}
	.candice-event__title {
		font-size: 24px;
	}
	.candice-event__desc,
	.candice-event__host {
		font-size: 24px;
	}
	.candice-event__time,
	.candice-event__place {
		font-size: 15px;
	}
	.candice-event > .candice-event__cta {
		flex: 0 0 100%;
		margin: 40px 0 0;
	}
	.candice-event__btn .wp-block-button__link {
		font-size: 14px;
	}
	.candice-events__title {
		font-size: 35px;
	}
}

/* Mobile ≤767: everything stacks; the date rule moves to the bottom edge */
@media (max-width: 767px) {
	/* Owner's mobile padding. !important is required because the block writes
	   its padding as an inline style, which no ordinary selector can outrank.
	   The horizontal 50px was the owner's earlier call; it now defers to the
	   shared mobile gutter so the text edge doesn't step in and out on a phone. */
	.candice-events {
		padding: 75px var(--candice-gutter-m) 125px !important;
	}
	.candice-event {
		padding: 30px 20px;
	}
	.candice-event__date {
		flex: 0 0 100%;
		padding: 10px 0 20px;
		border-right: 0;
		border-bottom: 1px solid #538914;
	}
	.candice-event__info {
		flex: 0 0 100%;
		padding: 30px 0 0;
	}
	.candice-events__title {
		font-size: 32px;
		padding-right: 0;
		text-align: center;
	}
	.candice-events__eyebrow {
		text-align: center;
	}
}

/* ---------------------------------------------------------------------------
   Latest Blog — header + post cards
   Production is an Elementor Pro Posts widget on the **Cards** skin. Values
   come from page-129-elementor.json + kit 388:
     eyebrow  Noto Serif 15 italic w400, navy
     title    Questrial 40/35/32 w400 lh1.4 (global cf25776), navy, mt 10px
     sub      the kit's default h3 = Questrial 26/24 w400 lh1.3 (global 9cd366b)
     button   Inter 15/14 w400 lh1em UPPERCASE, #fff on navy,
              padding 16/25, radius 0, shadow 6px 6px 0 #B5D5DB
     cards    3/2/1 columns, 20px gap, thumb ratio .66, "Read More »", "•"
--------------------------------------------------------------------------- */
.candice-blog__head {
	/* Bottom only. This used to be `50px 0`, and the top 50px stacked on the
	   section's own 80px padding-top, so the blog preview opened 130px below the
	   events band while every other seam on Home is 80px. The bottom 50px is
	   internal — it separates the head from the post grid — so it stays.
	   ≤1024 already zeroes this rule outright. */
	padding: 0 0 50px;
	margin-bottom: 0;
}
.candice-blog__head .wp-block-column > * {
	margin-top: 0;
	margin-bottom: 0;
}
.candice-blog__eyebrow {
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 15px;
	font-style: italic;
	font-weight: 400;
}
.candice-blog__title {
	margin-top: 10px !important;
	padding-right: 50px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 40px;
	font-weight: 400;
	line-height: 1.4em;
}
.candice-blog__sub {
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 26px;
	font-weight: 400;
	line-height: 1.3em;
}
.candice-blog__cta {
	margin-bottom: 10px;
}
.candice-blog__btn .wp-block-button__link {
	padding: 16px 25px;
	border-radius: 0;
	background: var(--wp--preset--color--navy);
	color: #fff;
	font-size: 15px;
	font-weight: 400;
	line-height: 1em;
	text-transform: uppercase;
	white-space: nowrap;
	box-shadow: var(--candice-btn-offset);
	transition: box-shadow 0.15s ease;
}
.candice-blog__btn .wp-block-button__link:hover {
	box-shadow: none;
}

/* The 3-up grid.
   `.candice-blog__grid` is the homepage's name for this and is baked into page
   129's stored content, so it stays. `.candice-card-grid` is the same mechanics
   under a context-neutral name, used by the blog index and the archives so all
   three preview grids share one definition instead of three near-copies. */
.candice-blog__grid,
.candice-card-grid {
	gap: 20px !important;
}
/* post-template wraps each card in an <li>; make it a flex parent so the card
   fills the grid row and every meta strip lines up along the bottom. */
.candice-blog__grid > li,
.candice-card-grid > li {
	display: flex;
}
/* Same step-down as the homepage grid below. Harmless where the base is already
   two-up (the blog index): the 1024 rule just restates it, and 767 still drops
   to a single column. */
@media (max-width: 1024px) {
	.candice-card-grid {
		grid-template-columns: repeat(2, minmax(0, 1fr)) !important;
	}
}
@media (max-width: 767px) {
	.candice-card-grid {
		grid-template-columns: 1fr !important;
	}
}
/* Same depth language as .candice-event — deliberately identical tokens, so
   the two card families read as one system rather than two. */
.candice-post-card {
	width: 100%;
	display: flex;
	flex-direction: column;
	background: #fff;
	border: var(--candice-edge);
	border-radius: var(--candice-card-radius);
	box-shadow: var(--candice-elev-card);
	transition: transform var(--candice-ease), box-shadow var(--candice-ease);
	overflow: hidden;
}
.candice-post-card:hover,
.candice-post-card:focus-within {
	transform: var(--candice-lift);
	box-shadow: var(--candice-elev-hover);
}
.candice-post-card__media {
	margin: 0;
}
.candice-post-card__media img {
	display: block;
	width: 100%;
	aspect-ratio: 1 / 0.66;
	object-fit: cover;
	transition: filter 0.2s ease;
}
.candice-post-card__media a:hover img {
	filter: brightness(105%) contrast(105%) saturate(105%);
}
.candice-post-card__body {
	flex: 1 1 auto;
	display: flex;
	flex-direction: column;
	padding: 20px;
}
.candice-post-card__body > * {
	margin-top: 0;
	margin-bottom: 0;
}
.candice-post-card__title {
	margin-bottom: 15px !important;
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 20px;
	font-weight: 400;
	line-height: 1.3em;
}
.candice-post-card__title a {
	color: var(--wp--preset--color--navy);
	text-decoration: none;
}
.candice-post-card__title a:hover {
	text-decoration: underline;
}
.candice-post-card__excerpt {
	color: rgba(0, 0, 0, 0.69);
	font-size: 15px;
	font-weight: 400;
	line-height: 1.5;
}
.candice-post-card__excerpt p {
	margin: 0;
}
/* "Read More »" pinned to the bottom of the body so the cards align */
.candice-post-card__more {
	margin-top: auto !important;
	padding-top: 20px;
	color: var(--wp--preset--color--navy);
	font-size: 13px;
	font-weight: 500;
	letter-spacing: 0.04em;
	text-transform: uppercase;
	text-decoration: none;
}
.candice-post-card__more:hover {
	text-decoration: underline;
}
/* Footer meta row — divider above, "date • No Comments" */
.candice-post-card__meta {
	gap: 8px !important;
	align-items: center;
	padding: 14px 20px;
	/* Navy-tinted hairline, matching the card edge — the old #ededed grey was
	   the only cool line left inside an otherwise warm card. */
	border-top: var(--candice-edge);
	color: rgba(0, 0, 0, 0.69);
	font-size: 13px;
	line-height: 1;
}
.candice-post-card__meta > * {
	margin: 0;
}
.candice-post-card__date,
.candice-post-card__sep,
.candice-post-card__comments,
.candice-post-card__comments a {
	color: rgba(0, 0, 0, 0.69);
	font-size: 13px;
	text-decoration: none;
}
/* core renders "No comments" — production shows "No Comments" */
.candice-post-card__comments {
	text-transform: capitalize;
}

@media (max-width: 1024px) {
	.candice-blog__head {
		padding: 0;
	}
	.candice-blog__title {
		font-size: 35px;
	}
	.candice-blog__sub {
		font-size: 24px;
	}
	.candice-blog__btn .wp-block-button__link {
		font-size: 14px;
	}
	.candice-blog__grid {
		grid-template-columns: repeat(2, 1fr) !important;
	}
}
@media (max-width: 767px) {
	.candice-blog__title {
		font-size: 32px;
		padding-right: 0;
	}
	.candice-blog__head {
		text-align: center;
	}
	.candice-blog__cta {
		justify-content: center !important;
	}
	.candice-blog__grid {
		grid-template-columns: 1fr !important;
	}
}

/* ---------------------------------------------------------------------------
   Newsletter signup
   Production is a 15/35/35/15 Elementor row: decorative lattices in the outer
   columns, copy and the form in the middle two. From page-129-elementor.json:
     copy   Questrial 28/30/28 w400 lh1.3em, word-spacing 2px, navy
     email  70% width, placeholder "Email"
     button 30% width, Questrial 12px capitalize, radius 4px, padding 0 20px
--------------------------------------------------------------------------- */
/* The cream band breaks out of the theme's 1200px column and `main`'s 64px
   gutter so it runs edge-to-edge at every width. !important is required to beat
   core's `.is-layout-constrained > :where(...) { margin-inline: auto !important }`.
   `.wp-site-blocks { overflow-x: clip }` (top of this file) absorbs the
   scrollbar difference that 100vw would otherwise expose. */
.candice-newsletter {
	width: 100vw;
	max-width: 100vw !important;
	margin-left: calc(50% - 50vw) !important;
	margin-right: calc(50% - 50vw) !important;
	/* Breathing room before the band. It sat flush against the page content on
	   every route (0px), so the cream started the instant the content stopped.
	   2.5rem is the theme's existing section-gap token — the same value
	   `.candice-meet-video` and `.candice-wall__invite` use. Set here rather
	   than per-template because the band is site-wide, at the top of the
	   footer. Being outside `.entry-content` keeps it out of the section table
	   `.rebuild-src/measure-rhythm.mjs` prints — but it is NOT visually neutral
	   on Home, which is what the override below fixes. */
	margin-top: 2.5rem;
}
/* Home is the one route whose last section brings its own bottom padding (the
   blog preview's 80px, inline on the block). There the 2.5rem above stacks on
   top of it and the band opens 120px below the last post card, against the
   80px every other seam on the page uses. Drop the margin here and the 80px
   comes from the section itself. Every other route still needs it — their
   content ends flush with `main`, which is what it was added for. */
.home .candice-newsletter {
	margin-top: 0;
}
/* Production's row is 15/35/35/15 on a ~1360px container. Capping the inner at
   990px keeps the text column at the width that reproduces the comp's
   four-line wrap, now that the band itself is full-bleed. */
.candice-newsletter__inner {
	max-width: min(75%, 1200px);
	margin-inline: auto;
	/* The band's 50px padding is symmetric, but core hangs `margin-bottom: 1.75em`
	   off every columns block — ~30px that landed inside the cream and made the
	   foot of the band read 80px against the head's 50px. Zeroed here rather than
	   by trimming the padding, so the two stops stay one number. Core's rule is
	   `:where(.wp-block-columns)`, specificity (0,0,0), so this class alone wins. */
	margin-bottom: 0;
	gap: 0 !important;
}
/* Give the copy a little more of the row than the form so it still breaks over
   four lines at the narrower inner width that keeps the lattices clear. */
.candice-newsletter__text {
	flex-basis: 54% !important;
	padding-bottom: 20px;
}
.candice-newsletter__form {
	flex-basis: 46% !important;
}
.candice-newsletter__text p {
	margin: 0;
	padding-right: 20px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 28px;
	font-weight: 400;
	line-height: 1.3em;
	word-spacing: 2px;
}
/* Lattices: corner-5 clipped off the left edge, corner-1 off the right.
   (Production also stacks a corner-hero-top-mobile on the left; the owner
   confirmed that one is a mistake on the live site, so it is not reproduced.) */
.candice-newsletter .candice-motif--nl-l {
	left: 0;
	top: 0;
	bottom: 0;
	width: auto;
	height: 100%;
	max-width: none;
}
.candice-newsletter .candice-motif--nl-r {
	right: 0;
	top: 0;
	bottom: 0;
	width: auto;
	height: 100%;
	max-width: none;
}
/* Mobile swaps in the wide lattice (corner-hero-top-mobile) — a top-cropped
   band reads better than the tall corner-5 there. src can't be swapped in CSS,
   so both are in the markup and toggled per breakpoint. */
.candice-newsletter .candice-motif--nl-m {
	display: none;
}

.candice-newsletter-form {
	/* One height for both controls. `align-items: stretch` matches them while
	   they share a row, but ≤781px they wrap onto separate rows and fall back
	   to their intrinsic heights, which differ by a pixel. Declaring the height
	   once is steadier than trying to make two different box models agree. */
	--nl-control-h: 47px;
	display: flex;
	align-items: stretch;
	gap: 10px;
	flex-wrap: wrap;
}
.candice-newsletter-form input[type="email"],
.candice-newsletter-form button {
	box-sizing: border-box;
	min-height: var(--nl-control-h);
}
.candice-newsletter-form input[type="email"] {
	flex: 1 1 0;
	min-width: 0;
	padding: 13px 16px;
	/* Navy hairline rather than the old #d8d8d8 grey, so the field belongs to
	   the cream band instead of reading as a widget dropped onto it. Strong
	   enough to be the control's boundary — see --candice-field-edge. */
	border: var(--candice-field-edge);
	border-radius: 0;
	background: #fff;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 15px;
	transition: border-color var(--candice-ease), box-shadow var(--candice-ease);
}
.candice-newsletter-form input[type="email"]::placeholder {
	/* Placeholder text is still text: #9a9a9a measures 2.81:1 on white, under
	   WCAG 1.4.3's 4.5:1. `muted` is 6.31:1. (The field is labelled properly
	   either way — the shortcode ships a .screen-reader-text <label> — so this
	   is a contrast fix, not a labelling one.) `opacity: 1` matches the Wall
	   field, where Firefox's default placeholder opacity was washing it out. */
	color: var(--wp--preset--color--muted);
	opacity: 1;
}
/* Same focus treatment as the Wall and Contact fields — one convention. */
.candice-newsletter-form input[type="email"]:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 1px;
	border-color: var(--wp--preset--color--navy);
}
.candice-newsletter-form button:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 2px;
}
/* Matched to "View Posts" like the other primary CTAs: Inter 15/400 uppercase,
   square, with the offset block. Elementor sets the button *column* to 30% but
   the button itself is auto-width, so it hugs "Subscribe".

   Padding is horizontal-only and the height comes from --nl-control-h, so the
   button lands on exactly 47px — the same as "View Posts" — while still
   matching the field it sits beside. (16px of vertical padding would make it
   49px once its 1px border is counted, and break that alignment.) The border
   is a transparent hairline so both controls share one box model when they
   wrap onto separate rows ≤781px. */
.candice-newsletter-form button {
	flex: 0 0 auto;
	padding: 0 25px;
	border: 1px solid transparent;
	border-radius: 0;
	background: var(--wp--preset--color--navy);
	color: #fff;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 15px;
	font-weight: 400;
	line-height: 1em;
	letter-spacing: 0.03em;
	text-transform: uppercase;
	white-space: nowrap;
	cursor: pointer;
	box-shadow: var(--candice-btn-offset);
	transition: box-shadow 0.15s ease;
}
.candice-newsletter-form button:hover {
	box-shadow: none;
}

@media (max-width: 1024px) {
	/* Copy and form stack; the lattices shrink back to the top-left corner.
	   WP only auto-stacks columns below 782px, so wrap them explicitly. */
	.candice-newsletter__inner {
		max-width: 100%;
		padding-left: 18%;
		flex-wrap: wrap !important;
	}
	.candice-newsletter__text,
	.candice-newsletter__form {
		flex-basis: 100% !important;
	}
	.candice-newsletter__text p {
		font-size: 30px;
		padding-right: 0;
	}
	.candice-newsletter .candice-motif--nl-r {
		display: none;
	}
}
@media (max-width: 767px) {
	/* The band is full-bleed, so its own padding is the page gutter here. */
	.candice-newsletter {
		padding-left: var(--candice-gutter-m);
		padding-right: var(--candice-gutter-m);
	}
	.candice-newsletter__inner {
		padding-left: 0;
		text-align: center;
	}
	.candice-newsletter__text p {
		font-size: 28px;
		text-align: center;
	}
	.candice-newsletter-form {
		justify-content: center;
	}
	.candice-newsletter-form input[type="email"] {
		flex: 0 0 100%;
	}
	.candice-newsletter-form button {
		flex: 0 0 auto;
		/* Horizontal padding only — vertical padding here would push the button
		   past --nl-control-h once it wraps onto its own row and leave it taller
		   than the field. A <button> centres its label vertically on its own. */
		padding: 0 28px;
	}
	/* Lattice centred and cropped by the band's top edge, sitting *above* the
	   copy rather than behind it (the inner block is padded to clear it). */
	.candice-newsletter .candice-motif--nl-l {
		display: none;
	}
	.candice-newsletter .candice-motif--nl-m {
		display: block;
		left: 0;
		right: auto;
		top: 0;
		bottom: auto;
		width: 40%;
		height: auto;
		max-width: none;
	}
	.candice-newsletter__inner {
		padding-top: 100px;
	}
}
.candice-newsletter__msg:empty {
	display: none;
}
.candice-newsletter__msg {
	flex-basis: 100%;
	margin: 0.5rem 0 0;
	font-size: 0.95rem;
}
.screen-reader-text {
	position: absolute !important;
	width: 1px;
	height: 1px;
	overflow: hidden;
	clip: rect(1px, 1px, 1px, 1px);
	white-space: nowrap;
}

/* ---------------------------------------------------------------------------
   Honeypot — off-screen (not display:none), skipped by assistive tech
--------------------------------------------------------------------------- */
.candice-hp {
	position: absolute !important;
	left: -9999px !important;
	width: 1px;
	height: 1px;
	overflow: hidden;
	opacity: 0;
}

/* ---------------------------------------------------------------------------
   The Wall of Honor — form + live entry list
--------------------------------------------------------------------------- */
.candice-wall {
	--wall-photo: 57%;
	--wall-panel-pad: clamp(24px, 3.4vw, 48px);
}
/* Every gap between sections on this page is 2.5rem, and this is what lets the
   block's own padding be that number. Core prints
   `:root :where(.is-layout-constrained) > * { margin-block-start: 1.5rem }`,
   so without this the top gap is 1.5rem + the padding while the bottom gap is
   the padding alone — 40px above and 16px below, from one symmetric value.
   Two classes (0,2,0) out-specify core's (0,1,0), so no !important is needed. */
.entry-content > .candice-wall-body {
	margin-block-start: 0;
}

/* --- the invitation card ------------------------------------------------ */
/* White mount + hairline: the border draws the mount, the outline the frame
   just outside it — one element, no extra wrapper in the shortcode. */
.candice-wall__invite {
	background: var(--color-panel-background);
	border: 9px solid var(--color-page-background);
	outline: 1px solid var(--color-subtle-border);
	outline-offset: -1px;
	padding: clamp(26px, 3.2vw, 40px) clamp(20px, 3vw, 44px) clamp(24px, 3vw, 36px);
	text-align: center;
	margin: 0 0 2.5rem;
}
.candice-wall__invite-title {
	font-family: var(--wp--preset--font-family--noto-serif);
	font-weight: 400;
	font-size: clamp(22px, 2.4vw, 30px);
	line-height: 1.3;
	color: var(--wp--preset--color--navy);
	margin: 0;
}
.candice-wall__invite-note {
	font-family: var(--wp--preset--font-family--inter);
	font-size: 15px;
	line-height: 1.5;
	color: var(--wp--preset--color--ink);
	margin: 10px 0 0;
}
.candice-wall__fields {
	display: flex;
	gap: 14px;
	align-items: stretch;
	justify-content: center;
	flex-wrap: wrap;
	margin: 22px 0 0;
}
.candice-wall__field {
	margin: 0;
	flex: 0 1 260px;
}
.candice-wall__field input,
.candice-wall__field select {
	/* Not inherited and not global here: core styles land border-box on the
	   select and the button but leave a text input content-box, so `width:100%`
	   plus the padding overflowed the field by 34px and lapped the select. */
	box-sizing: border-box;
	width: 100%;
	height: 100%;
	min-height: 52px;
	border: 1px solid #c9c5d2;
	border-radius: 3px;
	background: #fff;
	padding: 0 16px;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 16px;
	color: var(--wp--preset--color--heading);
}
.candice-wall__field input::placeholder {
	color: var(--wp--preset--color--muted);
	opacity: 1;
}
/* Native arrow varies wildly across platforms; draw our own. */
.candice-wall__field select {
	appearance: none;
	background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 12 8'%3E%3Cpath d='M1 1l5 5 5-5' fill='none' stroke='%235d6066' stroke-width='1.6'/%3E%3C/svg%3E");
	background-repeat: no-repeat;
	background-position: right 16px center;
	background-size: 12px 8px;
	padding-right: 40px;
}
.candice-wall__field select:invalid {
	color: var(--wp--preset--color--muted);
}
.candice-wall__field input:focus-visible,
.candice-wall__field select:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 1px;
	border-color: var(--wp--preset--color--navy);
}
.candice-wall__submit {
	flex: 0 0 auto;
	min-height: 52px;
	background: var(--wp--preset--color--navy);
	color: #fff;
	border: 0;
	border-radius: 3px;
	padding: 0 30px;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 15px;
	font-weight: 500;
	text-transform: uppercase;
	letter-spacing: 0.06em;
	cursor: pointer;
	transition: background 0.15s ease;
}
.candice-wall__submit:hover {
	background: #161d3d;
}

/* --- photograph + the names panel --------------------------------------- */
/* The section's height is set here, not by its contents — that is what makes
   the scroll work. The panel can only ever be as tall as the section, so a list
   longer than that scrolls inside `.candice-wall__names` rather than stretching
   the block. Letting the list drive the height instead would collapse the photo
   on a short list and defeat the scroll on a long one. It is viewport-relative
   so the memorial is always about a screenful, whatever the entry count. */
.candice-wall__memorial {
	display: grid;
	grid-template-columns: var(--wall-photo) 1fr;
	/* `100%` and not the implicit auto row: an auto row is sized by its content,
	   so the panel would overflow the fixed height instead of the list scrolling
	   inside it. This is what actually binds the panel to the section height. */
	grid-template-rows: 100%;
	height: clamp(680px, 92vh, 1100px);
	/* The panel level of the background system — same fill as the invitation
	   card above, so the two read as one block. Deliberately *not* the band
	   cream, which is reserved for the hero and the newsletter. The photograph
	   covers its own column, so this only ever shows behind the names. */
	background: var(--color-panel-background);
	align-items: stretch;
}
.candice-wall__photo {
	display: block;
	width: 100%;
	height: 100%;
	object-fit: cover;
	object-position: center 20%;
}
.candice-wall__panel {
	display: flex;
	flex-direction: column;
	min-width: 0;
	padding: var(--wall-panel-pad) clamp(14px, 1.6vw, 24px);
	text-align: center;
	/* `wall.js` scrolls the panel into view after a submit when it was below the
	   fold (phone/tablet). Same offset the `[id]` anchor rule uses so the sticky
	   header (§4j) doesn't cover the top of the list. */
	scroll-margin-top: calc(var(--candice-anchor-offset) + 1rem);
}
.candice-wall__panel-title {
	font-family: var(--wp--preset--font-family--noto-serif);
	font-weight: 400;
	font-size: clamp(20px, 2.1vw, 27px);
	line-height: 1.28;
	color: var(--wp--preset--color--navy);
	margin: 0;
}
.candice-wall__rule {
	display: flex;
	align-items: center;
	gap: 10px;
	width: min(100%, 240px);
	margin: 18px auto 22px;
}
.candice-wall__rule::before,
.candice-wall__rule::after {
	content: "";
	flex: 1;
	height: 1px;
	background: rgba(33, 41, 81, 0.3);
}
.candice-wall__rule span {
	width: 7px;
	height: 7px;
	transform: rotate(45deg);
	border: 1px solid rgba(33, 41, 81, 0.5);
}

/* The scroll container. It is focusable and labelled because a scrollable
   region that only responds to a mouse wheel is a keyboard trap in reverse —
   see WCAG 2.1.1. */
/* The scroller exists only to give the fade something to anchor to: a ::after
   on `.candice-wall__names` itself would sit *inside* the scrolled content and
   travel up with it, instead of staying pinned to the bottom edge. */
.candice-wall__scroller {
	position: relative;
	flex: 1 1 auto;
	min-height: 0;
	display: flex;
}
.candice-wall__scroller::after {
	content: "";
	position: absolute;
	inset: auto 0 0;
	height: 3.5rem;
	/* Must track --color-panel-background exactly or the fade shows as a band.
	   `transparent` is safe here: gradients interpolate in premultiplied alpha,
	   so it fades to clear rather than through grey. */
	background: linear-gradient(to top, var(--color-panel-background), transparent);
	opacity: 0;
	transition: opacity 0.25s ease;
	pointer-events: none;
}
/* `is-scrollable` / `is-at-end` are set by wall.js — CSS cannot ask whether an
   element overflows, and an inactive scroll-timeline would leave the cue
   showing on a list that fits. Both default to hidden, so with JS off nothing
   claims there is more to see. */
.candice-wall__panel.is-scrollable .candice-wall__scroller::after,
.candice-wall__panel.is-scrollable .candice-wall__cue {
	opacity: 1;
}
.candice-wall__panel.is-at-end .candice-wall__scroller::after,
.candice-wall__panel.is-at-end .candice-wall__cue {
	opacity: 0;
}
.candice-wall__cue {
	margin: 0.75rem 0 0;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 12px;
	line-height: 1.4;
	letter-spacing: 0.14em;
	text-transform: uppercase;
	color: var(--wp--preset--color--muted);
	opacity: 0;
	transition: opacity 0.25s ease;
	pointer-events: none;
}
.candice-wall__cue::after {
	content: "";
	display: inline-block;
	width: 0.42em;
	height: 0.42em;
	margin: 0 0 0.18em 0.6em;
	border-right: 1px solid currentColor;
	border-bottom: 1px solid currentColor;
	transform: rotate(45deg);
	vertical-align: middle;
}
@media (prefers-reduced-motion: reduce) {
	.candice-wall__scroller::after,
	.candice-wall__cue { transition: none; }
}
.candice-wall__names {
	flex: 1 1 auto;
	min-height: 0;
	overflow-y: auto;
	overscroll-behavior: contain;
	scrollbar-width: thin;
	scrollbar-color: rgba(33, 41, 81, 0.35) transparent;
}
.candice-wall__names:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 2px;
}
.candice-wall__names::-webkit-scrollbar {
	width: 6px;
}
.candice-wall__names::-webkit-scrollbar-thumb {
	background: rgba(33, 41, 81, 0.35);
	border-radius: 3px;
}
.candice-wall__list {
	list-style: none;
	margin: 0;
	padding: 0;
	display: flex;
	flex-direction: column;
	gap: 4px;
}
/* Three tracks so every initial and every state line up down the column,
   whatever their width. The bullet and the period are generated here rather
   than sitting in the markup, so a screen reader reads "L, Colorado" and not
   a decorative character. */
.wall-entry {
	display: grid;
	grid-template-columns: 1fr auto 1fr;
	column-gap: 14px;
	align-items: baseline;
	width: min(100%, 300px);
	margin: 0 auto;
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: clamp(15px, 1.3vw, 17px);
	line-height: 1.45;
	color: var(--wp--preset--color--navy);
}
/* Every child needs an explicit row. Grid auto-placement is *sparse*: once the
   ::before is placed in column 2, the cursor sits past it, and a later item
   asking for column 1 is pushed to the next row rather than back-filling —
   which stacks the bullet above each entry instead of between the two spans. */
.wall-entry::before {
	content: "\2022" / "";
	grid-area: 1 / 2;
	color: rgba(33, 41, 81, 0.45);
}
.wall-entry__initial {
	grid-area: 1 / 1;
	text-align: right;
	/* New entries are already uppercased on save, so this is for the ones that
	   aren't: the 19 migrated rows, and anything typed by hand in wp-admin →
	   Wall of Honor, where the initial is just the post title and nothing
	   normalises it. Display-only, so it never rewrites stored data. */
	text-transform: uppercase;
}
.wall-entry__initial::after {
	content: ".";
}
.wall-entry__state {
	grid-area: 1 / 3;
	text-align: left;
}
.wall-entry.is-new {
	animation: wall-in 1.4s ease both;
}
@keyframes wall-in {
	0% { opacity: 0; transform: translateY(-6px); background: #fdeec2; }
	60% { opacity: 1; background: #fdeec2; }
	100% { opacity: 1; transform: none; background: transparent; }
}
@media (prefers-reduced-motion: reduce) {
	.wall-entry.is-new { animation: none; }
}

@media (max-width: 900px) {
	.candice-wall { --wall-photo: 50%; }
	.wall-entry { column-gap: 10px; }
}
@media (max-width: 781px) {
	/* `grid-template-rows` must be reset too, not just the columns: the base rule
	   pins the single row to 100%, which once stacked stretches the photo over
	   the whole section and throws away its aspect ratio. */
	.candice-wall__memorial { grid-template-columns: 1fr; grid-template-rows: auto auto; height: auto; }
	/* 4:5 and anchored to the top: a square box crops 261px out of a 611px-tall
	   frame at 390, which takes the top of her head with it. */
	.candice-wall__photo { height: auto; aspect-ratio: 4 / 5; object-position: center top; }
	.candice-wall__panel { padding: clamp(28px, 7vw, 44px) 20px clamp(32px, 8vw, 48px); }
	.candice-wall__names { max-height: 60vh; }
	.candice-wall__fields { flex-direction: column; align-items: stretch; }
	.candice-wall__field { flex: 1 1 auto; }
	.candice-wall__submit { width: 100%; padding: 15px 30px; }
}

/* One voice for every form's status line — the Wall's, the contact form's and the
   newsletter's (styled with them below): navy italic, whatever the outcome.
   `is-ok` / `is-err` stay on the element, since all three scripts set them and
   they remain a hook, but they no longer colour it. Success and failure are still
   told apart by the wording — colour was never carrying that on its own, so
   dropping the green/red costs nothing a screen reader or a colour-blind reader
   was relying on. */
.candice-wall__msg,
.candice-contact__msg,
.candice-newsletter__msg {
	color: var(--color-navy);
	font-style: italic;
}
.candice-wall__msg,
.candice-contact__msg {
	flex-basis: 100%;
	margin: 0.75rem 0 0;
	min-height: 1.2em;
}
/* 20px, not the Wall's 12px: the contact submit carries the 6px offset block, so
   12px left only 6px of daylight between the shadow and the confirmation. The
   Wall's button is flat and needs no such allowance. */
.candice-contact__msg {
	margin-top: 1.25rem;
}
/* Contact only: with nothing to say this line reserved 32px at the foot of the
   card, which is what made the bottom read heavier than the top. Collapsed to a
   zero box rather than `display: none` (the newsletter's approach) — a live
   region that is removed from the box tree and then re-added in the same frame
   is unreliably announced, and this one carries the send confirmation. The Wall
   keeps its reserve: its status line sits between the fields and a long list, so
   nothing below it would shift anyway. */
.candice-contact__msg:empty {
	margin: 0;
	min-height: 0;
}

/* ---------------------------------------------------------------------------
   Contact form

   Matched to the Wall's invitation card (`.candice-wall__invite`) so the site's
   two public forms read as one component: the same matted frame, the same field
   hairline, height and radius, the same focus ring. The submit is the exception
   — it takes the newsletter's "Subscribe" treatment (offset block that collapses
   on hover) rather than the Wall's flat button, because unlike the Wall's, this
   button doesn't sit in a row with the fields and has room for the offset.
--------------------------------------------------------------------------- */
/* The card is a wrapper group in page content, not the <form> itself, so the
   heading inside it stays a real block the editor can reach. (The Wall hardcodes
   its title in the shortcode; that page's copy is fixed, this one's is not.) */
.candice-contact-card {
	/* One height for every single-line control, as on the Wall's fields. */
	--contact-control-h: 52px;
	/* Full width of the content column, matching the Wall's second section — its
	   `.candice-wall-body` is a flow section, so the invite card fills all 1200px
	   rather than being re-capped. This card's own section is flow for the same
	   reason; no max-width here or the cap would come back. */
	box-sizing: border-box;
	/* Ranged left, unlike the Wall invite — every row starts on one left edge (see
	   the shared measure below) while the group as a whole stays centred. */
	text-align: left;
	/* White mount + hairline, same construction as the Wall invite: the border
	   draws the mount, the outline the frame just outside it. Same panel token
	   and same hairline as that card too, so the two read as one component. */
	background: var(--color-panel-background);
	border: 9px solid var(--color-page-background);
	outline: 1px solid var(--color-subtle-border);
	outline-offset: -1px;
	/* Top and bottom deliberately the same clamp: the space under the button reads
	   as the space above the eyebrow. That only holds because the status line
	   collapses when empty (see `.candice-contact__msg:empty`) — while it reserved
	   a line, the foot of the card ran ~32px heavier than the head. */
	padding: clamp(26px, 3.2vw, 40px) clamp(20px, 3vw, 44px);
}
/* One measure for every row. The card keeps the full 1200px column so its frame
   lines up with the Wall's, but the eyebrow, heading, fields and button all live
   in the same centred 800px block — so they share a left edge, and the group sits
   on the card's centre line rather than against its padding. */
.candice-contact-card > * {
	max-width: 800px;
	margin-inline: auto;
}
/* Core's flow layout puts 24px above every child; the eyebrow is the card's
   first line and must sit on the padding. Both selectors out-specify core's
   `:root :where(.is-layout-flow) > *` (0,1,0) — the class pair on order, the
   :first-child rule on specificity. */
.candice-contact-card > :first-child {
	margin-top: 0;
}
/* Eyebrow and heading are one unit, so 10px between them — the same gap the Wall
   puts between its title and its note. 24px would read as two separate lines. */
.candice-contact-card .wp-block-heading {
	margin-top: 10px;
}
/* 22px under the heading — the gap the Wall leaves before its fields row, so the
   two cards share one internal rhythm. Width and centring come from the shared
   measure above; 800px is where the fields sat before the card went full width,
   and a 1096px-wide box for a first name is runway nobody needs. */
.candice-contact-card .candice-contact {
	margin-top: 22px;
}
.candice-contact__field {
	margin: 0 0 14px;
}
.candice-contact input,
.candice-contact textarea {
	/* Not inherited and not global here: core styles land border-box on the
	   textarea but leave a text input content-box, so `width:100%` plus the
	   padding overflows the card. Same fix as `.candice-wall__field`. */
	box-sizing: border-box;
	width: 100%;
	border: 1px solid #c9c5d2;
	border-radius: 3px;
	background: #fff;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 16px;
	color: var(--wp--preset--color--heading);
}
.candice-contact input {
	min-height: var(--contact-control-h);
	padding: 0 16px;
}
/* The textarea is multi-line, so it can't take the fields' vertical-padding-free
   box — an input centres its single line against `min-height`, a textarea starts
   at the top edge. Real padding here, and `rows` sets the height. */
.candice-contact textarea {
	padding: 15px 16px;
	line-height: 1.5;
	resize: vertical;
}
.candice-contact input::placeholder,
.candice-contact textarea::placeholder {
	color: var(--wp--preset--color--muted);
	opacity: 1;
}
.candice-contact input:focus-visible,
.candice-contact textarea:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 1px;
	border-color: var(--wp--preset--color--navy);
}

/* "Send" is the newsletter's "Subscribe": Inter 15/400 uppercase, square, navy,
   with the offset block. Height is 47px there and stays 47px here — it is a
   button in its own row, not a control matched to the 52px fields beside it, so
   growing it would only make it heavier than every other CTA on the site.
   Hover collapses the offset block and nothing else — no colour change, matching
   Subscribe. This button previously went red on hover; that came from an explicit
   rule here, not from theme.json. Core emits its red button hover as
   `:root :where(.wp-element-button:hover, …)`, and with the `:hover` *inside* the
   `:where()` the whole selector is (0,1,0) — a tie with the class below, which
   app.css wins on order. So the red never reaches either button on its own. */
.candice-contact__submit {
	box-sizing: border-box;
	/* 8px + the field's own 14px = the 22px the Wall puts above its fields row. */
	margin-top: 8px;
	min-height: 47px;
	padding: 0 25px;
	border: 1px solid transparent;
	border-radius: 0;
	background: var(--wp--preset--color--navy);
	color: #fff;
	font-family: var(--wp--preset--font-family--inter);
	font-size: 15px;
	font-weight: 400;
	line-height: 1em;
	letter-spacing: 0.03em;
	text-transform: uppercase;
	white-space: nowrap;
	cursor: pointer;
	box-shadow: var(--candice-btn-offset);
	transition: box-shadow 0.15s ease;
}
.candice-contact__submit:hover {
	box-shadow: none;
}
.candice-contact__submit:focus-visible {
	outline: 2px solid var(--wp--preset--color--navy);
	outline-offset: 2px;
}

/* ---------------------------------------------------------------------------
   Footer — matched to production (Elementor template "Footer - July 25", 1500)
     logo      candy-white.png @ 180px, 10px below
     tagline   Questrial 21 / 15 (≤1024), #FFFFFFE6, centred
     social    roundFB / roundINSTA @ 32px, centred row
     rule      70% wide, white
     heading   Questrial 26 / 24 (≤1024) w400 lh1.3, #FFFFFF
     nav       Questrial 18 / 15 (≤1024) lh1.8, #FFFFFF, 20px apart, pipe rules
     legal     margin-top 60, padding-top 40, border-top 1px #FFFFFF1A,
               right-aligned (centred ≤767), #FFFFFF4D
   Padding: 40px 0 desktop · 40px 35px ≤1024 · 100px 15px 30px ≤767.
   NOTE: the archived data sets the panel to #052C30 (dark teal); current
   production — and the owner's screenshots — are navy, so navy stays.
--------------------------------------------------------------------------- */
.candice-footer {
	background: var(--wp--preset--color--navy);
	color: #fff;
	padding: 40px 0;
}
.candice-footer a {
	color: #fff;
	text-decoration: none;
}
.candice-footer a:hover {
	color: var(--wp--preset--color--cream);
}
.candice-footer__logo {
	margin: 0 0 10px;
}
.candice-footer__logo img {
	width: 180px;
	height: auto;
}
.candice-footer__tagline {
	margin: 0;
	color: rgba(255, 255, 255, 0.9);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 21px;
	font-weight: 400;
	line-height: 1.85;
}
/* The two tagline lines sit further apart than a single line-height — in
   production Elementor's paragraph margins do it; here it's an explicit gap. */
.candice-footer__tagline + .candice-footer__tagline {
	margin-top: 19px;
}
/* Social row — 32px marks, ~1.5 icon-widths apart */
.candice-footer__social {
	display: flex;
	justify-content: center;
	align-items: center;
	gap: 48px;
	margin: 22px 0 0;
}
.candice-footer__social img {
	display: block;
	width: 32px;
	height: 32px;
}
.candice-footer__rule.wp-block-separator {
	width: 70%;
	max-width: 70%;
	margin: 30px auto 0;
	border: 0;
	border-top: 1px solid rgba(255, 255, 255, 0.55);
	background: none;
	opacity: 1;
}
.candice-footer__navtitle {
	margin: 30px 0 0;
	color: #fff;
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 26px;
	font-weight: 400;
	line-height: 1.3em;
}
/* Nav — inline links with a hairline rule between each pair. The separators are
   drawn in CSS so the markup stays a plain, editable list of links. */
.candice-footer-nav {
	display: flex;
	flex-wrap: wrap;
	justify-content: center;
	align-items: center;
	max-width: 900px;
	margin: 10px auto 0;
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 18px;
	line-height: 1.8;
}
.candice-footer-nav a {
	padding: 0 20px;
	position: relative;
}
.candice-footer-nav a:not(:last-child)::after {
	content: "";
	position: absolute;
	right: 0;
	top: 50%;
	transform: translateY(-50%);
	height: 1.1em;
	border-left: 1px solid rgba(255, 255, 255, 0.55);
}
/* Studio credit — small and italic, but kept at 70% white so it still clears
   WCAG AA on the navy panel (~7.5:1). The link is underlined so it is
   distinguishable without relying on colour alone. */
.candice-footer__credit {
	margin: 42px 0 0;
	color: rgba(255, 255, 255, 0.7);
	font-size: 14px;
	font-style: italic;
}
.candice-footer__credit a {
	color: inherit;
	text-decoration: underline;
	text-underline-offset: 2px;
}
.candice-footer__credit a:hover {
	color: var(--wp--preset--color--cream);
}
.candice-footer__legal {
	margin-top: 28px;
	padding-top: 40px;
	border-top: 1px solid rgba(255, 255, 255, 0.1);
}
.candice-footer__copy {
	margin: 0;
	text-align: right;
	/* Production uses #FFFFFF4D (30%) = 2.60:1, which fails WCAG AA for
	   informational text. 50% keeps the same muted look at ~4.6:1. */
	color: rgba(255, 255, 255, 0.5);
	font-size: 15px;
}

@media (max-width: 1024px) {
	.candice-footer {
		padding: 40px 35px;
	}
	.candice-footer__tagline {
		font-size: 15px;
	}
	.candice-footer__navtitle {
		font-size: 24px;
	}
	.candice-footer-nav {
		font-size: 15px;
	}
}
@media (max-width: 767px) {
	.candice-footer {
		padding: 100px var(--candice-gutter-m) 30px;
	}
	.candice-footer__copy {
		text-align: center;
	}
}

/* ---------------------------------------------------------------------------
   Blog index — the side runner (author card + Latest Blog)
   Production runs /blog/ as a two-thirds post grid with a narrow right-hand
   column. Proportions measured off the pre-rebuild baseline render
   `.site-check/render/chromium-desktop-blog.png` (1440px viewport, 1200px
   content): grid 798px · gutter 81px · runner 319px → 66% / 6% / 28%. That is
   also why the post grid dropped from three columns to two — the runner takes
   the third.

   The runner is an <aside> so it lands as a `complementary` landmark instead of
   another unlabelled div, and it stacks under the grid at ≤781px, the same stop
   the rest of the theme collapses columns at.
--------------------------------------------------------------------------- */
.candice-runner-layout {
	align-items: flex-start;
}

/* --- author card -------------------------------------------------------- */
/* The photo is deliberately narrower than the text beside it — production sets
   224px inside a 319px column — and it is left-aligned, not centred. */
.candice-side__photo {
	margin: 0;
}
.candice-side__photo img {
	display: block;
	width: 70%;
	max-width: 224px;
	height: auto;
	aspect-ratio: 1;
	border-radius: 50%;
	object-fit: cover;
}
.candice-side__social {
	display: flex;
	gap: 10px;
	margin: 18px 0 0;
}
.candice-side__social img {
	display: block;
	width: 30px;
	height: 30px;
}
.candice-side__name {
	margin: 18px 0 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 22px;
	font-weight: 500;
	line-height: 1.3;
}
.candice-side__bio {
	margin: 12px 0 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 15px;
	line-height: 1.75;
}
.candice-side__rule {
	margin: 22px 0 0;
	border: 0;
	border-top: 1px solid rgba(33, 41, 81, 0.18);
}

/* --- Latest Blog -------------------------------------------------------- */
.candice-side__title {
	margin: 22px 0 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 20px;
	font-weight: 500;
}
.candice-side-latest {
	margin-top: 18px;
}
.candice-side-latest__list {
	margin: 0;
	padding: 0;
	list-style: none;
}
.candice-side-latest__list > li + li {
	margin-top: 18px;
}
.candice-side-latest__item {
	align-items: flex-start;
}
.candice-side-latest__thumb {
	flex: 0 0 96px;
	margin: 0;
}
.candice-side-latest__thumb img {
	display: block;
	width: 96px;
	height: 70px;
	object-fit: cover;
}
/* Without this the flex item refuses to shrink below its longest word and the
   thumbnail gets squeezed instead of the title wrapping. */
.candice-side-latest__meta {
	min-width: 0;
}
.candice-side-latest__date {
	margin: 0;
	color: var(--wp--preset--color--red);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 13px;
	font-style: italic;
	line-height: 1.3;
}
.candice-side-latest__link {
	margin: 4px 0 0;
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 15px;
	font-weight: 500;
	line-height: 1.35;
}
.candice-side-latest__link a {
	color: var(--wp--preset--color--navy);
	text-decoration: none;
}
.candice-side-latest__link a:hover,
.candice-side-latest__link a:focus-visible {
	text-decoration: underline;
}

/* --- "More Posts" (single post runner) ---------------------------------- */
/* Full cards stacked one per row, not the compact thumb+text rows the blog
   index uses — that is what production shows beside an article. They reuse
   `.candice-post-card` wholesale, so the card treatment stays in one place. */
.candice-side-posts {
	margin-top: 18px;
}
.candice-side-posts__list {
	margin: 0;
	padding: 0;
	list-style: none;
}
.candice-side-posts__list > li + li {
	margin-top: 20px;
}
/* The card's media is tuned for a ~380px grid cell; in a ~318px runner the
   3:2 crop is still fine, but the body padding reads heavy, so tighten it. */
.candice-side-posts .candice-post-card__body {
	padding: 16px;
}
.candice-side-posts .candice-post-card__meta {
	padding-inline: 16px;
}

/* --- "Message Me" (single post runner) ---------------------------------- */
.candice-side-contact {
	margin-top: 28px;
	padding: 22px 20px 24px;
	background: #fff;
	border: var(--candice-edge);
	border-radius: var(--candice-card-radius);
	box-shadow: var(--candice-elev-card);
	/* Production caps the card with a heavier rule than the author-card divider
	   above it, which is what separates the form from the post list. */
	border-top: 3px solid var(--wp--preset--color--navy);
}
.candice-side-contact__title {
	margin: 0 0 16px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 22px;
	font-weight: 400;
}
/* The contact form ships sized for the full-width /contact/ page. */
.candice-side-contact .candice-contact__field {
	margin: 0 0 10px;
}
.candice-side-contact .candice-contact textarea {
	min-height: 96px;
}
.candice-side-contact .candice-contact__submit {
	width: 100%;
}

/* --- single post hero --------------------------------------------------- */
/* Reuses `.candice-page-hero--lattice` wholesale, so the band, motifs and h1
   are already right; only the date above and the byline below are new. The
   byline needs the doubled class because `.candice-page-hero--lattice > p` is
   (0,1,1) and would otherwise win and render it at the 24px standfirst size. */
.candice-post-hero__date {
	margin: 0 0 14px;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--inter);
	font-size: 14px;
	line-height: 1.4;
}
.candice-post-hero .candice-post-hero__byline {
	margin: 16px 0 0;
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--noto-serif);
	font-size: 14px;
	font-style: italic;
	font-weight: 400;
	line-height: 1.4;
}

/* --- previous / next post ----------------------------------------------- */
/* `linkLabel: true` on the block is what makes "Previous"/"Next" render as a
   real <span class="post-navigation-link__label"> rather than being dropped —
   with showTitle alone core emits only the title, and the label would have had
   to be faked with CSS content, which screen readers would not announce. */
.candice-postnav {
	margin-top: 48px;
	padding-top: 26px;
	border-top: 1px solid rgba(33, 41, 81, 0.18);
	gap: 0;
}
.candice-postnav .wp-block-post-navigation-link {
	display: flex;
	flex: 1 1 0;
	min-width: 0;
	align-items: center;
	gap: 14px;
}
.candice-postnav__prev {
	padding-right: 24px;
}
/* The rule between the two halves. Dropped when a post has only one neighbour
   (the newest and oldest posts), where a divider would hang off nothing. */
.candice-postnav__next {
	justify-content: flex-end;
	padding-left: 24px;
	border-left: 1px solid rgba(33, 41, 81, 0.18);
	text-align: right;
}
/* Core emits the wrapper even when there is no adjacent post, so the newest and
   oldest posts each get a genuinely empty <div> rather than nothing. Left
   alone it still takes a flex slot, and on the "next" side it hung the divider
   off no content at all. Hide it, and drop the divider when the surviving link
   is the only one. (`:only-child` cannot do this — there are always two.) */
.candice-postnav .wp-block-post-navigation-link:empty {
	display: none;
}
.candice-postnav__prev:empty + .candice-postnav__next {
	padding-left: 0;
	border-left: 0;
}
.candice-postnav a {
	display: flex;
	min-width: 0;
	flex-direction: column;
	gap: 3px;
	text-decoration: none;
}
.candice-postnav .post-navigation-link__label {
	color: var(--wp--preset--color--muted);
	font-family: var(--wp--preset--font-family--inter);
	font-size: 13px;
}
.candice-postnav .post-navigation-link__title {
	color: var(--wp--preset--color--navy);
	font-family: var(--wp--preset--font-family--questrial);
	font-size: 17px;
	line-height: 1.35;
	/* Production title-cases these, so "the Wrong Person" reads "The Wrong
	   Person" without editing the post titles themselves. */
	text-transform: capitalize;
}
.candice-postnav a:hover .post-navigation-link__title,
.candice-postnav a:focus-visible .post-navigation-link__title {
	text-decoration: underline;
}
.candice-postnav [class*="__arrow-"] {
	flex: 0 0 auto;
	color: var(--wp--preset--color--navy);
	font-size: 22px;
	line-height: 1;
}
@media (max-width: 640px) {
	/* Core's flex layout sets `flex-wrap: nowrap` on its own container class
	   (0,1,0); qualifying with the block class reaches (0,2,0) and wins. */
	.wp-block-group.candice-postnav {
		flex-wrap: wrap;
		gap: 22px;
	}
	/* Both selectors are qualified with `.candice-postnav` on purpose. The base
	   rule above is `.candice-postnav .wp-block-post-navigation-link { flex: 1 1
	   0 }` — (0,2,0). A bare `.candice-postnav__prev` here is (0,1,0) and loses
	   to it *even inside a media query*, which left `flex-basis: 0` in force and
	   the two links side by side in ~164px columns at 390, titles broken over
	   five lines. Matching (0,2,0) lets source order decide, and this block is
	   later in the file. */
	.candice-postnav .candice-postnav__prev,
	.candice-postnav .candice-postnav__next {
		flex: 0 0 100%;
		justify-content: flex-start;
		padding: 0;
		border-left: 0;
		text-align: left;
	}
	/* Chevrons go once the rows stack. Core puts the arrow *before* the link on
	   prev and *after* it on next — a mirror that works when the two sit side by
	   side, but stacked it indented "Previous" by the arrow's width while "Next"
	   sat flush, so the two rows no longer lined up. They are `aria-hidden`
	   decoration and the Previous/Next labels already carry the direction. */
	.candice-postnav [class*="__arrow-"] {
		display: none;
	}
}

/* The runner drops below the grid at Elementor's tablet stop (≤1024px), not at
   core's own 781px column collapse. Production is the reason: the baseline
   tablet render (`chromium-tablet-blog.png`, 820px viewport) shows the card
   grid running full width with no runner beside it, and the archived site's
   breakpoints are tablet ≤1024 / mobile ≤767. Waiting for 781 also looked bad
   on its own merits — between 782 and ~950 the runner is squeezed to ~190px,
   which breaks every Latest Blog title onto five lines and wraps the dates. */
@media (max-width: 1024px) {
	/* Core ships `@media (min-width: 782px) { .wp-block-columns { flex-wrap:
	   nowrap !important } }`. A plain `.candice-runner-layout` rule ties it on
	   specificity and loses on source order, so qualify with the block class to
	   reach (0,2,0) — otherwise the columns stay side by side and merely shrink,
	   which is exactly the squeezed runner this block is meant to prevent. */
	.wp-block-columns.candice-runner-layout {
		flex-wrap: wrap !important;
	}
	/* The block editor writes the widths as inline flex-basis, so overriding
	   them needs !important — same reason as the full-bleed margins (§4f.1). */
	.candice-runner-layout > .wp-block-column {
		flex-basis: 100% !important;
	}
	/* The air between the grid and the runner is the columns' own row gap
	   (44px, set on the block), not a margin here — core zeroes column margins
	   and wins, so a `margin-top` on the column computes to 0px. */

	/* Full width, a 96px thumbnail and a short title reads as mostly empty
	   space, so keep the runner to a comfortable measure once it is stacked. */
	.candice-side {
		max-width: 560px;
	}
	/* Latest Blog is dropped once the runner stacks. Beside the grid it reads as
	   a secondary index; underneath it, it just repeats the same posts the
	   reader has this moment scrolled past — with three posts published that is
	   a verbatim second copy. The author card is the part that still earns its
	   place, so only the list, its heading and the divider that introduces it go
	   (leave the divider in and it dangles off the foot of the card).

	   Scoped to `.blog`, the posts-index body class. Single posts (`.single`)
	   keep "More Posts" — that one lists the posts you are *not* reading, so it
	   is not a duplicate and stays useful stacked. */
	.blog .candice-side__rule,
	.blog .candice-side__title,
	.blog .candice-side-latest {
		display: none;
	}
}

@media (max-width: 781px) {
	.candice-side__photo img {
		width: 200px;
	}
}

/* ---------------------------------------------------------------------------
   Depth system — responsive + reduced motion
   Lives at the end of the file on purpose: these override the per-component
   rules above at equal specificity, so source order is what makes them win.
--------------------------------------------------------------------------- */

/* Softer, shorter shadows once the layout stacks. A shadow tuned for a 1100px
   card reads heavy under a 350px one, and on a phone the card already fills
   the width, so it needs far less help separating from the page. */
@media (max-width: 781px) {
	.candice-event,
	.candice-post-card,
	.candice-podcast-banner__img img {
		box-shadow: var(--candice-elev-card-sm);
	}
	.candice-about-photo img {
		box-shadow: none;
	}
}

/* Hover lift is decoration, so it goes entirely — no transform, no transition.
   The shadow *change* is kept: it is a state cue, not motion, and it is the
   only hover feedback these cards have left once the lift is gone. */
@media (prefers-reduced-motion: reduce) {
	.candice-event,
	.candice-post-card,
	.candice-podcast-banner__img img,
	.candice-newsletter-form input[type="email"] {
		transition: none;
	}
	.candice-event:hover,
	.candice-event:focus-within,
	.candice-post-card:hover,
	.candice-post-card:focus-within,
	.candice-podcast-banner__img a:hover img,
	.candice-podcast-banner__img a:focus-visible img {
		transform: none;
	}
}
