/**
 * Sticky call bar (Task 12).
 *
 * Ships its own minimal CSS so the bar renders correctly even on a page
 * where the theme is not active. Ported from the live bar
 * (design/reference/hvac-mold-treatment-50-per-vent.html, #bx-bar) with two
 * fixes a prior review found (DEPLOY-RUNBOOK.md, "PATCH A" and the 360px
 * wrap note):
 *
 *   1. body's padding-bottom now accounts for env(safe-area-inset-bottom),
 *      so the bar never overlaps page content on an iPhone with a home
 *      indicator.
 *   2. The Call label is shortened ("Call 843-282-7777", set in PHP) so it
 *      never wraps onto two lines at a 360px viewport. The 2026-09-03
 *      redesign set the buttons in Archivo at 78% width, 15px, 700, in
 *      place of 12px Libre Franklin. That is a larger size in a narrower
 *      face, and white-space: nowrap is still on the button, so a wrap
 *      cannot happen; what has NOT been re-measured is whether the two
 *      buttons still fit side by side at 360px without overflowing the
 *      bar. Measure on the rendered dev host before the cutover.
 *
 * REDESIGN, 2026-09-03 (Task 2): square corners, no shadow, sentence case, no
 * letter spacing. Primary is the red fill, secondary is an ink outline on
 * white, the dismiss control is a square. The theme's section 8 carries the
 * same values for the ported .bx-bar markup and loads after this file.
 *
 * REVIEW ROUND 1: the padding-bottom above used to be a bare `body{}` rule
 * gated only by the max-width media query, which left a permanent blank gap
 * once a visitor dismissed the bar (the media query alone can never know
 * about a dismissal). It is now scoped to `body.bx-bar-visible`, a class
 * callbar.js owns: added the moment the bar is shown, removed the moment it
 * is hidden or dismissed, and never added at all when a prior dismissal is
 * still remembered in localStorage. The invariant is: bar visible implies
 * padding, bar dismissed or hidden implies no padding. BX_Callbar::html()
 * also renders a tiny #bx-bar-pad <style> fallback carrying the same rule
 * unconditionally (a class cannot be added to <body> from wp_footer, which
 * runs after the tag is already sent), for the case JavaScript never runs at
 * all; callbar.js deletes that element the instant it does run, so the two
 * mechanisms never fight each other.
 *
 * No em dashes anywhere (house style).
 */

#bx-bar {
	position: fixed;
	left: 0;
	right: 0;
	bottom: 0;
	z-index: 99998;
	display: none;
	align-items: stretch;
	gap: 10px;
	box-sizing: border-box;
	padding: 10px 12px calc(10px + env(safe-area-inset-bottom, 0px));
	background: #ffffff;
	border-top: 1px solid #d9dcdf;
}

/* `screen and`, not a bare width query. A print sheet has a width too, and a
   narrow one matches `(max-width: 980px)` on its own: that is how the bar and
   its body padding reached paper. Naming the medium is the fix at the source;
   the @media print block at the foot of this file is the backstop. */
@media screen and (max-width: 980px) {
	#bx-bar {
		display: flex;
	}

	/* Only while the bar is actually on screen (see the review-round-1 note
	   in the file header). Toggled by callbar.js; see #bx-bar-pad for the
	   no-JS fallback that carries the same rule unconditionally. */
	body.bx-bar-visible {
		padding-bottom: calc(78px + env(safe-area-inset-bottom, 0px));
	}

	/* WCAG 2.2 SC 2.4.11 FOCUS NOT OBSCURED (MINIMUM), AA. This was failing
	   at every width where the bar renders, and it was measured, not guessed.
	   A Tab sweep comparing each focused element's rect against the bar's
	   found, before this rule:

	     360x800   4 partially obscured   3 ENTIRELY obscured
	     390x844   4 partially            2 ENTIRELY
	     768x800   7 partially            4 ENTIRELY
	     900x800   9 partially            5 ENTIRELY
	     980x800   7 partially            4 ENTIRELY
	     1024x800  no bar, 0 and 0

	   Entirely obscured at 900px included "How the $50-a-vent treatment works"
	   and "Book a treatment", which are the two most conversion-relevant links
	   on the page. The mechanism: Tab to a link near the foot of the viewport
	   and the browser scrolls it to the nearest edge, which is the bottom,
	   which is where a fixed z-index 99998 opaque bar is sitting. The element
	   is focused and correctly ringed, and it cannot be seen.

	   Not phone-only. The bar renders at 980px and below, so this also caught
	   a windowed desktop browser and anyone at 150 or 200 percent zoom on a
	   1440px screen.

	   scroll-padding-bottom tells the scroller to stop short of the bar. It has
	   to go on the SCROLLING element, which is <html>, not on <body>, and it is
	   scoped by the same condition as the padding above so a dismissed bar does
	   not leave the reservation behind.

	   TWO SELECTORS, ON PURPOSE, AND THE FIRST IS THE REAL ONE. :has() is
	   already load bearing in this project's theme stylesheet (the site-logo
	   rule and the no-image hero fallback) and it covers Chrome 105+, Safari
	   15.4+ and Firefox 121+. That is a fine dependency for a visual nicety and
	   the wrong one for an AA criterion: on an older Firefox or Safari the rule
	   would simply not match, JavaScript would already have removed the inline
	   fallback below, and the failure would be silent. So callbar.js puts the
	   same class on <html> as well, and html.bx-bar-visible needs no :has() at
	   all. The :has() form stays as the second line, for anything that sets the
	   body class without going through that script.

	   #bx-bar-pad carries the declaration unconditionally for the case where
	   JavaScript never runs and neither class is ever added. */
	html.bx-bar-visible,
	html:has(body.bx-bar-visible) {
		scroll-padding-bottom: calc(78px + env(safe-area-inset-bottom, 0px));
	}
}

.bx-bar-btn {
	flex: 1 1 0;
	display: flex;
	align-items: center;
	justify-content: center;
	box-sizing: border-box;
	min-height: 44px;
	padding: 14px 10px;
	border: 2px solid #bb2b1e;
	border-radius: 0;
	font-family: 'Archivo', 'Arial Narrow', Arial, sans-serif;
	font-stretch: 78%;
	font-size: 15px;
	line-height: 18px;
	font-weight: 700;
	letter-spacing: 0;
	text-align: center;
	text-transform: none;
	text-decoration: none;
	white-space: nowrap;
}

/* !important on both: .bx-bar-btn is an <a>, and a theme's own a{color:...}
   rule (or Divi's, on the live site) outranks a plain class on specificity
   grounds in some cascades; these two must always win regardless of theme. */
.bx-bar-primary {
	background: #bb2b1e;
	border-color: #bb2b1e;
	color: #ffffff !important;
}

.bx-bar-secondary {
	background: #ffffff;
	border-color: #2e3439;
	color: #2e3439 !important;
}

/* REVIEW ROUND 1 raised this from 22x22 to 26x26, clearing WCAG 2.2 SC 2.5.8
   Target Size (Minimum), whose floor is 24px. REVIEW ROUND 2 (2026-09-02)
   takes it to 44.
   BE ACCURATE ABOUT WHAT WAS WRONG. At AA, 26x26 PASSED: an independent sweep
   computing SC 2.5.8 with its spacing and inline exceptions found zero
   failures across 46 targets on the home page and 60 on the offer page. 44px
   is SC 2.5.5 Target Size (Enhanced), which is AAA. So this change is a
   free improvement toward the size every other control in this bar already
   has, not the repair of a conformance failure. The actual defect on this
   control was PERMANENCE, not size, and it is fixed in callbar.js: the
   dismissal moved from localStorage to sessionStorage.
   Only the TARGET grows. The visible control stays 26px (a square since the
   2026-09-03 redesign, which has no radius anywhere), because a 44px white
   box floating over the page reads as a second button rather than a dismiss.
   The extra area is a transparent ::before laid over the button: a
   pseudo-element is part of its originating element for hit testing, so a
   press anywhere in that 44x44 box activates the button. Measured with
   getBoundingClientRect() on the pseudo box, not assumed.
   THE GEOMETRY, and the reason for each number. top:-26px seats the 26px
   square flush on the bar's top edge (it spans -26 to 0). The 44x44 target is
   centred on that square, so it spans -35 to +9. The bar's padding-top is
   10px, so the Call and Book buttons begin at +10: the target ends one pixel
   short of them and no two targets overlap. The old -20px would have put a
   44px box 15px INTO the button row.
   It stays outside the two-button flex row on purpose, so it can never eat
   into the width the 360px no-wrap fix depends on. */
.bx-bar-dismiss {
	position: absolute;
	top: -26px;
	right: 6px;
	width: 26px;
	height: 26px;
	box-sizing: border-box;
	padding: 0;
	border: 1px solid #2e3439;
	border-radius: 0;
	background: #ffffff;
	color: #2e3439;
	font-size: 16px;
	line-height: 24px;
	text-align: center;
	cursor: pointer;
}

.bx-bar-dismiss::before {
	content: "";
	position: absolute;
	top: 50%;
	left: 50%;
	width: 44px;
	height: 44px;
	transform: translate(-50%, -50%);
}

/* The bar is a screen affordance. It was already listed in the theme's print
   block, but as `.bx-bar`, and this element is `id="bx-bar"` with no class of
   that name, so the rule never matched and the bar printed on every sheet
   (found 2026-09-02). It is fixed in both places: here, because this
   stylesheet has to work on a page where the theme is not active, and in the
   theme, whose own copy also covers the ported .bx-bar markup.
   The padding-bottom goes with it. Leaving it would print a blank strip at the
   foot of the last page for a bar that is no longer there. */
@media print {
	#bx-bar {
		display: none !important;
	}

	body.bx-bar-visible {
		padding-bottom: 0 !important;
	}
}
