/* Smackagram - shared site chrome.
   Loaded by every template BEFORE its own inline <style>, so any page-specific
   rule still wins by source order. Edit nav/brand styling HERE, once. */

/* Anton, for the nav wordmark (Andy, 24 Aug 2026).
   The wordmark now uses Anton on EVERY page, matching the home page. Only 27
   of the 63 customer templates <link> Anton themselves, so on the other 36 it
   would have silently fallen back to Impact and the logo would have looked
   different on more than half the site. Imported here instead of adding a
   <link> to 36 templates. @import must stay above every rule in this file. */
@import url("https://fonts.googleapis.com/css2?family=Anton&family=Barlow+Condensed:wght@400;500;600;700;800&display=swap");

/* =======================================================================
   SITEWIDE LAYOUT SCALE (Andy, 26 Aug 2026)
   =======================================================================
   THE PROBLEM THIS SOLVES. Every page had been built to its own handoff's
   numbers, so nothing lined up between them. Measured before this change:

     page column   1112 / 1120 / 1160 / 1180 / 1240 / 1280 / 1320 / 1440
     hero headline 52 / 62 / 66 / 68 / 72 / 72 / 78 / 91 px

   Nine content widths and eight type scales across eight pages, which is
   why the site changed size every time you clicked between them - and why
   the homepage headline (91px max inside a 709px copy column) ran under
   the hero artwork at wide viewports.

   ONE SCALE NOW. These tokens are declared here, in the file every template
   loads BEFORE its own inline <style>, so a page can still override one
   deliberately - but nothing has to, and a new page inherits the system for
   free by referencing them.
   ======================================================================= */
:root{
  /* The page content column and its side gutter. Every page-level wrapper
     resolves to width:min(--smk-content, 100% - 2*--smk-gutter). */
  --smk-content:1280px;
  --smk-gutter:clamp(20px, 4vw, 64px);
  /* Display type. --smk-h1 is every hero headline; --smk-h2 every section
     heading. Both are fluid between the same two viewport ends, so two
     pages side by side step at identical widths. */
  /* One clamp each, spanning phone to desktop, so no page needs a media
     override - which is what made the pages diverge again below 1024. */
  --smk-h1:clamp(30px, 4.2vw, 52px);
  --smk-h2:clamp(24px, 2.6vw, 38px);
  /* Body, eyebrow and button, so a page cannot look 50% bigger than its
     neighbour the way the homepage did (26px body against 16-18px, a
     22px eyebrow against 14-16px and a 66px button against 54px). */
  --smk-body:clamp(15px, 1.05vw, 17px);
  --smk-eyebrow:clamp(13px, .95vw, 15px);
  --smk-btn-size:20px;
  --smk-btn-h:54px;
  /* FLAGSHIP HERO. One deliberate step above the shared scale, for the
     homepage only: with its two CTAs removed there is room for the
     headline and description to carry the page. Kept as a token rather
     than a one-off so the step is visible and reusable, not a page
     quietly drifting again. */
  --smk-h1-flagship:clamp(38px, 5.2vw, 68px);
  --smk-body-flagship:clamp(17px, 1.45vw, 21px);

  /* THE SHARED HERO GRID (Andy, 26 Aug 2026).
     Every hero is viewport-wide. The COPY track lines up exactly with the
     page's content column, and the ART track runs from the copy's right edge
     all the way to the viewport edge - so hero artwork bleeds right, and with
     align-items:stretch and no hero padding it meets the top and bottom of
     the band too.

       track 1  the content column's own left margin
       track 2  the copy, 47% of whatever the content column currently is
       track 3  everything left over - the art

     Track 2 is a share of `min(content, 100% - 2*gutter)` rather than of the
     fixed 1280, so the copy keeps its proportion on a laptop instead of
     eating the whole row. */
  --smk-hero-cols:
    [full-start] max(var(--smk-gutter), (100% - var(--smk-content)) / 2)
    [copy-start] minmax(0, calc(min(var(--smk-content), 100% - 2 * var(--smk-gutter)) * .47)) [copy-end]
    minmax(0, 1fr) [full-end];

  /* ---------------------------------------------------------------
     ONE HERO HEIGHT (Andy, 26 Aug 2026).
     Every hero was content-driven, so its height moved with whatever
     copy the page happened to carry - the homepage ran ~90px taller
     than SmackCast at the same viewport, and the gap CHANGED with the
     headline's wrap. A shared floor plus vertically centred copy makes
     every split hero the same band on every page. Andy picked 620px on
     26 Aug - a step up from the 560 that shipped first, chosen against a
     side-by-side of 560/620/680/740 at 1660px.
     Heroes stack below 1024, where a fixed band makes no sense - the
     stacked rule sets this to auto and the art keeps its own height. */
  --smk-hero-h:620px;
}

/* Stacked: no shared band. */
@media (max-width:1023px){ :root{ --smk-hero-h:auto; } }

:root{
  --ink:#0D0D0D;
  --ink-2:#1A1A1A;
  --chalk:#F5F5F3;
  --chalk-dim:#9A9A96;
  --flare:#E10600;
  /* #E10600 only reaches 4.23:1 on --ink and 3.79:1 on --ink-2, so it fails
     WCAG AA (4.5:1) for anything under 18px. Use --flare-text for small text;
     --flare stays exactly as-is for buttons, borders and display type. */
  --flare-text:#E10600;
  --flare-dim:#3A0810;
  --turf:#39FF6A;
  --gold:#FFD400;   /* winner gold - Battle Room / Arena Room / Battle Card / Smack Chat only */
  /* Silver was defined page-by-page, so a page that forgot it got nothing.
     It belongs here with the rest of the palette. */
  --silver:#C3CAD3;
  --cyan:#F5F5F3;
  --line:rgba(245,245,243,0.10);
  --line-strong:rgba(245,245,243,0.24);
  /* Measured, not guessed: the nav is 75px at every breakpoint.
     Templates used to hardcode 76px and 77px, both wrong. */
  --nav-h:75px;
}

*{box-sizing:border-box; margin:0; padding:0;}

/* NOTE: `body` is deliberately NOT here. Line-height genuinely varies per page
   (1.5 / 1.6 / 1.65) and two pages set none at all. Page typography stays with
   the page. */

/* NAV, WHITE (25 Aug 2026). Sitewide request, not a per-page scope: every
   template shares this one <nav>, and it was still the original dark bar
   (--ink-2-ish, light text) on every page except the handful already
   individually re-themed - so the same page could show a white checkout
   panel under a black nav. Colours below are lifted verbatim from
   homepage-sports.css's body.home-v2 nav block (the first place this
   white nav shipped), hardcoded rather than var()'d so a future page's
   own :root remap (--ink, --chalk, etc., done per-page for that page's
   BODY content) can never accidentally recolour the one shared nav. This
   intentionally does NOT add home-v2's position:sticky/backdrop-filter -
   that's a layout/behaviour change 90+ templates never asked for, only
   the colour did. */
/* Visually-hidden utility, SITEWIDE. It existed only as `body.home-v3
   .sr-only` in homepage-sports.css, so the moment another page used the
   class its text rendered as ordinary visible copy - which is exactly what
   happened when the red ticker's screen-reader line was added to Send a
   Smack (Andy, 25 Aug 2026). Defined here so any page can use it. */
.sr-only{
  position:absolute; width:1px; height:1px; padding:0; margin:-1px;
  overflow:hidden; clip:rect(0 0 0 0); clip-path:inset(50%); white-space:nowrap; border:0;
}

nav{
  display:flex; justify-content:space-between; align-items:center; padding:20px 24px;
  background:#faf8f2; border-bottom:1px solid #c9c7c0;
}
.nav-links{display:flex; gap:32px; align-items:center; font-size:14px; color:#2e3035;}

/* --- Grouped nav dropdowns --- */
.nav-group{position:relative;}
.nav-group-btn{
  background:none; border:0; padding:0; cursor:pointer;
  font-family:inherit; font-size:14px; color:#2e3035;
  display:inline-flex; align-items:center; gap:5px;
}
.nav-group-btn:hover, .nav-group.is-open .nav-group-btn{color:var(--flare);}
.nav-caret{font-size:9px; transition:transform .15s ease;}
.nav-group.is-open .nav-caret{transform:rotate(180deg);}
.nav-menu{
  display:none; position:absolute; top:calc(100% + 12px); left:50%;
  transform:translateX(-50%); min-width:186px; z-index:60;
  background:#ffffff; border:1px solid #c9c7c0;
  border-radius:11px; padding:7px; box-shadow:0 12px 30px rgba(16,17,20,0.14);
}
.nav-group.is-open .nav-menu{display:block;}
/* Bridges the gap between button and menu so moving the cursor down
   doesn't close it mid-travel. */
.nav-menu::before{content:''; position:absolute; top:-12px; left:0; right:0; height:12px;}
.nav-menu a{
  display:block; padding:8px 11px; border-radius:7px; white-space:nowrap;
  color:#2e3035; text-decoration:none; font-size:13.5px;
}
.nav-menu a:hover{background:rgba(245,245,243,0.08); color:var(--flare);}
.nav-menu-hub{
  color:var(--flare) !important; font-weight:600;
  border-bottom:1px solid rgba(245,245,243,0.14); border-radius:7px 7px 0 0; margin-bottom:3px;
}

/* Drawer section headers - the mobile equivalent of the dropdowns. A
   drawer scrolls, so headers beat nested menus there. */
.nav-drawer-head{
  font-family:'JetBrains Mono',monospace; font-size:10px; font-weight:700;
  letter-spacing:2px; text-transform:uppercase; color:#9A9A96;
  margin:18px 0 6px; padding:0 2px; opacity:0.75;
}
.nav-drawer-head:first-of-type{margin-top:6px;}
.auth-links{display:flex; gap:20px; align-items:center; font-size:14px; color:#FFFFFF;}

/* MOBILE / TABLET NAV
   The desktop link row needs ~1250px to sit on one line. Below that it wrapped
   mid-phrase, and below 761px it vanished with nothing to replace it - leaving
   7 of 9 features unreachable on a phone. Below 1180px: slide-in drawer. */

.nav-toggle{
  display:none; width:44px; height:44px; padding:10px; margin:-10px -8px -10px 0;
  background:none; border:0; cursor:pointer; color:#FFFFFF; flex-shrink:0;
}
.nav-toggle span{display:block; height:2px; background:currentColor; border-radius:2px; margin:4px 0;}

/* Drawer matches the bar it slides out of - it reads as one nav, not a
   white bar hiding a black panel one tap away. */
.nav-drawer{
  position:fixed; top:0; right:0; bottom:0; width:min(82vw, 340px);
  background:#0D0D0D; border-left:1px solid #3A3D42;
  transform:translateX(100%); transition:transform .28s ease;
  z-index:9999; display:flex; flex-direction:column;
  padding:18px 22px calc(22px + env(safe-area-inset-bottom));
  overflow-y:auto; overscroll-behavior:contain;
  visibility:hidden;
}
.nav-drawer.open{transform:translateX(0); visibility:visible;}

.nav-scrim{
  position:fixed; inset:0; background:rgba(0,0,0,0.62); backdrop-filter:blur(2px);
  opacity:0; pointer-events:none; transition:opacity .28s ease; z-index:9998;
}
.nav-scrim.open{opacity:1; pointer-events:auto;}

.nav-drawer-close{
  align-self:flex-end; width:44px; height:44px; background:none; border:0;
  color:#FFFFFF; font-size:26px; line-height:1; cursor:pointer;
}
.nav-drawer-close:hover{color:var(--flare);}

.nav-drawer a{
  display:block; padding:13px 0; min-height:48px;
  font-family:'Oswald',sans-serif; font-size:19px; letter-spacing:0.4px;
  text-transform:uppercase; text-decoration:none; color:#FFFFFF;
  border-bottom:1px solid rgba(245,245,243,0.12);
}
.nav-drawer a:last-child{border-bottom:0;}
.nav-drawer a:hover,.nav-drawer a:focus-visible{color:var(--flare);}
/* Was two accent colours on individual drawer items. Every nav link now uses
   one colour - the hover state below is what distinguishes them, not a
   permanent highlight on two of them. */
.nav-drawer a.is-flare,
.nav-drawer a.is-gold{color:inherit;}

.nav-drawer-auth{margin-top:20px; padding-top:14px; border-top:1px solid rgba(245,245,243,0.20);}
.nav-drawer-auth a{font-size:17px;}

@media(max-width:1180px){
  .nav-links{display:none;}
  .auth-links{display:none;}
  .nav-toggle{display:block;}
}
@media(min-width:1181px){
  .nav-drawer,.nav-scrim{display:none;}
}
@media(prefers-reduced-motion:reduce){
  .nav-drawer,.nav-scrim{transition:none;}
}
body.nav-open{overflow:hidden;}

/* Footer links: contact.html had a completely unstyled <a>, which rendered as
   default browser blue (#0000EE) on black - 2.07:1. Also brings the tap target
   up from ~33x14 to the 44px minimum. */
/* ---------------------------------------------------------------------------
   Footer - one rule for the whole site
   ---------------------------------------------------------------------------
   Every page defined its own footer inline, so the layout differed page to
   page: some pushed the copyright and links to opposite ends, others centred
   everything. These rules are scoped to `html body footer` so they outrank a
   page's own inline <style> without needing all fifteen edited.
   ------------------------------------------------------------------------ */
html body footer{
  background:#0D0D0D;
  display:flex !important;
  flex-direction:column;
  align-items:center;
  justify-content:center;
  gap:6px;
  text-align:center;
  padding:34px 24px;
}
/* The footer's link row is a <nav class="flinks">, so the sitewide "nav{...}"
   bar rule (91px tall, cream background, 39px inline padding, red bottom rule)
   was landing on it. Invisible while every page was cream; on the black Daily
   Smack page it showed as a light 91px block sitting inside the footer. Reset
   here rather than per page - it was wrong everywhere, just not visible.
   (Andy, 27 Aug 2026) */
html body footer .flinks{
  display:flex; flex-wrap:wrap; justify-content:center; gap:4px 22px;
  background:transparent; border:0; min-height:0; height:auto;
  padding-inline:0; margin:0;
}
/* Anton and a size up. At 12px in body text these read as fine print on a
   site whose whole voice is loud - and they are the links somebody hunts for
   when they want to opt out, which is the worst place to be quiet. */
html body footer a{
  display:inline-block; padding:11px 4px;
  font-family:'Oswald', Impact, sans-serif;
  font-size:15px; letter-spacing:1px; text-transform:uppercase;
  /* The footer is WHITE sitewide, so the link colour has to be an ink, not
     the light blue-grey --silver still carries for the dark pages. Pages that
     already override --silver to an ink are unaffected; the homepage, which
     does not, was rendering #C3CAD3 on white. (Andy, 27 Aug 2026) */
  color:#FFFFFF; text-decoration:none;
}
html body footer a:hover{color:#E10600;}

/* The copyright stays small and quiet - it is not a link and nobody is
   looking for it. */
html body footer > span{
  font-family:'JetBrains Mono',monospace;
  font-size:10px; letter-spacing:1.6px; text-transform:uppercase;
  color:#9A9A96;
}

@media(max-width:520px){
  html body footer a{font-size:13.5px; letter-spacing:0.8px;}
  html body footer .flinks{gap:2px 14px;}
}

/* The logo link was 51x34 on all 19 pages. The nav is 75px tall regardless, so
   growing the hit area to 44px costs no layout.

   SCOPED BY CLASS, NOT POSITION (David, 26 Aug 2026). Was `nav > a:first-of-type`
   - "the first link in any <nav>" - which also matched the footer's own
   <nav class="flinks"> (_footer.html), silently growing whichever footer
   link happened to be listed first (Pricing) to 44px while every other
   footer link stayed at its natural ~38px, so Pricing sat visibly higher
   and taller than the rest. The logo link already carries class="brand"
   (_nav.html) - matching that directly hits only the one link this rule
   was ever meant for. */
nav > a.brand{min-height:44px; display:flex; align-items:center;}

/* The wordmark that replaced the image logo. Anton to match every display
   heading on the site, sized to occupy the same vertical space the image
   did so nothing else in the nav shifts.

   Tight letter-spacing because Anton is already condensed and the default
   tracking makes a nine-letter word sprawl across a phone's nav bar. */
.brand{
  font-family:'Oswald', Impact, sans-serif;
  font-size:25px;
  line-height:1;
  letter-spacing:0.5px;
  color:#101114; /* was var(--chalk) - white text on the nav's new white bar */
  text-decoration:none;
  white-space:nowrap;
  display:flex;
  align-items:center;
}
.brand span{color:var(--flare, #E10600);}
.brand:hover{opacity:0.88;}

@media(max-width:520px){
  .brand{font-size:21px;}
}

/* Buttons measured 37-42px. Not applied to `button` generally, because small
   icon buttons (the 16px sensitivity "i") would stretch and break their rows. */
.btn,.btn-play,.btn-flare,.btn-ghost{min-height:44px;}

/* Text fields measured 43px - one pixel under the minimum, everywhere. */
input[type=text],input[type=tel],input[type=email],input[type=password],
input[type=number],input[type=date],select,textarea{min-height:44px;}

/* ---------------------------------------------------------------------------
   KEYBOARD FOCUS
   16 templates carried `input:focus{outline:none; border-color:var(--flare);}`.
   A 1px border tint is a weak indicator, and on a checkbox it is invisible -
   tabbing through the site, 12 of 40 elements showed no focus state at all.

   `html body` is here on purpose: it lifts specificity to (0,1,2) so this beats
   those `input:focus` rules at (0,1,1), which would otherwise win on source
   order since the page's inline <style> loads after this file. That avoids
   having to touch 16 templates, and avoids !important.

   :focus-visible (not :focus) means mouse users don't get a ring on every
   click - only keyboard users, and text fields, which browsers always treat
   as focus-visible.
--------------------------------------------------------------------------- */
html body :focus-visible{
  outline:2px solid var(--chalk);
  outline-offset:2px;
}
/* smack_chat and smack_lab suppress the ring with class-level selectors like
   `.search-input:focus` (0,2,0) and `input[type=text]:focus` (0,2,1), which
   outrank the rule above at (0,1,2). :is() takes the specificity of its
   heaviest argument, lifting this to (0,2,2) so it wins - still no !important. */
html body :is(a,button,input,select,textarea,[tabindex]):focus-visible{
  outline:2px solid var(--chalk);
  outline-offset:2px;
}
/* Checkboxes are small and sit inside dark rows; give them a little more. */
html body input[type=checkbox]:focus-visible,
html body input[type=radio]:focus-visible{
  outline:2px solid #E10600;
  outline-offset:3px;
}

/* ---------------------------------------------------------------------------
   TYPE SCALE
   The site had 25 distinct font sizes across 297 declarations. These are the
   steps everything should land on. Headings use clamp() so a 36px desktop
   headline drops to 28px on a phone instead of wrapping awkwardly.

   Three heading tiers, deliberately:
     hero    clamp(38px,6vw,64px)  index only - the landing page
     page    clamp(28px,5vw,36px)  feature pages, confirmations, recaps
     form    clamp(22px,4vw,26px)  login / register / profile / verify
--------------------------------------------------------------------------- */
:root{
  --fs-2xs:10px;
  --fs-xs:11px;
  --fs-sm:12px;
  --fs-base:13px;
  --fs-md:14px;
  --fs-lg:16px;
  --fs-xl:18px;
  --fs-2xl:22px;
  --fs-3xl:26px;
  --h1-hero:clamp(38px,6vw,64px);
  --h1-page:clamp(28px,5vw,36px);
  --h1-form:clamp(22px,4vw,26px);
}

/* ---------------------------------------------------------------------------
   LOADING / PENDING STATE
   The site makes 48 fetch() calls and had zero spinners. Feedback was limited
   to disabling the button and swapping its label - and two templates
   (index.html, locked_n_loaded.html) had no :disabled styling at all, so on the
   paid Locked & Loaded flow the button looked completely unchanged after you
   pressed it.

   Pure CSS, no template changes needed, which is only safe because `disabled`
   is used almost exclusively for in-flight operations here - never for form
   validation, never set in markup at load. So a disabled button IS a pending
   operation and gets a spinner.

   The one exception is a button disabled to express a permanent state rather
   than a wait (conversation.html, "Audio unavailable"). Add `.no-spinner` to
   any such button so it doesn't spin forever.

   The ring uses currentColor, so it works on red, gold and ghost buttons alike.
--------------------------------------------------------------------------- */
button:disabled{
  opacity:0.6;
  cursor:not-allowed;
}
button:disabled:not(.no-spinner)::before{
  content:'';
  display:inline-block;
  width:0.85em;
  height:0.85em;
  margin-right:0.55em;
  vertical-align:-0.1em;
  border:2px solid currentColor;
  border-right-color:transparent;
  border-radius:50%;
  animation:smk-spin 0.7s linear infinite;
}
@keyframes smk-spin{to{transform:rotate(360deg);}}

/* Reduced motion: keep the ring so the state is still legible, drop the spin. */
@media(prefers-reduced-motion:reduce){
  button:disabled:not(.no-spinner)::before{
    animation:none; border-right-color:currentColor; opacity:0.5;
  }
}

/* ---------------------------------------------------------------------------
   REDUCED MOTION
   The site has 25 animations, 11 of them infinite - including a 28s marquee
   ticker that never stops. Continuous motion is a vestibular trigger, and only
   the drawer and the loading spinner respected the preference before this.

   The blanket rule finishes every animation instantly rather than removing it,
   which is the standard pattern. But three animations needed handling by hand,
   because their END state is not their resting state - finishing them instantly
   would leave the element hidden or displaced.
--------------------------------------------------------------------------- */
@media(prefers-reduced-motion:reduce){
  *,*::before,*::after{
    animation-duration:0.01ms !important;
    animation-iteration-count:1 !important;
    transition-duration:0.01ms !important;
    scroll-behavior:auto !important;
  }

  /* The ticker ends at translateX(-50%), so finishing instantly would freeze it
     scrolled halfway off screen. Park it at the start instead. */
  .ticker-track{animation:none !important; transform:none !important;}

  /* These two do not decorate - they ARE how the element becomes visible, and
     both end at opacity:0. Finishing instantly would mean a reduced-motion user
     never sees the round result or the countdown at all. Both are hidden again
     by JS afterwards (the popup via a 5s timeout, the countdown per tick), so
     showing them statically is safe. */
  .round-popup.show{
    animation:none !important; opacity:1 !important;
    transform:translate(-50%,-50%) scale(1) !important;
  }
  .intro-countdown.pulse{
    animation:none !important; opacity:1 !important; transform:none !important;
  }

  /* Keep the loading ring visible as a static indicator. */
  button:disabled:not(.no-spinner)::before{
    animation:none !important; border-right-color:currentColor; opacity:0.5;
  }
}

/* ---------------------------------------------------------------------------
   INVALID FIELDS
   Errors were announced (role="alert") but the offending input itself carried
   no marking - no aria-invalid, no visual cue. On a form with six fields that
   leaves the person hunting for which one is wrong.
--------------------------------------------------------------------------- */
html body [aria-invalid="true"]{
  border-color:var(--flare-text) !important;
  box-shadow:0 0 0 3px rgba(225,6,0,0.18);
}
html body input[type=checkbox][aria-invalid="true"]{
  outline:2px solid var(--flare-text);
  outline-offset:3px;
  box-shadow:none;
}

/* ---------------------------------------------------------------------------
   TEAM AUTOCOMPLETE
   Matches the look Smack Chat already had: team name, league abbreviation
   right-aligned in mono. Now available on every team field on the site.
--------------------------------------------------------------------------- */
.smk-ac-wrap{position:relative;}
.smk-ac-list{
  position:absolute; left:0; right:0; top:100%; z-index:400;
  background:var(--ink-2); border:1px solid var(--line-strong); border-top:0;
  border-radius:0 0 4px 4px; max-height:340px; overflow-y:auto;
  box-shadow:0 12px 28px rgba(0,0,0,0.55);
}
.smk-ac-item{
  display:flex; justify-content:space-between; align-items:center; gap:12px;
  padding:12px 14px; min-height:44px; cursor:pointer;
  border-bottom:1px solid var(--line);
}
.smk-ac-item:last-child{border-bottom:0;}
.smk-ac-item.is-active{background:rgba(225,6,0,0.14);}
.smk-ac-name{font-size:14px; font-weight:600; color:var(--chalk);}
.smk-ac-league{
  font-family:'JetBrains Mono',monospace; font-size:10px; color:var(--chalk-dim);
  text-transform:uppercase; letter-spacing:0.5px; flex-shrink:0;
  text-align:right; max-width:42%; line-height:1.35;
}
.smk-ac-item.is-active .smk-ac-league{color:var(--chalk);}

/* The "+N more" footer on the team autocomplete. Not selectable - it exists
   to explain why the list stops, since a query like "new" legitimately
   matches sixteen teams. */
.smk-ac-more{
  padding:10px 14px; font-family:'JetBrains Mono',monospace; font-size:10px;
  color:var(--chalk-dim); text-transform:uppercase; letter-spacing:0.5px;
  text-align:center; border-top:1px solid var(--line-strong); cursor:default;
}


/* ============================================================
   SITE FRAME
   A red frame around every page, with a light travelling round it, plus red
   rules banding each page's hero image.

   Applied to `body` rather than a wrapper div on purpose: it reaches every
   template from one place, with no markup changes and no risk of unbalanced
   divs across a dozen files.
   ============================================================ */


/* SUPERSEDED (Andy, 26 Aug 2026) - the frame now lives ONLY on html::before,
   further down this file.

   This rule drew a 5px rounded frame on <body> with a 10px margin. It had
   already been switched off page by page (send_a_smack kills it outright),
   so by now the homepage was the only page still showing it - which is why
   the homepage had a thick rounded red frame while every other page had the
   thin square one, and why its content column measured 30px narrower than
   everything else (5px border + 10px margin, twice). The body margin also
   put any 100vw child 30px wider than its parent, which is where the
   homepage's horizontal scrollbar came from.

   Kept as a comment rather than deleted so nobody re-adds it: html::before
   is the frame, on every page, one rule. */
html body{
  position:relative;
}

/* The page-wide travelling light was removed - at full screen width it read
   as a laser circling the whole page rather than a detail on a card. The
   solid frame below is a real border, so it is unaffected. The generator
   card keeps its own smaller orbiting LED. */

/* The solid border underneath is a REAL border, not part of the gradient, so
   a browser without @property or mask-composite still shows the red frame -
   just without the travelling light. */


/* Hero banding. Targeted by CLASS rather than document position: every page
   nests its hero differently - some wrap it in a styled div, some sit
   directly under the nav, some sit behind a Jinja conditional - so a
   positional selector only ever matched one page. The class is applied to the
   hero element itself in each template, which also means the logo inside
   <nav> is never caught by accident.

   display:block matters on <picture>: it's an inline wrapper by default and
   won't take a border without it. */
html body .hero-band{
  display:block;
  border-top:4px solid #E10600;
  border-bottom:4px solid #E10600;
  line-height:0;
}
html body .hero-band img,
html body img.hero-band{display:block; width:100%; height:auto;}

/* ---------------------------------------------------------------------------
   Every image gets the red frame, automatically
   ---------------------------------------------------------------------------
   Rather than remembering to add a class each time, images are framed by
   default and the exceptions opt out. New images added to any page pick this
   up with nothing to remember.

   Scoped to images inside page CONTENT, not chrome - the nav, the footer and
   anything inside a button are excluded, because framing an icon looks like a
   mistake rather than a style.

   Full four-sided border here, unlike .hero-band which is a top-and-bottom
   band because it bleeds edge to edge. An inset image needs closing on all
   four sides or it reads as unfinished.
   ------------------------------------------------------------------------ */
html body img:not(.hero-band):not(.no-frame):not(nav img):not(footer img){
  border:3px solid var(--flare, #E10600);
  border-radius:6px;
  display:block;
  max-width:100%;
  height:auto;
}

/* Things that are furniture rather than pictures. A framed avatar or a framed
   icon looks broken, so anything that is clearly UI opts out by name. */
/* An image inside a .hero-band already has its band from the wrapper - a
   four-sided frame on top of it is a border inside a border. */
html body .hero-band img,
html body picture.hero-band img,
html body nav img,
html body footer img,
html body button img,
html body .no-frame,
html body .no-frame img,
html body img.judge-face,
html body img.smacky-waiting-img,
html body img.smacky-portrait,
html body img[src*="logo"],
html body img[src*="icon"],
html body img[src*="avatar"]{
  border:none;
  border-radius:0;
}

/* ---- Share sheet (desktop fallback for navigator.share) ---- */
#smkShareSheet{position:fixed; inset:0; z-index:9999; display:grid; place-items:center;}
.smk-share-scrim{position:absolute; inset:0; background:rgba(0,0,0,.72); backdrop-filter:blur(3px);}
.smk-share-panel{
  position:relative; background:#141414; border:2px solid #E10600;
  border-radius:12px; padding:22px; width:min(92vw,420px);
  box-shadow:0 0 40px rgba(225,6,0,.35);
}
.smk-share-title{
  font-family:'Oswald',sans-serif; font-size:20px; text-transform:uppercase;
  margin:0 0 16px; color:#F5F5F3; letter-spacing:.5px;
}
.smk-share-grid{display:flex; gap:10px; flex-wrap:wrap; margin-bottom:18px; justify-content:center;}
.smk-share-btn{
  width:52px; height:52px; border-radius:50%;
  display:grid; place-items:center;
  background:#1C1C1C; border:1px solid #2A2A2A; color:#9A9595;
  text-decoration:none; transition:transform .12s, background .12s, color .12s, border-color .12s;
}
.smk-share-btn svg{width:23px; height:23px; display:block;}
.smk-share-btn:hover{transform:translateY(-2px); color:#fff;}
/* Each mark takes its own brand colour on hover - recognition is the entire
   point of a logo, and a grid of identical grey circles wastes it. */
.smk-x:hover{background:#000; border-color:#000;}
.smk-facebook:hover{background:#1877F2; border-color:#1877F2;}
.smk-whatsapp:hover{background:#25D366; border-color:#25D366;}
.smk-reddit:hover{background:#FF4500; border-color:#FF4500;}
.smk-telegram:hover{background:#26A5E4; border-color:#26A5E4;}
.smk-sms:hover{background:#34C759; border-color:#34C759;}
.smk-email:hover{background:#E10600; border-color:#E10600;}
.smk-share-copy{display:flex; gap:8px; margin-bottom:14px;}
.smk-share-copy input{
  flex:1; min-width:0; background:#0D0D0D; border:1px solid #2A2A2A;
  color:#B5B0B0; padding:10px 12px; border-radius:7px; font-size:12px;
}
.smk-share-copy button{
  background:#E10600; border:none; color:#fff; padding:10px 16px;
  border-radius:7px; font-weight:700; font-size:12.5px; cursor:pointer;
}
.smk-share-dl{display:block; color:#E10600; font-size:12.5px; margin-bottom:12px; text-decoration:none;}
.smk-share-note{font-size:11.5px; color:#7A7575; line-height:1.5; margin:0 0 14px;}
.smk-share-close{
  width:100%; background:transparent; border:1px solid #2A2A2A; color:#B5B0B0;
  padding:10px; border-radius:7px; cursor:pointer; font-size:13px;
}
@media(max-width:420px){ .smk-share-btn{width:46px; height:46px;} .smk-share-btn svg{width:20px; height:20px;} }

/* ===========================================================================
   Site background - stadium floodlights, a bleeding SMACK, and film grain
   ===========================================================================
   Applied through body::before and body::after, so it lands on every page
   without touching a single template.

   Fixed to the VIEWPORT rather than the document. Anchored to the page it
   would scroll away and leave flat black below the fold, which on something
   like the Smack Board is most of what anybody actually sees.

   Both layers sit at z-index -1 with pointer-events off. That puts them
   behind all content automatically, with no need to raise anything else -
   forcing position:relative onto every child of body would break any
   layout currently relying on body as its containing block.

   The page colour lives on html rather than body, because a background
   colour on body would paint over a z-index -1 pseudo-element and hide the
   whole thing.
   ========================================================================= */

html{background-color:#0D0D0D;}

/* !important is doing real work here. Most pages set their own
   body{background:var(--ink)} in an inline <style> that loads AFTER this
   sheet, and a solid colour on body paints straight over a z-index -1
   pseudo-element - the whole background would simply not appear on any of
   them. The page colour moves to html above, so this looks identical. */
/* SITE-WIDE BODY FONT (David, 11 Aug 2026).
   Fourteen templates - index, smack_board, smack_feed, newsdesk, the
   smackcast pages and others - never set a body font-family of their own.
   Nothing here set one either, so on those pages body fell through to the
   browser default (a serif), and .nav-group-btn - which is deliberately
   font-family:inherit - rendered the nav dropdown labels in Times while
   pages like /login, which do set their own body font, showed Inter.
   Same markup, same nav CSS, two different-looking navs.

   Set once here. Any page with its own body rule still wins on source
   order, so nothing that already looked right changes. */
body{font-family:'Inter',sans-serif; -webkit-font-smoothing:antialiased;}

body{position:relative; background-color:transparent !important;}

/* Floodlights from off the top, drifting a few degrees, the red pool they
   cast, and the grain - all as stacked background layers on one element.
   Layered here rather than on separate divs so no template needs editing. */
body::before{
  content:"";
  position:fixed;
  inset:-25%;
  z-index:-1;
  pointer-events:none;
  background-image:
    url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='140' height='140'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85' numOctaves='3'/%3E%3C/filter%3E%3Crect width='140' height='140' filter='url(%23n)' opacity='0.05'/%3E%3C/svg%3E"),
    /* a second pool in the opposite corner, so the page is lit from both
       ends rather than falling away into nothing at the bottom */
    /* Both glows identical now - same ellipse, same opacity, same falloff -
       so the page is lit evenly from opposite corners. They were 55%/35%
       and 60%/30%, which read as one being larger than the other. */
    /* Positioned for the VIEWPORT, not for this element.
       
       The layer is inset:-25% so it can rotate without exposing the
       corners, which makes it 1.5x the screen in both directions. A glow
       "at 0% 0%" therefore sits a quarter of a screen ABOVE and LEFT of
       anything anybody can see - both glows were entirely off-screen, and
       the light visible at the top was the beam rather than the glow.
       
       The viewport's own corners fall at 16.67% and 83.33% of this
       element. Sizes are scaled by the same factor so they read the same
       as they would at 60% 30% of the screen. */
    radial-gradient(ellipse 40% 20% at 83.33% 83.33%, rgba(225,6,0,0.13), transparent 70%),
    radial-gradient(ellipse 40% 20% at 16.67% 16.67%, rgba(225,6,0,0.13), transparent 70%),
    /* a matching pair of beams thrown back up from off the bottom right,
       so the light comes from two directions the way a stadium is lit
       rather than from a single source overhead */
    conic-gradient(from 20deg at 108% 118%,
      transparent 0deg,
      rgba(225,6,0,0.070) 15deg,
      transparent 32deg,
      transparent 44deg,
      rgba(225,6,0,0.050) 60deg,
      transparent 77deg),
    /* the beams themselves, red rather than white */
    conic-gradient(from 202deg at 50% -22%,
      transparent 0deg,
      rgba(225,6,0,0.075) 16deg,
      transparent 34deg,
      transparent 46deg,
      rgba(225,6,0,0.055) 62deg,
      transparent 80deg);
  background-repeat:repeat, no-repeat, no-repeat, no-repeat, no-repeat;
}

/* The beams rotate a few degrees over twenty-six seconds - slow enough
   that nobody consciously notices, fast enough that the page never feels
   like a static image.

   The layer is oversized rather than inset:0, because rotating a
   viewport-sized box exposes the corners. -25% on every side covers a
   four degree swing with room to spare. */
@keyframes smk-beams{
  from{transform:rotate(-4deg);}
  to{transform:rotate(4deg);}
}
body::before{
  animation:smk-beams 26s ease-in-out infinite alternate;
  transform-origin:50% 0%;
}

/* The word, low left and mostly off the edge. Outline only - filled at this
   size it would fight every piece of content on the page. */
body::after{
  content:"SMACK";
  position:fixed;
  /* Sits fully inside the frame now rather than bleeding off - the S was
     running past the left edge and the word read as a fragment. */
  left:32px;
  bottom:24px;
  z-index:-1;
  pointer-events:none;
  font-family:'Oswald', Impact, sans-serif;
  font-size:109px;
  line-height:1;
  white-space:nowrap;
  color:transparent;
  -webkit-text-stroke:1px rgba(225,6,0,0.15);
}

/* 200px off a 390px screen is most of the viewport and stops reading as
   texture. */
/* The same word again on the right, so the page is anchored at both
   corners rather than weighted to one side.

   On html::after rather than a third layer on body - body's two
   pseudo-elements are already carrying the beams and the left word, and
   html's are free, which means no template anywhere needs a new div. */
html::after{
  content:"SMACK";
  position:fixed;
  right:32px;
  bottom:24px;
  z-index:-1;
  pointer-events:none;
  font-family:'Oswald', Impact, sans-serif;
  font-size:109px;
  line-height:1;
  white-space:nowrap;
  color:transparent;
  -webkit-text-stroke:1px rgba(225,6,0,0.15);
}

/* 109px off a 390px screen is most of the viewport and stops reading as
   texture. Both words shrink together. */
@media(max-width:720px){
  body::after{font-size:62px; left:18px; bottom:16px;}
  html::after{font-size:62px; right:18px; bottom:16px;}
}

/* Two words at 109px need about 570px between them. Below that they would
   collide in the middle, so the right one steps aside and the left one
   carries the page on its own. */
@media(max-width:900px) and (min-width:721px){
  html::after{display:none;}
}

/* And the admin panel gets neither.

   :has() rather than a descendant selector - html is the ANCESTOR of body,
   so "body.smk-plain html::after" selects nothing at all. This asks the
   root element whether it contains a plain body, which is the only way to
   reach upward. */
html:has(body.smk-plain)::after{display:none;}

/* Somebody who has asked their system not to animate things means it. */
@media (prefers-reduced-motion: reduce){
  body::before{animation:none;}
}

/* The admin panel gets none of it - a working tool, not a shopfront. */
body.smk-plain::before,
body.smk-plain::after{display:none;}


/* ---------------------------------------------------------------------------
   The price, as a stamp
   ---------------------------------------------------------------------------
   A dollar is the strongest single argument the site makes, and it was set in
   ordinary body copy everywhere it appeared. Comic treatment - red fill, hard
   black outline, a tilt, a slow pulse - so it reads as something slapped on
   rather than a sentence.

   Defined once here so it is identical on every page rather than duplicated
   into each template and drifting apart.
   ------------------------------------------------------------------------ */
.smk-price-stamp{
  display:inline-block;
  font-family:'Oswald', Impact, sans-serif;
  font-size:26px;
  line-height:1;
  letter-spacing:0.5px;
  /* The words are white and only the PRICE is red - the number is the
     argument, and colouring the whole phrase red made none of it stand out. */
  color:#FFFFFF;
  padding:4px 14px;
  /* Straight, not tilted. A rocking gentle pulse is enough motion - a
     permanently skewed block of type fights every straight line around it. */
  transform:none;
  animation:smk-price-pulse 2.4s ease-in-out infinite;
  /* Outline drawn with shadows rather than -webkit-text-stroke, which thins
     the letterforms from the inside and makes Anton look frail. */
  /* Outline drawn with shadows rather than -webkit-text-stroke, which thins
     the letterforms from the inside and makes Anton look frail. */
  text-shadow:
    -2px -2px 0 #0D0D0D,  2px -2px 0 #0D0D0D,
    -2px  2px 0 #0D0D0D,  2px  2px 0 #0D0D0D,
    -3px  0   0 #0D0D0D,  3px  0   0 #0D0D0D,
     0   -3px 0 #0D0D0D,  0    3px 0 #0D0D0D,
     4px  5px 0 rgba(13,13,13,0.55);
}

/* Only the amount carries colour. */
.smk-price-stamp .smk-price-amt{
  color:#E10600;
}

/* Dips to 55% rather than blinking out - a price that vanishes is unreadable
   half the time, which on a page somebody is reading is just irritating. */
@keyframes smk-price-pulse{
  0%,100%{opacity:1;    transform:scale(1);}
  50%    {opacity:0.62; transform:scale(0.975);}
}

@media (prefers-reduced-motion:reduce){
  .smk-price-stamp{animation:none;}
}

/* The homepage hero version. Everywhere else the stamp sits under a heading
   and supports it; here it IS the claim, so it carries the weight. */
.smk-price-hero{
  font-size:62px;
  letter-spacing:1px;
  padding:8px 22px;
  /* Still, and straight.
     
     At 62px the pulse was the largest moving thing on the page and it sat
     directly above three cards that are themselves animated - something had
     to stop moving, and the biggest element is the one that reads as
     restless rather than alive. */
  animation:none;
  transform:none;
  /* Thicker outline to match the larger type - a 3px edge that reads right
     at 26px looks like a hairline at 62px. */
  text-shadow:
    -3px -3px 0 #0D0D0D,  3px -3px 0 #0D0D0D,
    -3px  3px 0 #0D0D0D,  3px  3px 0 #0D0D0D,
    -5px  0   0 #0D0D0D,  5px  0   0 #0D0D0D,
     0   -5px 0 #0D0D0D,  0    5px 0 #0D0D0D,
     7px  9px 0 rgba(13,13,13,0.55);
}

@media(max-width:1024px){
  .smk-price-hero{font-size:48px;}
}
@media(max-width:640px){
  .smk-price-hero{font-size:34px; padding:6px 16px;}
}

@media(max-width:640px){
  .smk-price-stamp{font-size:20px;}
}


/* ---------------------------------------------------------------------------
   THE WORDMARKS.
   
   These three names are always coloured the same way, everywhere they
   appear - a brand that is two-tone on the homepage and flat white in the
   nav is not a brand, it is a homepage.
   
   Written once here rather than repeated in every template, so changing the
   red later is one edit rather than forty.
   
   Usage:
     <span class="wm-smackagram">Smack<i>agram</i></span>
     <span class="wm-locked">Locked &amp; Loaded</span>
     <span class="wm-price">$39<i>.99</i></span>
   
   The <i> carries no italics - it is just the shortest tag that survives
   being dropped inside a heading without changing the layout.
--------------------------------------------------------------------------- */
.wm-smackagram{color:var(--chalk); font-style:normal;}
.wm-smackagram i{color:var(--flare); font-style:normal;}

/* Locked & Loaded: silver words, RED AMPERSAND.
   The two words stay silver so the product reads as its own thing rather
   than more of the house red - but the & carries the flare, which is what
   ties it back to the brand. Same trick as Smackagram, one character
   instead of a whole word. */
.wm-locked{color:var(--silver); font-style:normal;}
.wm-locked i{color:var(--flare); font-style:normal;}

/* The decimals carry the price, so they carry the colour. */
.wm-price i{color:var(--flare); font-style:normal;}

/* =====================================================================
   OSWALD WEIGHT SYSTEM — phase two of the Anton -> Oswald rollout.
   Approved in the Font Design project 2026-08-10; applied same day.

   WHY THIS EXISTS: Anton shipped a single weight, so every font-weight
   declaration on display type was inert - the browser ignored it. Oswald
   honors weights, so phase one (family swap only) left display elements
   rendering at whatever weight happened to be written blind, or at
   browser defaults. This block sets the approved hierarchy.

   WHY "html body" PREFIXES: every template loads this sheet BEFORE its
   own inline <style>, so an appended rule of equal specificity loses on
   order. The prefix adds two element types of specificity, which beats
   the templates' class-level rules regardless of load order - without
   resorting to !important.
   ===================================================================== */

/* Nav wordmark (SMACKAGRAM). Two-tone: each half's stroke declared in
   its OWN color - a single stroke on the parent via currentColor would
   give the red AGRAM half a white outline. Stroke does not scale with
   font-size: value = font-size / 55. .brand is 25px -> 0.45px; the
   homepage's separate .logo implementation is 22px -> 0.4px. */
html body .brand{font-weight:700; letter-spacing:1.5px; -webkit-text-stroke:0.45px #F5F5F3;}
html body .brand span{-webkit-text-stroke:0.45px var(--flare, #E10600);}
html body .logo{font-weight:700; letter-spacing:1.5px; -webkit-text-stroke:0.4px #F5F5F3;}
html body .logo span{-webkit-text-stroke:0.4px var(--flare, #E10600);}

/* Hero / page-title h1s: 700 with open 3px tracking. The bare-h1 rule
   covers pages that style "h1" directly; the class-qualified variants
   (taken from the 2026-08-10 repo audit, not guessed) outrank each
   template's own class-level rule that declares its old tuned
   letter-spacing. Specialty display pieces (score numbers, prices,
   banner stamps like .sbb-title) are deliberately NOT here - they keep
   their own tuned metrics. */
html body h1,
html body .hero h1, html body .intro h1, html body .fsign h1,
html body .bh h1, html body .hd h1, html body .smc-head h1,
html body .oo-head h1, html body .sx-head h1,
html body .zone-title, html body .nd-title{font-weight:700; letter-spacing:3px;}

/* Card headers */
html body .card h2, html body .card h3, html body .home-card h3,
html body .verify-card h3, html body .zone-card h2{font-weight:600;}

/* Section / sidebar headers */
html body .section-title, html body .rail-h, html body .shelf-head,
html body .div-head h3, html body .home-divh h3{font-weight:500;}

/* Pull-quotes */
html body .best-line, html body .ds-quote, html body .sotw-headline{font-weight:500;}

/* =======================================================================
   HERO DIVIDER (Andy, 24 Aug 2026)
   Closes the hero on every page that has one, so there's a clear line
   between "hero section" and the rest of the page. Built first on
   /daily-smack, then rolled out sitewide per Andy: "add this divider to
   every page on my site that has a hero photo".

   Usage - one line, immediately after the page's hero block closes:
     <hr class="hero-divider">

   Full-bleed on purpose: an inset rule reads as a gap between two cards
   rather than a boundary between two parts of the page. It lives here
   rather than in each template's own <style> block so the weight and
   colour stay identical across pages and change in one place. Red, not
   ink - it reads as a deliberate brand rule instead of a table border.
   ======================================================================= */
html body .hero-divider{
  border:0; height:2px; width:100%; margin:26px 0 0; padding:0;
  background:var(--flare, #E10600); opacity:0.85;
}

/* Nav bottom edge (Andy, 24 Aug 2026): was a 1px warm grey (#c9c7c0).
   Red, at the same weight as .hero-divider above, so the nav closes the
   top of the hero the way the divider closes the bottom - the hero reads
   as one banded section on every page. Overridden here rather than edited
   into the nav{} rule at the top of this file so the change is one block
   and easy to lift back out. */
html body nav{border-bottom:2px solid var(--flare, #E10600);}

/* Nav background (Andy, 24 Aug 2026): was #faf8f2, the warm off-white used
   as a general surface tone all over the site. Andy wants the bar to match
   the pure white of the pricing cards on the home page, which are #ffffff -
   next to them the old tone read as slightly dirty. The dropdown panels
   (.nav-menu) were ALREADY #ffffff, so this also stops the bar and the menu
   that drops out of it being two different whites. The mobile drawer moves
   with it for the same reason. */
/* BLACK NAV SITEWIDE (Andy, 29 Aug 2026). The bar was #ffffff (and
   #F3EFEC in the block below), left over from the light-paper era; with the
   whole site back on black it was the one white band on every page. Bar,
   dropdown panels, hamburger and the mobile drawer all move together, and
   the wordmark's SMACK half flips to white so it still reads - AGRAM stays
   red, which is the only colour in the lockup that never changes. */
html body nav{background:#0D0D0D;}
html body .nav-drawer{background:#0D0D0D;}

/* =======================================================================
   PAGE FRAME (Andy, 24 Aug 2026)
   A red rule around the whole viewport - top, bottom and both sides - so
   every customer page is framed the way the hero already is. Flat, the
   same red as .hero-divider and the nav's bottom edge; deliberately NOT
   the old neon/glow treatment.

   On html::before because body::before, body::after and html::after are
   all already spoken for by the floodlights, the SMACK watermark and the
   grain. This was the last free slot on the two root elements, which is
   why the frame lives here rather than as a fifth layer somewhere.

   Fixed to the VIEWPORT, not the document, for the same reason the
   background layers are: anchored to the page it would scroll away and
   only frame the first screenful. pointer-events:none so it can never
   swallow a click on anything underneath, and a z-index above the
   highest overlay in the app (12000, send_a_smack's sample player) so
   the frame stays unbroken even with a modal open.
   ======================================================================= */
html::before{
  content:"";
  position:fixed;
  inset:0;
  border:2px solid var(--flare, #E10600);
  pointer-events:none;
  z-index:12001;
}

/* NO FRAME ON PHONES (Andy, 30 Aug 2026: "when I scroll, the border cuts
   across the page on top and bottom" - seen on the payment-confirmed page).
   -------------------------------------------------------------------------
   Not a bug in this rule so much as a fact about iOS: a position:fixed
   element is sized to the LAYOUT viewport, which stays tall while Safari's
   URL bar collapses. The visible area shrinks and grows around it, so the
   frame's top and bottom edges travel across the content as you scroll -
   exactly the two lines cutting the page.
   Switching to 100dvh would track the visible viewport, but it repaints on
   every scroll frame and visibly jumps at the moment the bar collapses. The
   frame is a desktop flourish - a 2px keyline 8px from the edge of a phone
   reads as a rendering artefact even when it holds still - so phones simply
   do not draw it. Desktop is untouched. */
@media (max-width:767px){
  html::before{ display:none; }
}

/* Same opt-out the background layers use - the admin panel is a working
   tool, not a shopfront, so it gets no frame either. :has() because html
   is the ANCESTOR of body and cannot be reached with a descendant
   selector. */
html:has(body.smk-plain)::before{display:none;}

/* =======================================================================
   NAV WORDMARK + LINK SIZE (Andy, 24 Aug 2026)
   =======================================================================
   THE WORDMARK. The home page's treatment is now the sitewide one: Anton
   at 30px, weight 400, no tracking and no stroke. Everywhere else it was
   Oswald 25px with 1.5px tracking and a 0.45px #F5F5F3 stroke - that
   stroke dates from when the nav was DARK and the wordmark needed a light
   edge to separate from it. On the white bar it was quietly lightening
   and thinning the letterforms, which is a large part of why the logo
   read differently off the home page. Both are explicitly reset below
   rather than left to be overridden, because the earlier rules in this
   file carry the same "html body .brand" specificity and would otherwise
   win or lose on source order alone.

   Anton is @imported at the top of this file - without it, the 36
   customer templates that never linked Anton would fall back to Impact.

   THE LINKS. 14px was small for a bar this wide; 16px across the nav
   links, the dropdown buttons and the auth links on the right. The caret
   goes up with them so it stays in proportion.
   ======================================================================= */
html body .brand{
  font-family:'Anton', Impact, sans-serif;
  font-weight:400;
  font-size:30px;
  letter-spacing:0;
  -webkit-text-stroke:0;
  color:#101114;
}
html body .brand span{
  color:var(--flare, #E10600);
  -webkit-text-stroke:0;
}
@media(max-width:520px){
  html body .brand{font-size:25px;}
}

html body .nav-links,
html body .nav-group-btn,
html body .auth-links{font-size:16px;}
html body .nav-caret{font-size:11px;}

/* =======================================================================
   FOOTER: white, with a red top edge (Andy, 24 Aug 2026)
   =======================================================================
   Matches the nav - white bar, 2px red rule - so the page is bookended by
   the same treatment top and bottom.

   Scoped "html body footer" (0,0,3) on purpose. Sixteen templates declare
   their own bare "footer{...}" block with its own background and a 1px
   hairline border-top; a bare element selector is (0,0,1) and loses to
   this, so all sixteen come along without being edited one by one. Sits
   with the existing "html body footer" layout rules higher up this file,
   which is where footer chrome is meant to be decided.

   _footer.html itself is untouched - this is colour, not markup.
   ======================================================================= */
html body footer{
  background:#ffffff;
  border-top:2px solid var(--flare, #E10600);
}


/* =======================================================================
   ONE NAV, ONE TICKER (Andy, 26 Aug 2026)
   =======================================================================
   The nav markup was already shared (_nav.html) but every page restyled
   it, and each page had built its OWN ticker - 34px/36px/50px tall, in
   Oswald 14px or 16px or Barlow 24px, on three different reds. Clicking
   between pages, the top of the site changed shape every time.

   This block is the HOME PAGE's bar, promoted to the shared stylesheet so
   every template inherits it. Values are lifted straight from what the
   homepage computes: nav 91px on #F3EFEC with a 3px red rule, Anton
   wordmark, Barlow Condensed 17px uppercase links; ticker 50px of solid
   red, Barlow Condensed 24px/700 white at .055em.

   Selectors carry `html body` so they beat both the base nav rules higher
   up this file and the page-level rules that load after it. Page ticker
   classes are listed by name because each page built its own element -
   the markup is unchanged, only the styling is now shared.
   ======================================================================= */

html body nav{
  display:flex; align-items:center; gap:26px;
  min-height:91px; height:auto; flex-wrap:wrap; row-gap:0;
  padding:0 39px;
  background:#0D0D0D;
  border-bottom:3px solid #E10600;
  position:relative; z-index:40;
}
html body nav .brand{
  font-family:'Anton', Impact, sans-serif; font-weight:400;
  font-size:clamp(30px, 3.1vw, 52px);
  line-height:.9; letter-spacing:0; color:#FFFFFF; text-decoration:none;
  -webkit-text-stroke:0;
}
html body nav .brand span{ color:#E10600; -webkit-text-stroke:0; }

html body nav .nav-links{
  /* display stays with the base rules - flex above 1180px, none below,
     where the drawer takes over. Declaring it here breaks the mobile hide. */
  align-items:center; gap:clamp(14px, 1.7vw, 40px); margin-inline:auto;
}
html body nav .nav-links > a,
html body nav .nav-group-btn,
html body nav .auth-links a{
  font-family:'Barlow Condensed','Arial Narrow',sans-serif;
  font-size:17px; font-weight:700; letter-spacing:.035em;
  text-transform:uppercase; color:#FFFFFF !important;
  background:none; border:0; cursor:pointer; text-decoration:none;
  white-space:nowrap;
}
html body nav .nav-links > a,
html body nav .nav-group-btn{ padding:10px 0; }
html body nav .nav-links > a:hover,
html body nav .nav-group-btn:hover,
html body nav .auth-links a:hover{ color:#E10600 !important; }
html body nav .auth-links{ align-items:center; gap:22px; }
html body nav .auth-links a[href="/register"]{
  background:#E10600; color:#fff !important;
  min-width:119px; min-height:44px; display:inline-flex; align-items:center;
  justify-content:center; padding:0 20px; border-radius:2px;
}
html body nav .auth-links a[href="/register"]:hover{ background:#B80500; }
html body nav .nav-menu{
  background:#141416; border:2px solid #E10600; border-radius:2px;
}
html body nav .nav-menu a{
  color:#FFFFFF !important;
  font-family:'Barlow Condensed','Arial Narrow',sans-serif;
  text-transform:uppercase; font-size:16px; font-weight:700;
}
html body nav .nav-menu a:hover{ color:#E10600 !important; }
html body .nav-toggle span{ background:#FFFFFF; }
html body nav .nav-caret{ font-size:11px; }

/* The same steps the homepage already used, so every page tightens at
   exactly the same widths. Between the drawer breakpoint and full desktop
   the link set is wide, so the type steps down before anything collides. */
@media (max-width:1500px) and (min-width:1181px){
  html body nav .nav-links > a,
  html body nav .nav-group-btn,
  html body nav .auth-links a{ font-size:16px; letter-spacing:.03em; }
  html body nav .brand{ font-size:34px; }
}
@media (max-width:1439px){
  html body nav{ padding-inline:32px; }
}
@media (max-width:767px){
  html body nav{ min-height:68px; padding-inline:20px; }
  html body nav .brand{ font-size:36px; }
}

/* ------------------------------- THE TICKER ------------------------------ */
/* Every page's own ticker element, styled as one component. */
html body .v3-ticker,
html body .sc-ticker,
html body .sl-ticker,
html body .sb2-ticker,
html body .sas-ticker,
html body .ct-ticker,
html body .pr-ticker,
html body .ds-ticker,
html body .mk-ticker,
html body .sf-ticker,
html body .jt-ticker,
html body .sb-ticker{
  height:50px; min-height:50px;
  background:#E10600; color:#fff;
  overflow:hidden; display:flex; align-items:center;
  position:relative; z-index:10;
  border-top:0; border-bottom:0; margin:0;
}
html body .v3-ticker-track > *,
html body .sc-ticker-track > *,
html body .sl-ticker-track > *,
html body .sb2-ticker-track > *,
html body .sas-ticker-track > *,
html body .ct-ticker-track > *,
html body .pr-ticker-track > *,
html body .ds-ticker-track > *,
html body .mk-ticker-track > *,
html body .sf-ticker-track > *,
html body .jt-ticker-track > *,
html body .sb-ticker-track > *{ margin-right:34px; flex:none; }

html body .v3-tk-item,
html body .sc-tk,
html body .sl-tk,
html body .sb2-tk,
html body .sas-tk,
html body .ct-tk,
html body .pr-tk,
html body .ds-tk,
html body .mk-tk,
html body .sf-tk,
html body .jt-tk,
html body .sb-tk{
  font-family:'Barlow Condensed','Arial Narrow',sans-serif;
  font-size:24px; font-weight:700; letter-spacing:.055em;
  text-transform:uppercase; color:#fff;
}
html body .v3-tk-item em,
html body .sc-tk em, html body .sl-tk em, html body .sb2-tk em,
html body .sas-tk em, html body .ct-tk em, html body .pr-tk em,
html body .ds-tk em, html body .mk-tk em, html body .sf-tk em,
html body .sb-tk em{ font-style:normal; opacity:.92; }

html body .v3-tk-bolt,
html body .sc-tk-bolt, html body .sl-tk-bolt, html body .sb2-tk-bolt,
html body .sas-tk-bolt, html body .ct-tk-bolt, html body .pr-tk-bolt,
html body .ds-tk-bolt, html body .mk-tk-bolt, html body .sf-tk-bolt,
html body .sb-tk-bolt{ width:17px; height:17px; flex:none; }


/* =========================================================================
   THE ONE HERO - sitewide (Andy, 26 Aug 2026)
   =========================================================================
   Lifted verbatim from the homepage v6 hero and de-scoped: every rule below
   is the SAME declaration block that ships on the homepage, with the
   `body.home-v3` prefix removed so every page gets it.

   The homepage keeps its own prefixed copy in homepage-sports.css, which is
   more specific and loads after this file, so the homepage is byte-for-byte
   unchanged by this block - it just no longer has the design to itself.

   Markup comes from templates/_hero_v6.html. Per-page copy is passed in;
   nothing about the shell varies.
   ========================================================================= */
.v6-hero{
  position:relative;
  width:100%;
  height:650px; min-height:650px; max-height:650px;
  box-sizing:border-box;
  margin:0;
  overflow:hidden;
  background:#050505;
  border:0; border-bottom:3px solid #E10600; border-radius:0;
}

/* ---- artwork layer: one image, swap the src and nothing else changes ---- */
.v6-hero .v6-art{
  position:absolute; right:0; bottom:0; top:0;
  width:100%; pointer-events:none; z-index:3;
}
.v6-hero .v6-art picture{
  position:absolute; right:0; bottom:0; display:block;
  height:100%;
}
.v6-hero .v6-art-img{
  display:block;
  height:100%; width:auto; max-width:none;
  object-fit:contain; object-position:right bottom;
}

/* ---- the last of the fade, over the artwork's own baked-in one ---- */
.v6-hero .v6-fade{
  position:absolute; inset:0; z-index:4; pointer-events:none;
  background:linear-gradient(90deg,
    #050505 0%, #050505 46%, rgba(5,5,5,.98) 52%, rgba(5,5,5,.82) 59%,
    rgba(5,5,5,.35) 70%, rgba(5,5,5,.08) 100%);
}

/* ---- copy ---- */
.v6-hero .v6-copy{
  position:absolute; z-index:6;
  /* Andy, 26 Aug: moved 15% of the way from its old 7.5vw toward the hero's
     centre line. */
  left:14vw;
  /* Vertically CENTRED rather than pinned at top:62px. With the top pinned,
     every line-height change ate the space under the button - at 1920 with
     the new headline spacing only 22px would have been left. Centred, the
     block rebalances itself whatever the headline does. */
  top:50%; transform:translateY(-50%);
  width:min(750px, 52vw); max-width:none;
  text-align:left;
}
.v6-hero .v6-red{ color:#E10600; }

/* Matched to the DAILY SMACK / NEW EVERY MORNING eyebrow further down the
   page (Andy, 26 Aug). Read off that element's computed style rather than
   guessed: Barlow Condensed 18px / 700 / .055em / 27px, uppercase, #E10600,
   flex with a 12px gap. The only thing that differs now is the LED, which is
   this hero's own. */
.v6-hero .v6-eyebrow{
  font-family:'Barlow Condensed','Roboto Condensed','Arial Narrow',sans-serif;
  font-size:18px; font-weight:700; line-height:27px; letter-spacing:.055em;
  text-transform:uppercase; color:#E10600;
  margin:0 0 19px;
  display:flex; align-items:center; gap:12px;
}
.v6-hero .v6-eyebrow .v6-sep{ margin:0; font-style:normal; font-weight:700; }

/* ---- LIVE-LINE LED (Andy, 26 Aug) ----
   A call-waiting indicator, not a decoration: a lit red core with a halo
   that breathes out and fades, on a slow 1.6s cycle so it reads as "the
   line is open" rather than as an alert. The halo is a box-shadow, so it
   costs no layout and cannot shift the text beside it. */
.v6-hero .v6-dot{
  width:11px; height:11px; flex:none; border-radius:50%;
  background:#E10600;
  box-shadow:0 0 0 0 rgba(225,6,0,.55), 0 0 8px 2px rgba(225,6,0,.75);
  animation:v6led 1.6s ease-in-out infinite;
}
@keyframes v6led{
  0%   { opacity:1;   box-shadow:0 0 0 0    rgba(225,6,0,.55), 0 0 8px 2px rgba(225,6,0,.75); }
  55%  { opacity:.28; box-shadow:0 0 0 7px  rgba(225,6,0,0),   0 0 4px 1px rgba(225,6,0,.25); }
  100% { opacity:1;   box-shadow:0 0 0 0    rgba(225,6,0,.55), 0 0 8px 2px rgba(225,6,0,.75); }
}
/* Anyone who has asked the OS to stop animation gets the lit state, held. */
@media (prefers-reduced-motion:reduce){
  .v6-hero .v6-dot{ animation:none; opacity:1; }
}

.v6-hero .v6-h1{
  font-family:'Anton', Impact, 'Arial Narrow', sans-serif;
  font-size:clamp(70px, 4.65vw, 92px);
  font-weight:400;              /* Anton's native weight - never embolden */
  /* 1.02, up from the spec's .88 (Andy, 26 Aug): at .88 these three heavy
     uppercase lines read as one solid block with the caps almost touching. */
  line-height:1.02; letter-spacing:-.018em;
  text-transform:uppercase; color:#F5F2EC;
  margin:0;
  white-space:nowrap;           /* the three supplied breaks, and only those */
  -webkit-text-stroke:0; text-shadow:none;
}

.v6-hero .v6-line{
  font-family:'Barlow Condensed','Roboto Condensed','Arial Narrow',sans-serif;
  font-size:28px; font-weight:900; line-height:1; letter-spacing:.025em;
  text-transform:uppercase; color:#F5F2EC;
  margin:22px 0 14px;
}

.v6-hero .v6-desc{
  font-family:'Inter', Arial, sans-serif;
  font-size:20px; font-weight:500; line-height:1.48; letter-spacing:-.01em;
  color:#D2CFCA; margin:0;
  /* The spec asks for BOTH max-width:570px and a three-line wrap. At 20px
     Inter those fight: measured, 550px and up gives two lines and 530px is
     the widest that still breaks into the three specified lines. The wrap
     was the stated intent, so the measure follows it. */
  max-width:530px;
}

/* ---- the one CTA ---- */
.v6-hero .v6-cta{
  display:flex; align-items:center;
  width:440px; height:82px; margin:21px 0 0;
  padding:10px 20px 10px 16px;
  background:linear-gradient(180deg,#E5160C 0%,#C90B05 100%);
  border:1px solid #F23830; border-radius:5px;
  cursor:pointer; text-align:left;
  box-shadow:0 10px 26px rgba(225,6,0,.18), inset 0 1px 0 rgba(255,255,255,.16);
  transition:background 160ms ease, transform 160ms ease, box-shadow 160ms ease;
}
.v6-hero .v6-cta:hover{
  background:#F0180F; transform:translateY(-1px);
  box-shadow:0 14px 30px rgba(225,6,0,.24), inset 0 1px 0 rgba(255,255,255,.16);
}
.v6-hero .v6-cta:active{
  transform:translateY(0);
  box-shadow:0 6px 18px rgba(225,6,0,.16), inset 0 1px 0 rgba(255,255,255,.16);
}
.v6-hero .v6-cta:focus-visible{
  outline:3px solid #F5F2EC; outline-offset:3px;
}
.v6-hero .v6-cta-disc{
  width:58px; height:58px; flex-shrink:0; border-radius:50%;
  background:#F5F2EC; color:#E10600; margin-right:20px;
  border:1.5px solid #0B0B0B;   /* thin black keyline (Andy, 26 Aug) */
  box-sizing:border-box;
  display:inline-flex; align-items:center; justify-content:center;
}
.v6-hero .v6-cta-disc svg{ width:20px; height:20px; }
/* optical centring: a triangle looks left-heavy dead centre */
.v6-hero .v6-cta .v3-ic-play{ margin-left:2px; }
.v6-hero .v6-cta .v3-ic-pause{ display:none; }
/* the box never changes size between states - only the glyph does */
.v6-hero .v6-cta.is-playing .v3-ic-play{ display:none; }
.v6-hero .v6-cta.is-playing .v3-ic-pause{ display:block; margin-left:0; }
.v6-hero .v6-cta-txt{ display:flex; flex-direction:column; min-width:0; }
.v6-hero .v6-cta-main{
  font-family:'Barlow Condensed','Roboto Condensed','Arial Narrow',sans-serif;
  font-size:27px; font-weight:800; line-height:1; letter-spacing:.015em;
  color:#0B0B0B; text-transform:uppercase; white-space:nowrap;
}
.v6-hero .v6-cta-sub{
  font-family:'Barlow Condensed','Roboto Condensed','Arial Narrow',sans-serif;
  font-size:16px; font-weight:700; line-height:1; letter-spacing:.12em;
  color:#0B0B0B; text-transform:uppercase;
  margin-top:8px; white-space:nowrap;
}
.v6-hero .v3-audio-error{ color:#F5F2EC; margin:10px 0 0; }

/* ---- narrow desktop ----
   Measured, not guessed. Anton is condensed, so the headline's real INK is
   only 503px wide at its 70px floor - far narrower than its 750px box. The
   artwork therefore stays full height all the way down to 1320px with 49px
   of clearance to spare. Only below that does Smacky's pointing hand start
   to reach the text, and 94% is what buys the gap back. */
@media (max-width:1399px){
  .v6-hero .v6-art picture{ height:93%; }
}
@media (max-width:1319px){
  .v6-hero .v6-art picture{ height:90%; }
  .v6-hero .v6-copy{ left:10vw; }
}

/* ---- below the desktop breakpoint the fixed band is released ---- */
@media (max-width:1023px){
  .v6-hero{
    height:auto; min-height:0; max-height:none;
    padding:38px 0 0;
  }
  .v6-hero .v6-copy{
    position:static; width:auto; padding:0 24px 26px;
    left:auto; top:auto; transform:none;
  }
  .v6-hero .v6-h1{ white-space:normal; font-size:clamp(38px,7vw,70px); }
  .v6-hero .v6-art{ position:relative; height:340px; width:100%; }
  .v6-hero .v6-art picture{ height:100%; }
  .v6-hero .v6-fade{ display:none; }
  .v6-hero .v6-cta{ width:100%; max-width:440px; }
}


/* ---- shared-hero extras, not on the homepage ----------------------------
   The pages that had their own hero audio player each register it through
   window.smkRegisterPlayer, and every one of those registrations BAILS OUT
   if its waveform element is missing:

       if (!audio || !btn || !wave || ...) return;

   This hero has no waveform, so the element is kept in the DOM and hidden.
   Removing it would silently kill play/pause on five pages. */
.v6-hero .v6-wave-hidden{ display:none !important; }

/* link version of the CTA, for the heroes whose call to action is a link
   rather than a player. Same box, same type - only the disc's glyph. */
.v6-hero .v6-cta--link{
  text-decoration:none;
}
.v6-hero .v6-cta--link .v6-cta-disc{
  font-family:'Barlow Condensed','Roboto Condensed','Arial Narrow',sans-serif;
  font-size:30px; font-weight:800; line-height:1;
}
.v6-hero .v6-cta--nosub .v6-cta-main{ font-size:29px; }

/* MEASURED: the label box inside the 440px button is 324px and the main line
   "HEAR IT FROM SMACKY" is 327px of ink - 3px over, on the homepage too, and
   invisible. Only the SUB line is guarded, because a longer product name
   there ran a long way past the red. The main line is left exactly as the
   homepage has it. */
.v6-hero .v6-cta-sub{ overflow:hidden; text-overflow:ellipsis; }

/* a hero with no eyebrow LED (the pages whose kicker is not a live state) */
.v6-hero .v6-eyebrow--nodot .v6-dot{ display:none; }


/* ---- centred body variant (Andy, 26 Aug 2026) --------------------------
   Centres the paragraph and the CTA UNDER THE HEADLINE, not inside the copy
   column. The column is a flat min(750px, 52vw) box and the headline's ink
   is narrower than that, so centring inside the box would sit them off the
   headline's own centre line. width:fit-content shrinks the box to its
   widest child - the nowrap headline - and then auto margins are exact.
   The eyebrow and the headline stay left, as asked. */
.v6-hero .v6-copy--centerbody{
  width:fit-content;
  max-width:min(750px, 52vw);
}
.v6-hero .v6-copy--centerbody .v6-desc{
  text-align:center; margin-left:auto; margin-right:auto;
}
/* The bold one-liner too (Andy, 28 Aug 2026: "center align everything in its
   current position"). It was the ONE child of the centred copy block still
   left-aligned, which is why Send a Smack still read as off-centre after the
   26 Aug pass. Send a Smack is the only page that both centres its body and
   passes h_line, so this rule changes nothing anywhere else. */
.v6-hero .v6-copy--centerbody .v6-line{
  text-align:center; margin-left:auto; margin-right:auto;
}
.v6-hero .v6-copy--centerbody .v6-cta{
  margin-left:auto; margin-right:auto;
}
.v6-hero .v6-copy--centerbody .v3-audio-error{ text-align:center; }


/* -------------------------------------------------------------------------
   HERO ARTWORK: cover the band, don't hang off the right edge
   (Andy, 26 Aug 2026)
   -------------------------------------------------------------------------
   WHY THE ZOOM BROKE IT. The plate was an <img> sized by the band's HEIGHT
   (height:100%, width:auto) and pinned to the RIGHT edge. The copy is
   positioned in vw. So the two had nothing to do with each other, and the
   distance between the headline and Smacky swung wildly with the window -
   which is exactly what browser zoom changes. MEASURED, subject's left edge
   against the headline's right edge:

       2200px    347px of empty black between them
       1920px    135px
       1661px     10px
       1440px   -124px   <- the headline runs INTO him
       1280px   -180px

   Zoom out, gap. Zoom in, collision. Both are the same bug.

   The plates are full-bleed compositions now, faded in the file, so they are
   treated as one: the art fills the band and the subject holds its position
   in the frame at every width. 1866x843 over a 650px band is 2.214 against
   2.215 at 1440 - the plate and the band are the same shape, so at Andy's
   size nothing is cropped at all; wider windows trim top and bottom evenly.
   ------------------------------------------------------------------------- */
.v6-hero .v6-art{ position:absolute; inset:0; width:100%; }
.v6-hero .v6-art picture{
  position:absolute; inset:0;
  width:100%; height:100%;
}
.v6-hero .v6-art-img{
  width:100%; height:100%;
  max-width:none;
  object-fit:cover; object-position:center center;
}
/* the two narrow-desktop art rules existed to buy clearance from Smacky's
   pointing hand. Cover makes them meaningless - the subject no longer moves
   relative to the copy. */
@media (max-width:1399px){ .v6-hero .v6-art picture{ height:100%; } }
@media (max-width:1319px){ .v6-hero .v6-art picture{ height:100%; } }
@media (max-width:1023px){
  .v6-hero .v6-art{ position:relative; inset:auto; height:340px; }
  .v6-hero .v6-art picture{ position:absolute; inset:0; height:100%; }
}


/* ---- headline keeps scaling below 1400 ---------------------------------
   MEASURED off the plate itself, not guessed: it is pure black (luma 0) out
   to 36% of its width and the subject's bright edge starts at 52%. With the
   art covering the band, that edge sits at a FIXED 52% of the band at every
   width - which is the whole point of the change above.

   The headline did not hold up its end. Its clamp floors at 70px, so below
   about 1400 it stopped shrinking while the band kept narrowing, and its ink
   walked into that 52% line. Letting it keep scaling under 1400 restores the
   clearance without touching Andy's own size at 1440 and up. */
@media (max-width:1399px){
  .v6-hero .v6-h1{ font-size:clamp(48px, 5.2vw, 70px); }
}


/* ---- copy moves in as the band narrows ---------------------------------
   MEASURED per page against the subject's 52% line. With the art covering
   the band, home / Smack Lab / Smack Battle clear at every width, but the
   two longest headlines did not:

                     1920   1661   1440   1366   1280
       SmackCast      +16    +15    -14    -40     -1
       Send a Smack    -7     -7    -34    -60    -21

   Their headlines are two long lines rather than three short ones, so their
   ink runs further right at the same type size. Rather than shrink the type
   - which would change the homepage at Andy's own 1661 - the copy moves
   toward the left edge once the band drops under 1500. That buys 5vw, which
   is 72px at 1440 and 68px at 1366, and clears every page. Nothing above
   1500 moves at all. */
@media (max-width:1499px){
  .v6-hero .v6-copy{ left:9vw; }
}


/* -------------------------------------------------------------------------
   SMACKCAST HERO - vertical balance for the longer paragraph
   (Andy, 27 Aug 2026)
   -------------------------------------------------------------------------
   The new description runs 5 lines where the old one ran 4, so the copy
   block grew inside a band that is still a literal 650px. Measured before:
   87px above the block and 90px below the button at 1440 - the block was
   centred, but everything felt crowded together.

   The kicker and the headline lift, and the button drops away from the
   paragraph, so the block uses the band instead of sitting in the middle of
   it. Scoped to this page: the shared shell is untouched.
   ------------------------------------------------------------------------- */
body.page-smackcast-product .v6-hero .v6-copy{
  transform:translateY(calc(-50% - 26px));
}
body.page-smackcast-product .v6-hero .v6-cta{
  margin-top:40px;
}


/* ---- paragraph measure narrows with the band (Andy, 27 Aug 2026) --------
   MEASURED, paragraph's right edge against the plate's 52% subject line, on
   every page:

              1440   1280   1200   1100   1024
     most      +89    +23     -9    -50    -82
     meet      +49    -17    -49    -74   -106

   The measure was a flat 530px while the copy's left edge is 9vw and the
   subject sits at vw/2 + 29 - so below about 1250 the paragraph walked into
   the artwork on EVERY page. A fluid cap tracks it instead: 530 is still the
   measure everywhere it fits, and under ~1360 it follows the band. */
.v6-hero .v6-desc{
  max-width:min(530px, 39vw);
}


/* ---- 4px back from the disc's gutter (Andy, 27 Aug 2026) ----------------
   MEASURED: the label box inside the 440px button is 324px and the homepage's
   sub line is 327px of ink, so the ellipsis guard was clipping it to
   "HOW SMACKAGRAM WORKS - 0:4...". Trimming the disc's right margin from 20
   to 16 gives the box 328px. The button, the disc and the type are all
   unchanged - only the gutter between them. */
.v6-hero .v6-cta-disc{ margin-right:16px; }


/* A sentence that must not be split across lines. Used on the homepage hero
   so "Every loss deserves a RING." always lands whole on the last line
   instead of breaking after "deserves". MEASURED at 20px Inter it is 251px
   of ink against a 530-600px measure, so it always fits on one line - and
   because it cannot break, it is pushed down to a line of its own. */
.v6-hero .v6-nobreak{ white-space:nowrap; }


/* ---- headline lines centred on each other (Andy, 27 Aug 2026) -----------
   SEPARATE from h_center_body on purpose. SmackCast already uses
   center_body and its headline is deliberately left - centring it there
   without being asked would change a page that is signed off. This flag
   only fires where it is set.

   Pairs with .v6-copy--centerbody, which shrinks the copy box to the
   headline's widest line, so "centred" means centred on THAT line and the
   block does not move. */
.v6-hero .v6-copy--centertitle .v6-h1{ text-align:center; }
.v6-hero .v6-copy--centertitle .v6-eyebrow{ justify-content:center; }


/* ---- HERO PARAGRAPH NEVER RUNS WIDER THAN THE HEADLINE
   (Andy, 28 Aug 2026: "adjust every hero section so the descriptions are set
   like this where they dont go beyond the header text") -------------------
   MEASURED FIRST. The paragraph's box against the headline's INK, per page:

                   1280        1440        1920
     smackcast     +47         +78         -53
     daily         +56         +87         -42
     lab           +68         +76         -49
     battle        +58         +66         -62
     meet          +89         +99         -20
     send a smack  +43         +16        -134

   So on every page, at the two widths most people are on, the paragraph was
   40-100px WIDER than the headline above it - which is exactly what stops a
   centred hero reading as one block. It only came in under at 1920 because
   the headline is clamp()ed to vw and grows past it there.

   THE FIX IS THE `width:0; min-width:100%` PAIR, and it is not a hack for its
   own sake. `.v6-copy--centerbody` is `width:fit-content`, so the column
   sizes to its widest child - and the paragraph, with a 530px max-width and a
   long max-content, WAS that child on most pages. `width:0` drops its
   contribution to the column's intrinsic width, so the column sizes to the
   nowrap headline alone; `min-width:100%` then expands the paragraph back out
   to whatever that resolved column is. Net effect: the measure IS the
   headline's width, at every viewport, with no per-page numbers to maintain
   and nothing to re-measure when a headline changes.

   18px matches the homepage, which is the hero Andy pointed at. It is also
   what makes the narrower measure affordable: a shorter measure means more
   lines, and 18px gives back more height than the extra lines cost.

   The eyebrow is deliberately untouched - it is a status line, not part of
   the centred block. */
.v6-hero .v6-copy--centerbody .v6-desc{
  width:0;
  min-width:100%;
  max-width:100%;
  font-size:18px;
  margin-left:auto; margin-right:auto;
  /* MEASURED: the homepage puts 20px between the headline and the paragraph;
     every shell page had ZERO - the two blocks were touching, which is most
     of why they read as cramped next to the homepage. Same 20px here. There
     is room for it: the button clears the bottom of the band by 75-123px on
     every page after this change, against 31-66px before it. */
  margin-top:20px;
}

/* ---------------------------------------------------------------------------
   THE SCROLLBAR IS BRAND RED (Andy, 29 Aug 2026: "there's a grey scrolling
   bar going up and down the screen - make that red, on every page, for
   desktop"). This file is on every desktop page, so this is the one place
   to say it. Both syntaxes on purpose: `scrollbar-color` is what Firefox
   honours, `::-webkit-scrollbar-*` is what Chrome, Safari and Edge honour -
   and setting the webkit ones opts the page OUT of Chrome's overlay
   scrollbar, which is why the track gets an explicit near-black instead of
   inheriting grey. Phones keep their overlay scrollbars; these rules only
   change bars that are drawn, and mobile draws none.
--------------------------------------------------------------------------- */
html{ scrollbar-color:#E10600 #0A0A0B; }
::-webkit-scrollbar{ width:13px; height:13px; }
::-webkit-scrollbar-track{ background:#0A0A0B; }
::-webkit-scrollbar-thumb{
  background:#E10600; border-radius:7px;
  border:3px solid #0A0A0B;             /* inset look; the track shows through */
}
::-webkit-scrollbar-thumb:hover{ background:#FF3A30; }
::-webkit-scrollbar-corner{ background:#0A0A0B; }
