﻿/* ==========================================================================
   AgelessRx brand tokens (ARX-5452)

   Copied 2026-09-17 from arx-ui, which is the source of truth:
     Web/arx-ui/src/styles/tokens/colors.css
     Web/arx-ui/src/styles/theme/theme.css

   Copied rather than imported on purpose. arx-ui's theme.css is wrapped in
   Tailwind's @theme at-rule, so browsers ignore it, and this project has no
   node toolchain to resolve it with. This app is short lived, so a copy is
   the cheaper correct answer.
   ========================================================================== */

:root {
    /* scale */
    --arx-teal-50: #d8e5e3;
    --arx-teal-200: #a8bebc;
    --arx-teal-400: #6b9793;
    --arx-teal-500: #4a807b;
    --arx-teal-600: #386b66;
    --arx-teal-700: #1f524d;
    --arx-teal-800: #223533;
    --arx-gray-50: #e3e5e5;
    --arx-gray-100: #ced1d2;
    --arx-gray-200: #b5bbbc;
    --arx-gray-400: #848d8f;
    --arx-gray-600: #535f62;
    --arx-lime-50: #e7ffb2;
    --arx-lime-200: #c6fa5a;
    --arx-gray-800: #223235;
    --arx-gray-900: #091b1f;

    /* brand */
    --arx-forest-teal: var(--arx-teal-700);
    --arx-lime: var(--arx-lime-200);
    --arx-natural: #fafaf8;
    --arx-white: #ffffff;
    --arx-white-60: rgba(255, 255, 255, 0.6); /* text-white/60 on the marketing footer */

    /* semantic */
    --arx-surface-brand: var(--arx-forest-teal);
    --arx-surface-soft: var(--arx-teal-50);
    --arx-surface-subtle: var(--arx-natural);
    --arx-text: var(--arx-gray-800);
    --arx-heading: var(--arx-gray-900);
    --arx-link: var(--arx-teal-600);
    --arx-link-hover: var(--arx-teal-700);

    /* Card. --color-fill-button-default-secondary is
       color-mix(in srgb, var(--color-teal-500) 10%, transparent), resolved here
       to its rgba equivalent for the same reason the sizes are px. */
    --arx-fill-button-secondary: rgba(74, 128, 123, 0.1);
    --arx-card-border: var(--arx-gray-50);
    --arx-shadow-color: rgba(9, 27, 31, 0.05);
    --arx-shadow-sm: 0 0 1px 0 var(--arx-shadow-color), 0 1px 4px 1px var(--arx-shadow-color);

    /* Button. Disabled fill and focus ring are color-mix expressions in the
       design system, resolved here to rgba. */
    --arx-fill-button-disabled: rgba(9, 27, 31, 0.05);
    --arx-focus-inner: var(--arx-gray-900);
    --arx-focus-outer: rgba(9, 27, 31, 0.1);

    /* type */
    --arx-font-headings: "Fustat", "Helvetica Neue", Helvetica, Arial, sans-serif;
    --arx-font-body: "Instrument Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;

    /* black, used as the hero surface the same way the marketing site does */
    --arx-black: var(--arx-gray-900);

    /* Sizes below are px, not rem, deliberately. bootstrap.css line 1081 sets
       `html { font-size: 10px }`, while arx-ui's values assume Tailwind's 16px
       root, so ported rem values render at 62.5% of intent here. 3.5rem came
       out as 35px instead of 56px and the hero's 5rem padding as 50px instead
       of 80px. px is immune to that, and these are fixed design values anyway. */

    /* layout, from arx-ui tokens/spacing.css and tokens/max-widths.css */
    --arx-blade-y-small: 40px;   /* spacing-10 */
    --arx-blade-y: 80px;           /* 80px, spacing-20 */
    --arx-container-max: 1488px;   /* max-w-8xl */
    --arx-container-max-medium: 1280px;
    --arx-container-max-narrow: 448px;
    --arx-container-max-form-narrow: 512px;
    --arx-container-pad-base: 16px;   /* 16px */
    --arx-container-pad-sm: 32px;     /* 32px */
    --arx-container-pad-md: 40px;   /* 40px */
    --arx-container-pad-lg: 80px;     /* 80px */

    /* display type, from arx-ui tokens/typography.css */
    --arx-tracking-display-mobile: -0.0125em;
    --arx-tracking-display: -0.01875em;
    --arx-display-xl-mobile: 40px;  /* 40px */
    --arx-display-xl: 80px;           /* 80px */
    --arx-display-lg-mobile: 32px;    /* 32px */
    --arx-display-lg: 64px;           /* 64px */
    --arx-display-md-mobile: 30px; /* 30px */
    --arx-display-md: 56px;         /* 56px */
}

/* ==========================================================================
   arx-ui layout primitives (ARX-5452)

   Faithful ports of arx-ui/src/styles/layout/blade.css and container.css,
   with the token references resolved to literals because arx-ui's theme.css
   is Tailwind-only. Class names kept identical to arx-ui so this markup
   transfers directly when the app is rebuilt as a React app.
   ========================================================================== */

.layout-page-blade {
    width: 100%;
    padding-block: var(--arx-blade-y-small);
}

/* Background images: add a .layout-blade-background-image child holding an
   <img>. The blade picks up position: relative automatically. */
.layout-page-blade:has(.layout-blade-background-image) {
    position: relative;
}

.layout-blade-background-image {
    position: absolute;
    top: 0;
    left: 0;
    width: 100%;
    height: 100%;
    overflow: hidden;
    background-size: cover;
    background-position: center;
}

/* On the WordPress side the <img> gets its cover behaviour from Tailwind
   utilities on the element (object-cover w-full h-full). There is no Tailwind
   here, so the same thing is stated directly. Without this the image renders
   at its intrinsic size instead of filling the blade. */
.layout-blade-background-image img {
    width: 100%;
    height: 100%;
    object-fit: cover;
    object-position: center;
}

/* Content has to stack above the background image. WordPress puts a `relative`
   utility on the container; same thing, stated rather than composed. */
.layout-page-blade > .layout-container {
    position: relative;
}

/* Blade padding utilities, ported from the WordPress copy of blade.css. Each
   blade contributes half the design gap, so two stacked blades with different
   backgrounds read as half the intended separation. These double it. The
   marketing hero uses blade-p-2x, which is the knob for a taller hero. */
.layout-page-blade.blade-p-2x { padding-block: 80px; }
.layout-page-blade.blade-p-2x-top { padding-top: 80px; }
.layout-page-blade.blade-p-2x-bottom { padding-bottom: 80px; }
.layout-page-blade.blade-p-0 { padding-block: 0; }
.layout-page-blade.blade-p-0-top { padding-top: 0; }
.layout-page-blade.blade-p-0-bottom { padding-bottom: 0; }

/* Half. Not in the WordPress set, which ships only zero and double; added here
   because the blade sitting directly under the hero reads as too far from it at
   the full amount. Half of --arx-blade-y-small at base, half of --arx-blade-y at
   768. Only the -top variant exists because only it has a use. Raised as a
   punch-list item for arx-ui, whose blade.css has no padding utilities at all. */
.layout-page-blade.blade-p-half-top { padding-top: 20px; }

.layout-container {
    width: 100%;
    max-width: var(--arx-container-max);
    margin-inline: auto;
    padding-inline: var(--arx-container-pad-base);
}

.layout-container--medium {
    max-width: var(--arx-container-max-medium);
}

.layout-container--narrow {
    max-width: var(--arx-container-max-narrow);
}

.layout-container-form-narrow {
    width: 100%;
    max-width: var(--arx-container-max-form-narrow);
    margin-inline: auto;
    padding-inline: var(--arx-container-pad-base);
}

@media (min-width: 640px) {
    .layout-container {
        padding-inline: var(--arx-container-pad-sm);
    }
}

@media (min-width: 768px) {
    .layout-page-blade {
        padding-block: var(--arx-blade-y);
    }

    .layout-page-blade.blade-p-2x { padding-block: 160px; }
    .layout-page-blade.blade-p-2x-top { padding-top: 160px; }
    .layout-page-blade.blade-p-2x-bottom { padding-bottom: 160px; }
    .layout-page-blade.blade-p-half-top { padding-top: 40px; }

    .layout-container {
        padding-inline: var(--arx-container-pad-md);
    }

    .layout-container-form-narrow {
        padding-inline: 0;
    }
}

@media (min-width: 1024px) {
    .layout-container {
        padding-inline: var(--arx-container-pad-lg);
    }
}

/* ==========================================================================
   Page header and hero

   Replaces the Bootstrap .jumbotron that both pages used as a title band.
   The hero mirrors arxui-simple-hero on the marketing site: full-bleed
   section on brand black with a centered display heading. The marketing
   version also carries min-height 480px and doubled blade padding; both are
   omitted here because this is a utility page where the form should not be
   pushed off the first screen, especially on mobile.
   ========================================================================== */

/* Sticky, matching the marketing site's header, which uses `sticky top-0 z-40`.
   The hairline bottom border stands in for the JS-driven scrolled state on the
   WordPress nav: without it an opaque white header dissolves into the white
   form area once you scroll past the hero. */
.arx-site-header {
    position: sticky;
    top: 0;
    z-index: 40;
    background-color: var(--arx-white);
    padding-block: 16px;
    border-bottom: 1px solid var(--arx-teal-50);
}

.arx-site-header img {
    display: block;
    height: 28px;
    width: auto;
}

/* Footer: same construction as the hero, an edge-to-edge blade on brand black
   with a container inside. Replaces the Bootstrap .jumbotron bar that both
   views carried, along with the &nbsp; runs it used for spacing. */
.arx-site-footer {
    background-color: var(--arx-black);
    color: var(--arx-white);
}

/* Two stacked rows. The marketing footer uses gap-8 / lg:gap-10, but it has far
   more in it; 24px suits two rows. */
.arx-site-footer-inner {
    display: flex;
    flex-direction: column;
    gap: 24px;
}

.arx-site-footer-row {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 24px;
}

/* The label and its links as one wrapping unit. */
.arx-site-footer-links {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 24px;
}

/* The marketing footer renders the wordmark at h-10 lg:h-12. */
.arx-site-footer img {
    display: block;
    height: 40px;
    width: auto;
}

/* Extra separation between the wordmark and the links, s-10 in arx-ui terms.
   Sits on top of the row's 24px gap. The logo is the first child by
   construction. */
.arx-site-footer-row > a:first-child {
    margin-right: 40px;
}

/* Disclaimer, matching the marketing footer's `text-xs leading-4
   text-white/60`, with its links `no-underline hover:underline`. */
.arx-site-footer-disclaimer {
    margin: 0;
    max-width: 72ch;
    font-size: 12px;
    line-height: 16px;
    color: var(--arx-white-60);
}

/* The generic footer link rules come first deliberately. These and the
   disclaimer rules below are both (0,1,1), so specificity does not separate
   them and source order is the whole mechanism. With the generic pair last,
   the disclaimer's links rendered --arx-white and went lime on hover. */
.arx-site-footer a {
    color: var(--arx-white);
}

.arx-site-footer a:hover,
.arx-site-footer a:focus {
    color: var(--arx-lime);
}

.arx-site-footer-disclaimer a {
    color: var(--arx-white-60);
    text-decoration: none;
}

.arx-site-footer-disclaimer a:hover,
.arx-site-footer-disclaimer a:focus {
    color: var(--arx-white-60);
    text-decoration: underline;
}

@media (min-width: 1024px) {
    .arx-site-footer img {
        height: 48px;
    }
}

/* min-height needs the flex centring alongside it, otherwise the extra height
   all lands below the title and reads as stray bottom padding. 300 / 500 is
   close to the marketing hero's 480 / 552. */
.arx-hero {
    /* Stated rather than relying on the :has() rule above, which is the only
       thing that makes a blade a positioning context. Without :has() support
       the background image would not degrade, it would position against the
       initial containing block and cover the page. Baseline 2023, so this is
       insurance against an old engine rather than a live bug. */
    position: relative;
    background-color: var(--arx-black);
    color: var(--arx-white);
    overflow: hidden;
    min-height: 300px;
    display: flex;
    flex-direction: column;
    justify-content: center;
}

@media (min-width: 768px) {
    .arx-hero {
        min-height: 500px;
    }
}

/* The live hero constrains its content to an 880px centred column inside the
   container, not to the container's full width. Without this the title sprawls
   the whole viewport on a wide screen. The marketing version caps a
   sub-headline at 640px inside the same column if one is ever added here. */
.arx-hero-content {
    max-width: 880px;
    margin-inline: auto;
    text-align: center;
}

.arx-hero h1 {
    color: var(--arx-white);
    margin: 0;
}

/* Second line of the hero title. The marketing hero separates its h1 from a
   sub-headline with gap-6 / gap-10 (24px / 40px), but that is for a full
   supporting paragraph. This is a qualifier on the title itself, so the gap is
   tighter. One value to change if you want the marketing spacing. */
.arx-hero-subtitle {
    display: block;
    margin-top: 16px;
}

@media (min-width: 768px) {
    .arx-hero-subtitle {
        margin-top: 24px;
    }
}

/* Display heading scale, ported from arx-ui typography.css. Swap the class on
   the hero h1 to resize: xl is 40/80px, lg is 32/64px, md is 30/56px. */
.text-display-heading-xl,
.text-display-heading-lg,
.text-display-heading-md {
    font-family: var(--arx-font-headings);
    font-weight: 400;
    letter-spacing: var(--arx-tracking-display-mobile);
}

.text-display-heading-xl {
    font-size: var(--arx-display-xl-mobile);
    line-height: var(--arx-display-xl-mobile);
}

.text-display-heading-lg {
    font-size: var(--arx-display-lg-mobile);
    line-height: var(--arx-display-lg-mobile);
}

.text-display-heading-md {
    font-size: var(--arx-display-md-mobile);
    line-height: var(--arx-display-md-mobile);
}

@media (min-width: 768px) {
    .text-display-heading-xl,
    .text-display-heading-lg,
    .text-display-heading-md {
        letter-spacing: var(--arx-tracking-display);
    }

    .text-display-heading-xl {
        font-size: var(--arx-display-xl);
        line-height: var(--arx-display-xl);
    }

    .text-display-heading-lg {
        font-size: var(--arx-display-lg);
        line-height: var(--arx-display-lg);
    }

    .text-display-heading-md {
        font-size: var(--arx-display-md);
        line-height: var(--arx-display-md);
    }
}

body {
    font-family: var(--arx-font-body);

    /* Design system base is text-body-md, 16px on a 20px line. Bootstrap ships
       14px / 1.42857143. Expressed unitless so nested elements that do not set
       their own line-height scale with their own size rather than inheriting a
       fixed 20px. */
    font-size: 16px;
    line-height: 1.25;

    color: var(--arx-text);
    background-color: var(--arx-white);
}

h1, h2, h3, h4, h5, h6,
.h1, .h2, .h3, .h4, .h5, .h6 {
    font-family: var(--arx-font-headings);
    color: var(--arx-heading);
}

/* Bootstrap pins these at 14px so they never inherit the base size. Bring them
   up to the design system's 16px. .form-control at 16px also stops iOS Safari
   zooming the page on focus, which is the whole reason arx-ui has a separate
   text-ui-input-lg. Note this also beats .btn-lg, which is the same specificity
   and loads earlier, so the submit button is 16px rather than Bootstrap's 18. */
.form-control,
.input-group-addon,
.btn {
    font-size: 16px;
}

a {
    color: var(--arx-link);
}

a:hover,
a:focus {
    color: var(--arx-link-hover);
}


/* ==========================================================================
   Button (ARX-5452)

   Ported from arx-ui components/ui/button.css: the base plus the primary
   variant at the default size, which the design system treats as large. The
   base is written with @apply there, so its Tailwind utilities are resolved
   here: inline-flex, items-center, justify-center, gap-2, rounded-full, px-8,
   py-3, text-base, font-medium, whitespace-nowrap.

   These deliberately override Bootstrap's own .btn, which sets inline-block,
   6px/12px padding, a 4px radius, a 1px border and font-weight 400. Site.css
   loads after bootstrap.css, so equal specificity resolves our way. Note the
   design system button is a pill, which is a visible change from Bootstrap's
   slightly rounded rectangle.
   ========================================================================== */

.btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: 8px;
    border: none;
    border-radius: 9999px;
    padding: 12px 32px;
    font-size: 16px;
    line-height: 24px;
    font-weight: 500;
    white-space: nowrap;
    cursor: pointer;
    transition: all 150ms ease;
    outline: none;
}

.btn:focus-visible {
    box-shadow:
        0 0 0 0.5px var(--arx-focus-inner),
        0 0 0 3px var(--arx-focus-outer);
}

.btn:disabled {
    pointer-events: none;
    cursor: not-allowed;
}

.btn-primary {
    background-color: var(--arx-forest-teal);
    color: var(--arx-white);
}

.btn-primary:hover,
.btn-primary:focus {
    background-color: var(--arx-teal-800);
    color: var(--arx-white);
}

/* The submit button starts disabled until the consent box is ticked, so this
   state is on screen from page load. */
.btn-primary:disabled {
    background-color: var(--arx-fill-button-disabled);
    color: var(--arx-gray-400);
}

/* Tertiary, ported from arx-ui button.css:532. A text button: no fill, link
   colour, and the base pill geometry replaced. The source writes its geometry
   as `@apply gap-1 rounded-md p-0.5`, which resolves to 4px, 6px and 2px.

   Tokens resolved:
     --color-fill-button-default-tertiary   transparent
     --color-button-default-tertiary        text-link-default  = teal-600
     --color-button-default-tertiary-hover  text-link-hover    = teal-700
     --color-button-default-disabled        gray-400
   Focus is the ring from .btn:focus-visible and nothing else, per the QA V2
   note in the source: this variant takes no background on hover or focus. */
.btn-tertiary {
    background-color: transparent;
    color: var(--arx-link);
    gap: 4px;
    border-radius: 6px;
    padding: 2px;
}

/* Bootstrap's `.btn:hover, .btn:focus, .btn.focus { color: #333 }` is two
   classes, so restating focus at the same specificity is what keeps the label
   from going grey. :focus comes first so :hover wins the tie when both apply. */
.btn-tertiary:focus,
.btn-tertiary:focus-visible {
    background-color: transparent;
    color: var(--arx-link);
}

.btn-tertiary:hover {
    background-color: transparent;
    color: var(--arx-link-hover);
}

.btn-tertiary:disabled {
    background-color: transparent;
    color: var(--arx-gray-400);
}

/* Mirrors the `w-full md:w-auto` the marketing site puts on its CTAs: full
   width for a comfortable tap target on mobile, intrinsic width on desktop. */
.arx-btn-block {
    width: 100%;
}

@media (min-width: 768px) {
    .arx-btn-block {
        width: auto;
    }
}

/* ==========================================================================
   Card (ARX-5452)

   Base shell ported from arx-ui components/ui/card.css: the card, its header,
   content and title, with their padding and gaps. The variants, glass
   modifiers and product/citation/research layouts are not needed here.

   One deviation from the design system: the fill is
   --color-fill-button-default-secondary rather than the card default of white,
   so the aside reads as a tinted panel beside the form.
   ========================================================================== */

.card {
    display: flex;
    flex-direction: column;
    background-color: var(--arx-fill-button-secondary);
    color: var(--arx-text);
    border: 1px solid var(--arx-card-border);
    border-radius: 16px;
    box-shadow: var(--arx-shadow-sm);
    overflow: clip;
    width: 100%;
}

.card-header {
    display: flex;
    flex-direction: column;
    gap: 6px;
    padding: 24px;
}

/* Mobile-first, matching the design system: small padding by default, growing
   to the default size at 640px. */
.card-content {
    display: flex;
    flex-direction: column;
    gap: 6px;
    padding: 16px;
}

.card-header + .card-content {
    padding-top: 0;
}

.card-title {
    margin: 0;
    line-height: 1;
    font-weight: 600;
}

/* Card image, ported verbatim from arx-ui card.css:127. Three declarations and
   no variant: a direct child of .card is full bleed because .card is padded
   nowhere and clips its overflow. */
.card-image {
    width: 100%;
    overflow: clip;
}

.card-image img {
    width: 100%;
    height: 100%;
    object-fit: cover;
}

@media (min-width: 640px) {
    .card-content {
        padding: 24px;
    }
}

/* Local deviation from the ported card, scoped to the aside so the design
   system component itself stays faithful: roomier horizontal padding, plus a
   minimum height on desktop so the card holds its own beside the tall form.
   Not on mobile, where it is just empty space above the safety information. */
@media (min-width: 1024px) {
    .arx-col-side .card {
        min-height: 300px;
    }
}

/* The design system puts 24px on the header's bottom and then zeroes the
   content's top via `.card-header + .card-content`, so that 24px was the whole
   gap between the title and the links. Dropped to 16px, set on the content so
   the two boxes are not both contributing. */
.arx-col-side .card-header {
    padding: 24px 32px 0;
}

.arx-col-side .card-header + .card-content {
    padding: 16px 32px 24px;
}

/* Icon beside a card title */
.arx-card-title-icon {
    display: flex;
    align-items: center;
    gap: 12px;
}

.arx-card-title-icon img {
    width: 32px;
    height: auto;
    flex: none;
}

/* Link list inside a card. Replaces inline list-style and padding styles. */
.arx-card-links {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 12px;
}

/* ==========================================================================
   Form fields (ARX-5452)

   Replaces four nested Bootstrap grid divs per field with a single wrapper.
   Ported from arx-ui form-input-wrapper, which is `flex w-full flex-col gap-2`,
   and label.css, which is flex with an 8px gap so the tooltip trigger sits
   beside the label text.

   The unit suffix has no design system equivalent: arx-ui's InputGroup is
   React-only and there is no input-group.css. It is a span positioned inside
   the right edge of the input, which keeps the unit next to where the number is
   typed. On a calculator where mg/dL instead of g/dL silently yields a wrong
   biological age, that proximity is worth the few lines.
   ========================================================================== */

.form-input-wrapper {
    display: flex;
    width: 100%;
    flex-direction: column;
    gap: 8px;
}

/* The form's page heading. h1 is the hero, so this is the h2. */
.arx-col-main h2 {
    margin: 0 0 24px;
}

/* Vertical rhythm between fields. Bootstrap's .form-row supplied this with a
   15px bottom margin; a flex column with a gap replaces it. */
.arx-field-stack {
    display: flex;
    flex-direction: column;
    gap: 20px;
}

/* The email, consent and submit stack sits after the field stack. Matches the
   in-stack rhythm rather than butting against it. */
.arx-field-stack + .arx-field-stack {
    margin-top: 20px;
}

/* Wrapper for the label plus its tooltip trigger. arx-ui puts the gap on
   .label itself, but Html.LabelFor cannot take child content. */
.arx-field-label {
    display: flex;
    align-items: center;
    gap: 8px;
}

/* Ported from arx-ui label.css.

   This has to reset a lot, because .label is a genuine collision: in Bootstrap
   3 .label is a BADGE component (inline, 75% size, bold, white text on a
   coloured background), which is why the labels were rendering white. In arx-ui
   .label is a form label. Every Bootstrap property has to be overridden
   explicitly, not just the ones we want to change. */
.label {
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 0;
    margin: 0;
    font-family: var(--arx-font-body);
    font-size: 14px;
    font-weight: 500;
    line-height: 20px;
    letter-spacing: 0;
    color: var(--arx-text);
    background-color: transparent;
    border-radius: 0;
    text-align: left;
    white-space: normal;
    vertical-align: baseline;
    user-select: none;
}

/* Input, ported from arx-ui form-input.css at the lg size, which is the
   consumer-facing one: 48px tall with 16px text, and the 16px specifically
   stops iOS Safari zooming the page on focus.

   The border is an inset box-shadow rather than a real border. That is the
   design system's convention, and it exists because Figma draws form strokes
   centre-aligned, which has no CSS equivalent: a real border would add width
   inside the box and shift the layout. */
.form-control {
    width: 100%;

    /* Bootstrap pins .form-control to height: 34px, which clips the 48px the
       design system's lg size wants. */
    height: auto;

    padding: 12px 12px;
    border: none;
    border-radius: 8px;
    font-family: var(--arx-font-body);
    font-size: 16px;
    font-weight: 400;
    line-height: 24px;
    letter-spacing: 0;
    background-color: var(--arx-white);
    box-shadow: inset 0 0 0 1px var(--arx-gray-100);
    color: var(--arx-text);
    transition: all 150ms ease;
    outline: none;
}

.form-control::placeholder {
    color: var(--arx-gray-600);
}

.form-control:hover:not(:disabled):not(:focus) {
    box-shadow: inset 0 0 0 1px var(--arx-gray-200);
}

.form-control:focus {
    box-shadow:
        inset 0 0 0 1px var(--arx-gray-200),
        0 0 0 0.5px var(--arx-focus-inner),
        0 0 0 3px var(--arx-focus-outer);
}

.arx-field-control {
    position: relative;
}

/* Padding sized for the longest unit, cells/mL, so every input clears its
   suffix. Uniform across fields so the values line up. */
.arx-field-control .form-control {
    padding-right: 80px;
}

.arx-field-unit {
    position: absolute;
    top: 50%;
    right: 12px;
    transform: translateY(-50%);
    pointer-events: none;
    color: var(--arx-gray-400);
    font-size: 14px;
    line-height: 20px;
}

/* ==========================================================================
   Results page (ARX-5452)
   ========================================================================== */

/* Section heading with an action opposite it, e.g. Values entered + Edit */
.arx-result-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 16px;
    border-bottom: 1px solid var(--arx-card-border);
    margin-bottom: 16px;
}

.arx-result-header > h2 {
    margin-bottom: 6px;
}

/* The results card is the Learn more card plus an image half: same .card
   chrome, same .card-header and .card-content, same fill. The old
   --arx-surface-soft override is gone, and so are .arx-result-cols and
   .arx-result-values, which existed only to sit the values beside an inset
   image inside the padded content.

   A container query, not a media query, so the card stacks when the card is
   narrow whatever the page layout is doing. Page columns collapse at 1024px,
   which would leave a viewport query with a side-by-side card in a 400-500px
   column through the 1024-1280 window. First container query in this repo.

   The container is the column, not the card. An element is not its own query
   container, so container-type on .arx-result-panel let the image rules inside
   the block fire while the card's own flex-direction silently did not. The card
   is width: 100% of the column, so the two measure the same thing. */
.arx-result-columns .arx-col-side {
    container-type: inline-size;
}

/* Header and content wrapped so the card has exactly two things to lay out in a
   row: this stack, and the image. Without it the image becomes a third column. */
.arx-result-panel-body {
    display: flex;
    flex-direction: column;
    flex: 1 1 auto;
    min-width: 0;
}

/* Full bleed. A direct child of .card, so .card's overflow: clip crops it to
   the 16px corner radius for free. Narrow, the image sits at the bottom by
   document order and needs a stated height, because a percentage height has
   nothing to resolve against in an auto-height column. */
.arx-result-card-image {
    flex: none;
    height: 200px;
}

@container (min-width: 560px) {
    .arx-result-panel {
        flex-direction: row;
    }

    .arx-result-card-image {
        flex: 0 0 42%;
        height: auto;
        align-self: stretch;
    }
}

.arx-result-list {
    display: flex;
    flex-direction: column;
    gap: 12px;
    margin: 0;
    margin-bottom: 1rem;
    padding-bottom: 16px;
    border-bottom: 1px solid var(--arx-card-border);
}

.arx-result-list dd {
    text-align: right;
    width: 64px;
}

.arx-results-description{
 display: flex;
    flex-direction: column;

}

.arx-result-row {
    display: flex;
    gap: 16px;
}

.arx-result-row dt {
    flex: 0 0 160px;
}

.arx-result-row dd {
    margin: 0;
    font-weight: 600;
}

/* PDF download link. The class was already in the markup with nothing matching
   it; this is its first rule. The <img> is an inline sibling of the label text
   inside the <h2>, so it rides the text baseline and a height change drags the
   whole line box down. Flex takes it off the baseline and centres it instead. */
.arx-pdf-download h2 {
    display: flex;
    align-items: center;
    gap: 12px;
}

.arx-pdf-download img {
    height: 48px;
    width: auto;
    flex: none;
    transition: all 0.25s;
}


.arx-pdf-download:hover h2 {
    text-decoration: underline;
    width: fit-content;
}

.arx-pdf-download:hover img {
    transform: scale(1.2);
}

/* ==========================================================================
   Two column page layout (ARX-5452)

   Replaces Bootstrap's col-md-7 / col-md-5 pair for the page body. Single
   column on mobile, so document order decides the stack: form, then the learn
   more card, then the safety information blade below. On desktop the form takes
   the main column and the card sits beside it.
   ========================================================================== */

/* A blade holding several stacked containers. A flex column with a gap spaces
   them evenly, rather than each container carrying its own margin. Used so the
   instructions, the form and card, and the safety information can share one
   blade: two blades put 80px of padding on each side of the boundary, which was
   far more separation than it needed. */
.arx-page-sections {
    display: flex;
    flex-direction: column;
    gap: 40px;
}

.layout-container--columns {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 40px;
}

.arx-col-main,
.arx-col-side {
    flex: 1 1 100%;
    min-width: 0;
}

/* Portal note beneath the submit button. s-4 in arx-ui terms. */
.arx-note {
    margin-top: 16px;
}

/* The 600px cap sits on the column's contents, not on the column itself.
   Capping the flex item made flexbox redistribute the leftover to the other
   column, so the card widened and the form stayed pinned to the left edge of
   its slot. Capping the children keeps both slots even.

   Left aligned, not centred: margin-inline: auto was removed on request. */
.arx-col-main > * {
    max-width: 600px;
}

/* The cap above is for the entry form. The results page puts the value table in
   the same column and it should fill it, so the cap is lifted. */
.arx-result-columns .arx-col-main > * {
    max-width: none;
}


/* Switch at 1024, not 768, matching how the marketing site uses lg: for major
   layout changes. At 768 the container leaves only 688px of content, and
   splitting that gave each column under 330px.

   Even split. This supersedes the earlier 500px cap on the form column, which
   would have made the two sides unequal. The gap widens to 64px once the
   columns are genuinely side by side; below this it is the stacking gap. */
@media (min-width: 1024px) {
    .layout-container--columns {
        gap: 64px;

        /* Top-aligned once the columns are side by side. Centring put the card
           667px down a 1633px form, well below the fold, where it is no use to
           anyone filling in the first fields. flex-start rather than the
           default stretch, so the card keeps its 300px height instead of
           growing to match the form. */
        align-items: flex-start;
    }

    .arx-col-main,
    .arx-col-side {
        flex: 1 1 0;
    }
}

/* Override the default bootstrap behavior where horizontal description lists 
   will truncate terms that are too long to fit in the left column 
*/
.dl-horizontal dt {
    white-space: normal;
}

/* Bootstrap's .input-group is `display: table` with no width, so it shrinks to
   fit its content. Needs an explicit width to fill the column. */
.input-group {
    width: 100%;
}

/* Fields fill their column. No max-width anywhere.

   This used to be `input, select, textarea { max-width: 280px }`. Bootstrap's
   .input-group is a table at 100% width and the input is a table-cell at
   width: 100%, so capping the input cell left the table's remaining space
   unallocated and stranded the unit addon at the far right with a gap between
   them, visible between roughly 500px and 767px. Letting the group fill keeps
   the addon attached at every width, because the input cell absorbs whatever
   the addon does not use. */


/* One value table at every width, the two-column label/value one.

   The page used to carry a second table laying the nine biomarkers out three
   pairs to a row, swapped in on wider screens. The two-column results layout
   left it 488px at a 1200px window against a 572px min-content width, so it
   overflowed the column; a container query then held it back until the column
   reached 600px, which at 1440px it cleared by 8px and the labels wrapped to
   three lines anyway. Dropped on request: the label/value table reads better in
   a half column at every width, so the markup and the switch are both gone. */
#mobile {
    display: inline-table;
}

/* #mobile is a two-column label/value table, so the value is always the second
   cell. Replaces eleven Bootstrap .text-right utilities in the markup (ARX-5452). */
#mobile td:last-child {
    text-align: right;
}


/* ==========================================================================
   Moved out of the per-view <style> blocks (ARX-5452)

   Home/Index.cshtml and Result/Index.cshtml each carried an inline <style>
   block, and nine of the rules were identical copies. They now live here once.
   The !important flags are kept as they were so behaviour is unchanged; they
   are mostly unnecessary now that these rules load after bootstrap.css, but
   stripping them is a separate change.
   ========================================================================== */

/* `label { font-weight: unset !important }` used to live here, carried over
   from the views' inline style blocks. It was there to undo Bootstrap's bold
   labels, but !important also beat the ported .label weight, so labels rendered
   at 400 instead of 500. The .label rule handles this properly now. */

.help-block {
    color: red;
    font-style: italic;
}

/* ValidationMessageFor always renders its span, empty when the field is valid,
   and .help-block is a block with margins, so every field carried dead vertical
   space on top of the stack's gap. MVC swaps this class to
   field-validation-error when a message appears, so hiding the valid state
   costs nothing and the error still shows. */
.field-validation-valid {
    display: none;
}

/* Aligned to arx-ui components/ui/tooltip.css: brand black on white text, 8px
   radius, 8px/12px padding, shadow-sm, 256px cap, text-body-sm, and no caret.

   Bootstrap's JS tooltip is kept rather than switching to the design system's
   CSS-only version, because these tooltips contain real markup and
   content: attr(data-tooltip) renders plain text only.

   Bootstrap also fades the bubble to opacity 0.9, which is the transparency
   you were seeing. Set to 1. */
.tooltip.in {
    opacity: 1;
}

.tooltip-inner {
    background-color: var(--arx-black);
    color: var(--arx-white);
    padding: 8px 12px;
    border-radius: 8px;
    box-shadow: var(--arx-shadow-sm);
    max-width: 256px;
    text-align: left;
    font-size: 14px;
    line-height: 20px;
}

/* The design system tooltip has no caret */
.tooltip-arrow {
    display: none;
}

/* The tooltip titles are marked up as <u><b>…</b></u>. The bold reads as the
   heading; the underline just adds noise. Neutralised here rather than editing
   the <u> out of nine title attributes in each view. */
.tooltip-inner u {
    text-decoration: none;
}

.value-table td {
    margin-bottom: 10px;
    padding-bottom: 10px;
}

/* padding-right: the two-column layout halved the width available to this
   table, and without it the label and its value read as one run of text. */
.value-label {
    font-weight: bold;
    padding-right: 12px;
}

/* The tooltip trigger. Sized in px at 16px to sit properly beside a 14px
   label: the 1rem it used to carry resolved to 10px against Bootstrap's 10px
   root. The glyph arrives as a replaced element via content: url(), which does
   not take the pseudo-element's width and height unless it is a block, which is
   why it rendered oversized and low. */
.fa-question-circle-o {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 16px;
    height: 16px;
    flex: none;
}

/* The translateY(2px) that used to be here nudged the glyph down to line up
   with the old side-by-side label layout. The label is a flex row now, so
   align-items handles it and the nudge just pushed it low. */
.fa-question-circle-o:after {
    display: grid;
    place-content: center;
    width: 16px;
    height: 16px;
    content: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='12' fill='currentColor' class='bi bi-question-circle' viewBox='0 0 16 16'%3E%3Cpath d='M8 15A7 7 0 1 1 8 1a7 7 0 0 1 0 14zm0 1A8 8 0 1 0 8 0a8 8 0 0 0 0 16z'/%3E%3Cpath d='M5.255 5.786a.237.237 0 0 0 .241.247h.825c.138 0 .248-.113.266-.25.09-.656.54-1.134 1.342-1.134.686 0 1.314.343 1.314 1.168 0 .635-.374.927-.965 1.371-.673.489-1.206 1.06-1.168 1.987l.003.217a.25.25 0 0 0 .25.246h.811a.25.25 0 0 0 .25-.25v-.105c0-.718.273-.927 1.01-1.486.609-.463 1.244-.977 1.244-2.056 0-1.511-1.276-2.241-2.673-2.241-1.267 0-2.655.59-2.75 2.286zm1.557 5.763c0 .533.425.927 1.01.927.609 0 1.028-.394 1.028-.927 0-.552-.42-.94-1.029-.94-.584 0-1.009.388-1.009.94z'/%3E%3C/svg%3E");
}
/* ==========================================================================
   arx-ui type scale (ARX-5452)

   Ported from arx-ui/src/styles/components/ui/typography.css with token
   references resolved to literals. Class names are identical to arx-ui so
   markup transfers when this app is rebuilt as a React app.

   These classes are ALREADY RESPONSIVE. Never stack md: style overrides on
   them, and never reach for raw font-size where one of these will do.

   text-ui-caption is deliberately omitted: it is Geist Mono, which is not on
   Google Fonts, and this project does not self-host fonts.
   ========================================================================== */

/* Headings: Fustat, weight 600 */

.text-heading-lg,
.text-heading-md,
.text-heading-sm {
    font-family: var(--arx-font-headings);
    font-weight: 600;
    letter-spacing: 0;
}

.text-heading-lg { font-size: 30px; line-height: 40px; }   /* 30 / 40 */
.text-heading-md { font-size: 24px;   line-height: 32px; }     /* 24 / 32 */
.text-heading-sm { font-size: 20px;  line-height: 28px; }  /* 20 / 28 */

@media (min-width: 768px) {
    .text-heading-lg { font-size: 36px;  line-height: 44px; }  /* 36 / 44 */
    .text-heading-md { font-size: 30px; line-height: 40px; }   /* 30 / 40 */
    .text-heading-sm { font-size: 24px;   line-height: 32px; }     /* 24 / 32 */
}

/* Body, links, form text: Instrument Sans. Not responsive in arx-ui either. */

.text-body-lg,
.text-body-lg-strong,
.text-body-md,
.text-body-md-strong,
.text-body-sm,
.text-body-sm-strong,
.text-body-xs,
.text-link-md,
.text-link-sm,
.text-ui-label,
.text-ui-input,
.text-ui-input-lg {
    font-family: var(--arx-font-body);
    letter-spacing: 0;
}

.text-body-lg        { font-size: 18px; line-height: 24px;  font-weight: 400; } /* 18 / 24 */
.text-body-lg-strong { font-size: 18px; line-height: 24px;  font-weight: 600; }
.text-body-md        { font-size: 16px;     line-height: 20px; font-weight: 400; } /* 16 / 20 */
.text-body-md-strong { font-size: 16px;     line-height: 20px; font-weight: 600; }
.text-body-sm        { font-size: 14px; line-height: 20px; font-weight: 400; } /* 14 / 20 */
.text-body-sm-strong { font-size: 14px; line-height: 20px; font-weight: 600; }
.text-body-xs        { font-size: 12px;  line-height: 16px;    font-weight: 400; } /* 12 / 16 */

.text-link-md        { font-size: 16px;     line-height: 20px; font-weight: 500; }
.text-link-sm        { font-size: 14px; line-height: 20px; font-weight: 500; }

/* Subtitles carry tighter tracking than body text */
.text-subtitle-md,
.text-subtitle-lg {
    font-family: var(--arx-font-body);
    font-weight: 400;
    letter-spacing: -0.03125em;
}

.text-subtitle-md { font-size: 18px; line-height: 20px; }  /* 18 / 20 */
.text-subtitle-lg { font-size: 20px; line-height: 24px; }  /* 20 / 24 */

@media (min-width: 768px) {
    .text-subtitle-md { font-size: 20px; line-height: 24px; }
    .text-subtitle-lg { font-size: 24px; line-height: 28px; }
}

.text-ui-label       { font-size: 14px; line-height: 20px; font-weight: 500; } /* 14 / 20 */

/* 14px for compact controls. 16px for consumer-facing controls, which also
   prevents iOS Safari from zooming on focus. Relevant to the mobile form work. */
.text-ui-input       { font-size: 14px; line-height: 24px;  font-weight: 400; }
.text-ui-input-lg    { font-size: 16px;     line-height: 24px;  font-weight: 400; }
