/* /Components/Capture/CapturePanel.razor.rz.scp.css */
/* #78. A wrapping row of thumbnails: it has to read as "pages in order" on a phone and on a
   desktop without two layouts. */
.capture-panel__pages[b-etmd0j35i5] {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
}

.capture-panel__page[b-etmd0j35i5] {
    width: 148px;
}

.capture-panel__thumb[b-etmd0j35i5] {
    width: 100%;
    /* Fixed height with object-fit so a mix of portrait and landscape photos still lines up --
       phone cameras produce both, often in the same document. */
    height: 180px;
    object-fit: cover;
    display: block;
    border-radius: 2px;
    background: #f1f7f2;
}

/* #977: a PDF frame has no picture to show, so its tile is the same size as a photo's and says
   what it is. */
.capture-panel__thumb--pdf[b-etmd0j35i5] {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 4px;
    text-align: center;
}

/* #464: the in-place camera control. A <label> wrapping a visually hidden file input, because that is
   the one construction every mobile browser opens the camera from on a tap -- a script-driven .click()
   on a hidden input loses the user gesture on Safari after any await. Styled to read as a filled
   primary button, since on a device with a camera it IS the primary action. */
.capture-panel__camera[b-etmd0j35i5] {
    position: relative;
    display: inline-flex;
    align-items: center;
    gap: 0.5rem;
    padding: 0.375rem 1rem;
    border-radius: var(--mud-default-borderradius, 4px);
    background: var(--mud-palette-primary);
    color: var(--mud-palette-primary-text);
    font-weight: 500;
    cursor: pointer;
    user-select: none;
}

.capture-panel__camera:focus-within[b-etmd0j35i5] {
    outline: 2px solid var(--mud-palette-primary-darken, currentColor);
    outline-offset: 2px;
}

.capture-panel__camera--busy[b-etmd0j35i5] {
    opacity: 0.6;
    pointer-events: none;
}

/* Hidden but still in the accessibility tree and still focusable, so a keyboard or switch user
   reaches the camera through the same control as a finger. ::deep because InputFile is a child
   component and does not carry this stylesheet's scope attribute. */
.capture-panel__camera[b-etmd0j35i5]  input[type=file] {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    opacity: 0;
    cursor: pointer;
}

/* The sources row wraps rather than scrolling: at phone width the two buttons stack, and nothing in
   this panel is allowed to push the page body sideways. */
.capture-panel__sources[b-etmd0j35i5] {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 8px;
    max-width: 100%;
}

/* #464: every control introduced here meets 44x44 below Lg. SAME threshold as the row-action rule in
   wwwroot/css/app.css (max-width: 1279.98px, WCAG 2.5.5) -- reused, not a second breakpoint. */
@media (max-width: 1279.98px) {
    .capture-panel__camera[b-etmd0j35i5],
    .capture-panel__sources[b-etmd0j35i5]  .capture-panel__source {
        min-height: 44px;
        min-width: 44px;
    }
}
/* /Components/Capture/CaptureResumeBanner.razor.rz.scp.css */
/* #78. Thin and amber, as requested -- it has to be noticeable without stealing the page.
   Amber rather than the brand green: this is a transient offer, not part of the app's furniture. */
.capture-resume-banner[b-r8bnshj5zp] {
    background: #FFBD59;
    border-bottom: 1px solid #E5A73F;
    min-height: 34px;
}

.capture-resume-banner__action[b-r8bnshj5zp] {
    color: #23302a;
    text-transform: none;
    font-weight: 600;
    justify-content: space-between;
    padding: 2px 12px;
    min-height: 34px;
}

.capture-resume-banner__label[b-r8bnshj5zp] {
    /* A long form name plus a client name will not fit a phone; truncate rather than wrap and
       double the banner's height. */
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    text-align: left;
    flex: 1;
}

/* #180: the "we could not find out" bar. Deliberately NOT amber and deliberately not full-width
   tappable -- it is a correction, not an offer, and an offer-coloured bar over a target we do not
   have is the thing this state exists to stop. Muted grey, same 34px height so the shell does not
   jump between the two. */
.capture-resume-banner--unavailable[b-r8bnshj5zp] {
    background: #ECEAE4;
    border-bottom: 1px solid #D6D2C8;
    color: #4A4A46;
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 2px 12px;
    font-size: 0.8125rem;
}

.capture-resume-banner--unavailable .capture-resume-banner__retry[b-r8bnshj5zp] {
    color: #23302a;
    text-transform: none;
    font-weight: 600;
    flex: 0 0 auto;
}
/* /Components/Dashboard/DashboardStatCard.razor.rz.scp.css */
.dashboard-stat-card[b-s3n6hm3a1q] {
    transition: box-shadow 120ms ease-out;
}

.dashboard-stat-card:hover[b-s3n6hm3a1q],
.dashboard-stat-card:focus-visible[b-s3n6hm3a1q] {
    box-shadow: 0 0 0 2px var(--mud-palette-primary);
    outline: none;
}

/* Dimmed so a zero reads as "nothing here" rather than "broken link". */
.dashboard-stat-card-inert[b-s3n6hm3a1q] {
    opacity: .65;
}
/* /Components/Dashboard/HousingInventoryClusterCard.razor.rz.scp.css */
/* #891: a housing inventory block on the dashboard. Relative sizes only, so the card reflows at
   320px (WCAG 1.4.10) as the inventory page's own clusters do. */

.housing-dashboard-bar[b-0keywzdsf4] {
    display: flex;
    height: 12px;
    border-radius: 6px;
    overflow: hidden;
    background: var(--mud-palette-lines-default);
}

.housing-dashboard-segment[b-0keywzdsf4] {
    display: block;
    height: 100%;
}

.housing-dashboard-counts[b-0keywzdsf4] {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 4px;
}

.housing-dashboard-counts li[b-0keywzdsf4] {
    display: flex;
    align-items: center;
    min-width: 0;
    overflow-wrap: anywhere;
}

.housing-dashboard-swatch[b-0keywzdsf4] {
    display: inline-block;
    flex: none;
    width: 10px;
    height: 10px;
    border-radius: 2px;
}

.housing-dashboard-count[b-0keywzdsf4] {
    font-size: 1.15rem;
    font-weight: 600;
}
/* /Components/Workflows/WorkflowPositionBar.razor.rz.scp.css */
/* #217. The bar is pinned to the foot of the VIEWPORT rather than the end of the page: "a static bar
   at the bottom that tracks what step you are in a workflow" (Nate, paragraph 207), and a case
   manager three screens down a PSH intake has to be able to see it without scrolling.

   Its height is not written here. It comes from --hebron-workflow-bar-height in wwwroot/css/app.css,
   because the form page's pinned action row has to sit clear of exactly this many pixels and one
   number in one place is what keeps the two from drifting. min-height rather than height so the bar
   can never collapse to nothing if that property is missing. */
.workflow-position-bar[b-fsn80kaphe] {
    position: fixed;
    left: 0;
    right: 0;
    bottom: 0;
    min-height: var(--hebron-workflow-bar-height);
    box-sizing: border-box;
    display: flex;
    align-items: center;

    background-color: var(--mud-palette-surface);
    border-top: 1px solid var(--mud-palette-lines-default);
    box-shadow: 0 -1px 3px rgba(0, 0, 0, 0.08);

    /* Under MudBlazor's drawer (1200) and app bar (1100), so the phone-width OVERLAY drawer covers the
       bar the way it covers the rest of the page. A pinned drawer does not cover it: the rule below
       starts the bar at the drawer's right edge instead (#869). Under #blazor-error-ui (2000 since #1120) too: a
       fatal-error strip must never be the thing hidden by a status bar. */
    z-index: 900;

    /* The same timing MudBlazor gives .mud-main-content's margin, so the bar slides with the page. */
    transition: left 225ms cubic-bezier(0, 0, 0.2, 1) 0ms;
}

/* #869: the pinned nav drawer used to sit OVER the bar's left end -- "optional" read "ptional" and the
   workflow and stage names were under the menu. The z-index above was written assuming the drawer only
   covered space the bar did not need, and the bar's first items sit in exactly that space.

   So the bar starts where the drawer ends, by the same rule MudBlazor uses to push .mud-main-content
   over: MudLayout carries mud-drawer-open-responsive-md-left while AppShell's responsive nav drawer
   (NavBreakpoint = Breakpoint.Md) is open, and it is beside the page, not over it, from 960px up.
   Below 960px the drawer is an overlay and the bar keeps its full width, and a closed drawer drops the
   class, so the bar is full width again. The ancestor half of this selector is unscoped -- Blazor's
   CSS isolation stamps only the last compound, which is the bar's own root div. If NavBreakpoint
   moves, the -md- and the 960px move with it; WorkflowPositionBarDrawerOffsetTests pins both. */
@media (min-width: 960px) {
    .mud-drawer-open-responsive-md-left .workflow-position-bar[b-fsn80kaphe] {
        left: var(--mud-drawer-width-left);
    }
}

/* Beside the pinned drawer, a laptop's bar is 240px narrower than the window, so the Next control
   takes the same narrower cap the tablet block below gives it, and the workflow name and the reason
   beside it truncate with an ellipsis rather than pushing All steps off the right edge. */
@media (min-width: 960px) and (max-width: 1279.98px) {
    .mud-drawer-open-responsive-md-left .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next {
        max-width: 18rem;
    }
}

/* ::deep ON EVERYTHING BELOW, and #427 found out why the hard way. Every element inside the bar is drawn
   by a MudBlazor component (MudStack, MudText, MudButton), and Blazor's CSS isolation stamps its scope
   attribute only on elements written in THIS file's own markup -- so a plain `.workflow-position-bar__step`
   rule matched nothing. #217's truncation rules had been inert since they shipped; a browser check of the
   Next control showed "8 outstanding" wrapping onto a second line of a bar whose height is a layout
   constant. The bar's root div does carry the attribute, which is what ::deep hangs off. */

.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__inner {
    width: 100%;
    padding: 4px 16px;
    min-width: 0;
}

/* A workflow name plus a stage name will not fit a phone. Truncate rather than wrap: the bar's height
   is a layout constant that other pages position against, so it must not grow a second line. */
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__workflow,
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__step,
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__outstanding,
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__unavailable {
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    min-width: 0;
}

.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__action {
    text-transform: none;
    flex-shrink: 0;
}

/* #427: the Next control and the reason beside it. */

/* The reason may take two lines -- two lines of body2 still sit inside the bar's fixed height -- and is
   clamped rather than allowed to grow the bar. It is the part of the bar that gives up width first
   among the #427 pair, and the full sentence is the button's accessible description
   (aria-describedby) whether it is clamped or not.

   It takes three shares of the spare width to the spacer's one, up to 28rem, so a sentence the width
   of "Fill in this form's required fields and submit it to go on." (389px, measured) sits on one line
   on a wide desktop (1473px and up, measured). At 1 1 10rem and 24rem it was given 353px of a 1473px
   window and left "on." alone on a second line. When it does have to wrap, balanced wrapping splits it
   into two even lines rather than one full line and one word. */
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next-status {
    display: -webkit-box;
    -webkit-line-clamp: 2;
    -webkit-box-orient: vertical;
    overflow: hidden;
    flex: 3 1 10rem;
    min-width: 7rem;
    max-width: 28rem;
    line-height: 1.25;
    text-align: end;
    text-wrap: balance;
}

/* The title is what the control is for, so it keeps its width and the reason beside it gives way; very
   long form titles ("Hebron Housing Services Release of Information") still truncate, at the end. */
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next {
    text-transform: none;
    flex: 0 0 auto;
    max-width: 26rem;
}

/* The title truncates at its END, so "Next:" and the start of the form's name always show. */
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next .mud-button-label {
    min-width: 0;
    overflow: hidden;
}

.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next-text {
    min-width: 0;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

/* Disabled, but READABLE: the name of the next form is the whole reason the control is on screen while
   it cannot be pressed, and MudBlazor's disabled palette (26% black) would all but hide it. Text
   secondary on the surface (about 6:1) is the contrast the rest of the bar's text has. !important
   because MudBlazor's own `.mud-button-root:disabled` colour is. */
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next:disabled {
    color: var(--mud-palette-text-secondary) !important;
    border-color: var(--mud-palette-lines-inputs);
}

/* Green, and legible on it. This was written when the theme's Success (#2E9E5B) under white text measured
   about 3.4:1; #748 has since darkened Success itself to pass, but primary-darken (HebronTheme's GreenDark,
   #265F36, about 7.6:1) stays the ready colour so this control matches the rest of the bar. Hover and focus
   keep it rather than switching to success-darken. */
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next--ready:enabled,
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next--ready:enabled:hover,
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next--ready:enabled:focus-visible,
.workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next--ready:enabled:active {
    background-color: var(--mud-palette-primary-darken);
    color: #fff;
}

/* The content area beside a pinned nav drawer cannot hold the workflow's name, its stage, the outstanding
   count, a reason and two buttons on one line. The bearings are what #427 is for, so the summary gives
   way first -- the stage on a laptop, the rest on a phone -- and All steps still leads to the whole
   picture. */
@media (max-width: 1279.98px) {
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__step {
        display: none;
    }

    /* The same 44px thumb floor app.css puts on the row actions and on "Set to today" below this
       breakpoint (#511, #518). MudBlazor's Size.Small button measures 30.75px tall -- checked in a
       browser at 390px -- which is a mouse target, and these two are what a case manager presses
       while holding the tablet. 44px is the WCAG 2.5.5 / Apple HIG minimum.

       Both controls, so the pair still sits on one baseline. */
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next,
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__action {
        min-height: 44px;
    }

    /* And the bar absorbs those extra pixels rather than growing. --hebron-workflow-bar-height is
       52px and #202's pinned Save Draft / Submit row lifts by exactly that, so a 53px bar would sit
       1px over the control it must never cover. 52 less the 1px top border leaves 51; at 3px above
       and below, a 44px button fits in 50. Measured, not reasoned: at 4px the bar came back 53px. */
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__inner {
        padding-block: 3px;
    }
}

@media (max-width: 959.98px) {
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next {
        max-width: 18rem;
    }
}

/* A phone (checked at 390px wide): the summary and the route icon go, the gaps tighten, and the reason
   takes whatever width is left in a smaller type -- so "All steps" is never pushed off the right edge,
   which is what a first browser check of this bar showed. */
@media (max-width: 599.98px) {
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__icon,
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__workflow,
    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__outstanding {
        display: none;
    }

    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__inner {
        gap: 6px !important;
        padding: 3px 8px; /* 3px above and below for the 44px thumb targets -- see the Lg block. */
    }

    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next-status {
        flex: 1 1 0;
        min-width: 0;
        font-size: 0.75rem;
    }

    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__next {
        max-width: 36vw;
    }

    .workflow-position-bar[b-fsn80kaphe]  .workflow-position-bar__action {
        padding-inline: 4px;
        min-width: 0;
    }
}
/* /Pages/Admin/ProgramSetup.razor.rz.scp.css */
/* re: #811: the step list wraps rather than scrolling sideways, down to 320px. */
.program-setup-steps[b-zb7a5jakkh] {
    display: flex;
    flex-wrap: wrap;
    gap: 0.25rem 0.5rem;
    list-style: none;
    margin: 0;
    padding: 0;
}
/* /Pages/Auth/Login.razor.rz.scp.css */
/* Hebron Housing Services — login screen.
   Two-panel layout: a green brand panel (mission + logo) and a refined form card.
   Brand colours mirror Theme/HebronTheme.cs. */

.login-page[b-0fhcdywkdh] {
    display: flex;
    min-height: 100vh;
    width: 100%;
}

/* ---------- Brand panel ---------- */
.login-brand[b-0fhcdywkdh] {
    position: relative;
    flex: 1 1 46%;
    overflow: hidden;
    display: flex;
    align-items: center;
    padding: 4rem;
    color: #fff;
    background:
        radial-gradient(circle at 28% 18%, rgba(255, 255, 255, 0.18), transparent 55%),
        linear-gradient(150deg, #317a45 0%, #265f36 100%); /* HebronTheme Green to GreenDark (#748: white on #3e9c58 was 3.44:1) */
}

.login-watermark[b-0fhcdywkdh] {
    position: absolute;
    right: -3rem;
    bottom: -4rem;
    width: 26rem;
    max-width: 70%;
    filter: brightness(0) invert(1);
    opacity: 0.08;
    transform: rotate(-6deg);
    pointer-events: none;
    user-select: none;
}

.login-brand-content[b-0fhcdywkdh] {
    position: relative;
    z-index: 1;
    max-width: 30rem;
}

.login-brand-logo[b-0fhcdywkdh] {
    width: 16rem;
    max-width: 80%;
    height: auto;
    margin-bottom: 2.75rem;
    animation: hebron-rise-b-0fhcdywkdh 0.6s cubic-bezier(0.22, 1, 0.36, 1) both;
    animation-delay: 0.05s;
}

.login-brand-headline[b-0fhcdywkdh] {
    margin: 0 0 1rem;
    font-weight: 700;
    font-size: clamp(2rem, 3.4vw, 3rem);
    line-height: 1.08;
    letter-spacing: -0.01em;
    animation: hebron-rise-b-0fhcdywkdh 0.6s cubic-bezier(0.22, 1, 0.36, 1) both;
    animation-delay: 0.15s;
}

.login-brand-mission[b-0fhcdywkdh] {
    margin: 0;
    font-size: 1.1rem;
    font-weight: 400;
    line-height: 1.5;
    color: rgba(255, 255, 255, 0.88);
    animation: hebron-rise-b-0fhcdywkdh 0.6s cubic-bezier(0.22, 1, 0.36, 1) both;
    animation-delay: 0.25s;
}

/* ---------- Form panel ---------- */
.login-form[b-0fhcdywkdh] {
    flex: 1 1 54%;
    display: flex;
    align-items: center;
    justify-content: center;
    padding: 2.5rem 1.5rem;
    background: #f6f9f6;
}

.login-form[b-0fhcdywkdh]  .login-card {
    width: 100%;
    max-width: 26rem;
    padding: 2.75rem;
    border-radius: 16px;
    background: #fff;
    border: 1px solid #eaf1ec;
    box-shadow: 0 18px 48px -24px rgba(47, 125, 69, 0.35);
    animation: hebron-rise-b-0fhcdywkdh 0.55s cubic-bezier(0.22, 1, 0.36, 1) both;
    animation-delay: 0.1s;
}

/* Logo inside the card — only shown when the brand panel is hidden (mobile). */
.login-card-logo[b-0fhcdywkdh] {
    display: none;
    width: 13rem;
    max-width: 70%;
    height: auto;
    margin: 0 auto 2rem;
}

.login-form[b-0fhcdywkdh]  .login-card-title {
    font-weight: 700;
    color: #2b302c;
}

.login-form[b-0fhcdywkdh]  .login-card-subtitle {
    color: #5c665e;
    margin-top: 0.25rem;
}

.login-form[b-0fhcdywkdh]  .login-submit {
    border-radius: 10px;
    font-weight: 600;
    letter-spacing: 0.01em;
    height: 3rem;
}

.login-card-footer[b-0fhcdywkdh] {
    margin-top: 1.5rem;
    text-align: center;
}

@keyframes hebron-rise-b-0fhcdywkdh {
    from {
        opacity: 0;
        transform: translateY(16px);
    }

    to {
        opacity: 1;
        transform: none;
    }
}

/* ---------- Responsive: stack to a single column ---------- */
@media (max-width: 959px) {
    .login-brand[b-0fhcdywkdh] {
        display: none;
    }

    .login-form[b-0fhcdywkdh] {
        flex: 1 1 100%;
    }

    .login-card-logo[b-0fhcdywkdh] {
        display: block;
    }
}

@media (prefers-reduced-motion: reduce) {
    .login-brand-logo[b-0fhcdywkdh],
    .login-brand-headline[b-0fhcdywkdh],
    .login-brand-mission[b-0fhcdywkdh],
    .login-form[b-0fhcdywkdh]  .login-card {
        animation: none;
    }
}
/* /Pages/Forms/FormBuilder.razor.rz.scp.css */
/* Form builder canvas item states. Two independent signals:
   .builder-item-selected persists — it shows which field the property editor on the right is bound
   to — while .builder-item-new is a one-shot flash so the eye finds a just-added field or section.
   Both live on the wrapper div rather than the MudPaper so the ring hugs the paper's border box. */

.builder-item[b-li1ckrx6ts] {
    border-radius: var(--mud-default-borderradius);
}

.builder-item-selected[b-li1ckrx6ts] {
    box-shadow: 0 0 0 2px var(--mud-palette-primary);
}

/* The animation ends transparent, so the selected ring underneath reappears on its own when the
   flash finishes; the class is then dropped after FlashDuration (FormBuilder.razor). */
.builder-item-new[b-li1ckrx6ts] {
    animation: builder-item-flash-b-li1ckrx6ts 1.5s ease-out;
}

@keyframes builder-item-flash-b-li1ckrx6ts {
    from {
        box-shadow: 0 0 0 4px var(--mud-palette-primary);
    }

    to {
        box-shadow: 0 0 0 4px rgba(0, 0, 0, 0);
    }
}

/* An invalid schema key is a data-loss bug waiting to happen (two fields, one answer), so it
   outranks the selection ring -- the error state must stay visible while the field is selected. */
.builder-item-invalid[b-li1ckrx6ts] {
    box-shadow: 0 0 0 2px var(--mud-palette-error);
}

/* #760: the keyboard's way into a field. The same primary ring the selected card wears, drawn as an
   outline so it shows on top of a selected or invalid ring rather than replacing it. */
.builder-card-select[b-li1ckrx6ts] {
    border-radius: var(--mud-default-borderradius);
}

.builder-card-select:focus-visible[b-li1ckrx6ts] {
    outline: 2px solid var(--mud-palette-primary);
    outline-offset: 2px;
}
/* /Pages/Forms/InstanceDetail.razor.rz.scp.css */
/* #202: the Save Draft / Submit row, pinned to the bottom of the viewport for as long as the form is
   taller than it.

   "wherever you are, there should always be the save draft option" (Nate, paragraph 075) -- "Yes,
   that's so important" (the PSH case manager, 076). A PSH intake runs to dozens of fields, and the row used to
   render after the last signature card, which on the longest seeded form is several screens below the
   fold.

   This and the header rule below (#782) are the only position:sticky in the client, and both are
   scoped on purpose. The bar itself is
   drawn by DynamicFormRenderer, which FormBuilder also renders for its preview; putting the rule in
   wwwroot/css/app.css would pin it everywhere that component is ever used. `::deep` reaches the child
   component's markup from this page's own scope, so the pin belongs to the form-filling page and
   nowhere else.

   position:sticky needs an unclipped scroll ancestor. MudPaper is position:relative with no overflow,
   and neither .mud-layout nor .mud-main-content clips, so the scrollport here is the viewport.

   #218 added Previous / "Page N of M" / Next INSIDE this row rather than as a bar of its own, so
   pagination needs no rule here and adds no third fixed element to the stack. The row is a wrapping
   flex line, so on a narrow viewport the pager drops beneath Save Draft instead of pushing it off. */
.form-fill[b-uxlrk4axw8]  .form-action-bar--sticky {
    position: sticky;

    /* #217 put a second bar at the foot of the viewport, and only one of them can own bottom: 0. This
       row is the one that must never be covered -- it is the whole point of #202 -- so it rides above
       the workflow position bar by exactly that bar's height. The property is 0px whenever no bar is
       on screen (see wwwroot/css/app.css), which is every form that no workflow asked for, so #202's
       placement is untouched there. */
    bottom: var(--hebron-workflow-bar-height, 0px);
    z-index: 2;

    /* Opaque, or the answers scrolling underneath read through the buttons. */
    background-color: var(--mud-palette-surface);

    /* Full bleed across MudPaper's pa-4 (16px), so the rule above the bar spans the card rather than
       stopping short of its padding. */
    margin-inline: -16px;
    padding-inline: 16px;
    padding-block: 8px;
    border-top: 1px solid var(--mud-palette-lines-default);
}

/* #782: the header -- template name and "for <client>" -- pinned to the top while the form scrolls,
   so whose paperwork this is stays answered halfway down a long intake. Below the app bar, which is
   fixed; opaque for the same reason as the action bar. */
.form-instance-header--sticky[b-uxlrk4axw8] {
    position: sticky;
    top: var(--mud-appbar-height, 64px);
    z-index: 3;
    background-color: var(--mud-palette-background);
    padding-block: 8px;
}

/* Short viewports -- a laptop with the browser chrome and an on-screen keyboard up -- are exactly
   where the bar matters most and where it can eat the form. Let it scroll away there rather than
   holding a fifth of the screen. */
@media (max-height: 480px) {
    .form-fill[b-uxlrk4axw8]  .form-action-bar--sticky,
    .form-instance-header--sticky[b-uxlrk4axw8] {
        position: static;
    }
}
/* /Pages/HousingInventory/HousingInventoryList.razor.rz.scp.css */
/* #837: the housing inventory summary -- three labelled clusters of clickable counts, and the
   occupancy bar. Every size here is relative or a floor that fits a 320px viewport (WCAG 1.4.10):
   a cluster takes a third of a wide screen and a whole row of a narrow one, never more. */

.housing-summary-cluster[b-jfwo0yibe8] {
    flex: 1 1 240px;
    min-width: 0;
}

/* The bar is decorative (aria-hidden): the counts under it, each a button, carry the numbers. */
.housing-occupancy-bar[b-jfwo0yibe8] {
    display: flex;
    height: 12px;
    margin: 4px 0 8px;
    border-radius: 6px;
    overflow: hidden;
    background: var(--mud-palette-lines-default);
}

.housing-occupancy-segment[b-jfwo0yibe8] {
    display: block;
    height: 100%;
}

.housing-summary-counts[b-jfwo0yibe8] {
    display: flex;
    flex-direction: column;
    align-items: flex-start;
    gap: 2px;
}

/* Each count is a HousingSummaryCount, whose MudButton this scope does not reach without ::deep. A label that
   meets the edge of a narrow cluster wraps under itself rather than pushing the page wide. */
.housing-summary-counts[b-jfwo0yibe8]  .mud-button-root,
.housing-summary-cluster[b-jfwo0yibe8]  .mud-button-root {
    max-width: 100%;
    justify-content: flex-start;
}

.housing-summary-counts[b-jfwo0yibe8]  .mud-button-label,
.housing-summary-cluster[b-jfwo0yibe8]  .mud-button-label {
    white-space: normal;
    text-align: start;
}
/* /Pages/HousingInventory/HousingSummaryCount.razor.rz.scp.css */
/* #837: the status swatch beside an Occupancy count, matching its segment of the bar. */
.housing-occupancy-swatch[b-372ix7hmw4] {
    display: inline-block;
    flex: none;
    width: 10px;
    height: 10px;
    border-radius: 2px;
}
/* /Pages/Workflows/WorkflowBuilder.razor.rz.scp.css */
/* Workflow builder canvas. The canvas reads TOP TO BOTTOM (scoping answer 2026-08-20: "this should
   be viewed vertically not horizontally as pictured"), so every affordance here is horizontal-rule
   shaped and sits between two rows rather than beside them. */

.wf-item[b-rkp7c7rnzf] {
    border-radius: var(--mud-default-borderradius);
}

.wf-item-selected[b-rkp7c7rnzf] {
    box-shadow: 0 0 0 2px var(--mud-palette-primary);
}

.wf-item-invalid[b-rkp7c7rnzf] {
    box-shadow: 0 0 0 2px var(--mud-palette-error);
}

/* The "add block here" affordance. It occupies a real 24px gap at all times so revealing it never
   shifts the rows underneath the pointer -- only its opacity changes. It stays in the DOM when
   hidden (rather than being rendered conditionally) so it remains keyboard-reachable: focus-within
   brings it up for anyone tabbing through the canvas. */
.wf-gap[b-rkp7c7rnzf] {
    display: flex;
    align-items: center;
    justify-content: center;
    height: 24px;
    opacity: 0;
    transition: opacity 120ms ease-in-out;
}

.wf-gap:hover[b-rkp7c7rnzf],
.wf-gap:focus-within[b-rkp7c7rnzf] {
    opacity: 1;
}

/* A hairline through the gap, so what appears on hover reads as "insert a barrier on this line"
   rather than as a floating button. */
.wf-gap[b-rkp7c7rnzf]::before,
.wf-gap[b-rkp7c7rnzf]::after {
    content: "";
    flex: 1 1 auto;
    border-top: 1px dashed var(--mud-palette-lines-default);
}

.wf-gap-button[b-rkp7c7rnzf] {
    margin: 0 8px;
}

/* A block row: a full-width barrier, deliberately unlike a step card. */
.wf-block[b-rkp7c7rnzf] {
    border-top: 2px solid var(--mud-palette-warning);
    border-bottom: 2px solid var(--mud-palette-warning);
    background-color: var(--mud-palette-background-gray);
}

/* #760: the keyboard's way into a step. The same primary ring the selected card wears, drawn as an
   outline so it shows on top of a selected or invalid ring rather than replacing it. */
.wf-card-select[b-rkp7c7rnzf] {
    border-radius: var(--mud-default-borderradius);
}

.wf-card-select:focus-visible[b-rkp7c7rnzf] {
    outline: 2px solid var(--mud-palette-primary);
    outline-offset: 2px;
}
