/* ==========================================================================
   Health e Match — sign-up forms
   Loaded after styles.css, which supplies every token used here. Nothing in
   this file introduces a colour, a radius or a spacing value of its own.
   ========================================================================== */

/* --------------------------------------------------------------------------
   Density

   The form is stepped so that a person scrolls as little as possible, which
   only pays off if a whole step actually fits on screen. The landing page's
   spacing is built for a page you scroll through; carried into a form it
   spends most of a laptop viewport before the first input.

   So the form runs on a tighter scale of its own, still in whole 17px units:
   one unit between fields inside a block, two between blocks. Everything
   below refers to these rather than to the landing page's section rhythm.
   -------------------------------------------------------------------------- */

/* --------------------------------------------------------------------------
   Page shell
   The form sits on a white panel over the canvas, the same surface treatment
   the landing page uses for How It Works.
   -------------------------------------------------------------------------- */
.form-page {
  /* Not --section-gap. A form page has one section, and the space that reads
     as breathing room between landing-page sections reads as dead air above a
     Back link. */
  padding-block: var(--form-gap) var(--form-block);
}

/* The panel takes the landing page's card padding, which is generous because
   How It Works has three short cards in it. A form step has ten fields, and
   every pixel of that padding is a pixel of the step pushed under the fold. */
.form-shell .panel {
  padding: var(--form-block);
}
@media (min-width: 640px) {
  .form-shell .panel { padding: var(--form-block) calc(var(--hem-unit) * 3); }
}

/* No cap of its own: this element also carries .wrap, so it takes the same
   1200px page measure every landing-page section uses, and the panel inside it
   lands at the same 1072px as the How It Works panel. */
.form-shell {
  margin-inline: auto;
}

.form-masthead {
  text-align: center;
  margin-bottom: var(--form-block);
}
/* Not the landing page's hero scale. There the headline IS the content; here
   it is a label on a task, and at 5rem it costs a third of the fold before
   anyone reaches a field. */
.form-masthead .t-h1 {
  font-size: clamp(2rem, 4.4vw, 2.75rem);
  max-width: 18ch;
  margin-inline: auto;
}
.form-masthead .t-body-lg {
  max-width: 52ch;
  margin-inline: auto;
  margin-top: var(--form-gap);
}

/* On a wide screen the masthead line becomes the page's headline.

   It is marked up as a .t-label and stays one on a phone, where it sits close
   above the card and works as a small caption tying the two together. On a
   desktop the card is far below it and the line is left floating alone on a
   wide field - too quiet to be the only thing naming the page. Same words,
   same element, different weight given to it by width.

   Sized to match .form-masthead .t-h1 rather than the display scale: this is
   a page title above a form, not a hero. */
@media (min-width: 960px) {
  .form-masthead .t-label {
    font-family: var(--hem-font-display);
    font-weight: 700;
    font-size: clamp(2rem, 4.4vw, 2.75rem);
    line-height: var(--hem-lh-h1);
    letter-spacing: -0.02em;
    text-transform: none;
    color: var(--hem-text-heading);
    /* One line. The 18ch measure is inherited from the old .t-h1 treatment,
       which existed to stop a long sentence running the full width - but this
       is a short title, and 18ch broke "Create Free Patient Account" across
       two lines for no reason. No cap and no balancing: there is nothing to
       balance once it fits. */
    white-space: nowrap;
    max-width: none;
    margin-inline: auto;
  }
}

/* --------------------------------------------------------------------------
   Fieldsets
   Each step is a fieldset with a numbered legend, so the form announces its
   own structure to a screen reader rather than relying on visual grouping.
   -------------------------------------------------------------------------- */
.fieldset {
  border: 0;
  padding: 0;
  /* One unit on the stepped forms, where only one fieldset is ever on screen
     and this is really the gap before the actions row. */
  margin: 0 0 var(--form-gap);
}

/* Two units where fieldsets actually stack - the go-live screen. A section
   break has to read as bigger than the gap between two fields inside it, or
   the sections run together. */
/* Both sides :not([hidden]) so this never fires on the stepped forms, where
   the previous fieldset is display:none and the margin would silently push
   every step after the first down by a unit. */
/* --form-block, not --form-gap: adjacent margins collapse to the larger of
   the two, so a matching 17px here would have collapsed into the preceding
   fieldset margin and changed nothing. */
.fieldset:not([hidden]) + .fieldset:not([hidden]) { margin-top: calc(var(--hem-unit) * 3); }

/* No rule between fieldsets. It existed to separate sections on one long
   page; with a step at a time it only drew a line under the first heading of
   an otherwise empty screen. */

/* Only the current step is in the document. `hidden` rather than
   display:none so the step is genuinely removed from the accessibility tree
   and its fields drop out of the tab order. */
.fieldset[hidden] { display: none; }

/* The UA stylesheet gives [hidden] display:none, but any author rule setting
   display beats it - and .btn sets display:inline-flex. Without this the Back
   button carries the hidden attribute, is correctly removed from the
   accessibility tree, and still renders on screen: a button a sighted person
   can see and click but a screen reader has been told does not exist. */
[hidden] { display: none !important; }

.fieldset__legend {
  font-family: var(--hem-font-display);
  font-weight: 700;
  font-size: var(--hem-size-h3);
  line-height: var(--hem-lh-h3);
  color: var(--hem-text-heading);
  margin-bottom: var(--hem-lede-sm);
  padding: 0;
}

.fieldset__hint {
  font-size: var(--hem-size-body);
  color: var(--hem-text-muted);
  margin-bottom: var(--form-gap);
  max-width: 60ch;
}

/* --------------------------------------------------------------------------
   Fields
   -------------------------------------------------------------------------- */
.field {
  display: grid;
  gap: var(--hem-space-2);
  margin-bottom: var(--form-gap);
  /* Rows size to their content instead of stretching. Without this, a field
     placed beside a taller one absorbs the difference by growing its input,
     so two inputs side by side end up different heights and misaligned. */
  align-content: start;
}
/* A pair is one row, so the space after it is declared once - here - rather
   than by each field inside it. Without the reset below, a child's own bottom
   margin stacks on top of the pair's gap, and a pair that has stacked on
   mobile opens to twice the space sitting between any other two fields. */
.field--pair {
  display: grid;
  gap: var(--form-gap) var(--form-block);
  grid-template-columns: 1fr;
  margin-bottom: var(--form-gap);
}
.field--pair > .field { margin-bottom: 0; }
@media (min-width: 640px) {
  .field--pair { grid-template-columns: 1fr 1fr; }
}

/* Three fields that describe one credential - number, state, expiry - and
   only make sense read together. Stacks to a pair, then to a column, so a
   narrow screen never gets three inputs squeezed onto a line. */
.field--trio { grid-template-columns: 1fr; }
@media (min-width: 640px) {
  .field--trio { grid-template-columns: 1fr 1fr; }
}
@media (min-width: 900px) {
  .field--trio { grid-template-columns: 1fr 1fr 1fr; }
}

/* The gap below the last thing in a step belongs to the actions row, which
   sets its own padding-top. Leaving the field's margin there as well doubled
   it, so Continue sat further from the form than anything in the form sat
   from anything else. */
.fieldset > :last-child { margin-bottom: 0; }

.field__label {
  font-family: var(--hem-font-ui);
  font-weight: 700;
  font-size: var(--hem-size-body);
  color: var(--hem-text);
}
/* Scoped to .field__label before, which missed every asterisk outside one -
   the consent checkbox on step 5 among them, where it rendered as plain dark
   text the same colour as the sentence around it. A required marker that does
   not look like a required marker is worse than none: it reads as a typo. */
.req {
  color: var(--hem-crimson);
  margin-left: 2px;
}

.field__hint {
  font-size: var(--hem-size-caption);
  color: var(--hem-text-muted);
  /* Centred with the control it describes. The inputs are full width and the
     card is centred, so a left-aligned hint was the only thing on the step
     hanging off an edge of its own. */
  text-align: center;

  /* Tighter than caption line-height. A hint is one or two short lines under
     a control, not running text, and 1.5 spaced them far enough apart that a
     two-line hint read as two separate notes. */
  line-height: 1.35;

  /* Pulled up out of the field's own 8px gap, to about half it. A hint
     belongs to the control above it, and at the same distance as the label
     sits from the input it read as free-floating between two fields rather
     than attached to one.

     A negative margin rather than a smaller grid gap: the gap also sets
     label-to-input, which is correct as it is. */
  margin-top: -4px;
}

/* A hint that belongs to one column of a pair but has to live outside it to
   keep the two inputs aligned. Sits directly under the pair, closing the gap
   the pair's own bottom margin would otherwise leave. */
.field__hint--under-pair {
  margin-top: calc(var(--form-gap) * -1 + var(--hem-space-2));
  margin-bottom: var(--form-gap);
}

.input,
.select,
.textarea {
  font-family: var(--hem-font-body);
  font-size: var(--hem-size-body);
  line-height: var(--hem-lh-body);
  color: var(--hem-text);
  background: var(--hem-paper);
  border: 2px solid var(--hem-line);
  /* Matches the buttons. Extra horizontal padding because text set hard
     against a fully rounded edge reads as though it is falling out of the
     control. */
  border-radius: var(--hem-radius-pill);
  padding: 12px var(--hem-lede);
  width: 100%;
  min-height: var(--hem-tap-min);
  transition: border-color var(--hem-dur-fast) ease;
}

/* The one exception. A 999px radius on a multi-line box clamps to half its
   height and turns a textarea into a stadium, which fights the straight
   left edge every line of text sits against. It takes the brand's 14px
   ceiling for non-pill corners instead. */
.textarea {
  border-radius: var(--hem-radius-lg);
}
/* The panel is now page-width, so an unconstrained input becomes a 900px
   ribbon holding an email address. Single controls take a comfortable measure
   instead; the panel's width is spent on layout, not on stretching one field.
   Free text is the exception - a textarea genuinely benefits from the room. */
.field > .input,
.field > .select {
  max-width: 32rem;
}

.textarea {
  min-height: calc(var(--hem-unit) * 7);
  resize: vertical;
}
.input:hover,
.select:hover,
.textarea:hover { border-color: var(--hem-teal-300); }

.input:focus-visible,
.select:focus-visible,
.textarea:focus-visible {
  border-color: var(--hem-teal);
  outline: 3px solid var(--hem-teal);
  outline-offset: 2px;
}

.input[aria-invalid="true"],
.select[aria-invalid="true"],
.textarea[aria-invalid="true"] {
  border-color: var(--hem-critical);
}

.field__error {
  font-size: var(--hem-size-caption);
  color: var(--hem-critical);
  font-weight: 700;
}
.field__error:empty { display: none; }

/* Derived display name. Styled as a result rather than a control, so it never
   reads as something the patient can type into. */
.name-preview {
  display: inline-block;
  font-family: var(--hem-font-display);
  font-weight: 700;
  font-size: var(--hem-size-h3);
  line-height: var(--hem-lh-h3);
  color: var(--hem-text-heading);
  background: var(--hem-teal-50);
  /* Sits in the run of inputs, so it takes their shape. */
  border-radius: var(--hem-radius-pill);
  padding: var(--hem-space-3) var(--hem-lede);
  min-width: 12rem;
}
.name-preview[data-empty] {
  color: var(--hem-text-muted);
  font-family: var(--hem-font-body);
  font-weight: 400;

  /* One line, always. The placeholder is a sentence where a name will go, and
     it needed 200px inside 184px of content box - so it broke in two and the
     pill grew to a block. A wrapped placeholder makes the field look like it
     already holds something.

     Two levers together: the generous pill padding comes in (it exists to
     frame a short name, not a sentence), and the type scales with the
     viewport so it still fits at 320px. Both are scoped to the empty state -
     an actual name keeps the full h3 treatment above. */
  white-space: nowrap;
  padding-inline: var(--hem-space-4);
  font-size: clamp(0.875rem, 4.4vw, var(--hem-size-body));
}
/* Centred: the pill is a preview of how the name will appear, and a name
   centred in its own field reads as a label rather than as an entry. */
.name-preview { text-align: center; }
.name-preview__placeholder { font-style: italic; }

/* --------------------------------------------------------------------------
   Option lists
   Conditions and treatments are long, so they scroll inside their own box
   rather than pushing the submit button off the end of a very tall page.
   -------------------------------------------------------------------------- */
.options {
  display: grid;
  gap: var(--hem-space-2);
  max-height: calc(var(--hem-unit) * 16);
  overflow-y: auto;
  padding: var(--hem-lede-sm);
  border: 2px solid var(--hem-line);
  border-radius: var(--hem-radius-md);
  background: var(--hem-surface-raised);
}
@media (min-width: 640px) {
  .options { grid-template-columns: 1fr 1fr; }
}
/* At page width a third column fits, which shortens the scroll through the
   longest section of the form rather than leaving the extra room empty. */
@media (min-width: 1040px) {
  .options { grid-template-columns: repeat(3, 1fr); }
  /* Treatments keep two columns: each carries a status dropdown underneath,
     so three would crowd. */
  .options--treatments { grid-template-columns: 1fr 1fr; }
}

.option {
  display: flex;
  align-items: flex-start;
  gap: var(--hem-space-2);
  padding: var(--hem-space-2);
  border-radius: var(--hem-radius-sm);
  cursor: pointer;
  transition: background-color var(--hem-dur-fast) ease;
}
.option:hover { background: var(--hem-teal-50); }

.option input[type="checkbox"],
.option input[type="radio"] {
  width: 20px;
  height: 20px;
  margin-top: 2px;
  accent-color: var(--hem-teal);
  flex: none;
}
.option__text { font-size: var(--hem-size-body); }

/* One option standing alone as a choice, rather than one of a list.

   The self-pay opt-out sits under a centred search box as the alternative to
   it, so a left-aligned row left it hanging off the column's edge while
   everything around it was centred. Opt-in, not applied to .option itself:
   the consent checkboxes elsewhere are read as a list and must stay left,
   where the eye can run down the boxes.

   The row centres; the label inside it does not. Centring wrapped text beside
   a checkbox breaks the line-up between the box and its first line. */
.option--centred {
  justify-content: center;
  text-align: left;
}
.option--centred .option__text { max-width: 22ch; }

/* The box and its label centre together, as one control.

   An earlier version added a counterweight so the LABEL landed dead centre
   with the box hanging left. Removed: it centred the text at the cost of the
   thing the eye actually reads as the control - a box and a word travelling
   together. justify-content on the row is the whole of it. */

/* A selected treatment reveals its regulatory status control. The status is
   shown exactly as documented, per the public disclosure, so the practice
   must state it rather than the system assuming it. */
.option__status {
  margin-top: var(--hem-space-2);
  display: none;
}
/* The status control is nested inside .option__text, which is what is actually
   adjacent to the input - so the sibling combinator has to reach through it.
   Targeting .option__status directly after ~ silently never matches, and the
   practice is left unable to state a regulatory status at all. */
.option input:checked ~ .option__text .option__status { display: block; }
.option__status .select { padding: 8px var(--hem-space-3); min-height: 0; }

/* --------------------------------------------------------------------------
   Multi-select combobox
   -------------------------------------------------------------------------- */
.cb { display: grid; gap: var(--hem-space-2); }

.cb__field { position: relative; }

.cb__chips {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-wrap: wrap;
  gap: var(--hem-space-2);
}
.cb__chips:empty { display: none; }

.cb__chip {
  display: inline-flex;
  align-items: center;
  gap: var(--hem-space-2);
  padding-right: var(--hem-space-2);
}

/* A term awaiting review reads as provisional rather than settled: outlined
   instead of filled, so it is obvious at a glance which entries are actually
   doing matching work and which are still questions. */
.cb__chip--pending {
  background: transparent;
  border: 2px dashed var(--hem-teal-300);
  color: var(--hem-text-muted);
}
.cb__chip-badge {
  font-size: 0.68rem;
  text-transform: uppercase;
  letter-spacing: var(--hem-track-label);
  color: var(--hem-text-muted);
}

.cb__chip-remove {
  border: 0;
  background: transparent;
  color: inherit;
  font-size: 1.1rem;
  line-height: 1;
  cursor: pointer;
  padding: 2px 4px;
  border-radius: var(--hem-radius-pill);
  min-width: 24px;
  min-height: 24px;
}
.cb__chip-remove:hover { background: rgba(0, 0, 0, .08); }

.cb__list {
  list-style: none;
  margin: var(--hem-space-1) 0 0;
  padding: var(--hem-space-1);
  position: absolute;
  z-index: 20;
  left: 0;
  right: 0;
  max-height: calc(var(--hem-unit) * 15);
  overflow-y: auto;
  background: var(--hem-paper);
  border: 2px solid var(--hem-teal-200);
  border-radius: var(--hem-radius-lg);
  box-shadow: var(--hem-shadow-card);
}

.cb__option {
  padding: var(--hem-space-3) var(--hem-lede-sm);
  border-radius: var(--hem-radius-md);
  cursor: pointer;
  font-size: var(--hem-size-body);
}
.cb__option[aria-selected="true"],
.cb__option:hover {
  background: var(--hem-teal-50);
  color: var(--hem-teal-900);
}

/* The offer to submit an unknown term. Distinct from a real result so nobody
   mistakes a question for an answer. */
.cb__option--suggest {
  display: grid;
  gap: 2px;
  border-top: 1px solid var(--hem-line);
  margin-top: var(--hem-space-1);
}
.cb__suggest-label { font-weight: 700; color: var(--hem-teal); }
.cb__suggest-note { font-size: var(--hem-size-caption); color: var(--hem-text-muted); }

.cb__status {
  font-size: var(--hem-size-caption);
  color: var(--hem-text-muted);
  min-height: 1em;
}
/* Empty most of the time - it only speaks when something is chosen or removed
   - but min-height above reserved 15px under EVERY combobox on the site, and
   with the gap that came to 23px of dead space below each one. It was also
   what put the insurance column 5px out of line with the column beside it.

   Collapsed rather than display:none. A live region has to stay in the
   accessibility tree to be announced when its text changes; hiding it and
   showing it again is exactly the pattern screen readers miss. */
.cb__status:empty {
  min-height: 0;
  height: 0;
  overflow: hidden;
}

/* --------------------------------------------------------------------------
   Consent
   Set apart from ordinary fields: this is the block where a patient agrees to
   store health information, and it should not look like another checkbox.
   -------------------------------------------------------------------------- */
.consent {
  background: var(--hem-teal-50);
  border-radius: var(--hem-radius-md);

  /* One unit on a phone, two on a wide card.

     --hem-lede is 34px, which took 68px out of a 252px column - and after the
     checkbox claimed another 28, the consent sentence was left 137px to wrap
     in and ran to ten lines. A consent someone has to read should not be the
     narrowest column on the page.

     The inset still reads: the teal ground and the rounded corners are what
     mark this as a different kind of block, not the size of its padding. */
  padding: var(--hem-unit);
  margin-bottom: var(--hem-lede);
}
@media (min-width: 640px) {
  .consent { padding: var(--hem-lede); }
}
.consent p {
  font-size: var(--hem-size-caption);
  color: var(--hem-text);
  margin-bottom: var(--hem-lede-sm);
}
.consent .option { padding-left: 0; }
.consent .option:hover { background: transparent; }

/* --------------------------------------------------------------------------
   Progress
   -------------------------------------------------------------------------- */
.progress { margin-bottom: var(--form-block); }

.progress__track {
  height: 6px;
  background: var(--hem-surface);
  border-radius: var(--hem-radius-pill);
  overflow: hidden;
}
.progress__fill {
  height: 100%;
  width: 20%;
  background: var(--hem-teal);
  border-radius: var(--hem-radius-pill);
  transition: width var(--hem-dur-match) var(--hem-ease-glide);
}

.progress__steps {
  list-style: none;
  margin: var(--hem-space-2) 0 0;
  padding: 0;
  display: grid;
  /* Columns follow however many steps the markup has - the practice form
     has four, the patient form five - so neither has to restate the count. */
  grid-auto-flow: column;
  grid-auto-columns: 1fr;
  gap: var(--hem-space-2);
}

.progress__step {
  display: grid;
  justify-items: center;
  gap: var(--hem-space-1);
  text-align: center;
  color: var(--hem-text-muted);
}

.progress__num {
  width: 26px; height: 26px;
  display: grid; place-items: center;
  border-radius: var(--hem-radius-pill);
  border: 2px solid var(--hem-line);
  background: var(--hem-paper);
  font-family: var(--hem-font-ui);
  font-weight: 700;
  font-size: var(--hem-size-caption);
  transition: background-color var(--hem-dur-fast) ease,
              border-color var(--hem-dur-fast) ease,
              color var(--hem-dur-fast) ease;
}

.progress__label {
  font-size: 0.68rem;
  text-transform: uppercase;
  letter-spacing: var(--hem-track-label);
}
/* Labels are the first thing to go when there is no room for them; the
   numbered dots still carry the position. */
@media (max-width: 560px) {
  .progress__label { display: none; }
}

.progress__step[data-state="current"] { color: var(--hem-teal); }
.progress__step[data-state="current"] .progress__num {
  background: var(--hem-teal);
  border-color: var(--hem-teal);
  color: var(--hem-on-teal);
}
.progress__step[data-state="done"] { color: var(--hem-teal-700); }
.progress__step[data-state="done"] .progress__num {
  background: var(--hem-teal-100);
  border-color: var(--hem-teal-300);
  color: var(--hem-teal-900);
}

@media (prefers-reduced-motion: reduce) {
  .progress__fill { transition: none; }
}

/* --------------------------------------------------------------------------
   Submit
   -------------------------------------------------------------------------- */
.form-actions {
  display: grid;
  gap: var(--hem-lede-sm);
  justify-items: center;
  text-align: center;
  padding-top: var(--hem-lede);
}
.form-actions .btn { width: 100%; justify-content: center; }
@media (min-width: 640px) {
  .form-actions .btn { width: auto; min-width: 18rem; }
}

/* Back sits beside Continue rather than under it, so the forward action keeps
   the position the eye already expects. */
.form-actions--steps {
  display: flex;
  flex-wrap: wrap;
  gap: var(--hem-lede-sm);
  justify-content: center;
  align-items: center;
}
.form-actions--steps .btn--quiet { min-width: 0; }
@media (max-width: 639px) {
  .form-actions--steps { flex-direction: column-reverse; }
  .form-actions--steps .btn { width: 100%; }
}

.form-actions__note {
  text-align: center;
  margin-top: var(--hem-lede-sm);
}

/* Status region. Always in the DOM so screen readers announce into it. */
.form-status {
  margin-top: var(--hem-lede);
  padding: var(--hem-lede);
  border-radius: var(--hem-radius-md);
  font-size: var(--hem-size-body);
  display: none;
}
.form-status[data-state="error"],
.form-status[data-state="notice"],
.form-status[data-state="ok"] { display: block; }

.form-status[data-state="error"] {
  background: #FBE9E7;
  border-left: 4px solid var(--hem-critical);
  color: var(--hem-critical);
}
.form-status[data-state="notice"] {
  background: var(--hem-teal-50);
  border-left: 4px solid var(--hem-teal);
  color: var(--hem-text);
}
.form-status[data-state="ok"] {
  background: #E8F3ED;
  border-left: 4px solid var(--hem-success);
  color: var(--hem-success);
}

/* --------------------------------------------------------------------------
   Back link
   -------------------------------------------------------------------------- */
.form-back {
  display: inline-flex;
  align-items: center;
  gap: var(--hem-space-2);
  font-size: var(--hem-size-body);
  color: var(--hem-text-muted);
  text-decoration: none;
  margin-bottom: var(--form-gap);
}
.form-back:hover { color: var(--hem-teal); }

/* --------------------------------------------------------------------------
   Compact masthead after the first step

   The masthead makes a promise - here is what this is, here is what you get.
   That argument earns its space on the screen where somebody decides whether
   to start. From step 2 on they have already decided, and the same 180px of
   headline is re-arguing a point already won while pushing the fields they
   are trying to fill under the fold.

   So it shrinks once they are in. It does not disappear: the h1 stays as the
   thing that tells them which form they are in, and the Back link stays put.
   -------------------------------------------------------------------------- */
.form-page.is-underway .form-masthead {
  margin-bottom: var(--form-gap);
}
.form-page.is-underway .form-masthead .t-h1 {
  font-size: var(--hem-size-h3);
  line-height: var(--hem-lh-h3);
  max-width: none;
}
.form-page.is-underway .form-masthead .t-body-lg {
  display: none;
}

/* --------------------------------------------------------------------------
   Reveal

   A 12-character minimum on a masked field is a typo waiting to happen, and
   the person cannot see the typo, only the rejection afterwards. Letting them
   look is the cheapest fix there is - and safer in practice than the habit it
   replaces, which is choosing a shorter password you can type blind.
   -------------------------------------------------------------------------- */
.field__control {
  position: relative;
  max-width: 32rem;
}
/* The input is nested now, so the measure that used to sit on it lives on the
   wrapper; without this it would stretch the full panel width again. */
.field__control > .input {
  padding-right: calc(var(--hem-unit) * 4);
}

.input-reveal {
  position: absolute;
  right: var(--hem-space-2);
  top: 50%;
  transform: translateY(-50%);
  border: 0;
  background: none;
  cursor: pointer;
  font-family: var(--hem-font-ui);
  font-size: var(--hem-size-caption);
  font-weight: 700;
  color: var(--hem-teal);
  padding: var(--hem-space-2);
  border-radius: var(--hem-radius-pill);
}
.input-reveal:hover { text-decoration: underline; }
.input-reveal:focus-visible {
  outline: 3px solid var(--hem-teal);
  outline-offset: 2px;
}

/* --------------------------------------------------------------------------
   What we already hold

   One line on the go-live screen confirming the NPI carried over from
   sign-up. Deliberately not a progress row: the three credentials are a list,
   not a sequence, and progress chrome promised movement through steps that
   are all on screen at once.
   -------------------------------------------------------------------------- */
.onfile {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: var(--hem-space-2) var(--hem-lede-sm);
  margin-bottom: var(--form-block);
  padding: var(--hem-lede-sm) var(--form-block);
  background: var(--hem-teal-100);
  border-radius: var(--hem-radius-pill);
}

.onfile__label {
  font-family: var(--hem-font-ui);
  font-size: 0.68rem;
  text-transform: uppercase;
  letter-spacing: var(--hem-track-label);
  color: var(--hem-teal-900);
}

.onfile__value {
  font-family: var(--hem-font-ui);
  font-weight: 700;
  font-size: var(--hem-size-body);
  color: var(--hem-text-heading);
  /* Ten digits somebody may want to check against a document. */
  font-variant-numeric: tabular-nums;
  letter-spacing: 0.04em;
}

/* --------------------------------------------------------------------------
   Sign in

   A two-field form does not want the full 1072px panel the sign-up flows use;
   at that width the inputs read as a page rather than a task.
   -------------------------------------------------------------------------- */

/* Secondary routes out of the form - password recovery, and the way to a
   profile for someone who does not have one yet. */
.form-aside {
  font-size: var(--hem-size-body);
  color: var(--hem-text-muted);
  text-align: center;
  margin-top: var(--form-block);
}
.form-aside--foot { margin-top: var(--form-block); }
.form-aside a { color: var(--hem-teal); }


/* --------------------------------------------------------------------------
   The masthead on a phone

   Modest trims only. The first field sits around 520px down a 375x812 screen,
   which sounds like a lot until you look: the whole of step one - both fields
   and the Continue button - is above the fold. The space above is a nav, a
   Back link, a heading and a lede, and each of those earns its place. What is
   worth reclaiming is the doubled gap where the masthead's own bottom margin
   meets the panel, not the typography.
   -------------------------------------------------------------------------- */
@media (max-width: 640px) {
  .form-masthead { margin-bottom: var(--form-gap); }
  .form-masthead .t-body-lg { margin-top: var(--hem-lede-sm); }

  /* The page's own top padding sits on top of the masthead's, and the two
     together were most of what pushed the first field down. */
  .form-page { padding-top: var(--form-gap); }
}


/* --------------------------------------------------------------------------
   Sign Out on Go Live

   .nav__signin only appears at 1024px and up, because on the marketing pages
   it folds into the Menu drawer below that. Go Live has no drawer and is only
   reachable by a practice that is already signed in, so the control has to be
   in the bar at every width - a signed-in page with no way out is the same
   fault the dashboards had.

   Scoped to Go Live alone now. It used to catch every .form-page, which is
   also the sign-up pages - and those no longer carry a Sign Out or a text
   Sign In at all. They carry the same header pill as the landing page.
   -------------------------------------------------------------------------- */
.form-page .nav__signin[data-signout],
body:has(.form-page) .nav__signin[data-signout] { display: inline-flex; }

/* On a form page, Back takes the slot "How It Works" used to hold.

   That link only appeared at 1024px and up, so a desktop visitor mid-sign-up
   got an invitation to leave that a phone visitor never saw - and it pointed
   at the same landing page Back does. One way out, not two.

   Back moves into column one rather than the bar collapsing to two columns,
   because the wordmark stays centred on desktop. The three-column grid is
   what centres it: with the control on the right and nothing on the left, the
   mark would drift off centre.

   grid-row: 1 on both is doing real work. Auto-placement walks forward, so
   sending .nav__actions back to column one - when it comes AFTER the brand in
   source order - made the grid open a second row and the button fell out of
   the pill entirely. Naming the row pins them side by side. */
@media (min-width: 1024px) {
  body:has(.form-page) .nav__links   { display: none; }
  body:has(.form-page) .nav__actions { grid-column: 1; grid-row: 1; justify-self: start; }
  body:has(.form-page) .nav__brand   { grid-column: 2; grid-row: 1; justify-self: center; }
}

/* The form pages used to restyle the whole bar here: a three-column grid with
   the wordmark centred, and a 120px wordmark below 480px. That existed
   because these pages had a bare text link on the right and no Menu toggle,
   so the marketing bar's two-column layout left the wordmark stranded.

   Removed. The sign-up and sign-in pages now use the same header component as
   the landing page - same pill, same two-column layout, same 150px wordmark
   anchored left - so any override here is just a second header pretending to
   be the first. styles.css owns the bar; nothing about being a form page
   changes what the header is. */

/* A combobox switched off by another control (the self-pay checkbox on the
   patient sign-up). Dimmed rather than hidden: the search staying visible is
   what shows the person WHY they no longer need it. */
.cb.is-disabled,
[data-multiselect].is-disabled {
  opacity: 0.5;
}
[data-multiselect].is-disabled .cb__input {
  cursor: not-allowed;
  background: var(--hem-surface-raised);
}

/* The divider between the plan search and the self-pay opt-out. It marks the
   choice between the two controls rather than describing either, so it takes
   more room than a hint. Centring comes from .field__hint. */
#payer-or {
  margin-block: var(--hem-space-3);
}

/* --------------------------------------------------------------------------
   Wide screens

   Hints stay centred at every width now. They were briefly left-aligned here,
   which was the right call while the card was one wide column and a centred
   hint drifted hundreds of pixels from the field it described. The two-column
   layout removed that problem: each field fills its own column again, which
   is the same condition that makes centring work on a phone.
   -------------------------------------------------------------------------- */
@media (min-width: 960px) {
  /* A little more air between fields on a wide card.

     Redefining the token rather than setting margins: --form-gap is what the
     fields, the fieldset hints and the action row all measure from, so they
     move together and nothing drifts out of step with the rest.

     Half a unit, not a whole one. Under 40px the grid tolerates a half step
     (see the S1 note in styles.css), and a full unit here read as a gap
     between unrelated things rather than as breathing room in one list. */
  .form-page { --form-gap: calc(var(--hem-unit) * 1.5); }


  /* Postal code and Insurance are a .field--pair in the markup now, so the
     grid gives them half a column each. The max-width that used to do it by
     hand is gone - inside the pair it would have halved them again. */
  /* The divider between the plan search and Self Pay still marks the choice
     between two controls rather than describing either, so it stays centred. */
  .form-page #payer-or { text-align: center; }
}

/* The two ways of answering Insurance: search a plan, or say you have none.

   Stacked on a phone with the divider between them; side by side on a wide
   card, where the search no longer needs the whole width and the opt-out
   reads better as the alternative sitting beside it than as something further
   down the page.

   align-items: center so the divider and the checkbox sit on the search box's
   axis rather than at the top of a taller cell. */
.payer-choice {
  display: grid;
  gap: var(--hem-space-2);
}

/* Tightened on a wide card so the two columns end level.

   The right column carries three things under its label where the left
   carries two, so its closing hint sat 22px below the left one and the card
   ended on a ragged edge. Taking the air out from around the divider and the
   checkbox - rather than padding the left column to match - keeps the two
   answers reading as one tight group and brings the baselines together.

   Only above 960px. On a phone the columns are stacked, nothing is beside
   anything, and the divider needs its breathing room to separate the two
   answers. */
@media (min-width: 960px) {
  /* Same rhythm as a .field's own gap, so the right column steps down the
     page at the left column's pace. */
  .payer-choice { gap: var(--hem-space-2); }

  /* Only the FIRST gap is widened, by adding it to the divider's top margin
     rather than to the grid's gap - a bigger gap would push each row down
     cumulatively and the three pairs would drift apart again.

     10px is measured, not derived: it is what remains between this column and
     the one beside it once the combobox stopped reserving space for its empty
     status line. If either column's content changes, re-measure it. */
  .form-page #payer-or { margin-block: 10px 0; }

  /* The divider and the checkbox take the box heights of the two things they
     sit beside - the Display Name label and its preview. Their text is
     shorter, so without this they drift a few pixels out of line and the two
     columns stop reading as rows. Set as a minimum, not a height: if the copy
     ever grows, the row grows with it rather than clipping. */
  .payer-choice #payer-or {
    min-height: 31px;
    display: grid;
    place-items: center;
  }
  .payer-choice .option--centred { min-height: 48px; align-items: center; }
}
/* .payer-choice stays stacked at every width now. It briefly went two-up on
   desktop, which worked while the field spanned the whole card; inside a
   half-width column there is no room for a search box and a checkbox side by
   side, and the divider between them is doing real work again. */

/* --------------------------------------------------------------------------
   Two columns on a wide card

   Paired rows put each field beside an unrelated one - a postal code next to
   a name preview - so the step read across before it read down. Columns keep
   what belongs together in one place: who the person is on the left,
   how to reach and pay them on the right.

   align-items: start so a short column does not stretch its fields to match a
   taller neighbour. One column below 960px, in source order, which is the
   order a phone already had.
   -------------------------------------------------------------------------- */
.form-cols {
  display: grid;
  grid-template-columns: 1fr;

  /* One unit between the columns, which is the row gap once they stack.
     Without any gap the last field of one column sat flush against the first
     label of the next - its own bottom margin having been zeroed.

     A unit rather than a block: stacked, these are consecutive sections of one
     short step, and a phone has no width to spend on separation it does not
     need. The desktop rule below takes the wider block spacing back. */
  gap: var(--hem-unit);
}

/* The last field in a column drops its bottom margin, exactly as
   .field--pair > .field does. Without this the column carried a trailing
   25.5px that the fieldset then added its own gap on top of, so step 2 sat
   26px further from Continue than step 1 - the same form, two spacings. */
.form-col > .field:last-child { margin-bottom: 0; }

/* ...but the columns still need separating from whatever follows them.

   Zeroing the trailing margin above is right when .form-cols ends the step,
   which is what step 2 does. Step 3 puts a free-text field after the columns,
   and there the same rule left the two touching with no gap at all.

   A block's worth, not a field's: what follows the columns is a different
   kind of question, not the next item in the same list. And :last-child keeps
   step 2 exactly as it was - no margin when nothing follows. */
.form-cols { margin-bottom: var(--hem-unit); }
.form-cols:last-child { margin-bottom: 0; }
@media (min-width: 960px) {
  /* Side by side there is room to breathe, so the group takes a full block
     from whatever follows it. */
  .form-cols { margin-bottom: var(--form-block); }
  .form-cols:last-child { margin-bottom: 0; }
}
@media (min-width: 960px) {
  .form-cols {
    grid-template-columns: 1fr 1fr;
    gap: var(--form-block);
    align-items: start;
  }
}
