/*
 * components.css — i pezzi ricorrenti del contenuto: card, tabelle, pill,
 * barre filtro, paginazione, stati vuoti.
 *
 * Le regole agiscono sulle classi Bootstrap già presenti nei template
 * (.card, .table, .pagination) invece di introdurre un vocabolario parallelo:
 * così una pagina si restilizza togliendo il suo <style>, senza riscriverne
 * il markup. Le uniche classi nuove sono quelle che Bootstrap non ha:
 * .pill, .filter-card, .sort-link, .empty-state.
 */

/* ── Card ─────────────────────────────────────────────────────────────────
   Bordo 1px e ombra appena percettibile: la profondità la fa il bordo, non
   l'ombra. Testata e piè di pagina su --ui-surface-2 (via --bs-card-cap-bg
   nel bridge), quindi qui basta regolare tipografia e spaziature. */
.card {
    box-shadow: var(--sh-xs);
}

.card-header {
    font-size: var(--fs-sm);
    font-weight: 600;
    color: var(--ui-text);
}

/* La barra accento a sinistra delle vecchie card è stata rimossa dal design:
   la gerarchia la dà l'header, non un filetto colorato. */

/* ── Card collassabile ────────────────────────────────────────────────────
   Trigger di un Bootstrap collapse (data-bs-toggle="collapse"), sia esso
   l'intero .card-header o solo una porzione (quando l'header contiene anche
   un'azione separata come "Vedi tutti", non annidata nel trigger): Bootstrap
   stesso aggiunge/rimuove .collapsed sul trigger in base allo stato del
   target, qui basta far ruotare la freccina di conseguenza. */
[data-bs-toggle="collapse"] {
    cursor: pointer;
}

[data-bs-toggle="collapse"] .chevron-icon {
    transition: transform .2s ease;
}

[data-bs-toggle="collapse"].collapsed .chevron-icon {
    transform: rotate(-90deg);
}

/* ── Card "hero" a gradiente ──────────────────────────────────────────────
   Un'unica card di rilievo per KPI di sintesi (oggi solo il Cruscotto
   Direzionale — "Copertura obiettivo"): sfondo pieno sull'accent invece del
   bordo sottile delle card normali. --ui-accent-contrast è già lo stesso
   colore di testo usato sui bottoni pieni, quindi il contrasto è garantito
   in entrambi i temi senza calcoli aggiuntivi qui. */
.hero-coverage {
    background: linear-gradient(160deg, var(--ui-accent) 0%, var(--ui-accent-hover) 100%);
    color: var(--ui-accent-contrast);
    border-radius: var(--r-xl);
    padding: var(--sp-6);
    box-shadow: var(--sh-md);
}

.hero-coverage .kpi-label,
.hero-coverage .small,
.hero-coverage .text-muted {
    color: var(--ui-accent-contrast);
    opacity: .85;
}

.hero-coverage .kpi-value {
    color: var(--ui-accent-contrast);
    font-size: var(--fs-3xl);
}

.hero-coverage .pill--accent {
    background-color: rgba(255, 255, 255, .18);
    color: var(--ui-accent-contrast);
    border-color: rgba(255, 255, 255, .35);
}

/* ── Tabelle ──────────────────────────────────────────────────────────────
   Righe a filo, nessuna zebra: con 50 colonne selezionabili la zebra somma
   rumore invece di aiutare la lettura. La separazione è la sola riga di
   bordo, l'orientamento lo dà l'hover. */
.table {
    --bs-table-bg: transparent;
    font-size: var(--fs-xs);
    margin-bottom: 0;
}

.table > :not(caption) > * > * {
    padding: .5rem .75rem;
    background-color: transparent;
    box-shadow: none;
}

.table > tbody > tr > * {
    vertical-align: middle;
    color: var(--ui-text);
}

.table > thead th {
    font-size: var(--fs-3xs);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: var(--ls-eyebrow);
    color: var(--ui-muted);
    background-color: var(--ui-surface-2);
    border-bottom: 1px solid var(--ui-border);
    white-space: nowrap;
}

.table > tbody > tr {
    border-color: var(--ui-border);
}

.table-hover > tbody > tr:hover > * {
    background-color: var(--ui-surface-3);
    color: var(--ui-text);
}

/* Righe che portano a una scheda: il cursore è l'unico indizio, quindi
   deve esserci. La navigazione vera è in app.js. */
tr.row-clickable {
    cursor: pointer;
}

/* Offerta collegata a un ordine (o viceversa): bordo sinistro verde sulla riga,
   oltre all'icona bi-link-45deg nella colonna nome (vedi orders/list.html,
   quotes/list.html). box-shadow inset invece di border-left: coi bordi delle
   celle già disegnati da .table, un border-left verrebbe troncato dal collapse. */
tr.row-linked > td:first-child {
    box-shadow: inset 3px 0 0 var(--success-border);
}

/* Commessa senza BU assegnata (dato incompleto da normalizzare): stesso trucco
   di .row-linked, ma in giallo — vedi commesse/list.html. */
tr.row-warning > td:first-child {
    box-shadow: inset 3px 0 0 var(--warning-border);
}

/* Le colonne di importi si allineano a destra per far coincidere le unità;
   le cifre a larghezza fissa arrivano da base.css. */
.amount-col {
    text-align: right;
}

/* ── Intestazioni ordinabili ──────────────────────────────────────────────
   La colonna attiva non cambia colore di fondo (spezzerebbe la riga di
   testata): si marca con un underline accento sotto l'etichetta. */
.sort-link,
.sortable {
    display: inline-flex;
    align-items: center;
    gap: var(--sp-1);
    color: inherit;
    text-decoration: none;
    white-space: nowrap;
    padding-bottom: 2px;
    border-bottom: 2px solid transparent;
    transition: color var(--dur-fast) var(--ease-out),
                border-color var(--dur-fast) var(--ease-out);
}

.sort-link:hover,
.sortable:hover {
    color: var(--ui-text);
    text-decoration: none;
}

.sort-link.active-sort,
.sortable.active-sort {
    color: var(--ui-text);
    border-bottom-color: var(--ui-accent);
}

/* ── Riga di filtri dentro il thead ───────────────────────────────────────
   Usata dalla tabella aziende: input a tutta cella, senza etichetta. */
.thead-filter th {
    padding: .3rem .5rem;
    background-color: var(--ui-surface-2);
    border-bottom: 1px solid var(--ui-border);
}

.thead-filter input,
.thead-filter select {
    width: 100%;
    height: auto;
    padding: .2rem .4rem;
    font-size: var(--fs-2xs);
    color: var(--ui-text);
    background-color: var(--ui-surface);
    border: 1px solid var(--ui-border);
    border-radius: var(--r-xs);
}

.thead-filter input:focus,
.thead-filter select:focus {
    outline: none;
    border-color: var(--ui-accent);
    box-shadow: 0 0 0 3px var(--ui-focus);
}

/* ── Pill ─────────────────────────────────────────────────────────────────
   Sostituisce i badge Bootstrap pieni: fondo tenue, testo saturo, bordo.
   Ogni variante legge la terna bg/fg/border dei token semantici, quindi
   funziona in entrambi i temi senza .text-dark scritto a mano. */
.pill {
    display: inline-flex;
    align-items: center;
    gap: var(--sp-1);
    padding: .1rem .5rem;
    border: 1px solid transparent;
    border-radius: var(--r-full);
    font-size: var(--fs-3xs);
    font-weight: 600;
    line-height: 1.6;
    white-space: nowrap;
}

.pill--success { background-color: var(--success-bg); color: var(--success-fg); border-color: var(--success-border); }
.pill--warning { background-color: var(--warning-bg); color: var(--warning-fg); border-color: var(--warning-border); }
.pill--danger  { background-color: var(--danger-bg);  color: var(--danger-fg);  border-color: var(--danger-border); }
.pill--info    { background-color: var(--info-bg);    color: var(--info-fg);    border-color: var(--info-border); }
.pill--neutral { background-color: var(--neutral-bg); color: var(--neutral-fg); border-color: var(--neutral-border); }
.pill--accent  { background-color: var(--ui-accent-subtle); color: var(--ui-accent); border-color: var(--ui-accent-border); }

/* Variante "spenta": conteggio a zero, campo assente. Nessun fondo. */
.pill--quiet {
    background-color: transparent;
    color: var(--ui-muted);
    border-color: var(--ui-border);
}

/* ── Coppie etichetta/valore ──────────────────────────────────────────────
   La struttura portante delle schede di dettaglio: una griglia di campi in
   sola lettura. L'etichetta è un'eyebrow, il valore il testo primario, così
   la scansione verticale funziona anche con 40 campi in colonna. */
.field-label {
    margin-bottom: var(--sp-1);
    font-size: var(--fs-3xs);
    font-weight: 600;
    letter-spacing: var(--ls-eyebrow);
    text-transform: uppercase;
    color: var(--ui-muted);
}

.field-value {
    font-size: var(--fs-sm);
    color: var(--ui-text);
    /* Gli URL e i codici fiscali non hanno spazi: senza questo allargano
       la colonna oltre la card. */
    word-break: break-word;
}

/* Campo assente: nessun trattino colorato di accento per errore. */
.field-value .empty,
.field-value.empty {
    color: var(--ui-disabled);
}

/* Le descrizioni libere sono l'unico valore senza lunghezza massima:
   troncate, altrimenti da sole dettano la larghezza della tabella. */
.cell-desc {
    max-width: 220px;
}

/* ── KPI ──────────────────────────────────────────────────────────────────
   Il valore resta nel colore del testo: colorarlo di accento (com'era) mette
   sullo stesso piano il dato e le azioni, e su una griglia di sei riquadri
   diventa una parete di indaco. L'accento lo tengono i pulsanti. */
.kpi-value {
    font-size: var(--fs-2xl);
    font-weight: 700;
    line-height: var(--lh-tight);
    color: var(--ui-text);
}

/* Variante per i KPI testuali (trend, dimensione): stessa gerarchia, corpo
   ridotto perché una parola lunga a --fs-2xl manda a capo il riquadro. */
.kpi-value--text {
    font-size: var(--fs-lg);
}

.kpi-label {
    margin-bottom: var(--sp-1);
    font-size: var(--fs-3xs);
    font-weight: 600;
    letter-spacing: var(--ls-eyebrow);
    text-transform: uppercase;
    color: var(--ui-muted);
}

/* Intestazione di sezione fra gruppi di grafici in pagine con molti blocchi (es. statistiche opportunità). */
.section-title {
    margin: var(--sp-4) 0 var(--sp-3);
    padding-bottom: var(--sp-2);
    border-bottom: 1px solid var(--ui-border);
    font-size: var(--fs-sm);
    font-weight: 700;
    letter-spacing: var(--ls-eyebrow);
    text-transform: uppercase;
    color: var(--ui-muted);
}

/* Variazione rispetto al periodo di confronto. */
.kpi-delta {
    margin-top: var(--sp-1);
    font-size: var(--fs-2xs);
    font-weight: 600;
}
.kpi-delta.up   { color: var(--success-fg); }
.kpi-delta.down { color: var(--danger-fg); }
.kpi-delta.flat { color: var(--ui-muted); }

/* ── Contenitori dei grafici ──────────────────────────────────────────────
   Chart.js con maintainAspectRatio:false disegna sull'altezza del genitore,
   che quindi deve averne una esplicita. Una proporzione invece di un'altezza
   fissa: a 1440px un grafico da 300px è schiacciato, a 375px la stessa
   altezza su una colonna sola lo rende illeggibile. Il min-height evita che
   la proporzione lo faccia collassare nelle colonne strette. Width esplicita
   necessaria: senza, in colonne strette il browser deriva la larghezza
   dall'altezza bloccata dal min-height (invece del contrario), sfondando il
   genitore e creando scroll orizzontale. */
.chart-container {
    position: relative;
    width: 100%;
    aspect-ratio: 16 / 10;
    min-height: 220px;
}

.chart-container--md { aspect-ratio: 4 / 3;  min-height: 280px; }
.chart-container--lg { aspect-ratio: 2 / 1;  min-height: 320px; }
.chart-container--xl { aspect-ratio: 16 / 7; min-height: 380px; }

/* Grafici a piena larghezza (col-12): l'aspect-ratio scala con la larghezza della
   colonna, e su una colonna intera diventa altissimo. Altezza fissa, come le altre. */
.chart-container--hero { aspect-ratio: unset; height: 340px; }

/* ── Barra azioni dei form ────────────────────────────────────────────────
   Appiccicata in fondo: i form azienda sono lunghi due schermate e senza
   questo il pulsante Salva richiede uno scroll fino in fondo per essere
   raggiunto — su telefono, ogni volta. */
.form-actions {
    position: sticky;
    bottom: 0;
    z-index: 3;
    display: flex;
    gap: var(--sp-2);
    margin-top: var(--sp-4);
    padding: var(--sp-3) 0;
    background-color: var(--ui-canvas);
    border-top: 1px solid var(--ui-border);
}

/* ── Barra filtri ─────────────────────────────────────────────────────────
   Non è una .card perché non ha testata né piè: è una superficie sola. */
.filter-card {
    background-color: var(--ui-surface);
    border: 1px solid var(--ui-border);
    border-radius: var(--r-md);
    box-shadow: var(--sh-xs);
}

.filter-group {
    padding-top: var(--sp-3);
}

.filter-group + .filter-group {
    border-top: 1px dashed var(--ui-border);
}

.filter-group-label {
    margin-bottom: var(--sp-2);
    font-size: var(--fs-3xs);
    font-weight: 600;
    letter-spacing: var(--ls-eyebrow);
    text-transform: uppercase;
    color: var(--ui-muted);
}

/* Pulsante "filtri avanzati" con il contatore dei filtri attivi appeso
   all'angolo: senza, la sezione collassata nasconde filtri in vigore. */
.btn-adv-toggle {
    position: relative;
}

.btn-adv-toggle .adv-badge {
    position: absolute;
    top: -6px;
    right: -6px;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 1.1rem;
    height: 1.1rem;
    padding: 0;
    border-radius: var(--r-full);
    background-color: var(--ui-accent);
    color: var(--ui-accent-contrast);
    font-size: var(--fs-3xs);
    font-weight: 600;
}

/* ── Periodo di confronto (pagine statistiche) ────────────────────────────
   Il confronto è un secondo asse di lettura sovrapposto al primo: gli serve
   un colore proprio, distinto dall'accento delle azioni. Usiamo il ruolo
   "warning", che è il colore della seconda serie anche nei grafici. */
.compare-section {
    margin-top: var(--sp-3);
    padding-top: var(--sp-3);
    border-top: 1px dashed var(--ui-border);
}

.compare-label { color: var(--warning-fg); }

.compare-input { border-color: var(--warning-border); }

.btn-compare {
    background-color: var(--warning-solid);
    border-color: var(--warning-solid);
    color: #1F2937;
}
.btn-compare:hover,
.btn-compare:focus {
    background-color: var(--warning-fg);
    border-color: var(--warning-fg);
    /* Il testo prende lo sfondo tenue del ruolo: è l'unica coppia che resta
       leggibile sia in chiaro (scuro su chiaro) sia in scuro (chiaro su
       scuro), dato che fg e bg si invertono tra i due temi. */
    color: var(--warning-bg);
}

/* ── Selettori a pillola: preset di periodo e modalità dei grafici ─────── */
.preset-btn,
.chart-mode-btn {
    padding: var(--sp-1) var(--sp-3);
    border-radius: var(--r-full);
    font-size: var(--fs-2xs);
}

.preset-btn.active,
.chart-mode-btn.active {
    background-color: var(--ui-accent);
    border-color: var(--ui-accent);
    color: var(--ui-accent-contrast);
}

/* ── Chip dei filtri attivi ───────────────────────────────────────────────
   Diverso dalla .pill: la chip è interattiva (porta una × che rimuove il
   filtro), la pill è solo un'etichetta di stato. */
.chip {
    display: inline-flex;
    align-items: center;
    gap: var(--sp-1);
    padding: var(--sp-1) var(--sp-2);
    border-radius: var(--r-full);
    background-color: var(--ui-accent-subtle);
    color: var(--ui-accent);
    font-size: var(--fs-2xs);
    font-weight: 500;
}

.chip--compare {
    background-color: var(--warning-bg);
    color: var(--warning-fg);
}

.chip a {
    color: inherit;
    text-decoration: none;
    opacity: .7;
}
.chip a:hover { opacity: 1; }

/* ── Etichette di form ────────────────────────────────────────────────── */
.form-label {
    margin-bottom: var(--sp-1);
    font-size: var(--fs-xs);
    font-weight: 500;
    color: var(--ui-text-2);
}

/* Su iOS un input sotto i 16px fa zoomare la pagina al focus, e lo zoom non
   torna indietro da solo. */
@media (max-width: 767.98px) {
    .form-control,
    .form-select {
        font-size: 16px;
    }
}

/* ── Paginazione ──────────────────────────────────────────────────────── */
.pagination {
    --bs-pagination-padding-x: .6rem;
    --bs-pagination-padding-y: .25rem;
    --bs-pagination-font-size: var(--fs-xs);
    gap: var(--sp-1);
}

/* ── Stato vuoto ──────────────────────────────────────────────────────────
   Un elenco vuoto senza spiegazione si legge come un errore: qui dice cosa
   è successo e offre l'unica azione utile (azzerare i filtri). */
.empty-state {
    padding: var(--sp-10) var(--sp-4);
    text-align: center;
}

.empty-state-icon {
    display: block;
    margin-bottom: var(--sp-3);
    font-size: 2rem;
    line-height: 1;
    color: var(--ui-disabled);
}

.empty-state-title {
    margin-bottom: var(--sp-1);
    font-size: var(--fs-sm);
    font-weight: 600;
    color: var(--ui-text);
}

.empty-state-message {
    margin-bottom: 0;
    font-size: var(--fs-xs);
    color: var(--ui-muted);
}

.empty-state-action {
    margin-top: var(--sp-4);
}

/* ── Tabelle su schermi stretti ───────────────────────────────────────────
   Le tabelle scorrono già in orizzontale dentro .table-responsive, ma senza
   indizio visivo nessuno se ne accorge: la sfumatura sul bordo destro dice
   che il contenuto continua. Sta sul contenitore, non sull'area di scroll,
   così non scorre via insieme alle colonne.

   .col-optional marca le colonne a bassa priorità delle tabelle a colonne
   fisse (ordini, offerte): sotto i 768px spariscono. */
@media (max-width: 991.98px) {
    .table-fade {
        position: relative;
    }

    .table-fade::after {
        content: '';
        position: absolute;
        top: 0;
        right: 0;
        bottom: 0;
        width: 28px;
        pointer-events: none;
        background: linear-gradient(to right, rgba(0, 0, 0, 0), var(--ui-surface));
    }
}

@media (max-width: 767.98px) {
    .col-optional {
        display: none;
    }
}
