/* Page-level styles not covered by Studio.Ui (tokens.css + studio-ui.css). Component-level
   styling (buttons, cards, badges, forms, etc.) lives in the Studio.Ui component library —
   see design/brand.tokens.json for the token source and CC-069 for the adoption record. */

:root {
    color-scheme: light;
}

* {
    box-sizing: border-box;
}

body {
    margin: 0;
    font-family: "Segoe UI", system-ui, sans-serif;
    background: var(--color-surface-page);
    color: var(--color-text-primary);
}

a {
    color: var(--color-action-primary);
}

.app-brand {
    font-weight: 700;
    font-size: 1.25rem;
    text-decoration: none;
    color: var(--color-text-primary);
}

.auth-shell {
    min-height: 100vh;
    display: grid;
    place-items: center;
    padding: 2rem;
}

.muted {
    color: var(--color-text-muted);
}

.account-profile {
    display: grid;
    grid-template-columns: max-content 1fr;
    gap: 0.25rem 1.5rem;
    margin: 0 0 1rem;
}

.account-profile dt {
    color: var(--color-text-muted);
}

.account-profile dd {
    margin: 0;
}

/* certchain#73: brand teal applied to app chrome. Owner decision 2026-09-07 moved the shell to
   StudioAppShell Variant="AppShellVariant.TopbarSidebar" (DECISIONS.md); navigation links live in
   the side nav now, so the topbar's own surface area is just its background, wordmark color, and
   focus ring. */

.studio-app-shell__topbar {
    background: var(--primitive-color-brand-600);
}

.studio-app-shell__topbar .app-brand {
    color: var(--color-text-inverse);
}

.studio-app-shell__topbar :focus-visible {
    outline-color: var(--color-text-inverse);
}

.studio-card__header {
    background: var(--primitive-color-brand-50);
    color: var(--primitive-color-brand-700);
    border-radius: var(--radius-lg) var(--radius-lg) 0 0;
}

.studio-table__head th {
    background: var(--primitive-color-brand-50);
    color: var(--primitive-color-brand-700);
}

/* Shared loading-state primitive (LoadingSkeleton.razor, design/redesign-plan.md P2). */

.sr-only {
    position: absolute;
    width: 1px;
    height: 1px;
    padding: 0;
    margin: -1px;
    overflow: hidden;
    clip: rect(0, 0, 0, 0);
    white-space: nowrap;
    border: 0;
}

.loading-skeleton__grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(16rem, 1fr));
    gap: var(--space-4);
}

.status-tab-bar {
    margin: var(--space-4) 0;
}

/* Dashboard (owner decision 2026-09-07: chart-led dashboard, StudioStatCard row +
   Studio.Ui.Charts visuals, matching certfleet's Home.razor). */

/* Owner defect 2026-09-07: restores the shell's own space-4 header-to-content gap
   (.studio-app-shell__main > * + * in studio-ui.css) on this page's own <main> wrapper -- see
   Dashboard.razor's comment on the wrapper for why the shell rule alone no longer reaches here. */
.dashboard-page > * + * { margin-top: var(--space-4); }

/* Owner defect 2026-09-07: every stat card's label used to wrap to one, two, or three lines
   ("Total certifications" vs. "Expiring within 30 days"), pushing the value below it to a
   different height in every card. Reserving a fixed two-line block for the label -- sized in em
   so it tracks studio-stat-card__label's own font-size -- keeps the value's baseline identical
   across the row regardless of how many words a given label wraps to. Scoped under this page's
   own wrapper class, not a redeclaration of .studio-stat-card__label itself (G21). */
.dashboard-stat-row__item .studio-stat-card__label {
  display: block;
  min-height: 2.6em;
  line-height: 1.3;
}

.dashboard-secondary-grid { display: grid; grid-template-columns: 1fr; gap: var(--space-6); margin-top: var(--space-6); }
@media (min-width: 1024px) {
  .dashboard-secondary-grid { grid-template-columns: repeat(3, 1fr); }
  .dashboard-secondary-grid__wide { grid-column: span 2; }
}

/* Certification status donut: a status-coded series (Active/Expiring/Training overdue/Expired
   carry real severity, not an arbitrary category), so this deliberately does NOT rely on
   StudioPieChart's default color.chart.categorical.N hash -- slot 1 happens to alias brand.600,
   which would paint whichever slice hashed there in plain brand teal regardless of its status.
   DashboardView.StatusFor maps each label to a real color.status.* class instead; the slice ring's
   color is corrected here via the component's own data-slice attribute (present precisely so a
   host page can do this), and the legend dot picks up the same class via chart-legend-dot--{class}
   so both read the same semantic color for the same label. */
.dashboard-donut-row { display: flex; align-items: center; gap: var(--space-6); padding: var(--space-2) 0; flex-wrap: wrap; }
.dashboard-donut-row__chart { position: relative; flex-shrink: 0; width: 7rem; }
.dashboard-donut-row__chart .studio-pie { width: 7rem; height: 7rem; }
.dashboard-donut-row__chart .studio-pie circle[data-slice="Active"] { stroke: var(--color-status-success-text); }
.dashboard-donut-row__chart .studio-pie circle[data-slice="Expiring"] { stroke: var(--color-status-warning-text); }
.dashboard-donut-row__chart .studio-pie circle[data-slice="Expired"] { stroke: var(--color-status-danger-text); }
.dashboard-donut-row__chart .studio-pie circle[data-slice="Training overdue"] { stroke: var(--color-text-muted); }
.dashboard-donut-row__legend { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: var(--space-2); font-size: var(--font-size-xs); flex: 1; min-width: 10rem; }
.dashboard-donut-row__legend-row { display: flex; align-items: center; justify-content: space-between; }
.dashboard-donut-row__legend-key { display: flex; align-items: center; gap: 0.375rem; }
.dashboard-donut-row__legend-value { font-weight: var(--font-weight-bold); }
.dashboard-donut-row__legend-dot { height: 0.625rem; width: 0.625rem; border-radius: var(--radius-full); flex-shrink: 0; }
.chart-legend-dot--success { background: var(--color-status-success-text); }
.chart-legend-dot--warning { background: var(--color-status-warning-text); }
.chart-legend-dot--danger { background: var(--color-status-danger-text); }
.chart-legend-dot--neutral { background: var(--color-text-muted); }

.dashboard-due-next { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: var(--space-3); }
.dashboard-due-next__item { display: flex; flex-direction: column; gap: 0.125rem; }
.dashboard-due-next__detail { font-size: var(--font-size-xs); color: var(--color-text-muted); }

.dashboard-manufacturer-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: var(--space-4); }
.dashboard-manufacturer-list__item { display: flex; flex-direction: column; gap: var(--space-2); }
.dashboard-manufacturer-list__header { display: flex; align-items: baseline; justify-content: space-between; gap: var(--space-2); font-weight: var(--font-weight-bold); }
