/* Autoría: Miguel Goñi Moscoso del Prado */
/**
 * ============================================================
 * MICROLAY DESIGN SYSTEM — Component Library
 * ============================================================
 *
 * Full component library built entirely on design-tokens.css.
 * No hardcoded color values — everything references a token.
 *
 * Table of Contents:
 *   00. BASE RESET & GLOBALS
 *   01. TYPOGRAPHY
 *   02. LAYOUT SHELL (sidebar, topbar, main content)
 *   03. BUTTONS
 *   04. BADGES & CHIPS
 *   05. CARDS
 *   06. FORM CONTROLS
 *   07. TABLES
 *   08. NAVIGATION (tabs, breadcrumbs)
 *   09. ALERTS & NOTIFICATIONS
 *   10. MODALS & OVERLAYS
 *   11. TOASTS
 *   12. PROGRESS & LOADING
 *   13. AVATARS
 *   14. DROPZONE
 *   15. METRIC BOXES
 *   16. EMPTY STATES
 *   17. UTILITY CLASSES
 *   18. ANIMATIONS
 *
 * Requirements: design-tokens.css must be loaded first.
 * Version: 1.0 — Feb 2026
 * ============================================================ */

@import url('/static/css/design-tokens.css?v=20260621_contrast');


/* ============================================================
   00. BASE RESET & GLOBALS
   ============================================================ */
*, *::before, *::after {
    box-sizing: border-box;
    margin: 0;
    padding: 0;
}

html {
    font-size: 16px;
    scroll-behavior: smooth;
    -webkit-text-size-adjust: 100%;
}

body {
    font-family: var(--font-sans);
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-regular);
    line-height: var(--line-height-normal);
    color: var(--color-text-primary);
    background-color: var(--color-bg-canvas);
    overflow-x: hidden;
    -webkit-font-smoothing: antialiased;
    -moz-osx-font-smoothing: grayscale;
}

a {
    color: var(--color-text-brand);
    text-decoration: none;
    transition: color var(--transition-fast);
}
a:hover { color: var(--color-brand-hover); }
a:focus-visible {
    outline: 2px solid var(--color-border-focus);
    outline-offset: 2px;
    border-radius: var(--radius-sm);
}

img, svg { display: block; max-width: 100%; }

/* Skip to main content — accessibility */
.skip-link {
    position: absolute;
    top: -100%;
    left: var(--space-4);
    z-index: 9999;
    padding: var(--space-2) var(--space-4);
    background: var(--color-brand);
    color: #fff;
    border-radius: var(--radius-md);
    font-weight: var(--font-weight-semibold);
    text-decoration: none;
}
.skip-link:focus {
    top: var(--space-2);
    outline: 2px solid var(--color-border-focus);
}

button { cursor: pointer; font-family: var(--font-sans); }

input, textarea, select {
    font-family: var(--font-sans);
    font-size: var(--font-size-body-md);
}

code, pre, kbd {
    font-family: var(--font-mono);
    font-size: 0.9em;
}

hr {
    border: none;
    border-top: 1px solid var(--color-border);
    margin: var(--space-6) 0;
}

::selection {
    background-color: var(--color-brand-muted);
    color: var(--color-brand-active);
}

/* Scrollbar — webkit */
/* Scrollbar — Firefox */
* { scrollbar-width: thin; scrollbar-color: var(--color-border) transparent; }

/* Scrollbar — webkit */
::-webkit-scrollbar { width: 6px; height: 6px; }
::-webkit-scrollbar-track { background: transparent; }
::-webkit-scrollbar-thumb {
    background: var(--color-border);
    border-radius: var(--radius-full);
}
::-webkit-scrollbar-thumb:hover { background: var(--color-border-strong); }


/* ============================================================
   01. TYPOGRAPHY
   ============================================================ */

/* ── Headings */
h1, h2, h3, h4, h5, h6,
.ds-h1, .ds-h2, .ds-h3, .ds-h4, .ds-h5, .ds-h6 {
    font-family: var(--font-sans);
    font-weight: var(--font-weight-semibold);
    line-height: var(--line-height-snug);
    letter-spacing: var(--letter-spacing-tight);
    color: var(--color-heading);
}

h1, .ds-h1 { font-size: var(--font-size-h1); font-weight: var(--font-weight-bold); }
h2, .ds-h2 { font-size: var(--font-size-h2); }
h3, .ds-h3 { font-size: var(--font-size-h3); }
h4, .ds-h4 { font-size: var(--font-size-h4); font-weight: var(--font-weight-medium); }
h5, .ds-h5 { font-size: var(--font-size-h5); font-weight: var(--font-weight-medium); }
h6, .ds-h6 { font-size: var(--font-size-h6); font-weight: var(--font-weight-medium); letter-spacing: var(--letter-spacing-wide); text-transform: uppercase; }

/* ── Display (landing / hero text) */
.ds-display-lg {
    font-size: var(--font-size-display-lg);
    font-weight: var(--font-weight-bold);
    letter-spacing: var(--letter-spacing-tighter);
    line-height: 1.05;
}
.ds-display-md {
    font-size: var(--font-size-display-md);
    font-weight: var(--font-weight-bold);
    letter-spacing: var(--letter-spacing-tighter);
}
.ds-display-sm {
    font-size: var(--font-size-display-sm);
    font-weight: var(--font-weight-semibold);
    letter-spacing: var(--letter-spacing-tight);
}

/* ── Body */
.ds-body-lg  { font-size: var(--font-size-body-lg);  line-height: var(--line-height-relaxed); }
.ds-body-md  { font-size: var(--font-size-body-md);  line-height: var(--line-height-relaxed); }
.ds-body-sm  { font-size: var(--font-size-body-sm);  line-height: var(--line-height-normal); }
.ds-body-xs  { font-size: var(--font-size-body-xs);  line-height: var(--line-height-normal); }
/* Help text under form fields, card descriptions, and contextual body copy. */
.ds-help-text {
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
    margin: var(--space-1) 0 0;
    display: block;
}

/* ── Labels */
.ds-label-lg { font-size: var(--font-size-label-lg); font-weight: var(--font-weight-medium); }
.ds-label-md { font-size: var(--font-size-label-md); font-weight: var(--font-weight-medium); }
.ds-label-sm { font-size: var(--font-size-label-sm); font-weight: var(--font-weight-medium); letter-spacing: var(--letter-spacing-wide); }
.ds-caption   { font-size: var(--font-size-caption); color: var(--color-text-muted); }

/* ── Text utilities */
.ds-text-primary   { color: var(--color-text-primary) !important; }
.ds-text-secondary { color: var(--color-text-secondary) !important; }
.ds-text-muted     { color: var(--color-text-muted) !important; }
.ds-text-brand     { color: var(--color-text-brand) !important; }
.ds-text-success   { color: var(--color-text-success) !important; }
.ds-text-error     { color: var(--color-text-error) !important; }
.ds-text-warning   { color: var(--color-text-warning) !important; }
.ds-text-inverse   { color: var(--color-text-inverse) !important; }

.ds-font-light     { font-weight: var(--font-weight-light) !important; }
.ds-font-regular   { font-weight: var(--font-weight-regular) !important; }
.ds-font-medium    { font-weight: var(--font-weight-medium) !important; }
.ds-font-semibold  { font-weight: var(--font-weight-semibold) !important; }
.ds-font-bold      { font-weight: var(--font-weight-bold) !important; }

.ds-truncate {
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

/* Section title with accent bar */
.ds-section-title {
    font-size: var(--font-size-h5);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
    padding-left: var(--space-3);
    border-left: 3px solid var(--color-brand);
    margin-bottom: var(--space-4);
    letter-spacing: var(--letter-spacing-normal);
}


/* ============================================================
   02. LAYOUT SHELL
   ============================================================ */

/* ── Sidebar */
.sidebar {
    position: fixed;
    top: 0;
    left: 0;
    width: var(--layout-sidebar-collapsed-width);
    height: 100vh;
    background-color: var(--color-sidebar-bg);
    border-right: 1px solid var(--color-sidebar-border);
    display: flex;
    flex-direction: column;
    overflow: hidden;
    transition: width var(--transition-normal);
    z-index: var(--z-fixed);
}

/* Desktop: expand on hover */
@media (min-width: 992px) {
    .sidebar:hover,
    .sidebar.sidebar--pinned {
        width: var(--layout-sidebar-width);
    }
}

/* Mobile: hidden by default */
@media (max-width: 991px) {
    .sidebar {
        transform: translateX(-100%);
        width: var(--layout-sidebar-width);
    }
    .sidebar.sidebar--open {
        transform: translateX(0);
    }
}

.sidebar-logo {
    display: flex;
    align-items: center;
    justify-content: center;
    gap: var(--space-3);
    padding: var(--space-4) var(--space-4);
    border-bottom: 1px solid var(--color-sidebar-border);
    min-height: var(--layout-topbar-height);
    overflow: hidden;
}
.sidebar:hover .sidebar-logo,
.sidebar.sidebar--pinned .sidebar-logo { justify-content: flex-start; }

.sidebar-logo img {
    width: 32px;
    height: 32px;
    flex-shrink: 0;
    border-radius: var(--radius-md);
}

/* Keep Microlay sidebar logo variants proportional in collapsed/expanded states */
.sidebar-logo img.sidebar-logo-collapsed,
.sidebar-logo img.sidebar-logo-expanded {
    width: auto;
    height: 36px;
    max-width: 100%;
    object-fit: contain;
    border-radius: 0;
}

.sidebar-logo-text {
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-semibold);
    color: var(--color-sidebar-text);
    white-space: nowrap;
    opacity: 0;
    transition: opacity var(--transition-fast);
}

.sidebar:hover .sidebar-logo-text,
.sidebar.sidebar--pinned .sidebar-logo-text {
    opacity: 1;
}

/* Nav items */
.sidebar-nav {
    flex: 1;
    overflow-y: auto;
    overflow-x: hidden;
    padding: var(--space-3) 0;
    scrollbar-gutter: stable both-edges;
}

.sidebar-nav-section {
    margin-top: var(--space-4);
}

.sidebar-nav-title {
    font-size: var(--font-size-caption);
    font-weight: var(--font-weight-semibold);
    letter-spacing: var(--letter-spacing-widest);
    text-transform: uppercase;
    color: var(--color-sidebar-text-muted);
    padding: 0 var(--space-4);
    margin-bottom: var(--space-2);
    white-space: nowrap;
    overflow: hidden;
    opacity: 0;
    height: 0;
    transition: opacity var(--transition-fast), height var(--transition-fast);
}

.sidebar:hover .sidebar-nav-title,
.sidebar.sidebar--pinned .sidebar-nav-title {
    opacity: 1;
    height: auto;
}

.sidebar-nav-item {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    padding: var(--space-2) var(--space-4);
    color: var(--color-sidebar-text);
    text-decoration: none;
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-medium);
    white-space: nowrap;
    transition: background-color var(--transition-fast), color var(--transition-fast);
    border-left: 3px solid transparent;
    position: relative;
    min-height: 40px;
}

.sidebar-nav-item:hover {
    background-color: var(--color-sidebar-hover);
    color: var(--color-sidebar-text);
}

.sidebar-nav-item:focus-visible {
    outline: 2px solid var(--color-border-focus);
    outline-offset: -2px;
    background-color: var(--color-sidebar-hover);
}

.sidebar-nav-item.active,
.sidebar-nav-item[aria-current="page"] {
    background-color: var(--color-sidebar-active-bg);
    color: var(--prim-cyan-400);
    border-left-color: var(--color-sidebar-active-bar);
}

.sidebar-nav-item i,
.sidebar-nav-item .nav-icon {
    font-size: 1rem;
    flex-shrink: 0;
    width: 1.25rem;
    text-align: center;
    color: var(--color-sidebar-icon);
    transition: color var(--transition-fast);
}

/* Notification count badge on a sidebar nav item (e.g. pending orders to
   review). Absolutely positioned top-right so it shows in both the expanded
   and the collapsed/icon-only sidebar states. */
.sidebar-nav-badge {
    position: absolute;
    top: 5px;
    right: 8px;
    min-width: 18px;
    height: 18px;
    padding: 0 5px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    font-size: 11px;
    font-weight: var(--font-weight-bold);
    line-height: 1;
    color: var(--color-text-inverse);
    background: var(--color-brand);
    border-radius: 999px;
}
.sidebar-nav-badge[hidden] {
    display: none;
}

.sidebar-nav-item:hover i,
.sidebar-nav-item.active i {
    color: var(--prim-cyan-400);
}

.sidebar-nav-item .nav-label {
    opacity: 0;
    visibility: hidden;
    width: 0;
    min-width: 0;
    overflow: hidden;
    transition: opacity var(--transition-fast), visibility var(--transition-fast), width var(--transition-fast);
    flex: 1;
}

.sidebar:hover .sidebar-nav-item .nav-label,
.sidebar.sidebar--pinned .sidebar-nav-item .nav-label,
.sidebar.hover-expanded .sidebar-nav-item .nav-label {
    opacity: 1;
    visibility: visible;
    width: auto;
    overflow: visible;
}

/* Tooltip for collapsed state */
.sidebar-nav-item::after {
    content: attr(data-tooltip);
    position: absolute;
    left: calc(var(--layout-sidebar-collapsed-width) + var(--space-2));
    background: rgba(26, 35, 50, 0.95);
    color: #fff;
    padding: var(--space-1) var(--space-2);
    border-radius: var(--radius-md);
    font-size: var(--font-size-body-xs);
    white-space: nowrap;
    pointer-events: none;
    opacity: 0;
    transition: opacity var(--transition-fast);
    z-index: var(--z-tooltip);
}

@media (min-width: 992px) {
    .sidebar:not(:hover):not(.sidebar--pinned) .sidebar-nav-item:hover::after {
        opacity: 1;
    }
}

/* ── Topbar */
.topbar {
    position: fixed;
    top: 0;
    left: var(--layout-sidebar-collapsed-width);
    right: 0;
    height: var(--layout-topbar-height);
    background: linear-gradient(135deg, var(--color-topbar-bg), var(--color-topbar-bg-end));
    border-bottom: 2px solid var(--color-topbar-border);
    display: flex;
    align-items: center;
    padding: 0 var(--space-6);
    gap: var(--space-4);
    z-index: var(--z-sticky);
    transition: left var(--transition-normal);
}

.sidebar:hover ~ .topbar,
.sidebar.sidebar--pinned ~ .topbar {
    left: var(--layout-sidebar-width);
}

@media (max-width: 991px) {
    .topbar { left: 0; }
}

.topbar-title {
    font-size: var(--font-size-h5);
    font-weight: var(--font-weight-semibold);
    color: var(--color-topbar-text);
    flex: 1;
}

.topbar-actions {
    display: flex;
    align-items: center;
    gap: var(--space-2);
}

/* Mobile sidebar toggle */
.sidebar-toggle {
    display: none;
    background: transparent;
    border: none;
    color: var(--color-topbar-text);
    font-size: 1.25rem;
    padding: var(--space-2);
    border-radius: var(--radius-md);
    cursor: pointer;
    transition: background-color var(--transition-fast);
}
.sidebar-toggle:hover { background-color: rgba(255,255,255,0.15); }
@media (max-width: 991px) { .sidebar-toggle { display: flex; align-items: center; } }

/* ── Main content */
.main-content {
    margin-left: var(--layout-sidebar-collapsed-width);
    margin-top: var(--layout-topbar-height);
    padding: var(--layout-content-padding);
    min-height: calc(100vh - var(--layout-topbar-height));
    transition: margin-left var(--transition-normal);
}

.sidebar:hover ~ .main-content,
.sidebar.sidebar--pinned ~ .main-content {
    margin-left: var(--layout-sidebar-width);
}

@media (max-width: 991px) {
    .main-content { margin-left: 0; }
}

/* Page header */
.page-header {
    display: flex;
    align-items: flex-start;
    justify-content: space-between;
    gap: var(--space-4);
    margin-bottom: var(--space-6);
    flex-wrap: wrap;
}

.page-header-info {}
.page-header-title {
    font-size: var(--font-size-h2);
    font-weight: var(--font-weight-bold);
    color: var(--color-heading);
    margin-bottom: var(--space-1);
}
.page-header-subtitle {
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
}
.page-header-actions {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    flex-shrink: 0;
}


/* ============================================================
   03. BUTTONS
   ============================================================ */

/* ── Base */
.btn, .ds-btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: var(--space-2);
    padding: var(--space-2) var(--space-4);
    font-family: var(--font-sans);
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-medium);
    line-height: 1;
    text-decoration: none;
    border: 1px solid transparent;
    border-radius: var(--radius-md);
    cursor: pointer;
    transition:
        background-color var(--transition-fast),
        border-color var(--transition-fast),
        color var(--transition-fast),
        box-shadow var(--transition-fast),
        transform var(--duration-instant) var(--ease-standard);
    white-space: nowrap;
    user-select: none;
    -webkit-user-select: none;
    outline: none;
    min-height: 40px;
}

.btn:focus-visible, .ds-btn:focus-visible {
    box-shadow: 0 0 0 3px var(--color-focus-ring);
}

.btn:active:not(:disabled), .ds-btn:active:not(:disabled) {
    transform: translateY(1px);
}

.btn:disabled, .ds-btn:disabled,
.btn[disabled], .btn.disabled {
    opacity: var(--opacity-disabled);
    cursor: not-allowed;
    pointer-events: none;
    filter: grayscale(0.3);
    box-shadow: none;
}

/* Touch devices (Apple HIG 44pt min target): enlarge standard interactive controls.
   Desktop stays compact; explicit -sm/-xs variants remain a deliberate opt-in. */
@media (pointer: coarse) {
    .btn, .ds-btn,
    .form-control, .ds-input, .ds-select, .ds-textarea {
        min-height: 44px;
    }
}

/* ── Sizes */
.btn-xs, .ds-btn-xs {
    padding: var(--space-1) var(--space-2);
    font-size: var(--font-size-body-xs);
    min-height: 26px;
    border-radius: var(--radius-sm);
}
.btn-sm, .ds-btn-sm {
    padding: var(--space-1-5) var(--space-3);
    font-size: var(--font-size-body-xs);
    min-height: 36px;
}
.btn-lg, .ds-btn-lg {
    padding: var(--space-3) var(--space-6);
    font-size: var(--font-size-body-md);
    min-height: 44px;
    border-radius: var(--radius-lg);
}
.btn-xl, .ds-btn-xl {
    padding: var(--space-4) var(--space-8);
    font-size: var(--font-size-body-lg);
    min-height: 52px;
    border-radius: var(--radius-lg);
}

/* ── Icon buttons */
.btn-icon, .ds-btn-icon {
    padding: var(--space-2);
    min-width: 36px;
    border-radius: var(--radius-md);
}
.btn-icon.btn-sm { min-width: 30px; padding: var(--space-1-5); }
.btn-icon.btn-lg { min-width: 44px; padding: var(--space-3); }

/* ── Full width */
.btn-block, .ds-btn-block { width: 100%; }

/* ── Variants */

/* Primary — flat solid fill (Apple-style). The brand colour itself (#0398ac) only
   reaches 3.45:1 with white text, so the resting fill uses brand-hover (#027a8c,
   5.04:1 ✓) and hover deepens to brand-active (7.4:1). Neutral subtle shadow, no
   coloured glow, for a calmer/more timeless surface. */
.btn-primary, .ds-btn-primary {
    background: var(--color-brand-hover);
    border-color: var(--color-brand-hover);
    color: var(--color-text-inverse);
    box-shadow: var(--shadow-xs);
}
.btn-primary:hover, .ds-btn-primary:hover {
    background: var(--color-brand-active);
    border-color: var(--color-brand-active);
    color: var(--color-text-inverse);
    box-shadow: var(--shadow-sm);
}

/* Secondary */
.btn-secondary, .ds-btn-secondary {
    background-color: var(--color-bg-elevated);
    border-color: var(--color-border);
    color: var(--color-text-primary);
}
.btn-secondary:hover, .ds-btn-secondary:hover {
    background-color: var(--color-bg-hover);
    border-color: var(--color-border-strong);
}

/* Ghost */
.btn-ghost, .ds-btn-ghost {
    background-color: transparent;
    border-color: transparent;
    color: var(--color-text-secondary);
}
.btn-ghost:hover, .ds-btn-ghost:hover {
    background-color: var(--color-bg-elevated);
    color: var(--color-text-primary);
}

/* Outline (brand) */
.btn-outline, .ds-btn-outline,
.btn-outline-primary {
    background-color: transparent;
    border-color: var(--color-brand);
    color: var(--color-brand);
}
.btn-outline:hover, .ds-btn-outline:hover,
.btn-outline-primary:hover {
    background-color: var(--color-brand-subtle);
    color: var(--color-brand-hover);
}

/* Danger */
.btn-danger, .ds-btn-danger {
    background-color: var(--color-error);
    border-color: var(--color-error-hover);
    color: var(--color-text-inverse);
    box-shadow: var(--shadow-error);
}
.btn-danger:hover, .ds-btn-danger:hover {
    background-color: var(--color-error-hover);
    border-color: var(--color-error-hover);
    color: var(--color-text-inverse);
}

/* Outline danger */
.btn-outline-danger, .ds-btn-outline-danger {
    background-color: transparent;
    border-color: var(--color-error);
    color: var(--color-error);
}
.btn-outline-danger:hover, .ds-btn-outline-danger:hover {
    background-color: var(--color-error-subtle);
}

/* Success */
.btn-success, .ds-btn-success {
    background-color: var(--color-success);
    border-color: var(--color-success-hover);
    color: var(--color-text-inverse);
    box-shadow: var(--shadow-success);
}
.btn-success:hover, .ds-btn-success:hover {
    background-color: var(--color-success-hover);
    color: var(--color-text-inverse);
}

/* Warning */
.btn-warning, .ds-btn-warning {
    background-color: var(--color-warning);
    border-color: var(--color-warning-hover);
    color: var(--color-text-inverse);
}
.btn-warning:hover, .ds-btn-warning:hover {
    background-color: var(--color-warning-hover);
    color: var(--color-text-inverse);
}

/* Loading state */
.btn.is-loading, .btn[data-loading] {
    pointer-events: none;
    position: relative;
    color: transparent !important;
}
.btn.is-loading::after, .btn[data-loading]::after {
    content: '';
    position: absolute;
    width: 14px;
    height: 14px;
    border: 2px solid rgba(255,255,255,0.4);
    border-top-color: #fff;
    border-radius: 50%;
    animation: ds-spin 0.7s linear infinite;
}


/* ============================================================
   04. BADGES & CHIPS
   ============================================================ */
.badge, .ds-badge {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    padding: var(--space-0-5) var(--space-2);
    font-size: var(--font-size-label-sm);
    font-weight: var(--font-weight-semibold);
    letter-spacing: var(--letter-spacing-wide);
    border-radius: var(--radius-full);
    line-height: 1;
    white-space: nowrap;
}

/* Default (neutral) */
.badge-default, .ds-badge-default,
.badge.bg-secondary {
    background-color: var(--color-bg-elevated);
    color: var(--color-text-secondary);
    border: 1px solid var(--color-border);
}

.badge-brand, .ds-badge-brand,
.badge.bg-primary {
    background-color: var(--color-brand-subtle);
    color: var(--color-text-brand);
    border: 1px solid var(--color-brand-border);
}

.badge-success, .ds-badge-success,
.badge.bg-success {
    background-color: var(--color-success-subtle);
    color: var(--color-text-success);
    border: 1px solid var(--color-success-border);
}

.badge-error, .ds-badge-error,
.badge.bg-danger {
    background-color: var(--color-error-subtle);
    color: var(--color-text-error);
    border: 1px solid var(--color-error-border);
}

.badge-warning, .ds-badge-warning,
.badge.bg-warning {
    background-color: var(--color-warning-subtle);
    color: var(--color-text-warning);
    border: 1px solid var(--color-warning-border);
}

.badge-info, .ds-badge-info,
.badge.bg-info {
    background-color: var(--color-info-subtle);
    color: var(--color-info-text);
    border: 1px solid var(--color-info-border);
}

/* Solid variants */
.badge-solid-brand   { background-color: var(--color-brand);   color: #fff; }
.badge-solid-success { background-color: var(--color-success); color: #fff; }
.badge-solid-error   { background-color: var(--color-error);   color: #fff; }
.badge-solid-warning { background-color: var(--color-warning); color: #fff; }

/* Dot badge (notification indicator) */
.badge-dot {
    width: 8px;
    height: 8px;
    padding: 0;
    border-radius: var(--radius-full);
    flex-shrink: 0;
}
.badge-dot.brand   { background-color: var(--color-brand); }
.badge-dot.success { background-color: var(--color-success); }
.badge-dot.error   { background-color: var(--color-error); }
.badge-dot.warning { background-color: var(--color-warning); }

/* Count badge */
.badge-count {
    min-width: 18px;
    height: 18px;
    padding: 0 var(--space-1);
    font-size: 10px;
    background-color: var(--color-error);
    color: #fff;
    border-radius: var(--radius-full);
    display: inline-flex;
    align-items: center;
    justify-content: center;
    font-weight: var(--font-weight-bold);
}

/* Chip (removable tag) */
.ds-chip {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1-5);
    padding: var(--space-1) var(--space-2-5);
    background-color: var(--color-bg-elevated);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-full);
    font-size: var(--font-size-body-xs);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-primary);
    transition: all var(--transition-fast);
}
.ds-chip:hover { border-color: var(--color-border-brand); }
.ds-chip-remove {
    color: var(--color-text-muted);
    cursor: pointer;
    line-height: 0;
    transition: color var(--transition-fast);
}
.ds-chip-remove:hover { color: var(--color-error); }


/* ============================================================
   05. CARDS
   ============================================================ */
.card, .ds-card {
    background-color: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-xl);
    box-shadow: var(--shadow-xs);
    overflow: hidden;
    transition: box-shadow var(--transition-fast);
}

/* Hover elevation */
.card-hover:hover, .ds-card-hover:hover {
    box-shadow: var(--shadow-md);
    border-color: var(--color-border-brand);
}

/* Elevated */
.card-elevated, .ds-card-elevated {
    box-shadow: var(--shadow-md);
    border: none;
}

/* Flat (no shadow, just border) */
.card-flat, .ds-card-flat {
    box-shadow: none;
}

/* Brand accent card */
.card-brand, .ds-card-brand {
    border-top: 3px solid var(--color-brand);
}
.card-success { border-top: 3px solid var(--color-success); }
.card-error   { border-top: 3px solid var(--color-error); }
.card-warning { border-top: 3px solid var(--color-warning); }

/* ── Card sections */
.card-header, .ds-card-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: var(--space-4) var(--space-5);
    border-bottom: 1px solid var(--color-border);
    background-color: var(--color-bg-canvas);
}

.card-header-title {
    font-size: var(--font-size-h5);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
    margin: 0;
}

.card-header-actions {
    display: flex;
    align-items: center;
    gap: var(--space-2);
}

.card-body, .ds-card-body {
    padding: var(--space-5);
    color: var(--color-text-primary);
}

.card-body.card-body-sm { padding: var(--space-4); }
.card-body.card-body-lg { padding: var(--space-6) var(--space-8); }

.card-footer, .ds-card-footer {
    display: flex;
    align-items: center;
    justify-content: flex-end;
    gap: var(--space-2);
    padding: var(--space-3) var(--space-5);
    border-top: 1px solid var(--color-border);
    background-color: var(--color-bg-canvas);
}

/* Stat / KPI card */
.ds-stat-card {
    background-color: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-xl);
    padding: var(--space-5);
    display: flex;
    align-items: flex-start;
    gap: var(--space-4);
    box-shadow: var(--shadow-xs);
    transition: all var(--transition-fast);
}
.ds-stat-card:hover {
    box-shadow: var(--shadow-md);
    transform: translateY(-2px);
}
.ds-stat-icon {
    width: 44px;
    height: 44px;
    border-radius: var(--radius-lg);
    display: flex;
    align-items: center;
    justify-content: center;
    font-size: 1.125rem;
    flex-shrink: 0;
}
.ds-stat-icon.brand   { background-color: var(--color-brand-subtle);   color: var(--color-brand); }
.ds-stat-icon.success { background-color: var(--color-success-subtle); color: var(--color-success); }
.ds-stat-icon.error   { background-color: var(--color-error-subtle);   color: var(--color-error); }
.ds-stat-icon.warning { background-color: var(--color-warning-subtle); color: var(--color-warning); }
.ds-stat-body { flex: 1; min-width: 0; }
.ds-stat-label {
    font-size: var(--font-size-body-xs);
    font-weight: var(--font-weight-medium);
    letter-spacing: var(--letter-spacing-wider);
    text-transform: uppercase;
    color: var(--color-text-muted);
    margin-bottom: var(--space-1);
}
.ds-stat-value {
    font-size: var(--font-size-h2);
    font-weight: var(--font-weight-bold);
    color: var(--color-heading);
    letter-spacing: var(--letter-spacing-tight);
    line-height: 1;
    margin-bottom: var(--space-1);
}
.ds-stat-change {
    font-size: var(--font-size-body-xs);
    font-weight: var(--font-weight-medium);
    display: flex;
    align-items: center;
    gap: var(--space-1);
}
.ds-stat-change.up   { color: var(--color-text-success); }
.ds-stat-change.down { color: var(--color-text-error); }


/* ============================================================
   06. FORM CONTROLS
   ============================================================ */

/* ── Form group */
.ds-form-group {
    display: flex;
    flex-direction: column;
    gap: var(--space-1-5);
    margin-bottom: var(--space-4);
}

.ds-label {
    font-size: var(--font-size-label-md);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-primary);
    display: flex;
    align-items: center;
    gap: var(--space-1);
}

.ds-label .required {
    color: var(--color-error);
    font-size: var(--font-size-body-xs);
}

/* Bootstrap form label/helper on the DS scale (light mode) — match .ds-label/.ds-hint
   so plain Bootstrap forms get the same weight, colour and legible helper text. */
.form-label {
    font-size: var(--font-size-label-md);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-primary);
    margin-bottom: var(--space-1-5);
}
.form-text {
    font-size: var(--font-size-body-xs);
    color: var(--color-text-secondary);
}

.ds-hint {
    font-size: var(--font-size-body-xs);
    color: var(--color-text-secondary);   /* AA: helper text legible */
}

.ds-error-msg {
    font-size: var(--font-size-body-xs);
    color: var(--color-text-error);
    display: flex;
    align-items: center;
    gap: var(--space-1);
}

/* ── Base input */
.ds-input,
.ds-select,
.ds-textarea,
.form-control {
    width: 100%;
    padding: var(--space-2) var(--space-3);
    font-family: var(--font-sans);
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-regular);
    color: var(--color-text-primary);
    background-color: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    min-height: 40px;
    outline: none;
    transition:
        border-color var(--transition-fast),
        box-shadow var(--transition-fast),
        background-color var(--transition-fast);
    appearance: none;
    -webkit-appearance: none;
}

.ds-input::placeholder,
.ds-textarea::placeholder,
.form-control::placeholder {
    color: var(--color-text-muted);
}

.ds-input:hover,
.ds-select:hover,
.ds-textarea:hover,
.form-control:hover {
    border-color: var(--color-border-strong);
}

.ds-input:focus,
.ds-select:focus,
.ds-textarea:focus,
.form-control:focus {
    border-color: var(--color-border-focus);
    box-shadow: 0 0 0 3px var(--color-focus-ring);
    outline: none;
}

/* Error state */
.ds-input.is-invalid,
.ds-input[aria-invalid="true"],
.form-control.is-invalid {
    border-color: var(--color-error);
    background-image: none;
}
.ds-input.is-invalid:focus,
.form-control.is-invalid:focus {
    box-shadow: 0 0 0 3px rgba(234, 84, 85, 0.20);
}

/* Success state */
.ds-input.is-valid,
.form-control.is-valid {
    border-color: var(--color-success);
}
.ds-input.is-valid:focus,
.form-control.is-valid:focus {
    box-shadow: 0 0 0 3px rgba(40, 199, 111, 0.20);
}

/* Disabled */
.ds-input:disabled,
.ds-select:disabled,
.ds-textarea:disabled,
.form-control:disabled {
    background-color: var(--color-bg-disabled);
    color: var(--color-text-muted);
    cursor: not-allowed;
    opacity: 1;
}

/* Sizes */
.ds-input-sm, .form-control-sm {
    padding: var(--space-1-5) var(--space-2-5);
    font-size: var(--font-size-body-sm);
    min-height: 32px;
}
.ds-input-lg, .form-control-lg {
    padding: var(--space-3) var(--space-4);
    font-size: var(--font-size-body-lg);
    min-height: 48px;
    border-radius: var(--radius-lg);
}

/* Select */
.ds-select {
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8'%3E%3Cpath fill='%239ca3af' d='M1 1l5 5 5-5'/%3E%3C/svg%3E");
    background-repeat: no-repeat;
    background-position: right var(--space-3) center;
    padding-right: var(--space-8);
    cursor: pointer;
}

/* Textarea */
.ds-textarea {
    min-height: 100px;
    resize: vertical;
    line-height: var(--line-height-relaxed);
}

/* Input with icon */
.ds-input-group {
    position: relative;
    display: flex;
    align-items: center;
}
.ds-input-group .ds-input { padding-left: var(--space-9, 2.25rem); }
.ds-input-group .ds-input-icon {
    position: absolute;
    left: var(--space-3);
    color: var(--color-text-muted);
    pointer-events: none;
    font-size: 0.875rem;
}
.ds-input-group .ds-input-icon-right { left: auto; right: var(--space-3); }
.ds-input-group .ds-input.has-icon-right { padding-right: var(--space-9, 2.25rem); }

/* ── Checkbox & Radio */
.ds-check-group {
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
}

.ds-check-item {
    display: flex;
    align-items: flex-start;
    gap: var(--space-2);
    cursor: pointer;
}

.ds-check-input {
    width: 18px;
    height: 18px;
    margin-top: 1px;
    flex-shrink: 0;
    border: 1.5px solid var(--color-border-strong);
    border-radius: var(--radius-sm);
    background-color: var(--color-bg-surface);
    cursor: pointer;
    appearance: none;
    -webkit-appearance: none;
    transition: all var(--transition-fast);
    position: relative;
}

.ds-check-input[type="radio"] { border-radius: var(--radius-full); }

.ds-check-input:checked {
    background-color: var(--color-brand);
    border-color: var(--color-brand);
}

.ds-check-input:checked::after {
    content: '';
    position: absolute;
    inset: 0;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Cpath fill='white' d='M13.78 4.22a.75.75 0 0 1 0 1.06l-7.25 7.25a.75.75 0 0 1-1.06 0L2.22 9.28a.75.75 0 0 1 1.06-1.06L6 10.94l6.72-6.72a.75.75 0 0 1 1.06 0z'/%3E%3C/svg%3E");
    background-repeat: no-repeat;
    background-position: center;
    background-size: 10px;
}

.ds-check-input[type="radio"]:checked::after {
    background-image: none;
    border-radius: var(--radius-full);
    inset: 4px;
    background-color: #fff;
}

.ds-check-input:focus-visible {
    box-shadow: 0 0 0 3px var(--color-focus-ring);
    outline: none;
}

.ds-check-label {
    font-size: var(--font-size-body-sm);
    color: var(--color-text-primary);
    cursor: pointer;
    user-select: none;
    line-height: 1.4;
}

/* ── Toggle Switch */
.ds-switch {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    cursor: pointer;
}

.ds-switch-track {
    position: relative;
    width: 40px;
    height: 22px;
    background-color: var(--color-border);
    border-radius: var(--radius-full);
    transition: background-color var(--transition-fast);
    flex-shrink: 0;
}

.ds-switch input[type="checkbox"] {
    position: absolute;
    opacity: 0;
    width: 0;
    height: 0;
}

.ds-switch input[type="checkbox"]:checked + .ds-switch-track {
    background-color: var(--color-brand);
}

.ds-switch-track::after {
    content: '';
    position: absolute;
    top: 3px;
    left: 3px;
    width: 16px;
    height: 16px;
    background: #fff;
    border-radius: var(--radius-full);
    box-shadow: var(--shadow-sm);
    transition: transform var(--transition-fast);
}

.ds-switch input[type="checkbox"]:checked + .ds-switch-track::after {
    transform: translateX(18px);
}

.ds-switch-label {
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-primary);
    cursor: pointer;
    user-select: none;
}


/* ============================================================
   07. TABLES
   ============================================================ */
.ds-table-wrap {
    overflow-x: auto;
    border-radius: var(--radius-xl);
    border: 1px solid var(--color-border);
    box-shadow: var(--shadow-xs);
}

.ds-table,
.table {
    width: 100%;
    border-collapse: collapse;
    font-size: var(--font-size-body-sm);
}

.ds-table thead,
.table thead {
    background-color: var(--color-bg-canvas);
    border-bottom: 2px solid var(--color-border);
}

.ds-table th,
.table th {
    padding: var(--space-3) var(--space-4);
    font-size: var(--font-size-label-sm);
    font-weight: var(--font-weight-semibold);
    letter-spacing: var(--letter-spacing-wider);
    text-transform: uppercase;
    color: var(--color-text-secondary);   /* AA: muted #9ca3af was 2.54:1 */
    text-align: left;
    white-space: nowrap;
}

.ds-table td,
.table td {
    padding: var(--space-3) var(--space-4);
    color: var(--color-text-primary);
    border-bottom: 1px solid var(--color-border);
    vertical-align: middle;
}

.ds-table tbody tr:last-child td,
.table tbody tr:last-child td {
    border-bottom: none;
}

.ds-table tbody tr:hover,
.table-hover tbody tr:hover {
    background-color: var(--color-bg-hover);
}

.ds-table .ds-table-action-col { width: 1%; white-space: nowrap; }


/* ============================================================
   08. NAVIGATION
   ============================================================ */

/* ── Tabs */
.ds-tabs {
    display: flex;
    border-bottom: 1px solid var(--color-border);
    gap: var(--space-1);
    overflow-x: auto;
    scrollbar-width: none;
}
.ds-tabs::-webkit-scrollbar { display: none; }

/* Stepper variant (opt-in modifier — only applied to multi-step wizard
   navs such as the marketing assistant). Desktop rendering is identical to
   a plain .ds-tabs; the responsive compaction below lives entirely inside a
   max-width block, so other .ds-tabs consumers are never affected. */
@media (max-width: 768px) {
    .ds-tabs--stepper {
        scroll-snap-type: x proximity;
    }
    .ds-tabs--stepper .ds-tab {
        padding: var(--space-2) var(--space-3);
        scroll-snap-align: start;
    }
    /* Drop the per-step status line ("Pendiente/Hecho") on phones so each
       step pill stays compact and the row needs less horizontal scroll. */
    .ds-tabs--stepper .ds-tab small {
        display: none;
    }
}

.ds-tab {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    padding: var(--space-2-5) var(--space-4);
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-secondary);
    text-decoration: none;
    border-bottom: 2px solid transparent;
    margin-bottom: -1px;
    white-space: nowrap;
    cursor: pointer;
    background: none;
    border-top: none;
    border-left: none;
    border-right: none;
    transition: color var(--transition-fast), border-color var(--transition-fast);
}

.ds-tab:hover {
    color: var(--color-text-primary);
    background-color: var(--color-bg-elevated);
}

.ds-tab.active, .ds-tab[aria-selected="true"] {
    color: var(--color-brand);
    border-bottom-color: var(--color-brand);
}

/* ── Breadcrumbs */
.ds-breadcrumbs {
    display: flex;
    align-items: center;
    gap: var(--space-1-5);
    flex-wrap: wrap;
    font-size: var(--font-size-body-xs);
    color: var(--color-text-muted);
    margin-bottom: var(--space-4);
}

.ds-breadcrumb-item a {
    color: var(--color-text-secondary);
    text-decoration: none;
}
.ds-breadcrumb-item a:hover { color: var(--color-brand); }
.ds-breadcrumb-item.current { color: var(--color-text-primary); font-weight: var(--font-weight-medium); }
.ds-breadcrumb-sep { color: var(--color-text-muted); }


/* ============================================================
   09. ALERTS & NOTIFICATIONS
   ============================================================ */
.ds-alert {
    display: flex;
    align-items: flex-start;
    gap: var(--space-3);
    padding: var(--space-3) var(--space-4);
    border-radius: var(--radius-lg);
    border: 1px solid;
    font-size: var(--font-size-body-sm);
}

.ds-alert .ds-alert-icon {
    font-size: 1rem;
    flex-shrink: 0;
    margin-top: 1px;
}

.ds-alert .ds-alert-body { flex: 1; }
.ds-alert .ds-alert-title {
    font-weight: var(--font-weight-semibold);
    margin-bottom: var(--space-1);
}

.ds-alert .ds-alert-close {
    flex-shrink: 0;
    background: none;
    border: none;
    cursor: pointer;
    opacity: 0.5;
    font-size: 1rem;
    line-height: 1;
    padding: var(--space-0-5);
    transition: opacity var(--transition-fast);
}
.ds-alert .ds-alert-close:hover { opacity: 1; }

.ds-alert-info {
    background-color: var(--color-info-subtle);
    border-color: var(--color-info-border);
    color: var(--color-info-text);
}
.ds-alert-success {
    background-color: var(--color-success-subtle);
    border-color: var(--color-success-border);
    color: var(--color-success-text);
}
.ds-alert-error {
    background-color: var(--color-error-subtle);
    border-color: var(--color-error-border);
    color: var(--color-error-text);
}
.ds-alert-warning {
    background-color: var(--color-warning-subtle);
    border-color: var(--color-warning-border);
    color: var(--color-text-warning);
}


/* ============================================================
   10. MODALS & OVERLAYS
   ============================================================ */
.ds-overlay {
    position: fixed;
    inset: 0;
    background-color: var(--color-bg-overlay);
    z-index: var(--z-overlay);
    display: flex;
    align-items: center;
    justify-content: center;
    padding: var(--space-4);
    animation: ds-fade-in var(--duration-normal) var(--ease-decelerate);
}

/* Overlay elevado: para diálogos que pueden abrirse SOBRE un modal
   (p.ej. confirmDialog disparado desde dentro de un modal Bootstrap).
   Por encima de --z-modal (1055), por debajo de --z-toast (1080). */
.ds-overlay.ds-overlay-top { z-index: calc(var(--z-modal) + 20); }

.ds-modal {
    background-color: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-2xl);
    box-shadow: var(--shadow-2xl);
    width: 100%;
    max-width: 560px;
    max-height: calc(100vh - var(--space-8));
    overflow: hidden;
    display: flex;
    flex-direction: column;
    animation: ds-slide-up var(--duration-normal) var(--ease-decelerate);
}

.ds-modal-sm { max-width: 420px; }
.ds-modal-lg { max-width: 760px; }
.ds-modal-xl { max-width: 1040px; }

.ds-modal-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    padding: var(--space-5) var(--space-6);
    border-bottom: 1px solid var(--color-border);
    flex-shrink: 0;
}

.ds-modal-title {
    font-size: var(--font-size-h4);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
    margin: 0;
}

.ds-modal-close {
    width: 32px;
    height: 32px;
    display: flex;
    align-items: center;
    justify-content: center;
    background: var(--color-bg-elevated);
    border: none;
    border-radius: var(--radius-md);
    cursor: pointer;
    color: var(--color-text-muted);
    font-size: 1rem;
    transition: all var(--transition-fast);
}
.ds-modal-close:hover {
    background: var(--color-error-subtle);
    color: var(--color-error);
}

/* ── Calm modal header (Apple-style), opt-in via .modal-header-calm. Surface bg,
   dark title, subtle divider, small brand-icon accent, neutral close button. The
   semantic colour lives in the action buttons, not a saturated header bar. */
.modal-header-calm {
    background: var(--color-bg-surface);
    color: var(--color-heading);
    border-bottom: 1px solid var(--color-border);
}
.modal-header-calm .modal-title,
.modal-header-calm .ds-modal-title {
    color: var(--color-heading);
    font-weight: var(--font-weight-semibold);
}
.modal-header-calm .modal-title > i:first-child,
.modal-header-calm .ds-modal-title > i:first-child {
    color: var(--color-brand);
}
.modal-header-calm .btn-close { filter: none; }

/* Calm card/section header (Apple-style) — replaces saturated bg-* bars on page
   sections. Surface bg, dark title, brand-icon accent, subtle divider. */
.card-header.card-header-calm {
    background: var(--color-bg-surface);
    color: var(--color-heading);
    border-bottom: 1px solid var(--color-border);
    padding: var(--space-3) var(--space-4);
}
.card-header-calm h5, .card-header-calm h6 {
    color: var(--color-heading);
    font-weight: var(--font-weight-semibold);
    margin: 0;
}
.card-header-calm h5 > i:first-child,
.card-header-calm h6 > i:first-child { color: var(--color-brand); }

/* Canonical delete button (ghost → red on hover, × icon) — the calm microlai object-card
   delete, promoted to a reusable component for item/row delete actions app-wide. */
.ds-btn-delete {
    display: inline-flex; align-items: center; justify-content: center;
    width: 32px; height: 32px; padding: 0;
    background: transparent; color: var(--color-text-muted);
    border: none; border-radius: var(--radius-sm); cursor: pointer;
    transition: color var(--duration-fast) var(--ease-standard),
                background var(--duration-fast) var(--ease-standard);
}
.ds-btn-delete i { margin: 0; }
.ds-btn-delete:hover { background: var(--color-error-subtle); color: var(--color-error); }
.ds-btn-delete:focus-visible { outline: 2px solid var(--color-brand); outline-offset: 2px; }

/* Manufacturer logo — reusable circular container (mirrors the tank-card logo). */
.ds-mfr-logo {
    flex: 0 0 auto;
    display: inline-flex; align-items: center; justify-content: center;
    width: 40px; height: 40px;
    border-radius: 50%;
    background: #fff;
    border: 1px solid var(--color-border);
    overflow: hidden;
}
.ds-mfr-logo img { width: 75%; height: 75%; object-fit: contain; }
.ds-mfr-logo i { color: var(--color-text-muted); }
.ds-mfr-logo--sm { width: 32px; height: 32px; }
.ds-mfr-logo--lg { width: 48px; height: 48px; }
/* Semantic icon accent on a calm (light) header — colour stays only in the icon,
   not a full bar. Uses the AA -text shades so the glyph reads crisply on white. */
.modal-header-calm.mh-warning .modal-title > i:first-child,
.modal-header-calm.mh-warning .ds-modal-title > i:first-child { color: var(--color-warning-text); }
.modal-header-calm.mh-danger .modal-title > i:first-child,
.modal-header-calm.mh-danger .ds-modal-title > i:first-child { color: var(--color-error-text); }
.modal-header-calm.mh-info .modal-title > i:first-child,
.modal-header-calm.mh-info .ds-modal-title > i:first-child { color: var(--color-info-text); }
.modal-header-calm.mh-success .modal-title > i:first-child,
.modal-header-calm.mh-success .ds-modal-title > i:first-child { color: var(--color-success-text); }

/* ── Bootstrap modal chrome on the DS spacing scale (light mode). The .ds-modal-*
   system already uses tokens; these bring Bootstrap .modal-* in line so every modal
   shares the same padding rhythm, dividers and footer alignment. Utility overrides
   (.p-0 etc.) still win. */
.modal-content { border: 1px solid var(--color-border); }
.modal-header { padding: var(--space-4) var(--space-5); }
.modal-body { padding: var(--space-5); }
.modal-footer {
    padding: var(--space-4) var(--space-5);
    gap: var(--space-2);
    align-items: center;
    justify-content: flex-end;
    border-top: 1px solid var(--color-border);
}

.ds-modal-body {
    padding: var(--space-6);
    overflow-y: auto;
    flex: 1;
    color: var(--color-text-primary);
}

.ds-modal-footer {
    padding: var(--space-4) var(--space-6);
    border-top: 1px solid var(--color-border);
    display: flex;
    align-items: center;
    justify-content: flex-end;
    gap: var(--space-2);
    flex-shrink: 0;
    background-color: var(--color-bg-canvas);
}

/* Detail-card sections inside a ds-modal (e.g. the customer ficha). */
.ds-modal-section { margin-bottom: var(--space-5); }
.ds-modal-section:last-child { margin-bottom: 0; }
.ds-modal-subtitle {
    margin: 0 0 var(--space-2);
    font-size: var(--text-sm, 0.85rem);
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: var(--color-text-secondary);
    border-bottom: 1px solid var(--color-border);
    padding-bottom: var(--space-1);
}
.ds-field-row {
    display: flex;
    gap: var(--space-3);
    padding: var(--space-1) 0;
    align-items: baseline;
}
.ds-field-label {
    flex: 0 0 40%;
    max-width: 40%;
    color: var(--color-text-secondary);
    font-size: var(--text-sm, 0.85rem);
}
.ds-field-value {
    flex: 1;
    color: var(--color-text-primary);
    word-break: break-word;
}
/* Clickable table rows (customer list -> ficha modal). */
.sp-row-click { cursor: pointer; }
.sp-row-click:hover { background-color: var(--color-bg-subtle, rgba(0,0,0,0.04)); }
.sp-row-click:focus-visible { outline: 2px solid var(--color-primary, #2563eb); outline-offset: -2px; }


/* ============================================================
   11. TOASTS
   ============================================================ */
.ds-toast-container {
    position: fixed;
    z-index: var(--z-toast);
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
    pointer-events: none;
    padding: var(--space-4);
}

.ds-toast-container.top-right    { top: 0; right: 0; align-items: flex-end; }
.ds-toast-container.bottom-right { bottom: 0; right: 0; align-items: flex-end; }
.ds-toast-container.top-center   { top: 0; left: 50%; transform: translateX(-50%); align-items: center; }

.ds-toast {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    padding: var(--space-3) var(--space-4);
    background-color: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    box-shadow: var(--shadow-xl);
    font-size: var(--font-size-body-sm);
    color: var(--color-text-primary);
    pointer-events: all;
    max-width: 380px;
    animation: ds-slide-in-right var(--duration-normal) var(--ease-decelerate);
}

.ds-toast-icon { font-size: 1rem; flex-shrink: 0; }
.ds-toast-msg  { flex: 1; }
.ds-toast-stack {
    display: flex;
    flex: 1;
    flex-direction: column;
    gap: var(--space-1);
    min-width: 0;
}
.ds-toast-title {
    font-weight: var(--font-weight-semibold);
    line-height: 1.2;
}
.ds-toast-body {
    line-height: 1.45;
    overflow-wrap: anywhere;
}
.ds-toast-body > :last-child {
    margin-bottom: 0;
}
.ds-toast.rich {
    align-items: flex-start;
}
.ds-toast.rich .ds-toast-icon {
    margin-top: 2px;
}

.ds-toast.success .ds-toast-icon { color: var(--color-success); }
.ds-toast.error   .ds-toast-icon { color: var(--color-error); }
.ds-toast.warning .ds-toast-icon { color: var(--color-warning); }
.ds-toast.info    .ds-toast-icon { color: var(--color-brand); }

.ds-toast-close {
    background: none;
    border: none;
    cursor: pointer;
    color: var(--color-text-muted);
    font-size: 0.875rem;
    padding: var(--space-1);
    border-radius: var(--radius-sm);
    transition: all var(--transition-fast);
}
.ds-toast-close:hover {
    background: var(--color-bg-elevated);
    color: var(--color-text-primary);
}


/* ============================================================
   12. PROGRESS & LOADING
   ============================================================ */

/* ── Progress bar */
.ds-progress {
    height: 6px;
    background-color: var(--color-bg-elevated);
    border-radius: var(--radius-full);
    overflow: hidden;
}
.ds-progress-lg { height: 10px; }
.ds-progress-sm { height: 4px; }

.ds-progress-bar {
    height: 100%;
    border-radius: var(--radius-full);
    background: linear-gradient(90deg, var(--color-brand), var(--color-brand-hover));
    transition: width var(--duration-slow) var(--ease-standard);
}
.ds-progress-bar.success { background: var(--color-success); }
.ds-progress-bar.error   { background: var(--color-error); }
.ds-progress-bar.warning { background: var(--color-warning); }
.ds-progress-bar.striped {
    background-image: linear-gradient(
        45deg,
        rgba(255,255,255,.15) 25%, transparent 25%,
        transparent 50%, rgba(255,255,255,.15) 50%,
        rgba(255,255,255,.15) 75%, transparent 75%,
        transparent
    );
    background-size: 1rem 1rem;
    animation: ds-progress-stripes 1s linear infinite;
}

/* ── Spinner */
.ds-spinner {
    width: 20px;
    height: 20px;
    border: 2px solid var(--color-border);
    border-top-color: var(--color-brand);
    border-radius: var(--radius-full);
    animation: ds-spin 0.7s linear infinite;
    display: inline-block;
    flex-shrink: 0;
}
.ds-spinner-sm { width: 14px; height: 14px; border-width: 1.5px; }
.ds-spinner-lg { width: 32px; height: 32px; border-width: 3px; }
.ds-spinner-xl { width: 48px; height: 48px; border-width: 4px; }
.ds-spinner.success { border-top-color: var(--color-success); }
.ds-spinner.error   { border-top-color: var(--color-error); }

/* ── Skeleton loader */
.ds-skeleton {
    background: linear-gradient(
        90deg,
        var(--color-bg-elevated) 25%,
        var(--color-bg-hover) 50%,
        var(--color-bg-elevated) 75%
    );
    background-size: 200% 100%;
    animation: ds-skeleton 1.5s ease-in-out infinite;
    border-radius: var(--radius-md);
}
.ds-skeleton-text  { height: var(--font-size-body-md); margin-bottom: var(--space-2); }
.ds-skeleton-title { height: var(--font-size-h3); margin-bottom: var(--space-3); }
.ds-skeleton-avatar { width: 40px; height: 40px; border-radius: var(--radius-full); }

/* Inline skeleton shimmer — auto-removes when aria-busy is cleared */
[aria-busy="true"].ds-skeleton-text {
    color: transparent;
    background: linear-gradient(90deg, var(--color-bg-elevated) 25%, var(--color-bg-hover) 50%, var(--color-bg-elevated) 75%);
    background-size: 200% 100%;
    animation: ds-skeleton 1.5s ease-in-out infinite;
    border-radius: var(--radius-sm);
    min-width: 80px;
    display: inline-block;
}


/* ============================================================
   13. AVATARS
   ============================================================ */
.ds-avatar {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--radius-full);
    background-color: var(--color-brand-subtle);
    color: var(--color-brand);
    font-weight: var(--font-weight-semibold);
    font-size: var(--font-size-body-sm);
    overflow: hidden;
    flex-shrink: 0;
    /* default size */
    width: 36px;
    height: 36px;
}
.ds-avatar img { width: 100%; height: 100%; object-fit: cover; }
.ds-avatar-xs  { width: 24px; height: 24px; font-size: var(--font-size-caption); }
.ds-avatar-sm  { width: 32px; height: 32px; font-size: var(--font-size-body-xs); }
.ds-avatar-lg  { width: 48px; height: 48px; font-size: var(--font-size-body-md); }
.ds-avatar-xl  { width: 64px; height: 64px; font-size: var(--font-size-h4); }
.ds-avatar-2xl { width: 96px; height: 96px; font-size: var(--font-size-h2); }

/* Avatar group */
.ds-avatar-group {
    display: flex;
    flex-direction: row-reverse;
}
.ds-avatar-group .ds-avatar {
    border: 2px solid var(--color-bg-surface);
    margin-left: -8px;
}
.ds-avatar-group .ds-avatar:last-child { margin-left: 0; }


/* ============================================================
   14. DROPZONE
   ============================================================ */
.ds-dropzone {
    border: 2px dashed var(--color-border);
    border-radius: var(--radius-xl);
    padding: var(--space-10) var(--space-8);
    text-align: center;
    cursor: pointer;
    background-color: var(--color-bg-canvas);
    transition: all var(--transition-normal);
    position: relative;
}

.ds-dropzone:hover,
.ds-dropzone.ds-drag-over {
    border-color: var(--color-brand);
    background-color: var(--color-brand-subtle);
}

.ds-dropzone.ds-drag-over {
    box-shadow: inset 0 0 0 3px var(--color-focus-ring);
}

.ds-dropzone-icon {
    font-size: 2.5rem;
    color: var(--color-text-muted);
    margin-bottom: var(--space-3);
    transition: color var(--transition-fast);
}
.ds-dropzone:hover .ds-dropzone-icon,
.ds-dropzone.ds-drag-over .ds-dropzone-icon {
    color: var(--color-brand);
}

.ds-dropzone-title {
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-semibold);
    color: var(--color-text-primary);
    margin-bottom: var(--space-1);
}

.ds-dropzone-hint {
    font-size: var(--font-size-body-sm);
    color: var(--color-text-muted);
}

.ds-dropzone-link {
    color: var(--color-brand);
    font-weight: var(--font-weight-medium);
    cursor: pointer;
    text-decoration: underline;
    text-underline-offset: 2px;
}

/* Shared file dropper contract.
   Keep legacy selectors aligned so older pages inherit the same affordance. */
.ml-file-dropper,
.upload-zone,
.dropzone,
.p360-upload-dropzone {
    border: 2px dashed var(--color-border);
    border-radius: 8px;
    padding: var(--space-8) var(--space-6);
    text-align: center;
    cursor: pointer;
    background-color: var(--color-bg-canvas);
    color: var(--color-text-primary);
    transition:
        border-color var(--transition-normal),
        background-color var(--transition-normal),
        box-shadow var(--transition-normal),
        transform var(--transition-normal);
}

.ml-file-dropper:hover,
.ml-file-dropper:focus-visible,
.ml-file-dropper.is-dragover,
.ml-file-dropper.drag-over,
.ml-file-dropper.dragover,
.ml-file-dropper.ds-drag-over,
.upload-zone:hover,
.upload-zone:focus-visible,
.upload-zone.is-dragover,
.upload-zone.drag-over,
.upload-zone.dragover,
.dropzone:hover,
.dropzone:focus-visible,
.dropzone.is-dragover,
.dropzone.drag-over,
.dropzone.dragover,
.p360-upload-dropzone:hover,
.p360-upload-dropzone:focus-within,
.p360-upload-dropzone.is-dragover {
    border-color: var(--color-brand);
    background-color: var(--color-brand-subtle);
    box-shadow: inset 0 0 0 2px var(--color-focus-ring);
    transform: none;
}

.ml-file-dropper.is-dragover,
.ml-file-dropper.drag-over,
.ml-file-dropper.dragover,
.ml-file-dropper.ds-drag-over,
.upload-zone.is-dragover,
.upload-zone.drag-over,
.upload-zone.dragover,
.dropzone.is-dragover,
.dropzone.drag-over,
.dropzone.dragover,
.p360-upload-dropzone.is-dragover {
    box-shadow: inset 0 0 0 3px var(--color-focus-ring);
    transform: none;
}

.ml-file-dropper.has-file,
.dropzone.has-file,
.upload-zone.has-file,
.p360-upload-dropzone.is-filled {
    border-color: var(--color-success);
    background-color: var(--color-success-subtle);
    box-shadow: 0 10px 24px rgba(34, 197, 94, 0.12);
}

.ml-file-dropper.remote-file,
.dropzone.remote-file,
.upload-zone.remote-file {
    border-style: solid;
}

.ml-file-dropper.is-disabled,
.upload-zone.is-disabled,
.dropzone.is-disabled {
    cursor: not-allowed;
    opacity: 0.58;
}

.ml-file-dropper__content {
    display: grid;
    justify-items: center;
    gap: var(--space-2);
    min-width: 0;
}

.ml-file-dropper__icon {
    font-size: 2.25rem;
    color: var(--color-text-muted);
    margin-bottom: var(--space-1);
    transition: color var(--transition-fast);
}

.ml-file-dropper:hover .ml-file-dropper__icon,
.ml-file-dropper:focus-visible .ml-file-dropper__icon,
.ml-file-dropper.is-dragover .ml-file-dropper__icon,
.ml-file-dropper.drag-over .ml-file-dropper__icon,
.ml-file-dropper.dragover .ml-file-dropper__icon,
.ml-file-dropper.ds-drag-over .ml-file-dropper__icon {
    color: var(--color-brand);
}

.ml-file-dropper.has-file .ml-file-dropper__icon {
    color: var(--color-success);
}

.ml-file-dropper__title {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex-wrap: wrap;
    gap: var(--space-2);
    margin: 0;
    color: var(--color-text-primary);
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-semibold);
    line-height: 1.3;
}

.ml-file-dropper__hint {
    color: var(--color-text-muted);
    font-size: var(--font-size-body-sm);
    line-height: 1.35;
}

.ml-file-dropper__badge {
    display: inline-flex;
    align-items: center;
    min-height: 22px;
    padding: 3px 8px;
    border-radius: 999px;
    border: 1px solid var(--color-border);
    font-size: 11px;
    font-weight: 700;
    line-height: 1;
    white-space: nowrap;
}

.ml-file-dropper__badge--required {
    border-color: color-mix(in srgb, var(--color-brand) 35%, var(--color-border));
    background: var(--color-brand-subtle);
    color: var(--color-brand-hover);
}

.ml-file-dropper__badge--optional {
    background: var(--color-bg-surface);
    color: var(--color-text-muted);
}


/* ============================================================
   15. METRIC BOXES (printer / clinical KPIs)
   ============================================================ */
.metric-box {
    background: linear-gradient(135deg, var(--color-brand), var(--color-brand-hover));
    border-radius: var(--radius-lg);
    padding: var(--space-3) var(--space-4);
    color: #fff;
    text-align: center;
    box-shadow: var(--shadow-brand);
}

.metric-box.metric-success { background: linear-gradient(135deg, var(--color-success), var(--color-success-hover)); box-shadow: var(--shadow-success); }
.metric-box.metric-error   { background: linear-gradient(135deg, var(--color-error),   var(--color-error-hover));   box-shadow: var(--shadow-error); }
.metric-box.metric-warning { background: linear-gradient(135deg, var(--color-warning), var(--color-warning-hover)); }
.metric-box.metric-dark    { background: linear-gradient(135deg, var(--prim-sidebar-800), var(--prim-sidebar-700)); box-shadow: var(--shadow-md); }

.metric-box .metric-value {
    font-size: var(--font-size-h2);
    font-weight: var(--font-weight-bold);
    line-height: 1;
    color: #fff !important;
}
.metric-box .metric-label {
    font-size: var(--font-size-body-xs);
    opacity: 0.85;
    margin-top: var(--space-1);
    color: #fff !important;
    letter-spacing: var(--letter-spacing-wide);
    text-transform: uppercase;
}

.metric-box-sm {
    padding: var(--space-2) var(--space-3);
}
.metric-box-sm .metric-value { font-size: var(--font-size-h4); }
.metric-box-sm .metric-label { font-size: var(--font-size-caption); }


/* ============================================================
   16. EMPTY STATES
   ============================================================ */
.ds-empty {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    padding: var(--space-16) var(--space-8);
    text-align: center;
    color: var(--color-text-secondary);
}

.ds-empty-icon {
    font-size: 3rem;
    color: var(--color-border);
    margin-bottom: var(--space-4);
}

.ds-empty-title {
    font-size: var(--font-size-h4);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
    margin-bottom: var(--space-2);
}

.ds-empty-description {
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
    max-width: 380px;
    margin-bottom: var(--space-6);
}


/* ============================================================
   17. UTILITY CLASSES
   ============================================================ */

/* ── Spacing */
.ds-mt-0  { margin-top: var(--space-0) !important; }
.ds-mt-2  { margin-top: var(--space-2) !important; }
.ds-mt-4  { margin-top: var(--space-4) !important; }
.ds-mt-6  { margin-top: var(--space-6) !important; }
.ds-mt-8  { margin-top: var(--space-8) !important; }
.ds-mb-0  { margin-bottom: var(--space-0) !important; }
.ds-mb-2  { margin-bottom: var(--space-2) !important; }
.ds-mb-4  { margin-bottom: var(--space-4) !important; }
.ds-mb-6  { margin-bottom: var(--space-6) !important; }
.ds-mb-8  { margin-bottom: var(--space-8) !important; }
.ds-p-4   { padding: var(--space-4) !important; }
.ds-p-5   { padding: var(--space-5) !important; }
.ds-p-6   { padding: var(--space-6) !important; }
.ds-gap-2 { gap: var(--space-2) !important; }
.ds-gap-3 { gap: var(--space-3) !important; }
.ds-gap-4 { gap: var(--space-4) !important; }
.ds-pt-2  { padding-top: var(--space-2) !important; }
.ds-pt-3  { padding-top: var(--space-3) !important; }

/* ── Layout */
.ds-flex        { display: flex !important; }
.ds-inline-flex { display: inline-flex !important; }
.ds-grid        { display: grid !important; }
.ds-block       { display: block !important; }
.ds-hidden      { display: none !important; }

.ds-flex-center  { align-items: center; justify-content: center; }
.ds-flex-between { justify-content: space-between; }
.ds-flex-end     { justify-content: flex-end; }
.ds-items-center  { align-items: center !important; }
.ds-items-start   { align-items: flex-start !important; }
.ds-items-end     { align-items: flex-end !important; }
.ds-flex-wrap     { flex-wrap: wrap !important; }
.ds-flex-1        { flex: 1 !important; }
.ds-shrink-0      { flex-shrink: 0 !important; }
.ds-flex-column   { flex-direction: column !important; }
.ds-align-self-end { align-self: flex-end !important; }

.ds-w-full  { width: 100% !important; }
.ds-h-full  { height: 100% !important; }

/* ── Background */
.ds-bg-surface   { background-color: var(--color-bg-surface) !important; }
.ds-bg-canvas    { background-color: var(--color-bg-canvas) !important; }
.ds-bg-elevated  { background-color: var(--color-bg-elevated) !important; }
.ds-bg-brand     { background-color: var(--color-brand-subtle) !important; }

/* ── Border */
.ds-border       { border: 1px solid var(--color-border) !important; }
.ds-border-brand { border: 1px solid var(--color-brand-border) !important; }
.ds-rounded-sm   { border-radius: var(--radius-sm) !important; }
.ds-rounded-md   { border-radius: var(--radius-md) !important; }
.ds-rounded-lg   { border-radius: var(--radius-lg) !important; }
.ds-rounded-xl   { border-radius: var(--radius-xl) !important; }
.ds-rounded-full { border-radius: var(--radius-full) !important; }

/* ── Shadow */
.ds-shadow-sm { box-shadow: var(--shadow-sm) !important; }
.ds-shadow-md { box-shadow: var(--shadow-md) !important; }
.ds-shadow-lg { box-shadow: var(--shadow-lg) !important; }
.ds-shadow-none { box-shadow: none !important; }

/* ── Overflow */
.ds-overflow-hidden { overflow: hidden !important; }
.ds-overflow-auto   { overflow: auto !important; }

/* ── Position */
.ds-relative { position: relative !important; }
.ds-absolute { position: absolute !important; }
.ds-sticky   { position: sticky !important; }

/* ── Divider */
.ds-divider {
    border: none;
    border-top: 1px solid var(--color-border);
    margin: var(--space-5) 0;
}
.ds-divider-vertical {
    width: 1px;
    background-color: var(--color-border);
    align-self: stretch;
    margin: 0 var(--space-3);
}

/* ── Grid layouts */
.ds-grid-2 { display: grid; grid-template-columns: repeat(2, 1fr); gap: var(--space-4); }
.ds-grid-3 { display: grid; grid-template-columns: repeat(3, 1fr); gap: var(--space-4); }
.ds-grid-4 { display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--space-4); }
.ds-grid-auto { display: grid; grid-template-columns: repeat(auto-fill, minmax(280px, 1fr)); gap: var(--space-4); }

@media (max-width: 768px) {
    .ds-grid-2, .ds-grid-3, .ds-grid-4 { grid-template-columns: 1fr; }
    .ds-grid-auto { grid-template-columns: 1fr; }
}

@media (min-width: 769px) and (max-width: 991px) {
    .ds-grid-3, .ds-grid-4 { grid-template-columns: repeat(2, 1fr); }
}


/* ============================================================
   18. EMPTY STATES & ERROR BOUNDARIES
   ============================================================ */

/* Empty state — for lists/tables/pages with no data */
.ds-empty-state {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    text-align: center;
    padding: var(--space-10) var(--space-6);
    color: var(--color-text-muted);
}

.ds-empty-state i,
.ds-empty-state .ds-empty-icon {
    font-size: 3rem;
    margin-bottom: var(--space-4);
    opacity: 0.4;
}

.ds-empty-state .ds-empty-title {
    font-size: var(--font-size-body-lg);
    font-weight: var(--font-weight-semibold);
    color: var(--color-text-secondary);
    margin-bottom: var(--space-2);
}

.ds-empty-state .ds-empty-desc {
    font-size: var(--font-size-body-sm);
    max-width: 320px;
    margin-bottom: var(--space-5);
}

.ds-empty-state .btn {
    margin-top: var(--space-2);
}

/* Error boundary — for API failures / load errors */
.ds-error-boundary {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    text-align: center;
    padding: var(--space-8) var(--space-6);
    border: 1px dashed var(--color-error);
    border-radius: var(--radius-lg);
    background-color: var(--color-bg-surface);
}

.ds-error-boundary i {
    font-size: 2.5rem;
    color: var(--color-error);
    margin-bottom: var(--space-3);
    opacity: 0.6;
}

.ds-error-boundary .ds-error-title {
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-semibold);
    color: var(--color-text-primary);
    margin-bottom: var(--space-1);
}

.ds-error-boundary .ds-error-desc {
    font-size: var(--font-size-body-sm);
    color: var(--color-text-muted);
    margin-bottom: var(--space-4);
    max-width: 360px;
}


/* ============================================================
   19. ANIMATIONS
   ============================================================ */
@keyframes ds-spin {
    to { transform: rotate(360deg); }
}

@keyframes ds-skeleton {
    0%   { background-position: 200% 0; }
    100% { background-position: -200% 0; }
}

@keyframes ds-progress-stripes {
    to { background-position-x: 1rem; }
}

@keyframes ds-fade-in {
    from { opacity: 0; }
    to   { opacity: 1; }
}

@keyframes ds-fade-out {
    from { opacity: 1; }
    to   { opacity: 0; }
}

@keyframes ds-slide-up {
    from { opacity: 0; transform: translateY(16px) scale(0.98); }
    to   { opacity: 1; transform: translateY(0) scale(1); }
}

@keyframes ds-slide-in-right {
    from { opacity: 0; transform: translateX(24px); }
    to   { opacity: 1; transform: translateX(0); }
}

@keyframes ds-pulse {
    0%, 100% { opacity: 1; }
    50%       { opacity: 0.5; }
}

@keyframes ds-soft-highlight {
    0% {
        opacity: 1;
        transform: translateY(0);
        outline-color: transparent;
    }
    35% {
        opacity: 1;
        transform: translateY(-2px);
        outline-color: rgba(3, 152, 172, 0.32);
    }
    100% {
        opacity: 1;
        transform: translateY(0);
        outline-color: transparent;
    }
}

/* Motion utilities */
.ds-revealable {
    opacity: 0;
    transform: translateY(12px);
    filter: saturate(0.96);
    transition:
        opacity var(--duration-normal) var(--ease-decelerate),
        transform var(--duration-normal) var(--ease-decelerate),
        filter var(--duration-normal) var(--ease-decelerate);
    will-change: opacity, transform;
}

.ds-revealable.is-visible {
    opacity: 1;
    transform: translateY(0);
    filter: none;
}

.ds-updated-pulse {
    outline: 1px solid transparent;
    animation: ds-soft-highlight 0.9s var(--ease-standard);
}

/* Reduced motion */
@media (prefers-reduced-motion: reduce) {
    *, *::before, *::after {
        animation-duration: 0.01ms !important;
        animation-iteration-count: 1 !important;
        transition-duration: 0.01ms !important;
    }
}


/* ============================================================
   PREPARE FLOW — Progressive-disclosure phase cards (microl.ai /microlai)
   Calm, guided one-decision-at-a-time UX. Tokens in design-tokens.css.
   ============================================================ */
.prepare-phases {
    display: flex;
    flex-direction: column;
    gap: var(--space-3);
}

.phase-card {
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    background: var(--color-surface);
    overflow: hidden;
    transition:
        border-color var(--motion-phase-exit) var(--ease-standard),
        box-shadow   var(--motion-phase-exit) var(--ease-standard),
        opacity      var(--motion-phase-enter) var(--ease-soft-out),
        transform    var(--motion-phase-enter) var(--ease-soft-out);
}

/* Phase that has not been reached yet is not rendered at all */
.phase-card[hidden] { display: none; }

/* First mount: start a touch lower + transparent, then settle in */
.phase-card.is-entering { opacity: 0; transform: translateY(10px); }

.phase-card.phase--active {
    border-color: var(--color-brand);
    box-shadow: var(--shadow-md);
}

/* ── Header (also the collapsed-summary affordance) */
.phase-header {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    padding: var(--space-3) var(--space-4);
    user-select: none;
    transition: background var(--duration-fast) var(--ease-standard);
}
.phase-card.phase--done .phase-header,
.phase-card.phase--reachable .phase-header { cursor: pointer; }
.phase-card.phase--done .phase-header:hover,
.phase-card.phase--reachable .phase-header:hover { background: var(--color-surface-muted); }

.phase-index {
    flex: 0 0 auto;
    width: 1.75rem;
    height: 1.75rem;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: 50%;
    font-weight: var(--font-weight-semibold);
    font-size: 0.85rem;
    background: var(--color-surface-muted);
    color: var(--color-text-secondary);
    transition:
        background var(--duration-normal) var(--ease-standard),
        color      var(--duration-normal) var(--ease-standard);
}
.phase--active .phase-index { background: var(--color-brand); color: #fff; }
.phase--done   .phase-index { background: var(--color-success); color: #fff; }

.phase-title {
    font-weight: var(--font-weight-semibold);
    color: var(--color-text);
}
.phase-summary {
    margin-left: auto;
    color: var(--color-text-secondary);
    font-size: 0.85rem;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    max-width: 55%;
    transition: opacity var(--duration-fast) var(--ease-standard);
}
/* Summary only matters while collapsed */
.phase--active .phase-summary { opacity: 0; }

/* Collapsed-summary rendered as a small pill badge */
.phase-summary-badge {
    display: inline-block;
    padding: 1px 8px;
    border-radius: 999px;
    font-size: 0.72rem;
    font-weight: var(--font-weight-medium);
    line-height: 1.5;
    background: var(--color-surface-muted);
    color: var(--color-text-secondary);
    border: 1px solid var(--color-border);
}


.phase-chevron {
    margin-left: var(--space-2);
    color: var(--color-text-secondary);
    transition: transform var(--duration-normal) var(--ease-standard);
}
.phase--active .phase-chevron { transform: rotate(180deg); }

/* ── Body: grid-rows trick gives smooth auto-height fade without max-height hacks */
.phase-body {
    display: grid;
    grid-template-rows: 0fr;
    opacity: 0;
    transform: translateY(6px);
    transition:
        grid-template-rows var(--motion-phase-exit) var(--ease-accelerate),
        opacity            var(--motion-phase-exit) var(--ease-accelerate),
        transform          var(--motion-phase-exit) var(--ease-accelerate);
}
/* The grid track resolves to minmax(auto, 0fr); the clipped child must carry NO
   padding/border or its min-content (= padding) keeps the track from reaching 0.
   Padding lives on an inner wrapper instead. */
.phase-body > .phase-body-inner {
    overflow: hidden;
    min-height: 0;
}
.phase--active .phase-body {
    grid-template-rows: 1fr;
    opacity: 1;
    transform: translateY(0);
    transition:
        grid-template-rows var(--motion-phase-enter) var(--ease-soft-out),
        opacity            var(--motion-phase-enter) var(--ease-soft-out),
        transform          var(--motion-phase-enter) var(--ease-soft-out);
}
.phase-body-pad { padding: 0 var(--space-4) var(--space-4); }

/* ── Compact object mini-cards (phase 2): name + class badge, detail collapsed */
.object-mini-cards {
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
    margin-bottom: var(--space-3);
}
.object-mini-card {
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-surface);
    opacity: 0;
    transform: translateY(8px);
    animation: miniCardIn var(--motion-item-enter) var(--ease-soft-out) forwards;
    animation-delay: calc(var(--i, 0) * var(--motion-stagger));
}
@keyframes miniCardIn { to { opacity: 1; transform: translateY(0); } }

.object-mini-card__head {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    padding: var(--space-2) var(--space-3);
    cursor: pointer;
    min-height: 44px;
}
/* Two-line main column: filename on top (gets full width), class chip below */
.object-mini-card__main {
    flex: 1 1 auto;
    min-width: 0;
    display: flex;
    flex-direction: column;
    gap: 3px;
}
.object-mini-card__name {
    font-weight: var(--font-weight-medium);
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}
.object-mini-card__tags {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    min-width: 0;
}
.object-mini-card__tags .classification-object-badge,
.object-mini-card__tags .badge {
    max-width: 100%;
}
.object-mini-card__chevron {
    flex: 0 0 auto;
    color: var(--color-text-secondary);
    transition: transform var(--duration-fast) var(--ease-standard);
}
.object-mini-card.is-open .object-mini-card__chevron { transform: rotate(90deg); }

/* Status icon — subtle vector glyph (no emoji) */
.object-mini-card__status {
    flex: 0 0 auto;
    display: inline-flex;
    align-items: center;
    font-size: 0.9rem;
}

/* Delete — quiet ghost icon inside the row (overrides the legacy absolute red box) */
.object-mini-card__head .object-card-delete {
    position: static;
    flex: 0 0 auto;
    width: 32px;
    height: 32px;
    background: transparent;
    color: var(--color-text-muted);
    border: none;
    border-radius: var(--radius-sm);
    transition:
        color var(--duration-fast) var(--ease-standard),
        background var(--duration-fast) var(--ease-standard);
}
.object-mini-card__head .object-card-delete:hover {
    background: var(--color-error-subtle, rgba(234, 84, 85, 0.12));
    color: var(--color-error);
    transform: none;
}

/* Edit pencil on the class badge — reveal on hover to keep the row uncluttered
   (badge itself stays tappable, so touch users can still edit). */
.object-mini-card__head .classification-badge-edit-indicator {
    margin-left: 2px;
    opacity: 0;
    transition: opacity var(--duration-fast) var(--ease-standard);
}
.object-mini-card:hover .object-mini-card__head .classification-badge-edit-indicator,
.object-mini-card__head .classification-badge-clickable:focus-visible .classification-badge-edit-indicator {
    opacity: 0.6;
}

/* Tray switcher — only rendered when there is more than one tray */
.prepare-tray-nav { display: flex; flex-wrap: wrap; gap: var(--space-2); }

.object-mini-card__detail {
    display: grid;
    grid-template-rows: 0fr;
    opacity: 0;
    transition:
        grid-template-rows var(--duration-normal) var(--ease-standard),
        opacity            var(--duration-normal) var(--ease-standard);
}
.object-mini-card__detail > .object-mini-card__detail-inner { overflow: hidden; min-height: 0; }
.object-mini-card.is-open .object-mini-card__detail { grid-template-rows: 1fr; opacity: 1; }
.object-mini-card__detail-pad { padding: 0 var(--space-3) var(--space-3); }

/* ── Incoherence indicator (phase 3): icon + text, never colour-only */
.incoherence-indicator {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    color: var(--color-warning-text);
    font-size: 0.8rem;
    opacity: 0;
    transform: scale(0.9);
    animation: incoherenceIn var(--duration-normal) var(--ease-soft-out) forwards;
}
@keyframes incoherenceIn { to { opacity: 1; transform: scale(1); } }
.incoherence-banner {
    margin-top: var(--space-2);
    padding: var(--space-2) var(--space-3);
    border: 1px solid var(--color-warning-border);
    background: var(--color-warning-subtle);
    border-radius: var(--radius-md);
    color: var(--color-warning-text);
    font-size: 0.8rem;
    display: flex;
    align-items: flex-start;
    gap: var(--space-2);
}
.incoherence-banner__content {
    display: flex;
    flex-direction: column;
    align-items: flex-start;
    gap: var(--space-2);
    min-width: 0;
}
/* Informational tone of the same inline banner (e.g. modals/forms). Same size,
   padding, radius and layout as the sidebar warnings — only the colour changes. */
.incoherence-banner--info {
    border-color: var(--color-info-border);
    background: var(--color-info-subtle);
    color: var(--color-info-text);
}
.incoherence-banner > i { margin-top: 1px; flex-shrink: 0; }
/* Mini CTA inside the resin warning ("I've changed the resin") */
.incoherence-cta {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    font-size: 0.74rem;
    font-weight: var(--font-weight-semibold);
    padding: 5px 12px;
    line-height: 1.4;
    background: var(--color-bg-surface);
    border: 1px solid var(--color-warning-border);
    color: var(--color-warning-text);
    border-radius: var(--radius-md);
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.06);
    transition: background var(--duration-fast) var(--ease-standard), border-color var(--duration-fast) var(--ease-standard);
}
.incoherence-cta:hover {
    background: var(--color-warning-subtle);
    border-color: var(--color-warning);
    color: var(--color-warning-text);
}
.incoherence-cta i { color: var(--color-warning); }

/* Logo contrast chips — set by shared/logo_contrast.js from the logo luminance. */
.logo-on-dark { background: var(--prim-neutral-800, #232838) !important; }
.logo-on-light { background: #ffffff !important; }
.profile-context-row.has-incoherence .profile-context-value { color: var(--color-warning-text); }

/* ── Resin tank seen from above (phase 3): tank name on top, resin-coloured vat,
      resin name inside. Fill is a lightened tint of the DB resin colour. */
.tank-visual { margin-bottom: var(--space-3); }
.tank-visual__head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-2);
    margin-bottom: var(--space-1);
    min-height: 24px;
}
.tank-visual__refresh {
    flex: 0 0 auto;
    width: 28px;
    height: 28px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    padding: 0;
    border: none;
    background: transparent;
    color: var(--color-text-secondary);
    border-radius: var(--radius-sm);
    cursor: pointer;
    transition:
        color var(--duration-fast) var(--ease-standard),
        background var(--duration-fast) var(--ease-standard);
}
.tank-visual__refresh:hover {
    background: var(--color-surface-muted);
    color: var(--color-brand);
}
.tank-visual__label {
    font-size: 0.7rem;
    font-weight: var(--font-weight-semibold);
    letter-spacing: 0.06em;
    text-transform: uppercase;
    color: var(--color-text-secondary);
    margin-bottom: 0;
}
.tank-visual__vat {
    position: relative;
    display: flex;
    align-items: center;
    gap: var(--space-2);
    min-height: 52px;
    padding: var(--space-3);
    border-radius: 5px;
    /* Fill is a light tint of the resin colour; border a slightly darker tint of the
       same hue (set as custom props by renderTankVisual) → "fill like the border, lighter". */
    background: var(--tank-fill, var(--color-surface));
    border: 1px solid var(--tank-border, var(--color-border));
    box-shadow: var(--shadow-inner);
}
/* Dashed inset evokes the tank film / build area */
.tank-visual__vat::before {
    content: "";
    position: absolute;
    inset: 5px;
    border-radius: 2px;
    border: 1px dashed rgba(0, 0, 0, 0.12);
    pointer-events: none;
}
.tank-visual__vat.is-empty { background: var(--color-surface-muted); }
.tank-visual__vat.is-empty::before { display: none; }
/* Last so it wins for empty+incoherence: faint warning fill that matches the warning border */
.tank-visual__vat.has-incoherence {
    background: var(--color-warning-subtle);
    border-color: var(--color-warning-border);
    box-shadow: inset 0 0 0 1px var(--color-warning-border);
}
.tank-visual__swatch {
    flex: 0 0 auto;
    width: 14px;
    height: 14px;
    border-radius: 50%;
    border: 1px solid rgba(0, 0, 0, 0.18);
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.12);
}
.tank-visual__resin {
    position: relative;
    font-weight: var(--font-weight-medium);
    line-height: 1.3;
    color: #1f2937;            /* dark text — the vat fill is always a light tint */
}
.tank-visual__vat.is-empty .tank-visual__resin { color: var(--color-text-muted); }

/* ============================================================
   TANK WIDGET — unified resin-tank component (minimal: /microlai, full: Monitoriza)
   Resin colour is borrowed via --tankw-fill / --tankw-border (set by TankWidget.render).
   ============================================================ */
.tankw {
    --tankw-fill: var(--color-surface-muted);
    --tankw-border: var(--color-border);
    border: 1px solid var(--color-border);
    border-radius: 10px;
    background: var(--color-surface);
    overflow: hidden;
}
.tankw__logo {
    flex: 0 0 auto;
    border-radius: 50%;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    background: #fff;
    border: 1px solid rgba(148, 163, 184, 0.35);
    overflow: hidden;
}
.tankw__logo img { width: 75%; height: 75%; object-fit: contain; }
.tankw__logo i { color: var(--color-text-muted); }
.tankw__rinfo { flex: 1 1 auto; min-width: 0; }
.tankw__rname {
    font-weight: var(--font-weight-semibold);
    color: var(--color-text);
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}
.tankw__mfr, .tankw__minfilm {
    display: block;
    font-size: 0.72rem;
    color: var(--color-text-secondary);
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}
/* Tank-name badge above the resin name (minimal variant) */
.tankw__tankbadge {
    display: inline-block;
    max-width: 100%;
    margin-bottom: 3px;
    padding: 0 7px;
    font-size: 0.62rem;
    font-weight: var(--font-weight-semibold);
    letter-spacing: 0.04em;
    text-transform: uppercase;
    line-height: 1.6;
    color: var(--color-text-secondary);
    background: rgba(255, 255, 255, 0.6);
    border: 1px solid var(--color-border);
    border-radius: 999px;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    vertical-align: top;
}

.tankw__btn {
    flex: 0 0 auto;
    width: 34px;
    height: 34px;
    border: 1px solid rgba(0, 0, 0, 0.10);
    background: rgba(255, 255, 255, 0.65);
    color: var(--color-text-secondary);
    border-radius: 8px;
    cursor: pointer;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    transition: color var(--duration-fast) var(--ease-standard), background var(--duration-fast) var(--ease-standard);
}
.tankw__btn:hover { color: var(--color-brand); background: #fff; }

/* ── Minimal variant (single tinted row) */
.tankw--min {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    padding: var(--space-2) var(--space-3);
    background: var(--tankw-fill);
    border-color: var(--tankw-border);
}
.tankw--min .tankw__logo { width: 34px; height: 34px; }
.tankw--min .tankw__logo i { font-size: 0.95rem; }
.tankw--min .tankw__rname { font-size: 0.9rem; }
.tankw--min.has-incoherence {
    border-color: var(--color-warning-border);
    box-shadow: inset 0 0 0 1px var(--color-warning-border);
}

/* ── Full variant (header + tinted resin card + film bar) */
.tankw--full .tankw__head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-2);
    padding: var(--space-2) var(--space-3);
}
.tankw__title { display: flex; align-items: center; gap: var(--space-1); min-width: 0; }
.tankw__title > i { color: var(--color-brand); }
.tankw__label { font-size: 0.7rem; font-weight: var(--font-weight-semibold); letter-spacing: 0.05em; text-transform: uppercase; color: var(--color-text-secondary); }
.tankw__detbadge {
    display: inline-flex; align-items: center; gap: 4px;
    font-size: 0.62rem; font-weight: var(--font-weight-semibold);
    padding: 2px 8px; border-radius: var(--radius-full);
    background: var(--color-success-subtle); color: var(--color-success-text);
    text-transform: uppercase; letter-spacing: 0.03em; white-space: nowrap;
}
.tankw__detbadge.is-last { background: var(--color-bg-elevated); color: var(--color-text-secondary); }
.tankw__head .tankw__title { flex-wrap: wrap; gap: 4px 8px; }
.tankw__name { font-weight: var(--font-weight-semibold); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.tankw__pencil { font-size: 0.7rem; color: var(--color-text-muted); margin-left: 2px; }
.tankw__badge { flex: 0 0 auto; font-size: 0.7rem; font-weight: var(--font-weight-semibold); padding: 2px 8px; border-radius: 999px; }
.tankw__badge.badge-ok { background: var(--color-success-subtle); color: var(--color-success-text); border: 1px solid var(--color-success-border); }
.tankw__badge.badge-warn { background: var(--color-warning-subtle); color: var(--color-warning-text); border: 1px solid var(--color-warning-border); }
.tankw__badge.badge-danger { background: var(--color-error-subtle, rgba(234,84,85,0.12)); color: var(--color-error); border: 1px solid var(--color-error); }
.tankw--full .tankw__resin {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    margin: 0 var(--space-3) var(--space-3);
    padding: var(--space-3);
    border-radius: 8px;
    background: var(--tankw-fill);
    border: 1px solid var(--tankw-border);
}
.tankw--full .tankw__logo { width: 48px; height: 48px; }
.tankw--full .tankw__logo i { font-size: 1.3rem; }
.tankw__film { padding: 0 var(--space-3) var(--space-3); }
.tankw__film-top { display: flex; justify-content: space-between; align-items: center; margin-bottom: 4px; }
.tankw__film-top small { font-size: 0.72rem; color: var(--color-text-secondary); }
.tankw__film-track { height: 8px; border-radius: 999px; background: var(--color-surface-muted); overflow: hidden; }
.tankw__film-barrow { display: flex; align-items: center; gap: var(--space-2); }
.tankw__film-barrow .tankw__film-track { flex: 1 1 auto; }
.tankw__filmreset {
    flex: 0 0 auto; width: 26px; height: 26px; padding: 0; font-size: 0.75rem;
    display: inline-flex; align-items: center; justify-content: center; cursor: pointer;
    background: transparent; border: 1px solid var(--color-border);
    border-radius: var(--radius-sm); color: var(--color-text-muted);
    transition: color var(--duration-fast) var(--ease-standard), background var(--duration-fast) var(--ease-standard), border-color var(--duration-fast) var(--ease-standard);
}
.tankw__filmreset:hover { color: var(--color-brand); border-color: var(--color-brand); background: var(--color-bg-elevated); }
.tankw__film-fill { height: 100%; border-radius: 999px; transition: width var(--duration-slow) var(--ease-standard); }

/* ============================================================
   PREPARE LOADING OVERLAY — shown until workspace + tray STLs finish loading
   ============================================================ */
.prepare-page { position: relative; }
.prepare-loading-overlay {
    position: absolute;
    inset: 0;
    z-index: 50;
    display: flex;
    align-items: center;
    justify-content: center;
    background: rgba(255, 255, 255, 0.72);
    backdrop-filter: blur(2px);
    -webkit-backdrop-filter: blur(2px);
    transition: opacity 0.32s var(--ease-standard);
}
[data-theme="dark"] .prepare-loading-overlay { background: rgba(20, 22, 34, 0.72); }
.prepare-loading-overlay.is-hidden { opacity: 0; pointer-events: none; }
.prepare-loading-overlay[hidden] { display: none; }
.prepare-loading-overlay__inner {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: var(--space-3);
}
.prepare-loading-overlay__spinner {
    width: 42px;
    height: 42px;
    border: 3px solid var(--color-border);
    border-top-color: var(--color-brand);
    border-radius: 50%;
    animation: prepareSpin 0.8s linear infinite;
}
@keyframes prepareSpin { to { transform: rotate(360deg); } }
.prepare-loading-overlay__msg {
    color: var(--color-text-secondary);
    font-weight: var(--font-weight-medium);
    font-size: 0.9rem;
}
@media (prefers-reduced-motion: reduce) {
    .prepare-loading-overlay__spinner { animation-duration: 1.6s; }
    .prepare-loading-overlay { transition: none; }
}

/* ============================================================
   20. GLOBAL A11Y FIXES (UI/UX Audit 2026-03-10)
   ============================================================ */

/* ── Touch targets: ensure 44px min on touch devices */
@media (pointer: coarse) {
    .btn-sm, .ds-btn-sm {
        min-height: 44px;
        min-width: 44px;
    }

    .btn-icon.btn-sm {
        min-width: 44px;
        min-height: 44px;
        padding: var(--space-2);
    }

    .btn-close {
        min-width: 44px;
        min-height: 44px;
        padding: var(--space-3) !important;
    }

    /* Close buttons in modals (custom &times; pattern) */
    .close-btn {
        min-width: 44px;
        min-height: 44px;
    }

    /* Checkboxes and radio */
    .form-check-input {
        min-width: 24px;
        min-height: 24px;
    }
}

/* ── Global focus-visible (supplement existing rules) */
.btn-close:focus-visible,
.close-btn:focus-visible,
.form-select:focus-visible,
.dropdown-toggle:focus-visible,
.dropdown-item:focus-visible,
.list-group-item:focus-visible,
.nav-link:focus-visible {
    outline: 2px solid var(--color-border-focus);
    outline-offset: 2px;
    box-shadow: 0 0 0 4px var(--color-focus-ring);
}

/* ── Tabular figures for numeric displays */
.tabular-nums,
[data-numeric],
.metric-value,
.metric-value-sm,
.metric-subvalue,
.stat-value {
    font-variant-numeric: tabular-nums;
}

/* ── Table header accessibility */
table th {
    scope: col; /* CSS can't set attributes, but hint for devs */
}

/* ── Skip link ensure visibility on focus */
.skip-link:focus {
    clip: auto !important;
    clip-path: none !important;
    width: auto !important;
    height: auto !important;
    position: fixed;
    top: var(--space-2);
    left: var(--space-2);
    z-index: 10000;
    padding: var(--space-2) var(--space-4);
    background: var(--color-bg-surface);
    color: var(--color-text-brand);
    border: 2px solid var(--color-border-focus);
    border-radius: var(--radius-md);
    box-shadow: var(--shadow-lg);
}


/* ============================================================
   21. FLUTTER DARK THEME OVERRIDES
   ============================================================
 * Traduce el DNA visual del Flutter DarkModeTheme a la webapp.
 * Activo vía [data-theme="dark"] o prefers-color-scheme: dark.
 *
 * Principios:
 *   - Topbar plana navy (no gradiente cian)
 *   - Elevación por white overlay, no por sombras negras
 *   - Inputs con fondo azul-oscuro (#4B547D)
 *   - Temperatura de texto fría azul-gris en toda la jerarquía
 *   - Brand cian como único acento luminoso
 *
 * Ver: docs/FLUTTER_DARK_THEME_PLAN.md
 * ============================================================ */

/* ── Fase 2: Topbar dark — flat navy + línea cian ── */

[data-theme="dark"] .topbar,
[data-theme="dark"] #topbar {
    background: var(--color-topbar-bg) !important;
    background-image: none !important;
    border-bottom: 1px solid var(--color-brand) !important;
    box-shadow: 0 2px 12px rgba(3, 152, 172, 0.12);
}

[data-theme="dark"] .topbar-title,
[data-theme="dark"] .topbar-brand {
    color: var(--color-text-primary);
}

/* Accent cian para el nombre/logo en topbar dark */
[data-theme="dark"] .topbar-brand span,
[data-theme="dark"] .topbar-brand-accent {
    color: var(--color-brand);
}

/* Botones/acciones en topbar dark */
[data-theme="dark"] .topbar-actions .btn,
[data-theme="dark"] .topbar-actions button {
    color: var(--color-text-primary);
}

[data-theme="dark"] .topbar-actions .btn:hover,
[data-theme="dark"] .topbar-actions button:hover {
    background-color: rgba(255, 255, 255, 0.07);
}

/* Sidebar toggle icon en dark */
[data-theme="dark"] .sidebar-toggle {
    color: var(--color-text-primary);
}
[data-theme="dark"] .sidebar-toggle:hover {
    background-color: rgba(255, 255, 255, 0.08);
}

@media (prefers-color-scheme: dark) {
    :root:not([data-theme="light"]) .topbar,
    :root:not([data-theme="light"]) #topbar {
        background: var(--color-topbar-bg) !important;
        background-image: none !important;
        border-bottom: 1px solid var(--color-brand) !important;
        box-shadow: 0 2px 12px rgba(3, 152, 172, 0.12);
    }
}


/* ── Fase 3: Card elevation system dark — overlay blanco ── */

/* Cards base: overlay sutil sobre surface */
[data-theme="dark"] .card,
[data-theme="dark"] .ds-card {
    background-color: var(--color-bg-surface-overlay);
    border-color: var(--color-border);
    box-shadow: var(--shadow-sm);
}

/* Card hover: borde cian tonal */
[data-theme="dark"] .card:hover,
[data-theme="dark"] .ds-card:hover {
    border-color: rgba(3, 152, 172, 0.30);
    box-shadow: var(--shadow-md);
}

/* Card elevated: un nivel más de profundidad */
[data-theme="dark"] .card-elevated,
[data-theme="dark"] .ds-card--elevated {
    background-color: var(--prim-neutral-750);
    border: 1px solid rgba(3, 152, 172, 0.15);
    box-shadow: var(--shadow-md);
}

/* Card brand: acento de tope cian */
[data-theme="dark"] .card-brand,
[data-theme="dark"] .ds-card--brand {
    border-top: 2px solid var(--color-brand);
}

/* Card header dentro de dark */
[data-theme="dark"] .card-header {
    background-color: rgba(255, 255, 255, 0.03);
    border-bottom-color: var(--color-border);
}

[data-theme="dark"] .card-footer {
    background-color: rgba(255, 255, 255, 0.02);
    border-top-color: var(--color-border);
}

/* Metric boxes y KPI cards */
[data-theme="dark"] .metric-box,
[data-theme="dark"] .kpi-card,
[data-theme="dark"] .stat-card {
    background-color: var(--color-bg-surface-overlay);
    border-color: var(--color-border);
    box-shadow: var(--shadow-sm);
}

/* Modales dark: navy sólido + borde sutil */
[data-theme="dark"] .modal-content {
    background-color: var(--prim-neutral-800);
    border: 1px solid var(--color-border);
    box-shadow: var(--shadow-xl), 0 0 0 1px rgba(255, 255, 255, 0.04);
}

[data-theme="dark"] .modal-header {
    border-bottom-color: var(--color-border);
    background-color: rgba(255, 255, 255, 0.02);
}

[data-theme="dark"] .modal-footer {
    border-top-color: var(--color-border);
    background-color: rgba(255, 255, 255, 0.02);
}

/* Backdrop con blur (glassmorphism overlay) */
[data-theme="dark"] .modal-backdrop {
    background-color: rgba(0, 0, 0, 0.65);
    backdrop-filter: blur(4px);
    -webkit-backdrop-filter: blur(4px);
}

/* Dropdowns dark */
[data-theme="dark"] .dropdown-menu {
    background-color: var(--prim-neutral-800);
    border-color: var(--color-border);
    box-shadow: var(--shadow-lg);
}

[data-theme="dark"] .dropdown-item {
    color: var(--color-text-primary);
}

[data-theme="dark"] .dropdown-item:hover,
[data-theme="dark"] .dropdown-item:focus {
    background-color: rgba(3, 152, 172, 0.10);
    color: var(--color-text-primary);
}

[data-theme="dark"] .dropdown-divider {
    border-top-color: var(--color-border);
}

@media (prefers-color-scheme: dark) {
    :root:not([data-theme="light"]) .card,
    :root:not([data-theme="light"]) .ds-card {
        background-color: var(--color-bg-surface-overlay);
        border-color: var(--color-border);
    }
    :root:not([data-theme="light"]) .modal-content {
        background-color: var(--prim-neutral-800);
        border: 1px solid var(--color-border);
    }
    :root:not([data-theme="light"]) .modal-backdrop {
        background-color: rgba(0, 0, 0, 0.65);
        backdrop-filter: blur(4px);
        -webkit-backdrop-filter: blur(4px);
    }
}


/* ── Fase 4: Form inputs dark — fondo azul-oscuro Flutter ── */

[data-theme="dark"] input[type="text"],
[data-theme="dark"] input[type="email"],
[data-theme="dark"] input[type="password"],
[data-theme="dark"] input[type="number"],
[data-theme="dark"] input[type="date"],
[data-theme="dark"] input[type="datetime-local"],
[data-theme="dark"] input[type="time"],
[data-theme="dark"] input[type="search"],
[data-theme="dark"] input[type="tel"],
[data-theme="dark"] input[type="url"],
[data-theme="dark"] textarea,
[data-theme="dark"] select,
[data-theme="dark"] .form-control,
[data-theme="dark"] .form-select,
[data-theme="dark"] .ds-input {
    background-color: var(--color-bg-input);
    border-color: var(--color-border);
    color: var(--color-text-primary);
}

[data-theme="dark"] .form-control::placeholder,
[data-theme="dark"] .form-select::placeholder,
[data-theme="dark"] .ds-input::placeholder {
    color: var(--color-text-icon-muted);
}

[data-theme="dark"] .form-control:hover,
[data-theme="dark"] .form-select:hover,
[data-theme="dark"] .ds-input:hover {
    border-color: var(--color-border-strong);
    background-color: rgba(75, 84, 125, 0.85);
}

[data-theme="dark"] .form-control:focus,
[data-theme="dark"] .form-select:focus,
[data-theme="dark"] .ds-input:focus {
    background-color: var(--color-bg-input);
    border-color: var(--color-brand);
    box-shadow: 0 0 0 3px rgba(3, 152, 172, 0.20);
    outline: none;
}

/* Select — chevron blanco en dark */
[data-theme="dark"] select.form-control,
[data-theme="dark"] .form-select {
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='8' viewBox='0 0 12 8' fill='none'%3E%3Cpath d='M1 1L6 6L11 1' stroke='%23CFD3EC' stroke-width='1.5' stroke-linecap='round'/%3E%3C/svg%3E");
    background-repeat: no-repeat;
    background-position: right var(--space-3) center;
}

/* Checkboxes y radios */
[data-theme="dark"] .form-check-input {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
}

[data-theme="dark"] .form-check-input:checked {
    background-color: var(--color-brand);
    border-color: var(--color-brand);
}

[data-theme="dark"] .form-check-input:focus {
    border-color: var(--color-brand);
    box-shadow: 0 0 0 3px rgba(3, 152, 172, 0.20);
}

/* Input groups */
[data-theme="dark"] .input-group-text {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
    color: var(--color-text-muted);
}

/* Labels */
[data-theme="dark"] .form-label,
[data-theme="dark"] label {
    color: var(--color-text-title);
}

/* Disabled inputs */
[data-theme="dark"] .form-control:disabled,
[data-theme="dark"] .form-select:disabled,
[data-theme="dark"] input:disabled {
    background-color: var(--color-bg-unselect);
    opacity: var(--opacity-disabled);
    cursor: not-allowed;
}

/* Validation states dark */
[data-theme="dark"] .form-control.is-valid,
[data-theme="dark"] .was-validated .form-control:valid {
    border-color: var(--color-success);
    box-shadow: 0 0 0 3px rgba(40, 199, 111, 0.15);
}

[data-theme="dark"] .form-control.is-invalid,
[data-theme="dark"] .was-validated .form-control:invalid {
    border-color: var(--color-error);
    box-shadow: 0 0 0 3px rgba(234, 84, 85, 0.15);
}

@media (prefers-color-scheme: dark) {
    :root:not([data-theme="light"]) .form-control,
    :root:not([data-theme="light"]) .form-select,
    :root:not([data-theme="light"]) .ds-input {
        background-color: var(--color-bg-input);
        border-color: var(--color-border);
        color: var(--color-text-primary);
    }
    :root:not([data-theme="light"]) .form-control::placeholder {
        color: var(--color-text-icon-muted);
    }
    :root:not([data-theme="light"]) .input-group-text {
        background-color: var(--color-bg-unselect);
        border-color: var(--color-border);
        color: var(--color-text-muted);
    }
}


/* ── Fase 5: Refinamientos globales dark ── */

/* — 5.1 Botones dark — */

/* Primary: mismo cian + glow */
[data-theme="dark"] .btn-primary,
[data-theme="dark"] .ds-btn--primary {
    box-shadow: 0 2px 10px rgba(3, 152, 172, 0.30);
}

[data-theme="dark"] .btn-primary:hover,
[data-theme="dark"] .ds-btn--primary:hover {
    box-shadow: 0 4px 18px rgba(3, 152, 172, 0.45);
    transform: translateY(-1px);
}

[data-theme="dark"] .btn-primary:active,
[data-theme="dark"] .ds-btn--primary:active {
    transform: translateY(0);
    box-shadow: 0 2px 8px rgba(3, 152, 172, 0.25);
}

/* Secondary/ghost */
[data-theme="dark"] .btn-secondary,
[data-theme="dark"] .ds-btn--secondary {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
    color: var(--color-text-primary);
}

[data-theme="dark"] .btn-secondary:hover,
[data-theme="dark"] .ds-btn--secondary:hover {
    background-color: rgba(67, 73, 104, 0.6);
    border-color: var(--color-border-strong);
    color: var(--color-text-primary);
}

/* Ghost/outline dark */
[data-theme="dark"] .btn-outline-primary,
[data-theme="dark"] .ds-btn--outline {
    border-color: var(--color-brand);
    color: var(--color-brand);
    background-color: transparent;
}

[data-theme="dark"] .btn-outline-primary:hover,
[data-theme="dark"] .ds-btn--outline:hover {
    background-color: rgba(3, 152, 172, 0.12);
    color: var(--prim-cyan-400);
}

/* Danger: glow rojo */
[data-theme="dark"] .btn-danger,
[data-theme="dark"] .ds-btn--danger {
    box-shadow: 0 2px 10px rgba(234, 84, 85, 0.25);
}

[data-theme="dark"] .btn-danger:hover,
[data-theme="dark"] .ds-btn--danger:hover {
    box-shadow: 0 4px 18px rgba(234, 84, 85, 0.35);
}

/* Light/ghost buttons */
[data-theme="dark"] .btn-light,
[data-theme="dark"] .ds-btn--ghost {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
    color: var(--color-text-primary);
}


/* — 5.2 Tablas dark — */

[data-theme="dark"] .table th,
[data-theme="dark"] thead th {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
    color: var(--color-text-title);
}

[data-theme="dark"] .table td,
[data-theme="dark"] tbody td {
    border-color: rgba(67, 73, 104, 0.45);
    color: var(--color-text-primary);
}

[data-theme="dark"] .table-striped > tbody > tr:nth-of-type(odd) > * {
    background-color: rgba(255, 255, 255, 0.02);
    color: var(--color-text-primary);
}

[data-theme="dark"] .table-hover > tbody > tr:hover > * {
    background-color: rgba(3, 152, 172, 0.08);
    color: var(--color-text-primary);
}

[data-theme="dark"] .table-bordered {
    border-color: var(--color-border);
}

[data-theme="dark"] .table-bordered th,
[data-theme="dark"] .table-bordered td {
    border-color: var(--color-border);
}

/* Table footer */
[data-theme="dark"] .table tfoot td,
[data-theme="dark"] .table tfoot th {
    background-color: var(--color-bg-unselect);
    border-top-color: var(--color-border-strong);
    color: var(--color-text-secondary);
}


/* — 5.3 Badges dark (borde tonal para definición) — */

[data-theme="dark"] .badge,
[data-theme="dark"] .ds-badge {
    border: 1px solid rgba(255, 255, 255, 0.08);
}

/* Chips dark */
[data-theme="dark"] .chip,
[data-theme="dark"] .ds-chip {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
    color: var(--color-text-secondary);
}

[data-theme="dark"] .chip:hover,
[data-theme="dark"] .ds-chip:hover {
    background-color: rgba(3, 152, 172, 0.12);
    border-color: var(--color-brand);
    color: var(--prim-cyan-400);
}


/* — 5.4 Alerts dark (borde lateral de color) — */

[data-theme="dark"] .alert {
    border-left-width: 3px;
    border-left-style: solid;
}

[data-theme="dark"] .alert-success {
    border-left-color: var(--color-success);
}

[data-theme="dark"] .alert-danger,
[data-theme="dark"] .alert-error {
    border-left-color: var(--color-error);
}

[data-theme="dark"] .alert-warning {
    border-left-color: var(--color-warning);
}

[data-theme="dark"] .alert-info,
[data-theme="dark"] .alert-primary {
    border-left-color: var(--color-brand);
}


/* — 5.5 Sidebar active state refinado — */

[data-theme="dark"] .sidebar-item--active,
[data-theme="dark"] .sidebar .nav-item.active > .nav-link,
[data-theme="dark"] .sidebar .nav-link.active {
    box-shadow: inset 3px 0 0 var(--color-brand);
    background-color: rgba(3, 152, 172, 0.12);
}

[data-theme="dark"] .sidebar .nav-link:hover {
    background-color: rgba(255, 255, 255, 0.05);
}

/* Sidebar section titles dark */
[data-theme="dark"] .sidebar-section-title,
[data-theme="dark"] .nav-label {
    color: var(--color-text-unselect);
}

/* Sidebar icons muted */
[data-theme="dark"] .sidebar .nav-link:not(.active) .nav-icon,
[data-theme="dark"] .sidebar .nav-link:not(.active) i {
    color: var(--color-text-icon-muted);
}


/* — 5.6 Scrollbar dark (Flutter: #3A3E59) — */

[data-theme="dark"] ::-webkit-scrollbar-thumb {
    background-color: #3a3e59;
}

[data-theme="dark"] ::-webkit-scrollbar-thumb:hover {
    background-color: #4a4f6e;
}

[data-theme="dark"] ::-webkit-scrollbar-track {
    background-color: var(--prim-neutral-850);
}

[data-theme="dark"] ::-webkit-scrollbar {
    width: 6px;
    height: 6px;
}

@media (prefers-color-scheme: dark) {
    :root:not([data-theme="light"]) ::-webkit-scrollbar-thumb {
        background-color: #3a3e59;
    }
    :root:not([data-theme="light"]) ::-webkit-scrollbar-track {
        background-color: var(--prim-neutral-850);
    }
}


/* — 5.7 Section titles / subtítulos cian (Flutter titleMedium) — */

/* Section headers destacados usan cian como Flutter titleMedium/titleSmall */
[data-theme="dark"] .section-title,
[data-theme="dark"] .page-subtitle,
[data-theme="dark"] .card-subtitle,
[data-theme="dark"] .section-label {
    color: var(--prim-cyan-400);
}

/* Breadcrumbs dark */
[data-theme="dark"] .breadcrumb-item a {
    color: var(--color-brand);
}

[data-theme="dark"] .breadcrumb-item.active {
    color: var(--color-text-title);
}

[data-theme="dark"] .breadcrumb-item + .breadcrumb-item::before {
    color: var(--color-text-icon-muted);
}


/* — 5.8 Focus ring refinado para dark — */

[data-theme="dark"] *:focus-visible {
    outline: 2px solid var(--color-brand);
    outline-offset: 2px;
    box-shadow: 0 0 0 4px rgba(3, 152, 172, 0.20);
}


/* — 5.9 Progress bars dark — */

[data-theme="dark"] .progress {
    background-color: var(--color-bg-unselect);
}

[data-theme="dark"] .progress-bar {
    box-shadow: 0 0 8px rgba(3, 152, 172, 0.35);
}


/* — 5.10 Tabs / navigation dark — */

[data-theme="dark"] .nav-tabs {
    border-bottom-color: var(--color-border);
}

[data-theme="dark"] .nav-tabs .nav-link {
    color: var(--color-text-secondary);
    border-color: transparent;
}

[data-theme="dark"] .nav-tabs .nav-link:hover {
    color: var(--color-text-primary);
    border-color: var(--color-border);
    background-color: rgba(255, 255, 255, 0.04);
}

[data-theme="dark"] .nav-tabs .nav-link.active {
    color: var(--color-brand);
    background-color: var(--color-bg-surface-overlay);
    border-color: var(--color-border) var(--color-border) var(--color-bg-surface-overlay);
}

[data-theme="dark"] .nav-pills .nav-link {
    color: var(--color-text-secondary);
}

[data-theme="dark"] .nav-pills .nav-link.active {
    background-color: rgba(3, 152, 172, 0.18);
    color: var(--prim-cyan-400);
}


/* — 5.11 Toasts dark — */

[data-theme="dark"] .toast,
[data-theme="dark"] .ds-toast {
    background-color: var(--prim-neutral-750);
    border-color: var(--color-border);
    box-shadow: var(--shadow-lg);
}

[data-theme="dark"] .toast-header {
    background-color: rgba(255, 255, 255, 0.03);
    border-bottom-color: var(--color-border);
    color: var(--color-text-title);
}

[data-theme="dark"] .toast-body {
    color: var(--color-text-primary);
}


/* — 5.12 Page header dark — */

[data-theme="dark"] .page-header {
    border-bottom-color: var(--color-border);
}

[data-theme="dark"] .page-header h1,
[data-theme="dark"] .page-header h2,
[data-theme="dark"] .page-title {
    color: var(--color-heading);
}


/* — 5.13 List groups dark — */

[data-theme="dark"] .list-group-item {
    background-color: var(--color-bg-surface-overlay);
    border-color: var(--color-border);
    color: var(--color-text-primary);
}

[data-theme="dark"] .list-group-item:hover {
    background-color: rgba(255, 255, 255, 0.04);
}

[data-theme="dark"] .list-group-item.active {
    background-color: rgba(3, 152, 172, 0.15);
    border-color: var(--color-brand);
    color: var(--prim-cyan-400);
}


/* — 5.14 Skeleton / loading shimmer dark — */

[data-theme="dark"] .skeleton,
[data-theme="dark"] .ds-skeleton {
    background: linear-gradient(
        90deg,
        var(--color-bg-unselect) 25%,
        rgba(255, 255, 255, 0.05) 50%,
        var(--color-bg-unselect) 75%
    );
    background-size: 200% 100%;
}


/* — 5.15 Empty states dark — */

[data-theme="dark"] .empty-state-icon {
    color: var(--color-text-icon-muted);
}

[data-theme="dark"] .empty-state-title {
    color: var(--color-text-title);
}

[data-theme="dark"] .empty-state-description {
    color: var(--color-text-secondary);
}


/* — 5.16 HR / dividers dark — */

[data-theme="dark"] hr,
[data-theme="dark"] .divider {
    border-color: var(--color-border);
    opacity: 1;
}


/* — 5.17 Code blocks dark — */

[data-theme="dark"] code,
[data-theme="dark"] pre {
    background-color: var(--color-bg-unselect);
    border-color: var(--color-border);
    color: var(--prim-cyan-300);
}


/* ── Fin: Flutter Dark Theme Overrides ── */


/* ============================================================
   KLOCKNER AUTOMATE PROFILE OVERRIDES
   Controlled by config brand_identity.active_profile = "klockner".
   ============================================================ */
.brand-logo-lockup {
    display: inline-flex;
    align-items: center;
    gap: var(--space-3);
    min-width: 0;
}

.brand-logo-mark {
    width: 36px;
    height: 36px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex: 0 0 auto;
}

.brand-logo-mark img {
    width: 100%;
    height: 100%;
    object-fit: contain;
}

.brand-logo-wordmark img {
    width: auto;
    height: 36px;
    max-width: 160px;
    object-fit: contain;
}

.brand-logo-mark--klockner {
    position: relative;
    overflow: hidden;
    border: 3px solid var(--color-brand);
    background: var(--color-bg-surface);
    color: var(--color-heading);
    font-size: 1.35rem;
    font-weight: var(--font-weight-extrabold);
    line-height: 1;
    letter-spacing: 0;
    box-shadow: inset 0 0 0 1px color-mix(in oklch, var(--color-brand) 18%, transparent);
}

.brand-logo-mark--klockner::after {
    content: "";
    position: absolute;
    right: -3px;
    bottom: -3px;
    width: 13px;
    height: 13px;
    background: var(--color-accent-hot);
}

.brand-logo-wordmark {
    display: inline-flex;
    align-items: center;
    min-width: 0;
    color: var(--color-sidebar-text);
    white-space: nowrap;
}

.brand-logo-wordmark--text {
    flex-direction: column;
    align-items: flex-start;
    gap: 1px;
    line-height: 1;
}

.brand-logo-wordmark-main {
    font-size: 1.05rem;
    font-weight: var(--font-weight-extrabold);
    letter-spacing: 0;
}

.brand-logo-wordmark-sub {
    font-size: 0.62rem;
    font-weight: var(--font-weight-semibold);
    color: var(--color-sidebar-text-muted);
    text-transform: uppercase;
    letter-spacing: 0.08em;
}

.sidebar:not(:hover):not(.sidebar--pinned):not(.hover-expanded) .brand-logo-wordmark {
    display: none;
}
.sidebar:not(:hover):not(.sidebar--pinned):not(.hover-expanded) .brand-logo-lockup { gap: 0; width: 100%; justify-content: center; }
.sidebar:not(:hover):not(.sidebar--pinned):not(.hover-expanded) .sidebar-logo { padding-left: 0; padding-right: 0; }

[data-design-system="klockner"] body {
    background-color: var(--color-bg-canvas);
}

[data-design-system="klockner"] .main-content,
[data-design-system="klockner"] .content-wrapper,
[data-design-system="klockner"] .page-content,
[data-design-system="klockner"] main {
    background-color: var(--color-bg-canvas);
}

[data-design-system="klockner"] .sidebar {
    background-color: var(--color-sidebar-bg);
    background-image: linear-gradient(180deg, var(--color-sidebar-bg), var(--klockner-menu-grey-deep, var(--color-sidebar-bg)));
    border-right-color: var(--color-sidebar-border);
    box-shadow: 1px 0 0 var(--color-sidebar-border), 12px 0 28px color-mix(in oklch, var(--klockner-ink) 12%, transparent);
}

[data-design-system="klockner"] .sidebar-logo {
    padding: var(--space-3) var(--space-4);
    border-bottom-color: var(--color-sidebar-border);
}

[data-design-system="klockner"] .sidebar .brand-logo-mark--klockner {
    width: 38px;
    height: 38px;
    background: url('/static/img/klockner_mark.png') center / contain no-repeat;
    border: none;
    color: transparent;
    box-shadow: none;
    border-radius: 0;
}
[data-design-system="klockner"] .sidebar .brand-logo-mark--klockner::after { content: none; }

[data-design-system="klockner"] .sidebar .brand-logo-wordmark-main {
    display: inline-block;
    width: 96px;
    height: 18px;
    background: url('/static/img/klockner_wordmark.png') left center / contain no-repeat;
    color: transparent;
    font-size: 0;
    line-height: 0;
}

[data-design-system="klockner"] .sidebar .brand-logo-wordmark-sub {
    color: var(--color-sidebar-text-muted);
}

[data-design-system="klockner"] .sidebar-nav-title {
    color: var(--color-sidebar-text-muted);
    letter-spacing: 0.1em;
}

[data-design-system="klockner"] .sidebar-nav-item {
    border-left: 3px solid transparent;
    color: var(--color-sidebar-text);
    border-radius: var(--radius-md);
    margin-inline: var(--space-2);
    background: transparent;
}

/* Klockner sidebar redesign: real cyan brand, filled-cyan-chip active state
   (no magenta left bar, no magenta corner dot), cooler/darker rail surface. */
[data-design-system="klockner"] {
    --klockner-cyan: #0098D0;
    --color-sidebar-bg: oklch(21% 0.013 250);
}
[data-design-system="klockner"] .sidebar-nav-item {
    border-left: 0;
    justify-content: center;
}
[data-design-system="klockner"] .sidebar:hover .sidebar-nav-item,
[data-design-system="klockner"] .sidebar.sidebar--pinned .sidebar-nav-item {
    justify-content: flex-start;
}
/* collapsed rail: the nav-label keeps flex:1 + the row gap, which pushed the icon left.
   Zero them so the icon chip centers in the 70px rail. */
.sidebar:not(:hover):not(.sidebar--pinned):not(.hover-expanded) .sidebar-nav-item {
    gap: 0;
    padding-left: 0;
    padding-right: 0;
}
.sidebar:not(:hover):not(.sidebar--pinned):not(.hover-expanded) .sidebar-nav-item .nav-label {
    flex: 0 0 0;
}
[data-design-system="klockner"] .sidebar-nav-item i,
[data-design-system="klockner"] .sidebar-nav-item .nav-icon {
    width: 38px;
    height: 38px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--radius-md);
    color: var(--color-sidebar-icon);
    transition: background var(--transition-fast), color var(--transition-fast);
}
[data-design-system="klockner"] .sidebar-nav-item:hover,
[data-design-system="klockner"] .sidebar-nav-item:focus-visible,
[data-design-system="klockner"] .sidebar-nav-item.active,
[data-design-system="klockner"] .sidebar-nav-item[aria-current="page"] {
    background: transparent;
    border-left-color: transparent;
    box-shadow: none;
    color: var(--color-sidebar-text);
}
[data-design-system="klockner"] .sidebar-nav-item:hover i,
[data-design-system="klockner"] .sidebar-nav-item:focus-visible i,
[data-design-system="klockner"] .sidebar-nav-item:hover .nav-icon {
    background: color-mix(in oklch, var(--prim-neutral-0) 9%, transparent);
    color: var(--color-sidebar-text);
}
[data-design-system="klockner"] .sidebar-nav-item.active i,
[data-design-system="klockner"] .sidebar-nav-item[aria-current="page"] i,
[data-design-system="klockner"] .sidebar-nav-item.active .nav-icon {
    background: var(--klockner-cyan);
    color: #ffffff;
}

/* Expanded rail: the active highlight propagates to a full-row cyan pill (the icon
   chip grows into the row); collapsed stays the icon chip. */
[data-design-system="klockner"] .sidebar:hover .sidebar-nav-item.active,
[data-design-system="klockner"] .sidebar.sidebar--pinned .sidebar-nav-item.active,
[data-design-system="klockner"] .sidebar.hover-expanded .sidebar-nav-item.active,
[data-design-system="klockner"] .sidebar:hover .sidebar-nav-item[aria-current="page"],
[data-design-system="klockner"] .sidebar.sidebar--pinned .sidebar-nav-item[aria-current="page"],
[data-design-system="klockner"] .sidebar.hover-expanded .sidebar-nav-item[aria-current="page"] {
    background: var(--klockner-cyan);
    color: #ffffff;
    border-radius: var(--radius-md);
}
[data-design-system="klockner"] .sidebar:hover .sidebar-nav-item.active i,
[data-design-system="klockner"] .sidebar.sidebar--pinned .sidebar-nav-item.active i,
[data-design-system="klockner"] .sidebar.hover-expanded .sidebar-nav-item.active i,
[data-design-system="klockner"] .sidebar:hover .sidebar-nav-item[aria-current="page"] i,
[data-design-system="klockner"] .sidebar.sidebar--pinned .sidebar-nav-item[aria-current="page"] i,
[data-design-system="klockner"] .sidebar.hover-expanded .sidebar-nav-item[aria-current="page"] i {
    background: transparent;
    color: #ffffff;
}
[data-design-system="klockner"] .sidebar-nav-item.active::before,
[data-design-system="klockner"] .sidebar-nav-item[aria-current="page"]::before {
    content: none;
}

[data-design-system="klockner"] .sidebar-nav-item::after {
    background: var(--color-sidebar-active-bg);
    color: var(--color-sidebar-text);
    border: 1px solid var(--color-sidebar-border);
}

[data-design-system="klockner"] .sidebar-footer {
    border-top-color: var(--color-sidebar-border);
}

[data-design-system="klockner"] .sidebar-version {
    color: var(--color-sidebar-text-muted);
}

[data-design-system="klockner"] .topbar,
[data-design-system="klockner"] #topbar {
    background: var(--color-topbar-bg) !important;
    background-image: linear-gradient(135deg, var(--color-topbar-bg), var(--color-topbar-bg-end)) !important;
    border-bottom: 1px solid var(--color-topbar-border) !important;
    box-shadow: 0 10px 28px color-mix(in oklch, var(--color-topbar-bg) 16%, transparent) !important;
}

[data-design-system="klockner"] .topbar h1,
[data-design-system="klockner"] .topbar h2,
[data-design-system="klockner"] .topbar h3,
[data-design-system="klockner"] .topbar h4,
[data-design-system="klockner"] .topbar h5,
[data-design-system="klockner"] .topbar h6,
[data-design-system="klockner"] .topbar-title {
    color: var(--color-topbar-text);
}

[data-design-system="klockner"] .topbar-title i {
    color: var(--color-brand);
}

[data-design-system="klockner"] .topbar .printer-selector-btn,
[data-design-system="klockner"] .topbar .profile-indicator {
    color: var(--color-topbar-text);
    background: color-mix(in oklch, var(--color-topbar-text) 10%, transparent);
    border-color: color-mix(in oklch, var(--color-topbar-text) 24%, transparent);
}

[data-design-system="klockner"] .topbar .printer-selector-btn:hover,
[data-design-system="klockner"] .topbar .printer-selector-btn:focus-visible {
    color: var(--color-topbar-text);
    background: color-mix(in oklch, var(--color-topbar-text) 18%, transparent);
    border-color: color-mix(in oklch, var(--color-brand) 78%, var(--color-topbar-text));
}

[data-design-system="klockner"] .btn-primary,
[data-design-system="klockner"] .ds-btn-primary,
[data-design-system="klockner"] .ds-btn--primary {
    background: var(--color-brand);
    background-image: none;
    border-color: var(--color-brand);
    border-radius: var(--radius-md);
    box-shadow: none;
    color: var(--color-heading);
    font-weight: var(--font-weight-semibold);
}

[data-design-system="klockner"] .btn-primary:hover,
[data-design-system="klockner"] .ds-btn-primary:hover,
[data-design-system="klockner"] .ds-btn--primary:hover {
    background: var(--color-brand-hover);
    background-image: none;
    border-color: var(--color-brand-hover);
    color: var(--color-heading);
    box-shadow: none;
}

[data-design-system="klockner"] .btn-info,
[data-design-system="klockner"] .btn-success,
[data-design-system="klockner"] .btn-warning {
    color: var(--color-heading) !important;
    border-color: transparent;
    font-weight: var(--font-weight-semibold);
}

[data-design-system="klockner"] .btn-info *,
[data-design-system="klockner"] .btn-success *,
[data-design-system="klockner"] .btn-warning * {
    color: currentColor !important;
}

[data-design-system="klockner"] .btn-secondary,
[data-design-system="klockner"] .ds-btn-secondary,
[data-design-system="klockner"] .ds-btn--secondary {
    background: var(--color-bg-surface);
    border-color: var(--color-border-strong);
    color: var(--color-text-primary);
}

[data-design-system="klockner"] .btn-secondary:hover,
[data-design-system="klockner"] .ds-btn-secondary:hover,
[data-design-system="klockner"] .ds-btn--secondary:hover {
    background: var(--color-bg-hover);
    border-color: var(--color-border-strong);
}

[data-design-system="klockner"] .btn-outline-primary {
    color: var(--color-text-brand);
    border-color: var(--color-brand);
    border-radius: var(--radius-md);
}

[data-design-system="klockner"] .btn-outline-primary:hover {
    color: var(--color-heading);
    background: var(--color-brand-subtle);
    border-color: var(--color-brand-hover);
}

[data-design-system="klockner"] .main-content .btn-outline-secondary {
    color: var(--color-heading) !important;
    background: var(--color-bg-elevated) !important;
    border-color: var(--color-border-strong) !important;
}

[data-design-system="klockner"] .main-content .btn-outline-secondary:hover,
[data-design-system="klockner"] .main-content .btn-outline-secondary:focus-visible {
    color: var(--color-heading) !important;
    background: var(--color-bg-hover) !important;
    border-color: var(--color-border-strong) !important;
}

[data-design-system="klockner"] .main-content .btn-outline-secondary *,
[data-design-system="klockner"] .main-content .btn-outline-secondary:hover * {
    color: currentColor !important;
}

[data-design-system="klockner"] #tankResinDisplay .btn-outline-light {
    color: var(--color-heading);
    background: var(--color-bg-surface);
    border-color: var(--color-border-strong);
}

[data-design-system="klockner"] #tankResinDisplay .btn-outline-light:hover,
[data-design-system="klockner"] #tankResinDisplay .btn-outline-light:focus-visible {
    color: var(--color-heading);
    background: var(--color-brand-subtle);
    border-color: var(--color-brand);
}

[data-design-system="klockner"] #tankResinDisplay .btn-outline-light i {
    color: currentColor;
}

[data-design-system="klockner"] .main-content .inventory-hero .btn-outline-light,
[data-design-system="klockner"] .main-content .invoices-header .btn-outline-light {
    color: var(--color-heading) !important;
    background: color-mix(in oklch, var(--color-bg-surface) 44%, transparent) !important;
    border-color: color-mix(in oklch, var(--color-heading) 62%, transparent) !important;
}

[data-design-system="klockner"] .main-content .inventory-hero .btn-outline-light:hover,
[data-design-system="klockner"] .main-content .inventory-hero .btn-outline-light:focus-visible,
[data-design-system="klockner"] .main-content .invoices-header .btn-outline-light:hover,
[data-design-system="klockner"] .main-content .invoices-header .btn-outline-light:focus-visible {
    color: var(--color-heading) !important;
    background: var(--color-bg-surface) !important;
    border-color: var(--color-heading) !important;
}

[data-design-system="klockner"] .main-content .inventory-hero .btn-outline-light *,
[data-design-system="klockner"] .main-content .invoices-header .btn-outline-light * {
    color: currentColor !important;
}

[data-design-system="klockner"] .main-content .card-header.bg-primary,
[data-design-system="klockner"] .main-content .card-header.bg-info,
[data-design-system="klockner"] .main-content .card-header.bg-success,
[data-design-system="klockner"] .main-content .card-header.bg-warning,
[data-design-system="klockner"] .main-content .card-header.bg-secondary,
[data-design-system="klockner"] .modal-header.bg-primary,
[data-design-system="klockner"] .modal-header.bg-info,
[data-design-system="klockner"] .modal-header.bg-success,
[data-design-system="klockner"] .modal-header.bg-warning,
[data-design-system="klockner"] .modal-header.bg-secondary {
    position: relative;
    color: var(--color-heading) !important;
    background: var(--color-bg-elevated) !important;
    background-image: none !important;
    border-bottom: 1px solid var(--color-border) !important;
}

/* Headers: drop the decorative 4px left stripe — calmer, less "AI slop".
   The semantic color now lives in the section icon, rendered as a tinted chip. */
[data-design-system="klockner"] .main-content .card-header.bg-primary::before,
[data-design-system="klockner"] .main-content .card-header.bg-info::before,
[data-design-system="klockner"] .main-content .card-header.bg-success::before,
[data-design-system="klockner"] .main-content .card-header.bg-warning::before,
[data-design-system="klockner"] .main-content .card-header.bg-secondary::before,
[data-design-system="klockner"] .modal-header.bg-primary::before,
[data-design-system="klockner"] .modal-header.bg-info::before,
[data-design-system="klockner"] .modal-header.bg-success::before,
[data-design-system="klockner"] .modal-header.bg-warning::before,
[data-design-system="klockner"] .modal-header.bg-secondary::before {
    content: none;
}

/* Section title icon -> small tinted chip (color already applied by the i rules below) */
[data-design-system="klockner"] .main-content .card-header[class*="bg-"] > h5 > i:first-child,
[data-design-system="klockner"] .main-content .card-header[class*="bg-"] > h6 > i:first-child,
[data-design-system="klockner"] .modal-header[class*="bg-"] > h5 > i:first-child,
[data-design-system="klockner"] .modal-header[class*="bg-"] > h6 > i:first-child {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 30px;
    height: 30px;
    border-radius: var(--radius-md);
    margin-right: 0.55rem;
    font-size: 0.9rem;
    vertical-align: middle;
    flex: 0 0 auto;
}
[data-design-system="klockner"] .main-content .card-header.bg-primary > h5 > i:first-child,
[data-design-system="klockner"] .main-content .card-header.bg-primary > h6 > i:first-child,
[data-design-system="klockner"] .main-content .card-header.bg-info > h5 > i:first-child,
[data-design-system="klockner"] .main-content .card-header.bg-info > h6 > i:first-child,
[data-design-system="klockner"] .modal-header.bg-primary > h5 > i:first-child,
[data-design-system="klockner"] .modal-header.bg-info > h5 > i:first-child {
    background: var(--color-brand-subtle);
}
[data-design-system="klockner"] .main-content .card-header.bg-success > h5 > i:first-child,
[data-design-system="klockner"] .main-content .card-header.bg-success > h6 > i:first-child,
[data-design-system="klockner"] .modal-header.bg-success > h5 > i:first-child,
[data-design-system="klockner"] .modal-header.bg-success > h6 > i:first-child {
    background: var(--color-success-subtle);
}
[data-design-system="klockner"] .main-content .card-header.bg-warning > h5 > i:first-child,
[data-design-system="klockner"] .main-content .card-header.bg-warning > h6 > i:first-child,
[data-design-system="klockner"] .modal-header.bg-warning > h5 > i:first-child {
    background: var(--color-warning-subtle);
}
[data-design-system="klockner"] .main-content .card-header.bg-secondary > h5 > i:first-child,
[data-design-system="klockner"] .main-content .card-header.bg-secondary > h6 > i:first-child {
    background: var(--color-surface-muted);
}

[data-design-system="klockner"] .main-content .card-header.bg-primary *,
[data-design-system="klockner"] .main-content .card-header.bg-info *,
[data-design-system="klockner"] .main-content .card-header.bg-success *,
[data-design-system="klockner"] .main-content .card-header.bg-warning *,
[data-design-system="klockner"] .main-content .card-header.bg-secondary *,
[data-design-system="klockner"] .modal-header.bg-primary *,
[data-design-system="klockner"] .modal-header.bg-info *,
[data-design-system="klockner"] .modal-header.bg-success *,
[data-design-system="klockner"] .modal-header.bg-warning *,
[data-design-system="klockner"] .modal-header.bg-secondary * {
    color: var(--color-heading) !important;
}

[data-design-system="klockner"] .main-content .card-header.bg-primary i,
[data-design-system="klockner"] .main-content .card-header.bg-info i,
[data-design-system="klockner"] .modal-header.bg-primary i,
[data-design-system="klockner"] .modal-header.bg-info i {
    color: var(--color-brand) !important;
}

[data-design-system="klockner"] .main-content .card-header.bg-success i,
[data-design-system="klockner"] .modal-header.bg-success i {
    color: var(--color-success) !important;
}

[data-design-system="klockner"] .main-content .card-header.bg-warning i,
[data-design-system="klockner"] .modal-header.bg-warning i {
    color: var(--color-warning) !important;
}

[data-design-system="klockner"] .main-content .card-header .btn-outline-light,
[data-design-system="klockner"] .modal-header .btn-outline-light {
    color: var(--color-heading) !important;
    background: var(--color-bg-surface) !important;
    border-color: var(--color-border-strong) !important;
}

[data-design-system="klockner"] .main-content .card-header .btn-outline-light:hover,
[data-design-system="klockner"] .main-content .card-header .btn-outline-light:focus-visible,
[data-design-system="klockner"] .modal-header .btn-outline-light:hover,
[data-design-system="klockner"] .modal-header .btn-outline-light:focus-visible {
    color: var(--color-heading) !important;
    background: var(--color-bg-hover) !important;
    border-color: var(--color-brand) !important;
}

[data-design-system="klockner"] .main-content .card-header .btn-outline-light *,
[data-design-system="klockner"] .modal-header .btn-outline-light * {
    color: currentColor !important;
}

[data-design-system="klockner"] .modal-header .btn-close-white {
    filter: none;
    opacity: 0.72;
}

[data-design-system="klockner"] .modal-header .btn-close-white:hover,
[data-design-system="klockner"] .modal-header .btn-close-white:focus-visible {
    opacity: 1;
}

[data-design-system="klockner"] .main-content .progress-bar.bg-primary,
[data-design-system="klockner"] .main-content .progress-bar.bg-info,
[data-design-system="klockner"] .main-content .progress-bar.bg-success,
[data-design-system="klockner"] .main-content .progress-bar.bg-warning {
    color: var(--color-heading) !important;
    font-weight: var(--font-weight-semibold);
}

[data-design-system="klockner"] .main-content .card-body .metric-box,
[data-design-system="klockner"] .main-content .card-body .metric-box-sm {
    color: var(--color-heading) !important;
    background: var(--color-bg-elevated) !important;
    border-color: var(--color-border) !important;
}

[data-design-system="klockner"] .main-content .card-body .metric-box *,
[data-design-system="klockner"] .main-content .card-body .metric-box-sm * {
    color: var(--color-heading) !important;
}

[data-design-system="klockner"] .main-content .card-body .metric-box .metric-label,
[data-design-system="klockner"] .main-content .card-body .metric-box-sm .metric-label-sm {
    color: var(--color-text-secondary) !important;
}

[data-design-system="klockner"] .card,
[data-design-system="klockner"] .ds-card,
[data-design-system="klockner"] .auth-card {
    border-radius: var(--radius-lg);
    border-color: var(--color-border);
    background: var(--color-bg-surface);
    box-shadow: var(--shadow-sm);
}

[data-design-system="klockner"] .badge-brand,
[data-design-system="klockner"] .ds-badge-brand,
[data-design-system="klockner"] .badge-primary {
    color: var(--color-text-brand);
    background: var(--color-brand-subtle);
    border-color: var(--color-brand-border);
}

[data-design-system="klockner"] .alert-info,
[data-design-system="klockner"] .ds-alert-info {
    color: var(--color-text-primary);
    background: var(--color-brand-subtle);
    border-color: var(--color-brand-border);
}

[data-design-system="klockner"] .form-control,
[data-design-system="klockner"] .form-select,
[data-design-system="klockner"] .input-group-text {
    border-radius: var(--radius-md);
    background-color: var(--color-bg-surface);
    border-color: var(--color-border);
    color: var(--color-text-primary);
}

[data-design-system="klockner"] .form-control:focus,
[data-design-system="klockner"] .form-select:focus {
    border-color: var(--color-border-focus);
    box-shadow: 0 0 0 3px var(--color-focus-ring);
}

[data-design-system="klockner"] .auth-logo-badge {
    border-radius: var(--radius-lg);
    background: var(--color-bg-surface);
    border-color: var(--color-border);
    box-shadow: var(--shadow-sm);
}

[data-design-system="klockner"] .auth-logo-badge .brand-logo-mark--klockner {
    width: 54px;
    height: 54px;
    font-size: 2rem;
}

[data-design-system="klockner"] body.auth-page {
    background:
        linear-gradient(180deg, var(--color-bg-surface) 0 86px, var(--color-bg-canvas) 86px 100%);
}

@media (max-width: 768px) {
    [data-design-system="klockner"] body.auth-page {
        background: var(--color-bg-canvas);
    }
}


/* ============================================================
   SALES PORTAL — sp-* component module (P0-6)
   ============================================================
   Complete styling for the rep / territory-manager / logistics /
   admin-signup surfaces. Templates reference these classes today
   but the rules lived nowhere — every page rendered as raw HTML.
   Built entirely from design tokens so the Klockner Automate brand
   profile (data-design-system="klockner") inherits palette + radii
   for free.

   Chat / status / timeline classes (.sp-chat-panel, .sp-thread*,
   .sp-msg*, .sp-status-panel, .sp-timeline*) live in
   sales_portal_chat.css — that file is loaded only when threads are
   enabled and predates this module.
   ============================================================ */

/* ─── Shell ───────────────────────────────────────────────── */
.sp-shell {
    display: grid;
    grid-template-columns: 240px 1fr;
    min-height: 100vh;
    background: var(--color-bg-canvas);
    color: var(--color-text-primary);
    font-family: var(--font-sans);
    font-size: var(--font-size-body-md);
    line-height: var(--line-height-normal);
}

/* Public surfaces (login / register / pending-approval) render without
   the sidebar — the rep hasn't authenticated, the nav links would all
   bounce them straight back to login anyway. Centre the form so the
   page reads like a real login screen and not a 240-px-wide gap with
   content on the right. */
.sp-shell.sp-shell-public {
    grid-template-columns: 1fr;
    place-items: center;
}
.sp-shell.sp-shell-public .sp-main {
    max-width: 480px;
    width: 100%;
}

.sp-side {
    background: var(--color-sidebar-bg);
    color: var(--color-sidebar-text);
    padding: var(--space-6) var(--space-4);
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
    border-right: 1px solid var(--color-sidebar-border);
}

.sp-brand {
    font-size: var(--font-size-h4);
    font-weight: var(--font-weight-bold);
    letter-spacing: var(--letter-spacing-tight);
    color: var(--color-text-inverse);
    margin: 0 0 var(--space-4);
}

.sp-nav-item {
    display: block;
    padding: var(--space-2-5) var(--space-3);
    color: var(--color-sidebar-text-muted);
    text-decoration: none;
    border-radius: var(--radius-md);
    font-weight: var(--font-weight-medium);
    transition: background var(--transition-fast), color var(--transition-fast);
}

.sp-nav-item:hover,
.sp-nav-item:focus-visible {
    background: var(--color-sidebar-hover);
    color: var(--color-sidebar-text);
    outline: none;
}

.sp-nav-item.active,
.sp-nav-item[aria-current="page"] {
    background: var(--color-sidebar-active-bg);
    color: var(--color-sidebar-text);
    box-shadow: inset 3px 0 0 var(--color-sidebar-active-bar);
}

.sp-main {
    padding: var(--space-6) var(--space-8);
    max-width: var(--layout-content-max-width);
    width: 100%;
}

@media (max-width: 768px) {
    .sp-shell {
        grid-template-columns: 1fr;
    }
    .sp-side {
        flex-direction: row;
        flex-wrap: wrap;
        padding: var(--space-3) var(--space-4);
        border-right: none;
        border-bottom: 1px solid var(--color-sidebar-border);
    }
    .sp-brand { margin: 0 var(--space-4) 0 0; }
    .sp-main { padding: var(--space-4); }
}

/* ─── Section wrappers ────────────────────────────────────── */
.sp-section {
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    padding: var(--space-5);
    margin-bottom: var(--space-5);
    box-shadow: var(--shadow-xs);
}

.sp-section > h3 {
    margin: 0 0 var(--space-4);
    font-size: var(--font-size-h5);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
}

.sp-list-header,
.sp-editor-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-3);
    margin-bottom: var(--space-5);
    flex-wrap: wrap;
}

.sp-list-header h2,
.sp-editor-header h2 {
    margin: 0;
    display: flex;
    align-items: center;
    gap: var(--space-2);
    font-size: var(--font-size-h2);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
}

.sp-toolbar {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    margin-bottom: var(--space-4);
    flex-wrap: wrap;
}

.sp-toolbar label {
    display: inline-flex;
    align-items: center;
    gap: var(--space-2);
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
}

/* ─── Dashboard cards ─────────────────────────────────────── */
.sp-cards {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
    gap: var(--space-4);
    margin-bottom: var(--space-6);
}

.sp-card {
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    padding: var(--space-5);
    box-shadow: var(--shadow-sm);
    display: flex;
    flex-direction: column;
    gap: var(--space-2);
}

.sp-card h3 {
    margin: 0;
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-semibold);
    text-transform: uppercase;
    letter-spacing: var(--letter-spacing-wide);
    color: var(--color-text-secondary);
}

.sp-card a {
    margin-top: auto;
    color: var(--color-text-brand);
    font-weight: var(--font-weight-medium);
    font-size: var(--font-size-body-sm);
    text-decoration: none;
}
.sp-card a:hover { text-decoration: underline; }

.sp-metric {
    margin: 0;
    font-size: var(--font-size-display-sm);
    font-weight: var(--font-weight-bold);
    color: var(--color-heading);
    line-height: var(--line-height-tight);
    font-variant-numeric: tabular-nums;
}

/* ─── Buttons ─────────────────────────────────────────────── */
.sp-btn {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: var(--space-2);
    padding: var(--space-2-5) var(--space-4);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-bg-surface);
    color: var(--color-text-primary);
    font: inherit;
    font-weight: var(--font-weight-medium);
    line-height: var(--line-height-tight);
    cursor: pointer;
    text-decoration: none;
    transition: background var(--transition-fast),
                border-color var(--transition-fast),
                color var(--transition-fast),
                box-shadow var(--transition-fast);
}

.sp-btn:hover:not(:disabled) {
    background: var(--color-bg-hover);
    border-color: var(--color-border-strong);
}

.sp-btn:focus-visible {
    outline: none;
    box-shadow: 0 0 0 3px var(--color-focus-ring);
    border-color: var(--color-border-focus);
}

.sp-btn:disabled,
.sp-btn[aria-disabled="true"] {
    opacity: var(--opacity-disabled);
    cursor: not-allowed;
}

.sp-btn-primary {
    background: var(--color-brand);
    border-color: var(--color-brand);
    color: var(--color-text-inverse);
}
.sp-btn-primary:hover:not(:disabled) {
    background: var(--color-brand-hover);
    border-color: var(--color-brand-hover);
    color: var(--color-text-inverse);
}

.sp-btn-danger {
    background: var(--color-error);
    border-color: var(--color-error);
    color: var(--color-text-inverse);
}
.sp-btn-danger:hover:not(:disabled) {
    background: var(--color-error-hover);
    border-color: var(--color-error-hover);
    color: var(--color-text-inverse);
}

.sp-btn-sm {
    padding: var(--space-1-5) var(--space-3);
    font-size: var(--font-size-body-sm);
}

/* ─── Inputs / forms ──────────────────────────────────────── */
.sp-input,
.sp-form input:not([type="checkbox"]):not([type="radio"]):not([type="file"]),
.sp-form select,
.sp-form textarea,
.sp-grid input:not([type="checkbox"]):not([type="radio"]):not([type="file"]),
.sp-grid select,
.sp-grid textarea,
.sp-toolbar select,
.sp-toolbar input {
    width: 100%;
    padding: var(--space-2) var(--space-3);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-bg-surface);
    color: var(--color-text-primary);
    font: inherit;
    font-size: var(--font-size-body-md);
    transition: border-color var(--transition-fast), box-shadow var(--transition-fast);
}

.sp-input:focus,
.sp-form :is(input, select, textarea):focus,
.sp-grid :is(input, select, textarea):focus,
.sp-toolbar :is(select, input):focus {
    outline: none;
    border-color: var(--color-border-focus);
    box-shadow: 0 0 0 3px var(--color-focus-ring);
}

.sp-form,
.sp-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
    gap: var(--space-3) var(--space-4);
}

.sp-form label,
.sp-grid label {
    display: flex;
    flex-direction: column;
    gap: var(--space-1);
    font-size: var(--font-size-label-md);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-secondary);
}

.sp-grid textarea,
.sp-form textarea {
    min-height: 80px;
    resize: vertical;
}

/* Search results dropdown under .sp-input — used by customer/catalog pickers. */
.sp-results {
    list-style: none;
    margin: var(--space-1) 0 var(--space-3);
    padding: 0;
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    max-height: 280px;
    overflow-y: auto;
    box-shadow: var(--shadow-sm);
}
.sp-results:empty { display: none; }
.sp-results li {
    padding: var(--space-2) var(--space-3);
    cursor: pointer;
    border-bottom: 1px solid var(--color-border);
    font-size: var(--font-size-body-sm);
}
.sp-results li:last-child { border-bottom: none; }
.sp-results li:hover,
.sp-results li:focus-visible,
.sp-results li.sp-results-active {
    background: var(--color-bg-hover);
    outline: none;
}

/* Status placeholder rendered inside .sp-results (loading / empty /
   error). Non-clickable, dimmer than real items, italic so the rep's
   eye distinguishes "no matches" from a single-result list. */
.sp-results-status {
    padding: var(--space-2) var(--space-3);
    color: var(--color-text-muted);
    font-style: italic;
    font-size: var(--font-size-body-sm);
    cursor: default;
}

/* ─── Tables ──────────────────────────────────────────────── */
.sp-table,
.sp-lines {
    width: 100%;
    border-collapse: separate;
    border-spacing: 0;
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    overflow: hidden;
    font-size: var(--font-size-body-sm);
}

.sp-table thead th,
.sp-lines thead th {
    text-align: left;
    padding: var(--space-3) var(--space-4);
    background: var(--color-bg-elevated);
    color: var(--color-text-secondary);
    font-weight: var(--font-weight-semibold);
    text-transform: uppercase;
    letter-spacing: var(--letter-spacing-wide);
    font-size: var(--font-size-label-sm);
    border-bottom: 1px solid var(--color-border);
}

.sp-table tbody td,
.sp-lines tbody td {
    padding: var(--space-3) var(--space-4);
    border-bottom: 1px solid var(--color-border);
    color: var(--color-text-primary);
    vertical-align: middle;
}

.sp-table tbody tr:last-child td,
.sp-lines tbody tr:last-child td {
    border-bottom: none;
}

.sp-table tbody tr:hover,
.sp-lines tbody tr:hover {
    background: var(--color-bg-hover);
}

/* Numeric line columns: qty, unit price, discount, total. Right-align +
   tabular-nums so totals visually line up across rows. */
.sp-lines tbody td:nth-child(n+3):nth-child(-n+6) {
    text-align: right;
    font-variant-numeric: tabular-nums;
}

/* ─── Totals strip ────────────────────────────────────────── */
.sp-totals {
    display: flex;
    justify-content: flex-end;
    align-items: baseline;
    gap: var(--space-5);
    padding: var(--space-4) var(--space-5);
    background: var(--color-bg-elevated);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    margin: var(--space-5) 0;
    font-variant-numeric: tabular-nums;
    flex-wrap: wrap;
}

.sp-totals > div {
    color: var(--color-text-secondary);
    font-size: var(--font-size-body-sm);
}

.sp-totals .sp-total {
    color: var(--color-heading);
    font-size: var(--font-size-h4);
}

/* ─── Action footer (form footer with primary/secondary buttons) ─── */
.sp-actions {
    display: flex;
    justify-content: flex-end;
    gap: var(--space-3);
    padding-top: var(--space-4);
    border-top: 1px solid var(--color-border);
    margin-top: var(--space-5);
    flex-wrap: wrap;
}
.sp-actions-group {
    display: flex;
    gap: var(--space-3);
    flex-wrap: wrap;
}
/* Order editor uses two groups (destructive left, primary flow right). Other
   pages keep the default right-aligned flat action row. */
#order-editor .sp-actions { justify-content: space-between; }

/* Portal content shell: cap the line/scan width so pages don't stretch
   edge-to-edge on wide monitors (lists, forms, dashboard all benefit). The
   order editor caps tighter below for form readability. */
.sp-content-shell {
    max-width: 1400px;
    margin-inline: auto;
}

/* ─── Order editor polish ─────────────────────────────────── */
/* Constrain the editor to a comfortable reading/scan width instead of
   stretching fields edge-to-edge on wide screens. */
#order-editor {
    max-width: 1140px;
    margin-inline: auto;
}

/* Section headers gain a leading brand icon for scannability. */
.sp-section > h3 {
    display: flex;
    align-items: center;
    gap: var(--space-2);
}
.sp-section > h3 .sp-section-icon {
    color: var(--color-brand);
    font-size: 0.9em;
}

/* Attached-customer summary card: avatar + name + SAP condition chips. */
.sp-customer-summary {
    display: flex;
    align-items: flex-start;
    gap: var(--space-4);
    padding: var(--space-4);
    background: var(--color-bg-elevated);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    margin-bottom: var(--space-4);
}
.sp-cs-avatar {
    flex-shrink: 0;
    width: 40px;
    height: 40px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--radius-full);
    background: var(--color-brand-subtle);
    color: var(--color-text-brand);
    font-size: 1rem;
}
.sp-cs-body { min-width: 0; flex: 1; }
.sp-customer-name {
    margin: 0 0 var(--space-2);
    font-size: var(--font-size-body-lg);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
}

/* Chip row (reusable): small rounded info pills. */
.sp-chips {
    display: flex;
    flex-wrap: wrap;
    gap: var(--space-2);
}
.sp-chip {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    padding: 2px var(--space-2);
    border-radius: var(--radius-full);
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    font-size: var(--font-size-label-sm);
    color: var(--color-text-secondary);
    white-space: nowrap;
}
.sp-chip i { font-size: 0.85em; color: var(--color-text-muted); }
.sp-chip--code {
    background: var(--color-brand-subtle);
    border-color: var(--color-brand-border);
    color: var(--color-text-brand);
    font-weight: var(--font-weight-medium);
}
.sp-chip--code i { color: var(--color-text-brand); }

/* Standalone field label + helper text (titular picker, etc.). */
.sp-field-label {
    display: block;
    font-size: var(--font-size-label-sm);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-secondary);
    text-transform: uppercase;
    letter-spacing: var(--letter-spacing-wide);
    margin-bottom: var(--space-1);
}
.sp-help {
    margin: var(--space-1) 0 0;
    font-size: var(--font-size-body-sm);
    color: var(--color-text-muted);
}
.sp-titular { margin-top: var(--space-4); }

/* Lines empty state. */
.sp-lines-empty {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: var(--space-2);
    padding: var(--space-8) var(--space-4);
    text-align: center;
    color: var(--color-text-muted);
    background: var(--color-bg-subtle);
    border: 1px dashed var(--color-border);
    border-radius: var(--radius-md);
}
.sp-lines-empty i { font-size: 1.5rem; color: var(--color-text-icon-muted); }
.sp-lines-empty p { margin: 0; font-size: var(--font-size-body-sm); }
/* Numeric line cells align as tabular figures. */
.sp-lines td { font-variant-numeric: tabular-nums; }

/* Conditions grid: uppercase mini-labels + full-width note fields. */
.sp-grid label > .sp-field-label-inline {
    font-size: var(--font-size-label-sm);
    font-weight: var(--font-weight-medium);
    color: var(--color-text-secondary);
    text-transform: uppercase;
    letter-spacing: var(--letter-spacing-wide);
}
.sp-grid label.sp-col-span-all { grid-column: 1 / -1; }
.sp-grid label.sp-col-span-all textarea { min-height: 84px; resize: vertical; }

/* ─── Portal shared: empty states, fieldsets, status cards ──── */
/* Generic empty state (icon + guidance), reusable across list/table pages. */
.sp-empty-state {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: var(--space-2);
    padding: var(--space-8) var(--space-4);
    text-align: center;
    color: var(--color-text-muted);
    background: var(--color-bg-subtle);
    border: 1px dashed var(--color-border);
    border-radius: var(--radius-md);
}
.sp-empty-state i { font-size: 1.5rem; color: var(--color-text-icon-muted); }
.sp-empty-state p { margin: 0; font-size: var(--font-size-body-sm); }
.sp-empty-state .sp-empty-state-title {
    margin: 0;
    color: var(--color-heading);
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-semibold);
}
.sp-empty-state .sp-empty-state-desc {
    margin: 0;
    max-width: 52ch;
    color: var(--color-text-secondary);
    font-size: var(--font-size-body-sm);
    line-height: var(--line-height-snug);
}
.sp-empty-state.sp-empty-state-error {
    background: var(--color-error-subtle);
    border-color: var(--color-error-border);
    color: var(--color-error-text);
}
.sp-empty-state.sp-empty-state-error i,
.sp-empty-state.sp-empty-state-error .sp-empty-state-title {
    color: var(--color-error-text);
}

/* Required-field marker. */
.sp-required { color: var(--color-error); margin-left: 2px; text-decoration: none; cursor: help; }

/* Form fieldset group (semantic grouping inside a single form). */
.sp-fieldset {
    border: 0;
    padding: 0;
    margin: 0 0 var(--space-6);
    min-inline-size: 0;
}
.sp-fieldset > legend {
    padding: 0;
    margin: 0 0 var(--space-4);
    font-size: var(--font-size-h6);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
    display: flex;
    align-items: center;
    gap: var(--space-2);
}
.sp-fieldset > legend i { color: var(--color-brand); font-size: 0.9em; }

/* Centered status card (pending approval, simple status screens). */
.sp-status-card {
    max-width: 520px;
    margin: var(--space-8) auto;
    padding: var(--space-8);
    text-align: center;
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    box-shadow: var(--shadow-xs);
}
.sp-status-card .sp-status-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 64px;
    height: 64px;
    margin-bottom: var(--space-4);
    border-radius: var(--radius-full);
    background: var(--color-brand-subtle);
    color: var(--color-brand);
    font-size: 1.75rem;
}
.sp-status-card h2 { margin: 0 0 var(--space-2); }
.sp-status-card > p { color: var(--color-text-secondary); }
.sp-status-card .sp-actions {
    justify-content: center;
    border-top: 0;
    margin-top: var(--space-5);
    padding-top: 0;
}

/* Settings card (notification preferences and similar single-column forms). */
.sp-settings-card { max-width: 600px; }
.sp-settings-card .sp-form { display: flex; flex-direction: column; gap: var(--space-4); align-items: flex-start; }
.sp-settings-card .sp-form select { min-width: 260px; }
.sp-toggle-row { display: flex; align-items: center; gap: var(--space-2); }
.sp-toggle-row small { color: var(--color-text-muted); }

/* ── Logistics detail pages ──────────────────────────────────
   The logistics order/customer detail pages use lg-* classes that previously
   had NO CSS (raw browser defaults). Style them to match the portal: header,
   actions row, and the snapshot <pre> as a readable code block. The list pages
   (queue / sap-errors) now use the shared .sp-table / .sp-list-header. */
.lg-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-3);
    margin-bottom: var(--space-5);
    flex-wrap: wrap;
}
.lg-header h2 {
    margin: 0;
    display: flex;
    align-items: center;
    gap: var(--space-2);
    font-size: var(--font-size-h2);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
}
.lg-actions {
    display: flex;
    gap: var(--space-3);
    flex-wrap: wrap;
    padding-top: var(--space-4);
    border-top: 1px solid var(--color-border);
    margin-top: var(--space-5);
}
.lg-snapshot {
    margin: 0;
    padding: var(--space-4);
    background: var(--color-bg-elevated);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
    overflow: auto;
    max-height: 60vh;
    white-space: pre-wrap;
    word-break: break-word;
}

/* Collapsible raw-data block (logistics detail "datos técnicos"). */
.sp-details { margin: var(--space-4) 0; }
.sp-details > summary {
    cursor: pointer;
    color: var(--color-text-secondary);
    font-size: var(--font-size-body-sm);
    user-select: none;
    padding: var(--space-1) 0;
}
.sp-details[open] > summary { margin-bottom: var(--space-2); }

/* Inline error banner (e.g. last ERP dispatch error). */
.sp-error-banner {
    display: flex;
    align-items: flex-start;
    gap: var(--space-2);
    margin-top: var(--space-3);
    padding: var(--space-3) var(--space-4);
    background: var(--color-error-subtle);
    border: 1px solid var(--color-error-border);
    border-radius: var(--radius-md);
    color: var(--color-error-text);
    font-size: var(--font-size-body-sm);
}
.sp-error-banner i { color: var(--color-error); margin-top: 2px; }

.sp-warning-banner {
    display: flex;
    align-items: flex-start;
    gap: var(--space-2);
    margin-top: var(--space-3);
    padding: var(--space-3) var(--space-4);
    background: var(--color-warning-subtle);
    border: 1px solid var(--color-warning-border);
    border-radius: var(--radius-md);
    color: var(--color-warning-text);
    font-size: var(--font-size-body-sm);
}
.sp-warning-banner i { color: var(--color-warning); margin-top: 2px; }

/* Per-row actions cell (lists with inline actions). */
.sp-col-actions { white-space: nowrap; text-align: right; width: 1%; }
.sp-row-actions { display: inline-flex; gap: var(--space-2); justify-content: flex-end; }
/* "Load more" footer under a list/table. */
.sp-list-footer { display: flex; justify-content: center; padding: var(--space-4) 0; }

/* ─── Tabs ────────────────────────────────────────────────── */
.sp-tabs {
    display: flex;
    gap: var(--space-1);
    border-bottom: 1px solid var(--color-border);
    margin-bottom: var(--space-4);
}

.sp-tab {
    background: transparent;
    border: none;
    padding: var(--space-3) var(--space-4);
    color: var(--color-text-secondary);
    font: inherit;
    font-weight: var(--font-weight-medium);
    cursor: pointer;
    border-bottom: 2px solid transparent;
    margin-bottom: -1px;
    transition: color var(--transition-fast), border-color var(--transition-fast);
}

.sp-tab:hover { color: var(--color-text-primary); }

.sp-tab.active,
.sp-tab[aria-selected="true"] {
    color: var(--color-text-brand);
    border-bottom-color: var(--color-brand);
}

.sp-panel {
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    padding: var(--space-5);
    margin-bottom: var(--space-4);
}
.sp-panel[hidden] { display: none; }

/* ─── Badges + state color map ────────────────────────────── */
.sp-badge {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    padding: var(--space-1) var(--space-2-5);
    border-radius: var(--radius-full);
    background: var(--color-bg-elevated);
    color: var(--color-text-secondary);
    font-size: var(--font-size-label-sm);
    font-weight: var(--font-weight-semibold);
    text-transform: uppercase;
    letter-spacing: var(--letter-spacing-wide);
    border: 1px solid var(--color-border);
    line-height: var(--line-height-tight);
    white-space: nowrap;
}

/* State-specific badges (set by JS via the FSM state string).
   Keep names aligned 1:1 with OrderDraftState / CustomerDraftState. */
.sp-badge.sp-badge-draft,
.sp-badge.sp-badge-cancelled {
    background: var(--color-bg-elevated);
    color: var(--color-text-secondary);
    border-color: var(--color-border);
}
.sp-badge.sp-badge-pending_sales_approval,
.sp-badge.sp-badge-returned_to_sales,
.sp-badge.sp-badge-pending_logistics_review,
.sp-badge.sp-badge-pending_approval {
    background: var(--color-warning-subtle);
    color: var(--color-warning-text);
    border-color: var(--color-warning-border);
}
.sp-badge.sp-badge-approved_by_sales,
.sp-badge.sp-badge-pending_logistics,
.sp-badge.sp-badge-in_dispatch,
.sp-badge.sp-badge-exported,
.sp-badge.sp-badge-approved {
    background: var(--color-info-subtle);
    color: var(--color-info-text);
    border-color: var(--color-info-border);
}
.sp-badge.sp-badge-confirmed,
.sp-badge.sp-badge-promoted_to_erp {
    background: var(--color-success-subtle);
    color: var(--color-success-text);
    border-color: var(--color-success-border);
}
.sp-badge.sp-badge-rejected,
.sp-badge.sp-badge-logistics_error {
    background: var(--color-error-subtle);
    color: var(--color-error-text);
    border-color: var(--color-error-border);
}

/* AI-resolved row marker — used on lines that came from intake materializer
   so the rep can spot what the LLM authored before submit. */
.sp-ai-badge {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    padding: 0 var(--space-1-5);
    border-radius: var(--radius-sm);
    background: var(--color-brand-subtle);
    color: var(--color-text-brand);
    border: 1px solid var(--color-brand-border);
    font-size: var(--font-size-caption);
    font-weight: var(--font-weight-semibold);
    text-transform: uppercase;
    letter-spacing: var(--letter-spacing-wide);
}

.sp-intake-banner {
    background: var(--color-brand-subtle);
    border: 1px solid var(--color-brand-border);
    color: var(--color-text-brand);
    padding: var(--space-3) var(--space-4);
    border-radius: var(--radius-md);
    margin-bottom: var(--space-4);
    font-size: var(--font-size-body-sm);
}

/* ─── Feedback / empty state ──────────────────────────────── */
.sp-feedback {
    margin: var(--space-3) 0 0;
    padding: var(--space-3) var(--space-4);
    border-radius: var(--radius-md);
    font-size: var(--font-size-body-sm);
    border: 1px solid transparent;
    line-height: var(--line-height-snug);
}
.sp-feedback:empty { display: none; }
.sp-feedback[role="alert"] {
    background: var(--color-error-subtle);
    color: var(--color-error-text);
    border-color: var(--color-error-border);
}
.sp-feedback.sp-feedback-success {
    background: var(--color-success-subtle);
    color: var(--color-success-text);
    border-color: var(--color-success-border);
}
.sp-feedback.sp-feedback-info {
    background: var(--color-info-subtle);
    color: var(--color-info-text);
    border-color: var(--color-info-border);
}

.sp-empty {
    padding: var(--space-8);
    text-align: center;
    color: var(--color-text-muted);
    background: var(--color-bg-surface);
    border: 1px dashed var(--color-border);
    border-radius: var(--radius-lg);
}

/* ─── Dialog (uses native <dialog>) ───────────────────────── */
.sp-dialog,
dialog.sp-dialog {
    border: 1px solid var(--color-border);
    border-radius: var(--radius-xl);
    padding: var(--space-6);
    background: var(--color-bg-surface);
    color: var(--color-text-primary);
    box-shadow: var(--shadow-xl);
    max-width: 480px;
    width: 100%;
}
.sp-dialog::backdrop,
dialog.sp-dialog::backdrop {
    background: var(--color-bg-overlay);
}


/* ============================================================
   ERP COMMON COMPONENTS
   Patrones de ERP que faltaban en el vocabulario canónico y que
   antes cada módulo reinventaba (clinic-<x>-toolbar, -count, etc.).
   Todo tokenizado → paridad light/dark automática.
   ============================================================ */

/* ── Toolbar / filter bar ─────────────────────────────────────
   Barra horizontal para buscador + filtros + acciones. */
.ds-toolbar,
.ds-filter-bar {
    display: flex;
    align-items: center;
    gap: var(--space-3);
    flex-wrap: wrap;
}
.ds-filter-bar {
    padding: var(--space-3) var(--space-4);
    background: var(--color-bg-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
}
/* El buscador crece para ocupar el espacio disponible. */
.ds-toolbar-search,
.ds-filter-bar .ds-toolbar-search {
    position: relative;
    flex: 1 1 240px;
    min-width: 200px;
    display: flex;
    align-items: center;
}
.ds-toolbar-search > i {
    position: absolute;
    left: var(--space-3);
    color: var(--color-text-muted);
    pointer-events: none;
    font-size: var(--font-size-body-sm);
}
.ds-toolbar-search > input {
    width: 100%;
    padding-left: calc(var(--space-3) + 1.25rem);
}
/* Empuja lo que venga después al extremo opuesto. */
.ds-toolbar-spacer { flex: 1 1 auto; }

/* ── List view (cabecera con título + contador) ───────────────
   Envoltorio para vistas de lista/tabla con cabecera y cuerpo. */
.ds-list-view {
    display: flex;
    flex-direction: column;
    gap: var(--space-4);
}
.ds-list-view-header {
    display: flex;
    align-items: flex-start;
    justify-content: space-between;
    gap: var(--space-3);
}
.ds-list-view-header h2,
.ds-list-view-header h3 {
    margin: 0;
    font-size: var(--font-size-h4);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
}
.ds-list-view-header p {
    margin: var(--space-1) 0 0;
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
}
.ds-list-view-body { min-height: 0; }

/* Píldora de recuento (reemplaza clinic-<x>-count). */
.ds-count-pill {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 1.75rem;
    height: 1.75rem;
    padding: 0 var(--space-2);
    border-radius: var(--radius-full);
    background: var(--color-brand-subtle);
    color: var(--color-brand);
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-semibold);
    line-height: 1;
}

/* ── Pagination ───────────────────────────────────────────────
   No existía componente canónico; cada página inventaba el suyo. */
.ds-pagination {
    display: flex;
    align-items: center;
    gap: var(--space-1);
    flex-wrap: wrap;
}
.ds-pagination-item {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 2.25rem;
    height: 2.25rem;
    padding: 0 var(--space-2);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-bg-surface);
    color: var(--color-text-primary);
    font-size: var(--font-size-body-sm);
    cursor: pointer;
    transition: all var(--transition-fast);
}
.ds-pagination-item:hover:not(:disabled):not(.active) {
    background: var(--color-bg-elevated);
    border-color: var(--color-brand-border);
}
.ds-pagination-item.active {
    background: var(--color-brand);
    border-color: var(--color-brand);
    color: #fff;
    font-weight: var(--font-weight-semibold);
    cursor: default;
}
.ds-pagination-item:disabled {
    opacity: 0.45;
    cursor: not-allowed;
}

/* ── Severity badge ───────────────────────────────────────────
   Paleta de severidad tokenizada (antes hardcodeada en
   clinic_voice_reviews / clinic_voice_settings con hex). */
.ds-badge-severity {
    display: inline-flex;
    align-items: center;
    gap: var(--space-1);
    padding: 0.125rem var(--space-2);
    border-radius: var(--radius-full);
    font-size: var(--font-size-caption, 0.75rem);
    font-weight: var(--font-weight-semibold);
    line-height: 1.4;
    white-space: nowrap;
}
.ds-badge-severity.sev-info {
    background: var(--color-bg-elevated);
    color: var(--color-text-secondary);
}
.ds-badge-severity.sev-low {
    background: var(--color-success-subtle);
    color: var(--color-success-text, var(--color-success));
}
.ds-badge-severity.sev-medium {
    background: var(--color-warning-subtle);
    color: var(--color-warning-text, var(--color-warning));
}
.ds-badge-severity.sev-high {
    background: var(--color-error-subtle);
    color: var(--color-error-text, var(--color-error));
}
.ds-badge-severity.sev-critical {
    background: var(--color-error);
    color: #fff;
}

/* Dimensionado de selects/inputs dentro de la filter-bar (que no se
   estiren ni colapsen de forma rara en flex). */
.ds-filter-bar > select,
.ds-filter-bar > .form-select,
.ds-filter-bar > .ds-select {
    flex: 0 1 200px;
    min-width: 160px;
}

/* ── List (filas de registros seleccionables) ─────────────────
   Reemplaza los clinic-<x>-row/-list/-chip que cada módulo
   reinventaba. Ítem = botón/enlace con título + subtítulo + meta
   + valor a la derecha. */
.ds-list {
    display: grid;
    gap: var(--space-2-5);
    list-style: none;
    padding-left: 0;
    margin: 0;
}
.ds-list-item {
    width: 100%;
    display: grid;
    grid-template-columns: minmax(0, 1fr) auto;
    gap: var(--space-3);
    align-items: start;
    padding: var(--space-3-5);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    background: var(--color-bg-surface);
    color: inherit;
    text-align: left;
    cursor: pointer;
    transition: border-color var(--transition-fast), background-color var(--transition-fast);
}
.ds-list-item:hover,
.ds-list-item.is-selected {
    border-color: var(--color-brand-border);
    background: var(--color-bg-elevated);
}
.ds-list-item.is-muted,
.ds-list-item.is-archived {
    background: var(--color-bg-elevated);
}
.ds-list-item-title {
    margin: 0;
    font-size: var(--font-size-body-md);
    font-weight: var(--font-weight-semibold);
    color: var(--color-heading);
}
.ds-list-item-subtitle {
    margin: var(--space-1) 0 0;
    font-size: var(--font-size-body-sm);
    color: var(--color-text-secondary);
}
.ds-list-item-meta {
    display: flex;
    align-items: center;
    gap: var(--space-1-5);
    flex-wrap: wrap;
    margin-top: var(--space-2);
}
.ds-list-item-trailing {
    font-weight: var(--font-weight-bold);
    color: var(--color-heading);
    white-space: nowrap;
}
@media (max-width: 600px) {
    .ds-list-item { grid-template-columns: 1fr; }
}

/* ============================================================
   Marketing plan review (clinic marketing step 2)
   Budget bar + legend dots + collapsible package accordion
   ============================================================ */
.marketing-plan-bar {
    display: flex;
    height: 12px;
    border-radius: var(--radius-full);
    overflow: hidden;
    margin: var(--space-3) 0 var(--space-2);
    background: var(--color-bg-elevated);
}
.marketing-plan-bar-segment { height: 100%; }
.marketing-plan-dot {
    display: inline-block;
    width: var(--space-2-5);
    height: var(--space-2-5);
    border-radius: 50%;
    margin-right: var(--space-1);
    vertical-align: baseline;
}
/* Semantic tokens only: all four adapt per theme (border-strong has an
   explicit dark override, unlike the neutral primitives). */
.plan-bar-a { background: var(--color-brand); }
.plan-bar-b { background: var(--color-success); }
.plan-bar-c { background: var(--color-warning); }
.plan-bar-d { background: var(--color-border-strong); }
.marketing-plan-package > summary {
    cursor: pointer;
    list-style: none;
    display: flex;
    align-items: center;
    justify-content: space-between;
}
.marketing-plan-package > summary::-webkit-details-marker { display: none; }
.marketing-plan-package > summary::after {
    content: '\f078';
    font-family: 'Font Awesome 6 Free';
    font-weight: 900;
    font-size: 0.75rem;
    color: var(--color-text-secondary);
    transition: transform var(--transition-fast);
}
.marketing-plan-package[open] > summary::after { transform: rotate(180deg); }
.marketing-plan-accept {
    align-items: center;
    flex-wrap: wrap;
    margin-top: var(--space-3);
}

/* ============================================================
   Shared upload progress
   Used by FormData/XHR flows that can expose real upload bytes.
   ============================================================ */
.ml-upload-progress {
    display: grid;
    gap: var(--space-2);
    padding: var(--space-3);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-bg-surface);
}
.ml-upload-progress[hidden] {
    display: none;
}
.ml-upload-progress-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--space-3);
    color: var(--color-heading);
    font-size: var(--font-size-body-sm);
    font-weight: var(--font-weight-semibold);
}
.ml-upload-progress-status-wrap {
    display: inline-flex;
    align-items: center;
    min-width: 0;
    gap: var(--space-2);
}
.ml-upload-progress-spinner {
    display: none;
    width: 0.9rem;
    height: 0.9rem;
    flex: 0 0 auto;
    border: 2px solid color-mix(in srgb, var(--color-brand) 28%, transparent);
    border-top-color: var(--color-brand);
    border-radius: 50%;
}
.ml-upload-progress.is-processing .ml-upload-progress-spinner {
    display: inline-block;
    animation: ml-upload-progress-spin 0.8s linear infinite;
}
.ml-upload-progress-track {
    position: relative;
    width: 100%;
    height: 0.5rem;
    overflow: hidden;
    border-radius: var(--radius-full);
    background: color-mix(in srgb, var(--color-border) 64%, var(--color-bg-canvas));
}
.ml-upload-progress-bar {
    width: 0%;
    height: 100%;
    border-radius: inherit;
    background: var(--color-brand);
    transition: width var(--transition-fast);
}
.ml-upload-progress-detail {
    min-height: 1rem;
    color: var(--color-text-secondary);
    font-size: var(--font-size-body-xs);
}
.ml-upload-progress.is-indeterminate .ml-upload-progress-bar {
    width: 42%;
    animation: ml-upload-progress-indeterminate 1.15s ease-in-out infinite;
}
.ml-upload-progress.is-processing:not(.is-indeterminate) .ml-upload-progress-bar {
    background:
        linear-gradient(
            90deg,
            var(--color-brand) 0%,
            color-mix(in srgb, var(--color-brand) 70%, white) 48%,
            var(--color-brand) 100%
        );
    background-size: 220% 100%;
    animation: ml-upload-progress-processing 1.25s ease-in-out infinite;
}
@keyframes ml-upload-progress-indeterminate {
    0% { transform: translateX(-115%); }
    100% { transform: translateX(250%); }
}
@keyframes ml-upload-progress-processing {
    0% { background-position: 100% 0; }
    100% { background-position: -100% 0; }
}
@keyframes ml-upload-progress-spin {
    to { transform: rotate(360deg); }
}
@media (prefers-reduced-motion: reduce) {
    .ml-upload-progress-bar {
        transition: none;
    }
    .ml-upload-progress.is-indeterminate .ml-upload-progress-bar {
        animation: none;
        transform: none;
    }
    .ml-upload-progress.is-processing .ml-upload-progress-spinner,
    .ml-upload-progress.is-processing:not(.is-indeterminate) .ml-upload-progress-bar {
        animation: none;
    }
}
