/* NexDrive customer site — the showcase surface. Same design tokens as
   the admin (tokens.css), but treated with more care: this is what a
   stranger sees first. Still fast, still accessible, still works with
   zero JavaScript — the polish is in typography/spacing/imagery, not in
   anything that requires a script to render correctly. */

/* PROMOTED from .page-home: the confirmed look sits on white, with
   --color-bg kept as the *soft* surface (the floating nav bar, panels)
   that reads against it. Every customer page inherits this now. */
body {
  margin: 0;
  font-family: var(--font);
  background: var(--color-surface);
  color: var(--color-text);
  font-size: 16px;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
}

a {
  color: var(--color-primary);
  text-decoration: none;
}

/* Plain inline text links (prose, footer, breadcrumbs) get an underline
   on hover as their only affordance — nav items, cards, and buttons
   override this below since they already look interactive. */
a:hover {
  text-decoration: underline;
}

/* PROMOTED: the confirmed look never uses a 700-weight heading. Display
   headings run at 300 (see .section-head / .hero-title); everything else
   sits at 500 with slightly tighter tracking. */
h1, h2, h3 {
  color: var(--color-text);
  font-weight: 500;
  line-height: 1.2;
  letter-spacing: -0.02em;
}

img {
  max-width: 100%;
  display: block;
}

:focus-visible {
  outline: 3px solid var(--color-primary);
  outline-offset: 2px;
}

.container {
  max-width: 1180px;
  margin: 0 auto;
  padding: 0 var(--space-4);
}

/* ---------- Top nav (shared customer header) ----------

   Three zones — wordmark / floating pill link-group / actions — sitting
   on a lot of negative space rather than on a bordered bar. No divider
   line: the whitespace is the separation. Red appears in exactly one
   place here, as the small active-page dot. */

.site-nav {
  position: sticky;
  top: 0;
  z-index: 50;
  padding: var(--space-3) 0;
}

/* The header is a floating bar: narrower than the page grid, light fill,
   one hairline border, fully rounded. A 1fr/auto/1fr grid centres the
   link pill on the PAGE, not in the leftover space — so the wordmark and
   the actions being different widths can't pull it off-centre. */
.site-nav-inner {
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  gap: var(--space-3);
  max-width: 80%;
  padding: 0.45rem 0.5rem 0.45rem 1.25rem;
  background: var(--color-bg);
  border: 1px solid var(--color-border);
  border-radius: 999px;
  backdrop-filter: saturate(150%) blur(10px);
}

.site-nav .brand {
  justify-self: start;
  display: flex;
  align-items: center;
  gap: 0.6rem;
  font-weight: 600;
  font-size: 1.05rem;
  letter-spacing: -0.01em;
  color: var(--color-text);
  flex: none;
}

.site-nav .brand:hover {
  text-decoration: none;
}

/* The floating link container: a white pill raised off the bar's lighter
   fill. It sits in the grid's centre track, so it's truly page-centred;
   on narrow screens it moves to its own row (see below). */
.nav-pill {
  display: flex;
  align-items: center;
  gap: 0.15rem;
  padding: 0.3rem;
  border-radius: 999px;
  background: var(--color-surface);
  border: 1px solid var(--color-border);
  box-shadow: 0 1px 2px rgba(30, 20, 10, 0.03);
}

.nav-pill a {
  position: relative;
  padding: 0.5rem 1.05rem;
  border-radius: 999px;
  color: var(--color-text-muted);
  font-size: 0.9rem;
  font-weight: 500;
  white-space: nowrap;
  transition: color 0.15s ease, background 0.15s ease;
}

.nav-pill a:hover {
  color: var(--color-text);
  background: rgba(34, 32, 30, 0.04);
  text-decoration: none;
}

/* Active page: the body carries a page-* class (set per template), so
   the indicator needs no server-side "current page" field. The dot is
   the one small, deliberate use of brand red in the chrome. */
.page-home .nav-pill [data-nav="home"],
.page-fleet .nav-pill [data-nav="cars"],
.page-bookings .nav-pill [data-nav="bookings"],
.page-kyc .nav-pill [data-nav="kyc"] {
  color: var(--color-text);
  font-weight: 600;
}

.page-home .nav-pill [data-nav="home"]::after,
.page-fleet .nav-pill [data-nav="cars"]::after,
.page-bookings .nav-pill [data-nav="bookings"]::after,
.page-kyc .nav-pill [data-nav="kyc"]::after {
  content: "";
  position: absolute;
  left: 50%;
  bottom: 0.15rem;
  width: 4px;
  height: 4px;
  margin-left: -2px;
  border-radius: 999px;
  background: var(--color-primary);
}

.nav-actions {
  display: flex;
  align-items: center;
  gap: 0.6rem;
  justify-self: end;
}

.nav-actions form {
  margin: 0;
  display: flex;
}

/* The circular icon button that sits beside the primary pill action. */
.nav-icon-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 40px;
  height: 40px;
  flex: none;
  padding: 0;
  border-radius: 999px;
  border: 1px solid rgba(34, 32, 30, 0.12);
  background: var(--color-surface);
  color: var(--color-text);
  cursor: pointer;
  font: inherit;
  transition: background 0.15s ease, border-color 0.15s ease;
}

.nav-icon-btn:hover {
  background: var(--color-neutral-soft);
  text-decoration: none;
}

.nav-icon-btn svg {
  width: 18px;
  height: 18px;
  stroke: currentColor;
  fill: none;
  stroke-width: 1.6;
  stroke-linecap: round;
  stroke-linejoin: round;
}

/* Narrow screens: no toggle, no script. The pill group drops onto its
   own row full-width and scrolls sideways if it runs out of room, so
   every destination stays visible and tabbable with JS disabled. */
@media (max-width: 760px) {
  .site-nav-inner {
    grid-template-columns: auto auto;
    grid-template-areas:
      "brand actions"
      "pill  pill";
    gap: var(--space-3);
    padding: 0.7rem 0.8rem;
    border-radius: var(--radius-lg);
  }

  .site-nav .brand {
    grid-area: brand;
  }

  .nav-actions {
    grid-area: actions;
  }

  .nav-pill {
    grid-area: pill;
    overflow-x: auto;
    justify-content: flex-start;
    scrollbar-width: none;
  }

  .nav-pill::-webkit-scrollbar {
    display: none;
  }
}

/* The NexDrive mark. It's a transparent-background PNG sized by height,
   with width:auto so its aspect ratio holds whatever we set — the intrinsic
   width/height attributes on the <img> only reserve space while it loads. */
.brand-logo {
  height: 30px;
  width: auto;
  flex-shrink: 0;
}

/* ---------- Buttons (customer scale, slightly larger than admin) ----------

   PROMOTED: pill is the default shape now, not something .btn-lg opted
   into, and the weight drops from 600 to 500 to sit with the lighter
   headings. */

.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 0.5em;
  padding: 0.7rem 1.5rem;
  border-radius: var(--radius-pill);
  border: 1px solid var(--color-border-strong);
  background: var(--color-surface);
  color: var(--color-text);
  cursor: pointer;
  font-size: 0.95rem;
  font-weight: 500;
  font-family: inherit;
  text-decoration: none;
  transition: background 0.15s ease, border-color 0.15s ease, transform 0.15s ease, box-shadow 0.15s ease;
}

.btn:hover {
  background: var(--color-neutral-soft);
  text-decoration: none;
}

.btn-primary {
  background: var(--color-primary);
  border-color: var(--color-primary);
  color: #fff;
}

.btn-primary:hover {
  background: var(--color-primary-dark);
  border-color: var(--color-primary-dark);
}

.btn-lg {
  padding: 0.9rem 2rem;
  font-size: 1rem;
}

.btn-sm {
  padding: 0.4rem 0.9rem;
  font-size: 0.85rem;
}

.btn-block {
  width: 100%;
}

/* Compact pill — the header's primary action. (Shape is inherited from
   .btn now; this only tightens the size.) */
.btn-pill {
  padding: 0.55rem 1.15rem;
  font-size: 0.9rem;
}

/* A row of buttons at the end of a form or panel. Shared so no page has
   to reach for an inline margin. */
.form-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 0.6rem;
  margin-top: var(--space-4);
}

.form-actions .btn-block {
  flex: 1 1 100%;
}

/* The quiet companion to a primary button: outline only, no fill. */
.btn-ghost {
  background: transparent;
  border-color: rgba(34, 32, 30, 0.16);
  color: var(--color-text);
  box-shadow: none;
}

.btn-ghost:hover {
  background: rgba(34, 32, 30, 0.04);
  border-color: rgba(34, 32, 30, 0.28);
}

/* ---------- Hero ----------

   White, centred, and mostly empty. The old dark radial-gradient hero
   with a full-bleed crossfading photo backdrop is gone: a near-monochrome
   surface can't carry a dark slab, and the fleet photos it rotated
   through are the same photos the fleet strip below shows by name. */

.hero {
  position: relative;
  padding: var(--space-1) 0 var(--space-5);
  text-align: center;
}

.hero-eyebrow {
  margin: 0 0 var(--space-4);
  color: var(--color-text-faint);
  font-size: 0.78rem;
  font-weight: 500;
  letter-spacing: 0.14em;
  text-transform: uppercase;
}

/* Big and light — the headline carries the page, so it doesn't also need
   weight. Tight leading and negative tracking keep it from sprawling. */
.hero-title {
  margin: 0 auto var(--space-4);
  max-width: 16ch;
  font-size: clamp(2.6rem, 7vw, 4.6rem);
  font-weight: 300;
  line-height: 1.02;
  letter-spacing: -0.035em;
}

.hero-lede {
  margin: 0 auto var(--space-5);
  max-width: 52ch;
  color: var(--color-text-muted);
  font-size: 1.05rem;
  line-height: 1.7;
}

.hero-actions {
  display: flex;
  gap: 0.75rem;
  flex-wrap: wrap;
  justify-content: center;
}

/* The quick-book path, kept one action from the hero: a single line, no
   panel around it — a rule underneath is all the structure it needs. */
.hero-search {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  width: min(100%, 420px);
  margin: var(--space-5) auto 0;
  padding-bottom: 0.55rem;
  border-bottom: 1px solid var(--color-border-strong);
}

.hero-search input[type="search"] {
  flex: 1;
  min-width: 0;
  border: 0;
  background: transparent;
  padding: 0.35rem 0;
  font-family: inherit;
  font-size: 0.95rem;
  color: var(--color-text);
}

.hero-search input[type="search"]::placeholder {
  color: var(--color-text-faint);
}

.hero-search input[type="search"]:focus {
  outline: none;
}

.hero-search:focus-within {
  border-bottom-color: var(--color-text);
}

.hero-search-go {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 34px;
  height: 34px;
  flex: none;
  padding: 0;
  border: 0;
  border-radius: 999px;
  background: var(--color-text);
  color: #fff;
  cursor: pointer;
}

.hero-search-go svg {
  width: 16px;
  height: 16px;
  stroke: currentColor;
  fill: none;
  stroke-width: 1.8;
  stroke-linecap: round;
}

/* ---------- Brand bar (landing hero) ----------

   The strip drifts left-to-right and whichever brand is in the middle is
   highlighted — instantly, no fade or ease into it.

   How: two identical strips are stacked and driven by the SAME animation,
   so they can never fall out of register. The base layer is greyed back;
   the lens layer sits on top, larger and at full strength, and its
   wrapper is clipped to exactly one slot in the dead centre. The
   highlight is therefore a fixed window in SPACE, not a per-item timer —
   a brand is bright for precisely as long as it occupies the middle, and
   it switches on a hard clip edge. Nothing measures the container, so
   this holds at any width and any number of brands.

   The lens layer changes only font-size, never the slot width, so the
   letters get bigger without the two layers sliding apart.

   SWAPPING IN REAL LOGOS: replace the text inside .logo-mark with an
   <img>/<svg> per brand — give it `max-height: 26px; width: auto;` (and
   a taller max-height under .logo-lens). Slot geometry is fixed by
   --logo-w, so nothing about the motion or the highlight changes. */

.logo-bar {
  --logo-w: min(190px, 30vw);
  --beat: 2.2s;
  --slots: 3;
  position: relative;
  width: calc(var(--slots) * var(--logo-w));
  height: 46px;
  margin: var(--space-5) auto 0;
  overflow: hidden;
  -webkit-mask-image: linear-gradient(to right, transparent 0%, #000 22%, #000 78%, transparent 100%);
  mask-image: linear-gradient(to right, transparent 0%, #000 22%, #000 78%, transparent 100%);
}

/* Wider window on desktop — but only when there are enough brands that
   three repeats still cover it (see the seamless-loop note below); the
   template adds .logo-bar-narrow when there aren't. */
@media (min-width: 760px) {
  .logo-bar {
    --logo-w: 176px;
    --slots: 5;
  }

  .logo-bar-narrow {
    --slots: 3;
  }
}

/* The strip is rendered three times over, so shifting right by exactly
   one third lands on an identical frame — a seamless loop with no jump.
   Three repeats (rather than two) also guarantee the window stays
   covered for the whole shift, even with only a handful of brands. */
.logo-track {
  position: absolute;
  top: 0;
  left: 0;
  height: 100%;
  display: flex;
  align-items: center;
  width: max-content;
  animation: logo-marquee calc(var(--n) * var(--beat)) linear infinite;
}

@keyframes logo-marquee {
  from { transform: translateX(-33.3333%); }
  to   { transform: translateX(0); }
}

/* A grouping element for the template and for assistive tech, with no
   effect at all on the flex slot layout. */
.logo-copy {
  display: contents;
}

.logo-item {
  flex: 0 0 var(--logo-w);
  display: flex;
  align-items: center;
  justify-content: center;
}

.logo-mark {
  font-size: 0.9rem;
  font-weight: 700;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--color-text);
  white-space: nowrap;
}

/* Base layer — everything greyed back. */
.logo-bar > .logo-track {
  opacity: 0.22;
}

/* Lens layer — the same strip, the same animation, clipped to the one
   centre slot. This hard edge IS the highlight. */
.logo-lens {
  position: absolute;
  inset: 0;
  clip-path: inset(0 calc(50% - var(--logo-w) / 2));
}

.logo-lens .logo-mark {
  font-size: 1.15rem;
  font-weight: 800;
}

/* Reduced motion: no drift and no travelling highlight — the brands just
   sit there, evenly weighted, scrollable if they don't fit. Set
   explicitly rather than leaning on the blanket near-zero-duration
   override in tokens.css, which would otherwise leave the strip frozen
   at whatever offset its final keyframe happened to specify. */
@media (prefers-reduced-motion: reduce) {
  .logo-bar {
    overflow-x: auto;
    scrollbar-width: none;
    -webkit-mask-image: none;
    mask-image: none;
  }

  .logo-bar::-webkit-scrollbar {
    display: none;
  }

  .logo-lens {
    display: none;
  }

  .logo-bar > .logo-track {
    position: static;
    animation: none;
    transform: none;
    opacity: 0.5;
  }
}

/*
 * ---------------------------------------------------------------------
 * #hero-3d-mount — the hero car, and step 6's WebGL attachment point.
 * ---------------------------------------------------------------------
 * Self-contained by design. The mount reserves its own space via
 * aspect-ratio and draws the soft contact shadow itself (::after), so a
 * <canvas> can replace the <img> inside it with zero layout change and
 * without needing to re-create the shadow. Nothing outside this block
 * depends on what's inside the mount.
 *
 * No card, no border, no background: the car sits directly on the page.
 * NOTE: this reads as a true cut-out only if the source photo has a
 * white/transparent background — with a photographed backdrop it will
 * read as a floating photo instead. That's an asset question (the
 * roadmap's "photograph all 5 cars properly" track), not a CSS one.
 */
.hero-3d-mount {
  position: relative;
  width: min(100%, 980px);
  margin: var(--space-5) auto 0;
  /* aspect-ratio: 16 / 9; */
  padding: 0 var(--space-4);
}

/* No car photo yet (fresh fleet, no uploads): collapse the mount rather
   than reserve a large empty band with a shadow under nothing. The
   moment anything is mounted into it — a photo or step 6's canvas — it
   stops being :empty and comes back on its own. */
.hero-3d-mount:empty {
  display: none;
}

/* The contact shadow — a soft ellipse under the car, not a box shadow
   around a card. Drawn by the mount so 3D inherits it for free. */
.hero-3d-mount::after {
  content: "";
  position: absolute;
  left: 50%;
  bottom: 2%;
  width: 62%;
  height: 7%;
  transform: translateX(-50%);
  border-radius: 50%;
  background: radial-gradient(ellipse at center, rgba(30, 20, 10, 0.26) 0%, rgba(30, 20, 10, 0.10) 45%, rgba(30, 20, 10, 0) 72%);
  z-index: 0;
}

.hero-car {
  position: relative;
  z-index: 1;
  width: 60%;
  height: 60%;
  margin: 0 auto;
  object-fit: contain;
  animation: hero-car-float 9s ease-in-out infinite;
}

@keyframes hero-car-float {
  0%, 100% { transform: translateY(0); }
  50%      { transform: translateY(-8px); }
}

/* The float is decoration; reduced motion removes it outright rather
   than relying on the blanket near-zero-duration override in tokens.css,
   so the resting position is guaranteed rather than incidental. */
@media (prefers-reduced-motion: reduce) {
  .hero-car {
    animation: none;
    transform: none;
  }
}

/* ---------- Section / page headings ----------

   PROMOTED from .page-home. This is the one heading component for the
   whole customer site: a big light title, at most one muted line under
   it, and anything else (a status pill, a filter count) stacked beneath
   rather than floated to the opposite baseline. The old flex/
   space-between layout is gone — it was what made every page's heading
   read as a toolbar. .section-head-center is the landing's opt-in. */

.section {
  padding: var(--space-2) 0;
}

.section-head {
  display: block;
  margin: 0 0 var(--space-5);
}

.section-head h1,
.section-head h2 {
  font-size: clamp(1.9rem, 3.4vw, 2.8rem);
  font-weight: 300;
  letter-spacing: -0.03em;
  line-height: 1.08;
  margin: 0;
}

.section-head p {
  margin: var(--space-2) 0 0;
  color: var(--color-text-muted);
  font-size: 1rem;
  line-height: 1.7;
  max-width: 60ch;
}

.section-head .status-pill {
  margin-top: var(--space-3);
}

.section-head-center {
  text-align: center;
  max-width: 44ch;
  margin-left: auto;
  margin-right: auto;
}

/* The quiet "← back to …" line above a page heading. */
.back-link {
  display: inline-block;
  margin-bottom: var(--space-4);
  color: var(--color-text-muted);
  font-size: 0.9rem;
}

.back-link:hover {
  color: var(--color-text);
}

/* ---------- Fleet grid / car cards ----------

   PROMOTED from .car-carousel: the confirmed landing strips the card
   chrome entirely — no border, no fill, no shadow, no hover lift. The
   photo is the object and the page underneath stays white. The fleet
   grid now uses the identical component, so /cars and the landing read
   as one site rather than two design tiers. */

.fleet-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
  gap: var(--space-5) var(--space-4);
}

.car-card {
  color: inherit;
  text-decoration: none;
  background: transparent;
  border: 0;
  display: flex;
  flex-direction: column;
}

.car-card:hover {
  text-decoration: none;
}

.car-card-media {
  position: relative;
  aspect-ratio: 16 / 10;
  width: 100%;
  background: var(--color-surface-soft);
  border-radius: var(--radius-lg);
  overflow: hidden;
}

.car-card-media img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  transition: transform 0.25s ease;
}

.car-card:hover .car-card-media img {
  transform: scale(1.04);
}

.car-card-media.no-photo {
  display: flex;
  align-items: center;
  justify-content: center;
  color: var(--color-text-faint);
  font-size: 0.85rem;
}

/* PROMOTED: small caps, light weight, no shadow. */
.car-card-badge {
  position: absolute;
  top: var(--space-2);
  left: var(--space-2);
  background: rgba(255, 255, 255, 0.94);
  color: var(--color-text);
  font-size: 0.66rem;
  font-weight: 500;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  padding: 0.3rem 0.65rem;
  border-radius: var(--radius-pill);
}

/* PROMOTED: no horizontal padding — with the card chrome gone there's no
   box to inset the text from, so it aligns straight to the photo edge. */
.car-card-body {
  padding: var(--space-3) 0 0;
  display: flex;
  flex-direction: column;
  gap: 0.55rem;
  flex: 1;
}

.car-card-title {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--space-2);
}

.car-card-body h3 {
  font-size: 1.05rem;
  font-weight: 500;
  letter-spacing: -0.015em;
  margin: 0;
}

.car-card-year {
  color: var(--color-text-faint);
  font-weight: 400;
  font-size: 0.85rem;
  flex: none;
}

.spec-pills {
  display: flex;
  flex-wrap: wrap;
  gap: 0.4rem;
}

/* PROMOTED: outlined rather than filled — the grey chips read as UI
   chrome on pages this empty. Same content, quieter. */
.spec-pill {
  background: transparent;
  border: 1px solid var(--color-border);
  color: var(--color-text-muted);
  font-size: 0.72rem;
  font-weight: 500;
  letter-spacing: 0.03em;
  padding: 0.25rem 0.6rem;
  border-radius: var(--radius-pill);
}

.car-card-footer {
  margin-top: auto;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-2);
  padding-top: 0.15rem;
}

/* PROMOTED: 800 was listing-page weight; it fought the light headings. */
.price {
  font-weight: 500;
  font-size: 1rem;
  color: var(--color-text);
}

.price .unit {
  font-weight: 400;
  font-size: 0.78rem;
  color: var(--color-text-muted);
}

/* PROMOTED: no dashed placeholder box on a site whose whole idea is no
   boxes — the message carries itself in space. */
.empty-state {
  color: var(--color-text-muted);
  padding: var(--space-5) 0;
  text-align: center;
}

.muted {
  color: var(--color-text-muted);
  font-size: 0.9rem;
}

/* ---------- Fleet filter sidebar ---------- */

.section-fleet {
  padding-top: var(--space-4);
}

.fleet-layout {
  display: grid;
  grid-template-columns: 260px 1fr;
  gap: var(--space-5);
  align-items: start;
}

/* The filter column loses its card: no fill, no border, no shadow. The
   groups are separated by space rather than by rules, same as every
   other break on the site. */
/* Collapsed, the whole column fits on screen — but if every group is
   open at once it can still outgrow a short viewport, and a sticky
   element taller than the viewport can never be scrolled to the bottom.
   Capping it and letting it scroll internally keeps "Apply filters"
   reachable in every case. */
.fleet-sidebar {
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: var(--space-4);
  position: sticky;
  top: 110px;
  max-height: calc(100vh - 130px);
  overflow-y: auto;
  scrollbar-width: thin;
}

.fleet-sidebar-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-2);
}

.fleet-sidebar-head h2 {
  margin: 0;
  font-size: 0.78rem;
  font-weight: 500;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--color-text-faint);
}

.reset-all {
  display: inline-flex;
  align-items: center;
  gap: 0.45em;
  font-size: 0.82rem;
  font-weight: 500;
  color: var(--color-text-muted);
  text-decoration: none;
}

.reset-all:hover {
  color: var(--color-text);
  text-decoration: none;
}

/* One of the sanctioned small red accents: the count of filters you've
   actually applied. */
.filter-count-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 1.35em;
  height: 1.35em;
  padding: 0 0.4em;
  border-radius: var(--radius-pill);
  background: var(--color-primary);
  color: #fff;
  font-size: 0.7rem;
  font-weight: 500;
}

/* Search is the one control that never collapses. */
.filter-search label {
  display: block;
  font-size: 0.82rem;
  font-weight: 500;
  color: var(--color-text);
  margin-bottom: 0.4rem;
}

.filter-search input[type="search"] {
  padding: 0.65rem 1rem;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-pill);
  font-size: 0.9rem;
  font-family: inherit;
  width: 100%;
  background: var(--color-surface);
}

.filter-search input[type="search"]:focus {
  outline: none;
  border-color: var(--color-primary);
  box-shadow: 0 0 0 3px var(--color-primary-soft);
}

/* ---------- Collapsible filter categories ----------

   Each category is a <details>. Collapsed, the whole column is a short
   list of category names, so nothing gets pushed below the fold; open,
   only the one you asked for takes up room. Space separates the rows —
   no divider lines, same as everywhere else on the site. */

.filter-groups {
  display: flex;
  flex-direction: column;
  gap: 0.1rem;
}

.filter-group {
  border: 0;
  padding: 0;
  margin: 0;
}

.filter-group > summary {
  display: flex;
  align-items: center;
  gap: 0.55rem;
  padding: 0.6rem 0.75rem;
  margin: 0 -0.75rem;
  border-radius: var(--radius);
  cursor: pointer;
  font-size: 0.92rem;
  font-weight: 500;
  color: var(--color-text);
  list-style: none;
  transition: background 0.15s ease;
}

/* Hide the default triangle in every engine — we draw our own chevron. */
.filter-group > summary::-webkit-details-marker {
  display: none;
}

.filter-group > summary::marker {
  content: "";
}

.filter-group > summary:hover {
  background: var(--color-bg);
}

.filter-chevron {
  width: 15px;
  height: 15px;
  margin-left: auto;
  flex: none;
  stroke: var(--color-text-faint);
  fill: none;
  stroke-width: 1.6;
  stroke-linecap: round;
  stroke-linejoin: round;
  transition: transform 0.15s ease;
}

/* Points up once the group is open. It's a transition, so the global
   prefers-reduced-motion override in tokens.css flattens it for free. */
.filter-group[open] > summary .filter-chevron {
  transform: rotate(180deg);
}

.filter-options {
  border: 0;
  margin: 0;
  padding: 0.35rem 0 var(--space-4);
  display: flex;
  flex-direction: column;
  gap: 0.6rem;
}

.checkbox-row {
  display: flex;
  align-items: center;
  gap: 0.55rem;
  font-size: 0.87rem;
  color: var(--color-text-muted);
  cursor: pointer;
}

.checkbox-row input {
  accent-color: var(--color-primary);
  width: 16px;
  height: 16px;
  flex: none;
}

.checkbox-row:hover {
  color: var(--color-text);
}

.price-range-inputs {
  display: flex;
  align-items: center;
  gap: 0.5rem;
}

.price-range-inputs input {
  width: 100%;
  min-width: 0;
  padding: 0.55rem 0.9rem;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-pill);
  font-size: 0.87rem;
  font-family: inherit;
  background: var(--color-surface);
}

.price-range-inputs input:focus {
  outline: none;
  border-color: var(--color-primary);
  box-shadow: 0 0 0 3px var(--color-primary-soft);
}

.btn-block {
  width: 100%;
  justify-content: center;
}

.fleet-results-head {
  margin-bottom: var(--space-4);
}

.fleet-count {
  color: var(--color-text-faint);
  font-size: 0.78rem;
  font-weight: 500;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  margin: 0;
}

.fleet-empty-state {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: var(--space-2);
  color: var(--color-text-muted);
}

.fleet-empty-state svg {
  stroke: var(--color-text-faint);
  fill: none;
  stroke-width: 1.6;
  stroke-linecap: round;
  stroke-linejoin: round;
}

.fleet-empty-state h3 {
  color: var(--color-text);
  margin: 0;
}

.fleet-empty-state p {
  margin: 0 0 var(--space-1);
}

@media (max-width: 860px) {
  .fleet-layout {
    grid-template-columns: 1fr;
  }

  /* Stacked above the results, it must not cap its own height or scroll
     inside itself — the page scroll is the right one there. */
  .fleet-sidebar {
    position: static;
    max-height: none;
    overflow-y: visible;
  }
}

/* ---------- Featured-car carousel (landing only) ----------

   Everything this block used to override — chrome-less card, lightened
   type, outlined spec-pills, quiet badge and price — has been PROMOTED
   to the shared .car-card component above, so the fleet grid and this
   strip are now literally the same card. What's left here is only what
   makes it a carousel rather than a grid: scroll-snap and slide width. */

.car-carousel {
  display: flex;
  gap: var(--space-4);
  overflow-x: auto;
  scroll-snap-type: x mandatory;
  scroll-behavior: smooth;
  padding: var(--space-2) var(--space-4) var(--space-4);
  margin: 0 calc(-1 * var(--space-4));
  scrollbar-width: none;
}

.car-carousel::-webkit-scrollbar {
  display: none;
}

.car-carousel .car-card {
  scroll-snap-align: start;
  flex: 0 0 auto;
  width: min(78vw, 300px);
}

@media (min-width: 900px) {
  .car-carousel {
    gap: var(--space-5);
  }

  .car-carousel .car-card {
    width: 320px;
  }
}

/* ---------- Landing "why book with us" features ---------- */

/* Separated by space, not by a rule — same as every other break on this
   page. Centred to sit under a centred hero and section heading. */
.feature-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
  gap: var(--space-6) var(--space-5);
  max-width: 940px;
  margin: 0 auto;
}

.feature {
  text-align: center;
}

/* No tinted chip behind the icon — a thin monochrome line mark is enough
   at this scale, and it keeps red out of a three-across band. */
.feature-icon {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  color: var(--color-text-faint);
  margin-bottom: var(--space-3);
}

.feature-icon svg {
  width: 24px;
  height: 24px;
  stroke: currentColor;
  fill: none;
  stroke-width: 1.3;
  stroke-linecap: round;
  stroke-linejoin: round;
}

.feature h3 {
  font-size: 1.1rem;
  font-weight: 500;
  letter-spacing: -0.015em;
  margin: 0 0 0.6rem;
}

.feature p {
  color: var(--color-text-muted);
  margin: 0 auto;
  font-size: 0.92rem;
  line-height: 1.75;
  max-width: 32ch;
}

/* ---------- Car detail ---------- */

.detail-grid {
  display: grid;
  grid-template-columns: 1.5fr 1fr;
  gap: var(--space-6);
  align-items: start;
}

@media (max-width: 860px) {
  .detail-grid {
    grid-template-columns: 1fr;
    gap: var(--space-5);
  }
}

/* The car's own heading block: light display type, year and specs
   beneath it, no box. */
.detail-title {
  font-size: clamp(2rem, 4vw, 3.2rem);
  font-weight: 300;
  letter-spacing: -0.035em;
  line-height: 1.03;
  margin: 0;
}

.detail-meta {
  margin: var(--space-2) 0 var(--space-5);
  color: var(--color-text-faint);
  font-size: 0.95rem;
}

/* ---------- Car gallery ----------

   A scroll-snap track of full-width slides. Swipe/drag works natively;
   the arrows and thumbs are anchors to each slide's id, so "next photo"
   costs zero JavaScript. scroll-behavior stays smooth but is flattened
   by the global prefers-reduced-motion override in tokens.css. */

.gallery {
  position: relative;
  border-radius: var(--radius-lg);
  overflow: hidden;
  background: var(--color-surface-soft);
  margin-bottom: var(--space-3);
}

.gallery-track {
  display: flex;
  overflow-x: auto;
  scroll-snap-type: x mandatory;
  scroll-behavior: smooth;
  scrollbar-width: none;
}

.gallery-track::-webkit-scrollbar {
  display: none;
}

.gallery-slide {
  position: relative;
  flex: 0 0 100%;
  scroll-snap-align: center;
  aspect-ratio: 16 / 10;
  display: flex;
  align-items: center;
  justify-content: center;
}

.gallery-slide img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.gallery-arrow {
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
  display: flex;
  align-items: center;
  justify-content: center;
  width: 40px;
  height: 40px;
  border-radius: var(--radius-pill);
  background: rgba(255, 255, 255, 0.92);
  color: var(--color-text);
  transition: background 0.15s ease;
}

.gallery-arrow:hover {
  background: #fff;
  text-decoration: none;
}

.gallery-arrow svg {
  width: 18px;
  height: 18px;
  stroke: currentColor;
  fill: none;
  stroke-width: 1.6;
  stroke-linecap: round;
  stroke-linejoin: round;
}

.gallery-arrow-prev { left: var(--space-3); }
.gallery-arrow-next { right: var(--space-3); }

.gallery-counter {
  position: absolute;
  bottom: var(--space-3);
  right: var(--space-3);
  padding: 0.25rem 0.65rem;
  border-radius: var(--radius-pill);
  background: rgba(255, 255, 255, 0.92);
  color: var(--color-text);
  font-size: 0.72rem;
  font-weight: 500;
  letter-spacing: 0.04em;
}

/* Touch devices get the swipe; the arrows would just cover the photo. */
@media (hover: none) {
  .gallery-arrow {
    display: none;
  }
}

.gallery-thumbs {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(96px, 1fr));
  gap: var(--space-2);
  margin-bottom: var(--space-4);
}

.gallery-thumbs a {
  display: block;
  border-radius: var(--radius);
  overflow: hidden;
  opacity: 0.72;
  transition: opacity 0.15s ease;
}

.gallery-thumbs a:hover {
  opacity: 1;
  text-decoration: none;
}

.gallery-thumbs img {
  width: 100%;
  aspect-ratio: 4 / 3;
  object-fit: cover;
  background: var(--color-surface-soft);
}

/* ---------- Booking panel ----------

   This is the conversion surface, so it's the one place on the site that
   deliberately reads as a distinct object — but still the quiet way the
   nav bar does it: soft fill, one hairline, no shadow. The red lives in
   the submit button inside it, not in the panel. */

.booking-panel {
  background: var(--color-bg);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-xl);
  padding: var(--space-5);
  position: sticky;
  top: 110px;
}

.booking-panel .price {
  font-size: 1.9rem;
  font-weight: 300;
  letter-spacing: -0.03em;
}

.booking-panel .price-sub {
  color: var(--color-text-muted);
  font-size: 0.85rem;
  margin-bottom: var(--space-5);
}

.booking-panel .checkbox-row {
  margin-bottom: var(--space-4);
}

/* The same panel carries the "what to do next" column on the booking
   confirmation page, so its heading needs a size of its own — the panel
   has no heading at all on the car page. */
.booking-panel > h3 {
  margin: 0 0 var(--space-3);
  font-size: 1.15rem;
  font-weight: 500;
  letter-spacing: -0.015em;
  line-height: 1.35;
}

.booking-panel > p:last-child {
  margin-bottom: 0;
}

.date-fields {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: var(--space-3);
}

@media (max-width: 420px) {
  .date-fields {
    grid-template-columns: 1fr;
  }
}

/* ---------- Booking calendar ----------

   Injected above the two native datetime-local inputs by datepicker.js.
   Without the script none of these rules match anything and the panel
   renders exactly as it did before — this is styling for an enhancement,
   not for a requirement. */

.calendar {
  margin-bottom: var(--space-4);
}

.calendar-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-2);
  margin-bottom: var(--space-3);
}

.calendar-title {
  font-size: 0.95rem;
  font-weight: 500;
  letter-spacing: -0.01em;
}

.calendar-nav {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 30px;
  height: 30px;
  flex: none;
  padding: 0;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-pill);
  background: var(--color-surface);
  color: var(--color-text);
  cursor: pointer;
  transition: background 0.15s ease, opacity 0.15s ease;
}

.calendar-nav:hover:not(:disabled) {
  background: var(--color-neutral-soft);
}

.calendar-nav:disabled {
  opacity: 0.3;
  cursor: default;
}

.calendar-nav svg {
  width: 14px;
  height: 14px;
  stroke: currentColor;
  fill: none;
  stroke-width: 1.8;
  stroke-linecap: round;
  stroke-linejoin: round;
}

.calendar-dow,
.calendar-grid {
  display: grid;
  grid-template-columns: repeat(7, 1fr);
  gap: 2px;
}

.calendar-dow {
  margin-bottom: 0.35rem;
}

.calendar-dow span {
  text-align: center;
  font-size: 0.66rem;
  font-weight: 500;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--color-text-faint);
}

.calendar-day {
  aspect-ratio: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  border: 0;
  border-radius: var(--radius-pill);
  background: transparent;
  color: var(--color-text);
  font: inherit;
  font-size: 0.85rem;
  cursor: pointer;
  transition: background 0.12s ease, color 0.12s ease;
}

.calendar-day:hover:not(:disabled) {
  background: var(--color-neutral-soft);
}

.calendar-day.is-past {
  color: var(--color-border-strong);
  cursor: default;
}

/* Booked days are struck through as well as greyed — colour alone
   shouldn't be the only thing saying "you can't have this". */
.calendar-day.is-booked {
  color: var(--color-text-faint);
  background: var(--color-neutral-soft);
  cursor: not-allowed;
  text-decoration: line-through;
  text-decoration-thickness: 1px;
}

.calendar-day.is-between {
  background: var(--color-primary-soft);
  border-radius: 0;
}

.calendar-day.is-start,
.calendar-day.is-end {
  background: var(--color-primary);
  color: #fff;
}

.calendar-blank {
  aspect-ratio: 1;
}

.calendar-summary {
  margin: var(--space-3) 0 0;
  font-size: 0.88rem;
  color: var(--color-text-muted);
}

.calendar-legend {
  display: flex;
  align-items: center;
  gap: 0.45rem;
  margin: 0.4rem 0 0;
  font-size: 0.78rem;
  color: var(--color-text-faint);
}

.calendar-legend-dot {
  width: 10px;
  height: 10px;
  border-radius: var(--radius-pill);
  background: var(--color-neutral-soft);
  border: 1px solid var(--color-border-strong);
}

/* Once enhanced, the calendar owns the date and the two native
   datetime-local controls are switched to type="hidden" by the script —
   so this wrapper holds nothing visible and its labels would otherwise
   float on their own. Without the script this rule never applies and the
   native fields render normally. */
.date-picker-enhanced .date-fields {
  display: none;
}

/* The custom time controls that replace them. */
.time-fields {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: var(--space-3);
  margin-top: var(--space-4);
  padding-top: var(--space-4);
  border-top: 1px solid var(--color-border);
}

@media (max-width: 420px) {
  .time-fields {
    grid-template-columns: 1fr;
  }
}

/* ---------- Clock time picker ----------

   A trigger pill that opens an analog face. Every hour, minute and
   AM/PM target is a real <button>, so the whole thing is tab-navigable
   and Enter/Space-operable; Escape closes it. Injected by datepicker.js
   — with no script these rules match nothing and the native
   datetime-local controls render instead. */

.clock-field {
  position: relative;
  margin-bottom: 0;
}

.clock-trigger {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  width: 100%;
  padding: 0.7rem 1rem;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-pill);
  background: var(--color-surface);
  color: var(--color-text);
  font: inherit;
  font-size: 0.95rem;
  font-variant-numeric: tabular-nums;
  cursor: pointer;
  transition: border-color 0.12s ease, box-shadow 0.12s ease;
}

.clock-trigger:hover {
  border-color: var(--color-border-strong);
}

.clock-open .clock-trigger,
.clock-trigger:focus-visible {
  border-color: var(--color-primary);
  box-shadow: 0 0 0 3px var(--color-primary-soft);
  outline: none;
}

.clock-icon {
  width: 16px;
  height: 16px;
  flex: none;
  stroke: var(--color-text-faint);
  fill: none;
  stroke-width: 1.5;
  stroke-linecap: round;
}

.clock-pop {
  position: absolute;
  z-index: 20;
  top: calc(100% + 0.5rem);
  left: 0;
  width: 236px;
  max-width: 84vw;
  padding: var(--space-3);
  background: var(--color-surface);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-xl);
  box-shadow: 0 12px 32px rgba(30, 20, 10, 0.13);
}

/* The right-hand clock would otherwise overflow the booking panel. */
.time-fields > .clock-field:last-child .clock-pop {
  left: auto;
  right: 0;
}

.clock-meridiem {
  display: flex;
  gap: 0.25rem;
  padding: 0.2rem;
  margin-bottom: var(--space-3);
  border-radius: var(--radius-pill);
  background: var(--color-neutral-soft);
}

.clock-mer {
  flex: 1;
  padding: 0.3rem 0;
  border: 0;
  border-radius: var(--radius-pill);
  background: transparent;
  color: var(--color-text-muted);
  font: inherit;
  font-size: 0.78rem;
  font-weight: 500;
  letter-spacing: 0.06em;
  cursor: pointer;
  transition: background 0.12s ease, color 0.12s ease;
}

.clock-mer.is-on {
  background: var(--color-surface);
  color: var(--color-text);
}

.clock-face {
  position: relative;
  width: 200px;
  height: 200px;
  max-width: 100%;
  margin: 0 auto var(--space-3);
  border-radius: 50%;
  background: var(--color-bg);
}

/* Each hour sits in a slot rotated around the centre; the button inside
   is counter-rotated so the numeral stays upright. No trigonometry.

   The slots are inset:0, so all twelve are full-size layers stacked on
   top of each other — without pointer-events:none the topmost one
   swallows every click on the face and only its own hour is ever
   reachable. Events belong to the buttons, not the slots. */
.clock-slot {
  position: absolute;
  inset: 0;
  display: flex;
  justify-content: center;
  padding-top: 8px;
  pointer-events: none;
}

.clock-hour {
  pointer-events: auto;
  width: 30px;
  height: 30px;
  display: flex;
  align-items: center;
  justify-content: center;
  border: 0;
  border-radius: 50%;
  background: transparent;
  color: var(--color-text);
  font: inherit;
  font-size: 0.85rem;
  font-variant-numeric: tabular-nums;
  cursor: pointer;
  transition: background 0.12s ease, color 0.12s ease;
}

.clock-hour:hover {
  background: var(--color-neutral-soft);
}

.clock-hour.is-on {
  background: var(--color-primary);
  color: #fff;
}

.clock-centre {
  position: absolute;
  top: 50%;
  left: 50%;
  width: 7px;
  height: 7px;
  margin: -3.5px 0 0 -3.5px;
  border-radius: 50%;
  background: var(--color-primary);
}

.clock-hand {
  position: absolute;
  bottom: 50%;
  left: 50%;
  width: 2px;
  height: 62px;
  margin-left: -1px;
  border-radius: var(--radius-pill);
  background: var(--color-primary);
  transform-origin: bottom center;
  transition: transform 0.18s ease;
  pointer-events: none;
}

.clock-minutes {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 0.3rem;
}

.clock-minute {
  padding: 0.4rem 0;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-pill);
  background: var(--color-surface);
  color: var(--color-text-muted);
  font: inherit;
  font-size: 0.78rem;
  font-variant-numeric: tabular-nums;
  cursor: pointer;
  transition: background 0.12s ease, color 0.12s ease, border-color 0.12s ease;
}

.clock-minute:hover {
  border-color: var(--color-border-strong);
  color: var(--color-text);
}

.clock-minute.is-on {
  background: var(--color-primary);
  border-color: var(--color-primary);
  color: #fff;
}

.booked-note {
  margin-bottom: var(--space-4);
}

/* PROMOTED: pill inputs to match the pill buttons, a hairline border
   instead of the heavier one, and a label that reads as a quiet caption
   rather than a bold field name. A multi-line textarea keeps a rounded
   rectangle — a pill textarea just clips its own first and last lines. */
.field {
  margin-bottom: var(--space-4);
}

.field label {
  display: block;
  margin-bottom: 0.4rem;
  font-size: 0.82rem;
  font-weight: 500;
  letter-spacing: 0.01em;
  color: var(--color-text-muted);
}

.field input,
.field select,
.field textarea {
  width: 100%;
  padding: 0.7rem 1rem;
  border: 1px solid var(--color-border);
  border-radius: var(--radius-pill);
  font-size: 0.95rem;
  font-family: inherit;
  background: var(--color-surface);
  color: var(--color-text);
  transition: border-color 0.12s ease, box-shadow 0.12s ease;
}

.field textarea {
  border-radius: var(--radius-lg);
}

.field input:focus,
.field select:focus,
.field textarea:focus {
  outline: none;
  border-color: var(--color-primary);
  box-shadow: 0 0 0 3px var(--color-primary-soft);
}

/* File inputs can't take the pill treatment gracefully across browsers —
   the native "Choose file" button squares off the left end. Give them a
   soft rectangle instead of a broken pill. */
.field input[type="file"] {
  border-radius: var(--radius-lg);
  padding: 0.6rem 0.75rem;
  font-size: 0.9rem;
}

.field-hint {
  color: var(--color-text-muted);
  font-size: 0.8rem;
  margin-top: 0.5rem;
  line-height: 1.6;
}

/* "(optional)" beside a field label — was an inline style override on
   .field-hint, which is a block. */
.label-optional {
  color: var(--color-text-faint);
  font-weight: 400;
}

/* The itemized price. Every line the engine produced is still shown,
   verbatim — this only relaxes the spacing and drops the dashed rule so
   it reads as a statement rather than a receipt. */
.pricing-breakdown {
  font-size: 0.92rem;
}

.pricing-breakdown .row {
  display: flex;
  justify-content: space-between;
  gap: var(--space-3);
  padding: 0.45rem 0;
  color: var(--color-text-muted);
}

.pricing-breakdown .row.total {
  color: var(--color-text);
  font-weight: 500;
  font-size: 1.35rem;
  letter-spacing: -0.02em;
  border-top: 1px solid var(--color-border);
  margin-top: var(--space-2);
  padding-top: var(--space-3);
}

/* An adjustment that changed the price gets the sanctioned small red —
   it's the one thing on the page a customer must not miss. */
.pricing-breakdown .uplift-note {
  color: var(--color-primary);
}

#booking-result {
  margin-top: var(--space-3);
}

/* Feedback keeps its colour — an error must not be quiet — but loses the
   double treatment of tint AND border. Tint alone, softly rounded. */
.alert {
  padding: 0.8rem 1.1rem;
  border-radius: var(--radius-lg);
  border: 0;
  font-size: 0.9rem;
  line-height: 1.6;
  margin-bottom: var(--space-4);
}

.alert-error {
  background: var(--color-danger-soft);
  color: var(--color-danger);
}

.alert-success {
  background: var(--color-success-soft);
  color: var(--color-success);
}

.alert-info {
  background: var(--color-info-soft);
  color: var(--color-info);
}

/* ---------- Status pills (plain-language booking/kyc status) ----------

   PROMOTED to the monochrome language: the pill itself is now an
   outline with plain text, and the tone colour survives only in the
   little dot. That keeps the status readable AND semantically colour-
   coded (nothing is lost) without five tinted chips fighting a
   near-monochrome page. */

.status-pill {
  display: inline-flex;
  align-items: center;
  gap: 0.5em;
  padding: 0.35rem 0.85rem;
  border-radius: var(--radius-pill);
  font-size: 0.78rem;
  font-weight: 500;
  letter-spacing: 0.01em;
  background: transparent;
  border: 1px solid var(--color-border);
  color: var(--color-text);
  white-space: nowrap;
}

.status-pill::before {
  content: "";
  width: 6px;
  height: 6px;
  flex: none;
  border-radius: var(--radius-pill);
  background: var(--color-text-faint);
}

.status-pill.tone-warning::before { background: var(--color-warning); }
.status-pill.tone-success::before { background: var(--color-success); }
.status-pill.tone-info::before    { background: var(--color-info); }
.status-pill.tone-neutral::before { background: var(--color-text-faint); }
.status-pill.tone-danger::before  { background: var(--color-danger); }

/* ---------- Panels / auth pages ----------

   PROMOTED: no drop shadows anywhere on the customer site. Where a group
   of content genuinely needs to read as its own surface (a price
   breakdown, the booking panel, an auth form) it gets the same treatment
   the floating nav bar uses — a soft --color-bg fill and one hairline —
   never a raised white card. Plain content groups get no box at all. */

.card {
  background: var(--color-bg);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-lg);
  padding: var(--space-5);
  margin-bottom: var(--space-4);
}

.card > h3 {
  margin: 0 0 var(--space-3);
  font-size: 1.05rem;
  font-weight: 500;
}

.card > p:last-child,
.card > .instructions-list:last-child {
  margin-bottom: 0;
}

/* A content group that needs spacing but not a surface — the default
   choice on these pages. */
.block {
  margin-bottom: var(--space-5);
}

.block > h3 {
  margin: 0 0 var(--space-3);
  font-size: 1.05rem;
  font-weight: 500;
}

.narrow {
  max-width: 560px;
  margin: 0 auto;
}

.auth-wrap {
  min-height: calc(100vh - 220px);
  display: flex;
  align-items: center;
  justify-content: center;
  padding: var(--space-6) var(--space-3);
}

.auth-card {
  background: transparent;
  padding: 0;
  width: 100%;
  max-width: 400px;
  text-align: center;
}

.auth-card .brand-logo {
  height: 44px;
  margin: 0 auto var(--space-4);
}

.auth-card h1 {
  font-size: clamp(1.8rem, 4vw, 2.4rem);
  font-weight: 300;
  letter-spacing: -0.03em;
  margin: 0 0 var(--space-2);
}

.auth-card .subtitle {
  color: var(--color-text-muted);
  font-size: 0.95rem;
  margin: 0 0 var(--space-5);
}

/* The form itself reads left-aligned even though the header is centred —
   labels above pill inputs shouldn't be centred. */
.auth-card form {
  text-align: left;
}

.auth-switch {
  margin-top: var(--space-4);
  font-size: 0.9rem;
  color: var(--color-text-muted);
  text-align: center;
}

/* ---------- Booking summary (booking confirmation page) ---------- */

.booking-summary {
  display: flex;
  align-items: center;
  gap: var(--space-4);
  flex-wrap: wrap;
  margin-bottom: var(--space-6);
}

.booking-summary-media {
  width: 180px;
  aspect-ratio: 4 / 3;
  border-radius: var(--radius-lg);
  overflow: hidden;
  background: var(--color-surface-soft);
  flex-shrink: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  color: var(--color-text-faint);
  font-size: 0.85rem;
}

.booking-summary-media img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.booking-summary-body {
  flex: 1;
  min-width: 200px;
  display: flex;
  flex-direction: column;
  gap: var(--space-2);
}

.booking-summary .price {
  font-size: 1.5rem;
  font-weight: 300;
  letter-spacing: -0.03em;
}

/* ---------- My bookings ----------

   Deliberately NOT the fleet grid. A booking is a record of something
   you already did, so it reads as a list of rows — status first, wide
   and horizontal — rather than a wall of browsable cards. The photo,
   dates, status and total are all still here; only the arrangement
   differs. It reuses .car-card-media, .status-pill and .price rather
   than forking lookalike classes. */

.booking-list {
  display: flex;
  flex-direction: column;
  gap: var(--space-3);
}

.booking-row {
  display: grid;
  grid-template-columns: 132px 1fr auto;
  align-items: center;
  gap: var(--space-4);
  padding: var(--space-3);
  border: 1px solid var(--color-border);
  border-radius: var(--radius-xl);
  color: inherit;
  text-decoration: none;
  transition: background 0.15s ease, border-color 0.15s ease;
}

.booking-row:hover {
  background: var(--color-bg);
  border-color: var(--color-border-strong);
  text-decoration: none;
}

.booking-row .car-card-media {
  aspect-ratio: 4 / 3;
}

.booking-row-body {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 0.45rem;
  min-width: 0;
}

/* The status leads the row — it's the reason you opened this page. */
.booking-row .status-pill {
  background: var(--color-surface);
}

.booking-row-body h3 {
  margin: 0;
  font-size: 1.1rem;
  font-weight: 500;
}

.booking-row-dates {
  margin: 0;
  color: var(--color-text-muted);
  font-size: 0.9rem;
}

.booking-row-end {
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 0.55rem;
  text-align: right;
}

@media (max-width: 620px) {
  .booking-row {
    grid-template-columns: 96px 1fr;
  }

  .booking-row-end {
    grid-column: 1 / -1;
    flex-direction: row;
    align-items: center;
    justify-content: space-between;
    text-align: left;
  }
}

/* ---------- Payment claims (booking confirmation + admin review) ---------- */

.payment-row {
  padding: var(--space-4) 0 0;
  margin-top: var(--space-4);
  border-top: 1px solid var(--color-border);
}

.payment-row:first-of-type {
  border-top: 0;
  margin-top: 0;
  padding-top: 0;
}

.payment-row-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-2);
  margin-bottom: 0.3rem;
}

.payment-row code,
.muted code {
  background: var(--color-neutral-soft);
  padding: 0.15em 0.4em;
  border-radius: var(--radius-sm);
  font-size: 0.85em;
  word-break: break-word;
}

/* ---------- KYC ----------
   (.kyc-dropzone removed — no template ever referenced it.) */

.kyc-file-fields {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
  gap: var(--space-3);
}

/* The one instruction that matters on the booking page. */
.pay-line {
  margin: 0 0 var(--space-3);
  font-size: 1.05rem;
  line-height: 1.7;
}

.pay-line strong {
  font-weight: 500;
}

.pay-code {
  font-variant-numeric: tabular-nums;
  letter-spacing: 0.04em;
  white-space: nowrap;
}

.instructions-list {
  margin: 0;
  padding-left: 1.2rem;
  color: var(--color-text-muted);
}

.instructions-list li {
  margin-bottom: 0.7rem;
}

.instructions-list strong {
  color: var(--color-text);
  font-weight: 500;
}

/* ---------- Landing page ----------

   Almost everything that used to live here under .page-home has been
   PROMOTED to the shared layer above — the white page background, the
   heading scale, the centred-head modifier, the chrome-less empty state,
   the footer. What's left is genuinely landing-only. */

.section-cta {
  display: flex;
  justify-content: center;
  margin-top: var(--space-5);
}

/* The closing band gets the most air on the page. */
.page-home .section-features {
  padding-bottom: var(--space-6);
}

/* ---------- Footer ----------

   PROMOTED from .page-home: no top rule, more air, quieter text. The
   page ends in space rather than against a line. */

.site-footer {
  padding: var(--space-5) 0 var(--space-6);
  color: var(--color-text-faint);
  font-size: 0.85rem;
  text-align: center;
}
