/**
 * Theme Name: Edilgrisendi Blocksy Child
 * Description: Child theme del sito Edilgrisendi s.p.a.
 * Author: Black Studio
 * Template: blocksy
 * Text Domain: blocksy
 */

/* `Text Domain` resta `blocksy` di proposito: le stringhe in functions.php sono
 * tradotte con quel dominio, cambiarlo qui le lascerebbe senza traduzione. */

/* =============================================================================
 * Migrated from Appearance > Customize > Additional CSS on 2026-08-07.
 * The Customizer field is now empty: edit this file instead, so the CSS is
 * versioned and reviewable in a diff. See a11y-audit.md #17 and #18.
 *
 * This file is enqueued by functions.php at a late priority, so it loads AFTER
 * Blocksy's own `ct-main-styles`. Do not change that priority: `parent-style`
 * is printed BEFORE `ct-main-styles`, so depending on it would put this file
 * too early and the overrides below would lose.
 * ============================================================================= */

/* -----------------------------------------------------------------------------
 * Header
 * -------------------------------------------------------------------------- */

.ct-header-cta a {
	gap: 0.7em;
	padding: 9px 20px 9px 10px;
}

/* -----------------------------------------------------------------------------
 * a11y #19 - Form label colour, scoped instead of global
 *
 * This used to be `label { color: #ffffff !important }`, which turned EVERY
 * label on the site white and worked only because both forms happen to sit on
 * the dark blue section. It had already needed one exception patch for the
 * immobili filter, which is what a rule that does not scale looks like: the
 * next form on a light background would have had white-on-white labels.
 *
 * Only Fluent Forms needs white labels, so the rule is scoped to it and the
 * exception is gone. No `!important` required either.
 *
 * `label { color: inherit }` would have been more elegant and does NOT work:
 * the wrapper inside the dark section inherits the default dark body text, so
 * the labels would have rendered at 1.02:1. Measured before ruling it out.
 *
 * Residual risk, smaller and more predictable than before: a Fluent Form placed
 * on a light background would still get white labels. That belongs to whatever
 * styles that section, not to a global rule.
 * -------------------------------------------------------------------------- */

.fluentform label {
	color: #ffffff;
}

/* -----------------------------------------------------------------------------
 * Immobili filter block (rendered by functions.php)
 * -------------------------------------------------------------------------- */

.immobile-filter-form {
	display: flex;
	flex-wrap: wrap;
	align-items: center;
	padding-top: 10px;
	margin-block: 1rem;
}

/* The `color` override that used to live here is gone with a11y #19: it existed
 * only to undo the global white rule. These labels now take the theme's own
 * colour, measured at 12.91:1 on the filter's light background. */

.immobile-filter-form .immobile-filter-fieldset {
	display: flex;
	align-items: center;
	justify-content: space-between;
	flex-wrap: wrap;
	gap: 2rem;
	padding-top: 10px;
	padding-left: 0;
	margin-block: 1rem;
	flex: 1 1;
}

.immobile-filter-field {
	flex: 1;
	min-width: min(100%, 360px);
}

.immobile-filter-actions {
	display: flex;
	align-items: center;
	justify-content: flex-end;
	gap: 2rem;
	padding-top: 24px;
}

@media screen and (max-width: 960px) {
	.immobile-filter-form {
		display: block;
		padding-top: 0;
		margin-block: 0;
	}

	.immobile-filter-form .immobile-filter-fieldset {
		padding-right: 0;
		padding-bottom: 0;
		gap: 1rem;
	}

	.immobile-filter-actions {
		padding-top: 12px !important;
	}
}

/* -----------------------------------------------------------------------------
 * Immobile singolo Template - sticky column on short viewports
 *
 * The right-hand column of content block 305 (`Immobile singolo Template`) is
 * set to `position: sticky; top: 0` from the Greenshift block panel. When the
 * viewport is shorter than the column, sticky has nothing left to scroll and
 * the card ends up pinned with its lower part unreachable, so below 700px of
 * viewport height it falls back to normal flow.
 *
 * The ID is hardcoded, same caveat as the `uniqueId` filter in functions.php:
 * if that column is recreated from the backend the ID changes and this rule
 * stops applying silently.
 *
 * `!important` is needed because Greenshift prints its own
 * `#gspb_col-id-gsbp-0b8cfe0 { position: sticky }` as an inline <style>, at the
 * same specificity (one ID) but later in the document.
 * -------------------------------------------------------------------------- */

@media (max-height: 700px) {
	#gspb_col-id-gsbp-0b8cfe0 {
		position: static !important;
	}
}

/* -----------------------------------------------------------------------------
 * a11y #1 - Focus ring (WCAG 2.4.7 Focus Visible A, 1.4.11 Non-text Contrast AA)
 *
 * Replaces the previous single-colour ring (#0d47a1). A single colour cannot
 * work here: the theme reuses the same colours for section and button
 * backgrounds, so the ring dropped to 1.00-1.01:1 on the brand blue (#005077)
 * and the green section (#00573c), and 1.65:1 on the dark blue (#002e44) used
 * by header, footer and the contact section. At 1:1 the focus is invisible.
 *
 * Two bands instead: white inner + dark outer. Whichever the background, one
 * band clears 3:1. Measured on 20 elements across 4 pages: 20 pass, 0 fail,
 * worst case 8.65:1.
 *
 * Do NOT wrap the selectors in :where() - it zeroes their specificity, so
 * `:where(a):focus-visible` (0-1-0) loses to Blocksy's `a:focus-visible`
 * (0-1-1) even with !important on both. Measured: 12 of 20 stayed failing.
 * -------------------------------------------------------------------------- */

a:focus-visible,
button:focus-visible,
input:focus-visible,
select:focus-visible,
textarea:focus-visible,
summary:focus-visible,
[role="button"]:focus-visible,
[tabindex]:not([tabindex="-1"]):focus-visible,
.ct-menu-link:focus-visible,
.gspb-buttonbox:focus-visible,
.ff-btn-submit:focus-visible,
.ff-el-input--content input:focus-visible,
.ff-el-input--content textarea:focus-visible,
.ff-el-input--content select:focus-visible {
	outline: 2px solid #ffffff !important;
	outline-offset: 0 !important;
	box-shadow: 0 0 0 4px #002e44 !important;
	border-radius: 2px;
}

/* -----------------------------------------------------------------------------
 * a11y #7 - Links in a text block need a non-colour cue (WCAG 1.4.1 Use of Color)
 *
 * This rule already existed in the Customizer but was never applied: prose had
 * been pasted above it, and the CSS parser swallowed the first rule that
 * followed. Restored here as valid CSS. Real effect measured: 6 links per page,
 * all in the footer (email, PEC, phone, ANCE), which are exactly the ones axe
 * flagged at 1.49:1 against the surrounding text.
 *
 * 2026-08-14: widened from `.entry-content p a` / `.entry-content li a` to
 * `.entry-content a`. Greenshift wraps its text in `div.gspb_text`, not in `<p>`,
 * so the original selectors matched NOTHING inside the page content: the email,
 * PEC and phone links on /contatti/ were left without the underline that their
 * footer twins had. Counted on the rendered pages: 0 links in the content matched
 * the old selectors.
 *
 * The wider selector reaches two families that must NOT be underlined, both
 * handled in the exclusion rule below:
 *   - Greenshift buttons (the anchor itself carries `.gspb-buttonbox`)
 *   - immobile card titles, `<h2 class="ct-dynamic-data"><a>` in the home listing
 * Anchors that wrap only an image (`a.ct-dynamic-media`) need no exception:
 * text-decoration has no text to draw on there.
 * -------------------------------------------------------------------------- */

/* `text-decoration` is a SHORTHAND: `underline !important` also sets
 * `text-decoration-thickness: auto` at !important, which beat the plain 1px
 * longhand that used to sit here, whatever the source order. Measured: computed
 * thickness was `auto`, so the 1px and the 2px on focus below had never applied.
 * The longhands need !important too. `text-underline-offset` is fine as it is,
 * it is not part of the shorthand. */
/* The footer widget menus are in here too. They are plain `<a>` with NO class of
 * their own, so nothing else reached them: measured, they were the only links in
 * the footer still without the cue, next to the email and phone links that had it.
 * `.ct-widget .widget-menu a` matches exactly those 7 links and nothing outside
 * the footer, so it stands in for the `#nav_menu-2` / `#nav_menu-3` widget ids,
 * which change whenever a widget is recreated. Same selector as a11y #9 below. */
p a,
.entry-content a,
.ct-text-container a,
.ct-widget .widget-menu a {
	text-decoration: underline !important;
	text-decoration-thickness: 1px !important;
	text-underline-offset: 3px;
}

/* Hover drops the underline. 1.4.1 is satisfied by the resting state, which keeps
 * the cue; on hover the pointer is already over the link and the cursor change
 * carries the affordance. Keyboard focus is deliberately NOT included: it keeps
 * the thicker underline below, and it must stay after this rule, since the two
 * selectors tie on specificity and the later one wins when an element is hovered
 * and focused at the same time. */
p a:hover,
.entry-content a:hover,
.ct-text-container a:hover,
.ct-widget .widget-menu a:hover {
	text-decoration: none !important;
}

p a:focus-visible,
.entry-content a:focus-visible,
.ct-text-container a:focus-visible,
.ct-widget .widget-menu a:focus-visible {
	text-decoration: underline !important;
	text-decoration-thickness: 2px !important;
}

/* Buttons, menu items and form submits carry their own affordance, and so do the
 * card titles, whose whole card is the click target.
 *
 * The `.entry-content`-prefixed copies are not redundant: bare `.gspb-buttonbox`
 * is 0-1-0 and would LOSE to `.entry-content a` at 0-1-1, `!important` on both.
 * Every selector here has to outrank that. */
.gspb-buttonbox,
.ct-menu-link,
.ff-btn-submit,
.button,
.entry-content .gspb-buttonbox,
.entry-content .ff-btn-submit,
.entry-content .button,
.entry-content h1 a,
.entry-content h2 a,
.entry-content h3 a,
.entry-content h4 a,
.entry-content h5 a,
.entry-content h6 a {
	text-decoration: none !important;
}

/* -----------------------------------------------------------------------------
 * a11y #9 - Footer menu target size (WCAG 2.5.8 Target Size Minimum, AA)
 *
 * The links in the footer widget menus were 18px tall against a 24px minimum,
 * with 23.6px of safe clickable space between neighbours.
 *
 * The anchors carry no class of their own and are `display: inline`, so vertical
 * padding would not grow their box the way it does on a block. `inline-block`
 * plus a min-height does, and keeps the anchor as wide as its text: switching to
 * `display: block` also works but stretches every link to the full 238px column,
 * which would make the focus ring span the whole width and change the look.
 *
 * Measured: all 7 links go from 18px to 24px, widths unchanged, the menu grows
 * by 1px in total and the document height does not move. axe target-size 2 -> 0.
 * -------------------------------------------------------------------------- */

.ct-widget .widget-menu a {
	display: inline-block;
	min-height: 24px;
}

/* -----------------------------------------------------------------------------
 * a11y #13 - Font sizes in rem instead of px (WCAG 1.4.4 Resize Text, AA)
 *
 * A px font-size ignores the browser's font-size preference, so text-only
 * resize does nothing. The child stylesheet declared none: every px came from
 * vendor CSS or from values typed into the Greenshift editor.
 *
 * `font-size-units.js` counts 53 px rules, but only 9 of them match an element
 * that exists on this site: the other 44 are Fluent Forms cropper/steps/upload,
 * WooCommerce and pagination variants that are never rendered. Overriding all
 * 53 would mean 44 dead rules to maintain, so only the live ones are here.
 *
 * Root font-size measured at runtime: 16px. So rem = px / 16. Do not assume 16:
 * a theme using `html { font-size: 62.5% }` would need px / 10 and converting
 * with the wrong divisor rescales the whole site.
 *
 * Deliberately NOT converted: the 42px/20px on
 * `.gspb_slider-id-gsbp-62b6676 .swiper-button-*::after`. That is Swiper's arrow
 * glyph, an icon rather than text, and scaling it with the font preference would
 * push it out of its control box. 1.4.4 is about text.
 * -------------------------------------------------------------------------- */

/* Blocksy boilerplate (main.min.css): form labels and fieldset legends. */
label {
	font-size: 0.9375rem; /* was 15px */
}

legend {
	font-size: 0.875rem; /* was 14px */
}

/* Values typed into the Greenshift editor, emitted as inline <style>.
 *
 * CAVEAT: the size now lives in two places. If an editor changes one of these
 * blocks in wp-admin the new value will be overridden here and the change will
 * appear to do nothing. Better long term is to set the unit to rem in the block
 * panel and drop these five rules. Block IDs are listed so they can be found.
 */
.gspb_text-id-gsbp-4741d356-0b32,
.gspb_text-id-gsbp-335a990d-d932,
.gspb_text-id-gsbp-3329a9dd-619b {
	font-size: 1.125rem; /* was 18px */
}

.gspb_text-id-gsbp-f6b3bff4-2cd6 {
	font-size: 0.8125rem; /* was 13px */
}

.gspb_button-id-gsbp-06006e6c-4e3b > .gspb-buttonbox {
	font-size: 1rem; /* was 16px */
}

/* -----------------------------------------------------------------------------
 * Background video control (WCAG 2.2.2 Pause Stop Hide, 1.4.11 Non-text
 * Contrast, 2.5.8 Target Size)
 *
 * The button itself is built by `assets/js/hero-video-toggle.js`. Only its look
 * lives here.
 *
 * The solid background is not decoration: the control sits on top of a moving
 * video, so its contrast cannot depend on which frame happens to be showing.
 * A filled chip plus a white hairline keeps both the icon and the edge of the
 * control readable over any frame. 44x44 against the 24x24 that 2.5.8 asks for.
 * -------------------------------------------------------------------------- */

/* z-index 300 is not a magic number. The button and the hero content share one
 * stacking context, the one `.swiper-slide` creates, and inside it Greenshift
 * puts its content container at 220 with a full bleed `.gspb_backgroundOverlay`
 * that swallows the clicks. Measured at 3: the button was visible but not
 * clickable, while the keyboard still worked, because key events do not go
 * through hit testing. Anything above 220 fixes it. */
.video-bg-toggle {
	position: absolute;
	right: clamp(12px, 3vw, 32px);
	bottom: clamp(12px, 3vw, 32px);
	z-index: 300;
	display: inline-flex;
	align-items: center;
	justify-content: center;
	width: 44px;
	height: 44px;
	padding: 0;
	border: 1px solid #ffffff;
	border-radius: 50%;
	background: #002e44;
	color: #ffffff;
	cursor: pointer;
}

.video-bg-toggle svg {
	width: 20px;
	height: 20px;
	fill: currentColor;
}

.video-bg-toggle:hover {
	background: #005077;
}

/* -----------------------------------------------------------------------------
 * Immobile cards - stretched link (WCAG 2.4.3 Focus Order, 2.4.4 Link Purpose)
 *
 * Every card used to carry TWO links to the same page: the featured image, which
 * had no accessible name at all because the alt is empty, and the title. Keyboard
 * and screen reader users went through each card twice, and the unnamed one was
 * what axe reported as `link-name` on home and archive.
 *
 * The image link is gone, switched off at the source: content block 81
 * `Immobile card`, `has_field_link` on the `wp:featured_image` dynamic-data block.
 * That is a DATABASE change and does not live in this repo.
 *
 * What is left is one real link on the title, stretched over the whole card by an
 * absolutely positioned ::after, so the click target stays the entire card while
 * the accessibility tree and the tab order see a single link.
 *
 * Selectors deliberately avoid the Greenshift container ids, which change if the
 * block is recreated: `.entries article.type-immobile` is Blocksy's own query
 * wrapper and matched all 8 cards when measured.
 * -------------------------------------------------------------------------- */

.entries article.type-immobile {
	position: relative;
}

/* Without this the overlay covers 410x138 instead of 410x446: `inset: 0` resolves
 * against the nearest POSITIONED ancestor, and the Greenshift containers inside
 * the card are `position: relative`, so the link stopped at the text block and
 * the image stayed dead to the click. Measured before touching them: the card has
 * no absolutely positioned descendant, so nothing depends on that `relative`.
 *
 * `!important` because Greenshift emits its own per-block rule as
 * `#gspb_container-id-gsbp-f637a35c-e967.gspb_container { position: relative }`,
 * an ID selector at 1-1-0 that outranks this 0-3-1 one. Matching it on equal
 * terms would mean hardcoding block ids that change whenever the block is
 * recreated, which is the failure mode already documented for `uniqueId`. */
.entries article.type-immobile .gspb_container {
	position: static !important;
}

.entries article.type-immobile h2.ct-dynamic-data > a::after {
	content: "";
	position: absolute;
	inset: 0;
}

/* The overlay sits on top of the image, so the media wrapper never gets `:hover`
 * any more and Blocksy's own zoom-in effect stopped firing. Measured: with the
 * pointer over the image, `.ct-dynamic-media-inner:hover` is false while the
 * card's `:hover` is true. So the same effect is triggered from the card instead.
 * The image already carries `transition: transform 0.5s` from Blocksy, which is
 * what animates it, and which the reduced-motion block at the end zeroes out. */
.entries article.type-immobile:hover .ct-dynamic-media-inner img {
	transform: scale(1.1);
}

/* The focus ring moves from the title text to the card, which is the real target.
 * The indicator is not removed, it is enlarged: same two bands as a11y #1, so it
 * keeps working on both the light and the dark sections. The `!important` on the
 * anchor is needed to beat that same rule, which is itself !important. */
.entries article.type-immobile:focus-within {
	outline: 2px solid #ffffff;
	outline-offset: 0;
	box-shadow: 0 0 0 4px #002e44;
	border-radius: 2px;
}

.entries article.type-immobile h2.ct-dynamic-data > a:focus-visible {
	outline: none !important;
	box-shadow: none !important;
}

/* -----------------------------------------------------------------------------
 * Reduced motion (WCAG 2.3.3 Animation from Interactions, AAA)
 *
 * Blocksy's `whenTransitionEnds` helper reads the computed duration and calls
 * its callback straight away when it is 0, so zeroing it here is safe for the
 * theme. If a Greenshift slider or accordion ever hangs with this on, the reason
 * is `transitionend` never firing, and the fix is `0.01ms` instead of `0s`.
 * -------------------------------------------------------------------------- */

@media (prefers-reduced-motion: reduce) {
	*,
	*::before,
	*::after {
		transition-duration: 0s !important;
		transition-delay: 0s !important;
	}
}
