/* ===================================================================
   ServiceDesk -- shared stylesheet
   Ported from docs/servicedesk/ui/assets/servicedesk.css (reference
   prototype, never deployed).

   Served from BOTH trees, byte-identical:
     modern_storefront/src/main/webapp/static/www/css/servicedesk/servicedesk.css   (repo)
     /root/old_to_new/static/www/css/servicedesk/servicedesk.css                    (served)
   Undertow serves the second one. A repo-only edit changes nothing.

   Referenced by the funnel views as:
     ${cssPath}/servicedesk/servicedesk.css?v=${applicationScope['build_version']}

   FILE IS ASCII ONLY. The storefront pages declare ISO-8859-1
   (jsp/comman/plugin.jsp), so a stray en-dash or box-drawing character
   becomes mojibake on a real page and nowhere in an editor. The one
   glyph the design needs -- the selected-card check mark -- is written
   as the CSS escape \2713.

   SCOPING CONTRACT
   Everything below the token block is scoped under the root class
   .sd-flow, because this sheet loads alongside bootstrap.css,
   common.css, custom.css and ~20 others, and the prototype's class
   names (.grid, .field, .chip, .slot, .price, .summary, .actions,
   .btn, .day, .note, .policy, and a bare `label`) would otherwise
   collide with them in both directions.

   The markup contract is therefore:

       <div class="sd-flow flow"> ... </div>     (funnel page)
       <div class="sd-flow flow flow--wide"> ... </div>

   .flow is matched both as the root element itself (.sd-flow.flow) and
   as a descendant (.sd-flow .flow), so either shape works.

   The :root token block is deliberately NOT scoped. Tokens are meant to
   be global -- that is what keeps a re-skin a single-block edit.

   DESIGN TOKENS
   Every visual decision lives in :root. To match your storefront, edit
   this block only -- nothing below hard-codes a colour, radius or font.
   =================================================================== */
:root{
  /* Surface: eucalyptus. Hospital interiors moved off white decades ago
     because green lowers eye strain and anxiety. Grounded in the subject,
     not a mood choice. */
  --surface:        #EDF1EC;
  --surface-raised: #FBFCFA;
  --surface-sunk:   #E1E8DF;
  --line:           #C8D3C6;
  --line-strong:    #A9B8A6;

  --ink:            #16211A;
  --ink-soft:       #4A5A4E;
  --ink-faint:      #7A8A7D;
  --on-ink:         #DCE5DA;

  /* Primary action: marigold. Warm against the cool surface.

     CONTRAST -- DO NOT RESTORE THE PROTOTYPE VALUES.
     The prototype shipped --accent:#C9761B / --accent-hover:#A85F12.
     Measured in Chromium against the prototype pages, #C9761B failed
     WCAG AA (4.5:1 for normal-size text; these are 13.5-14.5px) in all
     three places it carries text:
       selected slot, white on accent  3.45 -> 4.87 at #A85F12
       ordinary slot, accent on raised 3.35 -> 4.73 at #A85F12
       primary button, white on accent 3.45 -> 4.87 at #A85F12
     The hue is unchanged; only the value moved, and --accent-hover was
     pushed down to #8C4E0C so the hover step survives.
     See PROTOTYPE_REVIEW P-3. */
  --accent:         #A85F12;
  --accent-hover:   #8C4E0C;
  --accent-ink:     #FFFFFF;
  --accent-wash:    #F7E9D8;

  /* RESERVED for clinical urgency triage. Never decorative. If red appears
     in this interface it always means something needs attention now. */
  --urgent:         #B3261E;
  --urgent-wash:    #FBE9E7;
  --urgent-ink:     #6E1A15;

  --ok:             #2F6B4F;
  --ok-wash:        #DFEDE5;
  --ok-ink:         #1F4A36;
  --white:          #FFFFFF;

  --radius:         10px;
  --radius-sm:      6px;
  --shadow:         0 1px 2px rgba(22,33,26,.06), 0 8px 24px -12px rgba(22,33,26,.18);
  --shadow-lift:    0 2px 4px rgba(22,33,26,.08), 0 18px 40px -16px rgba(22,33,26,.28);

  /* FONTS -- unresolved question, deliberately left degrading.
     Whether this storefront may load an external font host (Google
     Fonts) has not been decided, and nothing here links one. Until it
     is decided these stacks must keep their fallbacks: if the webfont
     never loads, display and body fall to system-ui and data falls to
     ui-monospace, which is a correct rendering, not a broken one.
     Do not add a <link> to fonts.googleapis.com without that decision. */
  --font-display:   'Bricolage Grotesque', system-ui, sans-serif;
  --font-body:      'IBM Plex Sans', system-ui, sans-serif;
  /* Times, prices and reference numbers are tabular data. Mono aligns them. */
  --font-data:      'IBM Plex Mono', ui-monospace, monospace;
}

/* -- Base ----------------------------------------------------------
   The prototype's `*`, `html` and `body` rules owned the whole document.
   Scoped to the funnel: the reset applies inside .sd-flow only, and the
   `html{-webkit-text-size-adjust}` rule is dropped entirely -- it is a
   document-level concern and plugin.jsp already ships the viewport meta.
   `body{...}` becomes `.sd-flow{...}`, so the eucalyptus surface paints
   the funnel container rather than the whole page. */
.sd-flow,.sd-flow *{box-sizing:border-box;margin:0;padding:0}
.sd-flow{font-family:var(--font-body);background:var(--surface);color:var(--ink);
  line-height:1.5;font-size:15px;-webkit-font-smoothing:antialiased}
.sd-flow button{font:inherit;color:inherit;cursor:pointer;border:none;background:none}
.sd-flow input,.sd-flow select,.sd-flow textarea{font:inherit;color:inherit}
.sd-flow a{color:inherit;text-decoration:none}
.sd-flow:focus-visible,.sd-flow :focus-visible{outline:2.5px solid var(--accent);
  outline-offset:2px;border-radius:3px}
@media (prefers-reduced-motion:reduce){.sd-flow *{animation-duration:.01ms!important;transition-duration:.01ms!important}}

/* -- Storefront chrome: REMOVED, do not port it back ----------------
   The prototype carried .topbar, .masthead, .logo, .searchbar,
   .masthead-actions, .catbar and the .cat* rules, plus the .wrap
   container they all used. Those were a stand-in for a storefront
   header the prototype did not have. This storefront has a real one --
   the pages include jsp/comman/navbar/topHeader.jsp and header.jsp --
   so porting them would style a second, competing header on top of it.
   .wrap went with them: it was used only by .topbar/.masthead/.catbar
   (assets/servicedesk.js:139,143,153) and by nothing else in the
   prototype, so no funnel rule needs it.
   The .searchbar input{outline:none} focus-ring defect noted in
   PROTOTYPE_REVIEW P-7 leaves with the block. */

/* -- Layout --------------------------------------------------------- */
.sd-flow.flow,.sd-flow .flow{display:grid;grid-template-columns:1fr 344px;gap:32px;
  max-width:1180px;margin:0 auto;padding:28px 20px 80px}
.sd-flow.flow--wide,.sd-flow .flow--wide{grid-template-columns:1fr;max-width:820px}
@media(max-width:940px){.sd-flow.flow,.sd-flow .flow{grid-template-columns:1fr;gap:20px}}

/* 360px OVERFLOW FIX -- keep this rule.
   A grid item defaults to min-width:auto, i.e. min-content. .daystrip
   holds seven .day cells at min-width:76px;flex-shrink:0, which is
   7*76 + 6*8 = 580px of min-content, so the column was forced to 580px
   and the whole page scrolled sideways with it -- .daystrip's own
   overflow-x:auto never got a chance because the strip was never made
   narrower than its contents. Measured in Chromium at a 360px viewport:
     without this rule  clientWidth 360, page scrollWidth 600
     with this rule     clientWidth 360, page scrollWidth 360,
                        day strip still scrolls internally (842px reachable)
   See PROTOTYPE_REVIEW P-2. */
.sd-flow.flow>section,.sd-flow.flow>aside,
.sd-flow .flow>section,.sd-flow .flow>aside{min-width:0}

.sd-flow .eyebrow{font-family:var(--font-data);font-size:11px;letter-spacing:.14em;
  text-transform:uppercase;color:var(--ink-faint);margin-bottom:8px}
.sd-flow h1{font-family:var(--font-display);font-size:clamp(26px,3.4vw,36px);line-height:1.08;
  letter-spacing:-.025em;font-weight:800;margin-bottom:8px}
.sd-flow h2{font-family:var(--font-display);font-size:19px;letter-spacing:-.015em;
  font-weight:600;margin-bottom:4px}
.sd-flow .lede{color:var(--ink-soft);max-width:56ch;margin-bottom:24px}

/* -- Progress rail --------------------------------------------------- */
.sd-flow .rail{display:flex;margin-bottom:28px;border-bottom:1px solid var(--line)}
.sd-flow .rail-step{flex:1;padding:0 0 10px;border-bottom:2.5px solid transparent;
  margin-bottom:-1px;text-align:left;transition:border-color .2s;display:block}
.sd-flow .rail-step .n{font-family:var(--font-data);font-size:11px;color:var(--ink-faint);
  display:block;margin-bottom:2px}
.sd-flow .rail-step .t{font-size:12.5px;color:var(--ink-faint);font-weight:500}
.sd-flow .rail-step[data-state="done"] .n,.sd-flow .rail-step[data-state="done"] .t{color:var(--ok)}
.sd-flow .rail-step[data-state="done"]{border-bottom-color:var(--ok)}
.sd-flow .rail-step[data-state="now"] .t{color:var(--ink);font-weight:600}
.sd-flow .rail-step[data-state="now"] .n{color:var(--accent)}
.sd-flow .rail-step[data-state="now"]{border-bottom-color:var(--accent)}
.sd-flow .rail-step[data-state="todo"]{cursor:default;opacity:.75}
@media(max-width:640px){.sd-flow .rail-step .t{display:none}}

/* -- Choice cards ---------------------------------------------------- */
.sd-flow .grid{display:grid;gap:12px}
.sd-flow .grid--3{grid-template-columns:repeat(auto-fill,minmax(190px,1fr))}
.sd-flow .grid--2{grid-template-columns:repeat(auto-fill,minmax(250px,1fr))}
.sd-flow .choice{background:var(--surface-raised);border:1px solid var(--line);
  border-radius:var(--radius);padding:16px;text-align:left;width:100%;display:block;
  transition:border-color .15s,box-shadow .15s,transform .15s;position:relative}
.sd-flow .choice:hover{border-color:var(--line-strong);box-shadow:var(--shadow);transform:translateY(-1px)}
.sd-flow .choice[aria-pressed="true"]{border-color:var(--accent);box-shadow:0 0 0 1px var(--accent)}
/* \2713 is U+2713 CHECK MARK, written as an escape to keep this file ASCII. */
.sd-flow .choice[aria-pressed="true"]::after{content:"\2713";position:absolute;top:12px;right:14px;
  color:var(--accent);font-weight:700}
.sd-flow .choice .ico{font-size:22px;display:block;margin-bottom:9px;line-height:1}
.sd-flow .choice .nm{font-weight:600;font-size:15px;margin-bottom:2px;display:block}
.sd-flow .choice .sub{font-size:12.5px;color:var(--ink-faint);display:block}
/* CL-029. The PRICE on a choice tile. Darker and heavier than .sub, because on the service step it is
   the thing being compared -- the duration beside it is context. It is still a .sub, so a tile with no
   price simply has one fewer line and needs no layout of its own: an unpriced service must render as a
   normal, bookable choice, not as a broken one. */
.sd-flow .choice .sub--price{color:var(--ink);font-weight:600;font-size:13.5px;margin-top:2px}
.sd-flow .choice .sub--muted{color:var(--ink-faint)}
.sd-flow .choice:disabled{opacity:.42;cursor:not-allowed}
.sd-flow .choice:disabled:hover{transform:none;box-shadow:none;border-color:var(--line)}

/* -- Fields & chips -------------------------------------------------- */
.sd-flow .field{background:var(--surface-raised);border:1px solid var(--line);
  border-radius:var(--radius);padding:12px 14px;width:100%;outline:none;font-size:15px}
.sd-flow .field:focus{border-color:var(--accent)}
/* FOCUS RING -- keep this rule, and keep it AFTER .field.
   .field sets outline:none. In the prototype the global :focus-visible
   rule had equal specificity (0,1,0) and came earlier in the file, so
   source order decided and the ring lost: measured outlineStyle "none"
   on every text input, select and textarea in the funnel, leaving only
   a border-colour change -- colour as the only signal, in the accent
   that also failed contrast. With this rule the ring is back
   (measured outlineStyle "solid"). See PROTOTYPE_REVIEW P-7. */
.sd-flow .field:focus-visible{outline:2.5px solid var(--accent);outline-offset:2px}
.sd-flow .chips{display:flex;flex-wrap:wrap;gap:8px;margin-top:14px}
.sd-flow .chip{background:var(--surface-raised);border:1px solid var(--line);
  border-radius:100px;padding:7px 14px;font-size:13px;transition:all .15s}
.sd-flow .chip:hover{border-color:var(--accent);color:var(--accent)}
.sd-flow .chip[aria-pressed="true"]{background:var(--accent);border-color:var(--accent);color:var(--accent-ink)}

/* -- Emergency triage. The only place red is allowed. ---------------- */
.sd-flow .triage{background:var(--urgent-wash);border:1px solid var(--urgent);border-left-width:4px;
  border-radius:var(--radius);padding:18px 20px;margin:20px 0}
.sd-flow .triage h3{font-family:var(--font-display);color:var(--urgent);font-size:17px;margin-bottom:6px}
.sd-flow .triage p{color:var(--urgent-ink);font-size:14px;margin-bottom:14px}
/* BOOTSTRAP COLLISION -- keep the second rule.
   .row is Bootstrap's grid row, and this WAR loads bootstrap.css on every
   page. Scoping wins for the properties named here (.sd-flow .triage .row
   is 0,3,0 against Bootstrap's 0,1,0), but Bootstrap also styles the
   CHILDREN: `.row > *{flex-shrink:0;width:100%;max-width:100%}`, and we had
   no counter-rule for that. Measured in Chromium on the real page: the two
   triage buttons rendered full-bleed and stacked, so the emergency call
   action looked like a form field. The children rule below is the fix.
   Nothing else in this sheet reuses a Bootstrap grid class. */
.sd-flow .triage .row{display:flex;gap:10px;flex-wrap:wrap}
.sd-flow .triage .row>*{width:auto;max-width:none}
.sd-flow .btn-urgent{background:var(--urgent);color:var(--white);border-radius:var(--radius-sm);
  padding:11px 18px;font-weight:600;font-size:14px}

/* -- Provider list --------------------------------------------------- */
.sd-flow .filters{display:flex;gap:8px;flex-wrap:wrap;margin-bottom:18px;
  padding-bottom:18px;border-bottom:1px solid var(--line)}
.sd-flow .provider{background:var(--surface-raised);border:1px solid var(--line);
  border-radius:var(--radius);padding:18px;display:grid;grid-template-columns:56px 1fr auto;
  gap:16px;align-items:start;margin-bottom:12px;transition:border-color .15s,box-shadow .15s}
.sd-flow .provider:hover{border-color:var(--line-strong);box-shadow:var(--shadow)}
.sd-flow .avatar{width:56px;height:56px;border-radius:50%;background:var(--surface-sunk);
  display:grid;place-items:center;font-family:var(--font-display);font-weight:700;
  font-size:19px;color:var(--ink-soft)}
.sd-flow .pname{font-family:var(--font-display);font-size:17px;font-weight:600;letter-spacing:-.01em}
.sd-flow .pqual{font-size:12.5px;color:var(--ink-faint);margin-bottom:7px}
.sd-flow .pmeta{display:flex;gap:14px;flex-wrap:wrap;font-size:12.5px;color:var(--ink-soft)}
.sd-flow .pmeta b{font-weight:600;color:var(--ink)}
.sd-flow .rating{color:var(--ok);font-weight:600}
.sd-flow .pright{text-align:right}
.sd-flow .price{font-family:var(--font-data);font-size:17px;font-weight:600;letter-spacing:-.02em}
.sd-flow .price s{color:var(--ink-faint);font-weight:400;font-size:13px;margin-right:5px}
.sd-flow .next-slot{font-size:12px;color:var(--ok);font-weight:500;margin-top:3px}
@media(max-width:600px){.sd-flow .provider{grid-template-columns:44px 1fr}
  .sd-flow .avatar{width:44px;height:44px;font-size:15px}
  .sd-flow .pright{grid-column:2;text-align:left}}

/* -- Day strip + slots ----------------------------------------------- */
.sd-flow .daystrip{display:flex;gap:8px;overflow-x:auto;padding-bottom:6px;margin-bottom:20px}
.sd-flow .day{min-width:76px;background:var(--surface-raised);border:1px solid var(--line);
  border-radius:var(--radius);padding:10px 8px;text-align:center;flex-shrink:0;
  transition:all .15s;display:block}
.sd-flow .day:hover{border-color:var(--line-strong)}
.sd-flow .day[aria-pressed="true"]{background:var(--ink);border-color:var(--ink);color:var(--surface-raised)}
/* display:block on all three -- the prototype omits it and its own day cell
   therefore renders on ONE line. Measured in Chromium against the real
   markup at 1280 and at 360: "TODAY22 6 free" run together, day number
   inline with the weekday. The design is three stacked lines and .day is
   already display:block with text-align:center, so this is the missing
   half of that rule, not a new decision. */
.sd-flow .day .dow{display:block;font-size:11px;text-transform:uppercase;letter-spacing:.06em;opacity:.72}
.sd-flow .day .dnum{display:block;font-family:var(--font-display);font-size:19px;font-weight:700;line-height:1.25}
.sd-flow .day .cnt{display:block;font-family:var(--font-data);font-size:10.5px;opacity:.72}
.sd-flow .day--none{opacity:.4}
/* RED IS RESERVED FOR CLINICAL URGENCY -- do not put --urgent back here.
   The prototype paints "none" in --urgent, which spends the one colour that
   is supposed to mean "this needs attention now" on a day that happens to
   be fully booked. Red only keeps that meaning if it is never spent
   anywhere else, and the triage block is the only thing in this funnel that
   qualifies. The word "none" and the faded cell carry the signal without it;
   opacity:1 stays so the word is still legible through the fade. */
.sd-flow .day--none .cnt{color:var(--ink-soft);opacity:1}

.sd-flow .slotgroup{margin-bottom:22px}
.sd-flow .slotgroup h4{font-size:12px;text-transform:uppercase;letter-spacing:.1em;
  color:var(--ink-faint);font-family:var(--font-data);margin-bottom:10px;
  display:flex;align-items:center;gap:9px;font-weight:500}
.sd-flow .slotgroup h4::after{content:"";flex:1;height:1px;background:var(--line)}
.sd-flow .slots{display:grid;grid-template-columns:repeat(auto-fill,minmax(94px,1fr));gap:8px}
.sd-flow .slot{font-family:var(--font-data);font-size:13.5px;background:var(--surface-raised);
  border:1px solid var(--line);border-radius:var(--radius-sm);padding:10px 6px;
  text-align:center;transition:all .12s;font-weight:500}
.sd-flow .slot:hover:not(:disabled){border-color:var(--accent);color:var(--accent)}
.sd-flow .slot[aria-pressed="true"]{background:var(--accent);border-color:var(--accent);color:var(--accent-ink)}
/* Disabled slot contrast is 2.92:1 and that is CORRECT -- do not "fix" it.
   Disabled controls are exempt from WCAG AA, the rule also carries
   line-through so colour is not the only signal, and raising it would
   erase the distinction between disabled and available.
   See PROTOTYPE_REVIEW P-3. */
.sd-flow .slot:disabled{background:var(--surface-sunk);color:var(--ink-faint);
  text-decoration:line-through;cursor:not-allowed}
.sd-flow .slot--last{border-color:var(--accent);color:var(--accent)}
/* COLOUR IS NEVER THE ONLY SIGNAL -- keep this rule.
   A taken time carries three independent signals: the line-through above,
   the sunken fill above, and the visible word "taken" that the view puts
   in this span. Without display:block that word runs into the time
   ("09:20taken", measured), so the one signal that does not depend on
   colour vision is also the one that reads worst. Roughly one man in
   twelve cannot rely on the fill. */
.sd-flow .slot .cnt{display:block;font-size:10.5px;letter-spacing:.04em}

/* -- Hold countdown -- honest to the hold-then-confirm engine -------- */
.sd-flow .hold{position:sticky;bottom:0;background:var(--ink);color:var(--surface-raised);
  border-radius:var(--radius);padding:13px 16px;display:flex;align-items:center;gap:14px;
  margin-top:20px;box-shadow:var(--shadow-lift);z-index:30}
.sd-flow .hold .clock{font-family:var(--font-data);font-size:21px;font-weight:600;
  letter-spacing:-.02em;min-width:62px}
.sd-flow .hold .msg{flex:1;font-size:13px;line-height:1.35}
.sd-flow .hold .msg b{display:block;font-weight:600}
.sd-flow .hold .msg span{opacity:.72;font-size:12px;display:block}
.sd-flow .hold--warn{background:var(--urgent)}
.sd-flow .holdbar{height:2.5px;background:rgba(255,255,255,.22);border-radius:2px;
  overflow:hidden;margin-top:7px}
.sd-flow .holdbar i{display:block;height:100%;background:var(--surface-raised);transition:width 1s linear}
.sd-flow .holdbar{opacity:1!important}
/* 360px -- keep this rule.
   .hold is one flex row: clock, message, Continue. Measured in Chromium at
   a 360px viewport, the message column was squeezed to about 50px and the
   sentence broke one word per line, ten lines deep. Nothing was clipped, so
   an overflow check does not catch it. Below 600px the message drops to its
   own row and the clock keeps the Continue button company on the first. */
@media(max-width:600px){
  .sd-flow .hold{flex-wrap:wrap}
  .sd-flow .hold .clock{order:1}
  .sd-flow .hold .btn{order:2;margin-left:auto}
  .sd-flow .hold .msg{order:3;flex:1 1 100%}
}

/* -- Summary card ---------------------------------------------------- */
/* top was 76px, measured against the prototype's own sticky .catbar, which
   is removed above. RETUNED TO 16px ON A MEASUREMENT, not a guess: this
   storefront's header is not sticky at all. Chromium, /aboutUs and
   /contactUs (both 200), at 1280 and at 360, before and after scrolling
   800px, the only fixed element of any size is div.block.block-content --
   the hidden search overlay -- sitting entirely above the viewport at
   top:-371 to -271. So there is no chrome for the card to clear, and 76px
   was 76px of nothing. 16px is a breathing gutter.
   If a sticky header is ever added, this is the number to change. */
.sd-flow .summary{background:var(--surface-raised);border:1px solid var(--line);
  border-radius:var(--radius);position:sticky;top:16px;overflow:hidden}
@media(max-width:940px){.sd-flow .summary{position:static}}
.sd-flow .summary-head{padding:15px 18px;border-bottom:1px dashed var(--line);
  display:flex;justify-content:space-between;align-items:baseline}
.sd-flow .summary-head .lbl{font-family:var(--font-data);font-size:10.5px;letter-spacing:.14em;
  text-transform:uppercase;color:var(--ink-faint)}
.sd-flow .summary-head .ref{font-family:var(--font-data);font-size:11px;color:var(--ink-faint)}
.sd-flow .summary-body{padding:16px 18px}
.sd-flow .srow{display:flex;justify-content:space-between;gap:14px;padding:9px 0;font-size:13.5px;
  border-bottom:1px solid var(--surface-sunk)}
.sd-flow .srow:last-child{border-bottom:none}
.sd-flow .srow .k{color:var(--ink-faint);flex-shrink:0}
.sd-flow .srow .v{text-align:right;font-weight:500}
.sd-flow .srow--empty .v{color:var(--ink-faint);font-weight:400;font-style:italic}
.sd-flow .money{font-family:var(--font-data)}
.sd-flow .stotal{display:flex;justify-content:space-between;align-items:baseline;padding:14px 18px;
  border-top:2px solid var(--ink);background:var(--surface-sunk)}
.sd-flow .stotal .k{font-weight:600;font-size:14px}
.sd-flow .stotal .v{font-family:var(--font-data);font-size:21px;font-weight:600;letter-spacing:-.02em}
.sd-flow .policy{padding:13px 18px;background:var(--ok-wash);font-size:12px;color:var(--ok-ink);
  border-top:1px solid var(--line)}
.sd-flow .policy b{display:block;margin-bottom:3px;font-weight:600}

/* -- Buttons --------------------------------------------------------- */
.sd-flow .actions{display:flex;gap:10px;margin-top:26px;padding-top:22px;
  border-top:1px solid var(--line);flex-wrap:wrap}
.sd-flow .actions--plain{border-top:none;padding-top:0}
.sd-flow .btn{border-radius:var(--radius-sm);padding:12px 22px;font-weight:600;font-size:14.5px;
  transition:background .15s,border-color .15s;display:inline-block;text-align:center}
.sd-flow .btn-primary{background:var(--accent);color:var(--accent-ink)}
.sd-flow .btn-primary:hover{background:var(--accent-hover)}
.sd-flow .btn-primary[aria-disabled="true"],.sd-flow .btn-primary:disabled{
  background:var(--line-strong);cursor:not-allowed;pointer-events:none}
.sd-flow .btn-ghost{border:1px solid var(--line);color:var(--ink-soft)}
.sd-flow .btn-ghost:hover{border-color:var(--ink-soft);color:var(--ink)}
.sd-flow .btn-sm{padding:9px 16px;font-size:13.5px}

/* -- Forms ----------------------------------------------------------- */
.sd-flow .formgrid{display:grid;grid-template-columns:1fr 1fr;gap:14px}
@media(max-width:600px){.sd-flow .formgrid{grid-template-columns:1fr}}
.sd-flow .formgrid .full{grid-column:1/-1}
.sd-flow label{display:block;font-size:12.5px;font-weight:500;color:var(--ink-soft);margin-bottom:6px}
.sd-flow .hint{font-size:12px;color:var(--ink-faint);margin-top:5px}
.sd-flow .who{display:flex;gap:10px;margin-bottom:20px;flex-wrap:wrap}
.sd-flow .note{background:var(--accent-wash);border-radius:var(--radius-sm);padding:13px 15px;
  font-size:13px;margin-bottom:20px;border-left:3px solid var(--accent)}

/* -- Confirmation ---------------------------------------------------- */
.sd-flow .confirm{background:var(--surface-raised);border:1px solid var(--line);
  border-radius:var(--radius);padding:36px;text-align:center}
.sd-flow .stamp{display:inline-block;border:2.5px solid var(--ok);color:var(--ok);
  font-family:var(--font-display);font-weight:800;font-size:13px;letter-spacing:.16em;
  padding:7px 16px;border-radius:5px;transform:rotate(-4deg);margin-bottom:20px;
  animation:sdStampIn .45s cubic-bezier(.3,1.5,.5,1) both}
/* Renamed from the prototype's `stampIn`: @keyframes names are global no
   matter how the selectors are scoped, and a bare `stampIn` in a page
   loading ~20 other stylesheets is a name that can be redefined out from
   under us. Prefixed for the same reason every class is. */
@keyframes sdStampIn{from{transform:rotate(-4deg) scale(2.4);opacity:0}
  to{transform:rotate(-4deg) scale(1);opacity:1}}
.sd-flow .bigref{font-family:var(--font-data);font-size:24px;font-weight:600;
  letter-spacing:.02em;margin:14px 0 6px}
.sd-flow .nextsteps{text-align:left;max-width:430px;margin:26px auto 0;
  border-top:1px solid var(--line);padding-top:20px}
.sd-flow .nextsteps li{list-style:none;display:flex;gap:12px;padding:9px 0;
  font-size:13.5px;align-items:flex-start}
.sd-flow .nextsteps .tm{font-family:var(--font-data);font-size:11.5px;color:var(--ink-faint);
  min-width:64px;padding-top:2px}
.sd-flow .hidden{display:none!important}

/* -- Waitlist (step 5, below the grid) -------------------------------- */
/* IT MUST NOT COMPETE WITH A TIME THE CUSTOMER COULD BOOK RIGHT NOW.
   The panel sits below the slot grid and is deliberately quieter than a
   choice card: sunk surface, no shadow, no accent border. A customer who
   can see a time that suits them should never be drawn down here first.
   That is why it is not `.note` either -- .note carries an accent left
   border, which reads as "attention", and this is an alternative. */
.sd-flow .sd-waitlist{background:var(--surface-sunk);border:1px solid var(--line);
  border-radius:var(--radius);padding:22px 24px;margin-top:30px}
.sd-flow .sd-waitlist h2{font-family:var(--font-display);font-size:17px;
  font-weight:700;margin-bottom:8px}
.sd-flow .sd-waitlist .lede{font-size:13.5px;color:var(--ink-soft);
  line-height:1.5;margin-bottom:18px}
.sd-flow .sd-waitlist .waitlist-form{margin-bottom:0}
.sd-flow .sd-waitlist .waitlist-scope{font-size:13px;color:var(--ink-soft);
  margin-top:4px}
/* The optional marker on a label. Lighter than the label, never a colour
   on its own -- see the slot rule: colour is never the only signal. */
.sd-flow .sd-waitlist .opt{color:var(--ink-faint);font-weight:400}

/* The customer's own entries, drawn by booking.js from waitlistMine.
   role="status" -- it is announced when it changes, which is why the join
   result is written INTO it rather than into a separate line. */
.sd-flow .waitlist-mine{margin-top:20px;border-top:1px solid var(--line);
  padding-top:16px}
.sd-flow .waitlist-mine h3{font-size:12px;text-transform:uppercase;
  letter-spacing:.1em;color:var(--ink-faint);font-weight:600;margin-bottom:10px}
.sd-flow .waitlist-mine ul{list-style:none;margin:0;padding:0}
.sd-flow .waitlist-mine li{display:flex;gap:12px;align-items:flex-start;
  justify-content:space-between;background:var(--surface-raised);
  border:1px solid var(--line);border-radius:var(--radius-sm);
  padding:11px 13px;margin-bottom:8px}
.sd-flow .waitlist-mine .when{font-family:var(--font-data);font-size:13px}
/* NOT `.who` -- that class already exists in this file as the persona chip
   row (`display:flex`), and reusing a name for a second meaning is how a
   later edit to one silently restyles the other. */
.sd-flow .waitlist-mine .forwhom{display:block;font-size:12.5px;color:var(--ink-soft);
  margin:2px 0 0}
/* WAITING vs OFFERED are different situations and must not be told apart by
   colour alone: each carries its own words. `ok` is the green already
   reserved for a settled state (the confirmation stamp), used here because
   an offer is the one moment the customer has something to act on. */
.sd-flow .waitlist-mine .state{display:block;font-size:12px;color:var(--ink-faint);
  margin-top:3px}
.sd-flow .waitlist-mine .state--offered{color:var(--ok-ink);font-weight:600}
