/* Smokin' Bull — brand colors sampled directly from the client's logo photo
   (assets/logo/smokin-bull-logo-from-facebook.png) via pixel sampling, 2026-08-17.
   Mobile-first: base rules target 320px, min-width media queries layer up. */

:root {
  --sb-red: #C31E16;
  --sb-red-dark: #9E1712;
  --sb-black: #221F23;
  --sb-cream: #D3D5CF;
  --sb-brown: #9B6958;
  --sb-brown-text: #7A4A38; /* darkened brown for AA contrast on white as small text (~7.3:1) */
  --sb-red-on-dark: #EF5850; /* lightened red for AA contrast on --sb-black (~4.8:1); --sb-red itself is only 2.7:1 there */
  --sb-blue: #2A75CD; /* sampled from the trailer's real paint (assets/photos/food-truck-exterior-side-view.jpg + food-truck-logo-panel.jpg), 2026-08-28 — deliberately not the lighter logo-photo blue, which is a photo of a printed sign under different lighting */
}

/* overflow-anchor does NOT inherit, so it has to sit on the universal
   selector, not just html/.sb-header — setting it only on the header
   stops the header ITSELF from being picked as the browser's scroll
   anchor, but the browser was still free to anchor to some OTHER element
   (e.g. the hero content right below it, which defaults to
   overflow-anchor:auto), and when the sticky header resizes on scroll,
   that anchor's position shifts too, re-triggering the same
   compensating-scroll feedback loop through a different element. This
   site relies on scroll-position-driven size/opacity changes (header
   shrink, .reveal fade-ins) throughout, so anchoring is more likely to
   misfire than help here — opting every element out closes that gap. */
* { box-sizing: border-box; margin: 0; padding: 0; overflow-anchor: none; }

html { -webkit-text-size-adjust: 100%; height: 100%; }

/* Sticky footer: on short pages (404, Privacy, Terms) the footer would
   otherwise end wherever the content stops, leaving a dead white gap below
   it on any viewport taller than the page. min-height:100vh + flex column
   keeps the footer pinned to the bottom of the viewport on short pages,
   while pushing it below the fold as usual once real content is taller. */
body {
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
  color: var(--sb-black);
  background: #ffffff;
  line-height: 1.5;
  font-size: 16px;
  min-height: 100vh;
  display: flex;
  flex-direction: column;
}
main { flex: 1 0 auto; }

.sb-container {
  max-width: 1100px;
  margin: 0 auto;
  padding: 0 16px;
}

a { color: inherit; text-decoration: none; }
button { font: inherit; }

img, .sb-img { max-width: 100%; }

/* Skip link — invisible until keyboard-focused, then jumps on-screen above
   everything else so keyboard/screen-reader users don't have to tab through
   the full header nav on every single page. */
.sb-skip-link {
  position: absolute;
  top: -100px;
  left: 8px;
  z-index: 1000;
  background: #1a1a1a;
  color: #fff;
  padding: 10px 16px;
  border-radius: 4px;
  font-weight: 600;
  font-size: 0.9rem;
  transition: top 0.15s ease;
}
.sb-skip-link:focus {
  top: 8px;
}

/* ---------- Header ---------- */
/* Sticky + starts larger, shrinks once the page scrolls (.sb-header-scrolled
   toggled by js/nav.js). Needs an opaque background since content now
   scrolls underneath it instead of pushing it away. */
.sb-header {
  border-bottom: 3px solid var(--sb-red);
  position: sticky;
  top: 0;
  z-index: 100;
  background: var(--sb-blue);
  color: #fff;
  box-shadow: none;
  transition: box-shadow 0.25s ease;
  /* This header's own height changes on scroll (padding/logo transition
     below) — without this, the browser's scroll anchoring "helpfully"
     compensates for that resize by nudging scrollY, which retriggers the
     resize near the threshold and flickers. See nav.js for the other half. */
  overflow-anchor: none;
}
.sb-header.sb-header-scrolled {
  box-shadow: 0 2px 10px rgba(0, 0, 0, 0.08);
}
/* Phone was tried in its own utility bar above the main nav first, to get
   it out of an overloaded main row (Gallery/About/Contact + phone + the
   CTA button all competing for space). Dropping "Contact" from the nav
   (its own page duplicates Request a Quote — same destination) freed up
   enough room to bring it back into the single main row instead, so the
   extra row/height isn't needed any more. See .sb-header-phone below. */
.sb-header-bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 12px;
  padding: 22px 24px;
  transition: padding 0.25s ease;
}
.sb-header-scrolled .sb-header-bar {
  padding: 10px 24px;
}
@media (min-width: 752px) {
  .sb-header-bar { padding-left: 16px; padding-right: 16px; }
}
.sb-logo-slot {
  display: inline-flex;
  align-items: center;
}
.sb-logo-img {
  display: block;
  height: 104px;
  width: auto;
  border-radius: 6px;
  transition: height 0.25s ease, filter 0.25s ease;
  /* The wordmark's "SMOKIN'" is solid black fill with only a thin white
     outline stroke — reads fine against a busy background but the black
     fill vanishes into flat black here, leaving just that thin stroke.
     This glow thickens the stroke itself rather than editing the source
     pixels. Sized for the full 78px logo — the scrolled 68px state below
     uses a smaller radius, since a fixed-pixel blur doesn't scale down
     with the element and turned into a soft smudge at the smaller size. */
  filter: drop-shadow(0 0 1.5px rgba(255, 255, 255, 0.9)) drop-shadow(0 0 3px rgba(255, 255, 255, 0.5));
}
.sb-header-scrolled .sb-logo-img {
  height: 88px;
  filter: drop-shadow(0 0 1px rgba(255, 255, 255, 0.9)) drop-shadow(0 0 2px rgba(255, 255, 255, 0.5));
}

/* hamburger button — visible by default (mobile), hidden at desktop breakpoint */
.sb-nav-toggle {
  display: flex;
  flex-direction: column;
  justify-content: center;
  gap: 4px;
  width: 44px;
  height: 44px;
  background: none;
  border: 1px solid rgba(255, 255, 255, 0.35);
  border-radius: 4px;
  cursor: pointer;
  padding: 0 8px;
}
.sb-nav-toggle span {
  display: block;
  height: 2px;
  background: #f0f0f0;
  border-radius: 1px;
  transition: transform 0.2s ease, opacity 0.2s ease;
}
.sb-nav-toggle[aria-expanded="true"] span:nth-child(1) { transform: translateY(6px) rotate(45deg); }
.sb-nav-toggle[aria-expanded="true"] span:nth-child(2) { opacity: 0; }
.sb-nav-toggle[aria-expanded="true"] span:nth-child(3) { transform: translateY(-6px) rotate(-45deg); }

/* collapsible panel — closed by default on mobile.
   flex-basis:100% forces it onto its own full-width row below the
   logo/hamburger row, instead of being squeezed into the same flex row. */
.sb-header-collapse {
  display: none;
  flex-direction: column;
  flex-basis: 100%;
  width: 100%;
  gap: 16px;
  padding: 8px 0 20px;
  border-top: 1px solid rgba(255, 255, 255, 0.15);
}
.sb-header-collapse.sb-nav-open { display: flex; }

.sb-nav {
  display: flex;
  flex-direction: column;
  gap: 4px;
  font-size: 1.1rem;
  font-weight: 600;
}
.sb-nav a {
  padding: 10px 4px;
  border-bottom: 1px solid rgba(255, 255, 255, 0.15);
}
.sb-nav a.active { color: #fff; text-decoration: underline; } /* red-on-dark (was ~4.8:1 on black) drops to ~1.4:1 on the new blue header — white clears AA here instead */
.sb-nav a.sb-inert { color: #aaa; cursor: default; }
.sb-nav a:not(.active, .sb-inert):hover { color: #fff; }

.sb-header-right {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 12px;
  font-size: 0.9rem;
}
.sb-header-right a:not(.sb-btn) {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: 44px;
  padding: 8px 16px;
  font-size: 1rem;
  font-weight: 600;
}
.sb-btn {
  display: inline-block;
  background: var(--sb-red);
  color: #fff;
  padding: 14px 28px;
  font-weight: 700;
  font-size: 0.85rem;
  text-transform: uppercase;
  border-radius: 4px;
  text-align: center;
  border: none;
  cursor: pointer;
  font-family: inherit;
  letter-spacing: 0.06em;
}
.sb-btn { transition: background 0.2s ease, transform 0.2s ease, box-shadow 0.2s ease; }
.sb-btn:hover { background: var(--sb-red-dark); transform: translateY(-2px); box-shadow: 0 8px 16px rgba(0, 0, 0, 0.2); }
.sb-btn-light { background: #fff; color: var(--sb-black); }
.sb-btn-light:hover { background: var(--sb-cream); }

/* Desktop centered-logo header — hidden on mobile, replaces the hamburger version entirely at 768px+ */
.sb-header-desktop { display: none; }

.sb-nav-side {
  display: flex;
  gap: 28px;
  font-size: 1.05rem;
  font-weight: 600;
  white-space: nowrap;
}
/* :not(.sb-btn) on purpose — the CTA button lives inside this same
   .sb-nav-side wrapper, and without the exclusion this descendant
   selector (specificity: class+element) silently beat .sb-btn's own
   padding (specificity: class only), collapsing the button down to a
   4px/2px outline instead of its real size. */
.sb-nav-side a:not(.sb-btn) { padding: 4px 2px; border-bottom: 2px solid transparent; transition: color 0.15s ease, border-color 0.15s ease; }
.sb-nav-side a.active { border-bottom-color: #fff; color: #fff; } /* same contrast fix as .sb-nav a.active above */
.sb-nav-side a.sb-inert { color: #aaa; cursor: default; }
.sb-nav-side a:not(.active, .sb-inert, .sb-btn):hover { color: #fff; border-bottom-color: rgba(255, 255, 255, 0.35); }

@media (min-width: 984px) {
  .sb-logo-mobile,
  .sb-nav-toggle,
  .sb-header-collapse {
    display: none !important;
  }

  /* Logo left, phone/Request a Quote anchored far right — the standard,
     battle-tested header convention (logo top-left, CTA far right).
     Nav is its OWN flex child here (not grouped with the logo) so that
     with exactly 3 children and justify-content:space-between, it lands
     centered in the space between logo and the CTA group, rather than
     hugging the logo — with a wide header and a short nav list, hugging
     the logo left one big lopsided void on the right instead of two
     balanced gaps. */
  .sb-header-desktop {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 32px;
    width: 100%;
  }
  .sb-header-cta-group {
    display: flex;
    align-items: center;
    gap: 20px;
    flex-shrink: 0;
  }
  /* Plain text, not a matching red box — tried as a second solid-red
     button first, but two identical red boxes side by side read as
     redundant/too much red rather than "here's a second way to reach
     us." Muted so Request a Quote stays the one clear visual anchor. */
  .sb-header-phone {
    font-size: 0.92rem;
    font-weight: 600;
    color: #fff;
    white-space: nowrap;
    transition: color 0.15s ease;
  }
  .sb-header-phone:hover { text-decoration: underline; }
}

/* ---------- Sections ---------- */
.sb-section {
  padding: 32px 0;
  border-bottom: 1px solid #eee;
}
/* No divider right before a section with its own diagonal-cut top edge
   (CTA banner, Why Us panel) — a flat grey line floating just above the
   angled shape reads as a stray leftover line, not a deliberate pairing. */
.sb-section:has(+ .sb-cta-banner),
.sb-section:has(+ .sb-why-section) { border-bottom: none; }
.sb-section h1 { font-size: 1.6rem; }
.sb-section h2 { font-size: 1.3rem; }
.sb-section h3 { font-size: 1.05rem; }
.sb-section h1, .sb-section h2, .sb-section h3 {
  margin-bottom: 10px;
  line-height: 1.25;
}
.sb-eyebrow {
  text-transform: uppercase;
  letter-spacing: 0.08em;
  font-size: 0.75rem;
  font-weight: 700;
  color: var(--sb-brown-text); /* AA-safe darkened brand brown, ~7.3:1 on white */
  margin-bottom: 8px;
}
.sb-placeholder-text {
  color: #555;
  font-size: 1rem;
  max-width: 640px;
}

@media (min-width: 752px) {
  .sb-section { padding: 48px 0; }
  .sb-section h1 { font-size: 2.1rem; }
  .sb-section h2 { font-size: 1.6rem; }
  .sb-section h3 { font-size: 1.1rem; }
}

/* ---------- Image placeholders ---------- */
/* Framed placeholder — real photos drop in later without needing this
   treatment removed; the brown "wood frame" border ties to the wood-fired
   theme and reads as an intentional design element, not a missing image. */
.sb-img {
  background:
    repeating-linear-gradient(135deg, #e7e4dc, #e7e4dc 3px, #dedad0 3px, #dedad0 6px);
  color: var(--sb-black);
  display: flex;
  align-items: center;
  justify-content: center;
  text-align: center;
  font-size: 0.75rem;
  font-weight: 600;
  letter-spacing: 0.02em;
  padding: 10px;
  border-radius: 6px;
  width: 100%;
  border: 5px solid var(--sb-brown);
  box-shadow: inset 0 0 0 2px #fff, inset 0 0 0 3px var(--sb-brown);
  overflow: hidden;
}
.sb-img img { width: 100%; height: 100%; object-fit: cover; border-radius: 2px; }
.sb-img.landscape { aspect-ratio: 16 / 9; }
/* Dedicated hero ratio for the Menu/Catering/Gallery page-top photos — kept
   separate from .landscape (also used on About, untouched here) so this can
   be tuned independently. 16:9 fixed the original crop problems (faces,
   trailer, tent all getting cut off) but ran ~600px tall on desktop, pushing
   real page content below the fold. 2:1 keeps enough vertical room to avoid
   those crops while taking noticeably less height. */
.sb-img.sb-page-hero { aspect-ratio: 2 / 1; }
.sb-img.square { aspect-ratio: 1 / 1; }
.sb-img.portrait { aspect-ratio: 3 / 4; max-width: 320px; margin: 0 auto; }
.sb-img.wide-banner { aspect-ratio: 4 / 3; }

@media (min-width: 600px) {
  .sb-img.wide-banner { aspect-ratio: 16 / 7; }
}
@media (min-width: 752px) {
  .sb-img.wide-banner { aspect-ratio: 21 / 6; }
  .sb-img { font-size: 0.8rem; }
}

/* ---------- Scroll-reveal (js/reveal.js toggles .is-visible via IntersectionObserver) ---------- */
.reveal {
  opacity: 0;
  transform: translateY(24px);
  transition: opacity 0.6s ease, transform 0.6s ease;
}
.reveal.is-visible { opacity: 1; transform: none; }
.reveal-delay-1 { transition-delay: 0.12s; }
.reveal-delay-2 { transition-delay: 0.24s; }
.reveal-delay-3 { transition-delay: 0.36s; }
@media (prefers-reduced-motion: reduce) {
  .reveal { transition: none; opacity: 1; transform: none; }
}

/* ---------- Hero (full-bleed photo/video + gradient scrim) ----------
   Replaces an earlier diagonal-split prototype (dark panel + video,
   hard-edged corner-to-corner cut). That looked bold but fighting it was
   real: clip-path geometry has to be re-solved by hand for every
   breakpoint (a percentage-based cut safe on a wide monitor put text
   directly on the video on an ordinary laptop; fixed-pixel cuts needed a
   real measured-content safety check across 320-2560px to trust). A
   gradient scrim sidesteps all of that — it's not a hard shape, so there
   is no boundary to keep clear of text at every screen size, and once
   real video exists here it reads as MORE immersive than the split ever
   did, since the whole hero is the footage, not a wedge of it. This is
   also the dominant real-world pattern for this kind of site (checked
   against current restaurant/catering/wedding-vendor hero design
   practice, not just improvised). */
.sb-hero-full {
  position: relative;
  min-height: 380px;
  overflow: hidden;
  background: var(--sb-black);
  /* True vertical centering via flex, not approximated with padding —
     the old padding-only approach left content sitting near the top with
     a large dead zone below it once the section grew taller at wider
     breakpoints (measured: 248px of empty space below the button at
     1200px+). */
  display: flex;
  align-items: center;
}
.sb-hero-photo {
  position: absolute;
  inset: 0;
  overflow: hidden;
}
.sb-hero-photo img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  object-position: 60% 0px;
  display: block;
}
.sb-hero-full-scrim {
  position: absolute;
  inset: 0;
  /* Darkest under the text (left), fading to clear by ~85% across so the
     photo/video reads clean on the right — #221F23 (--sb-black) as rgba,
     since custom properties can't carry an alpha channel into rgba()
     directly without newer relative-color syntax this project doesn't
     rely on elsewhere. */
  background: linear-gradient(90deg,
    rgba(34, 31, 35, 0.93) 0%,
    rgba(34, 31, 35, 0.85) 32%,
    rgba(34, 31, 35, 0.5) 60%,
    rgba(34, 31, 35, 0.05) 88%);
}
.sb-hero-full-content {
  position: relative;
  z-index: 2;
  padding: 40px 16px;
  width: 100%;
}
/* Sizes bumped from the browser-default 32px/16px — genuinely small for
   a hero headline against typical hospitality/catering-site practice,
   where a desktop hero H1 usually runs 48-64px+. Scales up by breakpoint
   rather than one fixed size, same as the rest of this file. */
.sb-hero-full-content h1 { color: #fff; margin: 4px 0 16px; max-width: 700px; font-size: 1.9rem; line-height: 1.15; text-shadow: 0 2px 10px rgba(0, 0, 0, 0.55); }
.sb-hero-full-content p { margin-bottom: 24px; max-width: 480px; color: #e2e2e2; font-size: 1.05rem; line-height: 1.6; text-shadow: 0 1px 6px rgba(0, 0, 0, 0.55); }
.sb-eyebrow-mobile-break { display: none; }
/* 320-359px only: at this narrowest width the crop is zoomed in tighter than
   375px+, so the base 60% X-position crowds the sign against the eyebrow
   text with no breathing room. Shifted left of the base rule so the sign
   sits with a bit more clearance at this size specifically. */
@media (max-width: 359px) {
  .sb-hero-photo img { object-position: 50% 0px; }
}
/* 414-480px: eyebrow text fits on one line here but Kevin wants "Low Country, SC"
   broken onto its own line same as it naturally does at 320/375 — 600px+ stays
   on one line as-is. Also shifts the hero photo left so the blue sign behind
   the grill is visible at this range too, matching the 320/375 adjustment. */
@media (min-width: 400px) and (max-width: 559px) {
  .sb-eyebrow-mobile-break { display: block; }
  .sb-hero-photo img { object-position: 60% 0px; }
}
/* 560-751px (tablet/mobile-landscape, still the full-bleed treatment): kept
   separate from the 752px+ desktop rule below so tuning this range doesn't
   also drag the desktop right-panel framing along with it. */
@media (min-width: 560px) and (max-width: 751px) {
  .sb-hero-photo img { object-position: 92% 0px; }
}
@media (min-width: 752px) {
  .sb-hero-photo img { object-position: 58% 0px; }
  .sb-hero-full { min-height: 620px; }
  .sb-hero-full-content { padding: 48px 16px; }
  .sb-hero-full-content h1 { font-size: 3rem; }
  .sb-hero-full-content p { font-size: 1.15rem; }
  /* Desktop+: photo pulls into a right-hand panel instead of running full-bleed,
     with its own blended left edge — the full-width scrim is only needed for the
     mobile/tablet full-bleed treatment above. */
  .sb-hero-photo { inset: auto; top: 0; right: 0; bottom: 0; width: 78%; }
  .sb-hero-photo::before {
    content: "";
    position: absolute;
    inset: 0;
    right: auto;
    width: calc(65% - 100px);
    background: linear-gradient(to right, var(--sb-black) 0%, var(--sb-black) 15%, rgba(34, 31, 35, 0.45) 50%, rgba(34, 31, 35, 0.15) 80%, rgba(34, 31, 35, 0) 100%);
    z-index: 1;
  }
  /* Flat tint across the whole photo (on top of the seam blend above) so
     white text stays readable wherever it overlaps the photo, not just
     near the seam. Adjust the opacity to taste. */
  .sb-hero-photo::after {
    content: "";
    position: absolute;
    inset: 0;
    height: auto;
    background: rgba(34, 31, 35, 0.14);
    z-index: 1;
  }
  .sb-hero-full-scrim { display: none; }
}
/* 752-1183px only (iPad portrait/landscape tier): narrower solid-black lead-in
   than the 1184px+ tier above — halves it at both 768 and 1024 (measured
   42px->21px and 62px->31px) by halving the stop percentage rather than
   hardcoding a px value, so it stays proportional across the whole range. */
@media (min-width: 752px) and (max-width: 1183px) {
  .sb-hero-photo::before {
    width: calc(65% - 60px);
    background: linear-gradient(to right, var(--sb-black) 0%, var(--sb-black) 7.5%, rgba(34, 31, 35, 0.55) 50%, rgba(34, 31, 35, 0.2) 80%, rgba(34, 31, 35, 0) 100%);
  }
  /* Bumped from the shared 0.14 (752px+) — pixel-measured contrast on the
     headline dropped to 2.77:1 (below the 3:1 large-text minimum) right in
     this range, where text crosses a lighter part of the new hero photo.
     768px and 1184px+ already passed fine, so this stays scoped here rather
     than darkening the whole desktop range. */
  .sb-hero-photo::after {
    background: rgba(34, 31, 35, 0.45);
  }
}
@media (min-width: 1184px) {
  .sb-hero-full { min-height: 760px; }
  .sb-hero-full-content h1 { font-size: 3.75rem; }
  .sb-hero-full-content p { font-size: 1.25rem; }
}

/* ---------- Staggered service cards (zigzag, not a flat row) ---------- */
.sb-stagger-grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: 20px;
  margin-top: 20px;
}
.sb-stagger-card {
  transition: transform 0.25s ease, box-shadow 0.25s ease;
}
.sb-stagger-card h3 { margin-top: 12px; }
.sb-stagger-card:hover { transform: translateY(-6px); }
.sb-stagger-card:hover .sb-img { box-shadow: inset 0 0 0 2px #fff, inset 0 0 0 3px var(--sb-brown), 0 14px 26px rgba(0, 0, 0, 0.16); }
@media (min-width: 752px) {
  .sb-stagger-grid { grid-template-columns: repeat(3, 1fr); gap: 24px; }
  .sb-stagger-card:nth-child(2) { margin-top: 36px; }
  .sb-stagger-card:nth-child(3) { margin-top: 12px; }
}

/* ---------- Why Us — dark diagonal panel, breaks the light/light/light rhythm ---------- */
.sb-why-section {
  position: relative;
  overflow: hidden;
  /* Extra mobile padding (vs. the 64px desktop tier below) — the diagonal
     clip-path on .sb-why-bg cuts in 6% of the section's own height at the
     top-left/bottom-right corners, and on short mobile sections that put
     the angled edge uncomfortably close to the text/image content. More
     vertical padding gives the angle room to cut without crowding anything. */
  padding: 60px 0;
}
.sb-why-bg {
  position: absolute;
  inset: -1px;
  background: var(--sb-black);
  clip-path: polygon(0 6%, 100% 0, 100% 94%, 0 100%);
  z-index: 0;
}
.sb-why-section .sb-container { position: relative; z-index: 1; }
.sb-eyebrow-dark { color: #F0B896; }
/* Why Us lives outside .sb-section, so it never got the section-heading
   size bump that every other section title gets from `.sb-section h2` —
   it was stuck at the small 12px kicker size instead of matching the rest
   of the page's section titles (1.3rem / 1.6rem). */
.sb-why-section h2 { font-size: 1.3rem; margin-bottom: 10px; }
.sb-why-section .sb-list-plain-dark li { color: #e6e6e6; }
.sb-why-section .sb-list-plain-dark li::before { color: var(--sb-red-on-dark); content: "\2022"; font-size: 1.1em; }
.sb-why-img { transform: rotate(1.4deg); }
@media (min-width: 752px) {
  .sb-why-section { padding: 64px 0; }
  .sb-why-section h2 { font-size: 1.6rem; }
  .sb-why-img { margin-top: -20px; }
}

/* ---------- Featured menu cards (signature item stands out) ---------- */
.sb-menu-card { position: relative; transition: transform 0.25s ease; }
.sb-menu-card:hover { transform: translateY(-6px); }
.sb-menu-card:hover .sb-img { box-shadow: inset 0 0 0 2px #fff, inset 0 0 0 3px var(--sb-brown), 0 14px 26px rgba(0, 0, 0, 0.16); }
.sb-menu-card.is-signature .sb-img { border-color: var(--sb-red); }
.sb-menu-ribbon {
  position: absolute;
  top: -10px;
  right: 8px;
  z-index: 2;
  background: var(--sb-red);
  color: #fff;
  font-size: 0.7rem;
  font-weight: 700;
  letter-spacing: 0.03em;
  padding: 4px 10px;
  border-radius: 999px;
  box-shadow: 0 4px 10px rgba(0, 0, 0, 0.2);
}

/* ---------- Bento gallery (one large + a stacked column, not a uniform grid) ---------- */
.sb-bento {
  display: flex;
  flex-direction: column;
  gap: 12px;
  margin-top: 16px;
}
.sb-bento-side { display: flex; flex-direction: column; gap: 12px; }
.sb-img.sb-bento-large { aspect-ratio: 4 / 3; }
.sb-img.sb-bento-small { aspect-ratio: 16 / 9; }
@media (min-width: 752px) {
  .sb-bento { flex-direction: row; align-items: stretch; }
  .sb-bento > .sb-img.sb-bento-large { flex: 2 1 0; }
  .sb-bento-side { flex: 1 1 0; justify-content: space-between; }
  .sb-img.sb-bento-large { aspect-ratio: auto; height: 100%; }
  .sb-img.sb-bento-small { aspect-ratio: auto; flex: 1 1 0; }
}

/* ---------- Timeline (connected steps, not three identical boxes) ---------- */
.sb-timeline {
  position: relative;
  display: grid;
  grid-template-columns: 1fr;
  gap: 28px;
  margin-top: 24px;
}
.sb-timeline-step { text-align: center; }
.sb-timeline-step .sb-step-num {
  width: 40px;
  height: 40px;
  font-size: 1.05rem;
  box-shadow: 0 0 0 6px #fff;
  position: relative;
  z-index: 1;
}
.sb-timeline-step p { font-size: 0.92rem; color: #444; max-width: 260px; margin: 0 auto; }
@media (min-width: 752px) {
  .sb-timeline { grid-template-columns: repeat(3, 1fr); }
  .sb-timeline::before {
    content: "";
    position: absolute;
    top: 20px;
    left: 16.5%;
    right: 16.5%;
    height: 2px;
    background: var(--sb-cream);
  }
}

/* ---------- Process steps (How It Works — card + colored badge, connecting line on desktop) ---------- */
.sb-process-grid {
  position: relative;
  display: grid;
  grid-template-columns: 1fr;
  gap: 20px;
  margin-top: 24px;
}
.sb-process-card {
  border: 2px solid var(--sb-cream);
  border-top: 4px solid var(--sb-brown);
  border-radius: 8px;
  padding: 24px 20px;
  text-align: center;
  background: #fff;
  transition: transform 0.25s ease, box-shadow 0.25s ease;
}
.sb-process-card.sb-accent-brown { border-top-color: var(--sb-brown); }
.sb-process-card.sb-accent-red { border-top-color: var(--sb-red); }
.sb-process-card.sb-accent-black { border-top-color: var(--sb-black); }
.sb-process-card:hover { transform: translateY(-6px); box-shadow: 0 14px 26px rgba(0, 0, 0, 0.1); }
.sb-process-num {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 52px;
  height: 52px;
  border-radius: 50%;
  color: #fff;
  font-size: 1.3rem;
  font-weight: 700;
  margin-bottom: 14px;
}
.sb-process-num.sb-accent-brown { background: var(--sb-brown); }
.sb-process-num.sb-accent-red { background: var(--sb-red); }
.sb-process-num.sb-accent-black { background: var(--sb-black); }
.sb-process-card p { margin-top: 4px; }
@media (min-width: 752px) {
  .sb-process-grid { grid-template-columns: repeat(3, 1fr); gap: 24px; }
  .sb-process-grid::before {
    content: "";
    position: absolute;
    top: 50px;
    left: 16.5%;
    right: 16.5%;
    height: 2px;
    background: var(--sb-cream);
    z-index: -1;
  }
}

/* ---------- Food truck location callout (secondary — casual tone, not competing with the catering CTAs) ---------- */
.sb-truck-cta {
  margin-top: 32px;
  display: flex;
  flex-direction: column;
  gap: 16px;
  align-items: center;
  text-align: center;
  background: var(--sb-cream);
  border-radius: 10px;
  padding: 24px 20px;
}
/* Matches the brown/red top-border accent used on the testimonial cards
   right above it, so this reads as part of the same section instead of an
   unrelated box that showed up underneath. */
.sb-truck-cta-accent { border-top: 4px solid var(--sb-black); }
.sb-truck-cta-icon { height: 72px; width: auto; flex-shrink: 0; }
.sb-truck-cta-accent .sb-truck-cta-icon { height: 140px; }
.sb-truck-cta-text { display: flex; flex-direction: column; gap: 4px; }
.sb-truck-cta-text strong { font-size: 1rem; }
.sb-truck-cta-text span { font-size: 0.88rem; color: #444; }
.sb-btn.sb-btn-outline {
  background: transparent;
  border: 2px solid var(--sb-black);
  color: var(--sb-black);
  flex-shrink: 0;
}
.sb-btn.sb-btn-outline:hover { background: var(--sb-black); color: #fff; }
.sb-truck-cta-content { display: flex; flex-direction: column; align-items: center; gap: 14px; }
@media (min-width: 752px) {
  .sb-truck-cta { flex-direction: row; justify-content: space-between; text-align: left; padding: 28px 32px; }
  /* Icon stays on the left with the text/button stacked beside it — narrower
     and a bit taller than the full-width strip, but not as tall as a fully
     stacked card, and narrower than the two testimonial cards combined so
     it reads as its own smaller card underneath them. */
  .sb-truck-cta-accent {
    flex-direction: row;
    align-items: center;
    text-align: left;
    max-width: 480px;
    margin-left: auto;
    margin-right: auto;
    padding: 28px 32px;
    gap: 20px;
  }
  .sb-truck-cta-accent .sb-truck-cta-content { align-items: flex-start; }
}

/* ---------- Testimonials (real reviews, quote-card style) ---------- */
.sb-testimonial-grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: 20px;
  margin-top: 20px;
}
.sb-testimonial-card {
  position: relative;
  display: flex;
  flex-direction: column;
  background: var(--sb-cream);
  border-top: 4px solid var(--sb-brown);
  border-radius: 10px;
  padding: 34px 26px 24px;
  overflow: hidden;
  transition: transform 0.25s ease, box-shadow 0.25s ease;
}
.sb-testimonial-card.sb-accent-brown { border-top-color: var(--sb-brown); }
.sb-testimonial-card.sb-accent-red { border-top-color: var(--sb-red); }
.sb-testimonial-card:hover { transform: translateY(-6px); box-shadow: 0 14px 26px rgba(0, 0, 0, 0.14); }
.sb-testimonial-mark {
  position: absolute;
  top: -3px;
  left: 16px;
  font-family: Georgia, 'Times New Roman', serif;
  font-size: 5.5rem;
  line-height: 1;
  color: rgba(155, 105, 88, 0.16);
  pointer-events: none;
  user-select: none;
}
.sb-testimonial-card.sb-accent-red .sb-testimonial-mark { color: rgba(195, 30, 22, 0.14); }
.sb-testimonial-quote {
  position: relative;
  flex: 1 0 auto;
  font-size: 1.05rem;
  font-style: italic;
  color: #333;
  margin-bottom: 16px;
  z-index: 1;
}
.sb-testimonial-author {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 0.85rem;
  font-weight: 700;
  color: var(--sb-black);
}
.sb-testimonial-source {
  font-weight: 500;
  color: var(--sb-brown-text);
}
.sb-testimonial-fb-icon { color: var(--sb-brown-text); flex-shrink: 0; }
@media (min-width: 752px) {
  .sb-testimonial-grid { grid-template-columns: repeat(2, 1fr); gap: 24px; }
}

/* ---------- Grid helpers (mobile-first: 1 col base) ---------- */
.sb-grid-3, .sb-grid-4, .sb-grid-2 {
  display: grid;
  grid-template-columns: 1fr;
  gap: 18px;
}
.sb-grid-2 { align-items: center; gap: 32px; }

.sb-about-hero-mascot { height: 150px; width: auto; margin: 16px auto 0; display: block; }
.sb-about-hero-text { text-align: center; }

.sb-pitmaster-mobile-break { display: none; }
@media (max-width: 375px) {
  .sb-pitmaster-comma { display: none; }
  .sb-pitmaster-mobile-break { display: block; }
}

@media (min-width: 480px) {
  .sb-grid-4 { grid-template-columns: repeat(2, 1fr); }
}
@media (min-width: 600px) {
  .sb-grid-3 { grid-template-columns: repeat(2, 1fr); }
}
@media (min-width: 752px) {
  .sb-grid-3 { grid-template-columns: repeat(3, 1fr); gap: 20px; }
  .sb-grid-4 { grid-template-columns: repeat(4, 1fr); gap: 16px; }
  .sb-grid-2 { grid-template-columns: 1fr 1fr; gap: 32px; }
}

/* Weddings section on Catering: the CTA button and quote are pulled out of
   the text column so they can be reordered independently. Below 901px
   (phones AND iPad-portrait/768) it's one stacked column, in this order:
   text, quote, photo, button — a 2-column split at iPad-portrait width left
   an awkward tall gap under the button because the photo+quote column ran
   much taller than the text+button column. True desktop (901px+) goes back
   to the photo | text side-by-side layout, quote and button stacked under
   the text in the right column, where there's enough width for it to
   balance visually. */
@media (max-width: 900px) {
  .sb-catering-wedding-grid { grid-template-columns: 1fr; }
  .sb-catering-wedding-grid > .sb-catering-wedding-text { order: 1; }
  .sb-catering-wedding-grid > .sb-catering-wedding-quote { order: 2; }
  .sb-catering-wedding-grid > .sb-catering-wedding-photo { order: 3; }
  .sb-catering-wedding-grid > .sb-catering-wedding-cta { order: 4; justify-self: center; }
}
@media (min-width: 901px) {
  .sb-catering-wedding-grid { grid-template-rows: auto auto auto; align-items: start; }
  .sb-catering-wedding-grid > .sb-catering-wedding-photo { grid-column: 1; grid-row: 1 / span 3; align-self: center; }
  .sb-catering-wedding-grid > .sb-catering-wedding-text { grid-column: 2; grid-row: 1; }
  .sb-catering-wedding-grid > .sb-catering-wedding-quote { grid-column: 2; grid-row: 2; }
  .sb-catering-wedding-grid > .sb-catering-wedding-cta { grid-column: 2; grid-row: 3; }
}

.sb-about-hero-story { margin-top: 48px; }
.sb-about-hero-story h2 { text-align: left; }
.sb-about-hero-lede { display: none; }

/* Mascot now lives nested inside .sb-about-hero-story (after the paragraph),
   so .sb-about-hero-grid only has 3 top-level children: photo, title text,
   story. It flows naturally under the story text at every breakpoint by
   virtue of DOM order — no per-breakpoint mascot placement needed anymore. */

/* About hero grid stays stacked through iPad-portrait width — 2 narrow
   344px columns at 768px looked cramped/imbalanced. Only goes side-by-side
   at landscape-tablet width and up, where there's room to breathe. */
@media (max-width: 1007px) {
  .sb-about-hero-grid { grid-template-columns: 1fr; }
  .sb-about-hero-grid > *:nth-child(1) { order: 2; }
  .sb-about-hero-grid > *:nth-child(2) { order: 1; }
  .sb-about-hero-grid > *:nth-child(3) { order: 3; }
}

/* iPad-landscape (1024) through desktop all share this one design now —
   Kevin's call after seeing a bespoke 1008-1183 layout rendered: just reuse
   the already-proven 1184px+ treatment instead ("make it look like the
   1440"). The 300+380+56=736px content width fits comfortably inside a
   1024px viewport with room to spare, so no separate narrower variant is
   needed. "About Smokin' Bull" sits as a kicker above everything; left
   column is photo → "Meet Travers" → lede, stacked; right column is "The
   Story" text with the mascot flowing right after the paragraph (its own
   small photo is dropped at this width — one photo is enough once the
   mascot's already following the text). Unwraps .sb-about-hero-text via
   display:contents so its eyebrow/h1/lede can each get independent grid
   placement without touching the DOM or any other breakpoint. */
@media (min-width: 1008px) {
  .sb-about-hero-grid {
    max-width: 1000px;
    margin: 0 auto;
    grid-template-columns: 300px 380px;
    justify-content: center;
    column-gap: 56px;
    align-items: start;
  }
  .sb-about-hero-grid .sb-img.portrait { max-width: 300px; margin: 0; }
  .sb-about-hero-text { display: contents; }
  .sb-about-hero-text > .sb-eyebrow {
    grid-column: 1 / -1;
    grid-row: 1;
    text-align: center;
    margin-bottom: 24px;
  }
  .sb-about-hero-grid > *:nth-child(1) { grid-column: 1; grid-row: 2; }
  .sb-about-hero-grid > *:nth-child(3) {
    grid-column: 2;
    grid-row: 2;
    align-self: start;
    margin-top: 0;
  }
  .sb-about-hero-story-inner { display: block; }
  .sb-about-hero-story-inner .sb-img.landscape { display: none; }
  .sb-about-hero-mascot { height: 120px; margin: 24px auto 0; }

  .sb-about-hero-text > h1 {
    grid-column: 1 / -1;
    grid-row: 3;
    text-align: center;
    margin-top: 40px;
    font-size: 1.6rem;
  }
  .sb-about-hero-text > .sb-about-hero-lede {
    grid-column: 1 / -1;
    grid-row: 4;
    display: block;
    text-align: center;
    font-size: 1.1rem;
    line-height: 1.6;
    color: var(--sb-black);
    max-width: 480px;
    margin: 20px auto 0;
    padding: 20px 24px;
    border: 2px solid var(--sb-cream);
    border-top: 4px solid var(--sb-brown);
    border-radius: 4px;
  }
}

.sb-card {
  border: 1px solid #ddd;
  border-radius: 6px;
  padding: 16px;
}
.sb-card h3 { font-size: 1rem; }
.sb-card p { font-size: 0.85rem; color: #666; }

.sb-list-plain {
  list-style: none;
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.sb-list-plain li {
  padding-left: 20px;
  position: relative;
  color: #444;
  font-size: 1rem;
}
.sb-list-plain li::before {
  content: "—";
  position: absolute;
  left: 0;
  color: #999;
}

/* ---------- Menu page — categorized menu board ---------- */
.sb-menu-category-card {
  background: #fff;
  border: 1px solid #e6e2d8;
  border-top: 4px solid var(--sb-brown);
  border-radius: 8px;
  padding: 22px 24px;
}
.sb-menu-category-card.sb-accent-red { border-top-color: var(--sb-red); }
.sb-menu-category-card.sb-accent-black { border-top-color: var(--sb-black); }
.sb-menu-category-card h3 {
  text-transform: uppercase;
  letter-spacing: 0.06em;
  font-size: 1rem;
  padding-bottom: 10px;
  margin-bottom: 2px;
  border-bottom: 2px solid var(--sb-cream);
}
.sb-menu-category-card .sb-list-plain { gap: 0; }
.sb-menu-category-card .sb-list-plain li {
  padding: 8px 4px 8px 18px;
  border-bottom: 1px solid #f1eee7;
  font-size: 0.92rem;
}
.sb-menu-category-card .sb-list-plain li:last-child { border-bottom: none; }
.sb-menu-category-card .sb-list-plain li::before { content: "\2022"; color: var(--sb-red); font-size: 1.1em; top: 6px; }

/* Sides — long list, laid out full-width in multiple columns instead of one tall column.
   Overrides .sb-list-plain's flex display — CSS multi-column has no effect on flex children. */
.sb-menu-sides-list li { break-inside: avoid-column; }
@media (min-width: 700px) {
  .sb-menu-sides-list { display: block; columns: 3; column-gap: 28px; }
}
@media (min-width: 984px) {
  .sb-menu-sides-list { columns: 4; column-gap: 28px; }
}

/* ---------- Steps ---------- */
.sb-steps {
  display: grid;
  grid-template-columns: 1fr;
  gap: 16px;
}
.sb-step {
  border: 1px solid #ddd;
  border-radius: 6px;
  padding: 16px;
  text-align: center;
}
.sb-step .sb-step-num {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 28px;
  height: 28px;
  border-radius: 50%;
  background: var(--sb-red);
  color: #fff;
  font-weight: 700;
  margin-bottom: 8px;
}
@media (min-width: 600px) {
  .sb-steps { grid-template-columns: repeat(3, 1fr); gap: 24px; }
}

/* Irregular "smoke" top edge instead of a straight diagonal cut — ties the
   shape itself back to the brand (wood-fired smoke) instead of a generic
   geometric divider. filter: drop-shadow (not border-top) traces the red
   accent along the actual clipped silhouette, since a real border ignores
   clip-path and only follows the box's original rectangle — that mismatch
   was why the old straight diagonal showed a grey/red split instead of one
   clean line. */
.sb-cta-banner {
  background: var(--sb-black);
  color: #fff;
  text-align: center;
  padding: 56px 0 40px;
  clip-path: polygon(
    0% 20px, 12% 6px, 24% 22px, 36% 4px, 50% 18px,
    64% 2px, 78% 16px, 90% 6px, 100% 14px,
    100% 100%, 0% 100%
  );
  filter: drop-shadow(0 -3px 0 var(--sb-red));
}
.sb-cta-banner h2 { margin-bottom: 26px; }
.sb-cta-banner .sb-container { position: relative; }
/* Below 768px it flows normally (centered, below the button) — at those
   widths Kevin wants it stacked under the button rather than offset to the
   side, and there isn't reliably enough side room for that anyway. Sized to
   scale up progressively across the 5 mobile breakpoints (320/375/414/480/
   600) instead of one flat size for the whole range. */
.sb-cta-banner-mascot { display: block; height: 70px; width: auto; margin: 20px auto 0; }
@media (min-width: 375px) { .sb-cta-banner-mascot { height: 85px; } }
@media (min-width: 414px) { .sb-cta-banner-mascot { height: 95px; } }
@media (min-width: 480px) { .sb-cta-banner-mascot { height: 110px; } }
@media (min-width: 600px) { .sb-cta-banner-mascot { height: 130px; } }
@media (min-width: 752px) {
  /* The longer Catering heading fits on one line at this width and stretches
     close to the container edge — without a width cap here the mascot
     collides with it the closer it sits. Capping wraps it to two lines and
     frees up real side room. A fixed "right" offset for the mascot doesn't
     scale correctly once the container is wider than the (now fixed-width)
     heading — the gap between them just keeps growing as the viewport
     grows. Anchoring from the container's own center instead keeps the
     mascot a consistent, close distance from the heading's edge at any
     width, since the heading's width no longer changes past this point. */
  .sb-cta-banner h2 { max-width: 480px; margin-left: auto; margin-right: auto; }
  .sb-cta-banner-mascot {
    position: absolute;
    display: block;
    height: 140px;
    margin: 0;
    right: auto;
    left: 50%;
    margin-left: 250px;
    /* Without an explicit vertical anchor this falls back to its "static"
       flow position — which sits deep enough (below the button) to run past
       the bottom of a short single-line-heading banner (Menu's "Build Your
       Event Menu") and get clipped by the section's clip-path, even though
       it fit fine on Catering's taller two-line-heading banner. Centering it
       on the button's own vertical middle keeps it inside the banner
       regardless of how tall the heading makes the banner. */
    top: 50%;
    transform: translateY(-50%);
  }
}
@media (min-width: 752px) {
  .sb-cta-banner {
    padding: 72px 0 48px;
    clip-path: polygon(
      0% 34px, 6% 10px, 13% 30px, 20% 6px, 28% 26px,
      36% 2px, 44% 24px, 52% 6px, 60% 28px, 68% 4px,
      76% 22px, 84% 2px, 92% 18px, 100% 8px,
      100% 100%, 0% 100%
    );
  }
}

/* ---------- Page intro (mascot beside the page's H1 — Menu, Catering, Gallery, Contact) ---------- */
.sb-page-intro {
  display: flex;
  align-items: center;
  gap: 24px;
}
.sb-page-intro-mascot { height: 150px; width: auto; flex-shrink: 0; }
.sb-page-intro p.sb-placeholder-text { margin-top: 6px; line-height: 1.5; }

/* Contact page only — single column (heading/text/quicklinks, then mascot last
   in both visual AND source order, so screen readers hear it in the same
   sequence sighted users see it), not the mascot-beside-heading row every
   other .sb-page-intro page uses. */
.sb-page-intro.sb-page-intro-stacked {
  flex-direction: column;
  align-items: center;
  text-align: center;
}
.sb-page-intro-stacked .sb-page-intro-mascot { margin-top: 8px; height: 100px; }
.sb-page-intro-stacked .sb-contact-quicklinks { justify-content: center; }

/* Tablet and desktop — back to the standard mascot-beside-heading row every
   other .sb-page-intro page uses (752px is this site's usual mobile/tablet
   cutoff, used by most other breakpoints sitewide — the header's own
   hamburger-to-full-nav switch is a separate, later breakpoint at 984px).
   Real phone widths (below this) keep the stacked, centered layout
   above. */
@media (min-width: 752px) {
  .sb-page-intro.sb-page-intro-stacked {
    /* row-reverse, not row: the mascot is now last in the HTML (for correct
       mobile reading order), but the original desktop layout puts it first
       visually, on the left. */
    flex-direction: row-reverse;
    align-items: center;
    justify-content: center;
    text-align: left;
  }
  .sb-page-intro-stacked .sb-page-intro-mascot { margin-top: 0; height: 150px; }
  .sb-page-intro-stacked .sb-contact-quicklinks { justify-content: flex-start; }
}

/* Contact page — phone/email as a pair of pill buttons instead of one plain crowded line */
.sb-contact-quicklinks {
  display: flex;
  flex-wrap: wrap;
  gap: 12px;
  margin-top: 16px;
}
.sb-contact-quicklink {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 8px 16px;
  border: 1.5px solid var(--sb-brown);
  border-radius: 999px;
  font-weight: 600;
  font-size: 0.9rem;
  color: var(--sb-black);
  overflow-wrap: anywhere;
  transition: background 0.2s ease, color 0.2s ease, border-color 0.2s ease;
}
.sb-contact-quicklink svg { flex-shrink: 0; }
.sb-contact-quicklink:hover,
.sb-contact-quicklink:focus-visible {
  background: var(--sb-red);
  border-color: var(--sb-red);
  color: #fff;
}

/* ---------- Gallery bento grid (desktop) / masonry (mobile) ----------
   Pattern documented in _Project Template/workflow/responsive-gallery-patterns.md
   — three tile types: `.sb-gi-v` (vertical/portrait photo, tall cell),
   `.sb-gi-h` (horizontal/landscape photo, wide cell), and `.sb-gi-sq`
   (square, plain 1x1 cell — used for the first 4 photos so the gallery opens
   on a clean, uniform row before settling into the mixed bento below).
   `grid-auto-flow: dense` packs whatever mix you give it automatically, in
   whatever order they appear — no per-photo positioning needed, so this
   scales to any number of photos without touching CSS. Built this way
   on purpose for the future Sanity-driven gallery: each upload just gets
   tagged vertical, horizontal, or square, nothing more bespoke than that.
   Mobile drops the explicit grid and flows as CSS-column masonry so nothing
   gets cropped at a narrow width — tile type has no effect there. */
.sb-gallery-grid {
  display: grid;
  grid-auto-flow: dense;
  grid-template-columns: repeat(4, 1fr);
  grid-auto-rows: 240px;
  gap: 12px;
  margin-top: 20px;
}
.sb-gi-v { grid-row: span 2; }
.sb-gi-h { grid-column: span 2; }
/* Square only kicks in at iPad-portrait width and down (752-900px) — each
   square tile also keeps its original .sb-gi-v/.sb-gi-h class so 901px+
   (real desktop, iPad landscape) falls back to the original bento shape
   automatically, no separate desktop rule needed. */
@media (max-width: 900px) {
  .sb-gi-sq { grid-row: span 1; grid-column: span 1; }
  /* Guests-mingling photo goes wide only at this narrower range, so it sits
     flush next to the firewood-stack photo at 768px — reverts to its normal
     vertical .sb-gi-v shape at 901px+ (1024, 1200, real desktop), where
     Kevin wants it back to how it always looked, next to the dessert photo. */
  .sb-gi-wide-tablet { grid-row: span 1; grid-column: span 2; }
}

@media (max-width: 751px) {
  .sb-gallery-grid {
    display: block;
    column-count: 2;
    column-gap: 10px;
    grid-template-columns: none;
    grid-template-rows: none;
  }
  .sb-gallery-grid .sb-img {
    display: block;
    break-inside: avoid;
    margin-bottom: 10px;
    width: 100%;
    height: auto;
    grid-column: auto !important;
    grid-row: auto !important;
  }
  .sb-gallery-grid .sb-img img {
    display: block;
    width: 100%;
    height: auto;
    object-fit: unset;
    object-position: unset;
  }
}
@media (max-width: 480px) {
  .sb-gallery-grid { column-gap: 8px; }
  .sb-gallery-grid .sb-img { margin-bottom: 8px; }
}

/* ---------- Footer ---------- */
/* A thin grey line marks the CTA-banner-to-footer seam on every page — both
   are solid black, so without it the two blocks would just blend into one
   another with no visual separation at all. Pages with NO CTA banner
   (Privacy, Terms, 404) cut straight from a light section into the footer
   instead, so they get `.sb-footer-flat-top` — a bolder red rule that gives
   the footer its own "entrance" rather than an abrupt white-to-black seam. */
.sb-footer {
  background: var(--sb-black);
  color: #ccc;
  padding: 52px 0 0;
  font-size: 0.9rem;
  border-top: 1px solid rgba(255, 255, 255, 0.14);
}
.sb-footer-flat-top { border-top: 4px solid var(--sb-red); }
.sb-footer-grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: 36px;
}
.sb-footer a { color: #ccc; text-decoration: none; }
.sb-footer a:hover { color: var(--sb-red-on-dark); }
.sb-footer .sb-logo-img { height: 48px; }
.sb-footer-brand {
  display: flex;
  flex-direction: column;
  gap: 14px;
}
.sb-footer-tagline {
  color: #999;
  font-size: 0.85rem;
  max-width: 260px;
  line-height: 1.55;
}
.sb-footer-social {
  display: flex;
  gap: 10px;
  margin-top: 2px;
}
.sb-social-icon {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 44px;
  height: 44px;
  border-radius: 50%;
  border: 1px solid rgba(255, 255, 255, 0.2);
  color: #ccc;
  transition: border-color 0.2s ease, color 0.2s ease;
}
a.sb-social-icon:hover { border-color: var(--sb-red-on-dark); color: var(--sb-red-on-dark); }
.sb-social-icon-soon {
  color: #666;
  border-color: rgba(255, 255, 255, 0.12);
  cursor: default;
}
.sb-footer-col { display: flex; flex-direction: column; }
.sb-footer-heading {
  font-size: 0.72rem;
  font-weight: 700;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: #F0B896;
  margin-bottom: 16px;
}
.sb-footer .sb-footer-nav {
  display: flex;
  flex-direction: column;
  gap: 11px;
  font-size: 1rem;
}
.sb-footer-contact {
  display: flex;
  flex-direction: column;
  gap: 11px;
  font-size: 0.88rem;
  color: #bbb;
}
/* Wraps to 2-3 lines like the rest of the footer's short text blocks —
   left unconstrained it stretches into one long line once the column
   is wide enough (tablet width and up, before the 3-column desktop grid). */
.sb-footer-service-area {
  max-width: 260px;
}
@media (min-width: 752px) {
  .sb-footer-service-area { max-width: 320px; }
}
.sb-footer-contact a { color: #ccc; font-weight: 500; }
/* Mobile-only: center every footer column as its own stacked block —
   left-aligned reads fine in the 3-column desktop grid, but as a single
   stacked column on mobile it looks like a stray ragged-left leftover
   rather than a deliberate centered layout. */
@media (max-width: 1007px) {
  .sb-footer-grid { justify-items: center; text-align: center; }
  .sb-footer-brand { align-items: center; }
  .sb-footer-col { align-items: center; }
  .sb-footer-social { justify-content: center; }
}
.sb-footer-bottom {
  margin-top: 40px;
  padding: 0 0 18px;
  color: #999;
  font-size: 0.78rem;
}
/* Divider sits on the container row itself — spans the full copyright-to-
   "Site by..." content width (matching the container width used by the
   footer grid above it), not the full black background edge-to-edge, and
   not shrunk to just the copyright text alone. */
.sb-footer-bottom-inner {
  display: flex;
  flex-direction: column;
  gap: 12px;
  align-items: center;
  text-align: center;
  border-top: 1px solid rgba(255, 255, 255, 0.14);
  padding-top: 18px;
}
.sb-footer-copyright { color: #999; }
.sb-footer-legal {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
  gap: 6px 18px;
}
.sb-footer-legal a { position: relative; color: #999; }
.sb-footer-legal a:hover { color: var(--sb-red-on-dark); }
.sb-footer-legal a:not(:last-child)::after {
  content: "";
  position: absolute;
  right: -10px;
  top: 50%;
  transform: translateY(-50%);
  width: 1px;
  height: 11px;
  background: rgba(255, 255, 255, 0.18);
}
/* At 320-375px "Site by Forged Digital Design" wraps to its own line,
   leaving the divider after "Terms of Service" dangling at the end of
   the line above with nothing after it on that line. */
@media (max-width: 399px) {
  .sb-footer-legal a:nth-last-child(2)::after { content: none; }
}
@media (min-width: 984px) {
  .sb-footer-grid {
    grid-template-columns: 1.2fr 1fr 1fr;
    gap: 32px;
  }
  .sb-footer .sb-footer-nav {
    display: grid;
    grid-template-columns: repeat(2, max-content);
    justify-content: start;
    column-gap: 28px;
    row-gap: 11px;
  }
  /* Bottom copyright bar: row layout on laptop/desktop so the copyright
     line and legal links sit on one line — the mobile/tablet breakpoint
     pass (2026-08-19) centered this at all widths, which unintentionally
     carried the stacked/centered mobile treatment up into desktop. The
     "All rights reserved." line break is mobile/tablet-only for the same
     reason — it collapses back onto the copyright line here. */
  .sb-footer-bottom-inner {
    flex-direction: row;
    justify-content: space-between;
    text-align: left;
  }
  .sb-footer-copyright br {
    display: none;
  }
}

/* ---------- Mobile call FAB ---------- */
/* Mobile only — on desktop the phone number already lives in the header
   utility bar. Fades out (not padding-reserved) as the footer scrolls
   into view, via IntersectionObserver in js/call-fab.js — confirmed
   approach from a prior client fix for the same FAB-over-footer overlap,
   preferred over static padding since it only "costs" space right when
   actually needed. */
.sb-call-fab {
  position: fixed;
  right: 18px;
  bottom: 18px;
  z-index: 90;
  width: 56px;
  height: 56px;
  border-radius: 50%;
  display: flex;
  align-items: center;
  justify-content: center;
  background: var(--sb-red);
  color: #fff;
  box-shadow: 0 6px 18px rgba(0, 0, 0, 0.35);
  /* visibility is in the transition list on purpose — without it, adding
     visibility:hidden below would snap invisible instantly instead of
     fading; with it, the browser delays the visibility switch until the
     opacity fade finishes (and applies it immediately going the other way). */
  transition: opacity 0.25s ease, transform 0.15s ease, visibility 0.25s ease;
}
.sb-call-fab:active { transform: scale(0.94); }
.sb-call-fab.sb-call-fab-hidden {
  opacity: 0;
  /* Faded out via opacity alone, this fixed link stayed in the keyboard tab
     order and focusable (pointer-events:none only blocks mouse/touch) — a
     keyboard user tabbing past it would land on an invisible, unfocusable-
     looking link with nothing visible at the focus position. visibility:hidden
     removes it from the tab order and AT tree while faded out. */
  visibility: hidden;
  pointer-events: none;
}
@media (min-width: 752px) {
  .sb-call-fab { display: none; }
}
@media (prefers-reduced-motion: reduce) {
  .sb-call-fab { transition: none; }
}

.sb-build-note {
  background: #fffbe6;
  border-bottom: 1px solid #f0e0a0;
  color: #6b5a00;
  font-size: 0.75rem;
  text-align: center;
  padding: 6px 12px;
}

/* ---------- Forms ---------- */
/* Matches the site's signature framed-card look (photo borders, process
   cards) instead of a generic grey box — a plain #ddd/#fafafa box was the
   one place on the site that didn't look like the rest of it. */
.sb-form-box {
  border: 2px solid var(--sb-cream);
  border-top: 4px solid var(--sb-brown);
  border-radius: 8px;
  padding: 20px;
  background: #fff;
}
@media (min-width: 752px) {
  .sb-form-box { padding: 28px; }
}

/* Anchor-jump targets need this because the header is position:sticky —
   without it, the sticky header covers the top of whatever you jump to.
   165px clears the header's largest (unscrolled) height (~151px, grown
   with the larger logo/nav) with room to spare. */
#quote {
  scroll-margin-top: 165px;
}

.sb-form-grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: 16px;
}
@media (min-width: 600px) {
  .sb-form-grid { grid-template-columns: 1fr 1fr; }
}
.sb-form-grid .sb-span-2 { grid-column: 1 / -1; }

.sb-form-group { display: flex; flex-direction: column; gap: 6px; }
.sb-form-group label {
  font-weight: 600;
  font-size: 0.85rem;
  color: #333;
}
.sb-hint {
  /* was scoped to ".sb-form-group .sb-hint" but the actual element isn't inside
     a .sb-form-group, so this never matched — rendered as plain unstyled text */
  display: block;
  font-weight: 400;
  font-size: 0.78rem;
  color: #666; /* was #888 — failed WCAG AA (3.4:1) on white, #666 passes (~5.7:1) */
}

.sb-form-box input[type="text"],
.sb-form-box input[type="email"],
.sb-form-box input[type="tel"],
.sb-form-box input[type="date"],
.sb-form-box input[type="number"],
.sb-form-box select,
.sb-form-box textarea {
  border: 1px solid #ccc;
  border-radius: 4px;
  padding: 10px 12px;
  font-size: 16px;
  font-family: inherit;
  width: 100%;
  background: #fff;
  color: #1a1a1a;
}
.sb-form-box textarea { resize: vertical; min-height: 90px; }
.sb-form-box input:focus,
.sb-form-box select:focus,
.sb-form-box textarea:focus {
  outline: 2px solid #1a1a1a;
  outline-offset: 1px;
}

.sb-menu-picker { display: flex; flex-direction: column; gap: 20px; }
/* Fieldset/legend (not div/h4) so screen readers announce which category
   each checkbox belongs to — 43 checkboxes with no group context read as
   an undifferentiated list otherwise (WCAG 1.3.1 Info and Relationships). */
.sb-menu-category { border: none; margin: 0; padding: 0; min-width: 0; }
.sb-menu-category legend {
  display: block;
  width: 100%;
  font-size: 0.95rem;
  font-weight: 700;
  margin-bottom: 10px;
  padding: 0 0 6px;
  border-bottom: 1px solid #e2e2e2;
}
.sb-checkbox-grid {
  display: grid;
  grid-template-columns: 1fr;
  gap: 8px 16px;
}
@media (min-width: 600px) {
  .sb-checkbox-grid { grid-template-columns: 1fr 1fr; }
}
@media (min-width: 900px) {
  .sb-checkbox-grid { grid-template-columns: 1fr 1fr 1fr; }
}
.sb-checkbox-grid label {
  display: flex;
  align-items: center;
  gap: 8px;
  font-weight: 400;
  font-size: 0.9rem;
  color: #333;
}
.sb-checkbox-grid input[type="checkbox"] {
  width: 16px;
  height: 16px;
  flex-shrink: 0;
}

/* Honeypot — visually hidden but still present in the DOM/tab order avoided via tabindex="-1"; real users never see or fill it, bots that auto-fill every field trip it */
.sb-hp-field {
  position: absolute;
  left: -9999px;
  width: 1px;
  height: 1px;
  overflow: hidden;
}

.sb-form-status {
  margin-top: 12px;
  font-size: 0.85rem;
  min-height: 1.2em;
}
.sb-form-status.sb-status-success { color: #1a1a1a; font-weight: 600; }
.sb-form-status.sb-status-error { color: #1a1a1a; font-weight: 600; text-decoration: underline; }

.sb-required {
  color: #1a1a1a;
  font-weight: 700;
}

.sb-optional {
  color: #707070; /* #777 measured ~4.48:1 on white at this font-size — just under
    the 4.5:1 AA minimum for normal text; #707070 measures ~4.95:1 */
  font-weight: 400;
  font-size: 0.85em;
}

/* Collapsed "just have a question?" disclosure below the Quote form —
   native <details>/<summary> instead of a modal: free keyboard support,
   focus handling, and screen-reader semantics with zero custom JS. */
.sb-turnstile-row { margin-top: 20px; min-height: 65px; overflow: hidden; }
@media (max-width: 340px) {
  .sb-turnstile-row .cf-turnstile { transform: scale(0.74); transform-origin: left top; }
}
@media (min-width: 341px) and (max-width: 400px) {
  .sb-turnstile-row .cf-turnstile { transform: scale(0.92); transform-origin: left top; }
}

.sb-question-disclosure { margin-top: 40px; text-align: center; }
.sb-question-toggle {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  background: transparent;
  border: 2px solid var(--sb-black);
  color: var(--sb-black);
  padding: 14px 28px;
  font-weight: 700;
  font-size: 0.85rem;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  border-radius: 4px;
  cursor: pointer;
  list-style: none;
  transition: background 0.2s ease, color 0.2s ease;
}
.sb-question-toggle::-webkit-details-marker { display: none; }
.sb-question-toggle::after {
  content: "+";
  font-size: 1.1rem;
  line-height: 1;
  transition: transform 0.2s ease;
}
.sb-question-toggle:hover { background: var(--sb-black); color: #fff; }
.sb-question-disclosure[open] .sb-question-toggle::after { transform: rotate(45deg); }
.sb-question-disclosure[open] .sb-question-toggle { margin-bottom: 4px; }

.sb-turnstile-placeholder {
  margin-top: 16px;
  border: 1px dashed var(--sb-brown);
  border-radius: 4px;
  padding: 14px;
  text-align: center;
  font-size: 0.8rem;
  color: #666;
  background: var(--sb-cream);
  max-width: 300px;
}

.sb-form-note {
  font-size: 0.8rem;
  color: #666; /* was #777 — failed WCAG AA on white */
  margin-top: 6px;
}

.sb-divider-label {
  text-align: center;
  color: var(--sb-brown-text);
  font-weight: 700;
  font-size: 1.1rem;
  text-transform: uppercase;
  letter-spacing: 0.06em;
  margin: 40px 0 24px;
  padding-top: 24px;
  border-top: 1px solid var(--sb-cream);
}

/* Respect reduced-motion preference */
@media (prefers-reduced-motion: reduce) {
  .sb-nav-toggle span { transition: none; }
}
