/*
 * Biomarkers overview — wide dashboard hero. Figma R2: Dashboard file
 * VtSQbiEqtuaowkAOQhXmpI, frame biomarkers_overview_use_cases 312:9129.
 *
 * Six states share one black rounded shell:
 *   - active_with_history / active_no_history → .content (data; desktop gets
 *     the animated flow canvas + .maskData, mobile is a flat card with
 *     full-width colour bars — nodes 1870:6366 / 1870:7176)
 *   - panel_processing (recalculating)        → .content + badge (1870:6828)
 *   - panel_processing_first (calculating)    → .heroCopy over the static
 *     flow art (1870:7071 / 1870:7378)
 *   - loading                                 → gradient skeleton blocks
 *     (1870:6902 / 1870:7376)
 *   - upsell                                  → .upsellInner + glass panel
 *     (1865:6633 / 1864:19966)
 *   - error                                   → .heroCopy over the static
 *     flow art (1870:7126 / 1870:7380)
 *
 * Mobile (Figma device=mobile variants, 390px designs) is driven by the
 * card's own measured width: the component sets .cardMobile below its
 * breakpoint. A viewport media query would miss narrow containers on wide
 * screens.
 *
 * The Figma variants layer a backdrop-blur(25px) over the background art on
 * the desktop data states; it is omitted here (same precedent as WelcomeCard)
 * because the live canvas replaces the static art.
 */

.card {
    position: relative;
    box-sizing: border-box;
    display: flex;
    align-items: center;
    width: 100%;
    /* Symbol height as a floor; fills the slot when a composed layout (the
     * dashboard row) sizes the parent — slots share one container height.
     * Standalone, 100% of an auto parent resolves to auto and the floor wins. */
    min-height: 278px;
    height: 100%;
    padding-left: var(--spacing-24);
    overflow: hidden;
    /* Radius/radius-medium — designer bump 12 -> 16 (sasha, 2026-07-14) */
    border-radius: var(--border-radius-md);
    background: var(--color-bg-base-dark);
    color: var(--color-text-primary-inverted);
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
}

/* Mobile shell: content drives the height (per-state Figma heights vary). */
.cardMobile {
    flex-direction: column;
    align-items: stretch;
    height: auto;
    padding: var(--spacing-20);
    border-radius: var(--border-radius-md);
    /* shadow-float (Figma effect token) */
    box-shadow:
        0 20px 25px -5px rgba(0, 0, 0, 0.1),
        0 8px 10px -6px rgba(0, 0, 0, 0.1);
}

/* Clickable data view — drives to the lab overview (sasha, 2026-07-14):
 * shadow-float on hover, mirrors the static mobile elevation. */
.cardClickable {
    cursor: pointer;
    transition: box-shadow 0.3s ease;
}

.cardClickable:hover {
    box-shadow:
        0 20px 25px -5px rgba(0, 0, 0, 0.1),
        0 8px 10px -6px rgba(0, 0, 0, 0.1);
}

/* ============================ Data view ============================ */

/*
 * Desktop legibility mask — dark wash behind the headline, over the canvas.
 * Figma: to-right rgba(0,0,0,.4) @ 20.914% → transparent @ 41.183%. The
 * status column carries its own gradient (see .groups).
 */
.maskData {
    position: absolute;
    inset: 0;
    border-radius: inherit;
    background: linear-gradient(90deg, rgba(0, 0, 0, 0.4) 20.914%, rgba(0, 0, 0, 0) 41.183%);
    pointer-events: none;
    z-index: 1;
}

/* Mobile-only link arrow, top-right of the card (Figma 1866:5607). */
.linkArrow {
    position: absolute;
    top: var(--spacing-20);
    right: var(--spacing-20);
    width: 20px;
    height: 20px;
    z-index: 2;
    color: var(--color-text-primary-inverted);
}

.content {
    position: relative;
    z-index: 2;
    display: flex;
    flex: 1;
    align-self: stretch;
    min-width: 0;
}

.cardMobile .content {
    flex: none;
    flex-direction: column;
    gap: var(--spacing-36);
    width: 100%;
}

/* Copy column — centred beside the canvas; the recalculating badge pushes it
 * into a top/bottom split (Figma 1870:6828 column-1 justify-between). */
.copyColumn {
    display: flex;
    flex-direction: column;
    justify-content: center;
    flex: 1;
    height: 234px;
    align-self: center;
    min-width: 0;
}

.copyColumnWithBadge {
    justify-content: space-between;
}

.cardMobile .copyColumn {
    flex: none;
    justify-content: flex-start;
    gap: var(--spacing-24);
    width: 100%;
    height: auto;
    align-self: auto;
}

.titleSub {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-16);
}

.titleRow {
    display: flex;
    align-items: center;
    gap: var(--spacing-16);
    /* shadow-float as text-shadow (Figma title node 1865:6964) */
    text-shadow:
        0 8px 10px rgba(0, 0, 0, 0.1),
        0 20px 25px rgba(0, 0, 0, 0.1);
}

.cardMobile .titleRow {
    width: 266px;
    height: 48px;
    text-shadow: none;
}

.totalValue {
    white-space: nowrap;
}

.headlineLabel {
    white-space: pre;
}

.cardMobile .headlineLabel {
    flex: 1;
    min-width: 0;
    white-space: pre-wrap;
}

/* The Figma mobile data variants have no subtitle. */
.cardMobile .subtitle {
    display: none;
}

/* Status groups (Optimal / In range / Out of range). Desktop: right column
 * with its own leftward black fade (Figma column-2, 1865:6969). */
.groups {
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    align-self: stretch;
    flex-shrink: 0;
    padding: var(--spacing-24) var(--spacing-80) var(--spacing-24) var(--spacing-24);
    background: linear-gradient(-90deg, rgb(0, 0, 0) 0%, rgb(0, 0, 0) 84.636%, rgba(0, 0, 0, 0) 100%);
}

/* Mobile: the three cells line up in a bottom row (154 / fill / 74 px). */
.cardMobile .groups {
    flex-direction: row;
    gap: var(--spacing-4);
    width: 100%;
    padding: 0;
    background: none;
    align-self: auto;
}

.cell {
    display: flex;
    flex-direction: column;
    gap: 6px; /* no --spacing-6 token */
}

.cardMobile .cell:first-child {
    width: 154px;
    flex: none;
}

.cardMobile .cell:nth-child(2) {
    flex: 1;
    min-width: 0;
}

.cardMobile .cell:last-child {
    width: 74px;
    flex: none;
}

.statusHeader {
    display: flex;
    align-items: center;
    gap: 6px; /* no --spacing-6 token */
}

.statusTile {
    width: 8px;
    height: 8px;
    border-radius: 2px;
    flex-shrink: 0;
    filter: drop-shadow(0 20px 12.5px rgba(0, 0, 0, 0.1)) drop-shadow(0 8px 5px rgba(0, 0, 0, 0.1));
}

/* Mobile status indicator — full-width 2px bar (Figma 1866:5639). */
.statusBar {
    width: 100%;
    height: 2px;
    border-radius: 2px;
}

/* Biomarker status palette — no marketing-v3 tokens; the same hexes are
 * hardcoded in BiomarkersFlowCanvas so the fibers match the tiles. */
.tileOptimal {
    background: #76b7e9;
}

.tileInRange {
    background: #5cc287;
}

.tileOutOfRange {
    background: #ffb770;
}

.statusValueRow {
    display: flex;
    align-items: flex-start;
    gap: 6px; /* no --spacing-6 token */
}

.cardMobile .statusValueRow {
    gap: var(--spacing-4);
}

.statusDelta {
    padding-top: var(--spacing-4);
    text-transform: uppercase;
    white-space: nowrap;
}

/* ====================== Calculating / empty hero ====================== */

.cardHero {
    padding: var(--spacing-24) var(--spacing-80) var(--spacing-24) var(--spacing-24);
}

.cardMobile.cardHero {
    padding: var(--spacing-20);
}

/*
 * Static crop of the converging flow-lines art (Figma image fill: width
 * 135.59%, height 210.44%, top -45.2%) with a dark wash on both edges.
 */
.heroArt {
    position: absolute;
    inset: 0;
    border-radius: inherit;
    overflow: hidden;
    pointer-events: none;
}

.heroArtImg {
    position: absolute;
    top: -45.2%;
    left: 0;
    width: 135.59%;
    height: 210.44%;
    max-width: none;
}

.heroMask {
    position: absolute;
    inset: 0;
    background: linear-gradient(90deg, rgba(0, 0, 0, 0.9) 0%, rgba(0, 0, 0, 0) 52.967%, rgba(0, 0, 0, 0.9) 100%);
}

.heroCopy {
    position: relative;
    z-index: 2;
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    /* .card centers items, so height: 100% resolved against auto and the
     * badge collapsed onto the title — stretch instead so the badge pins to
     * the top and the copy to the bottom (Figma 1870:7071 / 1870:7126;
     * designer note 2026-07-10). */
    align-self: stretch;
    height: auto;
    max-width: 282px;
    box-sizing: border-box;
}

.cardMobile .heroCopy {
    justify-content: flex-start;
    gap: var(--spacing-36);
    height: auto;
    width: 100%;
    max-width: none;
}

.heroTitleBlock {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-16);
}

/* The browser measures "biomarkers into insights" ~287px vs Figma's 282px
 * box (CSS counts trailing letter-spacing; Figma doesn't) — widen the title
 * alone so it keeps Figma's two-line wrap. */
.heroTitle {
    width: 288px;
}

.cardMobile .heroTitle {
    width: auto;
}

.cardMobile .heroTitleBlock {
    gap: var(--spacing-8);
}

/* =============================== Error =============================== */

/*
 * Error reuses the hero shell (1870:7126 / 1870:7380); only the mobile art
 * crop differs — Figma error mobile fills the card with a wider slice of the
 * flow art (width 250.49%, height 189.58%, left -26.77%, top -21.09%) where
 * the hero keeps the desktop crop.
 */
.cardMobile.cardError .heroArtImg {
    top: -21.09%;
    left: -26.77%;
    width: 250.49%;
    height: 189.58%;
}

/* Same browser-vs-Figma trailing letter-spacing quirk as .heroTitle: the
 * first line ("…trouble displaying") measures ~286.3px vs Figma's 282px box
 * (~326.4px vs 322px on mobile) — widen so the copy keeps Figma's two-line
 * wrap on both devices. */
.errorSub {
    width: 287px;
}

.cardMobile.cardError .errorSub {
    width: 327px;
}

/* ============================== Upsell ============================== */

.cardUpsell {
    min-height: 287px;
    padding: var(--spacing-24);
    gap: var(--spacing-48);
}

.cardMobile.cardUpsell {
    height: auto;
    padding: var(--spacing-20);
    gap: var(--spacing-40);
    /* Hairline frame on the mobile upsell only (Figma 1864:19966); the desktop
     * variant has none. */
    border: 1px solid var(--border-color-alpha-white-20);
    /* Press feedback (Figma widget_upsell_overview hover/tap=true, 1865:5908):
     * scale to 103% while held, ease back to 100% on release. */
    transform-origin: center;
    transition: transform 150ms ease-in-out;
}

.cardMobile.cardUpsell[data-pressed='true'] {
    transform: scale(1.03);
}

/*
 * Tilted glass composition (Figma card node 1864:19856: left -55px, top
 * 30.41px, 345×225.18 on the 930×287 card). The Figma panel ("Card /
 * Minimal") carries a liquid-distortion image fill that codegen cannot
 * export; a native backdrop-filter frosts the canvas lines instead (same
 * approach the portal PR took), with the R2 border / radius / shadows.
 */
.glassWrap {
    position: absolute;
    top: 30.41px;
    left: -55px;
    width: 345px;
    height: 225.18px;
    z-index: 1;
    pointer-events: none;
}

/* Mobile R2 update (1864:19966, 2026-07-10): the panel's rendered bounds sit
 * at top 53.77px, bleeding 2.49% past both side edges and off the bottom —
 * behind the benefits list instead of peeking over the top. */
.cardMobile .glassWrap {
    top: 53.77px;
    right: -2.49%;
    bottom: auto;
    left: -2.49%;
    width: auto;
    height: 263.09px;
}

/* Faint wavy-lines vector peeking over the panel (Figma Vector, opacity
 * baked into the svg). */
.glassLines {
    position: absolute;
    bottom: 10.33px;
    left: 50%;
    width: 286.169px;
    height: 57.234px;
    transform: translateX(-50%) rotate(-4.13deg);
}

.cardMobile .glassLines {
    top: 154.61px;
    right: 6.73%;
    bottom: auto;
    left: 9.41%;
    width: auto;
    height: auto;
    aspect-ratio: 318.67 / 85.51;
    transform: rotate(-4.13deg);
}

.glassPanel {
    position: absolute;
    inset: 0;
    border: 1.333px solid rgba(255, 255, 255, 0.3);
    border-radius: 13.328px;
    box-shadow:
        0 3.49px 24.941px 0 rgba(130, 135, 148, 0.15),
        inset -0.666px -0.666px 1.333px 0 rgba(0, 0, 0, 0.04),
        inset 0 1.333px 1.333px 0 rgba(255, 255, 255, 0.15);
    backdrop-filter: blur(4px);
    -webkit-backdrop-filter: blur(4px);
    transform: rotate(-4.53deg) skewX(-0.12deg);
    transform-origin: center;
}

.cardMobile .glassPanel {
    border-width: 1.54px;
    border-radius: 15.401px;
    box-shadow:
        0 4.033px 28.82px 0 rgba(130, 135, 148, 0.15),
        inset -0.77px -0.77px 1.54px 0 rgba(0, 0, 0, 0.04),
        inset 0 1.54px 1.54px 0 rgba(255, 255, 255, 0.15);
    transform: rotate(175.19deg) skewX(-0.66deg);
}

.upsellInner {
    position: relative;
    z-index: 2;
    display: flex;
    align-items: center;
    gap: var(--spacing-48);
    flex: 1;
    height: 100%;
    min-width: 0;
}

.cardMobile .upsellInner {
    flex: none;
    flex-direction: column;
    align-items: stretch;
    gap: var(--spacing-40);
    width: 100%;
    height: auto;
}

.upsellLead {
    display: flex;
    flex-direction: column;
    justify-content: center;
    gap: var(--spacing-24);
    flex-shrink: 0;
    max-width: 232px;
}

.cardMobile .upsellLead {
    max-width: none;
    width: 100%;
    padding: 0 var(--spacing-24);
    box-sizing: border-box;
}

/* Gradient ink headline (Figma 1864:19865: 140.246deg white 1.6153% →
 * 40%-white 82.392%; the mobile variant tilts to 144.843deg). */
.upsellTitle {
    margin: 0;
    background: linear-gradient(140.246deg, rgb(255, 255, 255) 1.6153%, rgba(255, 255, 255, 0.4) 82.392%);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}

.cardMobile .upsellTitle {
    text-align: center;
    background-image: linear-gradient(144.843deg, rgb(255, 255, 255) 1.6153%, rgba(255, 255, 255, 0.4) 82.392%);
}

.upsellCta {
    align-self: flex-start;
}

.upsellMobileContent {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-24);
    width: 100%;
}

.upsellCtaMobile button {
    width: 100%;
}

.benefits {
    display: flex;
    flex-wrap: wrap;
    align-items: flex-start;
    gap: var(--spacing-36);
    flex: 1 0 0;
    min-width: 0;
    margin: 0;
    padding: 0;
    list-style: none;
}

.benefit {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-8);
    flex: 1 0 0;
    min-width: 136px;
}

/* Gradient ink benefit titles (Figma 1864:19869: 180deg white → #999). */
.benefitTitle {
    background: linear-gradient(180deg, #fff 0%, #999 100%);
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
}

/* Mobile benefits — plain centred lines, no titles (Figma 1864:19952). */
.benefitsPlain {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-12);
    width: 100%;
    margin: 0;
    padding: 0;
    list-style: none;
}

/* ============================== Loading ============================== */

/*
 * Skeleton blocks: 10%-alpha white→grey gradient (Figma loading variants
 * 1870:6902 / 1870:7376). Figma varies the gradient angle a few degrees per
 * block; a single 135deg is used here (endpoints identical, difference
 * imperceptible at 10% alpha).
 */
.skel {
    display: block;
    border-radius: 3px;
    background: linear-gradient(135deg, rgba(255, 255, 255, 0.1) 3.7521%, rgba(198, 198, 198, 0.1) 97.815%);
}

.loadingContent {
    position: relative;
    z-index: 2;
    display: flex;
    align-items: flex-start;
    justify-content: space-between;
    flex: 1;
    align-self: center;
    height: 234px;
    min-width: 0;
    padding-right: var(--spacing-80);
}

.cardMobile .loadingContent {
    flex: none;
    flex-direction: column;
    gap: var(--spacing-36);
    width: 100%;
    height: auto;
    padding-right: 0;
    align-self: auto;
}

.loadingTitle {
    display: flex;
    flex-direction: column;
    justify-content: center;
    gap: var(--spacing-16);
    width: 124px;
    height: 100%;
}

.cardMobile .loadingTitle {
    flex-direction: row;
    align-items: center;
    gap: var(--spacing-12);
    width: 100%;
    height: auto;
}

.loadingLines {
    flex: 1;
    align-self: center;
    height: 194px;
    min-width: 0;
}

/* Desktop stacks the small block under the number inside the same column;
 * mobile splits them into a side column (Figma 1870:6165 vs 1870:6199). */
.loadingTitleAside {
    display: contents;
}

.cardMobile .loadingTitleAside {
    display: flex;
    flex-direction: column;
    justify-content: center;
    gap: var(--spacing-8);
    flex: 1;
    min-width: 0;
}

.skelNumber {
    width: 124px;
    height: 56px;
    border-radius: 4px;
}

.cardMobile .skelNumber {
    width: 86px;
    height: 48px;
}

.skelHeadline {
    width: 90px;
    height: 16px;
}

.cardMobile .skelHeadline {
    width: 194px;
    height: 24px;
}

/* Desktop loading has no subtitle block; mobile does (137×14). */
.skelSubtitle {
    display: none;
}

.cardMobile .skelSubtitle {
    display: block;
    width: 137px;
    height: 14px;
}

.loadingGroups {
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    height: 100%;
    flex-shrink: 0;
}

.cardMobile .loadingGroups {
    flex-direction: row;
    gap: var(--spacing-4);
    width: 100%;
    height: auto;
}

.loadingCell {
    display: flex;
    flex-direction: column;
    gap: 6px; /* no --spacing-6 token */
}

.cardMobile .loadingCell {
    flex: 1;
    min-width: 0;
}

/* Loading tiles render flat (no drop-shadow) per the Figma loading variant. */
.loadingCell .statusTile {
    filter: none;
}

/* Mobile loading bars sit at half opacity (Figma 1870:6208). */
.loadingCell .statusBar {
    opacity: 0.5;
}

.skelStatusLabel {
    width: 68px;
    height: 16px;
}

.skelStatusValue {
    width: 35px;
    height: 26px;
}

.skelCount {
    width: 24px;
    height: 20px;
}

.skelLabel {
    width: 45px;
    height: 17px;
}

/* The desktop row-alignment floors must not inflate the content-driven
 * mobile composition — min-height would beat the mobile height: auto. */
.cardMobile,
.cardMobile.cardUpsell {
    min-height: 0;
}
