/* ============================================================
   PORTUGALIST — INTERACTIVE COMPONENTS
   Loaded site-wide alongside design-system.css.

   The eligibility checker and income calculator are Gravity Forms
   forms — their styling lives in gravity-forms.css (kept isolated
   so a future form-plugin switch only touches that one file).

   This file brands the interactive blocks built with GenerateBlocks
   Pro. These are *defaults*: they make a freshly-inserted accordion
   or tabs block look Portugalist without per-block setup, while a
   block's own GenerateBlocks settings still override them.

   Font sizes are rem (off design-system.css tokens or literal rem);
   family is always inherited.

   Contents:
     1. Accordion  (generateblocks-pro/accordion)
     2. Tabs       (generateblocks-pro/tabs)
     3. Sticky sub-nav
     4. Citizenship timeline
     5. Site chrome (trust strip, footer)
     6. Post body (single posts &amp; pages — card + typography defaults)
     7. Search &amp; archive results (page-header, result cards)
   ============================================================ */

/* 1. ACCORDION ---------------------------------------------- */
/* GB Pro markup: .gb-accordion > .gb-accordion__item
   > .gb-accordion__toggle (+ .gb-accordion__toggle-icon)
   + .gb-accordion__content. The open item carries
   .gb-accordion__item-open. */
.gb-accordion {
	display: flex;
	flex-direction: column;
	gap: 8px;
}
.gb-accordion__item {
	background: var(--pg-white);
	/* No hairline — the pastry toggle vs the white item already
	   reads as a card. A very faint shadow keeps each item lifted
	   off the band without the harsh outline. The !important defeats
	   GenerateBlocks Pro's own default item border. */
	border: 0 !important;
	border-radius: var(--pg-radius-sm);
	overflow: hidden;
	box-shadow: 0 1px 2px rgba(28, 26, 23, .04);
}
.gb-accordion__toggle {
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 12px;
	padding: 14px 18px;
	font-size: var(--pg-text-body);
	font-weight: 600;
	color: var(--pg-ink);
	cursor: pointer;
	/* Tinted so the header reads as a header against the white item. */
	background: var(--pg-pastry);
	transition: background-color .12s ease;
}
.gb-accordion__toggle:hover { background: var(--pg-custard-soft); }
.gb-accordion__item-open > .gb-accordion__toggle {
	background: var(--pg-custard-soft);
	border-bottom: 1px solid var(--pg-border);
}
.gb-accordion__toggle-icon {
	display: flex;
	flex-shrink: 0;
	color: var(--pg-custard-deep);
}

/* Content. GB animates this with max-height, so vertical padding
   is applied only when open — otherwise a collapsed item would
   show a padding-height sliver. */
.gb-accordion__content { padding: 0 18px; }
.gb-accordion__item-open > .gb-accordion__content {
	padding-top: 14px;
	padding-bottom: 16px;
}
.gb-accordion__content > :last-child { margin-bottom: 0; }

/* Core/details — used for inline FAQs where the GB Pro accordion is
   overkill. Native <details>/<summary> means no JS, no plugin, just
   styled to match the .gb-accordion look. */
.wp-block-details {
	background: var(--pg-white);
	border: 0;
	border-radius: var(--pg-radius-sm);
	overflow: hidden;
	margin: 0 0 8px;
	box-shadow: 0 1px 2px rgba(28, 26, 23, .04);
}
.wp-block-details > summary {
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 12px;
	padding: 14px 18px;
	font-size: var(--pg-text-body);
	font-weight: 600;
	color: var(--pg-ink);
	cursor: pointer;
	background: var(--pg-pastry);
	list-style: none;
	transition: background-color .12s ease;
}
.wp-block-details > summary::-webkit-details-marker { display: none; }
.wp-block-details > summary::after {
	content: "▾";
	color: var(--pg-custard-deep);
	font-size: 0.85em;
	transition: transform .15s ease;
	flex-shrink: 0;
}
.wp-block-details[open] > summary {
	background: var(--pg-custard-soft);
	border-bottom: 1px solid var(--pg-border);
}
.wp-block-details[open] > summary::after { transform: rotate(180deg); }
.wp-block-details > summary:hover { background: var(--pg-custard-soft); }
.wp-block-details > *:not(summary) { padding: 14px 18px 16px; }
.wp-block-details > p:not(summary):last-child { margin-bottom: 0; }

/* 2. TABS --------------------------------------------------- */
/* GB Pro markup: .gb-tabs > .gb-tabs__menu > .gb-tabs__menu-item
   (the active one carries .gb-block-is-current) and
   .gb-tabs__items > .gb-tabs__item (panels).

   The whole block sits on a white card so it reads as distinct
   from the page background — every tab, active included. */
.gb-tabs {
	background: var(--pg-white);
	border: 1px solid var(--pg-border);
	border-radius: var(--pg-radius-sm);
	overflow: hidden;
}
.gb-tabs__menu {
	display: flex;
	flex-wrap: wrap;
	gap: 0;
	border-bottom: 1px solid var(--pg-border);
}
.gb-tabs__menu-item {
	padding: 12px 20px;
	font-size: 0.875rem;            /* 14px — UI label */
	font-weight: 500;
	color: var(--pg-ink-muted);
	cursor: pointer;
	border-bottom: 2px solid transparent;
	margin-bottom: -1px;
	transition: color .12s ease, border-color .12s ease, background-color .12s ease;
}
.gb-tabs__menu-item:hover { color: var(--pg-ink); }
.gb-tabs__menu-item.gb-block-is-current {
	color: var(--pg-ink);
	font-weight: 600;
	background: var(--pg-custard-soft);
	border-bottom-color: var(--pg-custard);
}

/* Panels */
.gb-tabs__item { padding: 20px; }
.gb-tabs__item > :last-child { margin-bottom: 0; }

/* 3. STICKY SUB-NAV ----------------------------------------- */
/* An in-page section nav for long guide pages. The .pg-subnav
   element is the full-width sticky bar; .pg-subnav__list is the
   constrained, horizontally-scrollable row of links. Scroll-spy
   is handled in components.js — it toggles .is-current. */
.pg-subnav {
	position: sticky;
	/* Sits at the top of the viewport. On a site with the sticky
	   header, raise this to the header's height so the two stack. */
	top: 0;
	z-index: 100;
	background: var(--pg-white);
	border-bottom: 1px solid var(--pg-border);
	box-shadow: 0 1px 8px rgba(28, 26, 23, .05);
}
.pg-subnav__list {
	display: flex;
	gap: 0;
	max-width: var(--pg-inner);
	margin-inline: auto;
	overflow-x: auto;
	-webkit-overflow-scrolling: touch;
	scrollbar-width: none;
}
.pg-subnav__list::-webkit-scrollbar { display: none; }
.pg-subnav__link {
	flex-shrink: 0;
	padding: 13px 16px;
	font-size: var(--pg-text-cap);
	font-weight: 500;
	color: var(--pg-ink-muted);
	text-decoration: none;
	border-bottom: 2px solid transparent;
	transition: color .12s ease, border-color .12s ease;
}
.pg-subnav__link:hover { color: var(--pg-ink); }
.pg-subnav__link.is-current {
	color: var(--pg-ink);
	font-weight: 600;
	border-bottom-color: var(--pg-custard);
}

/* 4. CITIZENSHIP TIMELINE ----------------------------------- */
/* A horizontal step timeline. Each step connects to the previous
   one with its own ::before line, so the pattern works with any
   number of steps. CSS only — no JS. */
.pg-timeline {
	display: grid;
	grid-template-columns: repeat(var(--pg-timeline-cols, 3), 1fr);
	gap: 24px;
}
.pg-timeline__step {
	position: relative;
	text-align: center;
}
/* Connector to the previous step's dot — drawn behind the dots */
.pg-timeline__step:not(:first-child)::before {
	content: "";
	position: absolute;
	top: 21px;
	right: 50%;
	left: -50%;
	height: 2px;
	background: var(--pg-border-strong);
	z-index: 0;
}
/* Inner rules carry the .pg-timeline parent class so they out-specify
   the scoped `.pg-section p` typography — the timeline keeps its look
   when dropped inside a section band (its usual home). */
.pg-timeline .pg-timeline__dot {
	position: relative;
	z-index: 1;
	width: 44px;
	height: 44px;
	margin: 0 auto 14px;
	border-radius: 50%;
	background: var(--pg-custard);
	color: var(--pg-ink);
	display: flex;
	align-items: center;
	justify-content: center;
	font-size: var(--pg-text-body);
	font-weight: 700;
}
.pg-timeline .pg-timeline__title {
	font-size: 0.875rem;            /* 14px */
	font-weight: 600;
	color: var(--pg-ink);
	margin: 0 0 4px;
}
.pg-timeline .pg-timeline__sub {
	font-size: var(--pg-text-cap);
	line-height: 1.5;
	color: var(--pg-ink-muted);
	margin: 0;
}

@media (max-width: 600px) {
	.pg-timeline { grid-template-columns: 1fr; gap: 20px; }
	.pg-timeline__step:not(:first-child)::before { display: none; }
}

/* 5. SITE CHROME -------------------------------------------- */
/* Trust strip and footer are not in a .pg-section, so they keep the
   normal cascade; inner rules still carry the parent class for safety. */

/* Trust strip — a slim site-wide social-proof bar. Drop the matching
   pattern into a GeneratePress Hook Element on `generate_after_header`.
   The "as featured in" logos are an image; the rating is the
   Trustindex Google-reviews widget. */
.pg-trust {
	background: var(--pg-white);
	border-bottom: 1px solid var(--pg-border);
}
.pg-trust__in {
	max-width: var(--pg-wide);
	margin-inline: auto;
	padding: 9px 24px;
	display: flex;
	align-items: center;
	justify-content: space-between;
	gap: 20px;
}
.pg-trust__feat {
	display: flex;
	align-items: center;
	gap: 16px;
}
.pg-trust .pg-trust__label {
	font-size: var(--pg-text-xs);
	font-weight: 700;
	text-transform: uppercase;
	letter-spacing: .09em;
	color: var(--pg-ink-muted);
	margin: 0;
	white-space: nowrap;
}
.pg-trust .pg-trust__rating {
	display: flex;
	align-items: center;
	gap: 7px;
	font-size: var(--pg-text-sm);
	color: var(--pg-ink-mid);
	white-space: nowrap;
	margin: 0;
}
.pg-trust__rating strong { color: var(--pg-ink); }
.pg-trust__stars { color: var(--pg-custard-deep); letter-spacing: 1px; }
/* On small screens the press logos drop; the rating stays. */
@media (max-width: 820px) {
	.pg-trust__feat { display: none; }
	.pg-trust__in { justify-content: center; }
}

/* Footer — a four-column link footer. Drop the matching pattern into
   a Hook Element on `generate_before_footer`, or a Block Element set
   as the site footer. */
.pg-footer {
	background: var(--pg-pastry);
	padding: 40px 24px 24px;
}
.pg-footer__grid {
	max-width: var(--pg-wide);
	margin-inline: auto;
	display: grid;
	grid-template-columns: 1.4fr 1fr 1fr 1fr;
	gap: 28px;
}
.pg-footer .pg-footer__heading {
	font-size: var(--pg-text-sm);
	font-weight: 700;
	text-transform: uppercase;
	letter-spacing: .07em;
	color: var(--pg-ink);
	margin: 0 0 10px;
}
.pg-footer .pg-footer__about {
	font-size: var(--pg-text-cap);
	line-height: 1.6;
	color: var(--pg-ink-mid);
	margin: 10px 0 0;
}
.pg-footer__links {
	list-style: none;
	margin: 0;
	padding: 0;
}
.pg-footer__links li { padding: 3px 0; }
.pg-footer__links a {
	font-size: var(--pg-text-cap);
	color: var(--pg-ink-mid);
	text-decoration: none;
}
.pg-footer__links a:hover { color: var(--pg-ink); }
.pg-footer__base {
	max-width: var(--pg-wide);
	margin: 26px auto 0;
	padding-top: 16px;
	border-top: 1px solid var(--pg-border-strong);
	font-size: var(--pg-text-sm);
	color: var(--pg-ink-muted);
}
@media (max-width: 820px) {
	.pg-footer__grid { grid-template-columns: 1fr 1fr; }
}

/* Header CTA — turn a primary-menu custom-link item into a brand
   button by adding the CSS class `pg-header-cta` in the Customizer's
   menu editor. Put it last in the menu so it sits at the right edge.
   Overrides GP's menu-link styling for that item only. */
.main-navigation .main-nav ul li.pg-header-cta > a {
	background: var(--pg-pass);
	color: var(--pg-cream);
	border-radius: var(--pg-radius-sm);
	padding: 10px 20px;
	margin: 0 0 0 14px;
	line-height: 1;
	font-weight: 600;
	text-transform: none;
	letter-spacing: 0;
	transition: background-color .15s ease, transform .15s ease;
}
.main-navigation .main-nav ul li.pg-header-cta > a:hover,
.main-navigation .main-nav ul li.pg-header-cta > a:focus {
	background: var(--pg-pass-deep);
	color: var(--pg-cream);
	transform: translateY(-1px);
}
/* Sticky header — when the nav scrolls and gets `is_stuck`, give it
   a hairline so it reads as a real surface against the page. */
.main-navigation.is_stuck,
.navigation-stick {
	box-shadow: 0 1px 6px rgba(28, 26, 23, .08);
}

/* 6. POST BODY --------------------------------------------------- */
/* Defaults for ordinary single posts and pages — the ones we won't
   hand-craft as landing pages. Goal: even an editor pasting plain
   text gets a result that feels like Portugalist, with the article
   readable above the fold (title + image share the top row instead
   of stacking).

   Scoped to .single .inside-article / .page .inside-article. The page
   body is painted cream and the article card is painted --pg-paper
   (a hair lighter than cream) so the card lifts off the page with a
   gentle contrast — not the harsh white-on-cream of pure #FFFFFF. */

body.single,
body.page {
	background-color: var(--pg-cream);
}

/* Landing-page escape hatch. When an article body contains a full-
   bleed .pg-section band, the card chrome must drop away — otherwise
   the white card strip leaks through above, below and between the
   bands. Same for any .entry-content background/padding the user may
   have set in Additional CSS. Detected via :has() (modern browsers). */
/* Landing-page mode applies when either of two conditions is true:
     (a) The body content opens with a .pg-hero block. The .pg-hero
         is our custom hero component (used by every visa landing
         page — D1, D3, D4, D6, D7, D8, Golden Visa). Pages with it
         define their own hero, so the theme's article wrapper is
         unnecessary regardless of whether a featured image is set
         for SEO / social-sharing purposes.
     (b) The body opens with a .pg-section band AND no featured
         image is set. Catches landing-style content without a
         .pg-hero block.
   GeneratePress's `.featured-image-active` body class plus
   :has(article.has-post-thumbnail) are checked together because WP
   core adds has-post-thumbnail to <article>, not <body>. */
.single .inside-article:has(> .entry-content > .pg-hero),
.page .inside-article:has(> .entry-content > .pg-hero),
body:not(.featured-image-active):not(:has(article.has-post-thumbnail)).single .inside-article:has(> .entry-content > .pg-section),
body:not(.featured-image-active):not(:has(article.has-post-thumbnail)).page .inside-article:has(> .entry-content > .pg-section) {
	background: transparent;
	box-shadow: none;
	border-radius: 0;
	padding: 0;
	display: block;
}
/* Always neutralise .entry-content background when it contains
   .pg-hero or .pg-section bands — defeats user/Customizer CSS like
   `.entry-content { background-color: #fcf9f2 }` that would
   otherwise show as a visible off-cream strip around bands. */
.single .entry-content:has(> .pg-hero),
.page .entry-content:has(> .pg-hero),
.single .entry-content:has(> .pg-section),
.page .entry-content:has(> .pg-section) {
	background: transparent !important;
}
/* Landing-page only: also strip the entry-content padding so bands
   can run edge-to-edge as full-bleed bands. On articles (with the
   theme article header card) we keep the user's entry-content padding
   so bands sit politely inside the wrapper card. */
.single .entry-content:has(> .pg-hero),
.page .entry-content:has(> .pg-hero),
body:not(.featured-image-active):not(:has(article.has-post-thumbnail)).single .entry-content:has(> .pg-section),
body:not(.featured-image-active):not(:has(article.has-post-thumbnail)).page .entry-content:has(> .pg-section) {
	padding: 0 !important;
}
/* Cream body — landing pages should also sit on the same cream field
   as the bands themselves. */
body:has(.entry-content > .pg-hero),
body:not(.featured-image-active):not(:has(article.has-post-thumbnail)).single:has(.entry-content > .pg-section),
body:not(.featured-image-active):not(:has(article.has-post-thumbnail)).page:has(.entry-content > .pg-section) {
	background-color: var(--pg-cream);
}

.single .inside-article,
.page .inside-article {
	/* Match the body cream rather than --pg-paper. The previous slight
	   shade difference (paper #FDFAF1 vs cream #FBF5E8) created a
	   visible lighter "frame" around .pg-section bands embedded in
	   the article — they share the cream tone, so the wrapper card
	   should too. The shadow + border-radius still establish the
	   card. */
	background: var(--pg-cream);
	border-radius: var(--pg-radius);
	box-shadow: var(--pg-shadow);
	padding: 40px 48px;
	/* Grid lets the entry header and featured image share the top row
	   so the article opens above the fold. Without a featured image
	   the :has() override below collapses back to a normal flow. */
	display: grid;
	grid-template-columns: 1.1fr .9fr;
	grid-template-areas:
		"header image"
		"content content";
	column-gap: 36px;
	row-gap: 28px;
	align-items: stretch;
}
.single .inside-article > .entry-header,
.page .inside-article > .entry-header {
	grid-area: header;
	/* Flex column with full row height lets the byline drop to the
	   bottom of the column (margin-top:auto) so it sits next to the
	   image's lower edge instead of bunching at the top. */
	display: flex;
	flex-direction: column;
	height: 100%;
	padding-top: 24px;            /* lower the H1 a touch so it doesn't
	                                 sit higher than the bleeding image */
}
.single .inside-article > .featured-image,
.single .inside-article > .post-image,
.page .inside-article > .featured-image,
.page .inside-article > .post-image {
	grid-area: image;
	margin: -40px -48px 0 0;       /* bleed top + right edge of card */
	align-self: stretch;
}
.single .inside-article > .featured-image img,
.single .inside-article > .post-image img,
.page .inside-article > .featured-image img,
.page .inside-article > .post-image img {
	width: 100%;
	height: 100%;
	min-height: 280px;
	display: block;
	object-fit: cover;
	border-radius: 0 var(--pg-radius) 0 0;
}
.single .inside-article > .entry-content,
.page .inside-article > .entry-content { grid-area: content; }

/* Anything else that lands inside .inside-article — typically a GP
   Hook Element attached to generate_after_content (e.g. .talktous) —
   has no grid-area, so it falls into the first cell of an implicit
   new row, which is the LEFT column. That's why the after-content
   CTA looked pinned to the left at ~50% width.
   Force any non-recognised direct child to span the full grid width. */
.single .inside-article > *:not(.entry-header):not(.featured-image):not(.post-image):not(.entry-content),
.page .inside-article > *:not(.entry-header):not(.featured-image):not(.post-image):not(.entry-content) {
	grid-column: 1 / -1;
}

/* Posts/pages with no featured image: drop the grid so the entry
   header takes the full card width instead of leaving an empty cell. */
.single .inside-article:not(:has(.featured-image, .post-image)),
.page .inside-article:not(:has(.featured-image, .post-image)) {
	display: block;
}
.single .inside-article:not(:has(.featured-image, .post-image)) > .entry-header,
.page .inside-article:not(:has(.featured-image, .post-image)) > .entry-header {
	padding-top: 0;
	height: auto;
}

/* Entry header — tighter title, sentence case to match the body. */
.single .inside-article .entry-title,
.page .inside-article .entry-title {
	font-size: var(--pg-text-hero);
	line-height: 1.15;
	margin: 0 0 14px;
	text-transform: none;
	letter-spacing: -.01em;
}

/* Native GP post meta (date · by · reading time) — give the items
   real separators and pull the reading time out as a small pill so
   the line reads as three distinct items, not one jumbled string. */
.entry-header .entry-meta {
	font-size: var(--pg-text-cap);
	color: var(--pg-ink-muted);
	margin: 0;
}
.entry-header .entry-meta > span + span::before,
.entry-header .posted-on .reading-time::before {
	content: "\00B7";              /* middle dot */
	margin: 0 8px;
	color: var(--pg-border-strong);
	font-weight: 700;
}
.entry-header .entry-meta a {
	color: var(--pg-ink-mid);
	text-decoration: none;
}
.entry-header .entry-meta a:hover { color: var(--pg-link); }
.entry-header .posted-on .reading-time {
	display: inline-block;
	font-size: var(--pg-text-xs);
	font-weight: 700;
	text-transform: uppercase;
	letter-spacing: .06em;
	color: var(--pg-pass);
	background: var(--pg-pass-bg);
	padding: 3px 9px;
	border-radius: 999px;
}
/* The pill is its own visual unit; suppress the leading bullet so
   it doesn't read as " · · 5 MIN READ". */
.entry-header .posted-on .reading-time::before {
	content: "";
	margin: 0 6px 0 0;
}

/* Hide the "by <author>" link in the small meta line — the rich
   byline card below the meta already shows the author, avatar, bio
   and Contact-author button, so the meta-line author is redundant. */
.entry-header .entry-meta > .byline { display: none; }

/* Optional excerpt — a short summary paragraph between the meta line
   and the author block. Emitted by the PHP hook when the post has an
   explicit Excerpt set. */
.pg-excerpt {
	font-family: var(--pg-serif);
	font-style: italic;
	font-size: var(--pg-text-lead);
	line-height: 1.55;
	color: var(--pg-ink);
	margin: 18px 0 0;
}

/* Author block — sits at the bottom of the left column (next to the
   image's lower edge). Avatar + name on row 1, contact button on row
   2, short bio below. The whole block is pushed down by margin-top:
   auto, with a soft hairline above to separate it from the excerpt. */
.pg-byline {
	margin-top: auto;
	padding-top: 18px;
	border-top: 1px solid var(--pg-border);
}
.pg-byline__head {
	display: flex;
	align-items: center;
	gap: 12px;
	margin: 0;
}
/* Push the contact button to the right edge of the head row so it
   sits next to "Written by <name>" instead of stacking below it. */
.pg-byline__head .pg-byline__contact {
	margin-left: auto;
}
/* When the head row gets too tight (narrow card), wrap the button
   below the name rather than crushing the text. */
@media (max-width: 520px) {
	.pg-byline__head { flex-wrap: wrap; }
	.pg-byline__head .pg-byline__contact { margin-left: 0; }
}
/* Avatar and name both link to the author archive. They inherit
   colour (no blue/custard body-link treatment) and pick up a subtle
   hover state so readers can tell they're tappable. */
a.pg-byline__avatar { display: inline-block; line-height: 0; }
a.pg-byline__avatar img,
.pg-byline__avatar img {
	width: 44px;
	height: 44px;
	border-radius: 50%;
	object-fit: cover;
	display: block;
	transition: box-shadow .15s ease;
}
a.pg-byline__avatar:hover img { box-shadow: 0 0 0 2px var(--pg-custard); }
.pg-byline__by {
	font-size: var(--pg-text-cap);
	color: var(--pg-ink-muted);
	line-height: 1.3;
}
a.pg-byline__name,
.pg-byline__name {
	display: block;
	font-size: var(--pg-text-body);
	font-weight: 700;
	color: var(--pg-ink);
	text-decoration: none;
}
a.pg-byline__name:hover { color: var(--pg-link); }
.pg-byline__contact {
	display: inline-flex;
	align-items: center;
	gap: 6px;
	padding: 8px 14px;
	font-size: var(--pg-text-cap);
	font-weight: 700;
	color: var(--pg-ink);
	background: var(--pg-sky);
	border-radius: var(--pg-radius-sm);
	text-decoration: none;
	transition: background-color .15s ease, color .15s ease, transform .15s ease;
}
.pg-byline__contact:hover {
	background: var(--pg-sky-deep);
	color: var(--pg-white);
	transform: translateY(-1px);
}
.pg-byline__bio {
	margin: 12px 0 0;
	font-size: var(--pg-text-cap);
	line-height: 1.55;
	color: var(--pg-ink-mid);
}

/* Tools strip — a hook the user can attach a GP Hook Element to.
   In GeneratePress: Elements → Add → Hook → Custom Hook field:
   `portugalist_post_intro_tools`. Buttons, a quiz CTA, anything.
   When nothing's attached this stays empty and zero-height. */
.pg-post-tools {
	margin-top: 14px;
}
.pg-post-tools:empty { display: none; }

/* Typography inside the post body. All rules scoped to direct
   children of .entry-content so they don't bleed into landing-page
   blocks dropped inside (GB carousels, tabs, buttons, .pg-section
   bands). A button-link inside a carousel must not pick up the
   blue/custard body-link styling. */
.entry-content > h2,
.entry-content > h3,
.entry-content > h4 {
	/* Landing-page bands use uppercase h2s. Inside a reading body,
	   sentence case reads as natural prose. */
	text-transform: none;
	letter-spacing: 0;
}
.entry-content > h2 { font-size: var(--pg-text-h2); margin: 1.6em 0 .6em; }
.entry-content > h3 { font-size: var(--pg-text-h3); margin: 1.4em 0 .5em; }
.entry-content > p,
.entry-content > ul,
.entry-content > ol {
	font-size: var(--pg-text-md);
	line-height: 1.7;
	color: var(--pg-ink-mid);
}

/* Body links — bold blue with a custard underline. Scoped to direct
   children only (paragraphs, lists, headings, blockquotes, tables)
   so button-style links inside carousels / accordions / tabs are
   not touched. */
.entry-content > p a,
.entry-content > p a:visited,
.entry-content > ul a,
.entry-content > ul a:visited,
.entry-content > ol a,
.entry-content > ol a:visited,
.entry-content > h2 a, .entry-content > h3 a, .entry-content > h4 a,
.entry-content > blockquote a,
.entry-content > table a {
	color: var(--pg-link);
	font-weight: 700;
	text-decoration: underline;
	text-decoration-color: var(--pg-custard);
	text-decoration-thickness: 2px;
	text-underline-offset: 3px;
}
.entry-content > p a:hover,
.entry-content > ul a:hover,
.entry-content > ol a:hover,
.entry-content > h2 a:hover, .entry-content > h3 a:hover, .entry-content > h4 a:hover,
.entry-content > blockquote a:hover,
.entry-content > table a:hover {
	color: var(--pg-link-hover);
	text-decoration-color: var(--pg-custard-deep);
}

/* Blockquote — editorial pull-quote: deeply indented, big serif open-
   quote glyph in caramel, soft cream fill that punches through the
   article surface and ties back to the page colour. */
.entry-content > blockquote {
	position: relative;
	margin: 1.8em 0 1.8em 2em;
	padding: 22px 28px 22px 36px;
	background: var(--pg-cream);
	border-left: 3px solid var(--pg-caramel);
	border-radius: 0 var(--pg-radius-sm) var(--pg-radius-sm) 0;
	font-family: var(--pg-serif);
	font-style: italic;
	font-size: var(--pg-text-lead);
	line-height: 1.6;
	color: var(--pg-ink);
}
.entry-content > blockquote::before {
	content: "\201C";              /* opening curly double-quote */
	position: absolute;
	left: 10px;
	top: -22px;
	font-size: 5rem;
	line-height: 1;
	color: var(--pg-caramel);
	font-family: Georgia, "Times New Roman", serif;
	font-style: normal;
	opacity: .9;
}
.entry-content > blockquote p { margin: 0 0 .5em; }
.entry-content > blockquote p:last-child { margin-bottom: 0; }
.entry-content > blockquote cite {
	display: block;
	margin-top: 8px;
	font-family: inherit;
	font-style: normal;
	font-size: var(--pg-text-cap);
	color: var(--pg-ink-muted);
}
.entry-content > blockquote cite::before { content: "\2014\00A0"; }

/* Tables — bare core/table blocks should look brand-correct without
   the editor adding a custom class. Mirrors .pg-table: custard-soft
   header, warm hairline rows, rounded corners. The figure wrapper
   gets the radius + overflow so the rounded corners aren't clipped
   off the inner <table>. Scrolls horizontally on narrow screens. */
.entry-content > .wp-block-table,
.entry-content > figure.wp-block-table {
	margin: 1.6em 0;
	border: 1px solid var(--pg-border);
	border-radius: var(--pg-radius);
	overflow-x: auto;
	background: var(--pg-white);
}
.entry-content > .wp-block-table table,
.entry-content > figure.wp-block-table table,
.entry-content > table {
	width: 100%;
	border-collapse: collapse;
	border-spacing: 0;
	font-size: var(--pg-text-body);
	color: var(--pg-ink-mid);
	background: var(--pg-white);
}
/* Bare <table> without the figure wrapper still gets brand treatment. */
.entry-content > table {
	margin: 1.6em 0;
	border: 1px solid var(--pg-border);
	border-radius: var(--pg-radius);
	overflow: hidden;
}
.entry-content > .wp-block-table thead tr,
.entry-content > figure.wp-block-table thead tr,
.entry-content > table thead tr { background: var(--pg-custard-soft); }
.entry-content > .wp-block-table th,
.entry-content > figure.wp-block-table th,
.entry-content > table th {
	text-align: left;
	padding: 12px 16px;
	font-size: var(--pg-text-sm);
	font-weight: 700;
	text-transform: uppercase;
	letter-spacing: .04em;
	color: var(--pg-ink);
	border-bottom: 1px solid var(--pg-border);
}
.entry-content > .wp-block-table td,
.entry-content > figure.wp-block-table td,
.entry-content > table td {
	padding: 12px 16px;
	border-top: 1px solid var(--pg-border);
	vertical-align: top;
}
/* The first body row sits right under the head — no double border. */
.entry-content > .wp-block-table tbody tr:first-child td,
.entry-content > figure.wp-block-table tbody tr:first-child td,
.entry-content > table tbody tr:first-child td { border-top: none; }
/* Subtle zebra so wide tables scan easily. */
.entry-content > .wp-block-table tbody tr:nth-child(even),
.entry-content > figure.wp-block-table tbody tr:nth-child(even),
.entry-content > table tbody tr:nth-child(even) { background: var(--pg-cream); }
.entry-content > .wp-block-table td strong,
.entry-content > figure.wp-block-table td strong,
.entry-content > table td strong { color: var(--pg-ink); }
/* If the editor adds a caption (figcaption), brand it. */
.entry-content > .wp-block-table figcaption,
.entry-content > figure.wp-block-table figcaption {
	padding: 10px 16px;
	font-size: var(--pg-text-cap);
	color: var(--pg-ink-muted);
	text-align: center;
	background: var(--pg-white);
	border-top: 1px solid var(--pg-border);
}

/* Lists — deeper indent, green markers (distinct from text and from
   link colours), room to breathe between items so they read as
   scanned bullets rather than a wall. */
.entry-content > ul,
.entry-content > ol {
	padding-left: 2.4em;
	margin: 1.1em 0 1.5em;
}
.entry-content > ul > li,
.entry-content > ol > li {
	padding: 6px 0 6px 6px;
}
.entry-content > ul > li::marker { color: var(--pg-pass); font-size: 1.2em; }
.entry-content > ol > li::marker { color: var(--pg-pass); font-weight: 700; }

@media (max-width: 820px) {
	/* On narrower screens, the side-by-side hero stacks: image full
	   width on top of the header. The author block falls back to a
	   normal flow position (no need for margin-top:auto). */
	.single .inside-article,
	.page .inside-article {
		grid-template-columns: 1fr;
		grid-template-areas:
			"image"
			"header"
			"content";
		row-gap: 20px;
	}
	.single .inside-article > .entry-header,
	.page .inside-article > .entry-header {
		height: auto;
		padding-top: 0;
	}
	.single .inside-article > .featured-image,
	.single .inside-article > .post-image,
	.page .inside-article > .featured-image,
	.page .inside-article > .post-image {
		margin: -40px -48px 0;     /* bleed top + both sides */
	}
	.single .inside-article > .featured-image img,
	.single .inside-article > .post-image img,
	.page .inside-article > .featured-image img,
	.page .inside-article > .post-image img {
		border-radius: var(--pg-radius) var(--pg-radius) 0 0;
		min-height: 200px;
		max-height: 320px;
	}
	.pg-byline { margin-top: 20px; }
}
@media (max-width: 600px) {
	.single .inside-article,
	.page .inside-article {
		padding: 24px 20px;
	}
	.single .inside-article > .featured-image,
	.single .inside-article > .post-image,
	.page .inside-article > .featured-image,
	.page .inside-article > .post-image {
		margin: -24px -20px 0;
	}
}

/* 7. SEARCH & ARCHIVE RESULTS ----------------------------------- */
/* Default GP archive output: an h1.page-title + a stack of article
   cards each with a featured image, title, excerpt, and "Read More"
   button. Out of the box it reads as a wall of text. This block:
     • makes each result a clear card (white surface, hairline, shadow)
     • puts the thumbnail on the left, the body on the right
     • styles the title as a real link, the read-more as a body link
     • adds a refinement search form below the page title
   Applies on both search-results and category/tag archive pages. */

body.search,
body.archive {
	background-color: var(--pg-cream);
}

.search-results .page-header,
.archive .page-header {
	max-width: var(--pg-wide);
	margin: 32px auto 24px;
	padding: 0 24px;
	text-align: center;
}
.search-results .page-header .page-title,
.archive .page-header .page-title {
	font-size: var(--pg-text-h2);
	color: var(--pg-ink);
	margin: 0 auto 16px;
	max-width: 800px;
	line-height: 1.2;
	text-transform: none;
	letter-spacing: -.005em;
}
/* Italic accent on the search query inside the page title. The PHP
   filter wraps the query in <em> — this just paints it custard. */
.search-results .page-header .page-title em {
	font-style: normal;
	color: var(--pg-custard-deep);
}
/* Refinement search bar — output by a generate_after_archive_title
   hook on search-results pages, using the .pg-search component. */
.search-results .page-header .pg-search {
	margin: 0 auto 8px;
}

/* Each result card */
.search-results .site-main > article.post,
.search-results .site-main > article.page,
.archive .site-main > article.post {
	max-width: var(--pg-wide);
	margin: 0 auto 16px !important;     /* defeat GP default vertical rhythm */
	padding: 0;
}
.search-results .site-main > article > .inside-article,
.archive .site-main > article > .inside-article {
	background: var(--pg-paper);
	border-radius: var(--pg-radius);
	box-shadow: var(--pg-shadow);
	padding: 20px 24px;
	display: grid;
	/* DEFAULT TO SINGLE COLUMN. The two-column "thumb + body" layout
	   is opted-in below only when the card has a verified working
	   image. This inverted logic is more robust than trying to
	   "collapse if broken" with nested :has(:not(:has())) chains,
	   which behaved unreliably in earlier iterations. */
	grid-template-columns: 1fr;
	column-gap: 22px;
	row-gap: 6px;
	align-items: start;
	transition: box-shadow .15s ease, transform .15s ease;
}
/* Two-column opt-in: only when an actual <img> lives inside one of
   the recognised thumbnail wrappers. Broken/empty .post-image
   wrappers don't trigger this and the card stays single-column. */
.search-results .site-main > article > .inside-article:has(> .post-image img),
.search-results .site-main > article > .inside-article:has(> .featured-image img),
.search-results .site-main > article > .inside-article:has(> .wp-block-post-featured-image img),
.archive .site-main > article > .inside-article:has(> .post-image img),
.archive .site-main > article > .inside-article:has(> .featured-image img),
.archive .site-main > article > .inside-article:has(> .wp-block-post-featured-image img) {
	grid-template-columns: 200px 1fr;
}
.search-results .site-main > article > .inside-article:hover,
.archive .site-main > article > .inside-article:hover {
	box-shadow: 0 5px 16px rgba(28, 26, 23, .12);
	transform: translateY(-1px);
}
/* CRITICAL: pin the thumbnail to column 1 and force every other
   child (header, summary, read-more) into column 2 — regardless of
   the source order GP emits them in. Some post types render the
   .post-image AFTER the entry-header, which without these explicit
   placements puts the title in the narrow 200px slot and balloons
   the image into the 1fr slot.

   GeneratePress / WordPress emit the thumbnail wrapper under
   different class names depending on the template:
     • .post-image                  — classic archive markup
     • .featured-image              — single-template-derived archives
     • .wp-block-post-featured-image — FSE / block-based archive query
   We target all three so cards stay consistent.

   FLOAT OVERRIDE: GP Premium's Blog → Featured Images addon adds
   the body class `post-image-aligned-left` and floats .post-image
   left from `featured-images.min.css`. Floats are removed from CSS
   grid flow, so grid-column has no effect on a floated element —
   the image escapes its column and overlaps the title. `float:none`
   forces the wrapper back into the grid. Same for `clear`, in case
   GP also sets `clear: both` on entry-header. */
.search-results .post-image,
.search-results .featured-image,
.search-results .wp-block-post-featured-image,
.archive .post-image,
.archive .featured-image,
.archive .wp-block-post-featured-image {
	float: none !important;
	clear: none !important;
	grid-column: 1;
	grid-row: 1;
	align-self: start;
	margin: 0;
	border-radius: var(--pg-radius-sm);
	overflow: hidden;
	aspect-ratio: 16 / 11;
	background: var(--pg-pastry);
}
/* Only force header/summary into column 2 when the card actually
   has a working thumbnail in column 1. Otherwise (no image, or
   broken image with hidden wrapper) let everything flow into the
   single column naturally. */
.search-results .site-main > article > .inside-article:has(> .post-image img) > *:not(.post-image):not(.featured-image):not(.wp-block-post-featured-image),
.search-results .site-main > article > .inside-article:has(> .featured-image img) > *:not(.post-image):not(.featured-image):not(.wp-block-post-featured-image),
.search-results .site-main > article > .inside-article:has(> .wp-block-post-featured-image img) > *:not(.post-image):not(.featured-image):not(.wp-block-post-featured-image),
.archive .site-main > article > .inside-article:has(> .post-image img) > *:not(.post-image):not(.featured-image):not(.wp-block-post-featured-image),
.archive .site-main > article > .inside-article:has(> .featured-image img) > *:not(.post-image):not(.featured-image):not(.wp-block-post-featured-image),
.archive .site-main > article > .inside-article:has(> .wp-block-post-featured-image img) > *:not(.post-image):not(.featured-image):not(.wp-block-post-featured-image) {
	grid-column: 2;
}
.search-results .post-image a,
.search-results .featured-image a,
.search-results .wp-block-post-featured-image a,
.archive .post-image a,
.archive .featured-image a,
.archive .wp-block-post-featured-image a { display: block; width: 100%; height: 100%; }
.search-results .post-image img,
.search-results .featured-image img,
.search-results .wp-block-post-featured-image img,
.archive .post-image img,
.archive .featured-image img,
.archive .wp-block-post-featured-image img {
	width: 100%;
	height: 100%;
	object-fit: cover;
	display: block;
}

/* Defensive backstop — if a template renders a bare <img> as a
   direct child of .inside-article (no recognised wrapper at all),
   clamp it to the thumbnail column instead of letting it bleed
   full-width like the Millennium card was doing. */
.search-results .site-main > article > .inside-article > img,
.archive .site-main > article > .inside-article > img {
	grid-column: 1;
	grid-row: 1;
	width: 100%;
	height: 100%;
	object-fit: cover;
	border-radius: var(--pg-radius-sm);
	aspect-ratio: 16 / 11;
}

/* Posts without ANY recognised thumbnail wrapper: collapse to a
   single column and release the column-2 lock so the body fills
   the full width. */
.search-results .site-main > article > .inside-article:not(:has(.post-image)):not(:has(.featured-image)):not(:has(.wp-block-post-featured-image)):not(:has(> img)),
.archive .site-main > article > .inside-article:not(:has(.post-image)):not(:has(.featured-image)):not(:has(.wp-block-post-featured-image)):not(:has(> img)) {
	grid-template-columns: 1fr;
}
.search-results .site-main > article > .inside-article:not(:has(.post-image)):not(:has(.featured-image)):not(:has(.wp-block-post-featured-image)):not(:has(> img)) > *,
.archive .site-main > article > .inside-article:not(:has(.post-image)):not(:has(.featured-image)):not(:has(.wp-block-post-featured-image)):not(:has(> img)) > * {
	grid-column: 1;
}

/* Hide the pastry placeholder background when an actual image has
   loaded successfully — the warm rectangle was meant as a fallback,
   not a visible "frame" around the thumbnail. */
.search-results .post-image:has(img),
.search-results .featured-image:has(img),
.archive .post-image:has(img),
.archive .featured-image:has(img) {
	background: transparent;
}

/* BROKEN THUMBNAIL — some posts (e.g. /mortgage-portugal/) have an
   empty .post-image wrapper:
       <div class="post-image"><a href="..."></a></div>
   GP emitted the container but no <img> made it through. Without
   intervention the wrapper still claims its grid column and shows
   the pastry placeholder rectangle. Hide the empty wrapper AND
   collapse the card to single column so the body fills the row. */
.search-results .post-image:not(:has(img)),
.search-results .featured-image:not(:has(img)),
.search-results .wp-block-post-featured-image:not(:has(img)),
.archive .post-image:not(:has(img)),
.archive .featured-image:not(:has(img)),
.archive .wp-block-post-featured-image:not(:has(img)) {
	display: none;
}
.search-results .site-main > article > .inside-article:has(.post-image:not(:has(img))),
.search-results .site-main > article > .inside-article:has(.featured-image:not(:has(img))),
.archive .site-main > article > .inside-article:has(.post-image:not(:has(img))),
.archive .site-main > article > .inside-article:has(.featured-image:not(:has(img))) {
	grid-template-columns: 1fr;
}
.search-results .site-main > article > .inside-article:has(.post-image:not(:has(img))) > *,
.search-results .site-main > article > .inside-article:has(.featured-image:not(:has(img))) > *,
.archive .site-main > article > .inside-article:has(.post-image:not(:has(img))) > *,
.archive .site-main > article > .inside-article:has(.featured-image:not(:has(img))) > * {
	grid-column: 1;
}

/* DEFENSIVE WIDTH CAP — belt and braces. The grid-template-columns
   declaration should already constrain .post-image to 200px, but if
   any rule (theme, plugin, future GP update) interferes with the
   grid track, the wrapper or image could blow out. Hard-cap both. */
.search-results .post-image,
.search-results .featured-image,
.search-results .wp-block-post-featured-image,
.archive .post-image,
.archive .featured-image,
.archive .wp-block-post-featured-image {
	max-width: 200px;
}
.search-results .post-image img,
.search-results .featured-image img,
.search-results .wp-block-post-featured-image img,
.archive .post-image img,
.archive .featured-image img,
.archive .wp-block-post-featured-image img {
	max-width: 100%;
	max-height: 100%;
}

/* Body content can contain inline <img>/<figure>/<iframe>/<video>
   blocks pulled from the post or page body. Hide them — the result
   card has its own thumbnail slot; an uncropped 1200px image inline
   balloons the card and breaks the row.

   IMPORTANT: pages (article.page) render via the_content() not
   the_excerpt(), so the whole page body lands inside .entry-content
   — including hero images, picsum placeholders, callouts. Without
   covering .entry-content too, page results blow out vertically
   while post results stay tidy. */
.search-results .entry-summary img,
.search-results .entry-summary figure,
.search-results .entry-summary iframe,
.search-results .entry-summary video,
.search-results .entry-content img,
.search-results .entry-content figure,
.search-results .entry-content iframe,
.search-results .entry-content video,
.archive .entry-summary img,
.archive .entry-summary figure,
.archive .entry-summary iframe,
.archive .entry-summary video,
.archive .entry-content img,
.archive .entry-content figure,
.archive .entry-content iframe,
.archive .entry-content video {
	display: none;
}

/* Pages render their entire body via the_content() in search results,
   so a long landing page would produce a result card the height of the
   page itself. Clamp the body height and fade the bottom so it reads
   as a preview, not the whole article. Posts use .entry-summary so
   they're naturally short and don't need this. */
.search-results .site-main > article.page .entry-content,
.archive .site-main > article.page .entry-content {
	max-height: 8em;
	overflow: hidden;
	position: relative;
	mask-image: linear-gradient(to bottom, #000 60%, transparent 100%);
	-webkit-mask-image: linear-gradient(to bottom, #000 60%, transparent 100%);
}

/* Page-body bands shouldn't get their own background paint inside a
   search-result card — strip the band chrome so the preview reads
   as text excerpt, not a stack of mini bands. */
.search-results .site-main > article.page .entry-content .pg-section,
.search-results .site-main > article.page .entry-content .pg-hero,
.archive .site-main > article.page .entry-content .pg-section,
.archive .site-main > article.page .entry-content .pg-hero {
	background: transparent !important;
	padding: 0 !important;
	margin: 0 !important;
	min-height: 0 !important;
}
.search-results .site-main > article.page .entry-content .pg-hero__media,
.archive .site-main > article.page .entry-content .pg-hero__media {
	display: none !important;
}

/* Defensive — some posts (custom landing pages with text-align:center
   inside their body) leak that alignment to the result card's title
   via inherited CSS. Force result cards back to a left-aligned
   reading rhythm regardless of what the source post does. */
.search-results .site-main > article > .inside-article,
.archive .site-main > article > .inside-article {
	text-align: left;
}
.search-results .site-main > article > .inside-article .entry-header,
.search-results .site-main > article > .inside-article .entry-title,
.search-results .site-main > article > .inside-article .entry-summary,
.archive .site-main > article > .inside-article .entry-header,
.archive .site-main > article > .inside-article .entry-title,
.archive .site-main > article > .inside-article .entry-summary {
	text-align: left;
}

/* Entry header + title — title becomes the primary clickable. */
.search-results .entry-header,
.archive .entry-header {
	margin: 0 0 6px;
	padding: 0;
}
/* Title — bumped specificity so a custom title colour set on a
   custom post type (e.g. places) can't paint these search-result
   titles giant-custard. */
.search-results .site-main > article > .inside-article .entry-title,
.archive .site-main > article > .inside-article .entry-title {
	font-size: var(--pg-text-h3);
	line-height: 1.25;
	margin: 0;
	text-transform: none;
	letter-spacing: 0;
	font-weight: 700;
	color: var(--pg-ink);
}
.search-results .site-main > article > .inside-article .entry-title a,
.archive .site-main > article > .inside-article .entry-title a {
	color: var(--pg-ink);
	text-decoration: none;
}
.search-results .site-main > article > .inside-article:hover .entry-title a,
.archive .site-main > article > .inside-article:hover .entry-title a {
	color: var(--pg-custard-deep);
}

/* Entry meta (date, category) — small, muted, above or below title. */
.search-results .entry-meta,
.archive .entry-meta {
	font-size: var(--pg-text-xs);
	color: var(--pg-ink-muted);
	margin: 0 0 8px;
}
.search-results .entry-meta a,
.archive .entry-meta a { color: inherit; text-decoration: none; }
.search-results .entry-meta a:hover,
.archive .entry-meta a:hover { color: var(--pg-link); }

/* Summary text — comfortable line-height, capped at ~3 lines. */
.search-results .entry-summary,
.archive .entry-summary {
	font-size: var(--pg-text-cap);
	line-height: 1.55;
	color: var(--pg-ink-mid);
	margin: 0;
}
.search-results .entry-summary p,
.archive .entry-summary p { margin: 0 0 10px; }

/* The "Read more" button — defeat GP's default dark filled button
   and present as a brand body-link with arrow. */
.search-results .read-more-container,
.archive .read-more-container { margin: 10px 0 0; }
.search-results .read-more-container .read-more,
.archive .read-more-container .read-more {
	display: inline-flex;
	align-items: center;
	gap: 4px;
	padding: 0;
	font-size: var(--pg-text-cap);
	font-weight: 700;
	color: var(--pg-link);
	background: transparent !important;
	border: none !important;
	border-radius: 0;
	text-decoration: underline;
	text-decoration-color: var(--pg-custard);
	text-decoration-thickness: 2px;
	text-underline-offset: 3px;
	transition: color .12s ease, text-decoration-color .12s ease;
}
.search-results .read-more-container .read-more::after,
.archive .read-more-container .read-more::after { content: "\00A0→"; }
.search-results .read-more-container .read-more:hover,
.archive .read-more-container .read-more:hover {
	color: var(--pg-link-hover);
	text-decoration-color: var(--pg-custard-deep);
	background: transparent !important;
}

/* No-results message (search returns nothing) */
.search-no-results .page-header { text-align: center; }
.search-no-results .no-results.not-found {
	max-width: 720px;
	margin: 32px auto;
	padding: 32px;
	background: var(--pg-paper);
	border-radius: var(--pg-radius);
	box-shadow: var(--pg-shadow);
	text-align: center;
}
.search-no-results .no-results .page-content .pg-search { margin: 24px auto 0; }

/* Pagination at the bottom of results */
.search-results .paging-navigation,
.archive .paging-navigation {
	max-width: var(--pg-wide);
	margin: 28px auto 60px;
	padding: 0 24px;
	text-align: center;
}

@media (max-width: 640px) {
	.search-results .site-main > article > .inside-article,
	.archive .site-main > article > .inside-article {
		grid-template-columns: 1fr;
		gap: 14px;
		padding: 18px 20px;
	}
	.search-results .post-image,
	.search-results .featured-image,
	.search-results .wp-block-post-featured-image,
	.archive .post-image,
	.archive .featured-image,
	.archive .wp-block-post-featured-image { aspect-ratio: 16 / 9; }
}

/* 9. TALK TO US — END-OF-CONTENT CTA -------------------------- */
/* Snippet attached via a GP "Hook" Element on generate_after_content.
   The raw markup is just a <div class="talktous"> wrapper with a logo,
   a heading, a paragraph, and a Gravity Form. Without help it inherits
   no width and clings to the left of whatever container it lands in.
   Wrap it in the same band-card chrome the design system uses for
   pg-callout so it reads as an editorial CTA, not an orphan form. */
.talktous {
	max-width: var(--pg-inner);
	margin: 48px auto 32px;
	padding: 36px 40px;
	background: var(--pg-pastry);
	border: 1px solid var(--pg-border);
	border-radius: var(--pg-radius);
	box-shadow: var(--pg-shadow);
	color: var(--pg-ink-mid);
	font-size: var(--pg-text-body);
	line-height: 1.6;
}

/* Heading row — small logo lockup + the "Thinking about Moving to
   Portugal?" line. The author wrote this as a single <p id="wecanhelp">
   with the logo as a sibling <img>, so flex it to keep them on one row. */
.talktous #wecanhelp {
	display: flex;
	align-items: center;
	gap: 14px;
	margin: 0 0 14px;
	padding: 0;
	font-family: var(--pg-serif);
	font-size: var(--pg-text-h2);
	line-height: 1.25;
	color: var(--pg-ink);
}
.talktous #wecanhelp img {
	width: 56px;
	height: 56px;
	flex: none;
	border-radius: 50%;
	object-fit: contain;
	background: var(--pg-white);
	padding: 6px;
	border: 1px solid var(--pg-border);
}
.talktous #wecanhelp strong {
	font-weight: 600;   /* the serif heading carries weight already */
}

/* Body copy that sits between the heading and the form. */
.talktous > p:not(#wecanhelp),
.talktous > br + *:not(form):not(.gform_wrapper):not(.gform_anchor) {
	margin: 0 0 18px;
}

/* The Gravity Form itself — give it a little breathing room from the
   intro text and let gravity-forms.css handle the rest. */
.talktous .gform_wrapper {
	margin-top: 20px;
}

@media (max-width: 640px) {
	.talktous {
		padding: 24px 22px;
		margin: 32px auto 24px;
	}
	.talktous #wecanhelp {
		font-size: var(--pg-text-h3);
		gap: 12px;
	}
	.talktous #wecanhelp img {
		width: 44px;
		height: 44px;
	}
}
