/* =============================================================================
   J CYCLE STUDIO — BOOKING
   Split screen: the room on the left, the flow on the right. Header + this section
   is exactly one viewport on desktop, so you can book without scrolling first.
   Reuses site.css for tokens, buttons, header, .days/.day and the WhatsApp float.
============================================================================= */

:root { --bar-h: 68px; }

.book {
  display: grid;
  grid-template-columns: minmax(300px, 36%) 1fr;
  height: calc(100svh - var(--header-h));
  border-bottom: 1px solid var(--line);
}

/* ------------------------------------------------------------- left panel -- */
.book__panel {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  border-right: 1px solid var(--line);
}
.book__panel-media { position: absolute; inset: 0; z-index: -2; }
.book__panel-media img { width: 100%; height: 100%; object-fit: cover; }
.book__panel::before {
  content: '';
  position: absolute;
  inset: 0;
  z-index: -1;
  background:
    radial-gradient(80% 50% at 50% 0%, rgba(254, 0, 2, 0.3), transparent 65%),
    linear-gradient(to bottom, rgba(0, 0, 0, 0.72) 0%, rgba(0, 0, 0, 0.9) 55%, rgba(0, 0, 0, 0.96) 100%);
}
.book__panel-inner {
  height: 100%;
  display: flex;
  flex-direction: column;
  gap: clamp(1.25rem, 3vh, 2.25rem);
  padding: clamp(1.5rem, 3.5vh, 2.75rem) clamp(1.25rem, 2.4vw, 2.25rem);
  overflow: hidden;
}
.book__title {
  font-size: clamp(2rem, 3.4vw, 3.25rem);
  margin-top: 0.75rem;
}

/* progress rail — also the way back. The <li> keeps the rule and the colour state;
   the button inside it is the hit area, so a completed step is a place you can
   return to without walking Back through every step between. */
.steps { display: flex; flex-direction: column; gap: 0.1rem; }
.step {
  border-bottom: 1px solid var(--line);
  color: var(--fg-3);
  transition: color 0.3s var(--ease);
}
.step__go {
  display: grid;
  grid-template-columns: auto 1fr;
  align-items: center;
  gap: 0.85rem;
  width: 100%;
  padding: 0.6rem 0;
  text-align: left;
}
.step__go[disabled] { cursor: default; }
.step[data-state='done'] .step__go:not([disabled]):hover .step__n {
  border-color: var(--white);
  color: var(--white);
}
.step__n {
  font-family: var(--font-mono);
  font-size: 0.6rem;
  font-weight: 700;
  letter-spacing: 0.1em;
  width: 2.1rem;
  height: 2.1rem;
  display: grid;
  place-items: center;
  border: 1px solid var(--line);
  border-radius: 50%;
  transition: all 0.3s var(--ease);
}
.step__t { font-size: var(--fs-sm); }

.step[data-state='current'] { color: var(--white); }
.step[data-state='current'] .step__n {
  background: var(--red);
  border-color: var(--red);
  color: var(--on-red);
  box-shadow: var(--glow-sm);
}
.step[data-state='done'] { color: var(--fg-2); }
.step[data-state='done'] .step__n { border-color: var(--red); color: var(--red); }

/* running summary */
.summary { margin-top: auto; border-top: 1px solid var(--line); padding-top: 1rem; }
.summary__row {
  display: grid;
  grid-template-columns: 4.5rem 1fr;
  gap: 0.75rem;
  padding: 0.4rem 0;
  align-items: baseline;
}
.summary dt {
  font-family: var(--font-mono);
  font-size: 0.56rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fg-3);
}
.summary dd { font-size: var(--fs-sm); color: var(--fg); font-weight: 500; }

/* ------------------------------------------------------------ right side --- */
.book__main {
  display: grid;
  grid-template-rows: 1fr auto;
  min-height: 0;               /* lets the scroll row actually shrink */
  min-width: 0;
}
.book__scroll {
  overflow-y: auto;
  min-height: 0;
  padding: clamp(1.5rem, 4vh, 3rem) clamp(1.25rem, 3vw, 3rem);
  scrollbar-width: thin;
  scrollbar-color: var(--nero-3) transparent;
}
.book__scroll::-webkit-scrollbar { width: 6px; }
.book__scroll::-webkit-scrollbar-thumb { background: var(--nero-3); }

.pane { max-width: 760px; animation: pane-in 0.45s var(--ease); }
@keyframes pane-in { from { opacity: 0; transform: translateY(10px); } to { opacity: 1; transform: none; } }

.pane__eyebrow { color: var(--red); margin-bottom: 0.85rem; }
.pane__h {
  font-family: var(--font-display);
  font-size: clamp(1.6rem, 3vw, 2.4rem);
  font-weight: 900;
  line-height: 0.95;
  letter-spacing: -0.03em;
  text-transform: uppercase;
}
.pane__note { color: var(--fg-3); font-size: var(--fs-sm); margin-top: 0.75rem; max-width: 52ch; }

/* action bar */
.book__bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  min-height: var(--bar-h);
  padding: 0.85rem clamp(1.25rem, 3vw, 3rem);
  border-top: 1px solid var(--line);
  background: rgba(0, 0, 0, 0.7);
}

/* On every other page the bottom-right corner belongs to the WhatsApp button.
   Here it belongs to Next, and the float was landing dead on the centre of it —
   the flow's primary action, unclickable. This is the resting offset; booking.js
   then keeps the float tied to the bar as the page scrolls, because the footer
   below this screen lets the bar ride up out from under a fixed offset.
   (position:sticky can't do it: the bar already sits at the bottom of a
   fixed-height parent, so there's no slack for it to stick against.) */
.wa-float { bottom: calc(var(--bar-h) + clamp(0.7rem, 2vw, 1.1rem)); }
.book__hint {
  font-family: var(--font-mono);
  font-size: 0.58rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--fg-3);
  text-align: center;
  flex: 1;
}
.btn[disabled] { opacity: 0.32; pointer-events: none; }

/* ------------------------------------------------------ 01 · the schedule -- */
/* One row per real class on a real day: time first, because that is what people
   are actually choosing between. */
.book .days { margin-top: 1.5rem; }
.classes { display: grid; gap: 0.6rem; margin-top: 0.5rem; }
.class-pick {
  display: grid;
  grid-template-columns: auto 92px 1fr auto auto;
  align-items: center;
  gap: clamp(0.75rem, 1.6vw, 1.25rem);
  padding: 0.7rem 0.85rem;
  border: 1px solid var(--line);
  background: var(--nero-1);
  text-align: left;
  width: 100%;
  transition: border-color 0.25s var(--ease), background 0.25s var(--ease), transform 0.25s var(--ease);
}
.class-pick:hover:not([disabled]) { border-color: var(--line-strong); transform: translateX(3px); }
.class-pick[aria-pressed='true'] {
  border-color: var(--red);
  background: rgba(254, 0, 2, 0.07);
  box-shadow: var(--glow-sm);
}
.class-pick[disabled] { opacity: 0.34; cursor: not-allowed; }
.class-pick__t {
  font-family: var(--font-mono);
  font-size: clamp(1rem, 1.5vw, 1.2rem);
  font-weight: 700;
  letter-spacing: 0.02em;
  min-width: 4.5ch;
}
.class-pick__img { width: 92px; height: 70px; object-fit: cover; }
.class-pick__b { display: flex; flex-direction: column; gap: 0.2rem; min-width: 0; }
.class-pick__n {
  font-family: var(--font-display);
  font-size: 1.02rem;
  font-weight: 800;
  text-transform: uppercase;
  letter-spacing: -0.01em;
}
.class-pick__m {
  font-family: var(--font-mono);
  font-size: 0.56rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--red);
}
.class-pick__l {
  font-family: var(--font-mono);
  font-size: 0.56rem;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--fg-3);
  white-space: nowrap;
}
.class-pick__l.is-low { color: var(--red); }
.class-pick__l.is-off { text-decoration: line-through; }
.class-pick__tick {
  width: 22px;
  height: 22px;
  border: 1px solid var(--line-strong);
  border-radius: 50%;
  display: grid;
  place-items: center;
  color: transparent;
  transition: all 0.25s var(--ease);
  flex: 0 0 auto;
}
.class-pick[aria-pressed='true'] .class-pick__tick { background: var(--red); border-color: var(--red); color: var(--on-red); }
.times__empty { color: var(--fg-3); padding: 2.5rem 0; font-size: var(--fs-sm); }

/* --------------------------------------------------------- 02 · the floor -- */

/* The room, drawn to scale: bikes in staggered rows, all pointed at the stage. */
.floor__wrap { margin-top: 1.75rem; overflow-x: auto; padding-bottom: 0.5rem; }
.floor {
  position: relative;
  aspect-ratio: 100 / 70;
  min-width: 460px;            /* below this the bikes stop being tappable */
  max-width: 620px;
  margin-inline: auto;
  background:
    radial-gradient(70% 42% at 50% 4%, rgba(254, 0, 2, 0.22), transparent 62%),
    var(--nero-2);
  border: 1px solid var(--line);
}
.floor__stage {
  position: absolute;
  left: 50%;
  top: 8.6%;
  transform: translate(-50%, -50%);
  width: 46%;
  height: 9%;
  display: grid;
  place-items: center;
  background: var(--red);
  color: var(--on-red);
  box-shadow: var(--glow-md);
}
.floor__stage .mono { font-size: 0.5rem; letter-spacing: 0.2em; }

.bike {
  position: absolute;
  width: 9%;
  aspect-ratio: 1;
  transform: translate(-50%, -50%);
  border-radius: 50%;
  border: 1px solid var(--line-strong);
  background: var(--nero-3);
  color: var(--fg-2);
  font-family: var(--font-mono);
  font-size: 0.56rem;
  font-weight: 700;
  display: grid;
  place-items: center;
  transition: background 0.2s, border-color 0.2s, color 0.2s, transform 0.2s var(--ease);
}
/* fattens the hit area past the visual circle without moving the dot */
.bike::before { content: ''; position: absolute; inset: -5px; border-radius: 50%; }
.bike:hover:not([disabled]) { border-color: var(--red); color: var(--white); transform: translate(-50%, -50%) scale(1.14); }
.bike[disabled] { background: transparent; border-style: dashed; border-color: rgba(255, 255, 255, 0.14); color: rgba(255, 255, 255, 0.22); cursor: not-allowed; }
.bike[aria-pressed='true'] {
  background: var(--red);
  border-color: var(--red);
  color: var(--on-red);
  box-shadow: var(--glow-sm);
  transform: translate(-50%, -50%) scale(1.16);
}

.legend { display: flex; flex-wrap: wrap; gap: 1.25rem; margin-top: 1.25rem; }
.legend li {
  display: flex;
  align-items: center;
  gap: 0.5rem;
  font-family: var(--font-mono);
  font-size: 0.56rem;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--fg-3);
}
.dot { width: 11px; height: 11px; border-radius: 50%; border: 1px solid var(--line-strong); background: var(--nero-3); }
.dot--taken { background: transparent; border-style: dashed; }
.dot--pick { background: var(--red); border-color: var(--red); }

/* ----------------------------------------------------- 03/04 · pack + form -- */
.form {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 1.1rem;
  margin-top: 1.75rem;
  max-width: 620px;
}
.field { display: flex; flex-direction: column; gap: 0.45rem; min-width: 0; border: 0; padding: 0; margin: 0; }
.field--wide { grid-column: 1 / -1; }
.field label, .field legend {
  font-family: var(--font-mono);
  font-size: 0.56rem;
  font-weight: 700;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fg-3);
  padding: 0;
}
.opt { color: rgba(255, 255, 255, 0.28); letter-spacing: 0.1em; }
.field input[type='text'], .field input[type='tel'], .field textarea {
  background: var(--nero-1);
  border: 1px solid var(--line);
  padding: 0.75rem 0.9rem;
  color: var(--fg);
  font-size: var(--fs-body);
  width: 100%;
  transition: border-color 0.2s;
  resize: vertical;
}
.field input:focus, .field textarea:focus { border-color: var(--red); outline: none; box-shadow: var(--glow-sm); }
.field input::placeholder, .field textarea::placeholder { color: rgba(255, 255, 255, 0.24); }
.field__err { color: var(--red); font-size: 0.72rem; min-height: 0; }
.field[data-invalid] input, .field[data-invalid] textarea { border-color: var(--red); }

/* ------------------------------------------------ 01/02 · account + credits -- */
/* The returning member. This card is the whole argument for the flow's order:
   once it appears, steps 01 and 02 are already answered and the rider is two taps
   from a bike. */
.member { margin-top: 1.75rem; display: flex; flex-direction: column; align-items: flex-start; gap: 1rem; }
.member__card {
  width: 100%;
  max-width: 26rem;
  padding: 1.15rem 1.25rem;
  border: 1px solid var(--red);
  background: rgba(254, 0, 2, 0.07);
  box-shadow: var(--glow-sm);
}
.member__hi { font-size: var(--fs-body); color: var(--fg-2); }
.member__hi b { color: var(--fg); font-weight: 700; }
.member__bal { display: flex; align-items: baseline; gap: 0.5rem; margin-top: 0.5rem; }
.member__bal b {
  font-family: var(--font-mono);
  font-size: clamp(1.8rem, 4vw, 2.4rem);
  font-weight: 700;
  line-height: 1;
  color: var(--red);
}
.member__bal span {
  font-family: var(--font-mono);
  font-size: 0.56rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fg-3);
}
.member__ph { margin-top: 0.6rem; font-size: 0.6rem; color: var(--fg-3); }

/* the same balance, restated on step 02 where the decision is "buy or don't" */
.balance {
  margin-top: 1.75rem;
  padding: 1.25rem;
  border: 1px solid var(--line);
  background: var(--nero-1);
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 0.6rem;
  max-width: 30rem;
}
.balance__v { display: flex; align-items: baseline; gap: 0.6rem; }
.balance__v b {
  font-family: var(--font-mono);
  font-size: clamp(2.2rem, 5vw, 3rem);
  font-weight: 700;
  line-height: 1;
  color: var(--red);
}
.balance__v span {
  font-family: var(--font-mono);
  font-size: 0.58rem;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fg-3);
}
.balance__l { color: var(--fg-2); font-size: var(--fs-sm); }
.balance__l b { color: var(--fg); }

.packs { display: grid; grid-template-columns: repeat(auto-fill, minmax(160px, 1fr)); gap: 0.5rem; margin-top: 1.5rem; }
.pack {
  display: flex;
  flex-direction: column;
  gap: 0.2rem;
  padding: 0.8rem 0.85rem 0.7rem;
  border: 1px solid var(--line);
  background: var(--nero-1);
  text-align: left;
  transition: border-color 0.2s, background 0.2s;
}
.pack:hover { border-color: var(--line-strong); }
.pack[aria-pressed='true'] { border-color: var(--red); background: rgba(254, 0, 2, 0.07); }
.pack__n { font-size: 0.82rem; font-weight: 600; }
.pack__p { font-family: var(--font-mono); font-size: 0.95rem; font-weight: 700; color: var(--red); }
/* what the money actually buys — the credits, not the class */
.pack__c {
  font-family: var(--font-mono);
  font-size: 0.58rem;
  font-weight: 700;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: var(--fg);
}
.pack__x { font-family: var(--font-mono); font-size: 0.5rem; letter-spacing: 0.12em; text-transform: uppercase; color: var(--fg-3); }
/* Expiry pinned to the bottom edge: the unlimited pack has no per-class rate, and
   without this its terms would ride up and break the row's baseline. */
.pack__note {
  margin-top: auto;
  padding-top: 0.5rem;
  font-size: 0.72rem;
  color: var(--fg-3);
}
.pack[aria-pressed='true'] .pack__note { color: var(--fg-2); }
.pack__tag {
  position: absolute;
  top: 0;
  right: 0;
  background: var(--red);
  color: var(--on-red);
  font-family: var(--font-mono);
  font-size: 0.44rem;
  letter-spacing: 0.14em;
  padding: 0.15rem 0.35rem;
}
.pack--best { position: relative; }

.check { display: flex; align-items: center; gap: 0.65rem; color: var(--fg-2); font-size: var(--fs-sm); cursor: pointer; }
.check input { width: 17px; height: 17px; accent-color: var(--red); flex: 0 0 auto; }

/* ------------------------------------------------------------ 05 · review -- */
.review { margin-top: 1.75rem; max-width: 560px; border-top: 1px solid var(--line); }
.review__row {
  display: grid;
  grid-template-columns: 7.5rem 1fr;
  gap: 1rem;
  padding: 0.7rem 0;
  border-bottom: 1px solid var(--line);
  align-items: baseline;
}
.review dt {
  font-family: var(--font-mono);
  font-size: 0.56rem;
  font-weight: 700;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--fg-3);
}
.review dd { font-size: var(--fs-body); color: var(--fg); }
.review__row--total { border-bottom: 0; padding-top: 1rem; }
.review__row--total dt { color: var(--red); }
.review__row--total dd {
  font-family: var(--font-mono);
  font-size: 1.4rem;
  font-weight: 700;
  color: var(--red);
}

/* ------------------------------------------------------------------ done --- */
.pane--done { display: grid; place-items: center; min-height: 100%; text-align: center; }
.done { display: flex; flex-direction: column; align-items: center; gap: 1rem; max-width: 44ch; }
.done__tick {
  width: 58px;
  height: 58px;
  border-radius: 50%;
  background: var(--red);
  color: var(--on-red);
  display: grid;
  place-items: center;
  box-shadow: var(--glow-md);
  margin-bottom: 0.5rem;
}
.done__tick svg { width: 26px; height: 26px; }
.done .btn { margin-top: 0.5rem; }
.done__credits {
  font-family: var(--font-mono);
  font-size: 0.62rem;
  font-weight: 700;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: var(--red);
}
.review__row--total dd small {
  font-family: var(--font-body);
  font-size: 0.8rem;
  font-weight: 400;
  letter-spacing: 0;
  color: var(--fg-3);
}

/* ---------------------------------------------------------------- mobile --- */
@media (max-width: 900px) {
  /* Stacks, but still locked to exactly one screen — header + .book = 100svh on
     every viewport, same as the home page's hero. The flow scrolls inside its own
     pane while the page itself stays put, so the action bar never runs away and
     the first screen is complete and already actionable. */
  .book {
    grid-template-columns: 1fr;
    grid-template-rows: auto minmax(0, 1fr);
    height: calc(100svh - var(--header-h));
  }
  .book__panel {
    border-right: 0;
    border-bottom: 1px solid var(--line);
    height: 28svh;
    min-height: 168px;
  }
  .book__panel-inner { gap: 0.6rem; padding: 1rem 1.15rem; }
  .book__title { font-size: clamp(1.6rem, 7vw, 2.25rem); margin-top: 0.35rem; }

  /* the rail goes horizontal: numbers only, the pane says what the step is */
  .steps { flex-direction: row; gap: 0.5rem; }
  .step { border-bottom: 0; }
  .step__go { grid-template-columns: auto; padding: 0; width: auto; }
  .step__t { display: none; }
  .step__n { width: 1.85rem; height: 1.85rem; }

  /* summary goes on one line so the panel stays short */
  .summary { display: flex; gap: 1.5rem; padding-top: 0.6rem; }
  .summary__row { display: flex; flex-direction: column; gap: 0.05rem; padding: 0; }
  .summary dd { font-size: 0.8rem; }

  .book__main { min-height: 0; }
  .form { grid-template-columns: 1fr; }
  .class-pick { grid-template-columns: auto 1fr auto; gap: 0.7rem; row-gap: 0.35rem; }
  .class-pick__img, .class-pick__tick { display: none; }
  .class-pick__l { grid-column: 2 / -1; }
  .review__row { grid-template-columns: 6rem 1fr; }

  /* The ride meta line is the single biggest block of text on this page — at
     9px it was the reason two thirds of the booking flow was illegible on a
     phone. See the matching note in site.css. */
  .class-pick__m, .class-pick__l, .summary dt, .book__hint,
  .pack__x, .legend li, .field label, .field legend, .review dt {
    font-size: 0.75rem;
    letter-spacing: 0.08em;
  }
  .step__n { font-size: 0.72rem; }
  .pack__tag { font-size: 0.6rem; }
}

@media (max-width: 520px) {
  .summary { gap: 1rem; }
  .summary__row:nth-child(4) { display: none; }   /* total repeats in the bar */
}
