/*========================================
  Reserva default theme

  The single default stylesheet for BOTH surfaces: the booking site (this
  section) and the kiosk (the "KIOSK SURFACE" section further down). It defines
  the complete styling contract — client stylesheets are loaded after it and
  may only override selectors, properties and tokens declared here. The server
  appends the active client's override to this file before serving each surface.
  See clients/README.md before adding or changing client styling.
========================================*/

/*========================================
  Design tokens

  Override these from the client stylesheet (Admin → Settings → "Style (CSS)")
  to re-skin the app. The brand palette below is shared by both surfaces; the
  kiosk's own (non-brand) tokens live in the ".kiosk" block further down. One
  :root override themes both surfaces. See clients/README.md.
========================================*/
:root {
    /* Brand palette — shared by the booking site and the kiosk */
    --brand-primary: #1f3a5f; /* primary buttons, checkbox accent, headers, service buttons */
    --brand-primary-hover: #2c4f7c; /* hover/active shade of primary */
    --brand-on-primary: #ffffff; /* text/icons on the primary colour */
    --brand-header: var(--brand-primary); /* header bar; can be set apart from primary */
    --brand-secondary: #5f1f3a; /* the "no booking" path (kiosk) */
    --brand-accent: #0369a1; /* highlights and focus rings */

    /* Surfaces */
    --surface-backdrop: #244662; /* dark backdrop behind the dialog and the queue screen */
    --surface-card: #fff; /* dialog, cards, inputs, menus */

    /* Status text */
    --status-success-text: green;
    --status-error-text: red;
    --status-warning-text: #d97706; /* notice / "important" accent */

    /* Typography */
    --font-body: sans-serif;
}

/* Base Reset & Global Styles */
* {
    box-sizing: border-box;
}

body, h1, h2, h3, h4, p, ul, li {
    margin: 0;
    padding: 0;
    font-family: var(--font-body);
}

/* Utility Classes */
.centered {
    text-align: center;
}

.mt-sm {
    margin-top: 0.5rem;
}

.mt-lg {
    margin-top: 1rem;
}

.placeholder-text {
    color: #999;
}

.custom-list {
    list-style: disc inside;
}

.required-indicator {
    color: var(--status-error-text);
    margin-left: 2px;
}

/*========================================
  Layout Containers

  min-height, not height: with a fixed height a centred flex child that is
  taller than the viewport overflows in BOTH directions, and the overflow above
  the top edge cannot be scrolled to — the header ends up permanently cut off.
  Growing the container instead keeps the whole dialog reachable. 100dvh (where
  supported) tracks mobile browser chrome as it collapses.
========================================*/
.app-fullscreen {
    width: 100%;
    min-height: 100vh;
    min-height: 100dvh;
    display: flex;
    align-items: center;
    justify-content: center;
    background-color: var(--surface-backdrop);
}

.app-dialog {
    width: 100%;
    max-width: 800px;
    background-color: var(--surface-card);
    border-radius: 8px;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
}

/*========================================
  Global Header & Flag Selector
========================================*/
.app-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: 10px;
    background-color: var(--brand-header);
    margin-bottom: 0;
}

.logo {
    width: 150px; /* Adjust as needed */
    height: 50px; /* Adjust as needed */
    background-size: contain;
    background-repeat: no-repeat;
    background-position: center;
    /* --brand-logo is set from the Logo setting when one is configured;
       otherwise the file shipped in wwwroot/branding is used. */
    background-image: var(--brand-logo, url('/branding/logo.svg'));
}

.flag-wrapper {
    display: flex;
    gap: 10px;
    margin-right: 15px;
}

.flag {
    width: 32px;
    height: 32px;
    background-size: cover;
    cursor: pointer;
    border: 1px solid transparent;
    border-radius: 4px;
    transition: border-color 0.3s;
}

    .flag:hover {
        border-color: var(--brand-primary);
    }

    .flag.small {
        /* Additional small flag styling if needed */
    }

.welcome-msg {
    margin-bottom: 10px;
}

/*========================================
  Global Content & Grid Layout
========================================*/
.app-content {
    padding: 20px;
}

.two-column-grid {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 20px;
}

/*========================================
  Global Form Elements & Dropdowns
========================================*/
.label {
    display: block;
    font-weight: bold;
    margin-bottom: 5px;
}

.select,
.input {
    width: 100%;
    padding: 8px 10px;
    border: 1px solid #ccc;
    border-radius: 4px;
    font-size: 16px;
}

/* Checkbox metadata fields (e.g. "the appointment is for a child") render as a
   full-width clickable card — the label element wraps the input, so tapping
   anywhere on the row toggles it. Clients can re-accent via their style.css. */
.checkbox-row {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 12px;
    border: 1px solid #ccc;
    border-radius: 4px;
    background-color: var(--surface-card);
    cursor: pointer;
    user-select: none;
    transition: border-color 0.2s, background-color 0.2s;
}

    .checkbox-row:hover {
        border-color: var(--brand-primary);
        background-color: #f5f9ff;
    }

    .checkbox-row:has(.checkbox:checked) {
        border-color: var(--brand-primary);
        background-color: #eef5ff;
    }

.checkbox {
    width: 22px;
    height: 22px;
    flex-shrink: 0;
    accent-color: var(--brand-primary);
    cursor: pointer;
}

.checkbox-text {
    font-size: 16px;
}

.dropdown {
    position: relative;
}

.dropdown-btn {
    width: 100%;
    padding: 8px 10px;
    border: 1px solid #ccc;
    border-radius: 4px;
    background-color: var(--surface-card);
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 8px;
    min-height: 44px; /* comfortable touch target */
    text-align: left;
    cursor: pointer;
    font-size: 16px;
}

    /* The label ("09:00 - 09:30" + its badge) must be free to shrink and wrap,
       or it pushes the chevron out of the button on a narrow screen. */
    .dropdown-btn > span {
        min-width: 0;
    }

    .dropdown-btn .icon {
        flex-shrink: 0;
    }

    .dropdown-btn:disabled {
        background-color: #eee;
        cursor: not-allowed;
    }

.dropdown-menu {
    position: absolute;
    top: 100%;
    left: 0;
    width: 100%;
    background-color: var(--surface-card);
    border: 1px solid #ccc;
    border-top: none;
    z-index: 1000;
    max-height: 200px;
    overflow-y: auto;
}

.dropdown-item,
.dropdown-item-clickable {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 8px;
    min-height: 44px; /* comfortable touch target */
    padding: 8px 10px;
    cursor: pointer;
}

.dropdown-item {
    background-color: #f9f9f9;
}

    .dropdown-item:hover,
    .dropdown-item-clickable:hover {
        background-color: #e9e9e9;
    }

.dropdown-item-clickable.disabled {
    opacity: 0.6;
    pointer-events: none;
}

/*========================================
  Global Icons
========================================*/
.icon {
    width: 20px;
    height: 20px;
}

/*========================================
  Global Badges & Capacity Indicators
========================================*/
.badge {
    display: inline-block;
    padding: 2px 6px;
    border-radius: 4px;
    font-size: 12px;
    margin-left: 5px;
}

    .badge[data-capacity="Closed"] {
        background-color: #ccc;
        color: #555;
    }

    .badge[data-capacity="Low"] {
        background-color: #d4edda;
        color: #155724;
    }

    .badge[data-capacity="Medium"] {
        background-color: #fff3cd;
        color: #856404;
    }

    .badge[data-capacity="High"] {
        background-color: #ffeeba;
        color: #856404;
    }

    .badge[data-capacity="Full"] {
        background-color: #f8d7da;
        color: #721c24;
    }

.day-closed {
    background-color: #ccc;
    color: #555;
}

.day-low {
    background-color: #d4edda;
    color: #155724;
}

.day-medium {
    background-color: #fff3cd;
    color: #856404;
}

.day-high {
    background-color: #ffeeba;
    color: #856404;
}

.day-full {
    background-color: #f8d7da;
    color: #721c24;
}

/*========================================
  Global Buttons & Messages
========================================*/
.confirm-message {
    margin-bottom: 20px;
}

.confirm-button {
    background-color: var(--brand-primary);
    color: var(--brand-on-primary);
    padding: 12px 20px;
    min-height: 44px; /* comfortable touch target */
    border: none;
    border-radius: 4px;
    cursor: pointer;
    font-size: 16px;
    transition: background-color 0.3s;
}

    .confirm-button:hover:not(:disabled) {
        background-color: var(--brand-primary-hover);
    }

    .confirm-button:disabled {
        background-color: #aaa;
        cursor: not-allowed;
    }

.success-message {
    color: var(--status-success-text);
    margin-top: 10px;
}

.error-message {
    color: var(--status-error-text);
    margin-top: 10px;
}

.info-text {
    color: #555;
    font-size: 14px;
    margin-top: 10px;
}

.thank-you-title {
    font-size: 2rem;
    font-weight: 600;
    margin-bottom: 20px;
}

/*========================================
  Notice / callout (e.g. the one-person booking note)
========================================*/
.notice {
    margin: 1rem 0;
    padding: 12px;
    border: 1px solid #ccc;
    border-radius: 4px;
    background-color: var(--surface-card);
    text-align: left;
}

.notice-header {
    display: flex;
    align-items: center;
    gap: 8px;
}

.notice-title {
    margin: 0;
    font-size: 14px;
    font-weight: 600;
}

.notice-icon {
    width: 18px;
    height: 18px;
    flex-shrink: 0;
    color: var(--status-warning-text);
}

.notice-body {
    margin-top: 4px;
    color: #555;
    font-size: 14px;
}

/*========================================
  Form Layout Improvements
========================================*/
.input-group {
    margin-bottom: 15px;
}

.form-section {
    margin-top: 2rem;
}

.form-group {
    margin-bottom: 1rem;
}

    .form-group label {
        font-weight: 600;
        margin-bottom: 0.25rem;
        display: block;
    }

/*========================================
  Component-Specific Styles
========================================*/

/* Home / Booking Form

   The booking form is a stack of <section>s revealed one after another as the
   user makes choices, so each needs to read as its own step. (The rules that
   used to do this hung off a `.home` class that no element carries — they were
   dead, which is why the form read as one undifferentiated block.) */
.app-content > section {
    margin-bottom: 1.5rem;
}

    .app-content > section:last-child {
        margin-bottom: 0;
    }

/* Section Title — a heading for the block BELOW it, so it needs clear space
   above, tight space below, and a rule to bind it to its own content. */
.section-title {
    margin-top: 2rem;
    margin-bottom: 1rem;
    padding-bottom: 0.5rem;
    border-bottom: 1px solid #e0e0e0;
    font-size: 1.25rem;
    font-weight: 600;
    color: #333;
}

/* Booking Details (shared by home & bookingDetail.razor) */
.booking-details {
    margin-bottom: 1.5rem;
}

    .booking-details .booking-field {
        display: flex;
        align-items: baseline;
        gap: 0.5rem;
        margin-bottom: 0.5rem;
    }

        .booking-details .booking-field .label {
            width: 220px;
            flex-shrink: 0;
            font-weight: 600;
            color: #333;
        }

        .booking-details .booking-field .value {
            font-weight: bold;
            color: #111;
            min-width: 0;
            overflow-wrap: anywhere; /* long references / emails must not overflow */
        }

    .booking-details .metadata-section {
        margin-top: 1.5rem;
    }

        .booking-details .metadata-section .metadata-title {
            font-weight: 600;
            margin-bottom: 0.5rem;
        }

        .booking-details .metadata-section .metadata-items {
            margin-left: 1rem;
            padding-left: 1rem;
            border-left: 2px solid #ccc;
        }

        .booking-details .metadata-section .metadata-field {
            display: flex;
            flex-wrap: wrap;
            gap: 0 1rem;
            justify-content: space-between;
            margin-bottom: 0.25rem;
            overflow-wrap: anywhere;
        }

        .booking-details .metadata-section .metadata-label {
            font-weight: 600;
        }

/* Queue Page */
.queue .card-container {
    display: flex;
    gap: 1rem;
}

.queue .booking-card {
    background: var(--surface-card);
    padding: 20px;
    border-radius: 4px;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
}

/* Thank You Section (example replacement for Tailwind) */
.thank-you-section {
    margin-top: 10px;
    margin-bottom: 10px;
}

/*========================================
  Queue Screen Redesign (Updated)
========================================*/

.queue-layout {
    display: flex;
    flex-direction: column;
    height: 100vh;
    background-color: var(--surface-backdrop);
    color: #fff;
    font-family: var(--font-body);
}

.queue-columns {
    display: flex;
    justify-content: space-between;
    flex: 1;
    padding: 30px 40px;
    gap: 40px;
}

.queue-section-header {
    font-size: 1.75rem;
    font-weight: 700;
    padding-bottom: 10px;
}

.queue-section.now-serving {
    flex-grow: 1;
}

.queue-section.waiting-queue {
    flex-grow: 2;
}

.called-column {
    flex: 1;
    display: flex;
    gap: 20px;
    flex-direction: column;
    overflow-y: auto;
}

.queue-column {
    flex: 2;
    display: grid;
    grid-template-columns: 1fr 1fr 1fr;
    gap: 20px;
    overflow-y: auto;
    opacity: 0.75;
}

.called-card,
.queue-card {
    background-color: #f5f5f5;
    color: #000;
    padding: 15px;
    font-size: 1.8rem;
    line-height: 1.3;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.15);
    height: fit-content;
    justify-items: center;
}

    .called-card.highlight {
        background-color: #d4edda; /* soft green */
        border-left: 8px solid #388e3c; /* medium green */
        color: #1b5e20;
        font-weight: 700;
        font-size: 2.4rem;
    }

.queue-card {
    border-left: 5px solid #607d8b;
}

.queue-header-right .time {
    font-size: 1.25rem;
    font-weight: 700;
}

.queue-header-right .location-name {
    font-size: 0.75rem;
}


/*========================================
  Booking site — small screens (phones)

  Everything above is the shared/desktop layout. Below ~640px the dialog stops
  being a centred card and becomes the screen: full-bleed, no radius, no
  shadow, and at least as tall as the viewport. Two-column rows collapse to one
  so that selects and dropdowns get the full width instead of truncating their
  labels. Clients may override these rules like any other.
========================================*/
@media (max-width: 640px) {
    /* Full-screen, not a floating card. */
    .app-fullscreen {
        align-items: stretch;
    }

    .app-dialog {
        max-width: none;
        min-height: 100vh;
        min-height: 100dvh;
        border-radius: 0;
        box-shadow: none;
        /* Keeps the confirm button clear of the iOS home indicator. */
        padding-bottom: env(safe-area-inset-bottom, 0px);
    }

    .app-content {
        padding: 16px;
    }

    /* One field per row: side-by-side selects truncate their options at this width. */
    .two-column-grid {
        grid-template-columns: 1fr;
        gap: 16px;
    }

    /* The header wraps rather than squeezing the logo when several flags are shown. */
    .app-header {
        flex-wrap: wrap;
        gap: 10px;
    }

    .flag-wrapper {
        margin-right: 0;
    }

    /* Full-width primary action — the standard mobile affordance, and an easy target. */
    .confirm-button {
        width: 100%;
    }

    /* The menu is anchored to a now full-width control, so it can afford to be taller. */
    .dropdown-menu {
        max-height: 50vh;
    }

    /* A 220px label column leaves almost nothing for the value on a phone. */
    .booking-details .booking-field {
        flex-direction: column;
        gap: 0;
        align-items: flex-start;
        margin-bottom: 0.75rem;
    }

        .booking-details .booking-field .label {
            width: auto;
        }

    /* Label-left / value-right leaves the value jammed against the screen edge;
       stack it and cut the indent so long names and emails have room. */
    .booking-details .metadata-section .metadata-field {
        flex-direction: column;
        align-items: flex-start;
        margin-bottom: 0.5rem;
    }

    .booking-details .metadata-section .metadata-items {
        margin-left: 0;
        padding-left: 0.75rem;
    }

    .thank-you-title {
        font-size: 1.5rem;
    }
}

/*========================================================================
  KIOSK SURFACE

  Everything below themes the kiosk (the .kiosk-* components). The kiosk host
  document carries `class="kiosk"` on <html>, so:

  - `.kiosk` declares the kiosk-only tokens plus the few that differ on the
    kiosk (typography, status shades). It has the same specificity as `:root`
    and sits after the booking-site :root above, so on the kiosk it wins —
    while a client's own `:root { … }` override (appended last on both
    surfaces) still wins over both. The brand palette is shared: it lives in
    :root and is not re-declared here.
  - The booking site never carries that class, so none of these rules — the
    kiosk token values, the full-screen scroll lock, or the .kiosk-* components
    — reach it. They stay inert there.
========================================================================*/
.kiosk {
    /* The brand palette is shared with the booking site (declared in :root
       above). The tokens below are kiosk-only, or differ on the kiosk. */

    /* --- Surfaces --------------------------------------------------------- */
    --background-main: #f7fafc; /* main background behind kiosk flows */
    /* Fine-grained aliases retained for compatibility with saved themes.    */
    --surface-page: var(--background-main); /* behind everything             */
    --surface-card: #ffffff; /* the main content panel           */
    --surface-content: var(--background-main); /* active flow beneath header */
    --surface-input: #ffffff;
    --surface-display: transparent;
    --surface-muted: #edf2f7; /* numpad keys, inert areas         */
    --surface-muted-hover: #e2e8f0;
    --surface-pressed: #cbd5e0;
    --surface-unavailable: var(--surface-pressed);
    --surface-disabled: #f0f0f0;
    --surface-control-disabled: #c0c0c0;
    --surface-overlay: rgba(0, 0, 0, 0.6);
    --surface-loader-track: #dddddd;
    --surface-loader-bar: #000000;

    /* --- Text ------------------------------------------------------------- */
    --text-strong: #0c0c0c;
    --text-body: #2d3748;
    --text-muted: #6c6c6c;
    --text-on-dark: #ffffff;
    --text-disabled: #a0a0a0;
    --text-unavailable: #efefef;
    --text-warning-on-dark: #f5f5f5;
    --text-input: var(--text-body);
    --text-key: var(--text-strong);
    --text-on-pressed: var(--text-body);

    /* --- Status ----------------------------------------------------------- */
    --status-success: #3a593a;
    --status-info: #2f4d66;
    --status-warning: #6b5d2d;
    --status-error: #663a3a;
    --status-error-text: #ff3f33;
    --status-warning-text: #eb5b00;
    --status-danger: #b00020;
    --status-ok: #38a169;
    --status-ok-hover: #2f855a;

    /* --- Borders & radii -------------------------------------------------- */
    --border-subtle: #e2e8f0;
    --border-strong: #cccccc;
    --display-border-width: 1px;
    --radius-sm: 0.25rem;
    --radius-md: 0.25rem;
    --radius-lg: 0rem; /* set to e.g. 16px for a rounded look */

    /* --- Elevation -------------------------------------------------------- */
    --shadow-card: 0 4px 12px rgba(0, 0, 0, 0.25);
    --shadow-raised: 0 10px 20px rgba(0, 0, 0, 0.12);

    /* --- Layout ----------------------------------------------------------- */
    /* Breathing room down each side of the panel. The header cancels it to stay
       full-bleed, so change it here rather than on the individual rules.       */
    --kiosk-gutter: 3rem;

    /* --- Typography ------------------------------------------------------- */
    --font-body: "Segoe UI", Tahoma, Geneva, Verdana, sans-serif;
    --font-size-question: 6vw; /* the "Do you have a booking?" headline */
    --font-size-answer: 12vw; /* the YES / NO buttons                  */
    --font-size-section: 4vw; /* "Enter your booking number"           */
    --font-size-service: 3.2vw; /* service / numpad key labels           */
    --font-size-display: 5vw; /* the numpad's typed value              */
    --font-size-ticket: 3.5rem; /* the printed ticket number on screen   */

    /* --- Motion ----------------------------------------------------------- */
    /* Set every duration to 0s to disable animation on slow kiosk hardware.  */
    --motion-fast: 0.2s;
    --motion-medium: 0.3s;

    /* --- Branding --------------------------------------------------------- */
    /* Overridden at runtime from the server's "Logo" setting. Falls back to
       the neutral wordmark below when no logo is configured.                 */
    --brand-logo: url("data:image/svg+xml;base64,PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHZpZXdCb3g9IjAgMCAyMDAgNDgiPjx0ZXh0IHg9IjAiIHk9IjM0IiBmaWxsPSIjZmZmIiBmb250LWZhbWlseT0iU2Vnb2UgVUksVGFob21hLHNhbnMtc2VyaWYiIGZvbnQtc2l6ZT0iMzAiIGZvbnQtd2VpZ2h0PSI2MDAiIGxldHRlci1zcGFjaW5nPSIyIj5SRVNFUlZBPC90ZXh0Pjwvc3ZnPg==");
    --brand-logo-width: 200px;
    --brand-logo-height: 70px;
}


/* =============================================================================
   2. RESET & APP SHELL
   -----------------------------------------------------------------------------
   #app is the Blazor root. Touch scrolling and overscroll are disabled because a
   kiosk should never rubber-band or reveal the browser chrome.
   ============================================================================= */
.kiosk,
.kiosk body {
    margin: 0;
    padding: 0;
    width: 100vw;
    height: 100vh;
    overflow: hidden;
    touch-action: none;
    overscroll-behavior: none;
    font-family: var(--font-body);
    color: var(--text-body);
}

.kiosk #app {
    width: 100vw;
    height: 100vh;
}

/* The whole check-in screen. Sits behind the header and content. */
.kiosk-screen {
    display: flex;
    flex-direction: column;
    justify-content: center;
    align-items: center;
    width: 100vw;
    height: 100vh;
    position: absolute;
    background-color: var(--surface-page);
}

/* The white panel that holds the header and the active flow. */
.kiosk-panel {
    display: flex;
    flex-direction: column;
    width: 100vw;
    height: 100vh;
    padding: 0 var(--kiosk-gutter);
    background-color: var(--surface-card);
}

/* Fills the space under the header; the flow screens are positioned inside it.
   flex: 1 (not height: 100%) so the box is the space actually left below the
   header — otherwise it is a full 100vh and every screen inside it sits too low. */
.kiosk-content {
    position: relative;
    flex: 1;
    min-height: 0;
    width: 100%;
    background-color: var(--surface-content);
}


/* =============================================================================
   3. HEADER — logo, error banner, language flags
   ============================================================================= */
/* z-index keeps the language flags clickable: a flow screen whose box happens to
   reach up into the header would otherwise paint over them and swallow the taps.
   Stays below the message overlay (2000) and the toast (3000). */
.kiosk-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    /* Full-bleed bar, but the logo and flags keep the panel's gutter so they stay
       aligned with the content below instead of hugging the screen edges. */
    padding: 10px var(--kiosk-gutter);
    background-color: var(--brand-header);
    margin: 0 calc(var(--kiosk-gutter) * -1);
    position: relative;
    z-index: 20;
}

/* The logo. Swap it via the admin's "Logo" setting, not by editing this rule. */
.kiosk-logo {
    width: var(--brand-logo-width);
    height: var(--brand-logo-height);
    background-image: var(--brand-logo);
    background-size: contain;
    background-repeat: no-repeat;
    background-position: center;
}

/* Transient error text shown in the header (network problems, bad config). */
.kiosk-header__error {
    margin: 0 50px;
    display: inline-block;
    color: var(--status-warning-text);
    font-size: 18px;
    font-weight: 700;
    padding: 8px 16px;
    border-radius: var(--radius-sm);
    max-height: 70px;
    overflow: hidden;
}

.kiosk-header__error-label {
    padding: 0;
    margin: 0 0 4px 0;
}

.kiosk-header__error-text {
    padding: 0;
    margin: 0;
    font-weight: normal;
    line-height: 1.3;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

/* Row of clickable country flags. `zoom` scales the flag sprite for touch. */
.kiosk-language-bar {
    display: flex;
    flex-direction: row;
    gap: 10px;
    zoom: 2.5;
    margin-right: 10px;
}

/* An individual flag. The `.flag`, `.small` and country classes come from
   flags.css; `.kiosk-language` is the stable hook for custom styling. */
.kiosk-language {
    cursor: pointer;
}

.kiosk-language--selected {
    outline: 3px solid var(--brand-accent);
    outline-offset: 1px;
}


/* =============================================================================
   4. NAVIGATION — the back arrow shown on every screen except the first
   ============================================================================= */
.kiosk-back {
    display: block;
    position: absolute;
    top: 25px;
    left: 25px;
    padding: 0;
    background: transparent;
    border: none;
    cursor: pointer;
    z-index: 10;
    overflow: visible;
    color: var(--text-strong);
}

.kiosk-back__icon {
    width: 58px;
    height: 58px;
    fill: currentColor;
}

.kiosk-back:hover .kiosk-back__icon {
    transform: translateX(-2px);
    transition: transform var(--motion-fast) ease;
}


/* =============================================================================
   5. QUESTION SCREEN — "Do you have a booking?" YES / NO
   ============================================================================= */
/* Centres the question and the two answer buttons, like the booking screen.
   height: 100% is what makes justify-content bite — without it the box is only
   as tall as its content and there is nothing left to centre in. */
.kiosk-question {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    height: 100%;
}

/* margin-top: 0 kills the browser's default heading margin, which would
   otherwise push the centred block off-centre by its own height. */
.kiosk-question__title {
    font-size: var(--font-size-question);
    color: var(--text-strong);
    margin: 0 0 3vw;
}

.kiosk-question__actions {
    display: flex;
    gap: 7vw;
}

/* The two big answer buttons. */
.kiosk-answer {
    font-size: var(--font-size-answer);
    font-weight: bold;
    border: none;
    border-radius: var(--radius-lg);
    cursor: pointer;
    width: 40vw;
    height: 45vh;
    transition: transform var(--motion-fast) ease;
}

.kiosk-answer:active {
    transform: scale(0.95);
}

.kiosk-answer--yes {
    background-color: var(--brand-primary);
    color: var(--brand-on-primary);
}

.kiosk-answer--no {
    background-color: var(--brand-secondary);
    color: var(--brand-on-primary);
}

/* Small print under the NO button ("you may have to wait"). */
.kiosk-answer__hint {
    display: block;
    margin-top: 0.25em;
    font-size: 2vw;
}


/* =============================================================================
   6. BOOKING SCREEN — heading + numpad
   ============================================================================= */
/* Centres the heading and the numpad, both horizontally and vertically. */
.kiosk-booking {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    height: 100%;
    gap: 2rem;
}

/* Generic screen heading, e.g. "Enter your booking number". */
.kiosk-section-title {
    font-size: 1.875rem;
    font-weight: bold;
    text-align: center;
}

/* margin-top: 0 kills the browser's default heading margin, which would
   otherwise push the centred block off-centre by its own height. */
.kiosk-section-title--booking {
    font-size: var(--font-size-section);
    margin: 0 0 2vh;
}


/* =============================================================================
   7. NUMPAD
   ============================================================================= */
.kiosk-numpad {
    position: relative;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    width: 55vw;
    margin-inline: auto;
}

/* The read-out showing the digits typed so far. */
.kiosk-numpad__display {
    position: relative;
    margin-bottom: 1rem;
    font-size: var(--font-size-display);
    font-weight: bold;
    width: 100%;
    min-width: 0;
    min-height: 7vw;
    border: var(--display-border-width) solid var(--border-subtle);
    border-radius: var(--radius-lg);
    padding: 0.5rem 0.75rem;
    box-sizing: border-box;
    height: 3rem;
    text-align: center;
    display: flex;
    align-items: center;
    justify-content: center;
    background-color: var(--surface-display);
    color: var(--text-input);
}

.kiosk-numpad__value {
    /* The typed digits. Style separately from the surrounding display box. */
}

/* The "✕" that empties the display. */
.kiosk-numpad__clear {
    position: absolute;
    right: 0.5vw;
    appearance: none;
    -webkit-appearance: none;
    background: transparent;
    border: none;
    padding: 0;
    cursor: pointer;
    color: var(--brand-primary);
}

.kiosk-numpad__clear:focus {
    outline: none;
}

.kiosk-numpad__clear-icon {
    height: 6vh;
    width: 6vw;
    fill: currentColor;
}

.kiosk-numpad__keys {
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    gap: 0.5rem;
    width: 100%;
    min-width: 0;
    min-height: 55vh;
}

/* A single key: 0-9 plus "Back" and "OK". */
.kiosk-key {
    padding: 1rem 0;
    background-color: var(--surface-muted);
    color: var(--text-key);
    border: none;
    border-radius: var(--radius-lg);
    text-align: center;
    font-size: var(--font-size-service);
    font-weight: bold;
    cursor: pointer;
    transition: background-color var(--motion-fast) ease, transform var(--motion-fast) ease;
}

.kiosk-key:hover {
    background-color: var(--surface-muted-hover);
}

.kiosk-key:active {
    background-color: var(--surface-pressed);
    color: var(--text-on-pressed);
    transform: scale(0.95);
}

.kiosk-key:disabled {
    background-color: var(--surface-disabled);
    color: var(--text-disabled);
    cursor: not-allowed;
    opacity: 0.6;
    transform: none;
}

.kiosk-key:disabled:hover {
    background-color: var(--surface-disabled);
}


/* =============================================================================
   8. WALK-IN SCREEN — the grid of services / sub-services
   ============================================================================= */
.kiosk-service-grid {
    padding: 0 2rem;
    margin-top: 4rem;
    display: grid;
    gap: 1.5rem;
    grid-auto-rows: minmax(11.4vw, auto);
}

/* Applied automatically depending on how many services the location offers. */
.kiosk-service-grid--two-columns {
    grid-template-columns: repeat(2, 1fr);
}

.kiosk-service-grid--one-column {
    grid-template-columns: 1fr;
}

.kiosk-service {
    padding: 1rem 0;
    border: none;
    border-radius: var(--radius-lg);
    text-align: center;
    font-size: var(--font-size-service);
    font-weight: bold;
    cursor: pointer;
    background-color: var(--brand-primary);
    color: var(--brand-on-primary);
    transition: background-color var(--motion-fast) ease, transform var(--motion-fast) ease;
}

.kiosk-service:active {
    background-color: var(--surface-pressed);
    transform: scale(0.95);
}

/* A service that is closed or at capacity: still tappable, shows a warning. */
.kiosk-service--unavailable {
    background-color: var(--surface-unavailable);
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
}

.kiosk-service__name {
    color: var(--text-on-dark);
}

.kiosk-service--unavailable .kiosk-service__name {
    color: var(--text-unavailable);
}

/* The "currently closed" line under an unavailable service's name. */
.kiosk-service__status {
    color: var(--status-error-text);
    font-size: 0.45em;
    margin-top: 4px;
}


/* =============================================================================
   9. MESSAGE OVERLAY — success / info / warning / error after a check-in
   ============================================================================= */
.kiosk-overlay {
    position: fixed;
    inset: 0;
    background: var(--surface-overlay);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 2000;
    animation: kiosk-fade-in var(--motion-fast) ease-in-out;
}

.kiosk-message {
    width: 60%;
    max-width: 800px;
    padding: 2.5rem 3rem;
    border-radius: var(--radius-lg);
    text-align: center;
    color: var(--text-on-dark);
    box-shadow: var(--shadow-card);
    animation: kiosk-scale-in 0.25s ease-out;
}

.kiosk-message__header {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 0.75rem;
}

.kiosk-message__title {
    font-size: 2rem;
    font-weight: 600;
    margin: 0;
}

/* The ticket number handed to the customer. */
.kiosk-message__body {
    margin: 0.5rem 0 0;
    font-size: 1.4rem;
    font-weight: 400;
}

.kiosk-message--success {
    background: var(--status-success);
}

.kiosk-message--info {
    background: var(--status-info);
}

.kiosk-message--warning {
    background: var(--status-warning);
    color: var(--text-warning-on-dark);
}

.kiosk-message--error {
    background: var(--status-error);
}


/* =============================================================================
   10. LOADING & BUSY INDICATORS
   ============================================================================= */
/* Full-screen loader shown until the kiosk has contacted the server. */
.kiosk-loader {
    width: 100vw;
    height: 100vh;
    align-items: center;
    display: flex;
    justify-content: center;
}

.kiosk-loader__bar {
    width: 240px;
    height: 40px;
    -webkit-mask: linear-gradient(90deg, var(--surface-loader-bar) 70%, transparent 0) left/20% 100%;
    background: linear-gradient(var(--surface-loader-bar) 0 0) left -25% top 0 / 20% 100% no-repeat var(--surface-loader-track);
    animation: kiosk-loader-slide 1s infinite steps(6);
}

/* Small inline spinner, shown inside the OK key while a check-in is in flight. */
.kiosk-spinner {
    width: 100%;
    height: 100%;
    align-items: center;
    display: block;
    position: relative;
}

.kiosk-spinner__disc {
    width: 24px;
    aspect-ratio: 1;
    border-radius: 50%;
    border: 6px solid currentColor;
    animation: kiosk-spinner-clip 0.8s infinite linear alternate,
               kiosk-spinner-flip 1.6s infinite linear;
    margin: 0 auto;
}


/* =============================================================================
   11. SETTINGS SCREEN (staff only — reached by typing the service code)
   ============================================================================= */
.kiosk-settings {
    margin: auto;
    padding: 1rem;
    width: 100%;
    max-width: 600px;
    display: flex;
    flex-direction: column;
}

.kiosk-settings__title {
    padding-left: 1rem;
    margin-bottom: 1rem;
    font-weight: 500;
}

.kiosk-fieldset {
    border: 1px solid var(--border-strong);
    padding: 1rem;
    border-radius: var(--radius-md);
    margin-bottom: 1rem;
}

.kiosk-field {
    margin-bottom: 1rem;
}

.kiosk-input,
.kiosk-select {
    width: 100%;
    padding: 0.5rem;
    font-size: 1rem;
    border: 1px solid var(--border-strong);
    border-radius: var(--radius-md);
    box-sizing: border-box;
    background-color: var(--surface-input);
    color: var(--text-input);
}

/* Inline result of "Validate" / "Test Printer". Wraps rather than widening the panel:
   the validation message can be a full sentence (status code, clock skew, host error). */
.kiosk-status {
    margin-left: 0.5rem;
    display: inline-block;
    max-width: 100%;
    overflow-wrap: anywhere;
}

.kiosk-status--ok {
    color: var(--status-ok);
}

.kiosk-status--error {
    color: var(--status-danger);
}

.kiosk-status--busy {
    color: var(--text-strong);
}

.kiosk-settings__actions {
    display: flex;
    gap: 0.5rem;
}


/* =============================================================================
   12. BUTTONS (settings screen)
   ============================================================================= */
.kiosk-btn {
    padding: 0.5rem 1rem;
    font-size: 1rem;
    cursor: pointer;
    border: none;
    border-radius: var(--radius-md);
    color: var(--text-on-dark);
    display: inline-block;
    text-align: center;
    transition: background-color var(--motion-fast) ease;
}

.kiosk-btn--primary {
    background-color: var(--brand-primary);
    font-weight: 600;
}

.kiosk-btn--primary:hover {
    background-color: var(--brand-primary-hover);
}

.kiosk-btn--success {
    background-color: var(--status-ok);
}

.kiosk-btn--success:hover {
    background-color: var(--status-ok-hover);
}

.kiosk-btn--back {
    background-color: var(--status-warning-text);
}

.kiosk-btn--danger {
    background-color: var(--status-danger);
    margin-left: auto;
}

.kiosk-btn--wide {
    width: 150px;
}

/* Disabled state for every button variant. */
.kiosk-btn:disabled,
.kiosk button:disabled {
    background-color: var(--surface-control-disabled);
    color: var(--text-muted);
    cursor: not-allowed;
    opacity: 0.6;
    pointer-events: none;
    transition: none;
}


/* =============================================================================
   13. FATAL ERROR SCREEN
   -----------------------------------------------------------------------------
   Rendered by the Blazor ErrorBoundary when the app crashes. Deliberately plain:
   it must render even if custom CSS is broken.
   ============================================================================= */
.kiosk-fatal {
    width: 100vw;
    height: 100vh;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 1.5rem;
    padding: 2rem;
    background: var(--surface-card);
    color: var(--brand-primary);
    text-align: center;
}

.kiosk-fatal__title {
    margin: 0;
    font-size: 3rem;
    font-weight: 700;
}

.kiosk-fatal__text {
    margin: 0;
    max-width: 40rem;
    font-size: 1.25rem;
}

.kiosk-fatal__actions {
    display: flex;
    gap: 1rem;
}

.kiosk-fatal__button {
    min-width: 12rem;
    padding: 1rem 1.5rem;
    border: none;
    background: var(--brand-primary);
    color: var(--brand-on-primary);
    font-size: 1.1rem;
    font-weight: 600;
    cursor: pointer;
}

.kiosk-fatal__button--secondary {
    background: var(--brand-secondary);
}

/* Blazor's built-in disconnect banner (index.html). */
.kiosk #blazor-error-ui {
    position: fixed;
    bottom: 0;
    left: 0;
    right: 0;
    z-index: 3000;
    padding: 0.8rem 1.4rem;
    background: var(--status-warning);
    color: var(--text-on-dark);
    box-shadow: var(--shadow-raised);
}

.kiosk #blazor-error-ui .reload,
.kiosk #blazor-error-ui .dismiss {
    color: var(--text-on-dark);
    cursor: pointer;
    margin-left: 0.75rem;
}

/* Reserved for a notch/status bar on tablet hardware. */
.kiosk .status-bar-safe-area {
    height: env(safe-area-inset-top, 0);
}


/* =============================================================================
   14. ANIMATIONS
   -----------------------------------------------------------------------------
   Redefine any keyframe below (or zero out the --motion-* tokens) to change or
   remove motion.
   ============================================================================= */
@keyframes kiosk-fade-in {
    from { opacity: 0; }
    to { opacity: 1; }
}

@keyframes kiosk-scale-in {
    from { transform: scale(0.9); opacity: 0; }
    to { transform: scale(1); opacity: 1; }
}

@keyframes kiosk-loader-slide {
    100% { background-position: right -25% top 0; }
}

@keyframes kiosk-spinner-clip {
    0%    { clip-path: polygon(50% 50%, 0 0, 50% 0%, 50% 0%, 50% 0%, 50% 0%, 50% 0%); }
    12.5% { clip-path: polygon(50% 50%, 0 0, 50% 0%, 100% 0%, 100% 0%, 100% 0%, 100% 0%); }
    25%   { clip-path: polygon(50% 50%, 0 0, 50% 0%, 100% 0%, 100% 100%, 100% 100%, 100% 100%); }
    50%   { clip-path: polygon(50% 50%, 0 0, 50% 0%, 100% 0%, 100% 100%, 50% 100%, 0% 100%); }
    62.5% { clip-path: polygon(50% 50%, 100% 0, 100% 0%, 100% 0%, 100% 100%, 50% 100%, 0% 100%); }
    75%   { clip-path: polygon(50% 50%, 100% 100%, 100% 100%, 100% 100%, 100% 100%, 50% 100%, 0% 100%); }
    100%  { clip-path: polygon(50% 50%, 50% 100%, 50% 100%, 50% 100%, 50% 100%, 50% 100%, 0% 100%); }
}

@keyframes kiosk-spinner-flip {
    0%      { transform: scaleY(1) rotate(0deg); }
    49.99%  { transform: scaleY(1) rotate(135deg); }
    50%     { transform: scaleY(-1) rotate(0deg); }
    100%    { transform: scaleY(-1) rotate(-135deg); }
}
