/*
Theme Name:   Oax Sport
Theme URI:    https://oaxsport.org/
Description:  Child theme of eStar. Carries the Oax Sport design system into the header,
              footer, sidebar and post layout, so the redesigned page bodies stop sitting
              inside an un-redesigned shell. Palette and spacing are the same tokens
              build/common.py emits, kept in sync by hand.
Author:       Oax Sport
Template:     estar
Version:      0.1.5
Text Domain:  oaxsport-child
*/

/* ------------------------------------------------------------------ tokens
   These mirror build/common.py. If you change one there, change it here.
   Kept as custom properties so the values appear exactly once.
   ------------------------------------------------------------------ */
:root {
  --oxs-navy:        #001253;
  --oxs-navy-deep:   #000a32;
  --oxs-navy-lift:   #0a1e6b;
  --oxs-red:         #B1191F;
  --oxs-red-dark:    #8f1319;
  --oxs-red-light:   #ff9aa0;
  --oxs-ivory:       #FAF8F4;
  --oxs-ink:         #4a5677;
  --oxs-ink-soft:    #5b6480;
  --oxs-on-dark:     #c3cbe6;
  --oxs-line-light:  rgba(0, 18, 83, .14);
  --oxs-line-dark:   rgba(255, 255, 255, .16);
  --oxs-mono:        ui-monospace, SFMono-Regular, Menlo, monospace;
  --oxs-container:   1240px;
}

/* ------------------------------------------------------------------ header
   eStar markup, read off the live site 2026-08-06:
     header#header.header > .header-inner.container > .branding
       > .site-name > nav#nav.nav > ul#primary-menu.menu > li.menu-item
   Styling only. No template override, so nothing here can break rendering.
   ------------------------------------------------------------------ */
#header.header {
  background: var(--oxs-navy);
  border-bottom: 1px solid var(--oxs-line-dark);
}

#header .header-inner.container {
  max-width: var(--oxs-container);
}

#header .site-title,
#header .site-title a {
  color: #fff;
  font-weight: 800;
  letter-spacing: -.01em;
}

#header .site-description {
  color: var(--oxs-on-dark);
}

/* Top-level menu items */
#header #primary-menu > li > a,
#header #primary-menu > li > .menu-text > a {
  color: #fff;
  font-weight: 700;
  font-size: 15px;
  letter-spacing: .01em;
}

#header #primary-menu > li > a:hover,
#header #primary-menu > li > .menu-text > a:hover,
#header #primary-menu > li.current-menu-item > .menu-text > a {
  color: var(--oxs-red-light);
}

/* The current page gets a red underline rather than a colour-only cue,
   which would fail on its own for colour-blind users. */
#header #primary-menu > li.current-menu-item > .menu-text > a,
#header #primary-menu > li.current-menu-ancestor > .menu-text > a {
  box-shadow: inset 0 -3px 0 0 var(--oxs-red);
}

/* Dropdowns */
#header .sub-menu {
  background: var(--oxs-navy-lift);
  border: 1px solid var(--oxs-line-dark);
  border-radius: 8px;
  padding: 6px 0;
}

#header .sub-menu a {
  color: var(--oxs-on-dark);
  font-size: 14.5px;
}

#header .sub-menu a:hover {
  color: #fff;
  background: rgba(255, 255, 255, .08);
}

#header .sub-menu-toggle svg.icon {
  fill: currentColor;
}

/* The Donate item. Marked with a CSS class on the menu item in
   Appearance > Menus so it can be styled without hard-coding an ID. */
#header #primary-menu > li.oxs-donate > .menu-text > a,
#header #primary-menu > li.oxs-donate > a {
  background: var(--oxs-red);
  color: #fff;
  border-radius: 6px;
  padding: 12px 22px;
  min-height: 44px;
  display: inline-block;
  line-height: 1.2;
  box-sizing: border-box;
}

#header #primary-menu > li.oxs-donate > .menu-text > a:hover,
#header #primary-menu > li.oxs-donate > a:hover {
  background: var(--oxs-red-dark);
  color: #fff;
  box-shadow: none;
}

/* Language switcher. The live site uses a globe emoji as the trigger, which is
   not an accessible control and renders differently on every platform.
   oaxsport_language_switcher_label() in functions.php replaces the label; this
   styles the result. */
#header #primary-menu > li.oxs-lang > .menu-text > a {
  font-family: var(--oxs-mono);
  font-size: 12.5px;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: var(--oxs-on-dark);
}

/* Touch targets. 66% of traffic is mobile, so every header control clears 44px. */
#header a,
#header button {
  min-height: 44px;
}

@media (max-width: 820px) {
  #header .menu-toggle.header-icon {
    color: #fff;
    min-width: 44px;
    min-height: 44px;
  }
  /* eStar drops the open menu into an absolutely-positioned #primary-menu that
     carries no background of its own, so it lands on the white page while the
     links above are still #fff for the navy header bar — 1:1 contrast, every
     item invisible. Give the panel the header's ground rather than recolouring
     the links, because .sub-menu above is already navy and expects a dark
     parent. Mobile-only, so it must stay in the UCSS Selector Allowlist. */
  #header #primary-menu {
    background: var(--oxs-navy-deep);
    padding: 8px 20px 16px;
  }
  #header #primary-menu > li > .menu-text > a {
    font-size: 17px;
    padding: 14px 0;
  }
  #header #primary-menu > li.oxs-donate > .menu-text > a {
    display: block;
    text-align: center;
    margin: 12px 0;
  }
}

/* ------------------------------------------------------------------ footer
   eStar markup: footer.footer > .footer-widgets / .address-section
     > .address-box / .textwidget.custom-html-widget / .site-info
   ------------------------------------------------------------------ */
.footer {
  background: var(--oxs-navy-deep);
  color: var(--oxs-on-dark);
  border-top: 4px solid var(--oxs-red);
}

.footer .container {
  max-width: var(--oxs-container);
}

.footer .widget-title {
  color: #fff;
  font-size: 13px;
  letter-spacing: .16em;
  text-transform: uppercase;
  font-family: var(--oxs-mono);
  font-weight: 700;
}

.footer a {
  color: var(--oxs-on-dark);
  text-decoration: underline;
  text-underline-offset: 3px;
}

.footer a:hover {
  color: #fff;
}

.footer .address-box {
  font-size: 14.5px;
  line-height: 1.7;
}

/* ---------------------------------------------- footer .site-info contrast
   AUDIT-2026-08-12-colour-tokens.md (D5): --oxs-ink-soft (#5b6480) on
   --oxs-navy-deep (#000a32) measures 3.30:1, under the 4.5:1 AA floor. This
   block is not decorative — it carries footer_copyright: the About text, both
   addresses, the EIN, the RFC, and the locked transparency sentence.

   --oxs-on-dark (#c3cbe6) on the same ground measures ~11.9:1.

   Do NOT lighten --oxs-navy-deep to fix this; that weakens the design sitewide,
   the same trade rejected for the payment-pill fix below. If this text must
   recede from the links above it, #8e99bb still clears the floor at ~6.8:1.

   ⚠️ LiteSpeed UCSS will drop this rule unless `.footer .site-info` is in the
   UCSS Selector Allowlist. Add it in the same change or the fix sits invisible
   behind the cron-backed queue, exactly as the payment-pill fix did. */
.footer .site-info {
  border-top: 1px solid var(--oxs-line-dark);
  font-size: 13px;
  color: var(--oxs-on-dark);
  padding-top: 20px;
}

/* ---------------------------------------------- footer payment logo pill
   Cristian Corbu, 2026-08-07: the PayPal mark is black on #000a32 and is
   "almost invisible", and the same goes for Givebutter and the third mark in
   the "Verified Donation Platforms" widget.

   A light pill behind the whole row fixes all three at once with no new
   assets, and does not touch either brand's mark — which matters, because
   PayPal and Givebutter both restrict recolouring their logos. Lightening the
   footer background instead was rejected: it weakens the design sitewide for
   one element.

   ⚠️ #custom_html-6 is the live widget ID for that widget. Widget IDs change
   if the widget is deleted and re-added, so .oxs-paylogos is supported as a
   stable alternative: wrap the logo row in <div class="oxs-paylogos"> inside
   the widget and this keeps working regardless of the ID.
   ------------------------------------------------------------------ */
.footer #custom_html-6 .custom-html-widget,
.footer .oxs-paylogos {
  background: #f4f6fb;
  border-radius: 10px;
  padding: 14px 16px;
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 14px 20px;
}

/* Links inside the pill sit on a light background now, so the footer's
   light-on-dark link colour would be unreadable. Override it here only. */
.footer #custom_html-6 .custom-html-widget a,
.footer .oxs-paylogos a {
  color: var(--oxs-navy);
  text-decoration: none;
}

.footer #custom_html-6 .custom-html-widget a:hover,
.footer .oxs-paylogos a:hover {
  color: var(--oxs-red);
  text-decoration: underline;
}

/* The three marks carry inline width:160px;height:auto set in the widget HTML.
   Inline styles beat a stylesheet, so sizing them from here would be dead code.
   Change the size in the widget itself if it ever needs changing. */

/* 66% of search clicks are mobile. At 375px the row must wrap, not overflow. */
@media (max-width: 480px) {
  .footer #custom_html-6 .custom-html-widget,
  .footer .oxs-paylogos {
    gap: 12px 14px;
    padding: 12px;
  }
}

/* ------------------------------------------------------------------ sidebar
   Blog posts only. This is the highest-value unused space on the site:
   88% of organic clicks land on posts, not on the designed pages.
   ------------------------------------------------------------------ */
aside.sidebar {
  font-size: 15px;
}

aside.sidebar .widget {
  background: var(--oxs-ivory);
  border: 1px solid var(--oxs-line-light);
  border-radius: 10px;
  padding: 22px 20px;
  margin-bottom: 20px;
}

aside.sidebar .widget-title {
  color: var(--oxs-navy);
  font-family: var(--oxs-mono);
  font-size: 12px;
  letter-spacing: .16em;
  text-transform: uppercase;
  margin: 0 0 12px;
}

/* The conversion panel, output by oaxsport_sidebar_conversion_panel().
   Deliberately the only navy block in the sidebar so it reads as the primary
   action rather than another widget. */
aside.sidebar .oxs-convert {
  background: var(--oxs-navy);
  border-color: var(--oxs-navy);
  color: #fff;
}

aside.sidebar .oxs-convert .widget-title,
aside.sidebar .oxs-convert h3 {
  color: #fff;
}

aside.sidebar .oxs-convert p {
  color: var(--oxs-on-dark);
  font-size: 14.5px;
  line-height: 1.65;
}

aside.sidebar .oxs-convert .oxs-btn {
  display: inline-block;
  background: var(--oxs-red);
  color: #fff;
  font-weight: 800;
  font-size: 15px;
  padding: 14px 26px;
  border-radius: 6px;
  text-decoration: none;
  min-height: 44px;
  box-sizing: border-box;
  margin-top: 6px;
}

aside.sidebar .oxs-convert .oxs-btn:hover {
  background: var(--oxs-red-dark);
  color: #fff;
}

aside.sidebar .oxs-convert .oxs-trust {
  font-size: 12px;
  line-height: 1.6;
  color: var(--oxs-on-dark);
  margin-top: 14px;
  opacity: .85;
}

/* ------------------------------------------------------------------ posts
   Typography only until the parent templates have been read. Long-form
   readability is the whole job here: these pages are why people arrive.
   ------------------------------------------------------------------ */
.single .entry-content {
  font-size: 18px;
  line-height: 1.75;
  color: var(--oxs-ink);
}

.single .entry-content > p,
.single .entry-content > ul,
.single .entry-content > ol {
  max-width: 68ch;
}

.single .entry-content h2 {
  color: var(--oxs-navy);
  font-weight: 800;
  letter-spacing: -.01em;
  margin-top: 1.8em;
}

.single .entry-content h3 {
  color: var(--oxs-navy);
  font-weight: 700;
  margin-top: 1.5em;
}

.single .entry-content a {
  color: var(--oxs-red);
  text-underline-offset: 3px;
}

.single .entry-content blockquote {
  border-left: 3px solid var(--oxs-red);
  background: var(--oxs-ivory);
  padding: 18px 22px;
  margin: 28px 0;
  border-radius: 0 8px 8px 0;
  font-style: normal;
}

.single .entry-content img {
  max-width: 100%;
  height: auto;
  border-radius: 10px;
}

/* Wide content must scroll inside its own box, never the page body. */
.single .entry-content table,
.single .entry-content pre {
  display: block;
  max-width: 100%;
  overflow-x: auto;
}

/* -------------------------------------------- archive / blog card ratio
   Card thumbnails now match the social card. eStar's registered
   post-thumbnail size renders 373x280 (4:3), while the site serves
   twitter:card = summary_large_image, which every platform crops to
   1.91:1. So the same post looked one shape in a feed and another on the
   archive. 1200/630 is that ratio expressed exactly.

   88% of organic clicks land on blog posts, so the archive card is the
   most-seen card on the site and the one worth making consistent.

   ⚠️ This crops, it does not re-render. The source files are still 4:3, so
   roughly a quarter of the image height is cut. object-position is set to
   50% 40% rather than dead centre because these are sports photographs and
   centre-cropping a standing athlete takes the head off; biasing upward
   keeps faces in frame. Anything that must not be cropped needs a real
   1.91:1 crop uploaded, or the thumbnail size regenerated — CSS alone
   cannot solve that.
   ------------------------------------------------------------------ */
.entry-thumbnail img,
.entry-thumbnail a > img {
  aspect-ratio: 1200 / 630;
  width: 100%;
  height: auto;
  object-fit: cover;
  object-position: 50% 40%;
  display: block;
  border-radius: 8px;
}

/* height:auto above would otherwise be overridden by the width/height
   attributes WordPress prints on the img, which force the 4:3 box back. */
.entry-thumbnail {
  overflow: hidden;
  border-radius: 8px;
}

/* ------------------------------------------------------------------ a11y */
a:focus-visible,
button:focus-visible {
  outline: 3px solid var(--oxs-red-light);
  outline-offset: 2px;
}

.screen-reader-text {
  position: absolute !important;
  width: 1px;
  height: 1px;
  overflow: hidden;
  clip: rect(1px, 1px, 1px, 1px);
  white-space: nowrap;
}
