/* ============================================================================
   booking-shared.css — the chrome BOTH checkouts share.
   ----------------------------------------------------------------------------
   book-lesson.html and book-rental.html used to carry these rules TWICE, in two
   <style> blocks that drifted apart: 58 selectors appeared in both pages and 22
   of them disagreed. Same component, two implementations, no single source.

   This file is that single source. Each page still keeps its own <style> block —
   deliberately, per CLAUDE.md — but only for what is genuinely page-specific
   (duration chips, rider cards, board cards, its own calendar-cell markup).

   Loaded BEFORE each page's <style>, so a page can still override deliberately.
   Generated from the pages' own effective cascade, so no value was retyped.
   ============================================================================ */


/* ── Design tokens — the palette both checkouts already agreed on ─────────────────────────────────────── */
:root {
  --navy: #10212B;
  --txt-muted:rgba(184,212,232,.75);
  --txt-faint:rgba(184,212,232,.65);
  --dark: #244665;
  --mid: #0E4D8A;
  --sky: #1A8FD1;
  --cyan: #1BD5FE;
  --gold: #F5A623;
  --light: #B8D4E8;
  --white: #FFFFFF;
  --red: #e74c3c;
  --lime: #88E534;
  --ink: #1e293b;
}


/* ── Reset + shell ─────────────────────────────────────── */
* {
  box-sizing: border-box;
  margin: 0;
  padding: 0;
  -webkit-tap-highlight-color: transparent;
}

body {
  overflow-x: hidden;
}

#app {
  display: flex;
  flex-direction: column;
  min-height: 100vh;
}

#checkout-container {
  margin-top:8px;
}


/* ── Header ─────────────────────────────────────── */
.hdr {
  position: sticky;
  top: 0;
  z-index: 10;
  background: rgba(15,39,68,.95);
  backdrop-filter: blur(12px);
  border-bottom: 1px solid rgba(0,198,255,.12);
  padding: 14px 20px;
  display: flex;
  align-items: center;
  gap: 12px;
}

.hdr-back {
  width: 44px;
  height: 44px;
  border-radius: 50%;
  border: 1px solid rgba(0,198,255,.25);
  background: transparent;
  color: var(--cyan);
  font-size: 18px;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  transition: background .2s;
}

.hdr-title {
  font-family: 'Oswald', sans-serif;
  font-size: 20px;
  letter-spacing: .08em;
  flex: 1;
  margin: 0;
  font-weight: inherit;
}


/* ── Progress dots ─────────────────────────────────────── */
.progress {
  display: flex;
  gap: 6px;
  align-items: center;
  padding: 14px 20px 0;
}

.pdot {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: rgba(255,255,255,.15);
  transition: all .3s;
}

.pdot.active {
  background: var(--cyan);
  width: 24px;
  border-radius: 4px;
}

.pdot.done {
  background: var(--cyan);
  opacity: .5;
}


/* ── Step chrome ─────────────────────────────────────── */
.step {
  display: none;
  flex: 1;
  flex-direction: column;
  padding: 28px 20px 120px;
}

.step.active {
  display: flex;
}

.step-label {
  font-family: 'Rubik', sans-serif;
  font-size: 11px;
  letter-spacing: .2em;
  text-transform: uppercase;
  color: var(--cyan);
  opacity: .7;
  margin-bottom: 8px;
}

.step-q {
  font-family: 'Oswald', sans-serif;
  font-size: 32px;
  line-height: 1.1;
  letter-spacing: .04em;
  margin: 0 0 6px;
  font-weight: inherit;
}

.step-sub {
  font-size: 14px;
  color: var(--light);
  opacity: .7;
  margin-bottom: 28px;
  line-height: 1.5;
}


/* ── Form fields ─────────────────────────────────────── */
.field {
  margin-bottom: 16px;
}

.field-label {
  font-family: 'Rubik', sans-serif;
  font-size: 11px;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--txt-muted);
  margin-bottom: 8px;
  display: block;
}

.field-err {
  color: #ff8a7a;
  font-size: 12.5px;
  margin-top: 6px;
  line-height: 1.4;
}

.inp {
  width: 100%;
  background: rgba(22,51,88,.7);
  border: 1px solid rgba(26,143,209,.25);
  color: var(--white);
  border-radius: 12px;
  padding: 16px;
  font-size: 16px;
  font-family: 'Inter', sans-serif;
  outline: none;
  transition: border-color .2s;
  -webkit-appearance: none;
}

.inp:focus {
  border-color: var(--cyan);
}

.inp::placeholder {
  color: rgba(184,212,232,.3);
}

.inp-bad {
  border-color: var(--red) !important;
}

select.inp {
  cursor: pointer;
}


/* ── Bottom nav + buttons ─────────────────────────────────────── */
.bottom-nav {
  position: fixed;
  bottom: 0;
  left: 0;
  right: 0;
  background: rgba(15,39,68,.97);
  border-top: 1px solid rgba(245,166,35,.12);
  padding: 16px 20px;
  padding-bottom: calc(16px + env(safe-area-inset-bottom, 0px));
  display: flex;
  gap: 12px;
  z-index: 10;
}

.btn-back {
  flex: 0 0 auto;
  background: transparent;
  border: 1.5px solid rgba(36,70,101,.5);
  color: rgba(184,212,232,.8);
  border-radius: 12px;
  padding: 16px 20px;
  font-family: 'Rubik', sans-serif;
  font-size: 14px;
  letter-spacing: .12em;
  text-transform: uppercase;
  cursor: pointer;
  transition: all .2s;
}

.btn-next {
  flex: 1;
  background: var(--lime);
  color: var(--ink);
  border: none;
  border-radius: 12px;
  padding: 16px;
  font-family: 'Rubik', sans-serif;
  font-size: 16px;
  font-weight: 700;
  letter-spacing: .12em;
  text-transform: uppercase;
  cursor: pointer;
  transition: opacity .2s, box-shadow .2s;
  box-shadow: 0 4px 20px rgba(136,229,52,.30);
}

.btn-next:disabled {
  opacity: .4;
  cursor: not-allowed;
}


/* ── Contact-preference trio ─────────────────────────────────────── */
.pref-grid {
  display: grid;
  grid-template-columns: repeat(3,1fr);
  gap: 8px;
}

/* NB: the rental declared .pref-* twice; the first copy was dead. This is the effective value, and it already matched the lesson. */
.pref-btn {
  background: rgba(255,255,255,.04);
  border: 1.5px solid rgba(26,143,209,.28);
  color: var(--white);
  border-radius: 12px;
  padding: 14px 8px;
  cursor: pointer;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 6px;
  transition: border-color .2s, background .2s;
}

.pref-btn.active {
  background: rgba(0,198,255,.12);
  border-color: var(--cyan);
}

.pref-btn:hover {
  border-color: rgba(0,198,255,.45);
}

.pref-ico {
  width: 22px;
  height: 22px;
  opacity: .85;
}

.pref-lbl {
  font-family: 'Rubik', sans-serif;
  font-size: 13px;
  letter-spacing: .06em;
  text-transform: uppercase;
}


/* ── Summary rows ─────────────────────────────────────── */
.sum-card {
  background: rgba(22,51,88,.5);
  border: 1px solid rgba(26,143,209,.2);
  border-radius: 14px;
  padding: 6px 16px;
  margin-bottom: 16px;
}

.sum-row {
  display: flex;
  justify-content: space-between;
  align-items: flex-start;
  padding: 12px 0;
  border-bottom: 1px solid rgba(26,143,209,.1);
}

.sum-row:last-child {
  border-bottom: none;
}

.sum-k {
  font-family: 'Rubik', sans-serif;
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: .12em;
  color: var(--txt-muted);
}

.sum-v {
  font-size: 14px;
  text-align: right;
  color: var(--white);
  max-width: 60%;
}


/* ── Boxes + banners ─────────────────────────────────────── */
.info-box {
  background: rgba(22,51,88,.6);
  border: 1px solid rgba(26,143,209,.2);
  border-radius: 14px;
  padding: 16px 20px;
  margin-top: 20px;
  text-align: left;
  font-size: 14px;
  line-height: 1.7;
  color: rgba(184,212,232,.8);
}

.err-banner {
  background: rgba(231,76,60,.1);
  border: 1px solid rgba(231,76,60,.3);
  border-radius: 10px;
  padding: 12px 16px;
  margin-bottom: 16px;
  font-size: 13px;
  color: #ff8a7a;
  display: none;
}

.err-banner.show {
  display: block;
}

.pay-disclosure {
  background: rgba(22,51,88,.5);
  border: 1px solid rgba(26,143,209,.2);
  border-radius: 12px;
  padding: 14px 16px;
  margin-top: 12px;
  font-size: 13px;
  line-height: 1.7;
  color: rgba(184,212,232,.85);
}

.pay-disclosure .row {
  display: flex;
  gap: 10px;
  align-items: flex-start;
}

.pay-disclosure .ico {
  flex-shrink: 0;
}

/* 12px top margin; the rental's 10px was the odd one out. */
.pay-note {
  margin-top:12px;
  padding:14px;
  background:rgba(22,51,88,.4);
  border:1px solid rgba(26,143,209,.12);
  border-radius:12px;
  font-size:13px;
  color:var(--txt-faint);
  line-height:1.6;
  text-align:center;
}


/* ── Success + loading ─────────────────────────────────────── */
.center-block {
  flex: 1;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  text-align: center;
  padding: 40px 24px;
}

.spinner {
  width: 48px;
  height: 48px;
  border: 3px solid rgba(245,166,35,.2);
  border-top-color: var(--gold);
  border-radius: 50%;
  animation: spin .8s linear infinite;
  margin-bottom: 24px;
}

.success-icon {
  font-size: 56px;
  margin-bottom: 20px;
}

/* 28px, and always prefixed with # (see .booking-ref usage in both pages). */
.booking-ref {
  font-family: 'Oswald', sans-serif;
  font-size: 28px;
  color: var(--gold);
  letter-spacing: .12em;
  background: rgba(245,166,35,.06);
  border: 1px solid rgba(245,166,35,.2);
  border-radius: 12px;
  padding: 12px 24px;
  margin: 16px 0;
}


/* ── Calendar ─────────────────────────────────────── */
.cal-month {
  font-family: 'Oswald', sans-serif;
  font-size: 22px;
  letter-spacing: .06em;
}

/* 44px hit area — the lesson's 38px was under the minimum touch target. */
.cal-nav {
  width: 44px;
  height: 44px;
  border-radius: 50%;
  border: 1.5px solid rgba(0,198,255,.2);
  background: transparent;
  color: var(--cyan);
  font-size: 22px;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  transition: background .2s;
  flex-shrink: 0;
}

.cal-nav:disabled {
  opacity: .3;
  cursor: default;
  pointer-events: none;
}


/* ── Header logo ───────────────────────────────────────────────────────────
   One mark on both flows: the real SVG, not typed text. Deliberately NOT a link —
   a logo that navigates home mid-checkout is an exit door on a paid funnel. */
.hdr-logo {
  display: flex;
  align-items: center;
}
.hdr-logo img {
  height: 28px;
  width: auto;
  display: block;
}

/* ── Calendar card ─────────────────────────────────────────────────────────
   The lesson wrapped its calendar in a card; the rental had no container rule at
   all, so its calendar floated bare on the page. */
.cal {
  background: rgba(22,51,88,.4);
  border: 1px solid rgba(26,143,209,.18);
  border-radius: 16px;
  padding: 14px;
}

/* ── Selected day ──────────────────────────────────────────────────────────
   A tint, not a flood. The rental filled the cell with solid cyan and needed THREE
   !important overrides to make it stick — the tell that it was forced in, not
   designed. What it was actually fighting is .cal-day.available, which has the SAME
   specificity and simply came later in the file.

   So this rule wins on SPECIFICITY instead (.cal-day.available.selected = 0,3,0
   beats .cal-day.available = 0,2,0). That holds no matter what order the
   stylesheets load in — which matters, because this file loads BEFORE the page's
   own <style>. Removing the !important without this would have silently killed the
   selected-day highlight. */
.cal-cell.selected,
.cal-day.selected,
.cal-cell.book.selected,
.cal-cell.call.selected,
.cal-day.available.selected,
.cal-day.call-only.selected,
.cal-day.unavailable.selected {
  background: rgba(0,198,255,.18);
  border: 1.5px solid var(--cyan);
  color: var(--white);
  font-weight: 600;
}

/* ── The rental SPAN (rental calendar only — lessons are single-day) ────────
   A 6-day rental is Jul 18 → Jul 24, and the calendar used to light exactly ONE cell of that.
   These rules paint the days the board is actually in the customer's hands.

   Every one of them follows the specificity contract above, and here it is load-bearing rather
   than tidy: .cal-day.available / .call-only / .unavailable all live in the page's own <style>,
   which loads AFTER this file, so a bare .cal-day.in-range (0,2,0) would tie and LOSE.

   .unavailable especially. _dayAvail answers "can a rental START here?" — so a 6-day rental
   starting Jul 20 may collide later and mark Jul 20 unavailable, even though Jul 20 sits squarely
   inside a perfectly valid Jul 18–24 booking. Without these, the customer sees a dim, dead-looking
   hole in the middle of their own rental.

   The fill has to be clearly STRONGER than .cal-day.available (rgba(0,198,255,.07) + a .2 border),
   not a nudge above it: at .10 with a transparent border, a day inside the customer's own rental
   actually read as WEAKER than a day they hadn't booked. So the band is a solid run of filled,
   borderless cells (.16) against outlined ones — a difference of treatment, not just of opacity. */
.cal-day.in-range,
.cal-day.available.in-range,
.cal-day.call-only.in-range,
.cal-day.unavailable.in-range,
.cal-day.loading.in-range,
.cal-day.outside.in-range {
  background: rgba(0,198,255,.16);
  border-color: transparent;
  color: var(--white);
  font-weight: 500;
  animation: none;
}

/* The return day carries the SAME weight as the pickup anchor — rentals run in 24h units, so a 5pm
   pickup means the board is yours until 5pm on the return date. It is not a lesser day and must not
   look like one. Dashed marks it as the END of the span rather than a second start. */
.cal-day.range-end,
.cal-day.available.range-end,
.cal-day.call-only.range-end,
.cal-day.unavailable.range-end,
.cal-day.loading.range-end,
.cal-day.outside.range-end {
  background: rgba(0,198,255,.18);
  border: 1.5px dashed var(--cyan);
  color: var(--white);
  font-weight: 600;
  animation: none;
}

/* Inside a chosen range, "can a rental start here?" is no longer the question the dot answers, so
   it is just noise across the band. */
.cal-day.available.selected::after,
.cal-day.call-only.selected::after,
.cal-day.available.in-range::after,
.cal-day.call-only.in-range::after,
.cal-day.available.range-end::after,
.cal-day.call-only.range-end::after {
  display: none;
}

/* Spill days from the next month, appended so a range crossing a month boundary still shows its
   end. Display-only: dim until they are part of the range, and never clickable. */
.cal-day.outside {
  color: rgba(255,255,255,.22);
  cursor: default;
}

.cal-legend-bar {
  width: 14px;
  height: 7px;
  border-radius: 2px;
  background: rgba(0,198,255,.35);
  border: 1px solid rgba(0,198,255,.5);
  flex-shrink: 0;
}

/* ── Calendar legend ───────────────────────────────────────────────────────
   Uppercase Rubik, like every other micro-label in the system (.field-label,
   .step-label, .card-tag). The lesson's 12px sentence case was the outlier. */
.cal-legend {
  display: flex;
  gap: 18px;
  justify-content: center;
  margin-top: 14px;
  flex-wrap: wrap;
}
.cal-legend-item {
  display: flex;
  align-items: center;
  gap: 6px;
  font-family: 'Rubik', sans-serif;
  font-size: 10.5px;
  letter-spacing: .08em;
  text-transform: uppercase;
  color: var(--txt-faint);
}
.cal-legend-dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  flex-shrink: 0;
}
.cal-legend-dot.dot-online { background: var(--cyan); }
.cal-legend-dot.dot-call   { background: var(--gold); }

/* ── Price ─────────────────────────────────────────────────────────────────
   Gold, and always the REAL total. "+ tax" is not a number anyone can act on. */
.price {
  font-family: 'Oswald', sans-serif;
  font-size: 32px;          /* board-card scale; compact contexts override */
  color: var(--gold);
  line-height: 1;
}
.price-note {
  font-family: 'Rubik', sans-serif;
  font-size: 10px;
  text-transform: uppercase;
  letter-spacing: .08em;
  color: var(--txt-muted);
  margin-top: 2px;
}

/* ── Waiver ────────────────────────────────────────────────────────────────
   The rental showed a bar that fills as you read; the lesson only printed a line of
   text saying "scroll to the end". A sentence is not feedback. Both get the bar. */
.waiver-progress-track {
  height: 3px;
  background: rgba(0,198,255,.12);
  border-radius: 2px;
  margin-bottom: 12px;
}
.waiver-progress-fill {
  height: 100%;
  width: 0%;
  background: var(--cyan);
  border-radius: 2px;
  transition: width .1s linear;
}
.waiver-read-banner {
  display: none;
  text-align: center;
  padding: 10px;
  margin-top: 10px;
  border: 1px solid var(--cyan);
  border-radius: 10px;
  background: rgba(0,198,255,.06);
  color: var(--cyan);
  font-family: 'Rubik', sans-serif;
  font-size: 11px;
  letter-spacing: .08em;
  text-transform: uppercase;
}
.waiver-read-banner.on { display: block; }

.sig-pad {
  width: 100%;
  height: 120px;
  background: #fff;
  display: block;
  border-radius: 10px;
  border: 1.5px solid rgba(26,143,209,.28);
  touch-action: none;
  cursor: crosshair;
}
.sig-pad.bad { border-color: var(--red); }

/* ── Exit route off the success screen ────────────────────────────────────
   The rental had one; the lesson dead-ended with nowhere to go. Both have it now. */
.back-link {
  display: block;
  margin-top: 24px;
  font-family: 'Rubik', sans-serif;
  font-size: 13px;
  letter-spacing: .12em;
  text-transform: uppercase;
  color: var(--txt-faint);
  text-decoration: none;
}

/* ── Running booking context ───────────────────────────────────────────────
   Keeps the customer's choices on screen for the whole flow ("Full Day · Jul 13 – Jul 14",
   "2 riders · Mon Jul 13, 7:30 AM"). The rental had this; the lesson forgot your choices
   the moment you advanced a step. */
.booking-context {
  padding: 8px 20px;
  display: flex;
  align-items: center;
  gap: 6px;
  font-family: 'Rubik', sans-serif;
  font-size: 12px;
  letter-spacing: .06em;
  color: var(--txt-faint);
  border-bottom: 1px solid rgba(0,198,255,.07);
  flex-wrap: wrap;
  min-height: 34px;
}
.ctx-val { color: rgba(184,212,232,.85); }
.ctx-sep { color: rgba(184,212,232,.2); margin: 0 2px; }

/* ── Promo ─────────────────────────────────────────────────────────────────
   A discount used to be visible on exactly ONE screen (the review step) — and on the rental,
   only if it happened to be a PERCENTAGE. A flat-$100 code showed nothing at all, so the
   customer concluded the code had been rejected while the server quietly applied it.

   Lime, not cyan: cyan is the everywhere-colour of this UI (links, focus, selected days), so a
   saving rendered in it reads as just more chrome. Lime appears nowhere else, which is the
   point — money coming OFF the price should be the one thing on the screen that looks different. */
.ctx-promo { color: var(--lime); }

.promo-saved {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  flex-wrap: wrap;
  margin: 14px 0;
  padding: 12px 16px;
  border-radius: 12px;
  background: rgba(136,229,52,.08);
  border: 1px solid rgba(136,229,52,.32);
  color: var(--lime);
  font-size: 14px;
}
.promo-saved strong { color: var(--white); }
.ps-tag {
  font-family: 'Rubik', sans-serif;
  font-size: 10.5px;
  letter-spacing: .1em;
  text-transform: uppercase;
  padding: 3px 8px;
  border-radius: 6px;
  background: rgba(136,229,52,.16);
}

/* The discount line inside the boards-step footer and the review summary. */
.bf-row-promo { color: var(--lime); }
.sum-v.discount { color: var(--lime); }


/* ════════════════════════════════════════════════════════════════════════════
   LIGHT THEME (owner-approved 2026-07-20) — the checkouts + /b/ share this.
   Scoped to html.theme-light so a page opts in by carrying the class; pages
   WITHOUT it stay dark. Mirrors booking-lookup.html's proven /b/ remap so all
   three light pages draw the theme from ONE source (fixes the drift where a new
   shared component shipped dark). Matches /o/ + /b/ exactly.

   Token remap is SURGICAL: --navy is deliberately NOT remapped — it doubles as
   the dark TEXT on cyan/gold/lime buttons (var(--ink) too). Accents flip to
   their AA-on-white variants; accent-as-BACKGROUND components get explicit rules
   so their fills stay vivid with dark text.
   ════════════════════════════════════════════════════════════════════════════ */
html.theme-light, html.theme-light body {
  background: #F4F7F9; color: #10212B;
  --white: #10212B;            /* "bright text" reads as ink on white */
  --light: #3A4A56;
  --txt-muted: #55707F;
  --txt-faint: #6B7F8C;
  --cyan: #0096A6;             /* text/border accent, AA on white */
  --gold: #9A6A0B;             /* text/border gold, AA on white */
}
/* Headings + labels — the brand-punch the owner liked on /b/ */
html.theme-light .step-q { color: #244665; font-weight: 700; }
html.theme-light .step-label { color: #1A8FD1; opacity: 1; font-weight: 700; }
html.theme-light .field-label { color: #1A8FD1; font-weight: 700; }
html.theme-light .cal-month { color: #244665; }
/* Surfaces → white/light + hairline borders */
html.theme-light .hdr { background: rgba(255,255,255,.95); border-bottom: 1px solid #E3E9ED; }
html.theme-light .hdr-back { border-color: #CFDAE1; }
html.theme-light .booking-context { border-bottom-color: #E3E9ED; }
html.theme-light .ctx-val { color: #3A4A56; }
html.theme-light .ctx-sep { color: #CFDAE1; }
html.theme-light .inp { background: #FFFFFF; border-color: #CFDAE1; color: #10212B; }
html.theme-light .inp::placeholder { color: #9FB2BD; }
html.theme-light .inp:focus { border-color: #0096A6; }
html.theme-light .field-err, html.theme-light .err-banner { color: #C0392B; }
html.theme-light .err-banner { background: rgba(231,76,60,.08); border-color: rgba(231,76,60,.3); }
html.theme-light .bottom-nav { background: rgba(255,255,255,.97); border-top-color: #E3E9ED; }
html.theme-light .btn-back { border-color: #CFDAE1; color: #55707F; }
html.theme-light .pref-btn { background: #FFFFFF; border-color: #CFDAE1; }
html.theme-light .pref-btn.active { background: rgba(0,150,166,.08); border-color: #0096A6; }
html.theme-light .pref-btn:hover { border-color: rgba(0,150,166,.45); }
html.theme-light .sum-card, html.theme-light .info-box, html.theme-light .pay-disclosure { background: #FFFFFF; border-color: #E3E9ED; }
html.theme-light .sum-card { box-shadow: 0 2px 10px rgba(16,33,43,.05); }
html.theme-light .sum-row { border-bottom-color: #E3E9ED; }
html.theme-light .pay-note { background: #FFFFFF; border-color: #E3E9ED; }
html.theme-light .cal { background: #FFFFFF; border-color: #E3E9ED; }
html.theme-light .cal-nav { border-color: rgba(0,150,166,.3); }
/* Spinner + booking ref */
html.theme-light .spinner { border-color: rgba(0,150,166,.2); border-top-color: #0096A6; }
html.theme-light .booking-ref { color: #C77F00; background: rgba(245,166,35,.08); border-color: rgba(154,106,11,.28); }
/* Price — keep the gold identity, dark enough to read at large sizes */
html.theme-light .price { color: #C77F00; }
/* ── Calendar selected day + the rental SPAN: solid vivid endpoints, readable
   tint between. Low-alpha cyan washes out on white, so strengthen. Dark text on
   the solid fills (the /o/ QUOTE-pill treatment). ─────────────────────────── */
html.theme-light .cal-cell.selected,
html.theme-light .cal-day.selected,
html.theme-light .cal-cell.book.selected,
html.theme-light .cal-cell.call.selected,
html.theme-light .cal-day.available.selected,
html.theme-light .cal-day.call-only.selected,
html.theme-light .cal-day.unavailable.selected {
  background: #1BD5FE; border-color: #1BD5FE; color: #0B2530;
}
html.theme-light .cal-day.in-range,
html.theme-light .cal-day.available.in-range,
html.theme-light .cal-day.call-only.in-range,
html.theme-light .cal-day.unavailable.in-range,
html.theme-light .cal-day.loading.in-range,
html.theme-light .cal-day.outside.in-range {
  background: rgba(0,150,166,.14); border-color: transparent; color: #10212B;
}
html.theme-light .cal-day.range-end,
html.theme-light .cal-day.available.range-end,
html.theme-light .cal-day.call-only.range-end,
html.theme-light .cal-day.unavailable.range-end,
html.theme-light .cal-day.loading.range-end,
html.theme-light .cal-day.outside.range-end {
  background: #1BD5FE; border: 1.5px dashed #0096A6; color: #0B2530;
}
html.theme-light .cal-day.outside { color: #B7C4CD; }
html.theme-light .cal-legend-bar { background: rgba(0,150,166,.35); border-color: rgba(0,150,166,.5); }
html.theme-light .cal-legend-dot.dot-online { background: #0096A6; }
html.theme-light .cal-legend-dot.dot-call { background: #F5A623; }
/* ── Waiver read-gate — box goes white/ink but the progress bar + banner stay
   clearly an accent on white (contrast is legally load-bearing). ──────────── */
html.theme-light .waiver-progress-track { background: rgba(0,150,166,.15); }
html.theme-light .waiver-progress-fill { background: #0096A6; }
html.theme-light .waiver-read-banner { border-color: #0096A6; background: rgba(0,150,166,.06); color: #0096A6; }
html.theme-light .sig-pad { border-color: #CFDAE1; }
/* ── Promo: green TEXT reads on white; the saved-pill keeps a lime tint ───── */
html.theme-light .ctx-promo, html.theme-light .bf-row-promo, html.theme-light .sum-v.discount { color: #2E7D0F; }
html.theme-light .promo-saved { background: rgba(136,229,52,.15); border-color: rgba(136,229,52,.5); color: #2E7D0F; }
html.theme-light .promo-saved strong { color: #244665; }
html.theme-light .ps-tag { background: rgba(136,229,52,.2); }
html.theme-light .back-link { color: #6B7F8C; }
/* ── policy.js injects the pause banner + staff chip with dark colors; these
   outrank them (higher specificity) so they read on white. Same as /b/. ──── */
html.theme-light .pause-banner { background: rgba(245,166,35,.1); border: 1px solid rgba(154,106,11,.3); color: #5A4A2B; }
html.theme-light .pause-banner b { color: #9A6A0B; }
html.theme-light .pause-banner a { color: #9A6A0B !important; }
html.theme-light .staff-chip { background: rgba(0,150,166,.08); border-color: rgba(0,150,166,.35); color: #0096A6; }
html.theme-light .staff-chip button { color: #0096A6; }

@keyframes spin { to { transform: rotate(360deg); } }

/* Skip link (WCAG 2.4.1 Bypass Blocks) — off-screen until it takes focus, then the
   first Tab on any page offers to jump past the nav. #main is an empty focus target
   placed right after the nav: no existing element is touched, so no layout can move. */
.skip-link{position:absolute;left:-9999px;top:0;z-index:1000}
.skip-link:focus{left:8px;top:8px;background:#fff;color:#10212b;padding:10px 14px;border-radius:8px;
  box-shadow:0 2px 10px rgba(0,0,0,.25);font-weight:700;text-decoration:none;outline:3px solid #1bd5fe}
#main:focus{outline:none}

/* WCAG 1.4.1 (Use of Colour) — a link sitting inside a block of text must be tellable
   from that text without relying on colour alone. These selectors are prose containers
   only: nav links, buttons and card CTAs are deliberately untouched, because a link that
   already looks like a button isn't "in a text block". */
.contact-note a, .savings-note a, .rental-info-note a,
.legal-doc p a, .legal-doc li a { text-decoration: underline; }
