/* ============================================================
   style.css — AFM Stiring — Design V2
   Sidebar sombre + palette ambre/vert — Notion/Slack inspired
   ============================================================ */

/* ============================================================
   DM Sans — hébergée en local (assets/fonts/)
   SIL Open Font License 1.1 — voir assets/fonts/OFL.txt

   Remplace l'ancien @import vers fonts.googleapis.com, qui était
   silencieusement BLOQUÉ par la Content-Security-Policy définie dans
   .htaccess (style-src 'self' / font-src 'self') : le site tournait
   en réalité sur la police de repli.

   Fichier variable unique (wght 400→700) au lieu de 4 graisses
   séparées : une seule requête, et plus aucun aller-retour vers Google.
   ============================================================ */

@font-face {
    font-family: 'DM Sans';
    font-style: normal;
    font-weight: 400 700;          /* plage variable */
    font-display: swap;
    src: url('../fonts/DMSans-var.woff2') format('woff2-variations'),
         url('../fonts/DMSans-var.woff2') format('woff2');
}

@font-face {
    font-family: 'DM Sans';
    font-style: italic;
    font-weight: 400;
    font-display: swap;
    src: url('../fonts/DMSans-Italic.woff2') format('woff2');
}

*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }

/* ═══════════════════════════════════════════════════
   DESIGN TOKENS — Light
   ═══════════════════════════════════════════════════ */
:root {
    /* Sidebar */
    --sidebar-bg: #1c1917;
    --sidebar-w: 240px;
    --sidebar-hover: rgba(255,255,255,.07);
    --sidebar-active: rgba(255,255,255,.12);
    --sidebar-text: rgba(255,255,255,.50);
    --sidebar-text-bright: rgba(255,255,255,.88);

    /* Surfaces */
    --color-bg:         #faf9f7;
    --color-surface:    #ffffff;
    --color-surface-alt:#f5f3f0;
    --color-border:     rgba(120,100,70,.10);
    --color-border-strong: rgba(120,100,70,.18);

    /* Text */
    --color-text:       #1c1917;
    --color-muted:      #78716c;
    --color-text-tertiary: #a8a29e;

    /* Accents */
    --color-primary:    #d97706;
    --color-primary-dk: #b45309;
    --color-primary-lt: #fffbeb;
    --color-primary-mid:#fef3c7;
    --color-accent:     #059669;
    --color-accent-dk:  #065f46;
    --color-accent-lt:  #ecfdf5;
    --color-accent-mid: #d1fae5;
    /* Module école arabe — indigo, distinct de l'ambre (tréso),
       du vert (secrétariat) et du bleu --color-info (badge bureau) */
    --color-ecole:      #4f46e5;
    --color-ecole-dk:   #4338ca;
    --color-ecole-lt:   #eef2ff;
    --color-ecole-mid:  #e0e7ff;

    /* Semantic */
    --color-danger:     #dc2626;
    --color-danger-lt:  #fef2f2;
    --color-success:    #16a34a;
    --color-success-lt: #f0fdf4;
    --color-warning:    #d97706;
    --color-warning-lt: #fffbeb;
    --color-info:       #2563eb;
    --color-info-lt:    #eff6ff;

    /* Shapes */
    --radius:           8px;
    --radius-lg:        12px;
    --radius-xl:        16px;
    --shadow:           0 1px 3px rgba(28,25,23,.05), 0 1px 2px rgba(28,25,23,.03);
    --shadow-md:        0 4px 16px rgba(28,25,23,.08);
    --shadow-lg:        0 12px 40px rgba(28,25,23,.12);
    --transition:       .15s ease;

    /* Font */
    --font: 'DM Sans', system-ui, -apple-system, sans-serif;
}

/* ═══════════════════════════════════════════════════
   DESIGN TOKENS — Dark
   ═══════════════════════════════════════════════════ */
[data-theme="dark"] {
    --sidebar-bg: #0c0a09;
    --color-bg:         #171412;
    --color-surface:    #231f1c;
    --color-surface-alt:#1c1917;
    --color-border:     rgba(255,255,255,.07);
    --color-border-strong: rgba(255,255,255,.13);
    --color-text:       #f5f5f4;
    --color-muted:      #a8a29e;
    --color-text-tertiary: #78716c;
    --color-primary:    #f59e0b;
    --color-primary-dk: #d97706;
    --color-primary-lt: #451a03;
    --color-primary-mid:#78350f;
    --color-accent:     #34d399;
    --color-accent-dk:  #10b981;
    --color-accent-lt:  #052e16;
    --color-accent-mid: #064e3b;
    --color-ecole:      #818cf8;
    --color-ecole-dk:   #a5b4fc;
    --color-ecole-lt:   #1e1b4b;
    --color-ecole-mid:  #312e81;
    --color-danger:     #f87171;
    --color-danger-lt:  #450a0a;
    --color-success:    #4ade80;
    --color-success-lt: #052e16;
    --color-warning:    #fbbf24;
    --color-warning-lt: #451a03;
    --color-info:       #60a5fa;
    --color-info-lt:    #172554;
    --shadow:           0 1px 3px rgba(0,0,0,.25);
    --shadow-md:        0 4px 16px rgba(0,0,0,.35);
    --shadow-lg:        0 12px 40px rgba(0,0,0,.5);
}

/* ═══════════════════════════════════════════════════
   BASE
   ═══════════════════════════════════════════════════ */
html {
    max-width: 100%;
    overflow-x: hidden;
}
body {
    font-family: var(--font);
    font-size: 14px;
    line-height: 1.55;
    color: var(--color-text);
    background: var(--color-bg);
    -webkit-font-smoothing: antialiased;
    transition: background var(--transition), color var(--transition);
    max-width: 100%;
    overflow-x: hidden;
}
img { max-width: 100%; height: auto; }
a { color: var(--color-primary); text-decoration: none; }
a:hover { text-decoration: underline; }

/* ═══════════════════════════════════════════════════
   LAYOUT — Sidebar + main
   ═══════════════════════════════════════════════════ */
.app-layout {
    display: flex;
    min-height: 100vh;
}
.main-area {
    margin-left: var(--sidebar-w);
    flex: 1;
    min-width: 0;
    display: flex;
    flex-direction: column;
}
.main-content {
    /* ⚠ width: 100% est indispensable, ce n'est pas une redondance.
       .main-area est un conteneur flex en colonne, et en flexbox une marge
       automatique sur l'axe transversal — ici « margin: 0 auto » — annule
       l'étirement : sans largeur explicite, ce bloc se réduit à la largeur
       de son contenu au lieu d'occuper les 960 px prévus.
       Invisible sur une page qui porte un grand tableau, qui remplit la
       largeur toute seule. Très visible sur une page de cartes étroites :
       l'écran Rapports se repliait sur une colonne de 400 px au milieu
       d'une fenêtre de 1900, et ses quatre cartes s'empilaient — dans un
       conteneur de largeur indéfinie, repeat(auto-fit, …) ne compte qu'une
       seule colonne.
       La règle mobile plus bas posait déjà width: 100% pour la même raison,
       sur le seul petit écran. */
    width: 100%;
    max-width: 960px;
    margin: 0 auto;
    padding: 24px 28px 100px;
}
.main-content.main-content--wide {
    max-width: 1100px;
}

@media (max-width: 768px) {
    .main-area { margin-left: 0; max-width: 100vw; min-width: 0; overflow-x: hidden; }
    .main-content { padding: 16px 12px 110px; width: 100%; max-width: 100%; min-width: 0; overflow-x: hidden; box-sizing: border-box; }
    /* Filet de sécurité : aucun enfant direct de main-content ne peut dépasser */
    .main-content > * { max-width: 100%; min-width: 0; }
}

/* ═══════════════════════════════════════════════════
   SIDEBAR
   ═══════════════════════════════════════════════════ */
/* Quatre étages, un seul défile : en-tête, modules, navigation du
   module (.sb-scroll), bloc utilisateur. Seul le troisième est de la
   navigation à proprement parler ; les autres doivent rester sous les
   yeux, y compris au bas d'une longue liste. */
.sidebar {
    width: var(--sidebar-w);
    background: var(--sidebar-bg);
    color: var(--sidebar-text);
    display: flex;
    flex-direction: column;
    position: fixed;
    top: 0; left: 0; bottom: 0;
    z-index: 200;
    border-right: 1px solid rgba(255,255,255,.05);
    /* Le défilement est descendu sur .sb-scroll : l'en-tête et le bloc
       utilisateur ne sont pas de la navigation, ils ne doivent pas
       partir avec elle. La barre elle-même ne défile donc plus. */
    overflow: hidden;
}

/* Entre les étages fixes : la navigation du module, et elle seule.
   min-height: 0 est indispensable — sans lui, un enfant flex refuse
   de devenir plus court que son contenu et le défilement remonterait
   sur la barre entière, ce qu'on vient justement d'empêcher. */
.sb-scroll {
    flex: 1;
    min-height: 0;
    overflow-y: auto;
    scrollbar-width: thin;
    scrollbar-color: rgba(255,255,255,.1) transparent;
}
.sb-scroll::-webkit-scrollbar { width: 4px; }
.sb-scroll::-webkit-scrollbar-thumb { background: rgba(255,255,255,.1); border-radius: 4px; }

/* Header */
.sb-header {
    padding: 18px 16px 14px;
    display: flex;
    align-items: center;
    gap: 10px;
    border-bottom: 1px solid rgba(255,255,255,.06);
    flex-shrink: 0;
}
.sb-logo {
    width: 32px; height: 32px;
    border-radius: 8px;
    display: flex; align-items: center; justify-content: center;
    font-size: 14px; font-weight: 700; color: #fff;
    flex-shrink: 0;
    transition: background .3s;
}
.sb-logo img { width: 100%; height: 100%; object-fit: contain; border-radius: 8px; }
.sb-logo--treso { background: linear-gradient(135deg, #d97706, #f59e0b); }
.sb-logo--secret { background: linear-gradient(135deg, #059669, #34d399); }
.sb-logo--ecole { background: linear-gradient(135deg, #4338ca, #6366f1); }
.sb-org { font-size: 13px; font-weight: 600; color: var(--sidebar-text-bright); line-height: 1.2; }
.sb-org-sub { font-size: 11px; color: var(--sidebar-text); margin-top: 1px; }

/* Module switcher */
/* flex-shrink: 0 — étage fixe : sans lui, les trois modules se
   feraient écraser par la navigation sur une fenêtre courte. */
.sb-modules { padding: 10px 10px 4px; flex-shrink: 0; }
.sb-module {
    display: flex; align-items: center; gap: 8px;
    margin: 3px 0; padding: 8px 10px;
    border-radius: 8px; cursor: pointer;
    font-size: 13px; font-weight: 600;
    text-decoration: none;
    transition: all .12s;
    border: none; width: 100%;
    font-family: var(--font); text-align: left;
}
.sb-module--treso {
    background: rgba(217,119,6,.12);
    color: #fbbf24;
}
.sb-module--treso:hover { background: rgba(217,119,6,.2); }
.sb-module--treso.active { background: rgba(217,119,6,.18); color: #fcd34d; }
.sb-module--secret {
    background: rgba(5,150,105,.12);
    color: #34d399;
}
.sb-module--secret:hover { background: rgba(5,150,105,.2); }
.sb-module--secret.active { background: rgba(5,150,105,.18); color: #6ee7b7; }
.sb-module--ecole {
    background: rgba(79,70,229,.14);
    color: #a5b4fc;
}
.sb-module--ecole:hover { background: rgba(79,70,229,.24); }
.sb-module--ecole.active { background: rgba(79,70,229,.22); color: #c7d2fe; }

/* Divider */
/* flex-shrink: 0 : celui qui sépare les modules de la navigation est
   un enfant direct de la barre, et un trait d'un pixel se fait
   écraser à zéro dans une colonne flex à l'étroit. */
.sb-divider { height: 1px; background: rgba(255,255,255,.06); margin: 8px 16px; flex-shrink: 0; }

/* Sections */
.sb-section { padding: 8px 10px 2px; }
.sb-label {
    font-size: 10px; font-weight: 700;
    text-transform: uppercase; letter-spacing: .08em;
    color: rgba(255,255,255,.25);
    padding: 0 6px; margin-bottom: 4px;
}
/* Sections repliables.
   Le chevron n'apparaît que sur les sections qui en ont une, pour ne
   pas laisser croire qu'un titre isolé se replie aussi. */
.sb-label--pliable {
    display: flex; align-items: center; justify-content: space-between;
    cursor: pointer; user-select: none;
    transition: color .12s;
}
.sb-label--pliable:hover { color: rgba(255,255,255,.55); }
.sb-label--pliable::after {
    content: '';
    width: 6px; height: 6px; margin-right: 2px;
    border-right: 1.5px solid currentColor;
    border-bottom: 1.5px solid currentColor;
    transform: rotate(45deg) translate(-2px, -2px);
    transition: transform .15s;
}
.sb-section--replie .sb-label--pliable::after {
    transform: rotate(-45deg) translate(-1px, 1px);
}
.sb-body { overflow: hidden; }
.sb-section--replie .sb-body { display: none; }
.sb-label--pliable:focus-visible {
    outline: 2px solid var(--sidebar-text-bright); outline-offset: 2px;
}

.sb-item {
    display: flex; align-items: center; gap: 8px;
    padding: 6px 10px; border-radius: 6px;
    font-size: 13px; font-weight: 500;
    color: var(--sidebar-text);
    text-decoration: none; cursor: pointer;
    transition: all .1s;
}
.sb-item:hover {
    background: var(--sidebar-hover);
    color: var(--sidebar-text-bright);
    text-decoration: none;
}
.sb-item.active {
    background: var(--sidebar-active);
    color: var(--sidebar-text-bright);
}
.sb-item .ico { font-size: 15px; width: 20px; text-align: center; flex-shrink: 0; }

/* User */
.sb-user {
    margin-top: auto;
    padding: 12px 14px;
    border-top: 1px solid rgba(255,255,255,.06);
    display: flex; flex-direction: column; gap: 8px;
    flex-shrink: 0;
}
.sb-user__top {
    display: flex; align-items: center; gap: 10px;
    min-width: 0;
}
.sb-avatar {
    width: 30px; height: 30px; border-radius: 50%;
    display: flex; align-items: center; justify-content: center;
    font-size: 11px; font-weight: 700; flex-shrink: 0;
}
.sb-avatar--treso { background: rgba(217,119,6,.2); color: #fbbf24; }
.sb-avatar--secret { background: rgba(5,150,105,.2); color: #34d399; }
.sb-avatar--ecole { background: rgba(79,70,229,.22); color: #a5b4fc; }
.sb-uname { font-size: 12px; font-weight: 600; color: var(--sidebar-text-bright); }
.sb-urole { font-size: 10px; color: var(--sidebar-text); text-transform: capitalize; }
.sb-user__info { flex: 1; min-width: 0; overflow: hidden; }
.sb-uname { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.sb-user__actions {
    display: flex; align-items: center; gap: 2px;
    width: 100%;
}
.sb-icon-btn {
    display: flex; align-items: center; justify-content: center;
    width: 28px; height: 28px; border-radius: 6px;
    background: none; border: none; cursor: pointer;
    color: var(--sidebar-text); font-size: .95rem;
    text-decoration: none; position: relative;
    transition: background .15s, color .15s;
    -webkit-tap-highlight-color: transparent;
}
.sb-icon-btn:hover { background: var(--sidebar-hover); color: var(--sidebar-text-bright); }
.sb-icon-btn--power { color: rgba(255,255,255,.35); }
.sb-icon-btn--power:hover { background: rgba(220,38,38,.15); color: #f87171; }
.sb-icon-badge {
    position: absolute; top: 2px; right: 2px;
    background: #ef4444; color: #fff;
    font-size: .5rem; font-weight: 700; line-height: 1;
    min-width: 12px; height: 12px; border-radius: 6px;
    display: flex; align-items: center; justify-content: center;
    padding: 0 2px;
}

/* Sidebar actions (recherche, notif, theme, logout) */
/* sb-actions removed — merged into sb-user block */
.sb-notif-count {
    margin-left: auto; font-size: 10px; font-weight: 700;
    padding: 1px 6px; border-radius: 999px;
    background: var(--color-danger); color: #fff;
    min-width: 16px; text-align: center;
}

/* Hide sidebar on mobile */
@media (max-width: 768px) {
    .sidebar { display: none; }
}

/* ═══════════════════════════════════════════════════
   MOBILE TOPBAR (replaces sidebar)
   ═══════════════════════════════════════════════════ */
.mobile-topbar {
    display: none;
    height: 48px;
    background: var(--sidebar-bg);
    padding: 0 10px;
    align-items: center;
    gap: 8px;
    position: sticky;
    top: 0;
    z-index: 200;
    border-bottom: 1px solid rgba(255,255,255,.06);
    overflow: hidden;
    max-width: 100vw;
    box-sizing: border-box;
}
.mobile-topbar .sb-logo { width: 26px; height: 26px; font-size: 12px; flex-shrink: 0; }
.mobile-topbar .sb-org {
    font-size: 13px; font-weight: 600; color: rgba(255,255,255,.88);
    white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
    min-width: 0; flex-shrink: 1;
}
/* flex-shrink: 1 + min-width: 0 + overflow-x: auto : sur un écran trop
   étroit pour les 3 onglets, c'est CETTE zone qui défile, plutôt que de
   forcer .mob-actions (recherche, notifs, thème, déconnexion) hors du
   bandeau — qui est en overflow: hidden et les rendait alors
   inatteignables, déconnexion comprise. */
.mob-tabs {
    display: flex; gap: 0; margin-left: auto; height: 100%;
    flex-shrink: 1; min-width: 0; overflow-x: auto; scrollbar-width: none;
}
.mob-tabs::-webkit-scrollbar { display: none; }
.mob-tab {
    padding: 0 10px; height: 100%;
    display: flex; align-items: center;
    font-size: 12px; font-weight: 600;
    color: rgba(255,255,255,.4);
    text-decoration: none;
    border-bottom: 2px solid transparent;
    transition: all .12s;
    white-space: nowrap;
    flex-shrink: 0;
}
.mob-tab:hover { color: rgba(255,255,255,.7); text-decoration: none; }
.mob-tab.active--treso { color: #fbbf24; border-bottom-color: #d97706; }
.mob-tab.active--secret { color: #34d399; border-bottom-color: #059669; }
.mob-tab.active--ecole { color: #a5b4fc; border-bottom-color: #4f46e5; }
.mob-tab-court { display: none; }

.mob-actions { display: flex; align-items: center; gap: 2px; margin-left: 4px; flex-shrink: 0; }
.mob-icon-btn {
    width: 30px; height: 30px; border-radius: 6px;
    border: none; background: transparent;
    color: rgba(255,255,255,.5); cursor: pointer;
    display: flex; align-items: center; justify-content: center;
    font-size: 14px; transition: all .12s;
    flex-shrink: 0;
}
.mob-icon-btn:hover { background: rgba(255,255,255,.08); color: rgba(255,255,255,.8); }
.mob-icon-btn--power { color: rgba(255,255,255,.35); text-decoration: none; }
.mob-icon-btn--power:hover { background: rgba(220,38,38,.2); color: #f87171; }

/* Menu ⋮ du bandeau (thème, mot de passe, administration, déconnexion).
   Son panneau est en position: fixed comme ceux de la sous-barre : le
   bandeau est en overflow: hidden, un panneau posé en absolu y serait
   rogné — c'est la contrainte déjà rencontrée sur iOS Safari. */
.mob-menu .mob-icon-btn { font-size: 18px; line-height: 1; }
.mob-menu.tn-open .mob-icon-btn { background: rgba(255,255,255,.12); color: #fff; }
/* Sélecteur en deux classes à dessein : il doit l'emporter sur la règle
   .tn-panel du mode mobile, écrite plus bas dans le fichier, qui colle
   les panneaux de la sous-barre sur toute la largeur. */
.mob-menu .tn-panel--compte {
    top: 52px;
    left: auto; right: 8px;
    width: 220px; min-width: 0; max-width: calc(100vw - 16px);
}
/* Une ligne de menu qui est un bouton (le thème) doit se présenter
   comme les liens voisins : le navigateur, lui, lui donne d'office une
   bordure, un fond et sa propre police.
   Sélecteurs en deux classes ici aussi : .tn-item est déclarée plus bas
   dans le fichier et reprendrait sinon la couleur de la déconnexion. */
.tn-panel--compte .tn-item--btn {
    width: 100%; text-align: left;
    background: none; border: none; cursor: pointer;
    font-family: var(--font); font-size: 13px;
}
.tn-panel--compte .tn-item--danger,
.tn-panel--compte .tn-item--danger:hover { color: var(--color-danger); }
.tn-panel--compte .tn-item--danger:hover { background: var(--color-danger-lt); }

@media (max-width: 768px) {
    .mobile-topbar { display: flex; }
    /* Un <select> sans largeur fixée se dimensionne parfois sur son
       option la plus longue (ex. un nom de groupe avec ses créneaux) et
       déborde de sa carte plutôt que de s'y contenir. Filet de sécurité
       général, pas propre à un écran. */
    select, input, textarea { max-width: 100%; }
}
/* Écrans étroits : les onglets de module passent à leur nom abrégé
   (clé 'court' de $MODULES).
   Ils n'affichaient auparavant que leur pictogramme, faute de place pour
   les trois noms complets — mais un pictogramme seul ne dit pas où mène
   le bouton à qui découvre le site. La place vient du regroupement des
   quatre actions de droite (thème, mot de passe, administration,
   déconnexion) derrière le menu ⋮ : un nom abrégé reste un nom. */
@media (max-width: 480px) {
    .mob-tab { padding: 0 8px; }
    .mob-tab-label { display: none; }
    .mob-tab-court { display: inline; }
}
/* Très petits écrans : masquer aussi le nom de l'asso (le logo suffit) */
@media (max-width: 420px) {
    .mobile-topbar .sb-org { display: none; }
    .mob-tab { padding: 0 8px; }
    .mob-icon-btn { width: 28px; height: 28px; font-size: 13px; }
}
@media (max-width: 360px) {
    .mob-tab { padding: 0 5px; font-size: 11px; }
}

/* ═══════════════════════════════════════════════════
   SUBNAV — mobile only (sidebar handles desktop nav)
   ═══════════════════════════════════════════════════ */
.subnav {
    height: 42px;
    background: var(--color-surface);
    border-bottom: 1px solid var(--color-border);
    display: none;
    align-items: center;
    padding: 0 24px;
    gap: 2px;
    overflow-x: auto;
    scrollbar-width: none;
    position: sticky;
    top: 48px;
    z-index: 100;
}
@media (max-width: 768px) {
    .subnav { display: flex; }
}
.subnav::-webkit-scrollbar { display: none; }

.sn-item, .tn-link {
    padding: 6px 12px; border-radius: 6px;
    font-size: 13px; font-weight: 500;
    color: var(--color-muted);
    text-decoration: none; white-space: nowrap;
    transition: all .12s;
    display: flex; align-items: center; gap: 5px;
}
.sn-item:hover, .tn-link:hover {
    background: var(--color-surface-alt);
    color: var(--color-text);
    text-decoration: none;
}
.sn-item.active, .sn-item.tn-on, .tn-link.tn-on {
    background: var(--color-primary-lt);
    color: var(--color-primary-dk);
    font-weight: 600;
}
/* Secrétariat active uses green */
.subnav--secret .sn-item.active,
.subnav--secret .tn-link.tn-on {
    background: var(--color-accent-lt);
    color: var(--color-accent-dk);
}
/* École arabe active uses indigo */
.subnav--ecole .sn-item.active,
.subnav--ecole .tn-link.tn-on,
.subnav--ecole .tn-btn.tn-on {
    background: var(--color-ecole-lt);
    color: var(--color-ecole-dk);
}

.sn-sep {
    width: 1px; height: 20px;
    background: var(--color-border);
    margin: 0 4px; flex-shrink: 0;
}

/* Dropdown in subnav */
.tn-dd, .sn-dd { position: relative; display: flex; align-items: center; flex-shrink: 0; }
.tn-btn, .sn-dd-btn {
    padding: 6px 10px; border-radius: 6px;
    font-size: 13px; font-weight: 500;
    color: var(--color-muted);
    background: none; border: none; cursor: pointer;
    font-family: var(--font);
    display: flex; align-items: center; gap: 4px;
    transition: all .12s; white-space: nowrap;
}
.tn-btn:hover, .sn-dd-btn:hover {
    background: var(--color-surface-alt);
    color: var(--color-text);
}
.tn-btn.tn-on { background: var(--color-primary-lt); color: var(--color-primary-dk); font-weight: 600; }
.tn-arr { font-size: .6rem; transition: transform .2s; margin-left: 2px; }
.tn-dd.tn-open .tn-arr { transform: rotate(180deg); }

.tn-panel, .sn-dd-panel {
    display: none;
    position: absolute;
    top: calc(100% + 4px);
    left: 0;
    min-width: 180px;
    background: var(--color-surface);
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    box-shadow: var(--shadow-lg);
    padding: 4px;
    z-index: 9999;
}
.tn-dd.tn-open .tn-panel,
.sn-dd.open .sn-dd-panel { display: block; }

.tn-item, .sn-dd-item {
    display: block;
    padding: 7px 12px;
    border-radius: 6px;
    font-size: 13px;
    color: var(--color-muted);
    text-decoration: none;
    transition: all .1s;
    white-space: nowrap;
}
.tn-item:hover, .sn-dd-item:hover {
    background: var(--color-surface-alt);
    color: var(--color-text);
}
.tn-item.tn-on {
    background: var(--color-primary-lt);
    color: var(--color-primary-dk);
    font-weight: 600;
}
/* Filet dans un menu déroulant : sépare ce qu'on consulte de ce qu'on
   administre, quand la barre n'a pas la place d'un menu de plus. */
.tn-sep { height: 1px; margin: 4px 8px; background: var(--color-border-strong); }

/* Subnav tréso — keep contextual style */
.subnav.subnav--treso,
.subnav.subnav--secret,
.subnav.subnav--ecole,
.subnav.subnav--admin { overflow: visible; }
.tn-bar {
    display: flex;
    align-items: center;
    padding: 0;
    gap: 2px;
    overflow: visible;
    width: 100%;
    flex-shrink: 0;
}

/* Subnav mobile — pictogramme au-dessus, nom en dessous.
 *
 *  Le nom était masqué pour faire tenir cinq entrées sur 375 px : il ne
 *  restait qu'une rangée d'emojis que seul quelqu'un connaissant déjà le
 *  site savait lire. Les empiler rend les deux lisibles pour une barre
 *  seulement 8 px plus haute.
 *
 *  Le pliage repose sur flex-wrap plutôt que sur flex-direction: column,
 *  parce que le bouton d'un groupe a trois enfants et non deux : son
 *  chevron ▾ doit rester à côté du nom, pas sur une troisième ligne.
 *  L'icône occupe donc une ligne entière (flex-basis: 100%), le nom et
 *  le chevron se partagent la suivante.
 */
@media (max-width: 768px) {
    .subnav { top: 48px; padding: 0 6px; height: 48px; }
    /* flex: 1 sur chaque onglet : les cinq destinations se partagent la
       largeur à parts égales, plutôt que de déborder d'un écran qui ne
       défile pas. */
    .tn-bar > .tn-link, .tn-bar > .tn-dd { flex: 1 1 0; min-width: 0; }
    .tn-bar .tn-link, .tn-bar .tn-btn {
        flex-wrap: wrap; justify-content: center; align-content: center;
        height: 44px; padding: 2px 1px; gap: 0;
        font-size: 9.5px; font-weight: 600; line-height: 1.15;
        text-align: center;
    }
    .tn-bar .tn-btn { width: 100%; }
    .tn-ico { flex: 0 0 100%; font-size: 16px; line-height: 1.2; }
    .tn-label {
        max-width: 100%; overflow: hidden;
        text-overflow: ellipsis; white-space: nowrap;
    }
    .tn-arr { font-size: 7px; margin-left: 1px; }
    .tn-panel {
        position: fixed;
        top: 100px;
        left: 8px;
        right: 8px;
        max-width: none;
        min-width: 0;
        border-radius: var(--radius-lg);
        box-shadow: var(--shadow-lg);
    }
}


/* ═══════════════════════════════════════════════════
   LOGIN PAGE
   ═══════════════════════════════════════════════════ */
.login-page {
    display: flex; align-items: center; justify-content: center;
    min-height: 100dvh; padding: 1rem;
    background: var(--sidebar-bg);
}
.login-container {
    background: var(--color-surface);
    border-radius: var(--radius-xl);
    box-shadow: var(--shadow-lg);
    padding: 2.5rem 2rem; width: 100%; max-width: 420px;
    transition: background var(--transition);
}
.login-logo { text-align: center; margin-bottom: 1.5rem; }
.login-logo img {
    width: 60px; height: 60px; object-fit: contain;
    margin-bottom: .75rem; border-radius: 12px;
    background: #fff; padding: 4px;
}
.login-logo h1 { font-size: 1.2rem; font-weight: 700; color: var(--color-primary); }
.login-logo .login-subtitle {
    font-size: .8rem; font-weight: 600; color: var(--color-accent);
    text-transform: uppercase; letter-spacing: .08em; margin-top: .2rem;
}
.login-logo p { color: var(--color-muted); font-size: .85rem; margin-top: .35rem; }
.login-help { text-align: center; margin-top: 1.25rem; font-size: .85rem; color: var(--color-muted); }
.login-help a { color: var(--color-primary); }

@media (max-width: 480px) {
    .login-container {
        border-radius: 0; padding: 2rem 1.25rem;
        max-width: 100%; min-height: 100dvh;
        display: flex; flex-direction: column; justify-content: center;
        box-shadow: none;
    }
}

/* ═══════════════════════════════════════════════════
   PAGE HEADER
   ═══════════════════════════════════════════════════ */
.page-header {
    display: flex; align-items: center; gap: 1rem;
    margin-bottom: 1.5rem; flex-wrap: wrap;
}
.page-header h1 {
    font-size: 1.4rem; font-weight: 700;
    letter-spacing: -.02em; flex: 1; min-width: 200px;
}
.page-header .text-muted { width: 100%; margin-top: -.5rem; font-size: .85rem; }
/* Boutons d'action d'un titre de page. Ils étaient posés dans un <div>
   nu : sur ordinateur ils s'alignent d'eux-mêmes, mais dès qu'une
   largeur d'écran les oblige à passer à la ligne, chacun garde la
   largeur de son texte et la rangée finit en escalier. */
.page-actions { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; }

@media (max-width: 768px) {
    .page-header h1 { font-size: 1.15rem; min-width: 0; }
    .page-header { margin-bottom: 1rem; }
}
/* Sur téléphone, ces boutons prennent toute la largeur du titre et se
   la partagent : deux courts tiennent une ligne, un long occupe la
   sienne en entier — plutôt que trois largeurs différentes décalées à
   gauche. */
@media (max-width: 640px) {
    .page-actions { width: 100%; }
    .page-actions > .btn { flex: 1 1 auto; justify-content: center; }
}

/* ═══════════════════════════════════════════════════
   FORMS
   ═══════════════════════════════════════════════════ */
.form-group { margin-bottom: 1.15rem; }
.form-group label {
    display: block; font-size: .82rem; font-weight: 600;
    margin-bottom: .35rem; color: var(--color-text);
}
/* Une case à cocher n'est pas un champ de saisie : la largeur pleine
   ci-dessous la fait dériver au milieu de sa ligne, loin de son
   libellé. Le sélecteur d'attribut passe devant la règle générique
   sans avoir à la réécrire. */
.form-group input[type="checkbox"],
.form-group input[type="radio"] { width: auto; }

.form-group input, .form-group select, .form-group textarea {
    width: 100%; padding: .5rem .75rem;
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    font-size: .9rem; color: var(--color-text);
    background: var(--color-surface);
    font-family: var(--font);
    transition: border-color var(--transition), box-shadow var(--transition);
}
.form-group input:focus, .form-group select:focus, .form-group textarea:focus {
    outline: none; border-color: var(--color-primary);
    box-shadow: 0 0 0 3px rgba(217,119,6,.12);
}
[data-theme="dark"] .form-group input:focus,
[data-theme="dark"] .form-group select:focus,
[data-theme="dark"] .form-group textarea:focus {
    box-shadow: 0 0 0 3px rgba(245,158,11,.15);
}
.form-group small { display: block; margin-top: .25rem; font-size: .78rem; color: var(--color-muted); }

/* ═══════════════════════════════════════════════════
   BUTTONS
   ═══════════════════════════════════════════════════ */
/*  Aucune règle n'existait pour cet état : « Envoyer à 0 membre(s) »,
    désactivé par le mécanisme des fenêtres d'envoi, gardait l'allure d'un
    bouton qui attend un clic. Vaut pour toutes les fenêtres d'envoi
    (convocation, diffusion du PV, reprise d'actions). */
.btn:disabled, .btn[disabled] { opacity: .5; cursor: not-allowed; box-shadow: none; }

.btn {
    display: inline-flex; align-items: center; justify-content: center; gap: .35rem;
    padding: .5rem 1.1rem; border-radius: var(--radius);
    font-size: .85rem; font-weight: 500; cursor: pointer;
    border: 1px solid var(--color-border-strong);
    background: var(--color-surface); color: var(--color-text);
    text-decoration: none; white-space: nowrap;
    font-family: var(--font);
    /* Un lien <a class="btn"> hérite de la hauteur de ligne de la page
       (1,55), un <button class="btn"> non : le navigateur lui impose la
       sienne, plus serrée. Deux boutons côte à côte — « Modifier » (un
       lien) et « Autres actions » (un bouton) — n'avaient donc pas la
       même hauteur. On aligne les liens sur les boutons, et non
       l'inverse : les boutons sont de loin les plus nombreux, c'est
       l'apparence que le site a déjà presque partout. */
    line-height: normal;
    transition: all var(--transition);
}
.btn:hover { background: var(--color-surface-alt); text-decoration: none; }
.btn:active { transform: scale(.97); }
.btn-primary { background: var(--color-primary); color: #fff; border-color: var(--color-primary); }
.btn-primary:hover { background: var(--color-primary-dk); }
.btn-secondary { background: var(--color-surface); color: var(--color-text); border-color: var(--color-border-strong); }
.btn-secondary:hover { background: var(--color-surface-alt); }
.btn-danger { background: var(--color-danger); color: #fff; border-color: var(--color-danger); }
.btn-danger:hover { opacity: .9; }
.btn-sm { padding: .3rem .7rem; font-size: .78rem; }
.btn-xs { padding: .2rem .5rem; font-size: .72rem; }
.btn-full { width: 100%; }
.btn-group { display: flex; gap: .5rem; flex-wrap: wrap; }

/* ═══════════════════════════════════════════════════
   ALERTS
   ═══════════════════════════════════════════════════ */
.alert {
    padding: .75rem 1rem; border-radius: var(--radius);
    font-size: .85rem; margin-bottom: 1rem;
    border: 1px solid transparent;
    display: flex; align-items: center; gap: 8px; flex-wrap: wrap;
    /* flex-wrap: un texte qui dépasse une ligne se compose de plusieurs
       items flex anonymes (le texte avant un lien, le lien, le texte
       après) : sans ce flex-wrap, ils se serrent chacun sur une seule
       ligne au lieu de s'enchaîner normalement, et le texte se
       fragmente en colonnes étroites illisibles. */
}
.alert-error, .alert-danger { background: var(--color-danger-lt); color: var(--color-danger); border-color: #fecaca; }
.alert-success { background: var(--color-success-lt); color: var(--color-success); border-color: #bbf7d0; }
.alert-info { background: var(--color-info-lt); color: var(--color-info); border-color: #bfdbfe; }
.alert-warning { background: var(--color-warning-lt); color: var(--color-warning); border-color: var(--color-primary-mid); }

[data-theme="dark"] .alert-error, [data-theme="dark"] .alert-danger { border-color: #7f1d1d; }
[data-theme="dark"] .alert-success { border-color: #14532d; }
[data-theme="dark"] .alert-info { border-color: #1e3a5f; }
[data-theme="dark"] .alert-warning { border-color: #78350f; }

/* ═══════════════════════════════════════════════════
   CARDS
   ═══════════════════════════════════════════════════ */
.card {
    background: var(--color-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    box-shadow: var(--shadow);
    overflow: hidden;
    transition: background var(--transition), border-color var(--transition);
}
.card-body { padding: 1.25rem; }
.card-header {
    display: flex; align-items: center; justify-content: space-between;
    padding: .85rem 1.25rem;
    border-bottom: 1px solid var(--color-border);
}
.card-header h2 { font-size: .95rem; font-weight: 600; margin: 0; }
.card-header h2 small { font-weight: 400; color: var(--color-muted); font-size: .78rem; }

/* ═══════════════════════════════════════════════════
   TABLES
   ═══════════════════════════════════════════════════ */
.table { width: 100%; border-collapse: collapse; font-size: .85rem; }
.table th {
    text-align: left; padding: .6rem .75rem;
    font-weight: 600; font-size: .72rem;
    color: var(--color-text-tertiary);
    text-transform: uppercase; letter-spacing: .04em;
    border-bottom: 1px solid var(--color-border);
    background: var(--color-surface-alt);
}
.table td {
    padding: .65rem .75rem;
    border-bottom: 1px solid var(--color-border);
    vertical-align: middle;
}
.table tr:last-child td { border-bottom: none; }
.table tr:hover td { background: var(--color-surface-alt); }
.table td a { color: var(--color-primary); text-decoration: none; font-weight: 500; }
.table td small { display: block; color: var(--color-muted); font-size: .72rem; }
.table-responsive { overflow-x: auto; -webkit-overflow-scrolling: touch; }
/* Un tableau en width: 100% ne déborde jamais tant que son texte peut
   se couper : les en-têtes se replient sur plusieurs lignes au lieu de
   déclencher le défilement de .table-responsive, qui ne sert alors à
   rien. Les en-têtes restent sur une ligne, quitte à élargir le
   tableau au-delà du conteneur — c'est justement ce qui fait défiler. */
.table-responsive .table th { white-space: nowrap; }

/* Bouton « Tout déplier / Tout replier » d'un tableau repliable
   (voir .table-mobile--repliable ci-dessous) : posé par le JS de
   footer.php, il n'a de sens que dans la vue carte du mobile — sur
   ordinateur le tableau est déjà entièrement visible. */
.table-mobile-toggle-all { display: none; }

/* Mobile table → cards */
@media (max-width: 768px) {
    /* Seul un tableau passé en cartes (.table-mobile) a besoin de ce
       débordement visible, pour que ses menus déroulants ne soient pas
       rognés. Un tableau resté classique dans un .table-responsive doit
       au contraire continuer à défiler, pas déborder de sa carte. */
    .table-responsive:has(.table-mobile) { overflow-x: visible; }
    .card { overflow: visible; }
    .table-mobile { min-width: 0 !important; border-collapse: separate; border-spacing: 0; }
    .table-mobile thead { display: none; }
    .table-mobile tbody { display: block; }
    .table-mobile tbody tr {
        display: block; background: var(--color-surface);
        border: 1px solid var(--color-border);
        border-radius: var(--radius);
        padding: .85rem; margin-bottom: .6rem;
        box-shadow: var(--shadow);
    }
    .table-mobile tbody td {
        display: flex; flex-wrap: wrap; justify-content: space-between; align-items: center;
        padding: .25rem 0; border-bottom: none; font-size: .85rem; width: 100% !important;
        gap: .1rem .5rem; min-width: 0; overflow-wrap: anywhere; word-break: break-word;
    }
    .table-mobile tbody td::before {
        content: attr(data-label); font-weight: 600; font-size: .68rem;
        text-transform: uppercase; letter-spacing: .03em;
        color: var(--color-text-tertiary); margin-right: .75rem; flex-shrink: 0;
    }
    .table-mobile tbody td > * { min-width: 0; overflow-wrap: anywhere; word-break: break-word; }
    /* Une valeur courte (date, code...) reste à côté de son étiquette ;
       une sous-ligne de détail (âge, enseignant, créneaux...) — toujours
       posée dans un <div> — passe systématiquement à la ligne plutôt que
       de se coincer à côté et de se couper lettre par lettre. */
    .table-mobile tbody td > div { flex-basis: 100%; }
    /* La sous-ligne (téléphone, âge, enseignant...) doit rester rattachée
       visuellement à la valeur au-dessus, qui est poussée à droite par
       justify-content: space-between — sinon elle retombe à gauche et
       semble appartenir à la ligne précédente. Le premier <td> fait
       exception : il agit comme un titre de carte, aligné à gauche. */
    .table-mobile tbody td:not(:first-child) > div { text-align: right; }
    .table-mobile tbody td:first-child {
        font-weight: 600; margin-bottom: .3rem;
        padding-bottom: .35rem; border-bottom: 1px solid var(--color-border);
        display: block;
    }
    .table-mobile tbody td:first-child::before { display: none; }
    .table-mobile tr:hover td { background: transparent; }
    /* Plusieurs boutons d'action dans une cellule : chacun est un item
       flex indépendant, donc dès qu'ils ne tiennent plus sur une seule
       ligne, celui qui passe à la ligne suivante se retrouve seul et
       colle à gauche au lieu de rester avec le premier. En les
       regroupant dans .table-mobile-actions, ce bloc devient un item
       unique (flex-basis: 100% via la règle des <div> ci-dessus) qui
       gère lui-même l'alignement à droite de son contenu. */
    .table-mobile tbody td > .table-mobile-actions {
        display: flex; flex-wrap: wrap; justify-content: flex-end;
        gap: .35rem;
    }
    /* Colonne présente dans le tableau desktop (et sur la fiche
       complète) mais superflue dans le coup d'œil rapide d'une carte
       mobile — typiquement une valeur dont une autre ligne visible est
       déjà la différence ou le résultat. */
    .table-mobile tbody td.table-mobile-secondary { display: none; }
    /* En-tête de carte avec nom + badge d'alerte + case à cocher : trois
       éléments qui se serrent sinon sur une seule ligne. Scopé à cette
       classe plutôt qu'à .card-header en général, pour ne pas changer
       les en-têtes des autres modules. */
    .ecole-header-wrap { flex-wrap: wrap; }

    /* Tableaux repliables (.table-mobile--repliable) : sur une liste
       de plusieurs dizaines d'élèves ou de familles, afficher chaque
       ligne en entier impose un défilement interminable. Seul le
       premier <td> (et ceux marqués .table-mobile-glance) reste visible
       par défaut ; un clic dessus déplie le reste. Le clic est branché
       dans footer.php, mutualisé comme .card--pliable — toute liste qui
       ajoute cette classe en hérite sans JS à écrire.
       Scopé à --repliable : les autres tableaux .table-mobile restent
       entièrement visibles comme avant. */
    .table-mobile-toggle-all { display: inline-flex; margin: .75rem .85rem .1rem; }
    .table-mobile--repliable tbody td:first-child {
        position: relative; padding-right: 1.5rem;
        cursor: pointer; user-select: none;
    }
    .table-mobile--repliable tbody td:first-child::after {
        content: ''; position: absolute; right: .15rem; top: .5rem;
        width: 7px; height: 7px;
        border-right: 2px solid var(--color-muted);
        border-bottom: 2px solid var(--color-muted);
        transform: rotate(45deg) translate(-1px, -2px);
        transition: transform .15s;
    }
    .table-mobile--repliable tbody tr.tr--ouverte td:first-child::after {
        transform: rotate(-45deg) translate(-1px, 1px);
    }
    .table-mobile--repliable tbody tr:not(.tr--ouverte) td:not(:first-child):not(.table-mobile-glance) {
        display: none;
    }
    /* Détail porté par le premier <td> lui-même — l'email et
       l'identifiant sous un nom de compte. Utile une fois la ligne
       ouverte, mais il triple la hauteur de l'en-tête de carte, qui est
       justement la seule chose censée rester visible quand tout est
       replié. Posé ici plutôt que dans la feuille d'un écran : toute
       liste repliable finit par avoir une sous-ligne de ce genre. */
    .table-mobile--repliable tbody tr:not(.tr--ouverte) .table-mobile-detail {
        display: none;
    }
}

/* ═══════════════════════════════════════════════════
   STAT CARDS
   ═══════════════════════════════════════════════════ */
.stats-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
    gap: .75rem; margin-bottom: 1.5rem;
}
.stat-card {
    background: var(--color-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    padding: 1rem 1.15rem;
    box-shadow: var(--shadow);
    position: relative; overflow: hidden;
    transition: all .15s;
}
.stat-card::before {
    content: ''; position: absolute;
    top: 0; left: 0; right: 0; height: 3px;
    border-radius: 3px 3px 0 0;
    background: var(--color-border);
}
.stat-card--primary::before { background: var(--color-primary); }
.stat-card--accent::before { background: var(--color-accent); }
.stat-card--danger::before { background: var(--color-danger); }
.stat-card--info::before { background: var(--color-info); }
.stat-card:hover { box-shadow: var(--shadow-md); border-color: var(--color-border-strong); }
.stat-card--link { text-decoration: none; display: block; cursor: pointer; color: inherit; }
.stat-card--link:hover { transform: translateY(-1px); }
.stat-card .stat-value {
    font-size: 1.6rem; font-weight: 700;
    letter-spacing: -.02em; color: var(--color-text);
    line-height: 1.1;
}
.stat-card--danger .stat-value { color: var(--color-danger); }
.stat-card .stat-label {
    font-size: .72rem; font-weight: 500;
    color: var(--color-text-tertiary);
    margin-bottom: 4px;
    text-transform: uppercase; letter-spacing: .03em;
}
.stat-card .stat-sub { font-size: .75rem; color: var(--color-muted); margin-top: 4px; }

@media (max-width: 768px) {
    .stats-grid { grid-template-columns: repeat(2, 1fr); gap: .5rem; }
    .stat-card { padding: .75rem .65rem; }
    .stat-card .stat-value { font-size: 1.25rem; }
    .stat-card .stat-label { font-size: .65rem; }
    /* Sur 2 colonnes, une tuile qui doit rester seule sur sa ligne
       (ex. le compte bancaire, à distinguer des caisses d'espèces qui
       se comparent côte à côte). En desktop la grille a la place : elle
       rejoint simplement la même ligne que les autres tuiles. */
    .stat-card--full { grid-column: 1 / -1; }
}

/* ═══════════════════════════════════════════════════
   BADGES
   ═══════════════════════════════════════════════════ */
.badge {
    display: inline-block; padding: .15rem .5rem;
    border-radius: 999px; font-size: .7rem; font-weight: 600;
}
.badge-brouillon { background: var(--color-surface-alt); color: var(--color-muted); }
.badge-relecture { background: var(--color-warning-lt); color: var(--color-primary-dk); }
.badge-approuve  { background: var(--color-success-lt); color: var(--color-accent-dk); }
.badge-danger    { background: var(--color-danger-lt); color: var(--color-danger); }

/* Plus de text-transform: capitalize — ces badges portent maintenant le
   libellé du rôle (« École arabe », « Enseignant ») et non sa clé en
   base (« ecole », « prof ») : capitaliser chaque mot en faisait
   « École Arabe ». */
.role-badge {
    display: inline-block; padding: .1rem .4rem;
    border-radius: 999px; font-size: .65rem; font-weight: 600;
}
.role-admin      { background: var(--color-primary); color: #fff; }
.role-secretaire { background: var(--color-accent); color: #fff; }
.role-tresorier  { background: var(--color-primary); color: #fff; }
.role-bureau     { background: var(--color-info); color: #fff; }
.role-cotisations{ background: var(--color-accent); color: #fff; }
.role-ecole      { background: var(--color-ecole); color: #fff; }
/* Enseignant : dans la famille indigo de l'école, mais en teinte claire
   — il vient à l'école sans en être le responsable. C'était le seul rôle
   sans règle ici, son badge s'affichait donc sans fond du tout. Les deux
   variables s'inversent en thème sombre (fond foncé, texte clair), le
   contraste tient des deux côtés sans règle supplémentaire. */
.role-prof       { background: var(--color-ecole-mid); color: var(--color-ecole-dk); }
.role-membre     { background: var(--color-surface-alt); color: var(--color-muted); }

[data-theme="dark"] .badge-brouillon { background: rgba(255,255,255,.08); }
[data-theme="dark"] .badge-relecture { background: var(--color-primary-lt); }
[data-theme="dark"] .badge-approuve  { background: var(--color-accent-lt); }
[data-theme="dark"] .badge-danger    { background: var(--color-danger-lt); }

/* ═══════════════════════════════════════════════════
   PAGINATION
   ═══════════════════════════════════════════════════ */
.pagination {
    display: flex; align-items: center; justify-content: center;
    gap: .3rem; margin-top: 1.5rem; flex-wrap: wrap;
}
.pagination a, .pagination span {
    display: inline-flex; align-items: center; justify-content: center;
    min-width: 34px; height: 34px; padding: 0 .5rem;
    border-radius: var(--radius); font-size: .82rem; font-weight: 500;
    text-decoration: none; border: 1px solid var(--color-border);
    background: var(--color-surface); color: var(--color-text);
    transition: all var(--transition);
}
.pagination a:hover { background: var(--color-surface-alt); border-color: var(--color-primary); }
.pagination .active { background: var(--color-primary); color: #fff; border-color: var(--color-primary); }
.pagination .disabled { opacity: .4; pointer-events: none; }
.pagination-info { text-align: center; font-size: .78rem; color: var(--color-muted); margin-top: .4rem; }
/* Libellés de « Précédente / Suivante » : complets, abrégés sur un petit
   écran — jamais une flèche seule. */
.pagination-court { display: none; }
@media (max-width: 480px) {
    .pagination-long { display: none; }
    .pagination-court { display: inline; }
}

/* ═══════════════════════════════════════════════════
   FILTERS
   ═══════════════════════════════════════════════════ */
.filters-bar {
    display: flex; gap: .75rem; flex-wrap: wrap;
    margin-bottom: 1.25rem; align-items: flex-end;
}
.filters-bar .form-group { margin-bottom: 0; }
/* .filters n'avait AUCUNE règle : les sélecteurs d'année de l'école
   tombaient sur l'apparence native du navigateur. */
.filters { display: flex; gap: .6rem; flex-wrap: wrap; align-items: center; }

/* Une seule règle pour les trois familles de barres de filtres, plutôt
   qu'une copie chacune. Le journal et .filters ne posaient ni bordure,
   ni fond, ni arrondi : leurs champs ne ressemblaient pas au reste du
   site. Les ajouter ici plutôt qu'à côté évite qu'une quatrième barre
   soit un jour oubliée de la même façon. */
.filters-bar select, .filters-bar input,
.filters select, .filters input,
.journal-filter-form select, .journal-filter-form input,
/* La barre des courriers manquait ici : sa recherche et son menu de
   statut gardaient l'apparence brute du navigateur. */
.cour-filtres-main select, .cour-filtres-main input {
    padding: .4rem .6rem; font-size: .82rem;
    border: 1px solid var(--color-border-strong); border-radius: var(--radius);
    background: var(--color-surface); color: var(--color-text);
    font-family: var(--font);
}
.filters-bar .btn,
.filters .btn,
.journal-filter-form .btn { padding: .4rem .75rem; font-size: .82rem; }

@media (max-width: 768px) {
    /* Deux menus par ligne, les boutons partagent la suivante : en colonne,
       quatre menus, « Filtrer » et « Retirer les filtres » faisaient six
       lignes pleine largeur avant la première réunion. Même principe que
       les barres de l'école. */
    .filters-bar { gap: .5rem; align-items: stretch; }
    .filters-bar .form-group { flex: 1 1 calc(50% - .25rem); min-width: 0; }
    .filters-bar select, .filters-bar input { width: 100%; }
    .filters-bar .btn { flex: 1 1 0; justify-content: center; }
}

/* ═══════════════════════════════════════════════════
   DASHBOARD SPECIFIC
   ═══════════════════════════════════════════════════ */
.dashboard-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(380px, 1fr));
    gap: 1.25rem;
}
@media (max-width: 768px) {
    .dashboard-grid { grid-template-columns: 1fr; }
}

/* Action list */
.action-list { list-style: none; display: flex; flex-direction: column; gap: .6rem; }
.action-item {
    padding: .65rem .85rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    border-left: 3px solid var(--color-primary);
    transition: background var(--transition);
}
.action-item--late { border-left-color: var(--color-danger); background: var(--color-danger-lt); }
.action-desc { font-size: .85rem; font-weight: 500; margin-bottom: .2rem; }
.action-meta { display: flex; gap: .75rem; font-size: .78rem; color: var(--color-muted); flex-wrap: wrap; }

/* ═══════════════════════════════════════════════════
   NOTIFICATION BELL
   ═══════════════════════════════════════════════════ */
.notif-bell { position: relative; text-decoration: none; font-size: 1.1rem; line-height: 1; }
.notif-badge {
    position: absolute; top: -6px; right: -8px;
    background: var(--color-danger); color: #fff;
    font-size: .6rem; font-weight: 700;
    min-width: 15px; height: 15px; border-radius: 999px;
    display: flex; align-items: center; justify-content: center; padding: 0 3px;
}
.notif-badge.hidden { display: none; }

/* ═══════════════════════════════════════════════════
   THEME TOGGLE
   ═══════════════════════════════════════════════════ */
.theme-toggle {
    background: none; border: none; cursor: pointer;
    font-size: 1rem; line-height: 1; padding: 4px;
    border-radius: 6px; transition: background var(--transition);
    display: flex; align-items: center; justify-content: center;
}

/* ═══════════════════════════════════════════════════
   SEARCH OVERLAY
   ═══════════════════════════════════════════════════ */
.search-overlay {
    display: none; position: fixed; inset: 0;
    background: rgba(0,0,0,.45); z-index: 10000;
    align-items: flex-start; justify-content: center;
    padding: 80px 16px 16px;
}
.search-overlay.open { display: flex; }
.search-box {
    background: var(--color-surface);
    border-radius: var(--radius-lg);
    max-width: 560px; width: 100%;
    box-shadow: var(--shadow-lg);
    overflow: hidden;
}
.search-input-wrap {
    display: flex; align-items: center; gap: 10px;
    padding: 14px 18px;
    border-bottom: 1px solid var(--color-border);
}
.search-input-wrap input {
    flex: 1; border: none; outline: none; font-size: .9rem;
    background: transparent; color: var(--color-text);
    font-family: var(--font);
}
.search-input-wrap input::placeholder { color: var(--color-muted); }
.search-esc {
    font-size: .62rem; padding: 2px 6px; border-radius: 4px;
    background: var(--color-surface-alt); color: var(--color-muted);
    border: 1px solid var(--color-border);
}
.search-results { max-height: 420px; overflow-y: auto; }
.search-section {
    font-size: .62rem; font-weight: 700; text-transform: uppercase;
    letter-spacing: 1.5px; color: var(--color-muted);
    padding: 10px 18px 4px;
}
.search-item {
    display: flex; align-items: center; gap: 12px;
    padding: 9px 18px; cursor: pointer;
    text-decoration: none; color: var(--color-text);
    transition: background .08s;
}
.search-item:hover, .search-item.active { background: var(--color-surface-alt); }
.search-item-icon { font-size: 1rem; flex-shrink: 0; width: 22px; text-align: center; }
.search-item-text { flex: 1; min-width: 0; }
.search-item-title {
    font-size: .82rem; font-weight: 600;
    overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.search-item-sub {
    font-size: .7rem; color: var(--color-muted);
    overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.search-empty { padding: 24px; text-align: center; color: var(--color-muted); font-size: .82rem; }

/* ═══════════════════════════════════════════════════
   BOTTOM BAR (mobile)
   ═══════════════════════════════════════════════════ */
.bottom-bar {
    display: none;
    position: fixed; bottom: 0; left: 0; right: 0;
    background: var(--color-surface);
    border-top: 1px solid var(--color-border);
    z-index: 900;
    padding: 6px 0 max(6px, env(safe-area-inset-bottom, 0px));
    justify-content: space-around;
}
.bb-item {
    display: flex; flex-direction: column; align-items: center; gap: 2px;
    text-decoration: none; color: var(--color-muted);
    font-size: .65rem; font-weight: 600;
    padding: 4px 12px; border-radius: var(--radius);
    transition: color .15s;
    -webkit-tap-highlight-color: transparent;
}
.bb-item .bb-icon { font-size: 1.2rem; line-height: 1; }
.bb-item .bb-label { font-size: .62rem; }
.bb-item.active { color: var(--color-primary); }
.bb-item:hover { color: var(--color-primary); text-decoration: none; }

@media (max-width: 768px) {
    .bottom-bar { display: flex; }
}

/* ═══════════════════════════════════════════════════
   FOOTER
   ═══════════════════════════════════════════════════ */
.app-footer {
    margin-top: auto; padding: 1rem 1.5rem;
    border-top: 1px solid var(--color-border);
    font-size: .72rem; color: var(--color-muted);
    display: flex; align-items: center; gap: .5rem; flex-wrap: wrap;
}
.app-footer a { color: var(--color-muted); text-decoration: none; }
.app-footer a:hover { color: var(--color-primary); }
.footer-sep { opacity: .3; }

@media (max-width: 768px) {
    .app-footer { display: none; }
}

/* ═══════════════════════════════════════════════════
   UTILITIES
   ═══════════════════════════════════════════════════ */
.text-muted { color: var(--color-muted); }
.text-center { text-align: center; }
/* Texte aligné sur ses deux bords, pour un paragraphe d'explication.
   La césure automatique l'accompagne toujours : sur une colonne étroite
   de téléphone, justifier sans couper les mots creuse de larges trous
   entre eux — le français a des mots longs. -webkit- reste nécessaire
   pour Safari iOS. Sans effet sur la dernière ligne d'un paragraphe,
   donc inoffensif sur un texte d'une seule ligne. */
.text-justify,
/* Les familles de paragraphes qui portent de la prose explicative, pour
   n'avoir pas à répéter la classe sur chacun des soixante et quelques
   du site. Toutes visent un <p> ou un <details>, jamais une cellule de
   tableau : .ecole-sub habille aussi des <td>, où justifier deux mots
   dans une colonne étroite ne ferait que creuser des trous — d'où le
   « p. » devant. Un paragraphe centré garde sa règle, déclarée après. */
p.ecole-sub,
details > p,
.tps-desc,
.bcp-annex-text,
.bil-transit-note {
    text-align: justify;
    -webkit-hyphens: auto;
            hyphens: auto;
}
/* Garde-fou : un paragraphe explicitement centré le reste, même s'il
   porte par ailleurs une des classes justifiées ci-dessus. */
p.text-center { text-align: center; }
/* Un numéro de téléphone qu'on touche pour appeler (afficherTelephone).
   Il garde la couleur du texte qui l'entoure — il se lit d'abord comme
   un numéro — et ne se signale que par un soulignement discret. Jamais
   coupé en fin de ligne : « 06 12 34 » / « 56 78 » ne se relit pas. */
.lien-tel {
    color: inherit;
    white-space: nowrap;
    text-decoration: underline dotted;
    text-underline-offset: 3px;
}
.lien-tel:hover { color: var(--color-primary); }
/* Le bouton WhatsApp qui le suit : écarté du numéro, et resserré pour
   tenir sur la même ligne dans une case de tableau. */
.btn.lien-tel-wa { margin-left: .35rem; padding: .1rem .45rem; vertical-align: baseline; }
.text-danger { color: var(--color-danger); }
.text-success { color: var(--color-success); }
.empty-state { text-align: center; padding: 3rem 1rem; color: var(--color-muted); }
.empty-state .empty-icon { font-size: 2.5rem; margin-bottom: .75rem; }
.empty-state p { font-size: .9rem; }
.chart-container { position: relative; width: 100%; }
.chart-container canvas { width: 100% !important; }
.hide-mobile { }
@media (max-width: 768px) { .hide-mobile { display: none !important; } }

/* Page header — titre + boutons */
.page-actions { display: flex; align-items: center; gap: 1rem; flex-wrap: wrap; margin-bottom: 1.5rem; }
.page-actions h1 { flex: 1; font-size: 1.5rem; font-weight: 600; }
/* Quand .page-actions porte aussi le titre (secrétariat, Utilisateurs),
   le titre prend sa ligne sur téléphone. Sans cela, les boutons — que
   la règle des petits écrans fait grandir pour se partager la largeur —
   lui disputaient la même ligne : « 📋 Réunions » se cassait en deux,
   l'emoji au-dessus du mot. Écrite après la règle de base ci-dessus, qui
   l'écraserait sinon à égalité de précision. */
@media (max-width: 640px) {
    .page-actions > h1 { flex: 1 1 100%; font-size: 1.3rem; }
    /* Sous un titre, les boutons se partagent la ligne à parts égales :
       grandir depuis la longueur de leur texte (règle des rangées de
       boutons de l'école) donnait deux boutons voisins de largeurs
       différentes. Les rangées sans titre gardent leur comportement. */
    .page-actions > h1 ~ .btn { flex: 1 1 0; min-width: 0; justify-content: center; }
}

/* Card sans padding interne */
.card-body--flush { padding: 0; }
/* Zone de carte qui prolonge la précédente au lieu d'ouvrir un nouveau
   sujet : sans cela, les deux rembourrages s'additionnent et creusent
   quarante pixels de vide au milieu d'un même groupe de commandes. */
.card-body--suite { padding-top: 0; }

/* Spacers */
.mt-sm { margin-top: .75rem; }
.mt-1  { margin-top: 1rem; }
.d-inline { display: inline; }
.d-none { display: none !important; }
.d-block { display: block !important; }
.ml-auto { margin-left: auto; }

/* Grilles formulaire */
.grid-2 { display: grid; grid-template-columns: 1fr 1fr; gap: 1rem; }
@media (max-width: 600px) { .grid-2 { grid-template-columns: 1fr; } }

/* Boutons formulaire */
.form-buttons { display: flex; gap: .75rem; margin-top: 1.5rem; }

/* Card formulaire (panneau blanc bordé) */
.form-card {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1.5rem; max-width: 700px;
}

/* Section séparée par un trait */

/* ═══════════════════════════════════════════════════
   RÉUNIONS — Composants spécifiques
   ═══════════════════════════════════════════════════ */
.reunion-link { color: var(--color-primary); text-decoration: none; font-weight: 500; }
.reunion-link:hover { text-decoration: underline; }
.reunion-type {
    display: inline-block; padding: .15rem .5rem; border-radius: 999px;
    font-size: .7rem; font-weight: 500; text-transform: uppercase;
}
.type-comite             { background: #dbeafe; color: #1e40af; }
.type-AG_ordinaire       { background: #fef3c7; color: #92400e; }
.type-AG_extraordinaire  { background: #fce7f3; color: #9d174d; }
.type-commission         { background: #f3e8ff; color: #6b21a8; }
.badge-hors-stats {
    display: inline-block;
    padding: .1rem .45rem;
    margin-left: .35rem;
    border-radius: 4px;
    font-size: .65rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: .3px;
    background: #f1f5f9;
    color: #64748b;
    border: 1px solid #e2e8f0;
    vertical-align: middle;
}
.reunion-meta { font-size: .78rem; color: var(--color-muted); margin-top: .2rem; }
/* Date dans l'en-tête de carte, téléphone seulement : sur ordinateur elle
   a sa colonne, et sur téléphone cette colonne est masquée
   (.table-mobile-secondary) pour ne pas la lire deux fois. */
.reunion-meta-mobile { display: none; }
@media (max-width: 768px) {
    .reunion-meta-mobile { display: block; font-size: .78rem; font-weight: 500; color: var(--color-muted); margin-top: .15rem; }
}

/* Date et heure d'une réunion (create.php, edit.php) : deux champs dans
   la colonne que le champ « date + heure » occupait seul. L'heure garde
   une largeur fixe — elle ne porte que cinq caractères, la date prend le
   reste. Sous 600 px la grille passe déjà en une colonne, et les deux
   tiennent encore côte à côte sur la largeur d'un téléphone. */
.reunion-datetime { display: flex; gap: .6rem; align-items: flex-start; }
.reunion-datetime > .form-group { flex: 1 1 auto; min-width: 0; margin-bottom: 0; }
.reunion-datetime > .reunion-datetime-heure { flex: 0 0 7rem; }

/*  Un repli posé DANS un formulaire (création d'une réunion : mandature,
    actions à reprendre). Il emprunte le mécanisme de details.ecole-pliable
    — chevron, résumé lisible fermé, mémorisation — mais pas son allure de
    carte : on est déjà dans .form-card, une carte dans une carte ferait un
    double cadre. Deux classes sur l'élément, comme .perms-module : la règle
    l'emporte par sa précision et non par sa place dans la feuille. */
details.form-repli.ecole-pliable {
    border: 1px solid var(--color-border); border-radius: var(--radius);
    margin-bottom: 1.15rem; background: var(--color-surface-alt);
}
details.form-repli.ecole-pliable > summary { padding: .6rem .85rem; }
details.form-repli.ecole-pliable[open] > summary { border-bottom: 1px solid var(--color-border); }
.form-repli-corps { padding: .85rem; background: var(--color-surface); }
.form-repli-corps > .form-group:last-child { margin-bottom: 0; }

/* Le rattachement calculé (mandature), écrit sous les champs : une
   information, pas un champ — d'où le ton discret et le filet à gauche
   qui la détache de la saisie. */
.reunion-mandature-info {
    margin: 0 0 1.15rem; padding: .5rem .75rem;
    border-left: 3px solid var(--color-border-strong);
    background: var(--color-surface-alt);
    border-radius: 0 var(--radius) var(--radius) 0;
    font-size: .82rem; color: var(--color-muted);
}
.reunion-mandature-info strong { color: var(--color-text); }

/* La ligne « Reprendre une action ouverte », sous le formulaire d'ajout
   d'action d'un point : un geste occasionnel, discret à côté du geste
   courant, mais nommé en toutes lettres. */
.point-reprise {
    display: flex; align-items: center; gap: .5rem; flex-wrap: wrap;
    margin: .5rem 0 0; font-size: .8rem;
}

/*  « Qui s'en occupe ? » : le panneau de cases à cocher d'une action
    (champResponsables()). Il emprunte .ecole-menu, déjà mutualisé ; ne
    restent que la largeur, la hauteur plafonnée — vingt-trois comptes
    dépasseraient l'écran — et le filet qui sépare la liste de la mention
    libre. */
.act-resp-panneau { min-width: 260px; max-width: 320px; padding: .5rem; }
.act-resp-liste { max-height: 14rem; overflow-y: auto; display: grid; gap: .25rem; }
.act-resp-liste .checkbox-label { font-size: .85rem; padding: .15rem .1rem; }
.act-resp-libre { border-top: 1px solid var(--color-border); margin-top: .5rem; padding-top: .5rem; }
.act-resp-libre label { display: block; font-size: .78rem; color: var(--color-muted); margin-bottom: .25rem; }
.act-resp-libre input { width: 100%; padding: .35rem .5rem; font-size: .85rem;
    border: 1px solid var(--color-border-strong); border-radius: var(--radius);
    background: var(--color-surface); color: var(--color-text); font-family: var(--font); }
/*  Le bouton dit qui a été choisi : son libellé s'allonge, il ne doit pas
    pousser la date et « + Action » hors de la ligne. */
.act-resp-btn { max-width: 16rem; }
.act-resp-resume { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }

/*  La ligne « Prévenir les responsables », au-dessus du récapitulatif des
    actions : un bouton et le compte de ce qui n'a jamais été annoncé. */
.pv-annonce-ligne {
    display: flex; align-items: center; gap: .6rem; flex-wrap: wrap;
    margin: 0 0 .75rem; font-size: .82rem;
}

/*  « À venir », sous la grille du calendrier : ce qu'il reste à préparer,
    même dans un autre mois. Une ligne par réunion, son état de convocation
    en coup d'œil et ses deux gestes à droite. */
.cal-avenir { margin-top: 1.25rem; }
.cal-avenir-liste { list-style: none; margin: 0; padding: 0; }
.cal-avenir-item {
    display: flex; align-items: center; gap: .5rem .75rem; flex-wrap: wrap;
    padding: .6rem 1.25rem; border-bottom: 1px solid var(--color-border);
    font-size: .85rem;
}
.cal-avenir-item:last-child { border-bottom: none; }
.cal-avenir-quand { color: var(--color-muted); font-size: .8rem; }
.cal-avenir-titre { font-weight: 600; color: var(--color-text); text-decoration: none; }
.cal-avenir-titre:hover { color: var(--color-primary); }
.cal-avenir-actions { display: flex; gap: .35rem; margin-left: auto; }
/*  Un jour se clique pour y préparer une réunion : le curseur doit le dire,
    y compris sur un jour vide. */
.cal-cell--clic { cursor: pointer; }
/*  Le lien d'ajout, en bas de la fenêtre d'un jour. */
.cal-modal-ajout { display: inline-flex; margin-top: .5rem; }
/*  La mention « Convoquée le … » d'une réunion passée : une information,
    pas une section — la carte d'envoi, elle, a disparu avec la date. */
.pv-convoc-rappel { margin: -.5rem 0 1.5rem; font-size: .82rem; }
@media (max-width: 768px) {
    .cal-avenir-item { align-items: flex-start; }
    .cal-avenir-quand, .cal-avenir-titre { flex: 1 0 100%; }
    .cal-avenir-actions { flex: 1 0 100%; margin-left: 0; }
    .cal-avenir-actions > * { flex: 1 1 0; justify-content: center; }
}

/* Calendrier (calendar.php) */
.cal-header {
    display: flex; align-items: center; justify-content: space-between;
    margin-bottom: 1.5rem; flex-wrap: wrap; gap: .75rem;
}
.cal-header h1 { font-size: 1.5rem; font-weight: 600; }
.cal-nav { display: flex; align-items: center; gap: .5rem; flex-wrap: wrap; }
.cal-nav a:not(.cal-today-btn) {
    display: inline-flex; align-items: center; justify-content: center;
    width: 36px; height: 36px; border-radius: var(--radius);
    border: 1px solid var(--color-border); background: var(--color-surface);
    color: var(--color-text); text-decoration: none; font-size: 1rem;
    flex-shrink: 0;
    transition: background .15s, border-color .15s;
}
.cal-nav a:not(.cal-today-btn):hover { background: var(--color-surface-alt, #f8fafc); border-color: var(--color-primary); }
.cal-month-label { font-size: 1.1rem; font-weight: 600; min-width: 160px; text-align: center; }
.cal-today-btn {
    height: 36px; padding: 0 .75rem; font-size: .82rem;
    display: inline-flex; align-items: center; justify-content: center;
    border-radius: var(--radius); border: 1px solid var(--color-border);
    background: var(--color-surface); color: var(--color-text);
    text-decoration: none; cursor: pointer; font-family: var(--font);
    transition: background .15s, border-color .15s;
}
.cal-today-btn:hover { background: var(--color-surface-alt, #f8fafc); border-color: var(--color-primary); }

.cal-grid {
    display: grid; grid-template-columns: repeat(7, 1fr);
    border: 1px solid var(--color-border); border-radius: var(--radius);
    overflow: hidden; background: var(--color-border); gap: 1px;
}
.cal-dow {
    background: var(--color-primary); color: #fff;
    text-align: center; padding: .5rem .25rem;
    font-size: .75rem; font-weight: 600; text-transform: uppercase;
}
.cal-cell {
    background: var(--color-surface); min-height: 90px;
    padding: .35rem; display: flex; flex-direction: column;
    position: relative; transition: background .15s;
}
.cal-cell:hover { background: var(--color-surface-alt, #f8fafc); }
.cal-cell.empty { background: var(--color-bg); }
.cal-cell.today { background: var(--color-accent-lt, #e0f7fa); }
.cal-day-num {
    font-size: .8rem; font-weight: 600; color: var(--color-muted);
    margin-bottom: .25rem; line-height: 1;
}
.cal-cell.today .cal-day-num { color: var(--color-primary); font-size: .85rem; }

.cal-event {
    display: block; padding: .15rem .35rem; margin-bottom: .2rem;
    border-radius: 4px; font-size: .68rem; font-weight: 500;
    text-decoration: none; color: #fff;
    overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
    transition: opacity .15s; line-height: 1.3;
}
.cal-event:hover { opacity: .85; }
.cal-event.type-comite            { background: #1e40af; }
.cal-event.type-commission        { background: #7e22ce; }
.cal-event.type-AG_ordinaire      { background: #92400e; }
.cal-event.type-AG_extraordinaire { background: #9d174d; }
.cal-event.statut-brouillon { opacity: .5; }
.cal-event.statut-relecture { border: 1px dashed rgba(255,255,255,.5); }

.cal-more {
    font-size: .65rem; color: var(--color-muted); font-weight: 500;
    padding: .1rem .25rem; cursor: pointer;
}

.cal-summary { margin-top: 1rem; font-size: .82rem; color: var(--color-muted); }

/* Modal détails jour */
.cal-modal {
    display: none; position: fixed; top: 0; left: 0; right: 0; bottom: 0;
    background: rgba(0,0,0,.4); z-index: 200;
    align-items: center; justify-content: center; padding: 1rem;
}
.cal-modal.active { display: flex; }
.cal-modal-content {
    background: var(--color-surface); border-radius: var(--radius);
    padding: 1.25rem; width: 100%; max-width: 400px;
    box-shadow: 0 10px 30px rgba(0,0,0,.2); max-height: 80vh; overflow-y: auto;
}
.cal-modal-content h3 { font-size: 1rem; font-weight: 600; margin-bottom: .75rem; }
.cal-modal-event {
    display: flex; align-items: center; gap: .6rem;
    padding: .5rem; border: 1px solid var(--color-border); border-radius: var(--radius);
    margin-bottom: .5rem; text-decoration: none; color: var(--color-text);
    transition: border-color .15s;
}
.cal-modal-event:hover { border-color: var(--color-primary); }
.cal-modal-dot { width: 10px; height: 10px; border-radius: 50%; flex-shrink: 0; }
.cal-modal-dot.type-comite { background: #1e40af; }
.cal-modal-dot.type-commission { background: #7e22ce; }
.cal-modal-dot.type-AG_ordinaire { background: #92400e; }
.cal-modal-dot.type-AG_extraordinaire { background: #9d174d; }
.cal-modal-ev-body { flex: 1; min-width: 0; }
.cal-modal-ev-title { font-weight: 500; display: block; }
.cal-modal-ev-meta { font-size: .78rem; color: var(--color-muted); }
.cal-modal-close { margin-top: .75rem; width: 100%; }

@media (max-width: 768px) {
    .cal-cell { min-height: 60px; padding: .25rem; }
    .cal-day-num { font-size: .7rem; }
    .cal-event { font-size: .6rem; padding: .1rem .2rem; }
    .cal-dow { font-size: .65rem; padding: .35rem .15rem; }
    .cal-month-label { font-size: .95rem; min-width: 120px; }
}
@media (max-width: 480px) {
    .cal-cell { min-height: 45px; }
    .cal-event { display: none; }
    .cal-cell.has-events::after {
        content: ''; width: 6px; height: 6px; border-radius: 50%;
        background: var(--color-primary); margin: .15rem auto 0;
    }
    .cal-cell.has-events { cursor: pointer; }
}

/* Vue PV (view.php) */
.pv-header {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1.5rem; margin-bottom: 1.5rem;
}
.pv-title { font-size: 1.4rem; font-weight: 600; margin-bottom: .5rem; }
.pv-meta { display: flex; gap: 1.5rem; flex-wrap: wrap; font-size: .85rem; color: var(--color-muted); }
.pv-meta span { display: flex; align-items: center; gap: .3rem; }

.pv-participants {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1rem 1.25rem; margin-bottom: 1.5rem;
}
.pv-participants h3 { font-size: .9rem; font-weight: 600; margin-bottom: .75rem; }
.pv-participants-list { display: flex; flex-wrap: wrap; gap: .5rem; }
.pv-participant {
    padding: .25rem .6rem; border-radius: 999px;
    font-size: .8rem; font-weight: 500;
}
/* Pastilles de présence (lecture du PV) sur les variables du thème : les
   fonds clairs écrits en dur restaient clairs en mode sombre. */
.pres-present { background: var(--color-success-lt); color: var(--color-success); }
.pres-excuse  { background: var(--color-warning-lt); color: var(--color-warning); }
.pres-absent  { background: var(--color-danger-lt);  color: var(--color-danger); }

.pv-point {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); margin-bottom: 1rem; overflow: hidden;
}
/* Fond et filet pris dans le thème : #f8fafc en dur restait blanc en
   mode sombre. Le filet passe sur le corps ouvert — posé sous l'en-tête,
   il doublait le bord de la carte sur chaque point replié. */
.pv-point-header {
    display: flex; align-items: center; gap: .75rem;
    padding: .75rem 1rem; background: var(--color-surface-alt);
    transition: background .15s; cursor: pointer;
}
.pv-point-header:hover { background: var(--color-primary-lt); }
.pv-point-header:focus-visible { outline: 2px solid var(--color-primary); outline-offset: -2px; }
.pv-toggle { font-size: .8rem; color: var(--color-muted); transition: transform .2s; flex-shrink: 0; }
.pv-toggle.collapsed { transform: rotate(-90deg); }
.pv-point-body { display: none; padding: 1rem 1.25rem; }
.pv-point-body.pv-point-open { display: block; border-top: 1px solid var(--color-border); }
.pv-point-intitule { display: block; }
/* Ce qu'on lit sans déplier. Flex plutôt qu'un séparateur écrit : les
   éléments absents ([hidden]) ne laissent ni trou ni « · » orphelin. */
.pv-point-resume { display: flex; flex-wrap: wrap; gap: 0 .75rem; font-size: .75rem; font-weight: 400; color: var(--color-muted); }
.pv-point-resume > span { margin-top: .15rem; }
.pv-point-resume > [hidden] { display: none; }
@media (max-width: 768px) {
    .pv-point-header { padding: .7rem .85rem; gap: .6rem; }
    .pv-point-body { padding: .85rem .9rem; }
}
.pv-point-num {
    background: var(--color-primary); color: #fff;
    width: 28px; height: 28px; border-radius: 50%;
    display: flex; align-items: center; justify-content: center;
    font-size: .8rem; font-weight: 700; flex-shrink: 0;
}
.pv-point-title { font-weight: 600; font-size: .95rem; flex: 1; }
.pv-contenu { font-size: .9rem; line-height: 1.7; margin-bottom: 1rem; }
.pv-contenu p { margin-bottom: .5rem; }
.pv-contenu ul, .pv-contenu ol { margin-left: 1.5rem; margin-bottom: .5rem; }
.pv-decisions {
    background: #eff6ff; border-left: 3px solid var(--color-primary);
    padding: .75rem 1rem; border-radius: 0 var(--radius) var(--radius) 0;
    margin-bottom: 1rem;
}
.pv-decisions strong { font-size: .85rem; display: block; margin-bottom: .3rem; color: var(--color-primary); }
.pv-decisions div { font-size: .9rem; }
.pv-decisions div p { margin-bottom: .3rem; }

/* Quill editor */
.quill-editor { background: var(--color-surface); min-height: 120px; border-radius: 0 0 var(--radius) var(--radius); }
.ql-toolbar.ql-snow { border-radius: var(--radius) var(--radius) 0 0; border-color: var(--color-border); }
.ql-container.ql-snow { border-color: var(--color-border); font-size: .9rem; }

/*  Ce qu'il y a à faire passe en tête, sur toute la largeur ; les
    responsables, la date, l'état et les boutons suivent dessous. Avec
    « Modifier », « Clore » et « Supprimer » d'un côté et trois noms de
    l'autre, la description était écrasée à deux mots par ligne — la seule
    chose qu'on vient lire.
    Règle à garder : dans une rangée en flex, ce qui identifie la ligne ne
    partage pas la largeur avec ses commandes. */
.pv-action-item {
    display: flex; gap: .4rem .75rem; align-items: center; flex-wrap: wrap;
    padding: .5rem .75rem; margin-top: .5rem;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    border-left: 3px solid var(--color-success); font-size: .85rem;
}
.pv-action-item.closed { opacity: .6; border-left-color: var(--color-muted); }
.pv-action-desc { flex: 1 0 100%; font-weight: 500; }

/*  Les boutons d'une action, groupés. Sur ordinateur ils se calent à
    droite de la ligne des informations ; sur téléphone ils forment une
    rangée à eux et se partagent la largeur à parts égales — sans ce
    groupe, ils se dispersaient une ligne sur deux au gré de la place
    restante. Même motif que .page-actions sur petit écran.
    Règle à garder : des commandes qui vont ensemble sont un groupe dans
    le HTML, sinon le retour à la ligne les sépare au hasard. */
.pv-action-btns, .action-btns {
    display: flex; gap: .35rem; flex-wrap: wrap; margin-left: auto;
}
.action-btns .d-inline { display: inline-flex; }

@media (max-width: 768px) {
    .pv-action-btns, .action-btns { flex: 1 0 100%; margin-left: 0; margin-top: .25rem; }
    .pv-action-btns > *, .action-btns > * { flex: 1 1 0; }
    .pv-action-btns .btn, .action-btns .btn { width: 100%; justify-content: center; }
}
.pv-add-action-wrap {
    display: flex; flex-wrap: wrap; gap: .4rem; align-items: center;
    margin-top: .75rem; padding: .6rem .75rem;
    background: var(--color-surface); border: 1px dashed var(--color-border);
    border-radius: var(--radius);
}
.pv-add-action-input { flex: 2; min-width: 140px; }
.pv-add-action-resp  { flex: 1; min-width: 120px; }
.pv-add-action-wrap select { flex: 1; min-width: 140px; }
.pv-add-action-wrap input[type="date"] { flex: 0 0 130px; width: 130px; }

.approve-bar {
    background: #fef3c7; border: 1px solid #fde68a;
    border-radius: var(--radius); padding: 1rem 1.25rem;
    display: flex; align-items: center; gap: 1rem;
    margin-bottom: 1.5rem; flex-wrap: wrap;
}
.approve-bar p { flex: 1; font-size: .9rem; color: #92400e; margin: 0; }

/* Commentaires */
.comments-section { margin-top: 1.25rem; padding-top: 1rem; border-top: 1px dashed var(--color-border); }
.comments-title {
    font-size: .85rem; font-weight: 600; color: var(--color-muted);
    margin-bottom: .75rem; display: flex; align-items: center; gap: .4rem;
}
.comment-item {
    display: flex; gap: .75rem; padding: .75rem; margin-bottom: .5rem;
    border-radius: var(--radius); background: #f8fafc;
    border: 1px solid var(--color-border);
}
.comment-item.resolved { opacity: .6; background: #f0fdf4; border-color: #bbf7d0; }
.comment-avatar {
    width: 32px; height: 32px; border-radius: 50%;
    background: var(--color-primary); color: #fff;
    display: flex; align-items: center; justify-content: center;
    font-size: .7rem; font-weight: 700; flex-shrink: 0;
}
.comment-body { flex: 1; min-width: 0; }
.comment-header {
    display: flex; align-items: center; gap: .5rem;
    margin-bottom: .3rem; flex-wrap: wrap;
}
.comment-author { font-size: .8rem; font-weight: 600; }
.comment-role { padding: .1rem .35rem; border-radius: 999px; font-size: .65rem; font-weight: 500; }
.comment-date { font-size: .75rem; color: var(--color-muted); }
.comment-text { font-size: .85rem; line-height: 1.5; white-space: pre-wrap; }
.comment-actions { display: flex; gap: .4rem; margin-top: .4rem; }
.comment-actions form { display: inline; }
.comment-actions button {
    background: none; border: none; cursor: pointer;
    font-size: .75rem; color: var(--color-muted); padding: .1rem .3rem; border-radius: 4px;
}
.comment-actions button:hover { background: var(--color-border); color: var(--color-text); }
.resolved-badge { font-size: .7rem; color: var(--color-success); font-weight: 500; }
.comment-form { display: flex; gap: .5rem; margin-top: .75rem; align-items: flex-start; }
.comment-form textarea {
    flex: 1; padding: .5rem .75rem;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    font-size: .85rem; font-family: inherit; line-height: 1.4;
    resize: vertical; min-height: 60px;
    color: var(--color-text); background: var(--color-surface);
}
.comment-form textarea:focus {
    outline: none; border-color: var(--color-primary);
    box-shadow: 0 0 0 3px rgba(37,99,235,.1);
}

/* Commentaires archivés */
.comments-archive { opacity: .75; border-top-style: dotted; }
.comments-archive summary {
    font-size: .85rem; font-weight: 600; color: var(--color-muted);
    margin-bottom: .75rem; display: flex; align-items: center; gap: .4rem;
    list-style: none; cursor: pointer; user-select: none;
}
.comments-archive summary::before { content: '▶'; font-size: .65rem; transition: transform .2s; }
.comments-archive details[open] summary::before { transform: rotate(90deg); }
.comments-archive summary small { font-weight: 400; color: var(--color-muted); margin-left: .5rem; }
.comments-archive .comment-item { opacity: .85; }

/* Utilitaires PV */
.pv-actions-bar { display: flex; gap: .75rem; align-items: center; margin-bottom: 1.5rem; flex-wrap: wrap; }
/* Le menu se cale à droite, même s'il passe à la ligne sur téléphone :
   son panneau s'ouvre vers la gauche (right: 0) et sortirait de l'écran
   depuis le bord gauche. */
.pv-actions-bar > .ecole-menu { margin-left: auto; }
.pv-approved-meta { margin-top: .75rem; font-size: .85rem; color: var(--color-success); }
.pv-participant--invite { background: #f1f5f9; color: #475569; }
[data-theme="dark"] .pv-participant--invite { background: #293241; color: #94a3b8; }
.pv-toggle-all-wrap { display: flex; justify-content: flex-end; margin-bottom: .75rem; }
.pv-comments-count { font-size: .75rem; color: var(--color-muted); }
.pv-actions-label { font-size: .85rem; }
.pv-action-meta   { color: var(--color-muted); font-size: .8rem; }
.pv-empty-point   { font-size: .85rem; }
.pv-edit-btn-wrap { margin-top: .75rem; }

/* Dropdown Export PDF (choix logo AFM / Mosquée) */
.pv-export-menu {
    position: relative;
    display: inline-block;
}
.pv-export-menu-items {
    display: none;
    position: absolute;
    top: calc(100% + 4px);
    left: 0;
    background: #fff;
    border: 1px solid var(--color-border, #e5e7eb);
    border-radius: 6px;
    box-shadow: 0 4px 12px rgba(0,0,0,.1);
    z-index: 100;
    min-width: 220px;
    overflow: hidden;
}
.pv-export-menu-items.open { display: block; }
.pv-export-menu-items a {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: .5rem;
    padding: .5rem .75rem;
    color: var(--color-text, #1f2937);
    text-decoration: none;
    font-size: .85rem;
    border-bottom: 1px solid var(--color-border, #e5e7eb);
}
.pv-export-menu-items a:last-child { border-bottom: none; }
.pv-export-menu-items a:hover { background: var(--color-bg-subtle, #f8f9fa); }
.pv-export-menu-badge {
    font-size: .65rem;
    padding: .1rem .4rem;
    background: var(--color-accent-soft, #fef3c7);
    color: var(--color-accent-dark, #92400e);
    border-radius: 8px;
    font-weight: 500;
}

/* Édition inline point */
.pv-edit-block    { display: none; }
.pv-edit-block.is-active { display: block; }
.pv-edit-group    { margin-bottom: .75rem; }
.pv-edit-label    { font-size: .8rem; font-weight: 600; }
.pv-edit-input    {
    width: 100%; padding: .4rem .6rem;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    font-size: .9rem; background: var(--color-surface); color: var(--color-text);
    font-family: var(--font);
}
.pv-edit-btns     { display: flex; gap: .5rem; }
.pv-save-status   { font-size: .8rem; color: var(--color-success); align-self: center; }
.pv-save-status.is-saving { color: var(--color-muted); }
.pv-save-status.is-error  { color: var(--color-danger); }
.pv-read-block { display: block; }
.pv-read-block.is-hidden { display: none; }

/* Documents attachés */
.pv-docs-wrap     { margin-top: 1.5rem; }
.pv-docs-title    { font-size: 1rem; font-weight: 600; margin-bottom: .75rem; }
.pv-docs-body     { padding: 0; }
.pv-doc-item {
    display: flex; align-items: center; gap: .75rem;
    padding: .65rem 1rem; border-bottom: 1px solid var(--color-border); font-size: .85rem;
}
.pv-doc-item:last-child { border-bottom: none; }
.pv-doc-icon      { font-size: 1.1rem; }
.pv-doc-body      { flex: 1; min-width: 0; }
.pv-doc-link      { color: var(--color-primary); text-decoration: none; font-weight: 500; }
.pv-doc-link:hover { text-decoration: underline; }
.pv-doc-meta      { font-size: .75rem; color: var(--color-muted); }

/* Édition réunion (edit.php) */
.edit-header { display: flex; align-items: center; gap: 1rem; margin-bottom: 1.5rem; flex-wrap: wrap; }
.edit-header h1 { flex: 1; font-size: 1.4rem; font-weight: 600; }
.status-bar { display: flex; gap: .75rem; align-items: center; flex-wrap: wrap; }

.quill-edit { background: var(--color-surface); min-height: 120px; border-radius: 0 0 var(--radius) var(--radius); }
/*  Les décisions sont courtes : 154 caractères en moyenne sur les 41
    points qui en portent, contre 447 pour la discussion — et un point sur
    deux n'en a aucune. Leur cadre partait pourtant à la même hauteur, ce
    qui faisait deux grandes boîtes identiques à l'écran. Il grandit à la
    saisie, comme l'autre. */
.quill-edit--court, .quill-editor--court { min-height: 64px; }

/*  Le repli des décisions, dans le corps d'un point : un simple titre
    cliquable, pas une carte — on est déjà dans celle du point. Le chevron
    est celui du motif commun ; le marqueur du navigateur est retiré des
    deux côtés, comme partout ailleurs. */
.pt-dec > summary {
    list-style: none; cursor: pointer;
    display: flex; align-items: center; gap: .4rem;
    font-size: .82rem; font-weight: 600; color: var(--color-text);
    margin-bottom: .35rem;
}
.pt-dec > summary::-webkit-details-marker { display: none; }
.pt-dec > summary::marker { content: ''; }
.pt-dec > summary:hover { color: var(--color-primary); }
.pt-dec:not([open]) > summary .ecole-pliable-chevron { transform: rotate(-90deg); }
.pt-dec[open] > summary .ecole-pliable-chevron { transform: rotate(0); }
.pt-dec-etat { font-weight: normal; font-size: .78rem; color: var(--color-muted); }
.pt-dec-etat:not(:empty)::before { content: "— "; }

.section { margin-bottom: 2rem; }
.section-title {
    font-size: 1.05rem; font-weight: 600; margin-bottom: 1rem;
    padding-bottom: .5rem; border-bottom: 2px solid var(--color-border);
}

/* Points éditables */
.point-card {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); margin-bottom: 1rem; overflow: hidden;
    transition: box-shadow .15s, opacity .15s;
}
.point-card.dragging { opacity: .45; box-shadow: 0 4px 16px rgba(0,0,0,.15); }
/* Fonds pris dans le thème : #eff6ff, #f8fafc et #f1f5f9 en dur restaient
   clairs en mode sombre. Le filet passe sur le corps ouvert — sous
   l'en-tête, il doublait le bord de la carte sur chaque point replié. */
.point-card.drag-over { border: 2px dashed var(--color-primary); background: var(--color-primary-lt); }
.point-header {
    display: flex; align-items: center; gap: .75rem;
    padding: .75rem 1rem; background: var(--color-surface-alt);
}
.point-header:hover { background: var(--color-primary-lt); }
.drag-handle {
    cursor: grab; font-size: 1.1rem; color: var(--color-muted);
    padding: 0 2px; flex-shrink: 0; user-select: none;
    opacity: .5; transition: opacity .15s;
}
.drag-handle:hover { opacity: 1; color: var(--color-primary); }
.drag-handle:active { cursor: grabbing; }
.point-move-btns { display: flex; flex-direction: column; gap: 1px; flex-shrink: 0; }
.point-move-btn {
    width: 22px; height: 15px; padding: 0; line-height: 1;
    border: 1px solid var(--color-border); background: var(--color-surface);
    color: var(--color-muted); border-radius: 3px; font-size: .6rem;
    cursor: pointer; display: flex; align-items: center; justify-content: center;
}
.point-move-btn:hover:not(:disabled) { color: var(--color-primary); border-color: var(--color-primary); }
.point-move-btn:disabled { opacity: .3; cursor: default; }
.point-numero {
    background: var(--color-primary); color: #fff;
    width: 28px; height: 28px; border-radius: 50%;
    display: flex; align-items: center; justify-content: center;
    font-size: .8rem; font-weight: 700; flex-shrink: 0;
}
.point-titre { flex: 1; min-width: 0; font-weight: 500; font-size: .9rem; cursor: pointer; }
.point-titre:focus-visible { outline: 2px solid var(--color-primary); outline-offset: 2px; border-radius: 4px; }
.point-intitule { display: block; }
.point-toggle { font-size: .8rem; color: var(--color-muted); cursor: pointer; flex-shrink: 0; transition: transform .2s; }
.point-toggle.collapsed { transform: rotate(-90deg); }
/* « À rédiger » dans le résumé du point (classes partagées avec la lecture du PV). */
.pv-resume-vide { color: var(--color-warning); font-weight: 500; }
.point-body { padding: 1rem; display: none; }
.point-body.open { display: block; border-top: 1px solid var(--color-border); }
/* Section Documents : l'envoi suit la liste dans la même carte. */
.edit-docs-upload { border-top: 1px solid var(--color-border); }
@media (max-width: 768px) {
    /* Le glisser-déposer natif ne marche pas au doigt : la poignée n'y
       serait qu'un pictogramme de plus. Les flèches ▲▼ la remplacent. */
    .drag-handle { display: none; }
    .point-header { padding: .7rem .75rem; gap: .55rem; }
    /* Titre de page sur sa ligne, le statut et les boutons en dessous —
       même écueil que .page-actions. Après la règle de base .edit-header h1. */
    .edit-header h1 { flex: 1 1 100%; font-size: 1.2rem; }
}
.point-body textarea {
    width: 100%; padding: .5rem .75rem;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    font-size: .9rem; font-family: inherit; line-height: 1.5;
    resize: vertical; min-height: 100px;
    color: var(--color-text); background: var(--color-surface);
}
.point-body textarea:focus {
    outline: none; border-color: var(--color-primary);
    box-shadow: 0 0 0 3px rgba(37,99,235,.1);
}

/* Actions inline */
.action-inline {
    display: flex; gap: .5rem; align-items: center;
    padding: .5rem; margin-top: .5rem;
    background: var(--color-success-lt); border: 1px solid var(--color-border); border-radius: var(--radius);
    font-size: .85rem; flex-wrap: wrap;
}
/*  Même raison que .pv-action-desc : la description prend sa ligne, les
    responsables, l'échéance et les boutons se rangent dessous. */
.action-inline .action-desc { flex: 1 0 100%; font-weight: 500; }
.action-inline .action-resp { color: var(--color-muted); }
.action-inline .action-ech  { color: var(--color-muted); font-size: .8rem; }
.actions-list { margin-top: 1rem; }
.actions-list-title { font-size: .85rem; font-weight: 600; }
.point-delete-zone { margin-top: 1rem; padding-top: .75rem; border-top: 1px dashed var(--color-border); }

/* Onglets scope Actions (Comité / Commissions) */
.actions-scope-tabs {
    display: flex;
    gap: .25rem;
    margin: 1rem 0 1.25rem;
    border-bottom: 2px solid var(--color-border);
    flex-wrap: wrap;
}
.actions-scope-tab {
    display: inline-flex;
    align-items: center;
    gap: .5rem;
    padding: .65rem 1.1rem;
    font-size: .92rem;
    font-weight: 600;
    color: var(--color-muted);
    text-decoration: none;
    border-bottom: 2px solid transparent;
    margin-bottom: -2px;
    border-radius: 6px 6px 0 0;
    transition: color .15s, background-color .15s, border-color .15s;
}
.actions-scope-tab:hover {
    color: var(--color-text);
    background-color: var(--color-bg-soft, rgba(0,0,0,.03));
}
.actions-scope-tab.is-active {
    color: var(--color-primary, #d97706);
    border-bottom-color: var(--color-primary, #d97706);
    background-color: var(--color-bg-soft, rgba(217,119,6,.06));
}
.actions-scope-tab__badge {
    display: inline-block;
    min-width: 1.4rem;
    padding: .1rem .45rem;
    font-size: .75rem;
    font-weight: 700;
    line-height: 1.2;
    text-align: center;
    border-radius: 999px;
    background: var(--color-border);
    color: var(--color-text);
}
.actions-scope-tab.is-active .actions-scope-tab__badge {
    background: var(--color-primary, #d97706);
    color: #fff;
}
.actions-scope-court { display: none; }
@media (max-width: 640px) {
    /* Les deux onglets se partagent la ligne : le libellé complet de
       « Commissions / Événements » renvoyait l'onglet sous « Comité ». */
    .actions-scope-tabs { flex-wrap: nowrap; }
    .actions-scope-tab { flex: 1 1 0; justify-content: center; min-width: 0; padding: .55rem .5rem; font-size: .85rem; }
    .actions-scope-long { display: none; }
    .actions-scope-court { display: inline; }
}

/* Sauvegarder + Supprimer ce point côte à côte, en bas du point */
.point-save-delete-row {
    display: flex;
    align-items: center;
    gap: .75rem;
    margin-top: 1rem;
    padding-top: .75rem;
    border-top: 1px dashed var(--color-border);
    flex-wrap: wrap;
}
.point-save-delete-row form { margin: 0; display: inline; }
@media (max-width: 640px) {
    .point-save-delete-row { gap: .5rem; }
}

/* Formulaire ajout action */
.add-action-form {
    display: grid; grid-template-columns: 1fr auto auto auto;
    gap: .5rem; align-items: end; margin-top: .75rem;
    padding-top: .75rem; border-top: 1px dashed var(--color-border);
}
.add-action-form input, .add-action-form select {
    padding: .4rem .5rem; font-size: .85rem;
    border: 1px solid var(--color-border); border-radius: 4px;
}
.add-action-form input:focus, .add-action-form select:focus { outline: none; border-color: var(--color-primary); }
.add-action-resp-wrap { display: flex; flex-direction: column; gap: 3px; }
.add-action-resp-hidden { display: none; }

/* Ajout point */
/* La note posee au-dessus de la rangee, pas dedans : voir edit.php. */
.add-point-note { margin: 0 0 .75rem; font-size: .82rem; }
.add-point-form { display: flex; gap: .75rem; align-items: end; }
.add-point-form .form-group { flex: 1; margin-bottom: 0; }

/* Participants — carte repliable <details class="ecole-pliable"> (edit.php) */

.part-table { width: 100%; border-collapse: collapse; }
.part-table th {
    text-align: center; padding: .4rem .3rem;
    font-size: .7rem; font-weight: 600; color: var(--color-muted);
    text-transform: uppercase; border-bottom: 1px solid var(--color-border);
}
.part-table th:first-child { text-align: left; }
.part-table td { padding: .4rem .3rem; border-bottom: 1px solid var(--color-border); vertical-align: middle; text-align: center; }
.part-table td:first-child { text-align: left; }
.part-table tr:last-child td { border-bottom: none; }
.part-table .part-name { font-size: .85rem; font-weight: 500; }
.part-table .part-role { font-size: .7rem; }

.part-radio { display: none; }
.part-radio-label {
    display: inline-flex; align-items: center; justify-content: center;
    width: 30px; height: 30px; border-radius: 50%;
    border: 2px solid var(--color-border); cursor: pointer;
    font-size: .75rem; transition: all .15s;
}
.part-radio-label:hover { border-color: var(--color-primary); }
.part-radio:checked + .part-radio-label.lbl-present { background: #16a34a; border-color: #16a34a; color: #fff; }
.part-radio:checked + .part-radio-label.lbl-excuse  { background: #d97706; border-color: #d97706; color: #fff; }
.part-radio:checked + .part-radio-label.lbl-absent   { background: #c0392b; border-color: #c0392b; color: #fff; }

.part-summary { display: flex; gap: .75rem; font-size: .8rem; color: var(--color-muted); }
.part-summary span { display: flex; align-items: center; gap: .25rem; }
.part-summary .dot { width: 8px; height: 8px; border-radius: 50%; }
.dot--present { background: #16a34a; }
.dot--excuse  { background: #d97706; }
.dot--absent  { background: #c0392b; }

.invites-field { margin-top: 1rem; padding-top: .75rem; border-top: 1px dashed var(--color-border); }
.invites-field label { font-size: .82rem; font-weight: 600; margin-bottom: .4rem; display: block; }
.invites-field textarea {
    width: 100%; padding: .5rem .75rem; font-size: .85rem; font-family: inherit;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    resize: vertical; min-height: 50px; color: var(--color-text); background: var(--color-surface);
}
.invites-hint { color: var(--color-muted); font-size: .75rem; }

/* Upload documents */
.upload-form { display: flex; gap: .75rem; align-items: flex-end; flex-wrap: wrap; }
.upload-form .form-group { flex: 1; margin-bottom: 0; min-width: 200px; }
.upload-form input[type="file"] {
    font-size: .85rem; padding: .3rem;
    border: 1px solid var(--color-border); border-radius: var(--radius); width: 100%;
}

/* Workflow */
.workflow-bar { display: flex; gap: 1rem; flex-wrap: wrap; align-items: center; }
.workflow-hint { font-size: .85rem; }
.workflow-delete { margin-left: auto; }

/* Envois aux membres par email — convocation (reunions/edit.php) et
   diffusion du PV (reunions/view.php). Deux colonnes de membres dans la
   fenêtre : vingt noms empilés la rendaient plus haute que l'écran. Une
   seule colonne quand la place manque, sans media query. */
.pv-envoi-etat    { margin-bottom: .75rem; }
.pv-envoi-odj     { margin: 0 0 .75rem 1.25rem; font-size: .9rem; }
.pv-membres-titre { display: flex; flex-wrap: wrap; gap: .5rem; align-items: center; margin: .75rem 0 .4rem; }
/*  Ces rangées portent un libellé et une paire de boutons (« Tout cocher /
    Tout décocher », « Copier / Ouvrir WhatsApp », « Envoyée au groupe /
    à chacun »). Sur un téléphone, chacun passait à la ligne pour lui seul,
    aligné à gauche et de largeur inégale. Le libellé prend sa ligne, les
    deux boutons se partagent la suivante — comme les boutons d'en-tête.
    :has() limite la règle aux rangées qui en portent : un simple
    paragraphe (« Ordre du jour ») garde sa mise en page. */
@media (max-width: 768px) {
    .pv-membres-titre:has(.btn) > strong { flex: 1 0 100%; }
    .pv-membres-titre:has(.btn) > .btn   { flex: 1 1 calc(50% - .25rem); justify-content: center; }
    .pv-membres-titre:has(.btn) > .text-muted { flex: 1 0 100%; }
}
.pv-membres-liste { display: grid; grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); gap: .5rem 1rem; margin-bottom: .5rem; }
.pv-membres-liste small { word-break: break-all; }
/*  La fenêtre de reprise d'actions liste des PHRASES, pas des noms : la
    grille à deux colonnes de 220 px y découpait des descriptions entières
    en colonnes étroites, et le word-break ci-dessus — posé pour qu'une
    adresse email trop longue ne déborde pas — coupait les mots en plein
    milieu (« Réunio / n Comité »). Une colonne, et des mots entiers.
    Règle à garder : une liste à cocher se met en colonnes quand ses
    libellés tiennent sur une ligne, jamais quand ce sont des phrases. */
.pv-membres-liste--phrases { grid-template-columns: 1fr; gap: .75rem; }
.pv-membres-liste--phrases small { word-break: normal; overflow-wrap: anywhere; }
/* Fenêtre d'envoi : le texte préparé pour WhatsApp, à relire ou à
   copier, et le filet qui sépare les deux façons d'envoyer. */
.pv-envoi-sep   { border: 0; border-top: 1px solid var(--color-border); margin: 1.25rem 0 .5rem; }

/*  Les deux façons d'envoyer, chacune dans son cadre et sous son nom.
    Elles se suivaient sans se distinguer : on croyait la fenêtre finie au
    milieu, en voyant le bouton d'envoi, et rien ne disait que ce qu'on
    venait de remplir partait par email. */
.pv-envoi-bloc {
    border: 1px solid var(--color-border); border-radius: var(--radius);
    padding: .85rem 1rem; margin-bottom: 1rem;
    background: var(--color-surface-alt);
}
.pv-envoi-bloc-titre {
    font-size: .9rem; font-weight: 700; margin: 0 0 .35rem;
    color: var(--color-text);
}
.pv-envoi-bloc-sous { font-size: .8rem; margin: 0 0 .75rem; }
/*  Le bouton d'envoi appartient à son bloc : calé à droite sur ordinateur,
    pleine largeur au doigt. */
.pv-envoi-action { display: flex; justify-content: flex-end; margin: .75rem 0 0; }
@media (max-width: 768px) {
    .pv-envoi-action .btn { flex: 1 1 100%; justify-content: center; white-space: normal; }
}
.pv-envoi-texte { width: 100%; font-size: .85rem; font-family: var(--font); margin-bottom: .5rem; }
.pv-diffusion      { margin-bottom: 1.5rem; }   /* comme .pv-header, juste au-dessus */

/* Aperçu du courrier dans la fenêtre d'envoi par email : un courrier peut
   faire deux pages, la fenêtre ne doit pas s'allonger d'autant. */
.cour-email-apercu {
    max-height: 240px; overflow-y: auto;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    padding: .75rem 1rem; margin-bottom: .5rem;
    background: var(--color-surface-alt); font-size: .9rem;
}

/* Info bar (mandature + type) */
.info-bar { display: flex; gap: .5rem; align-items: center; }
.info-bar-text { font-size: .85rem; }
.info-bar .btn { margin-left: auto; }

@media (max-width: 768px) {
    .part-table th:not(:first-child) { font-size: .6rem; padding: .3rem .15rem; }
    .part-radio-label { width: 26px; height: 26px; font-size: .65rem; }
    .part-table .part-name { font-size: .8rem; }
    .add-action-form { grid-template-columns: 1fr; }
    /* En colonne, l'alignement « en bas » de la version ordinateur
       (align-items: end) devient « à droite » : le champ et le bouton se
       collaient au bord droit de la carte. Pleine largeur à la place. */
    /* Workflow : en ligne sur ordinateur, la suppression est poussée à
       droite (margin-left: auto). Passé à la ligne sur téléphone, cela
       donnait trois alignements dans la même carte. En colonne : le geste
       courant pleine largeur, son explication dessous, la suppression à
       part, sous un filet — loin du pouce qui vient soumettre. */
    .workflow-bar { flex-direction: column; align-items: stretch; gap: .6rem; }
    .workflow-bar form .btn { width: 100%; justify-content: center; }
    .workflow-delete { margin-left: 0; margin-top: .25rem; padding-top: .75rem; border-top: 1px dashed var(--color-border); }
    .add-point-form { flex-direction: column; align-items: stretch; }
    .add-point-form .form-group input { width: 100%; }
    .add-point-form .btn { justify-content: center; }
}

/* ═══════════════════════════════════════════════════
   ADMIN — Composants spécifiques
   ═══════════════════════════════════════════════════ */

/* Boutons variantes (utilisés partout) */
.btn-warning { background: #fef3c7; color: #92400e; border-color: #fde68a; }
.btn-warning:hover { background: #fde68a; }
.btn-success { background: #f0fdf4; color: var(--color-success); border-color: #bbf7d0; }
.btn-success:hover { background: #bbf7d0; }
.btn-info    { background: #e0f2fe; color: #0369a1; border-color: #bae6fd; }
.btn-info:hover    { background: #bae6fd; }

/* Password form (change_password.php) */
.pwd-wrap { position: relative; }
.pwd-wrap input { padding-right: 40px; width: 100%; }
.pwd-eye {
    position: absolute; right: 8px; top: 50%; transform: translateY(-50%);
    background: none; border: none; cursor: pointer; font-size: 16px; padding: 2px;
}
.pwd-page { max-width: 420px; margin: 2rem auto; }
/* Ordinateur : deux colonnes. À gauche ce qu'on lit (profil) et ce qu'on
   ouvre rarement (mot de passe, replié) ; à droite ce qu'on modifie (me
   joindre), la carte la plus haute. La seconde ligne est en 1fr : c'est
   elle qui absorbe la hauteur de « Me joindre », sinon un vide se
   creuserait entre le profil et le mot de passe. Un changement imposé
   met le mot de passe en tête de la colonne gauche. */
@media (min-width: 900px) {
    .pwd-page { max-width: 960px; }
    .pwd-grille {
        display: grid; grid-template-columns: 1fr 1fr;
        grid-template-rows: auto 1fr; gap: 1.5rem; align-items: start;
        grid-template-areas: "profil joindre" "mdp joindre";
    }
    .pwd-grille--impose { grid-template-areas: "mdp joindre" "profil joindre"; }
    .pwd-grille > .card { margin-bottom: 0; }
    .pwd-carte--profil { grid-area: profil; }
    .pwd-carte--joindre { grid-area: joindre; }
    .pwd-carte--mdp { grid-area: mdp; }
}
/* La page s'appelle « Mon compte » depuis qu'elle porte aussi le
   téléphone et la préférence d'emails : elle a donc un titre. */
.pwd-titre { font-size: 1.3rem; font-weight: 700; margin-bottom: 1rem; }
/* « Mes coordonnées » : ce que le site sait du compte, en deux
   colonnes — le libellé, la valeur. Une seule colonne sur téléphone,
   où « Dernière connexion » et sa date ne tiennent pas côte à côte. */
.pwd-identite { display: grid; grid-template-columns: auto 1fr; gap: .35rem .75rem; margin: 0 0 1rem; font-size: .88rem; }
.pwd-identite dt { color: var(--color-muted); }
.pwd-identite dd { margin: 0; font-weight: 600; word-break: break-word; }
@media (max-width: 480px) {
    .pwd-identite { grid-template-columns: 1fr; gap: .1rem; }
    .pwd-identite dd { margin-bottom: .4rem; }
}
.pwd-strength-bar {
    height: 4px; border-radius: 2px; margin-top: 6px;
    background: var(--color-border); overflow: hidden;
}
.pwd-strength-fill { height: 100%; width: 0; border-radius: 2px; transition: all .3s; }
.pwd-strength-text { font-size: .72rem; color: var(--color-muted); }
.pwd-match-text { font-size: .72rem; }
.pwd-submit { width: 100%; margin-top: .5rem; }
.pwd-footer { text-align: center; font-size: .78rem; color: var(--color-muted); margin-top: 1rem; }

/* Journal (journal.php) */
.journal-filters { padding: .75rem 1rem; }
.journal-filter-form { display: flex; flex-wrap: wrap; gap: .5rem; align-items: center; }
/* L'apparence des champs vient de la règle partagée avec .filters-bar,
   plus haut. Ici on ne règle que les largeurs, pour que les cinq
   filtres tiennent sur une ligne.

   ⚠ La date doit reprendre la sienne : une règle globale
   `input[type="date"] { width: 100% }` (bloc « Fix date input mobile »)
   s'applique à TOUTES les largeurs, pas seulement au téléphone — elle
   faisait prendre la ligne entière au champ, qui repoussait les autres
   filtres en dessous. Le sélecteur ci-dessous est plus précis, donc il
   l'emporte où qu'il soit écrit dans la feuille. */
.journal-filter-form input[type="date"] { width: auto; flex: 0 0 9.5rem; }
/* La recherche prend la place qui reste : c'est le champ où l'on écrit
   le plus long, et le seul qui gagne à s'étirer. */
.journal-filter-form input[name="q"] { flex: 1 1 12rem; min-width: 8rem; }
.journal-filter-form select { flex: 0 0 auto; }
.journal-td-date { font-size: .78rem; color: var(--color-muted); white-space: nowrap; }
/*  Quatre badges de module, une seule mise en forme : seule la teinte
    change. Écrites une à une, trois d'entre elles avaient fini par
    diverger — le badge du secrétariat portait un texte vert sur un
    fond bleu, hérité d'un copier-coller. */
/*  Le rôle supplémentaire d'un compte, à côté de son rôle principal.
    Écrit plus discret : c'est un complément, pas une seconde identité,
    et deux badges de même poids se liraient comme deux comptes. */
.usr-role-second { opacity: .85; font-size: .68rem; }

.journal-badge-treso, .journal-badge-secre,
.journal-badge-ecole, .journal-badge-admin {
    font-size: .7rem; border-radius: 4px; padding: 2px 6px; font-weight: 600;
}
.journal-badge-treso { background: #fef9ec; color: #7a5c00; }
.journal-badge-secre { background: #e0f2fe; color: #075985; }
.journal-badge-ecole { background: #ede9fe; color: #5b21b6; }
.journal-badge-admin { background: #f1f5f9; color: #334155; }
/*  Le thème sombre n'habillait que le badge de l'école : les trois
    autres gardaient leur aplat clair, seuls éclats blancs de la page. */
[data-theme="dark"] .journal-badge-treso { background: #422006; color: #fcd34d; }
[data-theme="dark"] .journal-badge-secre { background: #0c4a6e; color: #bae6fd; }
[data-theme="dark"] .journal-badge-ecole { background: #2e1065; color: #c4b5fd; }
[data-theme="dark"] .journal-badge-admin { background: #1e293b; color: #cbd5e1; }

@media (max-width: 768px) {
    /*  La barre passait en colonne : une ligne pleine largeur par
        élément, soit sept lignes avant la première entrée du journal.
        Même principe que les autres barres de filtres du site — la
        recherche garde sa ligne (c'est elle qu'on touche le plus), les
        quatre autres se partagent les leurs deux par deux.

        ⚠ Cette règle est écrite APRÈS .journal-filter-form : à force
        égale, c'est la dernière qui gagne. Placée plus haut, elle
        serait annulée par la règle de base. */
    .journal-filter-form { align-items: stretch; }
    .journal-filter-form select,
    .journal-filter-form input[type="date"],
    .journal-filter-form input[type="text"] {
        flex: 1 1 calc(50% - .25rem);
        /*  Le min-width de 11rem du champ « Opérateur » dépasse la
            moitié d'un écran de 375 px : il le renverrait seul sur sa
            ligne. */
        min-width: 0;
    }
    .journal-filter-form input[name="q"] { flex-basis: 100%; }
    .journal-filter-form .btn { flex: 1 1 0; justify-content: center; }
}

/* Bande de chiffres clés — fiche famille. */
.ecole-chiffres { display: flex; flex-wrap: wrap; gap: 1.5rem; margin-bottom: .75rem; }
.ecole-chiffre-val { font-size: 1.15rem; font-weight: 600; font-variant-numeric: tabular-nums; }
.ecole-chiffre-lib { font-size: .78rem; color: var(--color-muted); }

/* Saisie ligne à ligne d'une remise de chèques. */
.ecole-cheques th, .ecole-cheques td { padding: .3rem .35rem; }
.ecole-cheques input { width: 100%; font-size: .85rem; }
.ecole-cheques tfoot th { font-size: .95rem; }

/* Sommaire d'ancres — fiche famille. */
.ecole-ancres {
    display: flex; flex-wrap: wrap; gap: .4rem;
    margin-bottom: 1rem;
}
.ecole-ancres a {
    font-size: .8rem; padding: .3rem .7rem; border-radius: 999px;
    background: var(--color-surface-alt); color: var(--color-muted);
    text-decoration: none; white-space: nowrap;
}
.ecole-ancres a:hover { background: var(--color-border); color: var(--color-text); }

/* Sur petit écran : le défilement au doigt laissait le dernier
   raccourci coupé net au bord de l'écran, comme une erreur d'affichage
   plutôt qu'une invitation à glisser. Une grille bien alignée tient
   les cinq raccourcis entiers, sans rien à découvrir. */
@media (max-width: 640px) {
    .ecole-ancres {
        display: grid;
        grid-template-columns: repeat(3, 1fr);
        gap: .4rem;
    }
    .ecole-ancres a {
        display: flex; align-items: center; justify-content: center;
        text-align: center; white-space: normal;
    }
}
/* Sans cette marge, l'ancre atterrit sous la barre du haut. */
.card-header[id] { scroll-margin-top: 70px; }

/* Registre en mobilité.
   Neuf colonnes ne tiennent pas sur un téléphone, et le registre se
   consulte souvent debout, un parent en face : la date, la famille et
   le montant suffisent pour lui répondre. Le mode et le compte sont
   repliés sous le nom plutôt que supprimés — masquer une information
   sans la remplacer, c'est la perdre. */
/* Colonne de sélection dans la liste des opérations. */
.ops-th-sel, .ops-td-sel { width: 2.5rem; text-align: center; }
.ops-td-sel input:disabled { opacity: .35; cursor: not-allowed; }

/* Barre de sélection multiple — dé-rapprochement en lot. */
.rp-lot-barre {
    display: flex; align-items: center; justify-content: space-between;
    gap: 1rem; flex-wrap: wrap;
    margin-top: 1rem; padding-top: .85rem;
    border-top: 1px solid var(--color-border);
}
/* La barre du haut porte son trait en dessous, pas au-dessus. */
.rp-lot-barre--haut {
    margin-top: 0; margin-bottom: 1rem;
    padding-top: 0; padding-bottom: .85rem;
    border-top: none; border-bottom: 1px solid var(--color-border);
}

/* Sélecteur du nombre de lignes par page. */
.ops-pp-form { display: inline-flex; align-items: center; }
.ops-pp-form label { font-size: .82rem; color: var(--color-muted); }
.ops-pp-form select { margin: 0 .3rem; font-size: .82rem; }

/* Cartes repliables. */
.card-header--pliable {
    cursor: pointer; user-select: none;
    transition: background .12s;
}
.card-header--pliable:hover { background: var(--color-surface-alt); }
.card-header--pliable h2 {
    display: flex; align-items: center; gap: .5rem;
}
.card-header--pliable h2::before {
    content: '';
    width: 7px; height: 7px; flex-shrink: 0;
    border-right: 2px solid var(--color-muted);
    border-bottom: 2px solid var(--color-muted);
    transform: rotate(45deg) translate(-1px, -2px);
    transition: transform .15s;
}
.card--replie .card-header--pliable h2::before {
    transform: rotate(-45deg) translate(-1px, 1px);
}
.card--replie .card-body { display: none; }
.card--replie { margin-bottom: .5rem; }
.card-header--pliable:focus-visible {
    outline: 2px solid var(--color-primary); outline-offset: -2px;
}
.card--pliable { scroll-margin-top: 70px; }

/* Cases à cocher des options facturées. */
.ecole-option {
    display: flex; align-items: flex-start; gap: .5rem;
    padding: .35rem 0; font-size: .88rem;
}
.ecole-option input { margin-top: .2rem; flex-shrink: 0; }

.col-repli { display: none; }
@media (max-width: 768px) {
    .col-secondaire { display: none; }
    .col-repli      { display: block; }
}
.ecole-soldes-ligne {
    display: flex; flex-wrap: wrap; gap: 1rem;
    align-items: center; justify-content: space-between;
}
.ecole-soldes-ligne .ecole-chiffres { margin-bottom: 0; }

/* Tableau de bord école — rangées de tuiles. */
/* La marge haute sépare deux rangées de tuiles qui ne parlent pas de la
   même chose (l'année scolaire en cours, puis l'argent en caisse toutes
   années confondues) : sans elle, le titre se colle au texte de la
   rangée précédente et la coupure ne se voit plus. */
.ecole-titre-rangee {
    font-size: .78rem; font-weight: 600; text-transform: uppercase;
    letter-spacing: .04em; color: var(--color-text-tertiary);
    margin: 1.6rem 0 .5rem;
}
/* Phrase d'une ligne posée sous un titre de rangée. */
/*  La phrase des soldes et le bouton qui la suit, sous la rangée de
    chiffres de l'accueil école.

    ⚠ Les marges sont écrites sur un sélecteur à DEUX classes, et c'est
    volontaire. .ecole-sub, déclarée six mille lignes plus bas dans cette
    feuille, pose « margin: .15rem 0 0 » et l'emporte donc, à force
    égale, sur toute règle de classe simple écrite plus haut. C'est ce
    qui rendait l'ancienne .ecole-sous-rangee totalement sans effet — ses
    marges ET son interligne — et ce qui a fait chevaucher ce bouton avec
    le texte : sa marge haute négative était calculée sur une marge basse
    que le paragraphe n'avait jamais. */
/*  Ni justifiée ni coupée : p.ecole-sub range cette phrase parmi la
    prose du site, or c'est une note courte posée autour de montants.
    Justifiée sur un téléphone, elle coupait les mots en deux. */
p.ecole-caisses-note {
    margin: 0 0 .6rem;
    text-align: left;
    -webkit-hyphens: manual;
            hyphens: manual;
}
p.ecole-caisses-action { margin: .8rem 0 0; }

/*  Le détail par caisse. Côte à côte tant qu'il y a la place, chaque
    caisse formant un bloc qui ne se coupe jamais en son milieu ; une par
    ligne sur téléphone, montant aligné à droite — c'est là qu'on les
    compare entre elles. */
.ecole-caisses-detail {
    list-style: none;
    margin: .3rem 0 0;
    padding: 0;
    display: flex;
    flex-wrap: wrap;
    gap: .25rem 1.5rem;
    font-size: .8rem;
    color: var(--color-muted);
}
.ecole-caisses-detail li { display: flex; gap: .45rem; white-space: nowrap; }
.ecole-caisses-detail strong { color: var(--color-text); font-weight: 600; }
@media (max-width: 640px) {
    /*  En colonne, et le montant poussé au bord droit : trois montants
        alignés se comparent d'un coup d'œil, alignés à gauche non. */
    .ecole-caisses-detail { flex-direction: column; gap: .2rem; }
    .ecole-caisses-detail li { justify-content: space-between; }
    /*  Le libellé cède avant le montant : « Compte bancaire école » se
        relit sur la page Caisses, un montant tronqué ne se devine pas. */
    .ecole-caisses-detail li > span {
        overflow: hidden;
        text-overflow: ellipsis;
        min-width: 0;
    }
}

/* Jauge de la part encaissée. */
.ecole-jauge {
    height: 4px; border-radius: 2px; margin-top: 8px;
    background: var(--color-border); overflow: hidden;
}
.ecole-jauge span {
    display: block; height: 100%; border-radius: 2px;
    background: var(--color-primary);
}
.journal-action-icon { margin-right: 6px; }
.journal-action-text { font-size: .85rem; }
.journal-user-name { font-size: .82rem; font-weight: 500; }
.journal-user-role { display: block; font-size: .7rem; }
.journal-count { font-size: .82rem; color: var(--color-muted); }

/* Logs (logs.php) */
.log-action-badge {
    display: inline-block; padding: .15rem .5rem;
    border-radius: 999px; font-size: .7rem; font-weight: 500;
    text-transform: uppercase; letter-spacing: .02em;
}
.log-LOGIN           { background: #dcfce7; color: #166534; }
.log-LOGOUT          { background: #f1f5f9; color: #475569; }
.log-LOGIN_FAILED    { background: #fef2f2; color: var(--color-danger); }
.log-default         { background: #dbeafe; color: #1e40af; }
.log-td-date { font-size: .8rem; white-space: nowrap; color: var(--color-muted); }
.log-td-user { font-size: .85rem; }
.log-td-objet { font-size: .8rem; color: var(--color-muted); }
.log-td-detail { font-size: .8rem; max-width: 250px; overflow: hidden; text-overflow: ellipsis; }
.log-td-ip { font-size: .75rem; color: var(--color-muted); font-family: monospace; }

/* Mandatures */
.mand-checkbox-label { display: flex; align-items: center; gap: 8px; cursor: pointer; font-weight: 500; }
.mand-td-name { font-weight: 500; }
.mand-td-date { font-size: .82rem; }
.mand-td-center { text-align: center; font-size: .85rem; }
.mand-actions { display: flex; gap: 4px; justify-content: center; }

/* Les deux actions d'une mandature portent leur nom depuis qu'un
   pictogramme seul ne disait rien au doigt. Sur téléphone, la cellule
   devient une ligne de carte : les deux boutons s'y partagent la largeur
   au lieu de déborder. Écrit après la règle de base, qu'il surcharge. */
@media (max-width: 768px) {
    .mand-actions { justify-content: flex-start; flex-wrap: wrap; }
    .mand-actions .btn, .mand-actions form { flex: 1 1 auto; }
    .mand-actions form .btn { width: 100%; }
}

/* Paramètres */
.params-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 1.5rem; }
.params-cp-grid { display: grid; grid-template-columns: 90px 1fr; gap: .75rem; }
.params-separator { margin: 1rem 0; border-color: var(--color-border); }
.params-section-label {
    font-size: .75rem; font-weight: 600; text-transform: uppercase;
    letter-spacing: .05em; color: var(--color-muted); margin-bottom: .75rem;
}
.params-section-small { font-weight: 400; }
.params-link-card { display: flex; align-items: center; gap: 1rem; flex-wrap: wrap; padding: 1rem 1.25rem; }
.params-link-icon { font-size: 1.3rem; }
.params-link-body { flex: 1; }
.params-link-title { font-weight: 600; margin-bottom: .2rem; }
.params-link-desc { font-size: .82rem; color: var(--color-muted); }
@media (max-width: 768px) { .params-grid { grid-template-columns: 1fr; } }
@media (max-width: 480px) { .params-cp-grid { grid-template-columns: 1fr; } }

/* Permissions */
/* 280 px et non 240 : à 240, « EL MOURABITI Moustapha » était coupé alors
   que la colonne des droits avait de la place à revendre. */
.perms-layout { display: grid; grid-template-columns: 280px 1fr; gap: 1.25rem; align-items: start; }

/* Sur ordinateur, la colonne des comptes se lit d'un coup d'œil et le
   menu déroulant ne servirait à rien : il reste masqué, et un élément en
   display: none ne compte pas comme cellule de la grille. */
.perms-choix { display: none; }

@media (max-width: 768px) {
    .perms-layout { grid-template-columns: 1fr; }
    /* Deux barres de navigation sont déjà collées en haut d'un téléphone :
       une troisième mangerait le tiers de l'écran utile. */
    .perms-barre { position: static; }
    .perms-choix {
        display: flex; flex-wrap: wrap; align-items: center; gap: .6rem;
    }
    .perms-choix label { font-size: .85rem; color: var(--color-muted); margin: 0; }
    /* Le menu garde sa ligne pleine largeur — un nom de compte suivi de
       son rôle est long —, le bouton se met en dessous. */
    .perms-choix select {
        flex: 1 1 100%; width: 100%; min-width: 0;
        padding: .4rem .6rem; font-size: .9rem;
        border: 1px solid var(--color-border);
        border-radius: var(--radius-sm, 6px);
        background: var(--color-surface); color: var(--color-text);
    }
    .perms-choix .btn { flex: 1 1 auto; justify-content: center; }
}

/* La colonne listait vingt-trois comptes et partait vers le haut avec le
   reste de la page : changer de personne obligeait à remonter tout ce
   qu'on venait de descendre. Elle se colle donc en haut et défile pour
   elle seule. (.perms-layout est déjà en align-items: start, sans quoi
   une cellule de grille s'étire sur toute la hauteur et rien ne colle.)

   `min-height: 0` sur la zone qui défile : sans lui, un enfant flex
   refuse de devenir plus court que son contenu et le débordement
   remonterait sur la colonne entière — même écueil que .sb-scroll dans
   la barre latérale. */
.perms-sidebar {
    padding: .5rem 0;
    position: sticky;
    top: 1rem;
    /* Plafonnée aussi en valeur absolue : sur un grand écran, la hauteur
       de la fenêtre laissait la liste descendre bien sous la colonne des
       droits, sections repliées. Au-delà, elle défile. */
    max-height: min(calc(100vh - 2rem), 40rem);
    display: flex;
    flex-direction: column;
}
.perms-sidebar-liste { overflow-y: auto; min-height: 0; }
.perms-filtre { padding: 0 12px 8px; flex-shrink: 0; }
.perms-filtre input {
    width: 100%; box-sizing: border-box;
    padding: .35rem .55rem; font-size: .8rem;
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    background: var(--color-surface); color: var(--color-text);
    font-family: var(--font);
}
.perms-vide { padding: .75rem 16px; font-size: .8rem; color: var(--color-muted); }

/* Sur téléphone, la colonne disparaît au profit du menu « Compte »
   (.perms-choix) : empilée au-dessus du formulaire, elle obligeait à
   traverser tous les comptes avant d'atteindre la première case.
   ⚠ Cette règle doit rester APRÈS celle de .perms-sidebar : à force
   égale, la dernière écrite gagne. Posée plus haut, elle était écrasée
   par le display: flex de la colonne collante, et la liste revenait sur
   téléphone. */
@media (max-width: 768px) {
    .perms-sidebar { display: none; }
}
/* Groupes par rôle : l'intitulé remplace le badge répété sur chaque
   ligne. Le résumé est un vrai <summary>, donc atteignable au clavier. */
.perms-groupe + .perms-groupe { border-top: 1px solid var(--color-border); }
.perms-groupe-titre {
    display: flex; align-items: center; gap: 7px;
    padding: 7px 14px 5px;
    font-size: .68rem; font-weight: 700; letter-spacing: .04em;
    text-transform: uppercase; color: var(--color-muted);
    cursor: pointer; list-style: none; user-select: none;
}
.perms-groupe-titre::-webkit-details-marker { display: none; }
.perms-groupe-titre::after {
    content: '▾'; margin-left: auto; font-size: .8rem;
    transition: transform .15s;
}
.perms-groupe:not([open]) > .perms-groupe-titre::after { transform: rotate(-90deg); }
.perms-groupe-titre:hover { color: var(--color-text); }
.perms-groupe-pastille { width: 8px; height: 8px; border-radius: 50%; flex-shrink: 0; }
.perms-groupe-nb {
    font-weight: 600; letter-spacing: 0;
    background: var(--color-surface-alt); border-radius: 999px; padding: 0 6px;
}

/* Une ligne par compte, sans avatar : ~32 px au lieu de 52. */
.perms-user-item {
    display: flex; align-items: center; gap: 6px;
    padding: 6px 14px 6px 29px; text-decoration: none; color: inherit;
    border-left: 3px solid transparent;
    transition: background .12s, border-color .12s;
}
.perms-user-item:hover  { background: var(--color-surface-alt); }
.perms-user-item.active { background: var(--color-accent-lt); border-left-color: var(--color-primary); }
.perms-user-item .perms-user-name { flex: 1; min-width: 0; display: block; }
.perms-user-ov { flex-shrink: 0; font-size: .8rem; }
.perms-avatar {
    width: 34px; height: 34px; border-radius: 50%;
    background: var(--color-surface-alt); border: 1px solid var(--color-border);
    display: flex; align-items: center; justify-content: center;
    font-size: 12px; font-weight: 700; color: var(--color-primary); flex-shrink: 0;
}
.perms-avatar--lg { width: 44px; height: 44px; font-size: 15px; }
.perms-user-name {
    font-size: .84rem; font-weight: 600;
    white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
    display: flex; align-items: center; gap: 5px;
}
.role-pill {
    display: inline-block; padding: 2px 8px; border-radius: 999px;
    font-size: .65rem; font-weight: 700; color: #fff;
}
.ov-badge {
    display: inline-block; font-size: .62rem; font-weight: 700;
    background: #fef3c7; color: #92400e; border-radius: 3px; padding: 1px 5px;
}
.ov-badge--lg { font-size: .72rem; padding: 2px 7px; }

/* Le bandeau du compte choisi porte les deux commandes qui écrivent.
   Il reste visible pendant qu'on descend les sections : « Enregistrer »
   était sinon tout en bas, derrière cinquante-trois lignes de cases à
   cocher, alors qu'on vient ici pour en changer une. */
.perms-barre { position: sticky; top: 1rem; z-index: 40; }
.perms-barre-actions { display: flex; gap: .5rem; flex-wrap: wrap; flex-shrink: 0; }

/* Compteur d'une section : replié, c'est lui qui remplace la lecture des
   cases une par une. Le ⚡ est sa partie indispensable — une ligne
   personnalisée est surlignée, mais ce surlignage disparaît avec la
   section refermée, et un réglage sur mesure invisible est un réglage
   oublié. */
.perms-section-compte {
    font-size: .72rem; font-weight: 600; color: var(--color-muted);
    white-space: nowrap; flex-shrink: 0;
}
.perms-section-compte--surmesure {
    color: #92400e; background: #fef3c7; border-radius: 3px; padding: 1px 6px;
}
[data-theme="dark"] .perms-section-compte--surmesure {
    color: #fbbf24; background: rgba(251,191,36,.12);
}

/* Les .perm-row portent déjà leur propre rembourrage : le corps de carte
   ne doit pas en ajouter un second autour d'elles. */
.perms-section-corps { padding: 0; }

.perms-header-bar { display: flex; align-items: center; gap: 12px; flex-wrap: wrap; }
.perms-header-body { flex: 1; }
.perms-header-name { font-size: 1rem; font-weight: 600; }
.perms-header-meta { margin-top: 4px; display: flex; gap: 8px; flex-wrap: wrap; align-items: center; }
.perms-header-caisse { font-size: .72rem; color: var(--color-muted); }
.perms-info-box {
    font-size: .8rem; color: var(--color-muted); background: var(--color-surface-alt);
    border-radius: var(--radius); padding: 10px 14px; margin-bottom: 1rem;
    border: 1px solid var(--color-border);
}
/* h3 depuis le regroupement par module : la règle .card-header h2 ne le
   couvre plus, graisse et marge sont reprises ici. */
.perms-section-title { font-size: .9rem; font-weight: 600; margin: 0; }

/* Bandeau de module : un titre et un compteur, pas une carte de plus.
   Il regroupe visuellement les sections d'un même module (six pour la
   trésorerie) et dit sans rien ouvrir où sont les droits d'une personne. */
.perms-module { margin-bottom: 1.5rem; }
.perms-module:not([open]) { margin-bottom: .6rem; }

/* Le module emprunte le repli mémorisé de details.ecole-pliable (app.js),
   pas son allure de carte : ces règles, écrites bien avant celles de
   l'école dans la feuille, l'emportent par leur précision (élément + deux
   classes) et non par leur place. Le <summary> reste en display: block,
   c'est le titre qui porte le flex (Safari iOS). */
details.perms-module.ecole-pliable > summary {
    padding: 0; border-bottom: none; background: none;
    list-style: none; cursor: pointer;
}
details.perms-module.ecole-pliable > summary::-webkit-details-marker { display: none; }
details.perms-module.ecole-pliable > summary:hover { background: none; }
details.perms-module.ecole-pliable > summary:hover .perms-module-titre { border-bottom-color: var(--color-primary); }

.perms-module-titre {
    display: flex; align-items: center; justify-content: space-between; gap: .5rem;
    margin: 0 0 .6rem; padding: 0 .15rem .4rem;
    font-size: .8rem; font-weight: 700; letter-spacing: .05em; text-transform: uppercase;
    color: var(--color-text);
    border-bottom: 2px solid var(--color-border-strong);
    transition: border-color .15s;
}
.perms-module:not([open]) .perms-module-titre { margin-bottom: 0; }
.perms-module-titre .perms-section-compte { text-transform: none; letter-spacing: 0; }
.perms-module-nom { display: flex; align-items: center; gap: .45rem; }
.perms-module-chevron {
    display: inline-block; font-size: .75rem; color: var(--color-muted);
    transition: transform .2s;
}
.perms-module:not([open]) .perms-module-chevron { transform: rotate(-90deg); }
.perms-icon { font-size: 15px; }
.perms-hint-locked { color: var(--color-muted); }
.perms-save-bar { display: flex; justify-content: flex-end; gap: .75rem; margin-top: .5rem; }

.perm-row {
    display: flex; align-items: center; justify-content: space-between;
    padding: 11px 20px; border-bottom: 1px solid var(--color-border); transition: background .1s;
}
.perm-row:last-child { border-bottom: none; }
.perm-row--changed { background: #fffbeb; }
[data-theme="dark"] .perm-row--changed { background: #2a2000; }

.perm-info { display: flex; align-items: center; gap: 10px; flex: 1; }
.perm-label { font-size: .85rem; font-weight: 500; display: block; }
.perm-default-hint { font-size: .72rem; margin-top: 2px; display: block; }
.hint--added   { color: #92400e; font-weight: 600; }
.hint--removed { color: var(--color-danger); font-weight: 600; }

.toggle-wrap { cursor: pointer; flex-shrink: 0; }
.toggle-wrap input { display: none; }
.toggle-track {
    display: block; width: 42px; height: 24px; border-radius: 12px;
    background: var(--color-border); position: relative; transition: background .2s;
}
.toggle-track::before {
    content: ''; position: absolute; width: 18px; height: 18px; border-radius: 50%;
    background: #fff; top: 3px; left: 3px; transition: transform .2s;
    box-shadow: 0 1px 3px rgba(0,0,0,.2);
}
.toggle-wrap input:checked + .toggle-track { background: var(--color-primary); }
.toggle-wrap input:checked + .toggle-track::before { transform: translateX(18px); }
.toggle-wrap--disabled { opacity: .4; cursor: not-allowed; pointer-events: none; }
.toggle-wrap.is-changed .toggle-track { outline: 2px solid var(--color-warning); outline-offset: 2px; }

/* Users (users.php) */
.user-form {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1.5rem; margin-bottom: 1.5rem; max-width: 620px;
}
.user-form h2 {
    font-size: 1.05rem; font-weight: 600; margin-bottom: 1.25rem;
    padding-bottom: .75rem; border-bottom: 1px solid var(--color-border);
}
.form-actions { display: flex; gap: .75rem; margin-top: 1.5rem; flex-wrap: wrap; }
.role-option {
    display: flex; align-items: flex-start; gap: 10px; padding: 10px 12px;
    border: 1.5px solid var(--color-border); border-radius: var(--radius);
    cursor: pointer; transition: border-color .15s, background .15s; margin-bottom: 8px;
}
.role-option:hover { border-color: var(--color-primary); background: var(--color-surface-alt); }
.role-option input[type=radio] { margin-top: 3px; flex-shrink: 0; }
.role-option.selected { border-color: var(--color-primary); background: var(--color-accent-lt); }
.role-icon { font-size: 18px; flex-shrink: 0; }
.role-label { font-size: .875rem; font-weight: 600; }
.role-desc { font-size: .78rem; color: var(--color-muted); margin-top: 2px; }
.caisse-preview {
    font-size: .8rem; background: var(--color-surface-alt); border: 1px solid var(--color-border);
    border-radius: 6px; padding: 6px 12px; margin-top: 8px; display: none;
}
.caisse-preview.is-visible { display: block; }
.caisse-preview code { background: #fef9ec; color: #7a5c00; padding: 1px 5px; border-radius: 3px; }
[data-theme="dark"] .caisse-preview code { background: #3a2d12; color: #f0c040; }
.usr-caisse-hint { display: block; margin-top: 4px; }

/* Le menu « Autres actions » d'une ligne s'ouvre en position absolue
   sous son bouton : la carte qui porte le tableau ne doit donc plus
   rogner ce qui dépasse d'elle. Sans contrepartie visuelle ici — ni les
   en-têtes ni les cellules de .users-table n'ont de fond, l'arrondi de
   la carte n'écrêtait donc rien qui se voie. */
.usr-list-card { overflow: visible; }

/* Ligne de suppression : elle est définitive et sans retour possible.
   Elle ne doit pas se lire comme les trois autres au moment où le doigt
   descend le menu. */
.usr-menu-danger { color: var(--color-danger); }

.users-table { width: 100%; border-collapse: collapse; font-size: .875rem; }
.users-table th {
    text-align: left; padding: .6rem .75rem; font-weight: 500; color: var(--color-muted);
    border-bottom: 2px solid var(--color-border); font-size: .78rem;
    text-transform: uppercase; letter-spacing: .03em;
}
.users-table td { padding: .7rem .75rem; border-bottom: 1px solid var(--color-border); vertical-align: middle; }
.users-table tr:last-child td { border-bottom: none; }
.users-table tr.inactive td { opacity: .5; }
.users-table a.usr-sort-link { text-decoration: none; color: inherit; }

.user-identity strong { font-weight: 500; display: block; }
.user-identity small { color: var(--color-muted); font-size: .76rem; }
.status-dot { display: inline-block; width: 8px; height: 8px; border-radius: 50%; margin-right: .4rem; }
.status-dot.active { background: var(--color-success); }
.status-dot.inactive { background: var(--color-danger); }
.actions-cell { display: flex; gap: .4rem; flex-wrap: wrap; }

.usr-self-role    { font-size: .85rem; }
.usr-list-body    { padding: 0; }
.usr-opt-badge    { font-size: .65rem; color: #92400e; background: #fef3c7; border-radius: 3px; padding: 1px 4px; }
[data-theme="dark"] .usr-opt-badge { color: #fbbf24; background: rgba(251,191,36,.12); }
.usr-caisse-code  { font-size: .75rem; background: var(--color-surface-alt); padding: 2px 5px; border-radius: 4px; }
.usr-locked       { color: var(--color-danger); }
.usr-connexions   { color: var(--color-muted); font-size: .8rem; }
.usr-count-wrap   { margin-top: .75rem; }

/* Utilisateurs groupés par rôle : une carte repliable par groupe. */
.usr-groupe { margin-bottom: .75rem; }
.usr-groupe-role { margin-top: .25rem; }

/* Chaque groupe est un tableau à part : laissées libres, ses colonnes
   prendraient la largeur de leur propre contenu et ne tomberaient plus
   les unes sous les autres d'une carte à l'autre. Largeurs fixées sur
   ordinateur seulement — sur téléphone, .table-mobile passe en cartes. */
@media (min-width: 769px) {
    .usr-table--groupe { table-layout: fixed; }
    .usr-table--groupe .usr-col-caisse     { width: 9rem; }
    .usr-table--groupe .usr-col-statut     { width: 8.5rem; }
    .usr-table--groupe .usr-col-connexions { width: 8.5rem; }
    .usr-table--groupe .usr-col-actions    { width: 16rem; }
}
.usr-check-label  { display: flex; align-items: center; gap: .5rem; cursor: pointer; }
.usr-actions-row  { display: flex; gap: .75rem; flex-wrap: wrap; }
.usr-stats-row { display: flex; gap: 1.5rem; flex-wrap: wrap; align-items: center; margin-bottom: 1rem; }
.usr-stat-item    { text-align: center; }
.usr-stat-val     { font-size: 1.8rem; font-weight: 700; }
.usr-stat-label   { font-size: .75rem; color: var(--color-muted); }
.usr-stat--present { color: #16a34a; }
.usr-stat--excuse  { color: #d97706; }
.usr-stat--absent  { color: #dc2626; }
.usr-stat--muted   { color: var(--color-muted); }
.usr-stat-bar-wrap { flex: 1; min-width: 120px; }
.usr-stat-bar { display: flex; height: 10px; border-radius: 5px; overflow: hidden; background: var(--color-border); }
.usr-stat-bar-seg { height: 100%; width: 0; transition: width .6s cubic-bezier(.22,.61,.36,1); }
.usr-stat-bar-seg--present { background: #16a34a; }
.usr-stat-bar-seg--excuse  { background: #d97706; }
.usr-stat-bar-seg--absent  { background: #dc2626; }
.usr-stat-bar-note { font-size: .7rem; color: var(--color-muted); margin-top: 4px; }

[data-theme="dark"] .btn-warning { background: rgba(251,191,36,.12); color: #fbbf24; border-color: rgba(251,191,36,.3); }
[data-theme="dark"] .btn-warning:hover { background: rgba(251,191,36,.2); }
[data-theme="dark"] .btn-danger  { background: rgba(220,38,38,.12); color: #f87171; border-color: rgba(220,38,38,.3); }
[data-theme="dark"] .btn-danger:hover  { background: rgba(220,38,38,.2); }
[data-theme="dark"] .btn-success { background: rgba(34,197,94,.12); color: #4ade80; border-color: rgba(34,197,94,.3); }
[data-theme="dark"] .btn-success:hover { background: rgba(34,197,94,.2); }
[data-theme="dark"] .btn-info    { background: rgba(59,130,246,.12); color: #60a5fa; border-color: rgba(59,130,246,.3); }
[data-theme="dark"] .btn-info:hover    { background: rgba(59,130,246,.2); }
[data-theme="dark"] .usr-stat--present { color: #4ade80; }
[data-theme="dark"] .usr-stat--excuse  { color: #fbbf24; }
[data-theme="dark"] .usr-stat--absent  { color: #f87171; }

@media (max-width: 768px) {
    /* Un compte désactivé s'estompait à 50 %. Entre deux lignes d'un
       tableau cela suffisait à le mettre en retrait ; isolé dans sa
       carte il ne se compare plus à rien et devient seulement illisible.
       La carte reprend donc sa lisibilité, son fond grisé et son filet
       en pointillés disent la mise à l'écart, et c'est le badge
       « Désactivé » — visible sans déplier — qui porte l'information. */
    .users-table tbody tr.inactive { background: var(--color-surface-alt); border-style: dashed; }
    .users-table tbody tr.inactive td { opacity: 1; }

    /* Le passage carte de .users-table est désormais géré par le motif
       partagé .table-mobile / .table-mobile--repliable (voir plus haut) :
       même liste repliable que Élèves/Familles, pas de règles propres ici. */
    .usr-stats-row { gap: 1rem; }
    .usr-stat-val { font-size: 1.4rem; }
    .usr-stat-bar-wrap { flex-basis: 100%; }
}

/* ═══════════════════════════════════════════════════
   PORTAIL — index.php
   ═══════════════════════════════════════════════════ */
.portal-page { margin: 0 auto; }
.portal-hello { margin-bottom: 2rem; }
.portal-hello h1 { font-size: 1.4rem; font-weight: 600; color: var(--color-text); margin-bottom: .25rem; }
.portal-hello p { color: var(--color-muted); font-size: .9rem; }

.modules-grid { display: grid; grid-template-columns: repeat(2, 1fr); gap: 1rem; margin-bottom: 1.25rem; }
@media (max-width: 600px) { .modules-grid { grid-template-columns: 1fr; } }

.module-card {
    display: flex; flex-direction: column;
    background: var(--color-surface); border: 1.5px solid var(--color-border);
    border-radius: var(--radius-lg); overflow: hidden;
    transition: border-color .15s, box-shadow .15s; position: relative;
}
.module-card--secret:hover { border-color: var(--color-primary); box-shadow: var(--shadow-md); }
.module-card--treso:hover  { border-color: #b8860b; box-shadow: var(--shadow-md); }
.module-card--ecole:hover  { border-color: var(--color-ecole); box-shadow: var(--shadow-md); }
.module-card__top {
    display: flex; flex-direction: column; padding: 1.4rem 1.4rem 1rem;
    text-decoration: none; color: inherit; transition: background .15s;
}
.module-card__top:hover { background: var(--color-surface-alt); }
.module-card__shortcuts {
    display: grid; grid-template-columns: repeat(2, 1fr); gap: 6px;
    padding: .85rem 1.4rem 1rem; border-top: 1px solid var(--color-border);
    background: var(--color-surface-alt);
}
@media (max-width: 480px) { .module-card__shortcuts { grid-template-columns: 1fr; } }
.module-card::before { content: ''; position: absolute; top: 0; left: 0; right: 0; height: 3px; }
.module-card--secret::before { background: var(--color-primary); }
.module-card--treso::before  { background: #c9a84c; }
.module-card--ecole::before  { background: var(--color-ecole); }
.module-card__icon { font-size: 1.8rem; margin-bottom: .6rem; }
.module-card__body { flex: 1; }
.module-card__title { font-size: 1.1rem; font-weight: 600; color: var(--color-text); margin-bottom: .3rem; }
.module-card__desc { font-size: .83rem; color: var(--color-muted); margin-bottom: .75rem; line-height: 1.4; }
.module-card__cta { font-size: .82rem; font-weight: 600; color: var(--color-primary); margin-top: auto; }
.module-card--treso .module-card__cta { color: #9a7000; }
.module-card--ecole .module-card__cta { color: var(--color-ecole-dk); }

.portal-stats {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 1.25rem;
    align-items: start;
}
.portal-stats__group {
    display: grid;
    grid-template-columns: repeat(2, 1fr);
    gap: .75rem;
    padding: .75rem;
    border-radius: 10px;
    background: var(--color-bg-soft, rgba(0,0,0,.02));
    border: 1px solid var(--color-border);
}
.portal-stats__group--secret { border-top: 3px solid var(--color-primary, #d97706); }
.portal-stats__group--treso  { border-top: 3px solid #b8860b; }
@media (max-width: 900px) {
    .portal-stats { grid-template-columns: 1fr; }
}
@media (max-width: 600px) {
    .portal-stats__group { grid-template-columns: 1fr; }
}
.pstat {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: .9rem 1rem; text-align: center;
    text-decoration: none; color: inherit; transition: border-color .15s, box-shadow .15s; display: block;
}
.pstat:hover { box-shadow: var(--shadow); }
.pstat--secret:hover { border-color: var(--color-primary); }
.pstat--treso:hover  { border-color: #b8860b; }
.pstat--danger { border-color: #f5c6cb !important; background: #fef2f2 !important; }
[data-theme="dark"] .pstat--danger { background: #2a1515 !important; border-color: #5a2020 !important; }
.pstat__val { font-size: 1.6rem; font-weight: 700; line-height: 1; color: var(--color-primary); margin-bottom: .3rem; }
.pstat--treso .pstat__val { color: #9a7000; }
.pstat--danger .pstat__val { color: var(--color-danger); }
.pstat__lbl { font-size: .72rem; color: var(--color-muted); line-height: 1.3; }

.shortcut {
    display: inline-flex; align-items: center; gap: 5px; padding: .4rem .85rem;
    border-radius: var(--radius); border: 1px solid var(--color-border);
    background: var(--color-surface); font-size: .82rem; font-weight: 500;
    text-decoration: none; color: var(--color-text); transition: all .15s;
}
.shortcut--s:hover { border-color: var(--color-primary); color: var(--color-primary); background: var(--color-accent-lt); }
.shortcut--t:hover { border-color: #b8860b; color: #7a5c00; background: #fef9ec; }
[data-theme="dark"] .shortcut--t:hover { background: #3d2e00; color: #fac775; }
.shortcut--e:hover { border-color: var(--color-ecole); color: var(--color-ecole-dk); background: var(--color-ecole-lt); }

/* ═══════════════════════════════════════════════════
   RECHERCHE — search/index.php
   ═══════════════════════════════════════════════════ */
.search-title { font-size: 1.5rem; font-weight: 600; margin-bottom: 1.5rem; }
.search-bar { display: flex; gap: .5rem; margin-bottom: 2rem; position: relative; }
.search-bar input[type="text"] {
    flex: 1; padding: .6rem 1rem; border: 2px solid var(--color-border);
    border-radius: var(--radius); font-size: 1rem; color: var(--color-text);
    background: var(--color-surface); transition: border-color .15s;
}
.search-bar input[type="text"]:focus { outline: none; border-color: var(--color-primary); box-shadow: 0 0 0 3px rgba(37,99,235,.1); }
.search-bar button { padding: .6rem 1.25rem; }
.search-dropdown {
    display: none; position: absolute; top: 100%; left: 0; right: 0; z-index: 50;
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); box-shadow: 0 8px 24px rgba(0,0,0,.12);
    margin-top: .35rem; max-height: 350px; overflow-y: auto;
}
.search-dropdown-item {
    display: flex; gap: .6rem; padding: .6rem .85rem; text-decoration: none;
    color: var(--color-text); border-bottom: 1px solid var(--color-border);
    align-items: center; font-size: .85rem; transition: background .1s;
}
.search-dropdown-item:hover { background: var(--color-surface-alt, #f8fafc); }
.search-dropdown-icon { font-size: 1.1rem; }
.search-dropdown-body { flex: 1; min-width: 0; }
.search-dropdown-label { font-weight: 500; display: block; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.search-dropdown-sub { font-size: .75rem; color: var(--color-muted); }
.search-stats { font-size: .85rem; color: var(--color-muted); margin-bottom: 1.5rem; }
.result-group-title {
    font-size: .9rem; font-weight: 600; color: var(--color-muted);
    text-transform: uppercase; letter-spacing: .03em;
    margin-bottom: .75rem; margin-top: 1.5rem;
    padding-bottom: .5rem; border-bottom: 1px solid var(--color-border);
}
.result-item {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1rem 1.25rem;
    margin-bottom: .75rem; transition: border-color .15s;
}
.result-item:hover { border-color: var(--color-primary); }
.result-title a { font-weight: 600; font-size: .95rem; color: var(--color-primary); text-decoration: none; }
.result-title a:hover { text-decoration: underline; }
.result-meta { display: flex; gap: 1rem; flex-wrap: wrap; margin-top: .3rem; font-size: .78rem; color: var(--color-muted); }
.result-snippet { margin-top: .5rem; font-size: .85rem; line-height: 1.6; color: var(--color-text); }
.result-snippet mark { background: #fef3c7; color: #92400e; padding: .05rem .2rem; border-radius: 2px; }
.result-point-label {
    display: inline-block; padding: .15rem .5rem; border-radius: 999px;
    font-size: .7rem; font-weight: 500; background: #eff6ff; color: var(--color-primary);
}
.empty-search { text-align: center; padding: 3rem 1rem; color: var(--color-muted); }
.empty-search .icon { font-size: 2.5rem; margin-bottom: 1rem; }
.search-hint { margin-top: .5rem; font-size: .85rem; }

/* ═══════════════════════════════════════════════════
   NOTIFICATIONS — notifications/index.php
   ═══════════════════════════════════════════════════ */
.notif-header { display: flex; align-items: center; gap: 1rem; margin-bottom: 1.5rem; flex-wrap: wrap; }
.notif-header h1 { flex: 1; font-size: 1.5rem; font-weight: 600; }
.notif-actions { display: flex; gap: .5rem; }
.notif-item {
    display: flex; gap: .75rem; align-items: flex-start;
    padding: .75rem 1rem; border-bottom: 1px solid var(--color-border); transition: background .15s;
}
.notif-item:last-child { border-bottom: none; }
.notif-item:hover { background: #f8fafc; }
.notif-item.unread { background: #eff6ff; }
.notif-icon {
    width: 36px; height: 36px; border-radius: 50%;
    display: flex; align-items: center; justify-content: center;
    font-size: 1rem; flex-shrink: 0;
}
.notif-icon.type-COMMENTAIRE_ADDED    { background: #dbeafe; }
.notif-icon.type-REUNION_RELECTURE    { background: #fef3c7; }
.notif-icon.type-REUNION_APPROUVEE    { background: #dcfce7; }
.notif-icon.type-ECHEANCE_J3          { background: #fef2f2; }
.notif-icon.type-ACTION_ASSIGNEE      { background: #ede9fe; }
.notif-icon.type-ACTION_COMMENT       { background: #dbeafe; }
.notif-icon.type-ACTION_MARKED_DONE   { background: #dcfce7; }
.notif-icon.type-default              { background: #f1f5f9; }
[data-theme="dark"] .notif-item:hover { background: var(--color-surface-alt); }
[data-theme="dark"] .notif-item.unread { background: #1a2a3a; }
[data-theme="dark"] .notif-icon.type-COMMENTAIRE_ADDED { background: #1a2a40; }
[data-theme="dark"] .notif-icon.type-REUNION_RELECTURE { background: #2a2515; }
[data-theme="dark"] .notif-icon.type-REUNION_APPROUVEE { background: #1a2a1a; }
[data-theme="dark"] .notif-icon.type-ECHEANCE_J3       { background: #2a1515; }
[data-theme="dark"] .notif-icon.type-ACTION_ASSIGNEE   { background: #1e1a30; }
[data-theme="dark"] .notif-icon.type-ACTION_COMMENT    { background: #1a2a40; }
[data-theme="dark"] .notif-icon.type-ACTION_MARKED_DONE { background: #1a2a1a; }
[data-theme="dark"] .notif-icon.type-default            { background: var(--color-surface-alt); }
.notif-body { flex: 1; min-width: 0; }
.notif-message { font-size: .875rem; line-height: 1.4; }
.notif-item.unread .notif-message { font-weight: 500; }
.notif-date { font-size: .75rem; color: var(--color-muted); margin-top: .2rem; }
.notif-read-btn {
    background: none; border: none; cursor: pointer;
    font-size: .8rem; color: var(--color-muted); padding: .2rem .4rem; border-radius: 4px; flex-shrink: 0;
}
.notif-read-btn:hover { background: var(--color-border); color: var(--color-text); }
.notif-dot { width: 8px; height: 8px; border-radius: 50%; background: var(--color-primary); flex-shrink: 0; margin-top: .4rem; }
.notif-dot.read { background: transparent; }
.notif-link { color: inherit; text-decoration: none; }
.notif-footer { margin-top: .75rem; display: flex; align-items: center; justify-content: space-between; flex-wrap: wrap; gap: .5rem; }
.empty-notif { text-align: center; padding: 3rem 1rem; color: var(--color-muted); }
.empty-notif .icon { font-size: 2.5rem; margin-bottom: 1rem; }

/* ═══════════════════════════════════════════════════
   ACTIONS — actions/index.php + mes_actions.php
   ═══════════════════════════════════════════════════ */
.actions-stats { display: grid; grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); gap: .75rem; margin-bottom: 1.5rem; }
.actions-stats .stat-card { padding: 1rem; }
.actions-stats .stat-value { font-size: 1.5rem; }
/* Tuile dont la liste est affichée en dessous. */
.actions-stats .actions-stat--active { border-color: var(--color-primary); box-shadow: 0 0 0 1px var(--color-primary); }

/* .action-resp : encore utilisée par reunions/edit.php. */
.action-resp { font-size: .85rem; }
.action-link-icon { color: var(--color-primary); font-size: .75rem; margin-left: 3px; }

.echeance-badge { padding: .2rem .5rem; border-radius: 999px; font-size: .75rem; font-weight: 500; white-space: nowrap; }
.ech-retard  { background: #fef2f2; color: var(--color-danger); }
.ech-soon    { background: #fef3c7; color: #92400e; }
.ech-ok      { background: #f0fdf4; color: var(--color-success); }
.ech-none    { background: #f1f5f9; color: var(--color-muted); }
[data-theme="dark"] .ech-retard { background: #2a1515; }
[data-theme="dark"] .ech-soon   { background: #2a2515; }
[data-theme="dark"] .ech-ok     { background: #1a2a1a; }
[data-theme="dark"] .ech-none   { background: var(--color-surface-alt); }

.close-modal {
    display: none; position: fixed; top: 0; left: 0; right: 0; bottom: 0;
    background: rgba(0,0,0,.4); z-index: 200; align-items: center; justify-content: center;
}
.close-modal.active { display: flex; }
.close-modal-content {
    background: var(--color-surface); border-radius: var(--radius);
    padding: 1.5rem; width: 100%; max-width: 450px; box-shadow: 0 10px 25px rgba(0,0,0,.15);
}
.close-modal-title { font-size: 1.05rem; font-weight: 600; margin-bottom: 1rem; }
.close-modal-desc { font-size: .9rem; margin-bottom: 1rem; color: var(--color-muted); }

/* Tableau des actions (actions/index.php). Retard et clôture sur les
   variables du thème : l'ancienne ligne en retard avait un fond clair
   écrit en dur, blanc cassé sur fond sombre. */
.actions-desc { font-weight: 500; }
.actions-source { font-size: .78rem; color: var(--color-muted); font-weight: 400; margin-top: .2rem; }
.actions-source a { color: var(--color-primary); text-decoration: none; }
.actions-table tr.actions-tr--retard td { background: var(--color-danger-lt); }
.actions-table tr.actions-tr--close { opacity: .65; }
@media (max-width: 768px) {
    .actions-table tbody tr.actions-tr--retard { border-left: 3px solid var(--color-danger); }
    .actions-table tbody tr.actions-tr--retard td { background: transparent; }
}

/* Mes actions */
.ma-stats { display: grid; grid-template-columns: repeat(auto-fit, minmax(120px, 1fr)); gap: .75rem; margin-bottom: 1.5rem; }
.ma-stats .stat-card { padding: .75rem; }
.ma-stats .stat-value { font-size: 1.4rem; }
.ma-filters { display: flex; gap: .75rem; margin-bottom: 1.5rem; align-items: center; }
.ma-filters .btn { padding: .35rem .75rem; font-size: .85rem; }
.ma-filters .btn.active { background: var(--color-primary); color: #fff; }
.ma-card {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); margin-bottom: 1rem; overflow: hidden;
}
.ma-card.late { border-left: 3px solid var(--color-danger); }
.ma-card.done { opacity: .65; }
.ma-card-header {
    padding: .75rem 1rem; display: flex; align-items: flex-start; gap: .75rem;
    background: var(--color-surface-alt); border-bottom: 1px solid var(--color-border);
}
.ma-card-icon { font-size: 1.1rem; }
.ma-card-body-wrap { flex: 1; }
.ma-card-body { padding: .75rem 1rem 1rem; }
.ma-desc { font-weight: 500; flex: 1; font-size: .9rem; }
.ma-meta { font-size: .78rem; color: var(--color-muted); display: flex; gap: .75rem; flex-wrap: wrap; margin-top: .3rem; }
.ma-comments { margin-top: .75rem; }
.ma-comments-title { font-size: .82rem; font-weight: 600; }
.ma-comment {
    padding: .5rem .75rem; background: var(--color-surface-alt);
    border-radius: var(--radius); margin-bottom: .5rem; font-size: .83rem;
}
.ma-comment-author { font-weight: 500; font-size: .78rem; color: var(--color-primary); }
.ma-comment-date { font-size: .72rem; color: var(--color-muted); }
.ma-comment-text { margin-top: .2rem; }
.ma-no-comment { font-size: .82rem; margin-top: .3rem; }
.ma-comment-form { display: flex; gap: .5rem; margin-top: .75rem; }
.ma-comment-form input[type="text"] {
    flex: 1; padding: .4rem .6rem; font-size: .85rem;
    border: 1px solid var(--color-border); border-radius: var(--radius);
    background: var(--color-surface); color: var(--color-text);
}
.ma-comment-form input[type="text"]:focus { outline: none; border-color: var(--color-primary); }
.ma-actions-btns { display: flex; gap: .5rem; margin-top: .75rem; }

/* Carte repliable (<details>). Repliée, l'en-tête perd son filet bas,
   qui soulignerait un corps absent. */
.ma-card > summary { list-style: none; cursor: pointer; }
.ma-card > summary::-webkit-details-marker { display: none; }
.ma-card > summary::marker { content: ''; }
.ma-card > summary:focus-visible { outline: 2px solid var(--color-primary); outline-offset: -2px; }
.ma-card:not([open]) .ma-card-header { border-bottom: none; }
.ma-card > summary:hover .ma-card-header { background: var(--color-primary-lt); }
.ma-card-chevron { font-size: .7rem; color: var(--color-muted); align-self: center; transform: rotate(-90deg); transition: transform .2s; }
.ma-card[open] .ma-card-chevron { transform: rotate(0); }
.ma-card-body-wrap { min-width: 0; }
@media (max-width: 640px) {
    /* L'échéance passe sous la description plutôt que de la comprimer :
       le bloc de texte réclame toute la ligne à côté de l'icône et du
       chevron, le badge retombe dessous, aligné sur le texte. */
    .ma-card-header { flex-wrap: wrap; gap: .4rem .6rem; }
    .ma-card-body-wrap { flex: 1 1 calc(100% - 3.2rem); }
    .ma-card-header .echeance-badge { order: 5; margin-left: 1.7rem; }
}

.done-modal-overlay {
    display: none; position: fixed; top: 0; left: 0; right: 0; bottom: 0;
    background: rgba(0,0,0,.4); z-index: 200; align-items: center; justify-content: center;
}
.done-modal-overlay.active { display: flex; }
.done-modal {
    background: var(--color-surface); border-radius: var(--radius-lg, var(--radius));
    padding: 1.5rem; width: 100%; max-width: 480px; margin: 1rem;
    box-shadow: 0 10px 25px rgba(0,0,0,.15); animation: modalIn .2s ease-out;
}
@keyframes modalIn { from { opacity: 0; transform: scale(.95) translateY(10px); } to { opacity: 1; transform: scale(1) translateY(0); } }
.done-modal-title { font-size: 1.05rem; font-weight: 600; margin-bottom: .5rem; }
.done-modal-desc { font-size: .85rem; color: var(--color-muted); margin-bottom: 1rem; }
.done-modal-label { font-size: .85rem; font-weight: 500; margin-bottom: .3rem; display: block; }
.done-modal-opt { color: var(--color-muted); font-weight: 400; }
.done-modal-hint { font-size: .72rem; color: var(--color-muted); margin-top: .75rem; }

/* ═══════════════════════════════════════════════════
   SECRÉTARIAT — secretariat/index.php
   ═══════════════════════════════════════════════════ */
.sec-shortcuts {
    display: flex; flex-wrap: wrap; gap: .5rem;
    margin-bottom: 1.25rem;
}
.sec-my-actions { margin-bottom: 1.5rem; }
.sec-my-actions-header { display: flex; align-items: center; justify-content: space-between; }
.sec-my-actions-header h2 { margin: 0; }
.sec-action-item {
    padding: .75rem 1rem; border-bottom: 1px solid var(--color-border);
    display: flex; align-items: center; gap: .75rem;
}
.sec-action-body { flex: 1; min-width: 0; }
.sec-action-desc { font-weight: 500; margin-bottom: .25rem; }
.sec-action-meta {
    font-size: .78rem; color: var(--color-muted);
    display: flex; gap: 1rem; flex-wrap: wrap;
}
.sec-action-respond { white-space: nowrap; font-size: .78rem; }

/* ═══════════════════════════════════════════════════
   PRÉSENCES — secretariat/presences.php
   ═══════════════════════════════════════════════════ */
.pres-filter-form { display: flex; gap: .75rem; align-items: flex-end; flex-wrap: wrap; margin-bottom: 1.5rem; }
.pres-filter-group { margin: 0; }
.pres-filter-label { font-size: .8rem; font-weight: 600; }
.pres-card { margin-bottom: 1.5rem; }
.pres-card-body--flush { padding: 0; }
.pres-empty { padding: 2rem; }
.pres-legende { font-size: .75rem; }
.pres-detail-table, .pres-stats-table { margin: 0; }
.pres-th-center  { text-align: center; }
.pres-td-date       { white-space: nowrap; font-size: .82rem; }
.pres-td-type       { font-size: .82rem; }
.pres-td-mandature  { font-size: .78rem; color: var(--color-muted); }
.pres-reunion-link  { color: var(--color-primary); font-weight: 500; }
.pres-td-presence   { text-align: center; font-weight: 600; font-size: .85rem; }
.pres-td-count { text-align: center; font-weight: 700; }
.pres-td-taux  { text-align: center; font-weight: 700; font-size: 1rem; }
.pres-td-bar   { min-width: 100px; }
.pres-role-badge { display: inline-block; margin-left: 4px; }
.pres-val--present { color: #16a34a; }
.pres-val--excuse  { color: #d97706; }
.pres-val--absent  { color: #dc2626; }
.pres-val--muted   { color: var(--color-muted); }
[data-theme="dark"] .pres-val--present { color: #4ade80; }
[data-theme="dark"] .pres-val--excuse  { color: #fbbf24; }
[data-theme="dark"] .pres-val--absent  { color: #f87171; }
.pres-bar {
    display: flex; height: 8px; border-radius: 4px; overflow: hidden;
    width: 100%; min-width: 80px; background: var(--color-border);
}
.pres-bar-seg { height: 100%; width: 0; transition: width .6s cubic-bezier(.22,.61,.36,1); }
.pres-bar-seg--present { background: #16a34a; }
.pres-bar-seg--excuse  { background: #d97706; }
.pres-bar-seg--absent  { background: #dc2626; }
.pres-bar-empty        { color: var(--color-muted); font-size: .75rem; }
@media (max-width: 768px) { .pres-filter-form { gap: .5rem; } .pres-td-bar { min-width: 0; } .pres-bar { min-width: 60px; } }

/* ═══════════════════════════════════════════════════
   MODÈLES — modeles/index.php
   ═══════════════════════════════════════════════════ */
.modele-form {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1.5rem; max-width: 600px; margin-bottom: 2rem;
}
.modele-form h2 {
    font-size: 1.1rem; font-weight: 600; margin-bottom: 1.25rem;
    padding-bottom: .75rem; border-bottom: 1px solid var(--color-border);
}
.points-list { display: flex; flex-direction: column; gap: .5rem; }
.points-list .point-input { display: flex; gap: .5rem; align-items: center; }
.points-list .point-input input {
    flex: 1; padding: .4rem .6rem; font-size: .85rem;
    border: 1px solid var(--color-border); border-radius: var(--radius);
}
.points-list .point-input input:focus { outline: none; border-color: var(--color-primary); }
.points-list .point-num {
    width: 24px; height: 24px; border-radius: 50%;
    background: var(--color-primary); color: #fff;
    display: flex; align-items: center; justify-content: center;
    font-size: .7rem; font-weight: 700; flex-shrink: 0;
}
.remove-point-btn { background: none; border: none; cursor: pointer; color: var(--color-danger); font-size: .85rem; padding: .2rem; }
.modele-empty { text-align: center; padding: 3rem; color: var(--color-muted); }
.modele-empty-icon { font-size: 2rem; margin-bottom: 1rem; }
.modele-name { font-weight: 500; }
.modele-desc { color: var(--color-muted); }
.modele-author { font-size: .85rem; color: var(--color-muted); }
.modele-actions { display: flex; gap: .4rem; justify-content: flex-end; }
.modele-del-btn { background: var(--color-danger-lt); color: var(--color-danger); border: 1px solid var(--color-border-strong); }
.modele-desc { font-size: .78rem; font-weight: 400; color: var(--color-muted); margin-top: .15rem; }

/* ═══════════════════════════════════════════════════
   DARK MODE — Inline style overrides
   ═══════════════════════════════════════════════════ */
[data-theme="dark"] input,
/* ══ Habillage de base d'une liste déroulante ══
   Le thème sombre habillait TOUS les select (règle ci-dessous), le thème
   clair aucun : il n'existait que des règles par contexte (.form-group,
   .filters, .ecole-filters…). Un select posé ailleurs — la colonne
   « Déplacer vers » d'une fenêtre de répartition, le jour d'un créneau —
   gardait donc l'apparence grise native du navigateur, au milieu de
   champs blancs et arrondis.

   Volontairement sans padding ni font-size : quatre contextes
   (.cour-sidebar-select, .ecole-appel-champ, .pv-add-action-wrap,
   .ops-pp-form) ne fixent pas les leurs et changeraient de taille. Cette
   règle habille, elle ne redimensionne pas — exactement ce que fait son
   équivalent sombre. Toute règle de classe l'emporte sur elle. */
select {
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    background: var(--color-surface);
    color: var(--color-text);
    font-family: var(--font);
}

/* ══ Le bouton « Choisir un fichier » ══
   Même défaut que les listes déroulantes, au même endroit : le cadre d'un
   champ de fichier venait de .form-group input, mais le bouton QUI EST
   DEDANS est dessiné par le navigateur et aucune règle du site ne le
   touchait — un bouton gris carré au milieu d'un champ blanc arrondi.
   Il est rare (quatre champs visibles : sauvegarde, les deux logos et la
   photo de couverture, une pièce jointe de réunion), donc jamais habillé
   contexte par contexte.
   Le pseudo-élément ne s'atteint que comme ceci : ni .btn ni une classe
   ne peuvent être posées sur un bouton que le navigateur fabrique. */
input[type="file"]::file-selector-button {
    margin-right: .6rem;
    padding: .3rem .7rem;
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    background: var(--color-surface-alt);
    color: var(--color-text);
    font-family: var(--font);
    font-size: .78rem;
    font-weight: 500;
    cursor: pointer;
}
input[type="file"]::file-selector-button:hover { background: var(--color-surface); }

[data-theme="dark"] select,
[data-theme="dark"] textarea {
    background: var(--color-surface);
    color: var(--color-text);
    border-color: var(--color-border-strong);
}
[data-theme="dark"] input::placeholder,
[data-theme="dark"] textarea::placeholder { color: var(--color-muted); }

[data-theme="dark"] .btn-secondary {
    background: var(--color-surface-alt);
    border-color: var(--color-border-strong);
}
[data-theme="dark"] .btn-danger {
    background: #7f1d1d; color: #fca5a5;
}

/* Inline colored backgrounds in dark */
[data-theme="dark"] [style*="background:#eff6ff"],
[data-theme="dark"] [style*="background: #eff6ff"] { background: var(--color-info-lt) !important; }
[data-theme="dark"] [style*="background:#f0fdf4"],
[data-theme="dark"] [style*="background: #f0fdf4"] { background: var(--color-success-lt) !important; }
[data-theme="dark"] [style*="background:#fef2f2"],
[data-theme="dark"] [style*="background: #fef2f2"] { background: var(--color-danger-lt) !important; }
[data-theme="dark"] [style*="background:#fffbeb"],
[data-theme="dark"] [style*="background: #fffbeb"],
[data-theme="dark"] [style*="background:#fef3c7"],
[data-theme="dark"] [style*="background: #fef3c7"] { background: var(--color-warning-lt) !important; }
[data-theme="dark"] [style*="background:#ecfeff"],
[data-theme="dark"] [style*="background: #ecfeff"] { background: var(--color-accent-lt) !important; }

/* Modals */
[data-theme="dark"] .modal-overlay { background: rgba(0,0,0,.6); }
[data-theme="dark"] .modal-coupures-box,
[data-theme="dark"] .modal-justif-box {
    background: var(--color-surface);
    box-shadow: var(--shadow-lg);
}

/* Coupures */
[data-theme="dark"] .coup-item { background: var(--color-surface-alt); border-color: var(--color-border); }
[data-theme="dark"] .coup-item.has-value { border-color: var(--color-primary); background: rgba(245,158,11,.06); }
[data-theme="dark"] .coup-btn-minus { background: #7f1d1d; color: #fca5a5; }
[data-theme="dark"] .coup-btn-plus  { background: var(--color-primary-lt); color: var(--color-primary); }

/* Justificatifs */
[data-theme="dark"] .justif-dropzone { border-color: var(--color-border); background: var(--color-surface); }
[data-theme="dark"] .justif-dropzone:hover { border-color: var(--color-primary); }

/* ═══════════════════════════════════════════════════
   PRINT
   ═══════════════════════════════════════════════════ */
@media print {
    /*  Les documents destinés au papier ont leurs propres pages, qui ne
        chargent pas cette feuille : export/rapport_ag_pdf.php,
        export/rapport_bureau_pdf.php, export/bilan_pdf.php, export/pdf.php…
        et le rapport de collecte s'imprime dans une fenêtre à part. Ce bloc
        ne sert donc qu'au reçu CERFA, imprimé depuis son écran, et à un
        Ctrl+P fait sur n'importe quelle autre page : il retire l'habillage
        de l'application. Les masquages qui étaient éparpillés dans les
        anciens blocs d'impression des rapports, et qui valaient en réalité
        pour toutes les pages, sont regroupés ici. */
    .sidebar, .mobile-topbar, .subnav, .bottom-bar,
    .app-footer, .theme-toggle, .notif-bell,
    .topbar-search-btn, .search-overlay,
    .btn, .filters-bar, .sb-actions,
    .topbar, .tn-bar, nav, .page-header, footer { display: none !important; }
    .main-area { margin-left: 0 !important; }
    .main-content { padding: 0 !important; margin: 0 !important; max-width: none !important; }
    body { background: #fff !important; color: #000 !important; }
    /* Sans ça, un aplat de couleur ne s'imprime pas : un texte blanc sur
       fond coloré sort blanc sur blanc. */
    html, body { -webkit-print-color-adjust: exact !important; print-color-adjust: exact !important; }
    .card { box-shadow: none !important; border: 1px solid #ccc !important; }
    * { color-scheme: light; }

    /*  ⚠ Une feuille A4 moins ses marges fait moins de 768px : la règle des
        petits écrans s'y applique, et son overflow-x: hidden sur .main-area
        et .main-content force l'autre axe à « auto ». La zone de contenu
        devenait une boîte qui défile, avec un ascenseur dessiné en travers
        de la feuille et tout ce qui dépassait rogné au lieu de passer à la
        page suivante. Sur du papier, rien ne défile. */
    html, body, .app-layout, .main-area, .main-content {
        overflow: visible !important;
        height: auto !important;
        max-height: none !important;
    }
    /*  Même piège pour les cartes : overflow: hidden arrondit leurs coins
        à l'écran, mais coupe net sur le papier une carte à cheval sur deux
        feuilles, au lieu de la laisser se poursuivre. */
    .card { overflow: visible !important; }

    /*  La marge appartient à la PAGE, pas au document : un rembourrage ne
        s'applique qu'au début et à la fin d'un bloc, et les feuilles du
        milieu toucheraient le bord. Page par défaut sans marge — ce qui
        prive le navigateur de la place où il imprime l'adresse du site —
        et contenu posé sur une page nommée qui porte les marges réelles.
        Même motif que export/pdf.php. */
    @page         { size: A4; margin: 0; }
    @page feuille { size: A4; margin: 15mm; }
    .main-content { page: feuille; }
}

/* ═══════════════════════════════════════════════════
   ANIMATIONS
   ═══════════════════════════════════════════════════ */
@keyframes fadeUp {
    from { opacity: 0; transform: translateY(6px); }
    to   { opacity: 1; transform: translateY(0); }
}
.stat-card { animation: fadeUp .25s ease both; }
.stat-card:nth-child(2) { animation-delay: .04s; }
.stat-card:nth-child(3) { animation-delay: .08s; }
.stat-card:nth-child(4) { animation-delay: .12s; }

/* ═══════════════════════════════════════════════════
   DASHBOARD TRÉSORERIE — Composants spécifiques
   ═══════════════════════════════════════════════════ */

/* « À traiter » — remplace les bandeaux pleine couleur, qui occupaient
   tout l'écran du téléphone avant les actions rapides. Fond neutre et
   filet de couleur : l'alerte se voit sans crier, et suit le thème.
   Hauteur mini 44 px : la ligne entière est la cible du doigt. */
/*  « À traiter » — composant partagé, et non un bloc de trésorerie.
    Né sur l'accueil du trésorier sous le préfixe treso-, il sert
    depuis à l'accueil de l'école : garder le préfixe d'un module
    aurait fait croire, à chaque lecture, que l'un des deux écrans
    emprunte le style de l'autre. */
.atraiter { margin-bottom: 1.25rem; }
.atraiter-liste { list-style: none; margin: 0; padding: 0; }
.atraiter-liste li + li { border-top: 1px solid var(--color-border); }
.atraiter-ligne {
    display: flex; align-items: center; gap: .6rem;
    min-height: 44px; padding: .5rem 1.25rem .5rem calc(1.25rem - 3px);
    border-left: 3px solid transparent;
    color: var(--color-text); text-decoration: none; font-size: .85rem;
}
.atraiter-ligne:hover { background: var(--color-surface-alt); text-decoration: none; }
.atraiter-ligne--danger { border-left-color: var(--color-danger); }
.atraiter-ligne--warn   { border-left-color: var(--color-warning); }
.atraiter-ligne--info   { border-left-color: var(--color-info); }
.atraiter-ico { flex-shrink: 0; }
.atraiter-lib { flex: 1; min-width: 0; }
.atraiter-val { font-weight: 700; white-space: nowrap; }
.atraiter-ligne--danger .atraiter-val { color: var(--color-danger); }
.atraiter-chevron { color: var(--color-muted); font-size: 1.1rem; flex-shrink: 0; }

@media (max-width: 768px) {
    .atraiter-ligne { padding-left: calc(.85rem - 3px); padding-right: .85rem; }
}

/* Actions rapides */
.actions-rapides {
    display: grid; grid-template-columns: repeat(auto-fit, minmax(130px, 1fr));
    gap: .65rem; margin-bottom: 1.25rem;
}
.action-card {
    display: flex; flex-direction: column; align-items: center; justify-content: center;
    gap: 6px; padding: .85rem .6rem; background: var(--color-surface);
    border: 1px solid var(--color-border); border-radius: var(--radius);
    text-decoration: none; color: var(--color-text); transition: all .15s;
    cursor: pointer; text-align: center;
}
.action-card:hover {
    border-color: var(--color-primary); background: var(--color-primary-lt);
    transform: translateY(-1px); box-shadow: var(--shadow);
    text-decoration: none;
}
.action-icon { font-size: 1.4rem; }
.action-label { font-size: .75rem; font-weight: 600; }

/* Stat sub-info */
.stat-sub { font-size: .75rem; color: var(--color-muted); margin-top: 4px; }
.stat-solde-reel { font-size: .8rem; font-weight: 600; margin-top: 3px; }

/* Soldes grid dashboard */
.treso-soldes { grid-template-columns: repeat(auto-fit, minmax(140px, 1fr)); margin-bottom: 1.25rem; }
.treso-stat { text-align: center; }
.treso-stat .stat-label { font-size: .72rem; color: var(--color-muted); margin-bottom: .35rem; font-weight: 500; }
.treso-stat .stat-value { font-size: 1.35rem; font-weight: 700; color: var(--color-primary); }
.treso-stat--total { border-color: var(--color-primary); }
.treso-stat--total .stat-value { color: var(--color-primary-dk); }
[data-theme="dark"] .treso-stat--total .stat-value { color: var(--color-primary); }

/* Stat card cliquable */
.treso-stat.stat-card--link { position: relative; cursor: pointer; transition: all .15s; }
.treso-stat.stat-card--link:hover { border-color: var(--color-primary); transform: translateY(-1px); box-shadow: var(--shadow-md); text-decoration: none; }
.treso-stat.stat-card--link::after { content:'↗'; position:absolute; top:.4rem; right:.6rem; font-size:.62rem; color:var(--color-muted); opacity:0; transition:opacity .15s; }
.treso-stat.stat-card--link:hover::after { opacity: 1; }

/* Carte dashboard */
.dash-card { margin-bottom: 1.25rem; }

/* Stats du mois */
.dash-mois-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 1rem; text-align: center; }
.dash-mois-value { font-size: 1.3rem; font-weight: 700; }
.dash-mois-label { font-size: .75rem; color: var(--color-muted); margin-top: .2rem; }

@media (max-width: 768px) {
    .treso-soldes { grid-template-columns: repeat(2, 1fr); }
    .dash-mois-grid { grid-template-columns: 1fr; gap: .5rem; }
    /*  Les grandes cases d'action ne servent que sur ordinateur : sur
        téléphone, la barre du bas mène déjà à la saisie et aux collectes,
        et deux cases de cette taille repoussaient les soldes hors de
        l'écran d'ouverture. Une grande case d'accueil est un geste du
        quotidien, pas une copie de la barre. */
    .actions-rapides { display: none; }
}

@media (max-width: 480px) {
    .treso-soldes { grid-template-columns: repeat(2, 1fr); }
}

/* Stat card danger variant (from index.php) */
.stat-card--danger .stat-value { color: var(--color-danger); }
[data-theme="dark"] .stat-card--danger { border-color: #7f1d1d; background: var(--color-danger-lt); }

/* Montant cells — common across trésorerie tables */
.treso-montant { text-align: right; font-weight: 600; white-space: nowrap; }
.treso-sub-count { font-size: .82rem; color: var(--color-muted); }

/* ═══════════════════════════════════════════════════
   CATÉGORIES — tresorerie/categories.php
   ═══════════════════════════════════════════════════ */

.cat-layout { display: grid; grid-template-columns: 320px 1fr; gap: 1.5rem; align-items: start; }
.cat-form-sticky { position: sticky; top: 110px; }
.card-title-sm { font-size: .9rem; }
.cat-col-scope { width: 140px; }
.cat-col-ops { width: 80px; text-align: center; }
.cat-col-actions { width: 80px; text-align: center; }
.cat-label { font-weight: 500; font-size: .88rem; }
.cat-scope-badge {
    font-size: .72rem; font-weight: 600;
    border-radius: 4px; padding: 2px 8px;
}
.cat-ops-count { text-align: center; font-size: .82rem; color: var(--color-muted); }
.cat-actions-row { display: flex; gap: 4px; justify-content: center; }
.cat-edit-zone { display: none; margin-top: 6px; }
.cat-edit-form { display: flex; gap: 4px; flex-wrap: wrap; }
.cat-edit-input { flex: 1; min-width: 0; font-size: .78rem; padding: 4px 6px; }
.cat-edit-select { font-size: .78rem; padding: 4px; }

[data-theme="dark"] .cat-scope-badge { filter: brightness(1.2); }

@media (max-width: 768px) {
    .cat-layout { grid-template-columns: 1fr; }
    .cat-form-sticky { position: static; }
}

/* ═══════════════════════════════════════════════════
   RÈGLES — tresorerie/regles.php
   ═══════════════════════════════════════════════════ */

.regles-info-box {
    background: #eff6ff; border-radius: var(--radius);
    padding: .75rem 1rem; margin-bottom: 1.25rem;
    font-size: .85rem; color: #1e40af;
}
[data-theme="dark"] .regles-info-box { background: rgba(37,99,235,.1); color: #93c5fd; }
.regles-info-example { margin-top: .3rem; display: block; }
.regles-code { background: white; padding: 1px 6px; border-radius: 4px; }
[data-theme="dark"] .regles-code { background: var(--color-surface-alt); }
.regles-form-grid {
    display: grid; grid-template-columns: 1fr 1fr 1fr auto;
    gap: .75rem; align-items: end; flex-wrap: wrap;
}
.regles-cat-flex { display: flex; gap: .4rem; }
.regles-cat-libre { width: 130px; }
.regles-col-actions { width: 80px; }
.regles-motcle {
    background: var(--color-surface-alt); padding: 2px 8px;
    border-radius: 4px; font-weight: 700;
}
.regles-cat-badge {
    background: #dbeafe; color: #1e40af;
    padding: 2px 10px; border-radius: 10px; font-size: .78rem;
}
[data-theme="dark"] .regles-cat-badge { background: rgba(37,99,235,.15); color: #93c5fd; }
.regles-sens { font-size: .78rem; color: var(--color-muted); }
.regles-match-badge {
    padding: 2px 10px; border-radius: 10px;
    font-weight: 700; font-size: .82rem;
}

/* Btn icon (used across tréso) */
.btn-icon {
    background: none; border: none; cursor: pointer;
    padding: 3px 5px; font-size: .9rem; opacity: .65; transition: opacity .15s;
}
.btn-icon:hover { opacity: 1; }

/* Modal overlay (used in regles, etc.) */
.modal-overlay {
    display: none; position: fixed; inset: 0;
    background: rgba(0,0,0,.5); z-index: 1000;
}
.modal-content {
    background: var(--color-surface); border-radius: var(--radius-lg);
    max-width: 480px; margin: 3rem auto; padding: 1.5rem;
}
.modal-title { margin-bottom: 1rem; }
.modal-footer { display: flex; gap: .5rem; justify-content: flex-end; margin-top: 1rem; }

@media (max-width: 768px) {
    .regles-form-grid { grid-template-columns: 1fr; }
    .regles-cat-libre { width: 100%; }
    .modal-content { max-width: 95vw; margin: 1rem auto; }
}

/* ═══════════════════════════════════════════════════
   CERFA — tresorerie/cerfa.php
   ═══════════════════════════════════════════════════ */

#cerfa-wrapper {
    position: fixed; inset: 0; background: #f0f0f0;
    z-index: 9999; overflow-y: auto; padding: 1rem;
}
.cerfa-bar { display: flex; gap: 1rem; justify-content: center; margin-bottom: 1rem; }
.cerfa-doc {
    background: #fff; max-width: 720px; margin: 0 auto;
    padding: 28px 32px; font-family: Arial, sans-serif;
    font-size: 11px; color: #000; line-height: 1.5; border: 1px solid #ccc;
}
.cerfa-num { text-align: right; font-size: 10px; color: #555; margin-bottom: 8px; }
.cerfa-h1 { font-size: 13px; font-weight: 700; text-align: center; text-transform: uppercase; margin: 0 0 6px; }
.cerfa-sub { text-align: center; font-size: 9.5px; color: #333; margin-bottom: 16px; line-height: 1.5; }
.cb { border: 1.5px solid #000; border-radius: 4px; padding: 10px 12px; margin-bottom: 10px; }
.cbl { border: 1px solid #bbb; border-radius: 4px; padding: 10px 12px; margin-bottom: 10px; }
.cts { font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .05em; color: #1a1a2e; margin-bottom: 8px; border-bottom: 1px solid #e5e5e5; padding-bottom: 4px; }
.cg2 { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; }
.cl { display: flex; gap: 4px; margin-bottom: 3px; font-size: 10.5px; }
.clb { color: #555; min-width: 110px; flex-shrink: 0; }
.cv { font-weight: 600; }
.cc { display: inline-block; border: 1px solid #000; padding: 0 3px; font-size: 10px; }
.cmb { font-size: 26px; font-weight: 700; text-align: center; color: #1a1a2e; margin: 8px 0 4px; }
.cft { margin-top: 14px; padding-top: 8px; border-top: 1px solid #ccc; font-size: 8.5px; color: #666; text-align: center; }
.cerfa-nature-line { margin-top: 8px; font-size: 10px; }
.cerfa-montant-lettres { text-align: center; font-size: 11px; margin-bottom: 10px; font-style: italic; }
.cerfa-avantage { background: #eeedf5; }
.cerfa-avantage-text { font-size: 10px; line-height: 1.7; }
.cerfa-sign-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 16px; margin-top: 12px; }
.cerfa-sign-date { font-size: 10px; font-weight: 700; margin-bottom: 4px; }
.cerfa-sign-president { font-size: 10px; margin-bottom: 4px; }
.cerfa-sign-space { height: 40px; }
.cerfa-sign-label { border-top: 1px solid #000; padding-top: 4px; font-size: 9px; color: #666; }
.cerfa-warning { background: #fffbeb; }
.cerfa-warn-title { font-size: 10px; font-weight: 700; margin-bottom: 4px; }
.cerfa-warn-text { font-size: 9px; line-height: 1.5; color: #555; }
.cerfa-main-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 1.5rem; align-items: start; }
.cerfa-gen-form { display: flex; flex-direction: column; gap: .85rem; }
.cerfa-readonly { padding: .5rem 0; font-size: .88rem; }
.cerfa-num-cell { font-family: monospace; font-size: .78rem; }

@media (max-width: 700px) {
    .cerfa-main-grid { grid-template-columns: 1fr; }
}
@media print {
    #cerfa-wrapper { position: static; background: none; padding: 0; overflow: visible; }
    .cerfa-bar, .no-print { display: none !important; }
    .cerfa-doc { max-width: 100%; border: none; padding: 0; }

    /*  ⚠ Cette règle s'écrivait « body > *:not(#cerfa-wrapper) ».
        Le seul enfant direct de <body> est .app-layout, sur TOUTES les
        pages du site : la règle le masquait donc partout, et tout aperçu
        d'impression sortait blanc — y compris celui du reçu CERFA, qui
        vit à l'intérieur de .app-layout et disparaissait avec lui.
        Ramenée à son intention : sur la page du reçu seulement, ne garder
        que le reçu en masquant ses voisins dans le contenu. Un navigateur
        sans :has() n'applique rien, plutôt que de tout cacher. */
    body:has(#cerfa-wrapper) .main-content > *:not(#cerfa-wrapper) { display: none !important; }
}

/* ═══════════════════════════════════════════════════
   RAPPORT AG — tresorerie/rapport_ag.php
   ═══════════════════════════════════════════════════ */

.ag-zone { margin: 0 auto; }
.ag-header-actions { display: flex; gap: .5rem; align-items: center; }
.ag-year-select {
    padding: .35rem .6rem; border: 1px solid var(--color-border);
    border-radius: var(--radius); font-size: .85rem; background: var(--color-surface);
}
.ag-header-block { text-align: center; margin-bottom: 2rem; padding-bottom: 1.5rem; border-bottom: 3px solid var(--color-primary); }
.ag-asso-name { font-size: 1.5rem; font-weight: 700; color: var(--color-primary); margin-bottom: .25rem; }
.ag-asso-sub { font-size: .72rem; letter-spacing: 2.5px; color: #c9a84c; text-transform: uppercase; margin-bottom: .6rem; }
.ag-report-title { font-size: 1.15rem; font-weight: 700; margin-bottom: .25rem; }
.ag-report-sub { font-size: .85rem; color: var(--color-muted); }

/* Résumé exécutif */
.ag-exec-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 1rem; margin-bottom: 1.75rem; }
.ag-exec-card { border-radius: var(--radius-lg); padding: 1.25rem; text-align: center; }
.ag-exec-card--recettes { background: #f0fdf4; border: 1px solid #bbf7d0; }
.ag-exec-card--depenses { background: #fef2f2; border: 1px solid #fecaca; }
.ag-exec-card--resultat { border-radius: var(--radius-lg); padding: 1.25rem; text-align: center; }
.ag-exec-label { font-size: .65rem; text-transform: uppercase; letter-spacing: 1.5px; margin-bottom: .5rem; font-weight: 600; }
.ag-exec-label--white { color: rgba(255,255,255,.7); }
.ag-exec-value { font-size: 1.5rem; font-weight: 800; }
.ag-exec-value--white { color: #fff; }
.ag-exec-n1 { font-size: .75rem; color: var(--color-muted); margin-top: .3rem; }
.ag-exec-n1--white { color: rgba(255,255,255,.5); }

[data-theme="dark"] .ag-exec-card--recettes { background: rgba(34,197,94,.08); border-color: rgba(34,197,94,.2); }
[data-theme="dark"] .ag-exec-card--depenses { background: rgba(239,68,68,.08); border-color: rgba(239,68,68,.2); }

/* Répartition banque / caisse */
.ag-split-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 1rem; margin-bottom: 1.75rem; }
.ag-split-card { border-radius: var(--radius-lg); overflow: hidden; }
.ag-split-card--banque { border: 1.5px solid #bfdbfe; }
.ag-split-card--caisse { border: 1.5px solid #fde68a; }
[data-theme="dark"] .ag-split-card--banque { border-color: rgba(59,130,246,.3); }
[data-theme="dark"] .ag-split-card--caisse { border-color: rgba(201,168,76,.3); }
.ag-split-body { padding: .9rem; display: grid; grid-template-columns: 1fr 1fr; gap: .5rem; text-align: center; }
.ag-split-label { font-size: .65rem; margin-bottom: .2rem; }
.ag-split-value { font-weight: 700; }

/* Section headers (colored bars) */
.ag-section-head {
    color: #fff; padding: .55rem 1rem;
    font-size: .7rem; font-weight: 700; letter-spacing: 1px; text-transform: uppercase;
}
.ag-section-head--banque { background: #1e40af; }
.ag-section-head--caisse { background: #c9a84c; }
.ag-section-head--cotis { background: #5b21b6; }
.ag-section-head--recettes { background: var(--color-success); }
.ag-section-head--depenses { background: var(--color-danger); }
.ag-section-head--mensuel { background: #1a3a5c; }
.ag-section-head--projets { background: #374151; }

/* Section cards */
.ag-section-card {
    border: 1.5px solid var(--color-border);
    border-radius: var(--radius-lg); overflow: hidden;
    margin-bottom: 1.5rem;
}
.ag-section-card--mb-lg { margin-bottom: 1.75rem; }

/* Cotisations grid */
.ag-cotis-grid { padding: 1.25rem; display: grid; grid-template-columns: repeat(4, 1fr); gap: 1rem; text-align: center; }
.ag-cotis-label { font-size: .65rem; color: var(--color-muted); text-transform: uppercase; letter-spacing: 1px; margin-bottom: .3rem; }
.ag-cotis-value { font-size: 1.4rem; font-weight: 700; }
.ag-cotis-value--sm { font-size: 1.1rem; }

/* Detail tables (recettes/dépenses) */
.ag-detail-body { padding: .9rem 1rem; }
.ag-detail-thead {
    display: flex; padding: .25rem 0 .5rem;
    font-size: .68rem; color: var(--color-muted);
    text-transform: uppercase; letter-spacing: 1px;
    border-bottom: 1px solid var(--color-border);
}
.ag-detail-row {
    display: flex; align-items: center; gap: .5rem;
    padding: .5rem 0; border-bottom: 1px solid var(--color-border);
}
.ag-col-cat { flex: 1; font-size: .83rem; }
.ag-col-montant { width: 100px; text-align: right; font-weight: 600; font-size: .83rem; }
.ag-col-n1 { width: 90px; text-align: right; font-size: .78rem; color: var(--color-muted); }
.ag-col-evol { width: 55px; text-align: right; }
.ag-detail-mixte { font-size: .7rem; color: var(--color-muted); }
.ag-mini-bar { width: 44px; height: 4px; background: var(--color-border); border-radius: 2px; overflow: hidden; flex-shrink: 0; }
.ag-mini-bar-spacer { width: 44px; }
.ag-detail-total { display: flex; padding-top: .6rem; font-weight: 700; font-size: .85rem; }
.ag-detail-total--success { border-top: 2px solid var(--color-success); }
.ag-detail-total--danger { border-top: 2px solid var(--color-danger); }

/* Évolution mensuelle */
.ag-mensuel-body { padding: 1.25rem 1rem 1rem; }
.ag-chart-grid { display: grid; grid-template-columns: repeat(12, 1fr); gap: 3px; align-items: end; height: 110px; margin-bottom: .4rem; }
.ag-chart-col { display: flex; flex-direction: column; align-items: center; gap: 0; height: 100%; justify-content: flex-end; }
.ag-chart-bars { display: flex; gap: 1px; align-items: flex-end; height: 100%; }
.ag-chart-labels { display: grid; grid-template-columns: repeat(12, 1fr); gap: 3px; text-align: center; }
.ag-chart-month { font-size: .62rem; color: var(--color-muted); font-weight: 600; }
.ag-chart-legend { display: flex; gap: 1rem; justify-content: center; margin-top: .75rem; font-size: .75rem; color: var(--color-muted); }
.ag-legend-dot {
    display: inline-block; width: 10px; height: 10px;
    border-radius: 2px; margin-right: 4px; vertical-align: middle; opacity: .8;
}
.ag-legend-dot--success { background: var(--color-success); }
.ag-legend-dot--danger { background: var(--color-danger); }

/* Projets */
.ag-projets-body { padding: .75rem 1rem; }
.ag-projet-row { padding: .6rem 0; border-bottom: 1px solid var(--color-border); display: flex; align-items: center; gap: .75rem; }
.ag-projet-dot { width: 10px; height: 10px; border-radius: 50%; flex-shrink: 0; }
.ag-projet-name { flex: 1; font-size: .85rem; font-weight: 500; }
.ag-projet-entree { font-size: .8rem; color: var(--color-success); }
.ag-projet-sortie { font-size: .8rem; color: var(--color-danger); }
.ag-projet-solde { font-size: .8rem; font-weight: 600; width: 90px; text-align: right; }
.ag-projet-budget { width: 70px; }
.ag-projet-budget-label { font-size: .65rem; color: var(--color-muted); margin-bottom: 2px; }
.ag-projet-bar-bg { height: 4px; background: var(--color-border); border-radius: 2px; overflow: hidden; }

/* Footer */
.ag-footer {
    display: flex; justify-content: space-between;
    font-size: .72rem; color: var(--color-muted);
    border-top: 1.5px solid var(--color-border);
    padding-top: .75rem; flex-wrap: wrap; gap: .5rem;
}

@media (max-width: 768px) {
    .ag-exec-grid { grid-template-columns: 1fr; }
    .ag-cotis-grid { grid-template-columns: repeat(2, 1fr); }
    .ag-split-grid { grid-template-columns: 1fr; }
    .ag-zone { font-size: .85rem; }
}

/* ═══════════════════════════════════════════════════
   UTILITAIRES TRÉSORERIE
   ═══════════════════════════════════════════════════ */

.mb-0 { margin-bottom: 0; }
.mb-1 { margin-bottom: 1rem; }
.mb-1-25 { margin-bottom: 1.25rem; }
.ml-05 { margin-left: .5rem; }
.p-0 { padding: 0; }
.p-1-5 { padding: 1.5rem; }
.w-full { width: 100%; }
.nowrap { white-space: nowrap; }
.d-inline { display: inline; }
.flex-1 { flex: 1; }
.overflow-x-auto { overflow-x: auto; }
.text-sm { font-size: .85rem; }
.text-right { text-align: right; }
.text-center { text-align: center; }
.text-uppercase { text-transform: uppercase; }
.text-primary { color: var(--color-primary); }
.empty-state { text-align: center; padding: 2rem; color: var(--color-muted); }

/* ═══════════════════════════════════════════════════
   OPÉRATIONS — Composants spécifiques
   ═══════════════════════════════════════════════════ */

/* Bandeau opération bancaire */
.ops-bank-notice {
    padding: .6rem 1.25rem; background: var(--color-info-lt);
    border-bottom: 1px solid var(--color-border);
    font-size: .78rem; color: var(--color-info);
    display: flex; align-items: center; gap: 6px;
}

/* Boutons formulaire */
.ops-form-btns { display: flex; gap: .75rem; margin-top: 1rem; flex-wrap: wrap; }

/* Ligne formulaire */
.form-row {
    display: grid; grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
    gap: .75rem; margin-bottom: .25rem;
}
@media (max-width: 768px) {
    .form-row { grid-template-columns: 1fr; }
}

/* Filtres */
.ops-filtres-inner { padding: .75rem 1rem; }
.ops-filtres select, .ops-filtres input {
    font-family: var(--font);
}
.ops-filtre-search { flex: 1; }

@media (max-width: 768px) {
    .ops-filtres { flex-direction: column; align-items: stretch; }
    .ops-filtre-btns { width: 100%; }
}


/* Bouton coupures */
.btn-coupures {
    display: inline-flex; align-items: center; gap: 4px;
    margin-top: 4px; padding: 3px 8px;
    font-size: .75rem; font-weight: 500;
    color: var(--color-primary); background: var(--color-primary-lt);
    border: 1px solid var(--color-primary-mid); border-radius: var(--radius);
    cursor: pointer; font-family: var(--font);
    transition: all .12s;
}
.btn-coupures:hover { background: var(--color-primary-mid); }

/* Justificatif dropzone */
.justif-dropzone {
    border: 2px dashed var(--color-border-strong);
    border-radius: var(--radius);
    padding: 1.25rem; text-align: center;
    transition: all .15s; cursor: pointer;
}
.justif-dropzone:hover { border-color: var(--color-primary); background: var(--color-primary-lt); }
.justif-drop-content { display: flex; flex-direction: column; align-items: center; gap: 6px; font-size: .85rem; color: var(--color-muted); }
.justif-spinner {
    width: 16px; height: 16px; border: 2px solid var(--color-border);
    border-top-color: var(--color-primary); border-radius: 50%;
    animation: spin .6s linear infinite;
}
@keyframes spin { to { transform: rotate(360deg); } }

/* Badge transfert */
.badge-transfert { font-size: .75rem; color: var(--color-info); font-weight: 500; }

/* ═══════════════════════════════════════════════════
   COLLECTES — Composants spécifiques
   ═══════════════════════════════════════════════════ */

/* Sections formulaire (espèces, CB, compteurs) */
.col-form-section {
    background: var(--color-surface-alt); border-radius: var(--radius);
    padding: 1rem; margin-bottom: 1.25rem; border: 1px solid var(--color-border);
}
.col-form-section-title { font-weight: 600; font-size: .85rem; margin-bottom: .75rem; }
.col-form-section-header {
    display: flex; align-items: center; justify-content: space-between; margin-bottom: .75rem;
}

/* Total banner — bien visible */
.col-total-banner {
    background: var(--color-primary); color: #fff; border-radius: var(--radius-lg);
    padding: 1.25rem; margin-bottom: 1.25rem; text-align: center;
    box-shadow: var(--shadow-md);
}
.col-total-label { font-size: .82rem; opacity: .85; margin-bottom: 6px; font-weight: 500; letter-spacing: .03em; text-transform: uppercase; }
.col-total-value { font-size: 2rem; font-weight: 800; letter-spacing: -.02em; }

/* Submit grid */
.col-form-submit { display: grid; grid-template-columns: 1fr 1fr; gap: .75rem; margin-top: .5rem; }
.col-form-submit .btn { text-align: center; }

/* Tiers compact */
.col-tiers-check { margin-bottom: 1.25rem; }
.col-tiers-label-compact {
    display: flex; align-items: center; gap: 8px; cursor: pointer;
    font-size: .88rem; font-weight: 500; color: var(--color-text);
    padding: 8px 12px; border-radius: var(--radius);
    border: 1px solid var(--color-border); background: var(--color-surface-alt);
    transition: all .15s;
    -webkit-tap-highlight-color: transparent;
}
.col-tiers-label-compact:hover { border-color: var(--color-primary); }
.col-tiers-label-compact input[type="checkbox"] {
    width: 16px; height: 16px; accent-color: var(--color-primary); flex-shrink: 0;
}
.col-tiers-label-compact input:checked ~ span { color: var(--color-primary-dk); font-weight: 600; }

/* Espacement entre les form-group dans le formulaire collecte */
.col-form-section .form-group { margin-bottom: .85rem; }
.col-form-section .form-group:last-child { margin-bottom: 0; }

/* Label optionnel inline */
.form-group label small { display: inline; }

/* Filtre année */
.col-filtre-annee {
    display: flex; align-items: center; gap: .5rem;
    margin-bottom: 1.25rem; flex-wrap: wrap;
}
.col-filtre-annee > span:first-child { font-size: .82rem; color: var(--color-muted); font-weight: 500; }

/* ═══════════════════════════════════════════════════════════════
   ADHÉRENTS — tresorerie/adherents.php
   ═══════════════════════════════════════════════════════════════ */
.adh-stats-grid { grid-template-columns: repeat(2, minmax(0, 200px)); margin-bottom: 1.25rem; }
.adh-val--warning { color: var(--color-warning); }
.adh-val--accent  { color: var(--color-accent); }
.adh-form-card    { max-width: 700px; margin-bottom: 1.5rem; }
.adh-input-cp     { max-width: 100px; }
.adh-checkbox-ecole { margin-top: .5rem; }
.adh-check-label  { display: flex; align-items: center; gap: 8px; cursor: pointer; font-weight: 500; }
.adh-form-actions { margin-top: 1.25rem; }
.adh-hr           { margin: 1.5rem 0; border: none; border-top: 1px solid var(--color-border); }
.adh-filters-card { margin-bottom: 1rem; }
.adh-filters-body { padding: .75rem 1rem; }
.adh-filters-form { display: flex; flex-wrap: wrap; gap: .5rem; align-items: center; }

.adh-filter-input-wrap {
    position: relative; display: flex; align-items: center;
}
.adh-filter-icon {
    position: absolute; left: .6rem; font-size: .85rem;
    pointer-events: none; z-index: 1;
}
.adh-search-input {
    padding: .4rem .75rem .4rem 2rem;
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    font-size: .82rem; min-width: 220px;
    background: var(--color-surface);
    color: var(--color-text);
    transition: border-color .15s, box-shadow .15s;
    font-family: var(--font);
}
.adh-search-input:focus {
    outline: none;
    border-color: var(--color-primary);
    box-shadow: 0 0 0 3px rgba(217,119,6,.12);
}
.adh-select {
    padding: .4rem .75rem; font-size: .82rem;
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    background: var(--color-surface);
    color: var(--color-text);
    font-family: var(--font);
    cursor: pointer;
    transition: border-color .15s;
}
.adh-select:focus { outline: none; border-color: var(--color-primary); }
.adh-check-filter { display: flex; align-items: center; gap: 5px; font-size: .82rem; cursor: pointer; }
.adh-pagination-wrap { display: flex; align-items: center; justify-content: space-between; flex-wrap: wrap; gap: .5rem; }
.adh-pagination-top  { margin-bottom: .75rem; }
.pagination-info     { font-size: .75rem; color: var(--color-muted); }

/* ── Desktop tableau / Mobile cartes ── */
.adh-cards-mobile  { display: none; }
.adh-table-desktop { display: block; }
@media (max-width: 768px) {
    .adh-table-desktop { display: none !important; }
    .adh-cards-mobile  { display: flex; flex-direction: column; gap: .75rem; }
}

.adh-table-body  { padding: 0; }
.adh-table       { min-width: 500px; }
.adh-th-num      { width: 90px; }
.adh-th-actions  { width: 70px; text-align: center; }

/* ── Cartes mobile adhérents ── */
.adh-card-item {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius-lg); box-shadow: var(--shadow); overflow: hidden;
    transition: box-shadow .15s;
}
.adh-card-item:active { box-shadow: var(--shadow-md); }
.adh-card-inactive { opacity: .6; }

.adh-card-head {
    display: flex; align-items: center; justify-content: space-between;
    padding: .85rem 1rem; gap: .75rem;
    border-bottom: 1px solid var(--color-border);
}
.adh-card-head-left { flex: 1; min-width: 0; }
.adh-card-nom {
    font-size: .92rem; font-weight: 600; color: var(--color-text);
    white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.adh-card-nom-link {
    text-decoration: none; color: inherit;
    border-bottom: 1px dashed var(--color-muted);
}
.adh-card-nom-link:hover { color: var(--color-primary); border-color: var(--color-primary); }
.adh-card-meta { font-size: .72rem; color: var(--color-muted); margin-top: 2px; }
.adh-card-badge-statut { flex-shrink: 0; }

.adh-card-details {
    display: flex; flex-direction: column; gap: 0;
}
.adh-card-detail-item {
    display: flex; justify-content: space-between; align-items: center;
    padding: .55rem 1rem; border-bottom: 1px solid var(--color-border);
    font-size: .82rem;
}
.adh-card-detail-item:last-child { border-bottom: none; }
.adh-card-detail-label { color: var(--color-muted); }
.adh-card-detail-val   { font-weight: 500; }

.adh-card-actions {
    display: flex; gap: 6px; padding: .6rem 1rem;
    border-top: 1px solid var(--color-border);
    background: var(--color-surface-alt);
}
.adh-card-act-btn {
    display: inline-flex; align-items: center; gap: 4px;
    padding: .3rem .7rem; border-radius: 6px;
    font-size: .75rem; font-weight: 500; text-decoration: none;
    color: var(--color-text); background: var(--color-surface);
    border: 1px solid var(--color-border);
    transition: background .15s, border-color .15s;
    cursor: pointer; font-family: inherit;
    -webkit-tap-highlight-color: transparent;
}
.adh-card-act-btn:hover { border-color: var(--color-primary); color: var(--color-primary); }

.adh-row-inactive td { opacity: .55; }
.adh-nom         { font-weight: 600; font-size: .88rem; }
.adh-nom-link    { text-decoration: none; color: var(--color-text); border-bottom: 1px dashed var(--color-muted); }
.adh-nom-link:hover { color: var(--color-primary); border-color: var(--color-primary); }
.adh-contact-line   { font-size: .78rem; }
.adh-cotis-val      { font-weight: 600; font-size: .85rem; }
.adh-cotis-period   { font-size: .72rem; }
.adh-derniere-cotis { display: block; font-size: .7rem; }
.adh-td-actions     { text-align: center; }
.adh-actions-btns   { display: flex; gap: 4px; justify-content: center; flex-wrap: wrap; }

.badge-ecole { font-size: .65rem; background: #e0f2fe; color: #0369a1; border-radius: 3px; padding: 1px 4px; margin-left: 4px; vertical-align: middle; }
[data-theme="dark"] .badge-ecole { background: #1a2a40; color: #6ec0e8; }
.btn-success { background: #f0fdf4; color: var(--color-success); border-color: #bbf7d0; }
.btn-success:hover { background: #bbf7d0; }
[data-theme="dark"] .btn-success { background: #1a2a1a; color: #4ade80; border-color: #2a4a2a; }
[data-theme="dark"] .btn-success:hover { background: #2a4a2a; }
.btn-scroll-top { display: none; position: fixed; bottom: 1.5rem; right: 1.5rem; z-index: 999; width: 42px; height: 42px; border-radius: 50%; border: none; cursor: pointer; background: var(--color-primary); color: #fff; font-size: 1.2rem; box-shadow: 0 2px 8px rgba(0,0,0,.2); align-items: center; justify-content: center; transition: opacity .2s; }
.modal-overlay { display: none; position: fixed; inset: 0; background: rgba(0,0,0,.45); z-index: 9999; align-items: center; justify-content: center; padding: 16px; }
.modal-overlay.open { display: flex; }
.modal-box { background: var(--color-surface); border-radius: 12px; max-width: 580px; width: 100%; max-height: 90vh; overflow-y: auto; box-shadow: 0 20px 60px rgba(0,0,0,.25); }
.modal-box--500 { max-width: 500px; }
[data-theme="dark"] .modal-box { box-shadow: 0 20px 60px rgba(0,0,0,.6); }
.modal-header { display: flex; justify-content: space-between; align-items: center; padding: 14px 20px; border-bottom: 1px solid var(--color-border); }
.modal-header-title { font-size: .95rem; font-weight: 600; }
.modal-close { background: none; border: none; font-size: 1.2rem; cursor: pointer; color: var(--color-muted); padding: 4px 8px; }
.modal-close:hover { color: var(--color-text); }
.modal-body { padding: 16px 20px; }

.modal-box--fiche { max-width: 720px; }
.adh-fiche-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 0; margin-bottom: 1rem; font-size: .85rem; }
.adh-fiche-field { display: flex; flex-direction: column; padding: .5rem .75rem; border-bottom: 1px solid var(--color-border); }
.adh-fiche-field:nth-last-child(-n+2) { border-bottom: none; }
.adh-fiche-label { font-size: .72rem; font-weight: 600; text-transform: uppercase; letter-spacing: .03em; color: var(--color-muted); margin-bottom: .15rem; }
.adh-import-info { font-size: .82rem; color: var(--color-muted); margin-bottom: 1rem; }
.adh-fiche-cotis { border-top: 1px solid var(--color-border); padding-top: .75rem; margin-top: .5rem; }
.adh-fiche-cotis-title { font-weight: 600; font-size: .85rem; margin-bottom: .5rem; }
.adh-fiche-cotis-list  { max-height: 260px; overflow-y: auto; overflow-x: auto; }
.adh-fiche-cotis-table { width: 100%; border-collapse: collapse; font-size: .82rem; }
.adh-fiche-cotis-table th { font-size: .7rem; text-transform: uppercase; letter-spacing: .03em; color: var(--color-muted); font-weight: 600; padding: .4rem .5rem; border-bottom: 2px solid var(--color-border); text-align: left; }
.adh-fiche-cotis-table td { padding: .55rem .5rem; border-bottom: 1px solid var(--color-border-strong, #d1d5db); vertical-align: top; }
.adh-fiche-cotis-table tbody tr:last-child td { border-bottom: none; }
.adh-fiche-cotis-table tbody tr:hover { background: var(--color-surface-alt); }
.adh-fiche-cotis-table tfoot td { border-top: 2px solid var(--color-border); border-bottom: none; padding-top: .5rem; }
.adh-fiche-cotis-desc { font-size: .78rem; color: var(--color-muted); max-width: 320px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.adh-fiche-cotis-rejet { background: var(--color-danger-lt, #fef2f2); }
.adh-fiche-nocotis { border-top: 1px solid var(--color-border); padding-top: .75rem; font-size: .82rem; color: var(--color-muted); }
.adh-fiche-actions { margin-top: 1rem; }
.form-row { display: grid; grid-template-columns: 1fr 1fr; gap: 1rem; }
@media (max-width: 600px) {
    .adh-stats-grid   { grid-template-columns: repeat(2,1fr); gap: .5rem; }
    .form-row         { grid-template-columns: 1fr; }
    .adh-search-input { min-width: 100%; }
    .adh-fiche-grid   { grid-template-columns: 1fr; }
    .adh-fiche-field  { padding: .4rem .5rem; }
    .modal-box--fiche { max-width: 100%; margin: 8px; border-radius: 10px; }
    .adh-fiche-cotis-table th,
    .adh-fiche-cotis-table td { padding: .35rem .3rem; font-size: .75rem; }
    .adh-fiche-cotis-desc { max-width: 140px; font-size: .72rem; }
    .adh-fiche-cotis-list { max-height: 220px; }
}

/* ═══════════════════════════════════════════════════════════════
   BILAN — tresorerie/bilan.php
   ═══════════════════════════════════════════════════════════════ */

/* Sélecteur année */
.bil-years { display: flex; gap: .5rem; flex-wrap: wrap; align-items: center; }
.bil-sep   { width: 1px; height: 20px; background: var(--color-border); margin: 0 4px; }

/* Blocs de section dashboard */
.bil-block { margin-bottom: 1.5rem; }
.bil-block-label {
    font-size: .78rem; font-weight: 600; text-transform: uppercase; letter-spacing: .05em;
    color: var(--color-muted); margin-bottom: .75rem;
}
.bil-note { font-size: .75rem; color: var(--color-muted); margin-top: .5rem; }

/* Couleurs sémantiques */
.bil-val--success { color: var(--color-success); }
.bil-val--danger  { color: var(--color-danger); }
.bil-val--muted   { color: var(--color-muted); }
.bil-val--primary { color: var(--color-primary); }
.bil-val--gold    { color: #9a7000; }
.bil-val--caisse  { color: #854f0b; }
.bil-val--small   { font-size: 1rem !important; }
[data-theme="dark"] .bil-val--gold   { color: #dbb850; }
[data-theme="dark"] .bil-val--caisse { color: #d4a559; }

/* Stat cards spécifiques */
.bil-stat--banque { border-color: #3bb8c4; }
.bil-stat--resultat-pos { border-color: #bbf7d0; }
.bil-stat--resultat-neg { border-color: #fecaca; }
[data-theme="dark"] .bil-stat--resultat-pos { border-color: rgba(34,197,94,.35); }
[data-theme="dark"] .bil-stat--resultat-neg { border-color: rgba(220,38,38,.35); }
.bil-stat--banque .stat-value,
.treso-stat .stat-value { font-size: 1.3rem; }

/* Card générique bilan */
.bil-card { margin-bottom: 1.5rem; }
.bil-card-body--flush { padding: 0; }
.bil-card-total { font-weight: 700; }

/* Cotisations */
.bil-cotis-grid {
    display: grid; grid-template-columns: repeat(3, 1fr);
    gap: 1rem; text-align: center;
}
.bil-cotis-item { min-width: 0; }
.bil-cotis-val   { font-size: 1.4rem; font-weight: 700; }
.bil-cotis-label { font-size: .75rem; color: var(--color-muted); }

/* Catégories (produits/charges) */
.bil-empty { padding: 1rem; }
.bil-cat-table { margin: 0; }
.bil-cat-name  { font-size: .85rem; font-weight: 500; }
.bil-cat-name--italic { font-style: italic; }
.bil-cat-right { text-align: right; white-space: nowrap; }
.bil-cat-val   { font-weight: 600; font-size: .88rem; }
.bil-cat-pct   { display: block; }
.bil-cat-row--amort { background: var(--color-surface-alt); }

/* Barres de progression */
.bil-bar {
    height: 4px; background: var(--color-border);
    border-radius: 2px; margin-top: 4px; overflow: hidden;
}
.bil-bar-fill {
    height: 100%; border-radius: 2px; width: 0;
    transition: width .6s cubic-bezier(.22,.61,.36,1);
}
.bil-bar-fill--success { background: var(--color-success); }
.bil-bar-fill--danger  { background: var(--color-danger); }

/* Flux transitoires (collapsible) */
.bil-transit { margin-top: 1.5rem; }
.bil-transit-head { cursor: pointer; }
.bil-transit-title { font-size: .9rem; color: var(--color-muted); }
.bil-transit-title small { font-weight: 400; }
.bil-transit-arrow { font-size: .8rem; color: var(--color-muted); transition: transform .15s; }
.bil-transit-body  { display: none; padding: 0; }
.bil-transit-body--open { display: block; }
.bil-transit-table { margin: 0; font-size: .83rem; }
.bil-transit-note  { padding: .75rem 1rem; font-size: .75rem; color: var(--color-muted); margin: 0; }
.bil-ta-r { text-align: right; }

/* ─────────────────────────────────────────────────────────
   BILAN COMPTABLE — Document officiel
   ─────────────────────────────────────────────────────── */
.bcp-doc { margin: 0 auto; font-size: .85rem; }

/* En-tête */
.bcp-head {
    text-align: center; padding-bottom: 16px;
    border-bottom: 2px solid var(--color-border); margin-bottom: 20px;
}
.bcp-head-title    { font-size: 1.3rem; font-weight: 800; color: var(--color-primary); }
.bcp-head-mentions { font-size: .72rem; color: var(--color-muted); margin-top: 2px; }
.bcp-head-subtitle { margin-top: 12px; font-size: .95rem; font-weight: 600; }
.bcp-head-legal    { font-size: .72rem; color: var(--color-muted); margin-top: 4px; }

/* Sections */
.bcp-section { margin-bottom: 24px; }
.bcp-section-title {
    color: #fff; padding: 8px 16px;
    border-radius: 8px 8px 0 0;
    font-weight: 700; font-size: .88rem;
}
.bcp-section-title--primary { background: var(--color-primary); }
.bcp-section-title--dark    { background: #374151; }
.bcp-section-title--green   { background: #065f46; }

/* Grille 2 colonnes (produits/charges et actif/passif) */
.bcp-2col {
    display: grid; grid-template-columns: 1fr 1fr;
    border: 1.5px solid var(--color-border);
    border-top: none;
    border-radius: 0 0 8px 8px;
    overflow: hidden;
}
.bcp-col              { min-width: 0; }
.bcp-col--divider     { border-right: 1px solid var(--color-border); }
.bcp-col-head {
    background: var(--color-surface-alt);
    padding: 8px 14px;
    font-weight: 700; font-size: .78rem;
    border-bottom: 1px solid var(--color-border);
    display: flex; justify-content: space-between;
}
.bcp-col-head--4 {
    display: grid; grid-template-columns: 1fr 110px 110px 110px;
    gap: 0; padding: 6px 14px; font-size: .72rem;
}
.bcp-col-head--4 span:nth-child(2),
.bcp-col-head--4 span:nth-child(3),
.bcp-col-head--4 span:nth-child(4) {
    text-align: right;
    padding-left: 8px;
    border-left: 1px solid var(--color-border);
}

/* Libellé latéral Actif/Passif */
.bcp-side-label {
    color: #fff; padding: 6px 14px;
    font-weight: 700; font-size: .75rem;
    text-transform: uppercase; letter-spacing: 1px;
}
.bcp-side-label--actif  { background: #1d4ed8; }
.bcp-side-label--passif { background: #7c3aed; }

/* Sous-en-têtes de groupe */
.bcp-subhead {
    padding: 6px 14px; font-weight: 600; font-size: .78rem;
    border-bottom: 1px solid rgba(0,0,0,.04);
}
.bcp-subhead--primary { color: var(--color-primary); background: rgba(29,78,216,.03); }
.bcp-subhead--success { color: var(--color-success); background: rgba(22,163,74,.03); }
.bcp-subhead--muted   { color: var(--color-muted);   background: rgba(0,0,0,.02); }
[data-theme="dark"] .bcp-subhead--primary { background: rgba(96,165,250,.06); }
[data-theme="dark"] .bcp-subhead--success { background: rgba(34,197,94,.06); }
[data-theme="dark"] .bcp-subhead--muted   { background: rgba(255,255,255,.02); }

/* Lignes */
.bcp-row {
    display: flex; justify-content: space-between;
    padding: 6px 14px;
    border-bottom: 1px solid rgba(0,0,0,.04);
    font-size: .82rem;
}
.bcp-row--2 { display: grid; grid-template-columns: 1fr auto; gap: 8px; font-size: .78rem; }
.bcp-row--4 { display: grid; grid-template-columns: 1fr 110px 110px 110px; gap: 0; font-size: .78rem; }
.bcp-row--4 > span:nth-child(2),
.bcp-row--4 > span:nth-child(3),
.bcp-row--4 > span:nth-child(4) {
    text-align: right;
    padding-left: 8px;
    border-left: 1px solid rgba(0,0,0,.06);
}
[data-theme="dark"] .bcp-row--4 > span:nth-child(2),
[data-theme="dark"] .bcp-row--4 > span:nth-child(3),
[data-theme="dark"] .bcp-row--4 > span:nth-child(4) {
    border-left-color: rgba(255,255,255,.08);
}
.bcp-row--indent { padding-left: 24px; padding-top: 5px; padding-bottom: 5px; }
.bcp-row--italic { font-style: italic; }
.bcp-row--total {
    background: var(--color-surface-alt);
    font-weight: 700; font-size: .85rem;
    padding: 8px 14px;
}
.bcp-row--subtotal {
    background: var(--color-surface-alt);
    font-weight: 600; font-size: .78rem;
    padding: 6px 14px;
    border-bottom: 1px solid var(--color-border);
}
.bcp-row--grandtotal {
    background: var(--color-surface-alt);
    font-weight: 800; font-size: .88rem;
    padding: 10px 14px;
}
.bcp-row-val { font-weight: 600; }
.bcp-ra      { text-align: right; }
[data-theme="dark"] .bcp-row     { border-bottom-color: rgba(255,255,255,.05); }
[data-theme="dark"] .bcp-subhead { border-bottom-color: rgba(255,255,255,.05); }

/* Résultat (grand encadré) */
.bcp-resultat {
    display: flex; align-items: center; justify-content: space-between;
    padding: 14px 20px; border-radius: 8px; margin-top: 8px;
    border: 2px solid;
}
.bcp-resultat--positif { background: rgba(22,163,74,.06); border-color: var(--color-success); }
.bcp-resultat--negatif { background: rgba(220,38,38,.06); border-color: var(--color-danger); }
.bcp-resultat-label {
    font-size: .72rem; text-transform: uppercase; letter-spacing: 1.5px;
    color: var(--color-muted); font-weight: 600;
}
.bcp-resultat-sub { font-size: .75rem; color: var(--color-muted); margin-top: 2px; }
.bcp-resultat-val { font-size: 1.4rem; font-weight: 800; }

/* Annexe */
.bcp-annex {
    border: 1.5px solid var(--color-border);
    border-top: none;
    border-radius: 0 0 8px 8px;
    padding: 20px;
}
.bcp-annex-block { margin-bottom: 16px; }
.bcp-annex-title { font-size: .85rem; font-weight: 700; margin-bottom: 6px; }
.bcp-annex-text  { font-size: .8rem; color: var(--color-muted); line-height: 1.7; margin: 0; }
.bcp-annex-box   { border-radius: 8px; padding: 14px 16px; margin-bottom: 16px; }
.bcp-annex-box--success { background: rgba(22,163,74,.05); }
.bcp-annex-box--purple  { background: rgba(124,58,237,.04); }
.bcp-val--purple { color: #7c3aed; }

.bcp-annex-table { width: 100%; font-size: .78rem; border-collapse: collapse; }
.bcp-annex-table thead tr { background: var(--color-surface-alt); }
.bcp-annex-table--purple thead tr { background: rgba(124,58,237,.08); }
.bcp-annex-table--purple thead th { color: #7c3aed; }
.bcp-annex-table th, .bcp-annex-table td {
    padding: 8px 12px;
    border-bottom: 1px solid rgba(0,0,0,.06);
}
[data-theme="dark"] .bcp-annex-table th,
[data-theme="dark"] .bcp-annex-table td { border-bottom-color: rgba(255,255,255,.06); }
.bcp-annex-table--purple td { border-bottom-color: rgba(124,58,237,.08); }
.bcp-th-l { text-align: left; }
.bcp-th-r, .bcp-td-r { text-align: right; }

/* Pied de document */
.bcp-footer {
    border-top: 1.5px solid var(--color-border);
    padding-top: 16px;
    display: flex; justify-content: space-between; align-items: flex-end;
    flex-wrap: wrap; gap: 1rem;
}
.bcp-footer-info { font-size: .75rem; color: var(--color-muted); }
.bcp-footer-sign { text-align: right; }
.bcp-footer-sign-label { font-size: .75rem; color: var(--color-muted); margin-bottom: 40px; }
.bcp-footer-sign-box   {
    border-top: 1px solid var(--color-text);
    padding-top: 4px;
    font-size: .75rem; color: var(--color-muted);
    width: 180px;
}

/* ── Mobile ── */
@media (max-width: 768px) {
    .bil-cotis-grid  { gap: .5rem; }
    .bil-cotis-val   { font-size: 1.15rem; }
    .bil-cotis-label { font-size: .68rem; }

    .dashboard-grid  { grid-template-columns: 1fr; gap: 1rem; }

    .bil-cat-name    { font-size: .8rem; }
    .bil-cat-val     { font-size: .82rem; }
    .bil-cat-pct     { font-size: .7rem; }

    .bcp-doc          { font-size: .82rem; }
    .bcp-2col         { grid-template-columns: 1fr; }
    .bcp-col--divider { border-right: none; border-bottom: 1px solid var(--color-border); }
    .bcp-col-head--4  { grid-template-columns: 1fr 80px 80px; font-size: .68rem; }
    .bcp-row--4       { grid-template-columns: 1fr 80px 80px; font-size: .72rem; }
    .bcp-row--4 > :nth-child(3) { display: none; }
    .bcp-col-head--4 > :nth-child(3) { display: none; }

    .bcp-resultat     { flex-direction: column; align-items: flex-start; gap: 8px; }
    .bcp-resultat-val { font-size: 1.2rem; }

    .bcp-annex-table  { font-size: .7rem; }
    .bcp-annex-table th,
    .bcp-annex-table td  { padding: 6px 8px; }

    .bcp-footer       { flex-direction: column; align-items: flex-start; }
    .bcp-footer-sign  { text-align: left; }
}
@media (max-width: 480px) {
    .bil-cotis-grid { grid-template-columns: repeat(3, 1fr); }
    .bil-cotis-val  { font-size: 1rem; }
}


/* ═══════════════════════════════════════════════════════════════
   COTISATIONS — tresorerie/cotisations.php
   ═══════════════════════════════════════════════════════════════ */
.cot-stats-grid  { grid-template-columns: repeat(3,1fr); margin-bottom: 1.25rem; }
.cot-val--success { color: var(--color-success); }
.cot-val--warning { color: var(--color-warning); }
.cot-val--gold    { color: #9a7000; font-size: 1rem; }
[data-theme="dark"] .cot-val--gold { color: #dbb850; }

/* Filtres */
.cot-filters-card { margin-bottom: .75rem; }
.cot-filters-body { padding: .6rem 1rem; }
.cot-filters-form { display: flex; flex-wrap: wrap; gap: .5rem; align-items: center; }
.cot-select {
    padding: .38rem .6rem; border: 1px solid var(--color-border-strong);
    border-radius: var(--radius); font-size: .85rem;
    background: var(--color-surface); color: var(--color-text);
    font-family: var(--font); cursor: pointer;
}
.cot-select:focus { outline: none; border-color: var(--color-primary); }
.cot-search-wrap  { position: relative; display: flex; align-items: center; }
.cot-search-icon  { position: absolute; left: .6rem; font-size: .82rem; pointer-events: none; }
.cot-search-input {
    padding: .38rem .6rem .38rem 1.9rem;
    border: 1px solid var(--color-border-strong); border-radius: var(--radius);
    font-size: .85rem; width: 160px;
    background: var(--color-surface); color: var(--color-text);
    font-family: var(--font);
}
.cot-search-input:focus { outline: none; border-color: var(--color-primary); }
.cot-info-mois { font-size: .78rem; color: var(--color-muted); margin-left: .25rem; }

/* Légende */
.cot-legende {
    display: flex; gap: 1rem; font-size: .78rem;
    color: var(--color-muted); margin-bottom: .75rem;
    flex-wrap: wrap; align-items: center;
}
.cot-legende-tip { font-style: italic; }

/* Tableau — wrapper dédié */
.cot-table-wrapper {
    background: var(--color-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    box-shadow: var(--shadow);
    overflow-x: auto;
    overflow-y: visible;
}
.cot-table th   { font-size: .75rem; font-weight: 600; white-space: nowrap; padding: .5rem .4rem; }

.cot-th-membre  { min-width: 170px; position: sticky; left: 0; background: var(--color-surface); z-index: 2; }
.cot-th-euromois { text-align: center; width: 55px; }
.cot-th-total   { text-align: right; width: 80px; padding-right: .75rem; }
.cot-th-statut  { text-align: center; width: 50px; }
.cot-th-action  { text-align: center; width: 50px; }

.cot-td-membre  { position: sticky; left: 0; background: var(--color-surface); z-index: 1; }
.cot-membre-link { text-decoration: none; color: inherit; font-weight: 500; }
.cot-membre-link:hover { color: var(--color-primary); }
.cot-membre-sub  { font-size: .7rem; color: var(--color-muted); }
.cot-td-euromois { text-align: center; font-size: .8rem; color: var(--color-muted); }
.cot-cell        { text-align: center; padding: .2rem .1rem; }
.cot-cell--futur { opacity: .3; }
.cot-cell--avant { opacity: .25; }
.cot-dot-futur   { color: var(--color-border); }
.cot-td-total    { text-align: right; font-size: .82rem; font-weight: 600; padding-right: .75rem; white-space: nowrap; }
.cot-td-total--ok   { color: var(--color-success); }
.cot-td-total--zero { color: var(--color-muted); }
.cot-td-statut   { text-align: center; font-size: 1rem; }
.cot-td-action   { text-align: center; }
.cot-empty-cell  { text-align: center; padding: 2rem; color: var(--color-muted); }

/* Badges mois */
.badge-ecole-sm { font-size: .63rem; background: #dbeafe; color: #1e40af; padding: 1px 4px; border-radius: 3px; margin-left: 3px; }
[data-theme="dark"] .badge-ecole-sm { background: #1a2a40; color: #6ec0e8; }
.cot-mois-th    { background: var(--color-surface-alt); transition: background .15s; text-align: center; width: 36px; font-size: .72rem; cursor: pointer; user-select: none; }
.cot-mois-th:hover { background: rgba(201,168,76,.12); }
.cot-mois--courant { background: rgba(201,168,76,.2) !important; color: #9a7000; font-weight: 700; }
.cot-mois-th.filtre-impaye { background: #fef2f2 !important; color: var(--color-danger); }
.cot-mois-th.filtre-paye   { background: #f0fdf4 !important; color: var(--color-success); }
[data-theme="dark"] .cot-mois--courant     { color: #f0c040; }
[data-theme="dark"] .cot-mois-th.filtre-impaye { background: #2a1515 !important; }
[data-theme="dark"] .cot-mois-th.filtre-paye   { background: #1a2a1a !important; }

.cot-badge      { display: inline-flex; align-items: center; justify-content: center; width: 22px; height: 22px; border-radius: 4px; font-size: .75rem; font-weight: 700; }
.cot-badge--ok  { background: #dcfce7; color: #166534; }
.cot-badge--non { background: transparent; color: var(--color-border); font-size: 1.1rem; }
[data-theme="dark"] .cot-badge--ok { background: #1a2a1a; color: #4ade80; }

.cot-row--impaye  > td:first-child { border-left: 3px solid var(--color-danger); }
.cot-row--partiel > td:first-child { border-left: 3px solid #f59e0b; }
.cot-row--solde   > td:first-child { border-left: 3px solid var(--color-success); }
.cot-row.cot-hidden { visibility: collapse; }

/* Bouton payer */
.btn-payer {
    background: none; border: 1.5px solid var(--color-border); border-radius: 6px;
    padding: 2px 6px; cursor: pointer; font-size: .85rem; transition: all .15s;
}
.btn-payer:hover { border-color: var(--color-primary); background: rgba(29,78,216,.04); }

/* Modal paiement */
.modal-overlay-cotis { display: none; position: fixed; inset: 0; background: rgba(0,0,0,.45); z-index: 9999; align-items: center; justify-content: center; padding: 16px; }
.modal-overlay-cotis.open { display: flex; }
.modal-paiement-box { background: var(--color-surface); border-radius: 12px; max-width: 520px; width: 100%; max-height: 90vh; overflow-y: auto; box-shadow: var(--shadow-lg); }
[data-theme="dark"] .modal-paiement-box { box-shadow: 0 20px 60px rgba(0,0,0,.6); }
.modal-paiement-header { display: flex; justify-content: space-between; align-items: center; padding: 14px 20px; border-bottom: 1px solid var(--color-border); }
.modal-paiement-title  { margin: 0; font-size: 1rem; font-weight: 600; }
.modal-paiement-close  { background: none; border: none; font-size: 1.2rem; cursor: pointer; color: var(--color-muted); padding: 4px 8px; }
.modal-paiement-close:hover { color: var(--color-text); }
.modal-paiement-body  { padding: 16px 20px 0; }
.modal-paiement-footer { padding: 14px 20px 20px; }

.cot-periode-wrap  { margin-bottom: 14px; }
.cot-periode-label { font-size: .7rem; font-weight: 700; text-transform: uppercase; letter-spacing: .5px; color: var(--color-muted); display: block; margin-bottom: 6px; }
.cot-periode-row   { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; margin-bottom: 8px; }
.cot-periode-sep   { font-size: .82rem; color: var(--color-muted); }
.cot-periode-select {
    padding: 6px 8px; border: 1.5px solid var(--color-border); border-radius: var(--radius);
    font-size: .82rem; background: var(--color-surface); color: var(--color-text);
    font-family: var(--font);
}
.cot-periode-select-sm { width: 80px; }
.cot-periode-resume   { font-size: .82rem; font-weight: 600; color: var(--color-primary); margin-top: 4px; }
.cot-periode-decoupe  { font-size: .75rem; color: var(--color-muted); margin-top: 4px; }
.p-form-grid { display: grid; grid-template-columns: 1fr 1fr; gap: .75rem; margin-bottom: .5rem; }

/* Réassignation mois */
.reassign-op-form { padding: .75rem 0; border-bottom: 1px solid var(--color-border); }
.reassign-op-form:last-of-type { border-bottom: none; }
.reassign-op-header { font-size: .85rem; margin-bottom: .5rem; }
.reassign-mois-grid { display: grid; grid-template-columns: repeat(6, 1fr); gap: .35rem; }
.reassign-mois-label {
    font-size: .78rem; display: flex; align-items: center; gap: .25rem;
    padding: .25rem .35rem; border-radius: var(--radius); cursor: pointer;
    border: 1px solid var(--color-border); background: var(--color-surface);
    transition: all .1s;
}
.reassign-mois-label:hover { border-color: var(--color-primary); background: var(--color-accent-lt); }
.reassign-mois-label input[type="checkbox"] { margin: 0; }

/* Historique paiements */
.histo-info {
    display: flex; gap: 1.5rem; flex-wrap: wrap;
    padding: .6rem .75rem; background: var(--color-surface-alt);
    border-radius: var(--radius); font-size: .85rem;
    margin-bottom: .5rem;
}

@media (max-width: 700px) { .cot-stats-grid { grid-template-columns: repeat(3,1fr); gap: .5rem; } .reassign-mois-grid { grid-template-columns: repeat(4, 1fr); } }
@media (max-width: 480px) {
    .cot-stats-grid { grid-template-columns: 1fr !important; gap: .5rem; }
    .p-form-grid    { grid-template-columns: 1fr; }
    .cot-info-mois  { display: none; }
}

/* ── Mobile ── */
@media (max-width: 768px) {
    .cot-filters-body { padding: .6rem .75rem; }
    .cot-filters-form { flex-direction: column; align-items: stretch; gap: .4rem; }
    .cot-select       { width: 100%; box-sizing: border-box; font-size: .88rem; }
    .cot-search-wrap  { width: 100%; }
    .cot-search-input { width: 100%; box-sizing: border-box; }

    .cot-legende-tip  { display: none; }

    .cot-table-wrapper {
        margin-left:  -12px;
        margin-right: -12px;
        width: 100vw;
        max-width: 100vw;
        box-sizing: border-box;
        border-radius: 0;
        border-left: none;
        border-right: none;
        overflow-x: auto;
        -webkit-overflow-scrolling: touch;
    }
    .cot-table-wrapper::after {
        content: '← Faites défiler le tableau →';
        display: block;
        text-align: center;
        font-size: .68rem;
        color: var(--color-muted);
        padding: .35rem 0 .45rem;
        border-top: 1px solid var(--color-border);
        background: var(--color-surface-alt);
    }

    .cot-table { font-size: .72rem; min-width: 680px; }
    .cot-table th, .cot-table td { padding: .3rem .22rem; }
    .cot-th-membre   { min-width: 110px; font-size: .72rem; padding-left: 12px; }
    .cot-td-membre   { padding-left: 12px; }
    .cot-th-euromois { display: none; }
    .cot-td-euromois { display: none; }
    .cot-mois-th     { width: 26px; font-size: .63rem; padding: .3rem .1rem; }
    .cot-th-total    { width: 55px; font-size: .65rem; }
    .cot-th-statut   { width: 32px; }
    .cot-th-action   { width: 32px; }
    .cot-membre-link { font-size: .76rem; }
    .cot-membre-sub  { font-size: .61rem; }
    .cot-td-total    { font-size: .7rem; padding-right: .35rem; }
    .cot-badge       { width: 17px; height: 17px; font-size: .62rem; border-radius: 3px; }
    .btn-payer       { font-size: .7rem; padding: 1px 3px; }

    .cot-th-membre, .cot-td-membre {
        position: sticky; left: 0;
        background: var(--color-surface);
        box-shadow: 2px 0 6px rgba(0,0,0,.08);
        z-index: 2;
    }
    .cot-th-membre { z-index: 3; background: var(--color-surface-alt); }
    [data-theme="dark"] .cot-th-membre,
    [data-theme="dark"] .cot-td-membre {
        box-shadow: 2px 0 6px rgba(0,0,0,.25);
    }

    .cot-row:hover .cot-td-membre { background: var(--color-surface-alt); }
}

/* ═══════════════════════════════════════════════════════════════
   VERSEMENT — tresorerie/versement.php
   ═══════════════════════════════════════════════════════════════ */

/* Layout */
.vers-raccourcis {
    display: flex; flex-wrap: wrap;
    gap: 8px; margin-bottom: 1rem;
}
.vers-layout {
    display: grid; grid-template-columns: 380px 1fr;
    gap: 1.5rem; align-items: start;
}
.vers-col-form { min-width: 0; }

/* Card soldes */
.vers-soldes-card { margin-bottom: 1rem; }
.vers-card-title  { font-size: .9rem; }
.vers-soldes-body { padding: .75rem; }
.vers-solde-row {
    display: flex; justify-content: space-between; align-items: center;
    padding: 6px 0; border-bottom: 1px solid var(--color-border);
    font-size: .85rem;
}
.vers-solde-row:last-child { border-bottom: none; }
.vers-solde-val { font-weight: 700; }
.vers-val--primary { color: var(--color-primary); }
.vers-val--danger  { color: var(--color-danger); }
.vers-val--success { color: var(--color-success); }
.vers-val--muted   { color: var(--color-muted); }

/* Source read-only (trésorier) */
.vers-source-readonly {
    padding: .6rem .75rem;
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    font-size: .88rem; font-weight: 500;
}

/* Solde message */
.vers-solde-msg {
    color: var(--color-muted); font-size: .75rem;
}
.vers-solde-msg.is-danger  { color: var(--color-danger); }
.vers-solde-msg.is-success { color: var(--color-success); }

/* Récap */
.vers-recap {
    display: none;
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    padding: .75rem 1rem;
    margin-bottom: 1rem;
    font-size: .85rem;
}
.vers-recap.is-visible { display: block; }
.vers-recap-txt { text-align: center; font-weight: 600; }

/* Raccourcis */
.btn-raccourci {
    padding: 8px 14px; border: 1.5px solid var(--color-border); border-radius: var(--radius);
    background: var(--color-surface); cursor: pointer; font-size: .78rem; font-weight: 600;
    color: var(--color-text); transition: all .15s; white-space: nowrap;
}
.btn-raccourci:hover {
    border-color: var(--color-primary); background: rgba(29,78,216,.04);
    transform: translateY(-1px);
}
.btn-raccourci.active {
    border-color: var(--color-primary); background: rgba(29,78,216,.08);
    color: var(--color-primary);
}

/* Historique */
.vers-hist-body  { padding: 0; }
.vers-hist-empty { padding: 2rem; }
.vers-hist-table { margin: 0; }
.vers-th-date    { width: 90px; }
.vers-th-montant { text-align: right; width: 110px; }
.vers-th-actions { width: 70px; }
.vers-td-date    { font-size: .82rem; white-space: nowrap; }
.vers-td-compte  { font-size: .82rem; }
.vers-td-montant {
    text-align: right; font-weight: 700;
    font-size: .88rem; color: var(--color-primary);
}
.vers-td-statut    { font-size: .78rem; }
.vers-td-operateur { font-size: .78rem; color: var(--color-muted); }

.vers-badge { font-weight: 600; }
.vers-badge--ok   { color: var(--color-success); }
.vers-badge--wait { color: var(--color-muted); }

.vers-btn-delete {
    color: var(--color-danger); font-size: .78rem;
}

/* ── Mobile ── */
@media (max-width: 768px) {
    .vers-layout      { grid-template-columns: 1fr; gap: 1rem; }
    .vers-raccourcis  { gap: 6px; }
    .btn-raccourci    { flex: 1 1 auto; font-size: .72rem; padding: 7px 10px; }

    .vers-td-montant  { color: var(--color-primary); font-weight: 700; }
}

/* ═══════════════════════════════════════════════════════════════
   UTILITAIRES — ajoutés par lot 2B
   ═══════════════════════════════════════════════════════════════ */
.text-xs { font-size: .75rem; }

/* ═══════════════════════════════════════════════════════════════
   CHÈQUES — tresorerie/cheques.php
   ═══════════════════════════════════════════════════════════════ */
/* Les cases de tête utilisent .treso-soldes, qui gère déjà l'auto-fit et
   les 2 colonnes sur téléphone. Une surcharge à 3 colonnes fixes existait
   ici : elle s'appliquait aussi en mobile, où elle écrasait la règle
   responsive et serrait les cases sur toute la largeur. */
.chq-val--success { color: var(--color-success); }
.chq-val--muted   { color: var(--color-muted); }

.chq-form-card     { max-width: 680px; margin-bottom: 1.5rem; }
.chq-reste-zone    { margin: .75rem 0; }
.chq-form-actions  { margin-top: 1rem; }

/* Filtres */
.chq-filtres {
    display: flex; align-items: center; justify-content: space-between;
    flex-wrap: wrap; gap: .5rem; margin-bottom: 1rem;
}
.chq-filtres-statuts { display: flex; gap: .5rem; flex-wrap: wrap; }

/* Desktop / Mobile switch */
.chq-cards-mobile  { display: none; }
.chq-table-desktop { display: block; }
@media (max-width: 768px) {
    .chq-table-desktop { display: none !important; }
    .chq-cards-mobile  { display: flex; flex-direction: column; gap: .75rem; }
    .chq-filtres       { flex-direction: column; align-items: flex-start; }
    .chq-btn-groupe    { width: 100%; justify-content: center; }
}

/* Tableau desktop */
.chq-table-body  { padding: 0; }
.chq-table       { min-width: 600px; }
.chq-th-date     { width: 90px; }
.chq-th-montant  { width: 100px; text-align: right; }
.chq-th-cat      { width: 110px; }
.chq-th-statut   { width: 100px; }
.chq-th-actions  { width: 120px; text-align: center; }
.chq-empty       { padding: 2rem; }

.chq-td-date    { white-space: nowrap; font-size: .82rem; }
.chq-emetteur   { font-weight: 500; font-size: .88rem; }
.chq-meta-line  { display: block; font-size: .72rem; }
.chq-notes-line { display: block; font-size: .7rem; }
.chq-td-montant { text-align: right; font-weight: 700; font-size: .9rem; }
.chq-badge-cat  { font-size: .72rem; }
.chq-td-actions { text-align: center; }
.chq-actions-btns { display: flex; gap: 3px; justify-content: center; flex-wrap: wrap; }

/* Cartes mobile */
.chq-card-item {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius-lg); box-shadow: var(--shadow); overflow: hidden;
}
.chq-card-head {
    display: flex; align-items: flex-start; justify-content: space-between;
    padding: .85rem 1rem; gap: .75rem; border-bottom: 1px solid var(--color-border);
}
.chq-card-head-left { flex: 1; min-width: 0; }
.chq-card-emetteur { font-size: .92rem; font-weight: 600; color: var(--color-text); }
.chq-card-meta     { font-size: .72rem; color: var(--color-muted); margin-top: 2px; }
.chq-card-right    { flex-shrink: 0; text-align: right; }
.chq-card-montant  { font-size: 1rem; font-weight: 800; color: var(--color-success); }
.chq-card-badge    { display: block; margin-top: 4px; font-size: .68rem; }

.chq-card-details { display: flex; flex-direction: column; }
.chq-card-detail-item {
    display: flex; justify-content: space-between; align-items: center;
    padding: .5rem 1rem; border-bottom: 1px solid var(--color-border);
    font-size: .82rem;
}
.chq-card-detail-item:last-child { border-bottom: none; }
.chq-card-detail-label { color: var(--color-muted); }
.chq-card-detail-val   { font-weight: 500; }

.chq-card-actions {
    display: flex; flex-wrap: wrap; gap: 6px; padding: .6rem 1rem;
    border-top: 1px solid var(--color-border); background: var(--color-surface-alt);
}
.chq-card-act-btn {
    display: inline-flex; align-items: center; gap: 4px;
    padding: .3rem .7rem; border-radius: 6px;
    font-size: .75rem; font-weight: 500; text-decoration: none;
    color: var(--color-text); background: var(--color-surface);
    border: 1px solid var(--color-border);
    transition: background .15s, border-color .15s;
    cursor: pointer; font-family: inherit;
    -webkit-tap-highlight-color: transparent;
}
.chq-card-act-btn:hover         { border-color: var(--color-primary); color: var(--color-primary); }
.chq-card-act-btn--success      { color: var(--color-success); border-color: #bbf7d0; }
.chq-card-act-btn--success:hover{ background: #f0fdf4; }
.chq-card-act-btn--warning      { color: #92400e; border-color: #fde68a; }
.chq-card-act-btn--warning:hover{ background: #fef3c7; }
.chq-card-act-btn--danger       { color: var(--color-danger); border-color: #fecaca; }
.chq-card-act-btn--danger:hover { background: #fef2f2; }
[data-theme="dark"] .chq-card-act-btn--success:hover { background: #1a2a1a; }
[data-theme="dark"] .chq-card-act-btn--warning:hover { background: #2a2515; }
[data-theme="dark"] .chq-card-act-btn--danger:hover  { background: #2a1515; }

.chq-pagination { margin-top: 1rem; }

/* Boutons action (utilisés dans cheques) */
.btn-warning { background: #fef3c7; color: #92400e; border-color: #fde68a; }
.btn-warning:hover { background: #fde68a; }
[data-theme="dark"] .btn-warning { background: #2a2515; color: #f0c040; border-color: #5a4a20; }
[data-theme="dark"] .btn-warning:hover { background: #3a3520; }

/* Suggestion split */
.chq-suggestion {
    border: 1.5px solid #67e8f9; border-radius: var(--radius);
    padding: 10px 12px; background: #ecfeff; font-size: .82rem;
}
.chq-suggestion__title { font-weight: 600; color: #0e7490; margin-bottom: 8px; }
.chq-suggestion__select {
    padding: 2px 6px; border: 1px solid var(--color-border);
    border-radius: 4px; font-size: .78rem;
    background: var(--color-surface); color: var(--color-text);
}
[data-theme="dark"] .chq-suggestion { background: #1a2a30; border-color: #2a4a50; }
[data-theme="dark"] .chq-suggestion__title { color: #7dd3fc; }

/* Modal chèques — variante 460 */
.modal-box--460 { max-width: 460px; }

/* Checkbox carrée primary-accent */
.chq-grp-check {
    width: 18px; height: 18px; flex-shrink: 0;
    accent-color: var(--color-primary);
}

/* Modals — compléments utilisés dans cheques */
.chq-modal-list { overflow-y: auto; flex: 1; }
.chq-modal-row {
    display: flex; align-items: center; gap: .75rem;
    padding: .65rem 1.25rem; cursor: pointer;
    border-bottom: 1px solid var(--color-border);
    transition: background .1s;
}
.chq-modal-row:hover { background: var(--color-surface-alt); }
.chq-modal-row-info { flex: 1; min-width: 0; }
.chq-modal-row-nom  { font-weight: 500; font-size: .88rem; }
.chq-modal-row-montant { font-weight: 700; color: var(--color-success); white-space: nowrap; }
.chq-modal-footer { padding: .75rem 1.25rem; border-top: 1px solid var(--color-border); background: var(--color-surface-alt); flex-shrink: 0; }
.chq-modal-total { font-size: .88rem; color: var(--color-muted); margin-bottom: .75rem; }

.chq-enc-info      { margin-bottom: 1rem; }
.chq-enc-emetteur  { font-weight: 600; font-size: .9rem; }
.chq-enc-montant   { font-size: 1.1rem; font-weight: 700; color: var(--color-success); margin-top: 4px; }
.chq-enc-cat-badge { font-size: .72rem; margin-top: 4px; display: inline-block; }
.chq-enc-decoupage { display: none; margin-bottom: 1rem; }
.chq-enc-radio     { display: flex; align-items: center; gap: 8px; cursor: pointer; margin-bottom: 6px; font-size: .85rem; }
.chq-enc-mois-config { display: none; margin-top: 8px; padding-top: 8px; border-top: 1px solid #a7f3d0; }
.chq-enc-mois-row  { display: flex; gap: 8px; align-items: center; font-size: .8rem; }

/* Récap dépôt groupé — span total */
.chq-grp-total-val { color: var(--color-success); font-weight: 700; }

@media (max-width: 600px) { .form-row { grid-template-columns: 1fr; } }

/* ═══════════════════════════════════════════════════════════════
   COLLECTES — tresorerie/collectes.php
   ═══════════════════════════════════════════════════════════════ */


/* ── Rapport imprimable (classes col-rpt-*) ── */
.col-rpt-doc { max-width: 680px; margin: 0 auto; }

.col-rpt-head {
    text-align: center; padding-bottom: 16px;
    border-bottom: 2px solid var(--color-border); margin-bottom: 16px;
}
.col-rpt-logo {
    width: 60px; height: 60px; object-fit: contain;
    border-radius: 10px; margin-bottom: 8px;
}

.col-rpt-asso-nom  { font-size: 1.25rem; font-weight: 800; color: var(--color-primary); }
.col-rpt-asso-ville{ font-size: .82rem; color: var(--color-muted); margin-top: 2px; }
.col-rpt-mentions  { font-size: .72rem; color: var(--color-muted); margin-top: 2px; }
.col-rpt-title-badge {
    margin-top: 12px; display: inline-block;
    background: var(--color-primary); color: #fff;
    padding: 6px 20px; border-radius: 8px;
    font-size: .85rem; font-weight: 700; letter-spacing: .5px;
}
.col-rpt-tiers-badge {
    font-size: .88rem; font-weight: 700; margin-top: 8px;
    color: #92400e; border: 2px solid #f59e0b;
    display: inline-block; padding: 4px 16px; border-radius: 8px;
}

.col-rpt-info-grid {
    display: grid; grid-template-columns: 1fr 1fr;
    gap: 12px; margin-bottom: 16px;
}
.col-rpt-info-box {
    background: var(--color-surface-alt);
    border-radius: 10px; padding: 12px 16px;
}
.col-rpt-info-label {
    font-size: .65rem; text-transform: uppercase; letter-spacing: 1px;
    color: var(--color-muted); margin-bottom: 4px;
}
.col-rpt-info-val { font-size: .9rem; font-weight: 600; }

.col-rpt-detail {
    border: 1.5px solid var(--color-border);
    border-radius: 12px; overflow: hidden; margin-bottom: 16px;
}
.col-rpt-row {
    display: flex; justify-content: space-between; align-items: center;
    padding: 12px 16px; border-bottom: 1px solid var(--color-border);
}
.col-rpt-row-label { font-size: .85rem; font-weight: 600; }
.col-rpt-row-val   { font-size: 1.1rem; font-weight: 700; }
.col-rpt-total {
    background: var(--color-primary); color: #fff;
    padding: 14px 16px;
    display: flex; justify-content: space-between; align-items: center;
}
.col-rpt-total-label {
    font-size: .9rem; font-weight: 800;
    text-transform: uppercase; letter-spacing: 1px;
}
.col-rpt-total-val { font-size: 1.6rem; font-weight: 800; }

.col-rpt-msg {
    padding: 10px 16px; border-radius: 8px;
    font-size: .78rem; margin-bottom: 10px;
}
.col-rpt-msg--success {
    background: rgba(22,163,74,.06);
    border: 1px solid rgba(22,163,74,.2);
    color: var(--color-success);
}
.col-rpt-msg--tiers {
    background: #fffbeb; border: 1px solid #fbbf24; color: #92400e;
}

.col-rpt-compteurs-box {
    border: 1.5px solid var(--color-border);
    border-radius: 10px; padding: 14px 16px; margin-bottom: 16px;
}
.col-rpt-compteurs-title {
    font-size: .72rem; text-transform: uppercase; letter-spacing: 1px;
    color: var(--color-muted); margin-bottom: 8px; font-weight: 700;
}
.col-rpt-compteurs-list { display: flex; flex-wrap: wrap; gap: 8px; }
.col-rpt-compteur {
    display: inline-flex; align-items: center; gap: 6px;
    padding: 6px 14px; background: var(--color-surface-alt);
    border: 1px solid var(--color-border); border-radius: 8px;
    font-size: .85rem; font-weight: 500;
}
.col-rpt-compteur-icon { opacity: .7; }

.col-rpt-footer {
    display: flex; justify-content: space-between; align-items: center;
    font-size: .72rem; color: var(--color-muted);
    border-top: 1.5px solid var(--color-border);
    padding-top: 12px; margin-top: 12px;
    flex-wrap: wrap; gap: .5rem;
}
.col-rpt-footer-sub    { margin-top: 2px; }
.col-rpt-footer-right  { text-align: right; }
.col-rpt-footer-asso   { font-weight: 600; }

/* ── Formulaire collecte ── */
.col-form-card { }
.col-input-nofix { min-width: 0; }

.form-row-collecte { grid-template-columns: 140px 1fr; }
@media (max-width: 600px) {
    .form-row-collecte { grid-template-columns: 1fr !important; }
}

.col-form-group-mb-sm { margin-bottom: .75rem; }
.col-form-group-mb-0  { margin-bottom: 0; }
.col-grid-coupures-wrap { display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1fr); gap: 12px; }
.col-section-title-lbl { font-size: .8rem; font-weight: 700; color: var(--color-text); }
.col-coupures-list { display: flex; flex-direction: column; gap: 5px; }

/* Zone compte / tiers (avec initial state PHP via d-none) */
.col-compte-dest-zone { margin-bottom: 1rem; }

.col-btn-add-compteur { padding: .2rem .6rem; font-size: .75rem; }
.col-compteurs-list   { display: flex; flex-direction: column; gap: .5rem; }
.col-form-hint        { display: block; margin-top: .5rem; font-size: .72rem; }
.col-btn-cancel       { text-align: center; }

/* ── Filtre année ── */
.col-filtre-annee-label { font-size: .82rem; color: var(--color-muted); font-weight: 500; }
.col-filtre-annee-btn   { padding: .3rem .75rem; font-size: .8rem; }

/* ── Toggle "Voir collectes tiers" ── */
.col-tiers-toggle {
    display: inline-flex; align-items: center; gap: 6px;
    padding: .3rem .65rem; border-radius: var(--radius);
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border);
    font-size: .8rem; cursor: pointer; user-select: none;
    margin-left: auto;
    -webkit-tap-highlight-color: transparent;
    transition: border-color .15s, background .15s;
}
.col-tiers-toggle:hover { border-color: var(--color-primary); }
.col-tiers-toggle input[type="checkbox"] {
    margin: 0; cursor: pointer; accent-color: var(--color-primary);
}
.col-tiers-badge {
    display: inline-flex; align-items: center; justify-content: center;
    min-width: 20px; height: 20px; padding: 0 6px;
    border-radius: 10px; background: #fef3c7; color: #92400e;
    font-size: .7rem; font-weight: 700; line-height: 1;
}
[data-theme="dark"] .col-tiers-badge { background: #3a3015; color: #fac775; }

@media (max-width: 700px) {
    .col-tiers-toggle { margin-left: 0; width: 100%; justify-content: center; }
}

/* ── Bandeau info mode tiers ── */
.col-tiers-banner {
    background: linear-gradient(135deg, #fef9ec, #fdf3d7);
    border: 1px solid #e5c94c;
    border-radius: var(--radius);
    padding: .75rem 1rem;
    font-size: .85rem;
    color: #7a5c00;
    margin-bottom: 1.25rem;
    line-height: 1.4;
}
[data-theme="dark"] .col-tiers-banner {
    background: linear-gradient(135deg, #2a2515, #1f1a0d);
    color: #dbb850;
    border-color: #8a7030;
}

/* ── État vide ── */
.col-empty-msg { padding: 1.5rem 0; }

/* ── Tableau desktop ── */
.col-table-body { padding: 0; }
.col-th-date    { width: 90px; }
.col-th-especes { width: 100px; text-align: right; }
.col-th-cb      { width: 100px; text-align: right; }
.col-th-total   { width: 110px; text-align: right; font-weight: 700; }
.col-th-compte  { width: 100px; text-align: center; }
.col-th-actions { width: 90px; text-align: center; }

.col-td-date      { white-space: nowrap; font-size: .82rem; }
.col-td-occasion  { font-weight: 500; font-size: .88rem; }
.col-td-operateur { font-size: .72rem; }
.col-td-amount    { text-align: right; font-size: .85rem; font-weight: 500; }
.col-td-compte    { text-align: center; font-size: .78rem; }
.col-td-actions   { text-align: center; }
.col-actions-btns { display: flex; gap: 4px; justify-content: center; }

.col-pagination { margin-top: 1rem; }

/* ── Rest of original style block ── */
.col-stats-grid {
    display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: .75rem; margin-bottom: 1.25rem;
}
.col-stat-card {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius); padding: 1rem .75rem; text-align: center;
    box-shadow: var(--shadow); transition: transform .15s, box-shadow .15s;
}
.col-stat-card:hover { transform: translateY(-2px); box-shadow: var(--shadow-md); }
.col-stat-card--total {
    border-color: #c9a84c; background: linear-gradient(135deg,#fffdf5,#fef9ec);
}
[data-theme="dark"] .col-stat-card--total { background: linear-gradient(135deg,#2a2515,#1f1a0d); border-color: #8a7030; }
.col-stat-icon { font-size: 1.3rem; margin-bottom: .3rem; }
.col-stat-value { font-size: 1.15rem; font-weight: 700; color: var(--color-primary); line-height: 1.2; overflow-wrap: anywhere; }
.col-stat-card--total .col-stat-value { color: #9a7000; }
[data-theme="dark"] .col-stat-card--total .col-stat-value { color: #dbb850; }
.col-stat-label { font-size: .7rem; color: var(--color-muted); margin-top: .25rem; }

@media (max-width: 700px) {
    .col-stats-grid { grid-template-columns: 1fr; gap: .5rem; min-width: 0; }
    .col-stat-card  { padding: .75rem .5rem; min-width: 0; overflow: hidden; }
    .col-stat-icon  { font-size: 1.1rem; margin-bottom: .2rem; }
    .col-stat-value { font-size: 1rem; overflow-wrap: anywhere; word-break: break-word; }
}

.col-badge-tiers {
    font-size: .62rem; background: #fef3c7; color: #92400e;
    border-radius: 3px; padding: 1px 6px; margin-left: 4px;
    font-weight: 700; letter-spacing: .3px; vertical-align: middle;
}
[data-theme="dark"] .col-badge-tiers { background: #3a3015; color: #fac775; }

.col-td-total {
    text-align: right; font-weight: 700; font-size: .92rem;
    color: #9a7000;
}
[data-theme="dark"] .col-td-total { color: #dbb850; }

.col-compte-badge {
    display: inline-flex; align-items: center; gap: 3px;
    padding: 2px 8px; border-radius: 6px; font-weight: 500;
    background: var(--color-surface-alt); border: 1px solid var(--color-border);
    white-space: nowrap;
}

.col-cards-mobile { display: none; }
.col-table-desktop { display: block; }

@media (max-width: 768px) {
    .col-table-desktop { display: none !important; }
    .col-cards-mobile  { display: flex; flex-direction: column; gap: .75rem; min-width: 0; }
}

.col-card-item {
    background: var(--color-surface); border: 1px solid var(--color-border);
    border-radius: var(--radius-lg); box-shadow: var(--shadow);
    overflow: hidden; transition: box-shadow .15s;
    max-width: 100%; min-width: 0;
}
.col-card-item:active { box-shadow: var(--shadow-md); }

.col-card-head {
    display: flex; align-items: center; justify-content: space-between;
    padding: .85rem 1rem; gap: .75rem;
    border-bottom: 1px solid var(--color-border);
    min-width: 0; max-width: 100%;
}
.col-card-head-left { flex: 1; min-width: 0; }
.col-card-occasion {
    font-size: .92rem; font-weight: 600; color: var(--color-text);
    white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.col-card-date {
    font-size: .75rem; color: var(--color-muted); margin-top: 3px;
    overflow-wrap: anywhere; word-break: break-word;
    line-height: 1.4;
}
.col-card-date-strong {
    font-weight: 700; color: var(--color-text); font-size: .8rem;
}
.col-card-date-meta {
    color: var(--color-muted); font-weight: 400;
}

/* Zone cliquable : ouvre le rapport au tap (head + amounts) */
.col-card-clickable {
    display: block; color: inherit; text-decoration: none;
    -webkit-tap-highlight-color: transparent;
    transition: background .12s;
}
.col-card-clickable:hover { text-decoration: none; color: inherit; }
.col-card-clickable:active { background: var(--color-surface-alt); }
.col-card-item:hover .col-card-occasion { color: var(--color-primary); }

.col-card-total-badge {
    flex-shrink: 0;
    background: linear-gradient(135deg,#fef9ec,#fdf3d7);
    color: #7a5c00; font-weight: 800; font-size: 1rem;
    padding: .4rem .85rem; border-radius: 8px;
    border: 1.5px solid #e5c94c; white-space: nowrap;
}
[data-theme="dark"] .col-card-total-badge {
    background: linear-gradient(135deg,#2a2515,#1f1a0d);
    color: #dbb850; border-color: #8a7030;
}

.col-card-amounts { display: flex; gap: 0; padding: 0; min-width: 0; }
.col-card-amount {
    flex: 1; display: flex; flex-direction: column; align-items: center;
    padding: .65rem .5rem;
    border-right: 1px solid var(--color-border);
}
.col-card-amount:last-child { border-right: none; }
.col-card-amount-label { font-size: .68rem; color: var(--color-muted); margin-bottom: .15rem; }
.col-card-amount-val   { font-size: .88rem; font-weight: 600; color: var(--color-text); }

.col-card-actions {
    display: flex; gap: 6px; padding: .6rem 1rem;
    border-top: 1px solid var(--color-border);
    background: var(--color-surface-alt);
    flex-wrap: wrap;
}
.col-card-act-btn {
    display: inline-flex; align-items: center; gap: 4px;
    padding: .3rem .7rem; border-radius: 6px;
    font-size: .75rem; font-weight: 500; text-decoration: none;
    color: var(--color-text); background: var(--color-surface);
    border: 1px solid var(--color-border);
    transition: background .15s, border-color .15s;
    cursor: pointer; font-family: inherit;
    -webkit-tap-highlight-color: transparent;
}
.col-card-act-btn:hover { border-color: var(--color-primary); color: var(--color-primary); }
.col-card-act-btn--danger { color: var(--color-danger); }
.col-card-act-btn--danger:hover { border-color: var(--color-danger); background: #fef2f2; }
[data-theme="dark"] .col-card-act-btn--danger:hover { background: #2a1515; }

@media (max-width: 600px) {
    .col-btn-text { display: none; }
    .col-btn-icon { font-size: 1.1rem; }
    .col-btn-add, .col-btn-export { padding: .35rem .6rem !important; min-width: 38px; }
}
@media (min-width: 601px) {
    .col-btn-icon { margin-right: 2px; }
}

/* ── Checkbox tiers ── */
.col-tiers-check { margin-bottom: 1.25rem; }
.col-tiers-label {
    display: flex; align-items: flex-start; gap: 10px; cursor: pointer;
    -webkit-tap-highlight-color: transparent;
}
.col-tiers-label input[type="checkbox"] {
    margin-top: 12px; width: 18px; height: 18px; flex-shrink: 0;
    accent-color: var(--color-primary);
}
.col-tiers-box {
    display: flex; align-items: center; gap: 10px;
    padding: 10px 14px; border-radius: var(--radius);
    border: 1.5px solid var(--color-border); background: var(--color-surface-alt);
    transition: border-color .15s, background .15s; flex: 1;
}
.col-tiers-label input:checked ~ .col-tiers-box {
    border-color: #f59e0b; background: #fffbeb;
}
[data-theme="dark"] .col-tiers-label input:checked ~ .col-tiers-box {
    border-color: #8a7030; background: #2a2515;
}
.col-tiers-icon { font-size: 1.3rem; flex-shrink: 0; }
.col-tiers-box strong { display: block; font-size: .85rem; color: var(--color-text); }
.col-tiers-box small  { display: block; font-size: .72rem; color: var(--color-muted); margin-top: 1px; }

/* ── Fix date input mobile ── */
input[type="date"] {
    width: 100%; max-width: 100%; box-sizing: border-box;
    -webkit-appearance: none; appearance: none;
}

/* ── Compteurs ── */
.compteur-row { display: flex; align-items: center; gap: 8px; }
.compteur-num {
    width: 24px; height: 24px; border-radius: 50%;
    background: var(--color-primary); color: #fff;
    font-size: .7rem; font-weight: 700;
    display: flex; align-items: center; justify-content: center;
    flex-shrink: 0;
}
.compteur-row input[type="text"] {
    flex: 1; padding: .45rem .7rem; border: 1px solid var(--color-border);
    border-radius: var(--radius); font-size: .88rem;
    background: var(--color-surface); color: var(--color-text);
    min-width: 0;
}
.compteur-row input:focus { outline: none; border-color: var(--color-primary); box-shadow: 0 0 0 3px rgba(26,82,118,.12); }
.compteur-remove {
    width: 28px; height: 28px; border-radius: 6px; border: 1px solid var(--color-border);
    background: var(--color-surface); color: var(--color-danger);
    font-size: .85rem; cursor: pointer;
    display: flex; align-items: center; justify-content: center;
    flex-shrink: 0; transition: background .15s, border-color .15s;
    font-family: inherit; -webkit-tap-highlight-color: transparent;
}
.compteur-remove:hover { background: #fef2f2; border-color: var(--color-danger); }
[data-theme="dark"] .compteur-remove:hover { background: #2a1515; }

/* ── Coupures collecte ── */
.col-section-toggle {
    display: flex; align-items: center; gap: 8px; cursor: pointer;
    padding: 8px 10px; border-radius: var(--radius); user-select: none;
    transition: background .15s;
}
.col-section-toggle:hover { background: rgba(0,0,0,.03); }
.col-chevron {
    font-size: .65rem; transition: transform .2s; color: var(--color-muted);
}
.col-section-toggle.open .col-chevron { transform: rotate(90deg); }
.col-section-badge {
    margin-left: auto; font-size: .72rem; font-weight: 700;
    color: var(--color-muted); background: var(--color-surface);
    padding: 2px 8px; border-radius: 10px; border: 1px solid var(--color-border);
    min-width: 55px; text-align: center;
}
.col-section-badge.has-value {
    color: var(--color-success); border-color: var(--color-success);
    background: rgba(22,163,74,.06);
}
.col-section-body { padding: 8px 0 4px 0; display: none; }
.col-section-body.is-open { display: block; }

.col-coupure {
    display: flex; align-items: center; gap: 4px; padding: 5px 8px;
    background: var(--color-surface); border: 1.5px solid var(--color-border);
    border-radius: 8px; transition: border-color .2s, box-shadow .2s;
}
.col-coupure:hover { border-color: var(--color-primary); }
.col-coupure.has-value {
    border-color: var(--color-primary);
    background: rgba(29,78,216,.03);
    box-shadow: 0 0 0 2px rgba(29,78,216,.06);
}
.col-coupure .col-val {
    font-size: .75rem; font-weight: 700; color: var(--color-text); min-width: 36px;
}
.col-coupure .col-btn {
    width: 28px; height: 28px; border: 1.5px solid var(--color-border);
    border-radius: 6px; background: var(--color-surface); cursor: pointer;
    font-size: 16px; display: flex; align-items: center; justify-content: center;
    color: var(--color-text); transition: background .15s, border-color .15s;
    user-select: none; -webkit-tap-highlight-color: transparent; flex-shrink: 0;
}
.col-coupure .col-btn:active {
    background: rgba(29,78,216,.08); border-color: var(--color-primary);
}
.col-coupure input[type="number"] {
    width: 40px; padding: 3px 2px; border: 1.5px solid var(--color-border);
    border-radius: 6px; font-size: .85rem; font-weight: 600; text-align: center;
    outline: none; background: var(--color-surface); color: var(--color-text);
    transition: border-color .2s; -moz-appearance: textfield;
}
.col-coupure input[type="number"]::-webkit-inner-spin-button,
.col-coupure input[type="number"]::-webkit-outer-spin-button { -webkit-appearance: none; margin: 0; }
.col-coupure input:focus { border-color: var(--color-primary); }
.col-coupure .col-sous {
    font-size: .68rem; color: var(--color-muted); margin-left: auto;
    min-width: 44px; text-align: right;
}
.col-coupure .col-sous b { transition: color .2s; }
.col-coupure.has-value .col-sous b { color: var(--color-success); font-size: .72rem; }

@media (max-width: 600px) {
    .col-grid-coupures { grid-template-columns: 1fr !important; gap: 8px !important; }
}

/* ═══════════════════════════════════════════════════════════════
   PARAMÈTRES — tresorerie/parametres.php
   ═══════════════════════════════════════════════════════════════ */

/* Groupes de sections */
.tps-group-label {
    font-size: .7rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 2px;
    color: var(--color-muted);
    padding: .75rem 0 .5rem;
    margin-top: .5rem;
}
.tps-group-label:first-of-type { margin-top: 0; }

/* Card info (identité légale — redirige vers admin) */
.tps-info-card {
    display: flex;
    align-items: center;
    gap: 1rem;
    flex-wrap: wrap;
    padding: 1rem 1.25rem;
}
.tps-info-card .tps-info-icon { font-size: 1.5rem; }
.tps-info-card .tps-info-content { flex: 1; min-width: 200px; }
.tps-info-card .tps-info-title { font-weight: 600; margin-bottom: .2rem; }
.tps-info-card .tps-info-desc  { font-size: .82rem; color: var(--color-muted); line-height: 1.45; }

/* Logo */
.tps-logo-row {
    display: flex;
    align-items: center;
    gap: 1.25rem;
    flex-wrap: wrap;
    margin-bottom: 1rem;
}
.tps-logo-preview,
.tps-logo-placeholder {
    width: 80px; height: 80px;
    border-radius: var(--radius-lg);
    flex-shrink: 0;
}
.tps-logo-preview {
    border: 2px solid var(--color-border);
    object-fit: cover;
}
.tps-logo-placeholder {
    border: 2px dashed var(--color-border);
    display: flex;
    align-items: center;
    justify-content: center;
    color: var(--color-muted);
    font-size: 1.5rem;
}
.tps-logo-form {
    flex: 1;
    min-width: 200px;
    max-width: 100%;
    display: flex;
    flex-direction: column;
    gap: .5rem;
    overflow: hidden;
}
.tps-logo-form input[type="file"] { font-size: .82rem; width: 100%; max-width: 100%; }
.tps-logo-hint {
    font-size: .75rem;
    color: var(--color-muted);
    margin: 0;
    line-height: 1.45;
}
.tps-logo-actions { display: flex; gap: .5rem; margin-top: .25rem; flex-wrap: wrap; }
.tps-logo-new-preview {
    display: none;
    width: 80px; height: 80px;
    border-radius: var(--radius-lg);
    border: 2px solid var(--color-success);
    object-fit: cover;
    margin-top: .5rem;
}

/* --- Paramètres trésorerie : bloc double logo --- */
.tps-logo-grid {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 1.5rem;
}

@media (max-width: 768px) {
    .tps-logo-grid { grid-template-columns: 1fr; }
}

@media (max-width: 480px) {
    /* Côte à côte, l'image et le formulaire se serrent trop pour laisser
       de la place au champ fichier natif (texte tronqué) : on les empile. */
    .tps-logo-row { flex-direction: column; align-items: stretch; }
    .tps-logo-form { min-width: 0; }
}

.tps-logo-block {
    padding: 1rem;
    background: var(--color-bg-subtle, #f8f9fa);
    border-radius: 8px;
    border: 1px solid var(--color-border, #e5e7eb);
}

.tps-logo-title {
    margin: 0 0 .75rem;
    font-size: 1rem;
    font-weight: 600;
    display: flex;
    align-items: center;
    gap: .5rem;
}

.tps-logo-badge {
    font-size: .7rem;
    padding: .15rem .5rem;
    border-radius: 10px;
    background: var(--color-accent-soft, #fef3c7);
    color: var(--color-accent-dark, #92400e);
    font-weight: 500;
}

/* Descriptions génériques */
.tps-desc {
    font-size: .82rem;
    color: var(--color-muted);
    margin-bottom: 1rem;
    line-height: 1.5;
}
.tps-hint {
    font-size: .78rem;
    color: var(--color-muted);
    margin-bottom: .75rem;
    line-height: 1.5;
}

/* Assistant de calcul (encadré bleu info) */
.tps-assist {
    background: var(--color-info-lt);
    border: 1.5px solid rgba(37, 99, 235, .25);
    border-radius: var(--radius);
    padding: 1rem;
    margin-bottom: 1.25rem;
}
[data-theme="dark"] .tps-assist {
    background: rgba(37, 99, 235, .08);
    border-color: rgba(37, 99, 235, .35);
}
.tps-assist-title {
    font-weight: 600;
    color: var(--color-info);
    margin-bottom: .5rem;
    font-size: .88rem;
}
[data-theme="dark"] .tps-assist-title { color: #60a5fa; }
.tps-assist-desc {
    font-size: .8rem;
    color: var(--color-muted);
    margin-bottom: .75rem;
    line-height: 1.5;
}
.tps-assist-row {
    display: flex;
    gap: .75rem;
    align-items: flex-end;
    flex-wrap: wrap;
}
.tps-assist-field label {
    font-size: .78rem;
    font-weight: 600;
    display: block;
    margin-bottom: .3rem;
}
.tps-assist-field input {
    padding: .5rem .75rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    font-size: .88rem;
    width: 180px;
    background: var(--color-surface);
    color: var(--color-text);
}
.tps-assist-field input:focus {
    outline: none;
    border-color: var(--color-info);
    box-shadow: 0 0 0 3px rgba(37, 99, 235, .1);
}
.tps-assist-result {
    font-size: .85rem;
    color: var(--color-muted);
    line-height: 1.5;
}
.tps-assist-result strong { color: var(--color-text); }

/* Grilles formulaires */
.tps-form-grid-2 {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 1rem;
}
.tps-form-actions { margin-top: .75rem; display: flex; gap: .5rem; flex-wrap: wrap; }

/* Commission TPE */
.tps-tpe-row {
    display: flex;
    gap: .75rem;
    align-items: center;
    flex-wrap: wrap;
}
.tps-tpe-input {
    width: 90px;
    padding: .5rem .75rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    font-size: 1rem;
    font-weight: 700;
    text-align: center;
    background: var(--color-surface);
    color: var(--color-text);
}
.tps-tpe-input:focus {
    outline: none;
    border-color: var(--color-primary);
    box-shadow: 0 0 0 3px rgba(217, 119, 6, .1);
}
.tps-tpe-unit { font-size: 1rem; font-weight: 600; }
.tps-tpe-example { font-size: .82rem; color: var(--color-muted); }

/* Transitoires code */
.tps-code {
    font-family: ui-monospace, "SF Mono", Menlo, Consolas, monospace;
    font-size: .78rem;
    padding: .1rem .4rem;
    background: var(--color-surface-alt);
    border-radius: 4px;
    color: var(--color-text);
}

/* Export / Import */
.tps-export-row { display: flex; gap: 1rem; flex-wrap: wrap; margin-bottom: 1.25rem; }
.tps-import-block {
    border-top: 1px solid var(--color-border);
    padding-top: 1rem;
}
.tps-import-title {
    font-weight: 600;
    margin-bottom: .5rem;
    font-size: .88rem;
}
.tps-import-row {
    display: flex;
    gap: .75rem;
    align-items: center;
    flex-wrap: wrap;
}
.tps-import-row input[type="file"] { font-size: .82rem; }

/* Immobilisations */
.tps-immo-form {
    display: none;
    background: var(--color-surface-alt);
    border-radius: var(--radius);
    padding: 1rem;
    margin-bottom: 1rem;
}
.tps-immo-form.is-open { display: block; }
.tps-immo-form-grid {
    display: grid;
    grid-template-columns: 2fr 1fr 1fr 1fr;
    gap: .75rem;
    align-items: end;
}
.tps-immo-form .form-group { margin: 0; }

/* Tableau immobilisations desktop */
.tps-immo-table-wrap { overflow-x: auto; }
.tps-immo-table {
    width: 100%;
    border-collapse: collapse;
    font-size: .85rem;
}
.tps-immo-table thead th {
    text-align: left;
    padding: .6rem .75rem;
    font-size: .72rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: .04em;
    color: var(--color-muted);
    border-bottom: 2px solid var(--color-border);
}
.tps-immo-table th.tps-align-right  { text-align: right; }
.tps-immo-table th.tps-align-center { text-align: center; }
.tps-immo-table th.tps-col-actions  { width: 50px; text-align: center; }
.tps-immo-table tbody td {
    padding: .7rem .75rem;
    border-bottom: 1px solid var(--color-border);
    vertical-align: middle;
}
.tps-immo-table tbody tr:last-child td { border-bottom: none; }
.tps-immo-name { font-weight: 500; }
.tps-align-right  { text-align: right; }
.tps-align-center { text-align: center; }
.tps-amort-yearly { color: var(--color-muted); }
.tps-empty {
    text-align: center;
    color: var(--color-muted);
    padding: 2rem 1rem;
}

/* Bouton icône (corbeille) */
.tps-btn-icon {
    background: none;
    border: none;
    cursor: pointer;
    opacity: .6;
    font-size: 1rem;
    padding: .25rem;
    transition: opacity .15s;
    color: var(--color-text);
}
.tps-btn-icon:hover { opacity: 1; }

/* Cartes mobile immobilisations */
.tps-immo-cards { display: none; }
.tps-immo-card {
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    padding: .85rem 1rem;
    margin-bottom: .6rem;
    background: var(--color-surface);
}
.tps-immo-card-head {
    display: flex;
    align-items: flex-start;
    gap: .5rem;
    margin-bottom: .5rem;
}
.tps-immo-card-head .tps-immo-card-name {
    flex: 1;
    font-weight: 600;
    font-size: .92rem;
}
.tps-immo-card-grid {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: .5rem .75rem;
    font-size: .82rem;
}
.tps-immo-card-grid .tps-immo-kv {
    display: flex;
    flex-direction: column;
    gap: .1rem;
}
.tps-immo-kv-label {
    font-size: .68rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: .04em;
    color: var(--color-muted);
}
.tps-immo-kv-value { font-weight: 500; }

@media (max-width: 768px) {
    .tps-form-grid-2       { grid-template-columns: 1fr; }
    .tps-immo-form-grid    { grid-template-columns: 1fr; }
    .tps-assist-field input { width: 100%; }
    .tps-assist-field       { flex: 1; min-width: 180px; }

    .tps-immo-table-wrap { display: none; }
    .tps-immo-cards      { display: block; }

    .tps-info-card { padding: .85rem 1rem; }
    .tps-info-card .tps-info-content { flex-basis: 100%; }
}

/* Utilitaires locaux */
.tps-mb { margin-bottom: 1.5rem; }
.tps-inline-form { display: inline; }

/* ═══════════════════════════════════════════════════════════════
   PROJETS — tresorerie/projets.php
   ═══════════════════════════════════════════════════════════════ */

/* Grille des cartes projets */
.proj-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(240px, 1fr));
    gap: 1rem;
    margin-bottom: 1.5rem;
}

/* Carte projet */
.proj-card {
    display: block;
    background: var(--color-surface);
    border: 1.5px solid var(--color-border);
    border-left-width: 4px;
    border-radius: var(--radius);
    padding: 1rem 1rem .75rem;
    text-decoration: none;
    color: var(--color-text);
    transition: box-shadow .15s, transform .15s;
    cursor: pointer;
}
.proj-card:hover {
    box-shadow: var(--shadow-md);
    transform: translateY(-2px);
}
.proj-card.is-active { box-shadow: var(--shadow-md); }
.proj-card__head {
    display: flex;
    align-items: center;
    gap: .5rem;
    margin-bottom: .6rem;
    font-size: .88rem;
}
.proj-card__title { flex: 1; min-width: 0; }
.proj-card__actions {
    margin-left: auto;
    display: flex;
    gap: .2rem;
}
.proj-card__stats {
    display: flex;
    gap: .75rem;
    font-size: .82rem;
    margin-bottom: .5rem;
    flex-wrap: wrap;
}
.proj-stat-entree { color: var(--color-success); }
.proj-stat-sortie { color: var(--color-danger); }
.proj-stat-solde  { font-weight: 700; }
.proj-stat-solde.is-positive { color: var(--color-success); }
.proj-stat-solde.is-negative { color: var(--color-danger); }

.proj-dot {
    display: inline-block;
    width: 10px;
    height: 10px;
    border-radius: 50%;
    flex-shrink: 0;
}

/* Badge clôturé */
.proj-badge-cloture {
    font-size: .7rem;
    background: var(--color-surface-alt);
    color: var(--color-muted);
    padding: 1px 6px;
    border-radius: 4px;
    font-weight: 500;
    margin-left: 4px;
}

/* Barre de budget */
.proj-budget-info {
    font-size: .75rem;
    color: var(--color-muted);
    margin-bottom: .3rem;
}
.proj-bar {
    height: 6px;
    background: var(--color-border);
    border-radius: 3px;
    overflow: hidden;
    margin-bottom: .3rem;
}
.proj-bar__fill {
    height: 100%;
    border-radius: 3px;
    transition: width .3s;
}
.proj-bar__fill.is-ok     { background: var(--color-success); }
.proj-bar__fill.is-warn   { background: #f59e0b; }
.proj-bar__fill.is-danger { background: var(--color-danger); }

.proj-ops-count {
    font-size: .75rem;
    color: var(--color-muted);
    margin-top: .4rem;
}

/* Filtre années */
.proj-filter-year {
    margin-bottom: 1rem;
    display: flex;
    align-items: center;
    gap: .75rem;
    flex-wrap: wrap;
}
.proj-filter-year__label {
    font-size: .85rem;
    color: var(--color-muted);
}

/* Empty state */
.proj-empty {
    text-align: center;
    padding: 2rem;
    color: var(--color-muted);
}

/* Détail projet — card wrapper */
.proj-detail-card { margin-top: 1.5rem; }
.proj-detail-head { border-left: 4px solid var(--color-primary); }
.proj-detail-head h2 {
    display: flex;
    align-items: center;
    gap: .5rem;
    flex-wrap: wrap;
}
.proj-detail-head small {
    font-weight: 400;
    font-size: .8rem;
    color: var(--color-muted);
}

/* Tableau opérations */
.proj-ops-wrap {
    padding: 0 !important;
    overflow-x: auto;
}
.proj-ops-table {
    width: 100%;
    border-collapse: collapse;
    font-size: .85rem;
}
.proj-ops-table thead th {
    text-align: left;
    padding: .6rem .75rem;
    font-size: .72rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: .04em;
    color: var(--color-muted);
    border-bottom: 2px solid var(--color-border);
}
.proj-ops-table th.proj-align-right { text-align: right; }
.proj-ops-table tbody td {
    padding: .65rem .75rem;
    border-bottom: 1px solid var(--color-border);
    vertical-align: middle;
}
.proj-ops-table tbody tr:last-child td { border-bottom: none; }
.proj-nowrap { white-space: nowrap; }
.proj-align-right { text-align: right; }
.proj-cell-compte {
    font-size: .78rem;
    color: var(--color-muted);
}
.proj-cell-montant {
    text-align: right;
    font-weight: 600;
    white-space: nowrap;
}
.proj-cell-montant.is-entree { color: var(--color-success); }
.proj-cell-montant.is-sortie { color: var(--color-danger); }

/* Bouton icône */
.proj-btn-icon {
    background: none;
    border: none;
    cursor: pointer;
    padding: 2px 4px;
    font-size: .85rem;
    opacity: .6;
    transition: opacity .15s;
    color: var(--color-text);
}
.proj-btn-icon:hover { opacity: 1; }

.proj-empty-ops {
    text-align: center;
    color: var(--color-muted);
    padding: 2rem;
}

/* Modals */
.proj-modal {
    display: none;
    position: fixed;
    inset: 0;
    background: rgba(0, 0, 0, .5);
    z-index: 1000;
    overflow-y: auto;
}
.proj-modal.is-open { display: block; }

.proj-modal__box {
    background: var(--color-surface);
    border-radius: var(--radius-lg);
    margin: 2rem auto;
    padding: 1.5rem;
    color: var(--color-text);
}
.proj-modal__box--sm { max-width: 480px; }
.proj-modal__box--lg { max-width: 700px; }

.proj-modal__header {
    display: flex;
    justify-content: space-between;
    align-items: center;
    gap: .75rem;
    margin-bottom: 1.25rem;
}
.proj-modal__footer {
    display: flex;
    gap: .5rem;
    justify-content: flex-end;
    margin-top: 1rem;
}

/* Modal rattacher — champ de recherche + liste scrollable */
.proj-search-input {
    width: 100%;
    padding: .5rem .75rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    margin-bottom: .75rem;
    font-size: .85rem;
    background: var(--color-surface);
    color: var(--color-text);
}
.proj-search-input:focus {
    outline: none;
    border-color: var(--color-primary);
    box-shadow: 0 0 0 3px rgba(217, 119, 6, .1);
}
.proj-rattacher-list {
    max-height: 350px;
    overflow-y: auto;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
}
.proj-rattacher-table {
    width: 100%;
    border-collapse: collapse;
    font-size: .82rem;
    margin: 0;
}
.proj-rattacher-table thead th {
    position: sticky;
    top: 0;
    background: var(--color-surface);
    text-align: left;
    padding: .55rem .6rem;
    font-size: .7rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: .04em;
    color: var(--color-muted);
    border-bottom: 1px solid var(--color-border);
}
.proj-rattacher-table thead th.proj-align-right { text-align: right; }
.proj-rattacher-table thead th.proj-col-check { width: 32px; }
.proj-rattacher-table tbody td {
    padding: .5rem .6rem;
    border-bottom: 1px solid var(--color-border);
}
.proj-rattacher-table tbody tr:last-child td { border-bottom: none; }

/* Modal projet — champ couleur */
.proj-color-input {
    width: 100%;
    height: 38px;
    padding: 2px;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    cursor: pointer;
    background: var(--color-surface);
}
.proj-form-grid-2 {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 1rem;
}

/* Divers */
.proj-form-hidden { display: none; }
.proj-inline-form { display: inline; }
.proj-hidden-row  { display: none; }

@media (max-width: 768px) {
    .proj-modal__box {
        max-width: 95vw !important;
        margin: 1rem auto;
        padding: 1rem;
    }
    .proj-rattacher-list { max-height: 250px; }
    .proj-form-grid-2    { grid-template-columns: 1fr; }
}

/* Complément chèques — labels split suggestion */
.chq-suggestion__label {
    display: flex; align-items: center; gap: 8px; cursor: pointer;
}
.chq-suggestion__label--mb { margin-bottom: 6px; }

/* ═══════════════════════════════════════════════════════════════
   OPÉRATIONS — tresorerie/operations/*.php
   ═══════════════════════════════════════════════════════════════ */

/* Form-row & utilitaires de base */
.btn-xs { padding: .2rem .5rem; font-size: .72rem; border-radius: 4px; }
.badge-transfert {
    background: #dbeafe; color: #1d4ed8;
    padding: 2px 8px; border-radius: 6px;
    font-size: .72rem; font-weight: 600;
}
[data-theme="dark"] .badge-transfert { background: #1a2a40; color: #6ec0e8; }
.btn-danger { background: #fef2f2; color: var(--color-danger); border-color: #fecaca; }
.btn-danger:hover { background: #fecaca; }
[data-theme="dark"] .btn-danger { background: #2a1515; color: #f87171; border-color: #5a2020; }
[data-theme="dark"] .btn-danger:hover { background: #3a2020; }

/* ── Filtres opérations ── */
.ops-filtres {
    display: flex;
    flex-wrap: wrap;
    gap: .5rem;
    align-items: center;
}
.ops-filtres select,
.ops-filtres input {
    font-size: .82rem;
    padding: .4rem .6rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    background: var(--color-surface);
    color: var(--color-text);
}
.ops-filtre-search { min-width: 140px; }
.ops-filtre-btns { display: flex; gap: .5rem; }

/* ── Tableau opérations ── */
.ops-table-wrap { overflow-x: auto; }
.ops-desc { font-size: .85rem; font-weight: 500; }
.ops-actions { display: flex; gap: 4px; justify-content: center; flex-wrap: wrap; }

/* En-têtes tableau */
.ops-th-montant  { width: 100px; text-align: right; }
.ops-th-justif   { width: 40px; text-align: center; }
.ops-th-actions  { width: 80px; text-align: center; }

/* Cellules */
.ops-td-montant {
    text-align: right; font-weight: 700; white-space: nowrap;
}
.ops-td-justif    { text-align: center; }
.ops-td-actions   { text-align: center; }

/* Couleurs sens entrée/sortie/transfert */
td.ops-amount--entree,
span.ops-amount--entree    { color: var(--color-success) !important; }
td.ops-amount--sortie,
span.ops-amount--sortie    { color: var(--color-danger) !important; }
td.ops-amount--transfert,
span.ops-amount--transfert { color: var(--color-muted) !important; }

/* Bouton icône plain (background:none, border:none) */
.btn-icon-plain {
    background: none; border: none; cursor: pointer;
    padding: 0; color: inherit; font-family: inherit;
}
.btn-icon-plain--md  { font-size: .9rem; }
.btn-icon-plain--lg  { font-size: 1.1rem; }
.btn-icon-plain--xs  { font-size: .7rem; opacity: .4; }
.btn-icon-plain--xxs { font-size: .6rem; opacity: .4; margin-left: 2px; }
.btn-icon-plain--faded { font-size: 1rem; opacity: .35; }

.ops-justif-btns {
    display: flex; gap: 2px;
    justify-content: center; align-items: center;
}
.ops-justif-ignored {
    font-size: .7rem; color: var(--color-muted); cursor: help;
}

/* Bouton notes — variantes selon contenu */
.ops-btn-note--has  { color: var(--color-primary); }

/* Éléments visibles uniquement sur mobile.
   .ops-mobile-meta sert encore aux courriers (secretariat/courriers.php,
   courrier_destinataires.php) : les listes d'opérations, elles, ont leur
   propre ligne .ops-ligne-meta, visible aux deux largeurs. */
.ops-mobile-montant { display: none; }
.ops-mobile-meta    { display: none; }

/* ── Page header opérations ── */
.ops-header-btns {
    display: flex;
    gap: .5rem;
    align-items: center;
    flex-wrap: wrap;
}

/* Inputs readonly (banque importée) */
.ops-input-readonly {
    opacity: .6;
    pointer-events: none;
}
.ops-input-readonly--alt {
    opacity: .6;
    background: var(--color-surface-alt);
}
.ops-input-disabled-soft { opacity: .6; }

/* Zones suggestion / cotisation */
.ops-form-mb-sm { margin-bottom: .75rem; }

/* Justificatif zone */
.ops-justif-existing {
    display: flex; align-items: center; gap: .75rem; flex-wrap: wrap;
    padding: .6rem .9rem;
    background: var(--color-surface-alt);
    border-radius: var(--radius);
    border: 1px solid var(--color-border);
}
.ops-justif-link {
    font-size: .85rem; color: var(--color-primary); font-weight: 500;
    background: none; border: none; cursor: pointer;
    text-decoration: underline; font-family: inherit;
}
.ops-justif-icon-lg { font-size: 1.5rem; }
.ops-justif-browse {
    color: var(--color-primary); cursor: pointer;
    font-weight: 600; text-decoration: underline;
}
.ops-justif-progress { font-size: .8rem; margin-top: 6px; }
.ops-justif-progress-row {
    display: flex; align-items: center; gap: 8px;
}
.ops-justif-progress-text { color: var(--color-muted); }
.ops-justif-progress-info {
    font-size: .75rem; color: var(--color-muted); margin-top: 4px;
}

/* Cards filtres / tableau */
.ops-filtres-card  { margin-bottom: 1rem; }
.ops-table-body    { padding: 0; }
.ops-empty-msg     { padding: 2rem; }

/* Pagination opérations */
.ops-pag-wrap {
    display: flex; align-items: center; justify-content: space-between;
    flex-wrap: wrap; gap: .5rem;
}
.ops-pag-info { margin: 0; font-size: .75rem; }
.ops-pag-mb   { margin-bottom: .75rem; }
.pagination-noflow { margin: 0; }

/* Bouton retour en haut */
.btn-top {
    display: none; position: fixed;
    bottom: 1.5rem; right: 1.5rem; z-index: 999;
    width: 42px; height: 42px; border-radius: 50%;
    border: none; cursor: pointer;
    background: var(--color-primary); color: #fff;
    font-size: 1.2rem;
    box-shadow: 0 2px 8px rgba(0,0,0,.2);
    transition: opacity .2s;
}

/* ══════════════════════════════════════════
   MOBILE — Opérations
   ══════════════════════════════════════════ */
@media (max-width: 768px) {
    .ops-filtres {
        display: grid;
        grid-template-columns: 1fr 1fr;
        gap: .4rem;
    }
    .ops-filtres select,
    .ops-filtres input {
        width: 100%;
        font-size: .8rem;
    }
    .ops-filtre-search {
        grid-column: 1 / -1;
        min-width: 0;
    }
    .ops-filtre-btns {
        grid-column: 1 / -1;
        display: flex;
        gap: .4rem;
    }
    .ops-filtre-btns .btn {
        flex: 1;
        text-align: center;
        justify-content: center;
    }


    .ops-table-wrap { overflow-x: visible; }
    .ops-table { min-width: 0 !important; }

    .ops-table thead { display: none; }
    .ops-table tbody { display: block; }

    .ops-table tbody tr.ops-row {
        display: block;
        background: var(--color-surface);
        border: 1px solid var(--color-border);
        border-radius: var(--radius);
        padding: .75rem;
        margin-bottom: .6rem;
        box-shadow: 0 1px 3px rgba(0,0,0,.04);
    }
    .ops-table tbody tr.ops-row:hover td { background: transparent; }

    .ops-table tbody td {
        display: block;
        padding: .15rem 0;
        border-bottom: none;
        width: 100% !important;
    }
    .ops-table tbody td::before { display: none; }

    .ops-mobile-montant {
        display: inline;
        font-size: 1rem;
        font-weight: 700;
    }

    .ops-desc {
        font-size: .88rem;
        font-weight: 600;
        margin-bottom: .2rem;
    }

    .ops-mobile-meta {
        display: flex !important;
        align-items: center;
        gap: .4rem;
        margin-top: .3rem;
        flex-wrap: wrap;
    }

    .hide-mobile,
    .ops-desktop-montant {
        display: none !important;
    }

    td[data-label="Actions"] {
        padding-top: .4rem !important;
        margin-top: .3rem;
        border-top: 1px solid var(--color-border);
    }
    .ops-actions {
        justify-content: flex-start;
        gap: 6px;
    }
    .ops-actions .btn-xs {
        padding: .3rem .6rem;
        font-size: .78rem;
    }

    .page-header {
        flex-direction: column;
        align-items: flex-start !important;
        gap: .5rem !important;
    }
    .ops-header-btns {
        width: 100%;
    }
    .ops-header-btns .btn {
        flex: 1;
        text-align: center;
        justify-content: center;
        font-size: .75rem !important;
    }
}

@media (max-width: 400px) {
    .ops-filtres { grid-template-columns: 1fr; }
}

/* ═══════════════════════════════════════════════════
   OPÉRATIONS — haut de page rangé
   Placé après les deux blocs ops-* plus haut (hérités, en partie en
   double) : sélecteurs à deux classes pour l'emporter quel que soit
   l'ordre et le point de rupture.
   ═══════════════════════════════════════════════════ */
.ops-filtres.ops-filtres--range { display: flex; flex-direction: column; align-items: stretch; gap: .5rem; }
.ops-filtres--range .ops-filtres-principaux { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem; }
.ops-filtres--range .ops-filtre-search { flex: 1 1 240px; min-width: 0; }
.ops-filtres--range .ops-filtres-principaux > select { flex: 0 1 auto; }
.ops-filtres--range .ops-filtre-btns { display: flex; gap: .4rem; }
.ops-filtres-plus > summary {
    display: inline-flex; align-items: center; gap: .35rem; cursor: pointer;
    font-size: .82rem; font-weight: 500; color: var(--color-primary); list-style: none;
}
.ops-filtres-plus > summary::-webkit-details-marker { display: none; }
.ops-filtres-plus > summary::marker { content: ''; }
.ops-filtres-plus > summary::before { content: '▸'; transition: transform .15s; }
.ops-filtres-plus[open] > summary::before { transform: rotate(90deg); }
.ops-filtres-nb { color: var(--color-muted); font-weight: 400; }
.ops-filtres--range .ops-filtres-avances { display: flex; flex-wrap: wrap; gap: .5rem; margin-top: .5rem; }

.ops-resume { display: flex; flex-direction: column; gap: .4rem; margin-bottom: .75rem; }
/* Carte : montants en colonnes à gauche, nombre et pages à droite. */
.ops-resume-carte {
    display: flex; flex-wrap: wrap; align-items: center; gap: .5rem 1.75rem;
    padding: .65rem 1rem; background: var(--color-surface);
    border: 1px solid var(--color-border); border-radius: var(--radius-lg);
}
.ops-resume-totaux { display: flex; gap: 1.75rem; }
.ops-resume-tot { display: flex; flex-direction: column; gap: .1rem; min-width: 0; }
.ops-resume-lib { font-size: .66rem; font-weight: 600; text-transform: uppercase; letter-spacing: .04em; color: var(--color-muted); }
.ops-resume-montant { font-size: 1rem; font-weight: 700; white-space: nowrap; }
.ops-resume-pied { margin-left: auto; display: flex; align-items: center; gap: 1rem; font-size: .82rem; }
.ops-resume-nb { font-weight: 600; }
.ops-resume-page { color: var(--color-muted); white-space: nowrap; }
.ops-resume-pag { display: inline-flex; align-items: center; gap: .45rem; font-size: .78rem; color: var(--color-muted); }
.ops-resume-pag a, .ops-resume-pag .is-off {
    padding: .2rem .55rem; border: 1px solid var(--color-border); border-radius: var(--radius);
    color: var(--color-text); text-decoration: none; white-space: nowrap;
}
.ops-resume-pag a:hover { border-color: var(--color-primary); }
.ops-resume-pag .is-off { opacity: .4; }
.ops-resume-infos { display: flex; flex-wrap: wrap; gap: .15rem 1.1rem; font-size: .78rem; color: var(--color-muted); padding: 0 .25rem; }
.ops-resume-infos a { color: var(--color-primary); text-decoration: none; }
.ops-resume-infos a:hover { text-decoration: underline; }
.rp-lot-barre[hidden] { display: none; }

/* Actions de ligne : « Modifier » + menu « ⋯ ». Le tableau défile
   horizontalement sur ordinateur (overflow-x: auto), ce qui rogne tout
   ce qui dépasse, y compris le panneau d'un menu ouvert sur les
   dernières lignes : le défilement est levé le temps qu'un menu est
   ouvert, comme pour les cartes. */
.ops-table-wrap:has(.ecole-menu-list.open) { overflow: visible; }
.ops-table .ops-th-actions { width: auto; }
.ops-table .ops-td-actions .ops-actions { flex-wrap: nowrap; justify-content: flex-end; align-items: center; }
.ops-td-actions .ecole-menu-list .ops-btn-note--has { color: var(--color-primary); }

@media (max-width: 768px) {
    /* Recherche seule, compte et mois côte à côte, boutons sur la ligne
       suivante, puis « Plus de filtres » : trois à quatre lignes au lieu
       de huit. */
    .ops-filtres--range .ops-filtre-search { flex: 1 1 100%; }
    .ops-filtres--range .ops-filtres-principaux > select,
    .ops-filtres--range .ops-filtres-avances > select { flex: 1 1 calc(50% - .25rem); width: auto; min-width: 0; }
    .ops-filtres--range .ops-filtre-btns { flex: 1 1 100%; }
    .ops-filtres--range .ops-filtre-btns .btn { flex: 1; justify-content: center; }
    /* Téléphone : trois colonnes égales pour les montants, puis sous un
       filet le nombre d'opérations à gauche et les pages à droite. */
    .ops-resume-carte { flex-direction: column; align-items: stretch; gap: .5rem; padding: .6rem .7rem; }
    .ops-resume-totaux { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: .4rem; }
    .ops-resume-montant { font-size: .84rem; }
    .ops-resume-pied { margin-left: 0; justify-content: space-between; gap: .5rem; padding-top: .45rem; border-top: 1px solid var(--color-border); }
    .ops-resume-pag { gap: .3rem; }
    .ops-resume-infos { flex-direction: column; gap: .2rem; }
    .ops-table .ops-td-actions .ops-actions { justify-content: flex-start; }
}

/* Suggestions dynamiques (adhérent, règle auto, découpage) */
.op-suggestion {
    padding: 8px 12px; border-radius: 8px;
    display: flex; align-items: center; gap: 10px;
    flex-wrap: wrap; font-size: .82rem;
}
.op-suggestion--adherent { background: #f0fdf4; border: 1.5px solid #86efac; }
.op-suggestion--regle    { background: #eff6ff; border: 1.5px solid #93c5fd; }
.op-suggestion--info     { background: #ecfeff; border: 1.5px solid #67e8f9; color: #0e7490; }
.op-sugg-btn {
    padding: 3px 10px; border: none; border-radius: 6px;
    cursor: pointer; font-size: .78rem;
}
.op-sugg-btn--ok      { background: #16a34a; color: #fff; }
.op-sugg-btn--ok-blue { background: #1d4ed8; color: #fff; }
.op-sugg-btn--close   { background: none; border: 1px solid #ccc; color: #666; padding: 3px 8px; }
[data-theme="dark"] .op-suggestion--adherent { background: #1a2a1a; border-color: #2a4a2a; }
[data-theme="dark"] .op-suggestion--regle    { background: #1a2a3a; border-color: #2a4a5e; }
[data-theme="dark"] .op-suggestion--info     { background: #1a2a30; border-color: #2a4a50; color: #7dd3fc; }
[data-theme="dark"] .op-sugg-btn--close      { border-color: var(--color-border); color: var(--color-muted); }

/* Suggestion split — utilisé dans innerHTML */
.op-sugg-title { font-weight: 600; margin-bottom: 6px; }
.op-sugg-label-row {
    display: flex; align-items: center; gap: 6px; cursor: pointer;
}

/* Drag-drop zone justificatif */
.justif-dropzone {
    border: 2px dashed var(--color-border);
    border-radius: var(--radius);
    padding: 20px 16px;
    text-align: center;
    cursor: pointer;
    transition: all .2s;
    background: var(--color-surface);
}
.justif-dropzone:hover { border-color: var(--color-primary); background: rgba(29,78,216,.02); }
.justif-drop-active   { border-color: var(--color-primary) !important; background: rgba(29,78,216,.06) !important; }
.justif-drop-content {
    display: flex; flex-direction: column; align-items: center;
    gap: 4px; font-size: .85rem; color: var(--color-muted);
}

/* Spinner */
.justif-spinner {
    width: 16px; height: 16px;
    border: 2px solid var(--color-border);
    border-top-color: var(--color-primary);
    border-radius: 50%;
    animation: justif-spin .7s linear infinite;
}
@keyframes justif-spin { to { transform: rotate(360deg); } }

/* ── Modals communes opérations ── */
.modal-justif-box {
    background: var(--color-surface); border-radius: 12px;
    max-width: 680px; width: 100%; max-height: 92vh; overflow-y: auto;
    box-shadow: 0 20px 60px rgba(0,0,0,.3);
}
.modal-justif-box--480 { max-width: 480px; }
.modal-justif-header {
    display: flex; justify-content: space-between; align-items: center;
    padding: 12px 20px; border-bottom: 1px solid var(--color-border);
}

/* Modal note */
.note-modal-title { font-size: .95rem; font-weight: 600; }
.note-modal-body  { padding: 16px 20px; }
.note-op-block    { margin-bottom: 12px; }
.note-op-desc {
    font-weight: 600; font-size: .88rem; color: var(--color-text);
}
.note-op-info {
    font-size: .78rem; color: var(--color-muted); margin-top: 2px;
}
.note-textarea {
    width: 100%; padding: 10px 14px;
    border: 1.5px solid var(--color-border); border-radius: 8px;
    font-size: .88rem; font-family: inherit; outline: none; resize: vertical;
    background: var(--color-surface); color: var(--color-text);
    transition: border-color .2s;
}
.note-textarea:focus { border-color: var(--color-primary); }
.note-actions {
    display: flex; gap: 8px; margin-top: 12px;
}
.note-btn-save { flex: 1; }

/* Modal justif preview */
.modal-justif-title {
    font-size: .9rem; font-weight: 600;
    min-width: 0; overflow: hidden;
    text-overflow: ellipsis; white-space: nowrap;
}
.modal-justif-body {
    padding: 16px 20px; text-align: center;
}
.modal-justif-actions {
    padding: 0 20px 16px;
    display: flex; gap: 8px; flex-wrap: wrap;
}
.modal-justif-iframe {
    width: 100%; height: 480px;
    border: 1.5px solid var(--color-border); border-radius: 8px;
}
.modal-justif-img {
    max-width: 100%; max-height: 480px;
    border-radius: 8px;
    border: 1.5px solid var(--color-border);
    cursor: zoom-in;
}

/* ── Modal coupures ── */
.btn-coupures {
    display: block; width: 100%; margin-top: 4px; padding: 6px 12px;
    background: var(--color-surface-alt); border: 1.5px solid var(--color-border);
    border-radius: var(--radius); cursor: pointer;
    font-size: .78rem; font-weight: 600;
    color: var(--color-text); transition: all .15s; text-align: center;
}
.btn-coupures:hover { border-color: var(--color-primary); background: rgba(29,78,216,.04); }

.modal-overlay {
    display: none; position: fixed; inset: 0;
    background: rgba(0,0,0,.45); z-index: 9999;
    align-items: center; justify-content: center; padding: 16px;
}
.modal-overlay.open { display: flex; }

.modal-coupures-box {
    background: var(--color-surface); border-radius: 12px;
    max-width: 440px; width: 100%; max-height: 90vh; overflow-y: auto;
    box-shadow: 0 20px 60px rgba(0,0,0,.25);
}
.modal-coupures-box--lg { max-width: 520px; }
.modal-coupures-header {
    display: flex; justify-content: space-between; align-items: center;
    padding: 14px 20px; border-bottom: 1px solid var(--color-border);
}
.modal-coupures-title { margin: 0; font-size: 1.05rem; }
.modal-coupures-close {
    background: none; border: none; font-size: 1.2rem;
    cursor: pointer; color: var(--color-muted); padding: 4px 8px;
}
.modal-coupures-close:hover { color: var(--color-text); }
.modal-coupures-body { padding: 16px 20px; }

.coup-block { margin-bottom: 14px; }

.coup-section-label {
    font-size: .68rem; font-weight: 700;
    text-transform: uppercase; letter-spacing: 1px;
    color: var(--color-muted); margin-bottom: 6px;
}
.coup-grid { display: flex; flex-wrap: wrap; gap: 5px; }

.coup-item {
    display: flex; align-items: center; gap: 3px;
    background: var(--color-surface-alt);
    border: 1.5px solid var(--color-border); border-radius: 8px;
    padding: 5px 6px; min-width: 95px; transition: all .15s;
}
.coup-item.has-value {
    border-color: var(--color-primary);
    background: rgba(29,78,216,.04);
}

.coup-item .coup-val {
    font-size: .8rem; font-weight: 700;
    color: var(--color-text); min-width: 36px;
}
.coup-item.has-value .coup-val { color: var(--color-primary); }

.coup-btn {
    width: 26px; height: 26px;
    border: none; border-radius: 50%;
    font-size: 15px; font-weight: 700; cursor: pointer;
    display: flex; align-items: center; justify-content: center;
    transition: all .12s; flex-shrink: 0;
    user-select: none; -webkit-tap-highlight-color: transparent;
}
.coup-btn-minus { background: #fee2e2; color: var(--color-danger); }
.coup-btn-minus:disabled { background: var(--color-surface-alt); color: var(--color-border); cursor: default; }
.coup-btn-plus { background: #e0f2fe; color: var(--color-primary); }
.coup-btn-plus:hover { background: #bae6fd; }

.coup-item input[type="number"] {
    width: 38px; padding: 3px 1px;
    border: 1.5px solid var(--color-border); border-radius: 5px;
    font-size: .85rem; font-weight: 600; text-align: center;
    outline: none;
    background: var(--color-surface); color: var(--color-text);
    -moz-appearance: textfield; transition: border-color .15s;
}
.coup-item input[type="number"]::-webkit-inner-spin-button,
.coup-item input[type="number"]::-webkit-outer-spin-button { -webkit-appearance: none; margin: 0; }
.coup-item input:focus { border-color: var(--color-primary); }

.coup-sous {
    font-size: .68rem; color: var(--color-muted);
    margin-left: auto; min-width: 40px; text-align: right;
}
.coup-item.has-value .coup-sous {
    color: var(--color-success); font-weight: 700;
}

.coup-total-bar {
    background: var(--color-surface-alt); border-radius: 8px;
    padding: 10px 14px;
    display: flex; align-items: center; justify-content: space-between;
    border: 1px solid var(--color-border);
}
.coup-total-label { font-size: .9rem; font-weight: 600; color: var(--color-primary); }
.coup-total-val   { font-size: 1.35rem; font-weight: 800; color: var(--color-primary); }

.coup-modal-actions {
    padding: 0 20px 16px;
    display: flex; gap: 10px;
}
.coup-btn-apply { flex: 1; }

@media (max-width: 480px) {
    .coup-grid { gap: 4px; }
    .coup-item { min-width: 85px; padding: 4px 5px; }
}

/* ── Modal suppression en masse ── */
.masse-grid-2 {
    display: grid; grid-template-columns: 1fr 1fr;
    gap: 10px; margin-bottom: 12px;
}
.masse-form-group        { margin: 0; }
.masse-form-group-mb-sm  { margin-bottom: 10px; }
.masse-form-group-mb-md  { margin-bottom: 14px; }
.masse-label-sm          { font-size: .78rem; font-weight: 600; }
.masse-input-sm          { font-size: .82rem; }
.masse-btn-preview       { width: 100%; margin-bottom: 12px; font-size: .85rem; }

.masse-preview {
    display: none;
    background: var(--color-surface-alt);
    border-radius: 10px; padding: 14px 16px;
    margin-bottom: 14px; max-height: 220px;
    overflow-y: auto; font-size: .82rem;
}
.masse-preview.is-visible { display: block; }

.masse-confirm-zone { display: none; }
.masse-confirm-zone.is-visible { display: block; }

.masse-confirm-warn {
    background: #fef2f2;
    border: 1.5px solid var(--color-danger); border-radius: 10px;
    padding: 12px 16px; margin-bottom: 12px;
    font-size: .82rem; color: var(--color-danger);
}
.masse-confirm-actions {
    display: flex; gap: 10px;
}
.masse-confirm-btn-yes { flex: 1; font-size: .85rem; }
.masse-confirm-btn-no  { font-size: .85rem; }

.masse-purge-block {
    border-top: 1.5px solid var(--color-border);
    margin-top: 16px; padding-top: 16px;
}
.masse-purge-btn { width: 100%; font-size: .85rem; }
.masse-purge-hint {
    font-size: .7rem; color: var(--color-muted);
    text-align: center; margin-top: 6px;
}

/* Preview opérations innerHTML — utilisé par previsualiserMasse */
.masse-preview-empty {
    color: var(--color-muted); text-align: center; font-size: .82rem;
}
.masse-preview-head {
    display: flex; gap: 16px; margin-bottom: 10px;
    font-weight: 700; font-size: .85rem;
}
.masse-preview-head .pos { color: var(--color-success); }
.masse-preview-head .neg { color: var(--color-danger); }
.masse-preview-row {
    display: flex; gap: 10px; padding: 4px 0;
    border-bottom: 1px solid var(--color-border);
    font-size: .78rem; align-items: center;
}
.masse-preview-row .date {
    color: var(--color-muted); width: 75px; flex-shrink: 0;
}
.masse-preview-row .desc {
    flex: 1; overflow: hidden;
    text-overflow: ellipsis; white-space: nowrap;
}
.masse-preview-row .amt { font-weight: 700; flex-shrink: 0; }
.masse-preview-row .amt--pos { color: var(--color-success); }
.masse-preview-row .amt--neg { color: var(--color-danger); }
.masse-preview-more {
    text-align: center; color: var(--color-muted);
    font-size: .75rem; margin-top: 6px;
}

/* ============================================================
   SOUS-LOT 2D — Inventaire / Mots-clés / Rapports / Rapprochement
   ============================================================ */

/* ── Inventaire ── */
.inv-solde-card       { margin-bottom:1.5rem; max-width:500px; }
.inv-solde-body       { text-align:center; padding:1.5rem; }
.inv-solde-label      { font-size:.82rem; color:var(--color-muted); margin-bottom:.5rem; }
.inv-solde-val        { font-size:2.5rem; font-weight:700; color:var(--color-primary); }
.inv-solde-note       { font-size:.78rem; color:var(--color-muted); margin-top:.5rem; }
.inv-solde-divider    { margin-top:1rem; padding-top:.75rem; border-top:1px solid var(--color-border); }
.inv-solde-detail     { font-size:.78rem; color:var(--color-muted); }
.inv-solde-span       { font-size:.72rem; }
.inv-ecart-warn       { font-size:.78rem; font-weight:600; margin-top:4px; }
.inv-ecart-warn--over { color:#92400e; }
.inv-ecart-warn--under{ color:var(--color-danger); }
.inv-grid             { display:grid; grid-template-columns:1fr 1fr; gap:1.5rem; align-items:start; }
.inv-section-title    { font-size:.82rem; font-weight:700; margin:.75rem 0 .5rem; color:var(--color-muted); }
.inv-total-box        { background:var(--color-primary); color:#fff; border-radius:var(--radius);
                        padding:1rem; margin:1rem 0; text-align:center; }
.inv-total-label      { font-size:.78rem; opacity:.8; margin-bottom:4px; }
.inv-total-val        { font-size:2rem; font-weight:700; }
.inv-ecart-zone       { display:none; border-radius:var(--radius); padding:.75rem 1rem; margin-bottom:1rem; text-align:center; }
.inv-ecart-sublabel   { font-size:.78rem; margin-bottom:2px; }
.inv-ecart-val        { font-size:1.3rem; font-weight:700; }
.inv-card-sm          { margin-bottom:1rem; }
.inv-card-h2          { font-size:.9rem; }
.inv-card-pad0        { padding:0; }
.inv-empty            { padding:1rem; font-size:.85rem; }
.inv-table-sm         { font-size:.8rem; }
.inv-td-date          { width:80px; }
.inv-td-amount        { text-align:right; font-weight:600; }
.inv-td-amount--entree{ color:var(--color-success); }
.inv-td-amount--sortie{ color:var(--color-danger); }
.inv-arrete-header    { display:flex; justify-content:space-between; align-items:center; flex-wrap:wrap; gap:.5rem; }
.inv-arrete-filter    { display:flex; gap:.4rem; align-items:center; flex-wrap:wrap; }
.inv-arrete-form      { display:flex; gap:.4rem; align-items:center; margin:0; }
.inv-arrete-select    { font-size:.75rem; padding:3px 8px; border:1px solid var(--color-border); border-radius:6px; }
.inv-arrete-clear     { font-size:.75rem; color:var(--color-muted); text-decoration:none; }
.inv-recaler-bar      { padding:.6rem 1rem; background:#eff6ff; border-bottom:1px solid var(--color-border); font-size:.82rem; }
[data-theme="dark"] .inv-recaler-bar { background:#1a2a40; }
.inv-recaler-inner    { display:flex; align-items:center; gap:.5rem; flex-wrap:wrap; justify-content:space-between; }
.inv-recaler-text     { color:var(--color-primary); }
.inv-td-right         { text-align:right; font-weight:600; }
.inv-td-center        { text-align:center; }
.inv-td-w50           { width:50px; }
.inv-small-block      { display:block; }
.inv-recalage-tag     { color:var(--color-primary); font-size:.68rem; }
.inv-acquitte-small   { display:block; font-size:.68rem; color:var(--color-muted); font-weight:400; }
.inv-btn-acquit       { font-size:.68rem; padding:2px 6px; }
.inv-btn-full         { width:100%; }
.inv-btn-nowrap       { font-size:.75rem; white-space:nowrap; }
.inv-flex-btns        { display:flex; gap:.5rem; flex-wrap:wrap; }

/* Écart dynamique (couleur conditionnelle via PHP) */
.inv-ecart-color--ok       { color:var(--color-success); }
.inv-ecart-color--warn     { color:#92400e; }
.inv-ecart-color--danger   { color:var(--color-danger); }
.inv-ecart-color--muted    { color:var(--color-muted); }

/* Modal partagé inventaire */
.modal-box.modal-box--inv { max-width:420px; }
.modal-box-header       { display:flex; justify-content:space-between; align-items:center;
                          padding:14px 20px; border-bottom:1px solid var(--color-border); }
.modal-box-title        { font-size:.95rem; font-weight:600; }
.modal-box-close        { background:none; border:none; font-size:1.2rem; cursor:pointer; color:var(--color-muted); }
.modal-box-body         { padding:16px 20px; }
.modal-box-desc         { font-size:.85rem; margin-bottom:1rem; color:var(--color-text); }
.modal-box-desc--sm     { font-size:.8rem; margin-bottom:1rem; color:var(--color-muted); }
.modal-box-desc--half   { font-size:.85rem; margin-bottom:.5rem; color:var(--color-text); }
.modal-box-actions      { display:flex; gap:8px; margin-top:1rem; }
.modal-box-actions .btn { flex:1; }
.inv-input-full         { width:100%; }

@media(max-width:768px) {
    .inv-grid { grid-template-columns:1fr !important; }
}

/* ── Mots-clés ── */
.mk-header-stats        { font-size:.8rem; color:var(--color-muted); }
.mk-stat-danger         { color:var(--color-danger); font-weight:600; }
.mk-stat-warn           { color:#92400e; font-weight:600; }
.mk-alert-mb            { margin-bottom:1rem; }
.mk-suspect-box         { background:#fef2f2; border:1.5px solid #fecaca; border-radius:var(--radius-lg); margin-bottom:1.25rem; }
[data-theme="dark"] .mk-suspect-box { background:#2a1515; border-color:#5c2020; }
.mk-suspect-header      { padding:.75rem 1.25rem; border-bottom:1px solid #fecaca; display:flex;
                          align-items:center; gap:.75rem; flex-wrap:wrap; }
[data-theme="dark"] .mk-suspect-header { border-color:#5c2020; }
.mk-suspect-title       { font-weight:600; color:var(--color-danger); }
.mk-btn-delier          { background:#fee2e2; color:var(--color-danger); border:none; padding:3px 10px;
                          border-radius:6px; cursor:pointer; font-size:.75rem; }
[data-theme="dark"] .mk-btn-delier { background:#3a1515; }
.mk-btn-delier-all      { background:#fee2e2; color:var(--color-danger); border-color:#fecaca; }
[data-theme="dark"] .mk-btn-delier-all { background:#3a1515; border-color:#5c2020; }
.mk-td-nowrap           { white-space:nowrap; }
.mk-td-libelle          { font-size:.78rem; color:var(--color-muted); max-width:200px; overflow:hidden;
                          text-overflow:ellipsis; white-space:nowrap; }
.mk-td-montant          { text-align:right; color:var(--color-success); font-weight:600; }
.mk-td-nom              { font-size:.8rem; }
.mk-td-motcles          { font-size:.75rem; color:var(--color-muted); }
.mk-code-motcle         { background:#f3f4f6; padding:1px 5px; border-radius:3px; }
[data-theme="dark"] .mk-code-motcle { background:#2a2a2a; }
.mk-ambigu-box          { background:#fffbeb; border:1.5px solid #fde68a; border-radius:var(--radius-lg); margin-bottom:1.25rem; }
[data-theme="dark"] .mk-ambigu-box { background:#2a2515; border-color:#5c4a15; }
.mk-ambigu-header       { padding:.75rem 1.25rem; border-bottom:1px solid #fde68a; }
[data-theme="dark"] .mk-ambigu-header { border-color:#5c4a15; }
.mk-ambigu-title        { font-weight:600; color:#92400e; }
[data-theme="dark"] .mk-ambigu-title { color:#f0c040; }
.mk-code-ambigu         { background:#fef3c7; padding:2px 8px; border-radius:4px; font-weight:700; }
[data-theme="dark"] .mk-code-ambigu { background:#3a3015; }
.mk-td-cat-danger       { font-size:.8rem; color:var(--color-danger); }
.mk-btn-suppr-motcle    { background:#fef3c7; color:#92400e; border:none; padding:3px 10px;
                          border-radius:6px; cursor:pointer; font-size:.75rem; }
[data-theme="dark"] .mk-btn-suppr-motcle { background:#3a3015; }
.mk-ok-box              { background:#f0fdf4; border-radius:var(--radius); padding:.75rem 1.25rem;
                          margin-bottom:1.25rem; font-size:.85rem; color:#166534; font-weight:500; }
[data-theme="dark"] .mk-ok-box { background:#0a2a0a; color:#4ade80; }
.mk-info-box            { background:#f0fdf4; border-radius:var(--radius); padding:.75rem 1rem;
                          margin-bottom:1.25rem; font-size:.85rem; color:#166534; }
[data-theme="dark"] .mk-info-box { background:#0a2a0a; color:#4ade80; }
.mk-code-inline         { background:white; padding:1px 6px; border-radius:4px; }
[data-theme="dark"] .mk-code-inline { background:#222; }
.mk-doublon-box         { background:#fef2f2; border:1.5px solid #fecaca; border-radius:var(--radius-lg);
                          padding:1rem 1.25rem; margin-bottom:1.25rem; }
[data-theme="dark"] .mk-doublon-box { background:#2a1515; border-color:#5c2020; }
.mk-doublon-title       { font-weight:600; color:var(--color-danger); margin-bottom:.75rem; }
.mk-doublon-row         { background:white; border-radius:var(--radius); padding:.6rem 1rem; margin-bottom:.5rem;
                          font-size:.83rem; display:flex; align-items:center; gap:.75rem; flex-wrap:wrap; }
[data-theme="dark"] .mk-doublon-row { background:var(--color-surface); }
.mk-doublon-code        { font-weight:700; background:#f3f4f6; padding:2px 8px; border-radius:4px; }
[data-theme="dark"] .mk-doublon-code { background:#2a2a2a; }
.mk-doublon-label       { color:var(--color-muted); }
.mk-doublon-pill        { background:#fef2f2; padding:2px 10px; border-radius:20px; display:inline-flex;
                          align-items:center; gap:5px; }
[data-theme="dark"] .mk-doublon-pill { background:#2a1515; }
.mk-doublon-del         { background:none; border:none; color:var(--color-danger); cursor:pointer;
                          font-size:.8rem; padding:0; }
.mk-table-card          { padding:0; overflow-x:auto; }
.mk-table               { font-size:.84rem; }
.mk-th-name             { min-width:160px; }
.mk-th-ops              { text-align:center; width:80px; }
.mk-th-add              { width:200px; }
.mk-th-sync             { width:80px; }
.mk-td-name             { font-weight:500; }
.mk-td-email            { font-size:.72rem; color:var(--color-muted); }
.mk-pill                { display:inline-flex; align-items:center; gap:3px; padding:2px 8px;
                          border-radius:20px; font-size:.78rem; margin:2px; }
.mk-pill--normal        { background:var(--color-surface-alt); border:1px solid var(--color-border); }
.mk-pill--doublon       { background:#fef2f2; border:1px solid #fecaca; }
[data-theme="dark"] .mk-pill--doublon { background:#2a1515; border-color:#5c2020; }
.mk-pill-warn           { color:var(--color-danger); font-size:.65rem; }
.mk-pill-del            { background:none; border:none; color:var(--color-muted); cursor:pointer;
                          font-size:.75rem; padding:0; line-height:1; }
.mk-no-motcle           { color:var(--color-border); font-style:italic; font-size:.8rem; }
.mk-ops-badge           { padding:2px 10px; border-radius:10px; font-weight:700; font-size:.82rem; }
.mk-ops-badge--active   { background:#dcfce7; color:#166534; }
[data-theme="dark"] .mk-ops-badge--active { background:#0a2a0a; color:#4ade80; }
.mk-ops-badge--none     { background:var(--color-surface-alt); color:var(--color-muted); }
.mk-add-form            { display:flex; gap:.3rem; }
.mk-add-input           { width:110px; padding:.3rem .5rem; border:1px solid var(--color-border);
                          border-radius:var(--radius); font-size:.8rem; text-transform:uppercase;
                          background:var(--color-surface); }
.mk-no-perm             { color:var(--color-border); font-size:.78rem; }
.mk-sync-btn            { font-size:.75rem; white-space:nowrap; }
.mk-sync-form           { display:inline; }
.mk-page-header-actions { display:flex; gap:.5rem; align-items:center; }
.mk-sync-all-form       { display:inline; }
.mk-overflow            { overflow-x:auto; }

/* ── Rapports ── */
.rpt-header-actions     { display:flex; gap:.5rem; }
.rpt-zone               { margin:0 auto; }
.rpt-entete             { text-align:center; margin-bottom:2rem; padding-bottom:1.25rem;
                          border-bottom:3px solid var(--color-primary); }
.rpt-asso-name          { font-size:1.4rem; font-weight:700; color:var(--color-primary); margin-bottom:.2rem; }
.rpt-mentions           { font-size:.75rem; letter-spacing:2px; color:#c9a84c; text-transform:uppercase; margin-bottom:.5rem; }
.rpt-titre              { font-size:1.2rem; font-weight:700; margin-bottom:.2rem; }
.rpt-periode            { font-size:.85rem; color:var(--color-muted); }
.rpt-summary            { display:grid; grid-template-columns:repeat(3,1fr); gap:1rem; margin-bottom:1.75rem; }
.rpt-summary-card       { border-radius:var(--radius-lg); padding:1.25rem; text-align:center; }
.rpt-summary-card--e    { background:#f0fdf4; border:1px solid #bbf7d0; }
[data-theme="dark"] .rpt-summary-card--e { background:#0a2a0a; border-color:#166534; }
.rpt-summary-card--s    { background:#fef2f2; border:1px solid #fecaca; }
[data-theme="dark"] .rpt-summary-card--s { background:#2a1515; border-color:#5c2020; }
.rpt-summary-card--r-pos{ background:#1a5276; }
.rpt-summary-card--r-neg{ background:#7b241c; }
.rpt-summary-label      { font-size:.68rem; text-transform:uppercase; letter-spacing:1.5px; margin-bottom:.4rem; font-weight:600; }
.rpt-summary-label--e   { color:var(--color-success); }
.rpt-summary-label--s   { color:var(--color-danger); }
.rpt-summary-label--r   { color:rgba(255,255,255,.7); }
.rpt-summary-val        { font-size:1.5rem; font-weight:800; }
.rpt-summary-val--e     { color:var(--color-success); }
.rpt-summary-val--s     { color:var(--color-danger); }
.rpt-summary-val--r     { color:#fff; }
.rpt-compte-grid        { display:grid; grid-template-columns:1fr 1fr; gap:1rem; margin-bottom:1.75rem; }
.rpt-compte-card        { border-radius:var(--radius-lg); overflow:hidden; }
.rpt-compte-card--bank  { border:1.5px solid #bfdbfe; }
.rpt-compte-card--cash  { border:1.5px solid #fde68a; }
.rpt-compte-header      { color:#fff; padding:.6rem 1rem; font-size:.72rem; font-weight:700;
                          letter-spacing:1px; text-transform:uppercase; }
.rpt-compte-header--bank{ background:#1e40af; }
.rpt-compte-header--cash{ background:#c9a84c; }
.rpt-compte-body        { padding:1rem; display:grid; grid-template-columns:1fr 1fr; gap:.75rem; text-align:center; }
.rpt-compte-sublabel    { font-size:.68rem; text-transform:uppercase; letter-spacing:1px; margin-bottom:.25rem; }
.rpt-compte-sublabel--e { color:var(--color-success); }
.rpt-compte-sublabel--s { color:var(--color-danger); }
.rpt-compte-val         { font-size:1.05rem; font-weight:700; }
.rpt-compte-val--e      { color:var(--color-success); }
.rpt-compte-val--s      { color:var(--color-danger); }
.rpt-compte-solde       { text-align:center; padding:0 1rem .75rem; font-size:.85rem; font-weight:600; }
.rpt-cat-grid           { display:grid; grid-template-columns:1fr 1fr; gap:1rem; margin-bottom:1.5rem; }
.rpt-cat-card           { border:1.5px solid var(--color-border); border-radius:var(--radius-lg); overflow:hidden; }
.rpt-cat-header         { color:#fff; padding:.6rem 1rem; font-size:.72rem; font-weight:700;
                          letter-spacing:1px; text-transform:uppercase; }
.rpt-cat-header--e      { background:var(--color-success); }
.rpt-cat-header--s      { background:var(--color-danger); }
.rpt-cat-body           { padding:.75rem 1rem; }
.rpt-cat-empty          { text-align:center; color:var(--color-muted); font-size:.82rem; padding:.5rem; }
.rpt-cat-row            { display:flex; align-items:center; gap:.5rem; padding:.4rem 0;
                          border-bottom:1px solid var(--color-border); }
.rpt-cat-name           { flex:1; font-size:.82rem; }
.rpt-cat-detail         { font-size:.7rem; color:var(--color-muted); }
.rpt-cat-val            { font-size:.82rem; font-weight:600; white-space:nowrap; }
.rpt-cat-val--e         { color:var(--color-success); }
.rpt-cat-val--s         { color:var(--color-danger); }
.rpt-cat-bar            { width:48px; height:4px; background:var(--color-border); border-radius:2px;
                          overflow:hidden; flex-shrink:0; }
.rpt-cat-bar-fill       { height:100%; border-radius:2px; }
.rpt-cat-bar-fill--e    { background:var(--color-success); }
.rpt-cat-bar-fill--s    { background:var(--color-danger); }
.rpt-cat-total          { display:flex; justify-content:space-between; padding-top:.6rem; font-weight:700;
                          font-size:.85rem; margin-top:.25rem; }
.rpt-cat-total--e       { border-top:2px solid var(--color-success); }
.rpt-cat-total--s       { border-top:2px solid var(--color-danger); }
.rpt-transferts-info    { background:#ede9fe; border-radius:var(--radius); padding:.75rem 1rem;
                          margin-bottom:1.25rem; font-size:.85rem; color:#5b21b6; display:flex;
                          align-items:center; gap:.75rem; }
[data-theme="dark"] .rpt-transferts-info { background:#1a1a2e; color:#a78bfa; }
.rpt-exclusions         { font-size:.72rem; color:var(--color-muted); margin-bottom:1rem; font-style:italic; }
.rpt-footer             { display:flex; justify-content:space-between; align-items:center; font-size:.72rem;
                          color:var(--color-muted); border-top:1.5px solid var(--color-border);
                          padding-top:.75rem; margin-top:.5rem; flex-wrap:wrap; gap:.5rem; }
.rpt-select             { padding:.35rem .6rem; border:1px solid var(--color-border); border-radius:var(--radius);
                          font-size:.82rem; background:var(--color-surface); }
.rpt-form-col           { margin-top:1rem; display:flex; flex-direction:column; gap:.5rem; }
.rpt-form-row           { display:flex; gap:.5rem; justify-content:center; flex-wrap:wrap; }
.rpt-form-center        { align-self:center; }

@media (max-width:768px) {
    .rpt-summary { grid-template-columns:1fr !important; }
    .rpt-compte-grid, .rpt-cat-grid { grid-template-columns:1fr !important; }
    .rpt-zone { font-size:.85rem !important; }
}

/* ── Rapprochement ── */
.rp-upload-card         { max-width:640px; margin:0 auto; }
.rp-upload-zone         { display:flex; flex-direction:column; align-items:center; justify-content:center;
                          gap:.75rem; padding:2.5rem; border:2px dashed var(--color-border);
                          border-radius:var(--radius-lg); cursor:pointer; text-align:center;
                          transition:border-color .2s, background .2s; background:var(--color-surface-alt); }
.rp-upload-zone--drag   { border-color:var(--color-primary); background:rgba(201,168,76,.08); }
.rp-upload-icon         { font-size:2.5rem; }
.rp-upload-filename     { font-size:.8rem; color:var(--color-primary); font-weight:600; }
.rp-upload-info         { margin-top:1rem; background:var(--color-surface-alt); border:none; }
.rp-upload-info-body    { padding:.75rem 1rem; font-size:.82rem; line-height:1.7; }
.rp-upload-hint         { color:var(--color-primary); }
.rp-upload-submit       { margin-top:1.25rem; text-align:right; }
.rp-summary-bar         { padding:.75rem 1.25rem; }
.rp-summary-inner       { display:flex; flex-wrap:wrap; gap:1rem; align-items:center; font-size:.88rem; }
.rp-import-btns         { margin-bottom:1rem; display:flex; gap:.5rem; flex-wrap:wrap; align-items:center; }
.rp-nb-coches           { font-size:.8rem; color:var(--color-muted); }
.rp-section-success     { margin-bottom:1rem; border-color:var(--color-success); }
.rp-section-header--ok  { background:var(--color-success-pale); padding:.6rem 1rem; }
.rp-section-title--ok   { font-size:.9rem; color:var(--color-success); }
.rp-td-nowrap           { white-space:nowrap; }
.rp-td-libelle          { max-width:200px; overflow:hidden; text-overflow:ellipsis; white-space:nowrap; color:var(--color-muted); }
.rp-td-libelle--sm      { max-width:180px; overflow:hidden; text-overflow:ellipsis; white-space:nowrap; color:var(--color-muted); }
.rp-td-amount           { text-align:right; font-weight:600; white-space:nowrap; }
.rp-td-amount--entree   { color:var(--color-success); }
.rp-td-amount--sortie   { color:var(--color-danger); }
.rp-td-match-detail     { font-size:.75rem; color:var(--color-muted); margin-top:2px; }
.rp-td-match-info       { font-size:.72rem; color:var(--color-info); margin-top:1px; }
.rp-td-match-cat        { font-size:.82rem; font-weight:600; }
.rp-section-warning     { margin-bottom:1rem; border-color:var(--color-warning); }
.rp-td-select           { font-size:.8rem; padding:3px 6px; border:1px solid var(--color-border);
                          border-radius:var(--radius); background:var(--color-surface); min-width:130px; }
.rp-td-memo-label       { display:flex; align-items:center; gap:4px; font-size:.78rem; white-space:nowrap; }
.rp-section-doublon     { margin-bottom:1rem; border-color:var(--color-danger); opacity:.7; }
.rp-doublon-title       { font-size:.85rem; color:var(--color-danger); }
.rp-doublon-status      { color:var(--color-danger); font-size:.78rem; font-weight:600; }
.rp-td-chk              { text-align:center; width:32px; }
.rp-th-right            { text-align:right; }

@media (max-width:768px) {
    .rp-upload-card { max-width:100% !important; }
    .rp-td-select { min-width:0 !important; width:100%; font-size:.75rem !important; }
    .rp-td-memo-label { white-space:normal !important; font-size:.7rem !important; }
}

/* ── Résidus header/permissions/secretariat ── */
.sb-header-link         { text-decoration:none; color:inherit; }
.mob-icon-pos           { position:relative; }
.notif-badge-pos        { position:absolute; top:2px; right:2px; font-size:.55rem; min-width:12px; height:12px; }
.search-icon            { font-size:1rem; opacity:.5; }
.sec-border-accent      { border-left:4px solid var(--color-primary); }
.sec-border-accent--danger { border-left-color:var(--color-danger); }


/* ── Inventaire: coupures grid (migré depuis <style> block) ── */
.coupures-grid { display:flex; flex-direction:column; gap:4px; margin-bottom:.5rem; }
.coupure-row {
    display:grid; grid-template-columns:60px 80px 1fr;
    align-items:center; gap:8px;
    padding:4px 0;
    border-bottom:1px solid var(--color-border);
}
.coupure-row:last-child { border-bottom:none; }
.coupure-val { font-size:.82rem; font-weight:600; color:var(--color-text); }
.coupure-nb {
    text-align:center; padding:4px 6px;
    border:1px solid var(--color-border);
    border-radius:4px; font-size:.82rem;
    background:var(--color-surface);
    color:var(--color-text); width:100%;
}
.coupure-total { font-size:.8rem; font-weight:600; color:var(--color-primary); text-align:right; }

/* ── Rapports: grille de choix (migré depuis <style> block) ──
   auto-fit et non auto-fill : quand une carte manque — l'export CSV ne
   s'affiche qu'à qui peut exporter — les trois restantes se partagent la
   ligne au lieu de laisser une colonne vide. min() sur le minimum : sur un
   écran plus étroit que la carte, la colonne rétrécit au lieu de déborder.
   180px plutôt que 220 : quatre cartes tiennent sur une ligne dès qu'il y
   a la place, au lieu de passer à deux lignes pour quelques pixels. */
.rapport-grid { display:grid; grid-template-columns:repeat(auto-fit,minmax(min(100%,180px),1fr)); gap:1rem; margin-bottom:1.5rem; }
.rapport-card { background:var(--color-surface); border:1.5px solid var(--color-border); border-radius:var(--radius-lg);
                padding:1.5rem; text-align:center; transition:box-shadow .15s,transform .15s;
                /* Colonne : les cartes ont déjà la même hauteur (la grille les
                   étire), mais leur contenu était collé en haut — le bouton
                   d'une carte à deux menus tombait deux crans plus bas que
                   celui d'une carte à un seul lien. Le bloc d'action est
                   poussé en bas, les quatre boutons s'alignent. */
                display:flex; flex-direction:column; }
.rapport-card .rpt-form-col { margin-top:auto; padding-top:1rem; }
.rapport-card:hover { box-shadow:var(--shadow-md); transform:translateY(-2px); }
.rapport-icon { font-size:2.5rem; margin-bottom:.75rem; }
.rapport-card h3 { font-size:1rem; font-weight:600; margin-bottom:.3rem; color:var(--color-text); }
.rapport-card p { font-size:.82rem; color:var(--color-muted); }

/* En dessous d'un grand écran : deux colonnes carrées, toujours. Sans ce
   palier, quatre cartes tombaient en 3 + 1 — la dernière seule sur sa ligne —
   sur une fenêtre d'ordinateur pas très large comme sur une tablette. Moins
   de colonnes plutôt que des colonnes plus petites. */
@media (max-width: 1160px) {
    .rapport-grid { grid-template-columns: 1fr 1fr; }
}

/* Téléphone : deux cartes par ligne plutôt que quatre pavés empilés, qui
   demandaient trois écrans de défilement pour choisir un rapport. Cartes
   resserrées en conséquence, et les menus prennent toute la largeur de leur
   carte — écrite APRÈS la règle de base, sinon elle ne l'écraserait pas. */
@media (max-width: 560px) {
    .rapport-grid { gap:.6rem; }
    .rapport-card { padding:.9rem .6rem; }
    .rapport-card .rpt-form-col { padding-top:.6rem; gap:.4rem; }
    .rapport-icon { font-size:1.75rem; margin-bottom:.4rem; }
    .rapport-card h3 { font-size:.85rem; }
    .rapport-card p  { font-size:.72rem; }
    .rapport-card .rpt-form-row { flex-direction:column; gap:.4rem; }
    .rapport-card .rpt-select { width:100%; }
    .rapport-card .rpt-form-center { align-self:stretch; }
}

/* ── Utility text colors ── */
.text-info    { color: var(--color-info); }
.text-warning { color: var(--color-warning); }

/* ── Rapprochement: badges (migré depuis <style> block) ── */
.rp-badge { padding:2px 8px; border-radius:6px; font-size:.78rem; font-weight:600; display:inline-block; }
.rp-badge--transfert { background:#dbeafe; color:#1e40af; }
.rp-badge--adherent  { background:#dcfce7; color:#166534; }
.rp-badge--cheque    { background:#fef9c3; color:#854d0e; }
.rp-badge--regle     { background:#e0f2fe; color:#075985; }
[data-theme="dark"] .rp-badge--transfert { background:#1a2a40; color:#6ec0e8; }
[data-theme="dark"] .rp-badge--adherent  { background:#1a2a1a; color:#4ade80; }
[data-theme="dark"] .rp-badge--cheque    { background:#2a2515; color:#f0c040; }
[data-theme="dark"] .rp-badge--regle     { background:#1a2a35; color:#7dd3fc; }
.rp-header--warning  { background:#fffbeb; padding:.6rem 1rem; }
.rp-title--warning   { font-size:.9rem; color:#92400e; }
.rp-header--danger   { background:#fef2f2; padding:.5rem 1rem; cursor:pointer; }
.rp-row--danger      { background:#fef2f2; }
[data-theme="dark"] .rp-header--warning { background:#2a2515; }
[data-theme="dark"] .rp-title--warning  { color:#f0c040; }
[data-theme="dark"] .rp-header--danger  { background:#2a1515; }
[data-theme="dark"] .rp-row--danger     { background:#2a1515; }
.rp-upload-submit    { margin-top:1.25rem; text-align:right; }

/* ── Justificatifs échéancier ── */
.ops-justif-modele-row {
    margin-top: .6rem;
}
.ops-justif-modele-row--modal {
    margin-bottom: 1rem;
}
.ops-justif-modele-label {
    display: flex;
    align-items: flex-start;
    gap: .5rem;
    cursor: pointer;
    font-size: .9rem;
}
.ops-justif-modele-label input[type="checkbox"] {
    margin-top: .15rem;
    flex-shrink: 0;
    accent-color: var(--color-primary);
}
.ops-modele-badge {
    font-size: .85rem;
    opacity: .75;
    cursor: default;
}
.badge-modele-echeancier {
    display: inline-block;
    background: var(--color-primary-lt);
    color: var(--color-primary);
    border-radius: 6px;
    padding: 1px 7px;
    font-size: .75rem;
    font-weight: 600;
    margin-left: .4rem;
}
[data-theme="dark"] .badge-modele-echeancier {
    background: rgba(245,158,11,.15);
    color: #fbbf24;
}

/* Justificatif hérité d'un modèle échéancier (🔗) : visuellement
   distinct du trombone d'une pièce propre, pour qu'un contrôle des
   comptes voie tout de suite d'où vient la justification. */
.ops-justif-herite {
    opacity: .8;
    filter: saturate(.7);
}
.ops-justif-herite:hover { opacity: 1; filter: none; }

/* Pointeur d'échéancier cassé : modèle supprimé ou fichier retiré */
.ops-justif-orphelin {
    color: var(--color-danger, #dc2626);
    font-size: .9rem;
    cursor: help;
}

.ops-justif-modele-warn {
    margin-top: .4rem;
    font-size: .78rem;
}

.modal-justif-note {
    font-size: .78rem;
    color: var(--color-muted);
    margin-right: auto;
    align-self: center;
}

/* ── Mes actions — lien compte rendu ── */
.ma-reunion-link {
    color: var(--color-primary);
    text-decoration: none;
    font-weight: 500;
}
.ma-reunion-link:hover {
    text-decoration: underline;
}

/* ── Adherents — cartes stats cliquables ── */
a.stat-card { text-decoration: none; color: inherit; cursor: pointer; }
a.stat-card:hover { transform: translateY(-2px); box-shadow: 0 4px 12px rgba(0,0,0,.1); }
.adh-stat--active { outline: 2px solid var(--color-primary); outline-offset: 2px; }

/* ── Dernier import bancaire ── */
.dash-import-info {
    font-size: .82rem;
    color: var(--color-muted);
    padding: .4rem .75rem;
    margin-bottom: .75rem;
    background: var(--color-surface-alt);
    border-radius: 6px;
    border-left: 3px solid var(--color-border);
}
.dash-import-info strong { color: var(--color-text); }
.dash-import-info a { color: var(--color-primary); text-decoration: none; }
.dash-import-info a:hover { text-decoration: underline; }
[data-theme="dark"] .dash-import-info { background: rgba(255,255,255,.04); }

/* ── Immobilisations — nouveau design ── */
.tps-immo-summary {
    display: flex;
    align-items: center;
    gap: 1rem;
    flex-wrap: wrap;
    background: var(--color-surface-alt);
    border-radius: 8px;
    padding: .85rem 1.1rem;
    margin-bottom: 1.25rem;
    border: 1px solid var(--color-border);
}
.tps-immo-summary-item { display: flex; flex-direction: column; gap: .15rem; }
.tps-immo-summary-label { font-size: .72rem; color: var(--color-muted); text-transform: uppercase; letter-spacing: .04em; }
.tps-immo-summary-val { font-size: 1.05rem; font-weight: 700; }
.tps-immo-summary-val--primary { color: var(--color-primary); }
.tps-immo-summary-val--muted { color: var(--color-muted); font-size: .95rem; }
.tps-immo-summary-sep { color: var(--color-border); font-size: 1.2rem; }
.tps-immo-summary-sep--right { margin-left: auto; }

.tps-immo-bien-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(280px, 1fr));
    gap: 1rem;
}
.tps-immo-bien-card {
    border: 1px solid var(--color-border);
    border-radius: 10px;
    padding: 1rem 1.1rem;
    background: var(--color-surface);
    transition: box-shadow .15s;
}
.tps-immo-bien-card:hover { box-shadow: 0 2px 10px rgba(0,0,0,.08); }
.tps-immo-bien-card--amorti { opacity: .7; border-style: dashed; }

.tps-immo-bien-head {
    display: flex;
    align-items: center;
    gap: .5rem;
    margin-bottom: .3rem;
}
.tps-immo-bien-nom { font-weight: 600; flex: 1; font-size: .95rem; }
.tps-immo-badge-amorti {
    font-size: .7rem; font-weight: 600;
    background: var(--color-surface-alt);
    color: var(--color-muted);
    border-radius: 4px;
    padding: 1px 6px;
}
.tps-immo-bien-meta {
    font-size: .78rem;
    color: var(--color-muted);
    margin-bottom: .75rem;
}

.tps-immo-bar-wrap {
    display: flex;
    align-items: center;
    gap: .6rem;
    margin-bottom: .75rem;
}
.tps-immo-bar-track {
    flex: 1;
    height: 7px;
    background: var(--color-border);
    border-radius: 99px;
    overflow: hidden;
}
.tps-immo-bar-fill {
    height: 100%;
    border-radius: 99px;
    transition: width .4s ease;
}
.tps-immo-bar-pct {
    font-size: .75rem;
    color: var(--color-muted);
    white-space: nowrap;
    min-width: 70px;
    text-align: right;
}

.tps-immo-bien-kpis {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: .4rem .8rem;
}
.tps-immo-kpi { display: flex; flex-direction: column; gap: .1rem; }
.tps-immo-kpi-label { font-size: .7rem; color: var(--color-muted); text-transform: uppercase; letter-spacing: .03em; }
.tps-immo-kpi-val { font-size: .88rem; font-weight: 600; }
.tps-immo-kpi-val--primary { color: var(--color-primary); }

/* Suggestions durée */
.tps-immo-presets {
    display: flex;
    flex-wrap: wrap;
    gap: .3rem;
    margin-top: .4rem;
    align-items: center;
}
.tps-immo-preset-label { font-size: .72rem; color: var(--color-muted); }
.tps-immo-preset {
    font-size: .72rem;
    padding: 2px 8px;
    border-radius: 99px;
    border: 1px solid var(--color-border);
    background: var(--color-surface-alt);
    cursor: pointer;
    color: var(--color-text);
    transition: border-color .15s, background .15s;
}
.tps-immo-preset:hover { border-color: var(--color-primary); background: var(--color-primary-lt); }

[data-theme="dark"] .tps-immo-bien-card { background: var(--color-surface-alt); }
[data-theme="dark"] .tps-immo-summary { background: rgba(255,255,255,.04); }

/* ── Récap actions réunion ── */
.pv-recap-card { margin-top: 1.5rem; }
.pv-recap-header {
    display: flex; align-items: center; gap: 1rem; flex-wrap: wrap;
}
.pv-recap-header h2 { flex: 1; }
.pv-recap-filters { display: flex; gap: .4rem; flex-wrap: wrap; margin-bottom: .75rem; }
/* Participants en carte repliable (reunions/view.php) : même écart sous
   la carte que l'ancien bloc, avant l'ordre du jour. */
.pv-participants-carte { margin-bottom: 1.5rem; }
.pv-recap-filter.active { background: var(--color-primary); color: #fff; border-color: var(--color-primary); }

.pv-recap-stats {
    display: flex; gap: 1rem; flex-wrap: wrap;
    margin-bottom: .75rem; padding-bottom: .75rem;
    border-bottom: 1px solid var(--color-border);
}
.pv-recap-stat { font-size: .82rem; font-weight: 600; }
.pv-recap-stat--open   { color: var(--color-primary); }
.pv-recap-stat--closed { color: var(--color-success); }
.pv-recap-stat--total  { color: var(--color-muted); }

.pv-recap-list { display: flex; flex-direction: column; gap: .5rem; }
.pv-recap-item {
    display: flex; align-items: flex-start; gap: .75rem;
    padding: .6rem .75rem;
    border-radius: 8px;
    border: 1px solid var(--color-border);
    background: var(--color-surface);
}
.pv-recap-item--clos { opacity: .6; background: var(--color-surface-alt); }
.pv-recap-item--late { border-left: 3px solid var(--color-danger); }
.pv-recap-icon { font-size: 1rem; flex-shrink: 0; margin-top: .1rem; }
.pv-recap-body { flex: 1; min-width: 0; }
.pv-recap-desc { font-weight: 500; font-size: .88rem; margin-bottom: .2rem; }
.pv-recap-meta {
    display: flex; flex-wrap: wrap; gap: .5rem 1rem;
    font-size: .75rem; color: var(--color-muted);
}
.pv-recap-point { font-style: italic; }
.pv-recap-empty { padding: 1rem 0; }
.pv-recap-loading { color: var(--color-muted); font-size: .85rem; padding: .5rem 0; }
[data-theme="dark"] .pv-recap-item { background: var(--color-surface-alt); border-color: rgba(255,255,255,.08); }
[data-theme="dark"] .pv-recap-item--clos { background: rgba(255,255,255,.02); }

/* ── Courriers — Carnet d'adresses ── */
.cour-dest-table td { vertical-align: middle; }
.cour-dest-adresse { font-size: .82rem; }
.cour-dest-actions { white-space: nowrap; text-align: right; }

/* ── Courriers — Templates ── */
.cour-tpl-grid { display: flex; flex-direction: column; gap: .75rem; }
.cour-tpl-type-label {
    font-size: .75rem; font-weight: 700; text-transform: uppercase;
    letter-spacing: .06em; color: var(--color-muted);
    padding: .5rem 0 .25rem;
    border-bottom: 1px solid var(--color-border);
    margin-top: .5rem;
}
.cour-tpl-card-head {
    display: flex; align-items: center; gap: .75rem;
    flex-wrap: wrap;
}
.cour-tpl-card-nom { font-weight: 600; flex: 1; font-size: .95rem; }
.cour-tpl-card-btns { display: flex; gap: .4rem; align-items: center; }
.cour-tpl-card-objet { margin-top: .3rem; }
.cour-tpl-card-auteur { margin-top: .15rem; }

/* Éditeur Quill template */
.cour-tpl-editor {
    min-height: 220px;
    border: 1px solid var(--color-border);
    border-top: none;
    border-radius: 0 0 6px 6px;
    background: var(--color-surface);
    font-size: .9rem;
}

/* Boutons variables */
.cour-tpl-variables {
    display: flex; flex-wrap: wrap; gap: .3rem;
    align-items: center;
    margin-bottom: 0;
    padding: .5rem .75rem;
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border);
    border-bottom: none;
    border-radius: 6px 6px 0 0;
}
.cour-tpl-var-label {
    font-size: .72rem; color: var(--color-muted);
    margin-right: .25rem;
}
.cour-tpl-var-btn {
    font-size: .72rem; font-family: monospace;
    padding: 2px 7px;
    border-radius: 4px;
    border: 1px solid var(--color-border);
    background: var(--color-surface);
    cursor: pointer; color: var(--color-primary);
    transition: background .15s;
}
.cour-tpl-var-btn:hover {
    background: var(--color-primary-lt);
    border-color: var(--color-primary);
}

/* ── Courriers — Rédaction ── */
.cour-rediger-grid {
    display: grid;
    grid-template-columns: 280px 1fr;
    gap: 1.25rem;
    align-items: start;
}
.cour-rediger-sidebar { display: flex; flex-direction: column; gap: .75rem; }
/* Les trois champs de la colonne de rédaction d'un courrier : modèle,
   destinataire et date. Seule la largeur était posée ici ; les deux
   listes recevaient l'habillage général des select, le champ date rien
   du tout — il gardait l'apparence native du navigateur, cadre carré au
   milieu de champs arrondis (signalé par l'utilisateur). Le contexte
   pose donc son habillage complet, padding compris : c'est ce que la
   règle de base des select laisse volontairement à chaque contexte. */
.cour-sidebar-select {
    width: 100%;
    padding: .4rem .6rem;
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius);
    background: var(--color-surface);
    color: var(--color-text);
    font-family: var(--font);
    font-size: .9rem;
}
/* Devenu un <button> (il ouvre la fenêtre d'ajout au lieu d'un autre
   onglet) : on lui rend l'allure de lien qu'il avait. */
.cour-sidebar-link { font-size: .8rem; color: var(--color-primary); display: block; margin-top: .4rem;
    background: none; border: 0; padding: 0; text-align: left; cursor: pointer; font-family: inherit; }
.cour-sidebar-link:hover { text-decoration: underline; }
.cour-sidebar-actions { display: flex; flex-direction: column; gap: .5rem; }
.cour-btn-full { width: 100%; justify-content: center; }

.cour-dest-preview {
    font-size: .8rem;
    color: var(--color-muted);
    margin-top: .5rem;
    padding: .4rem .6rem;
    background: var(--color-surface-alt);
    border-radius: 6px;
    border: 1px solid var(--color-border);
    display: none;
    line-height: 1.6;
}
.cour-dest-preview:not(:empty) { display: block; }

.cour-sig-label {
    display: flex; align-items: center; gap: .5rem;
    padding: .35rem 0;
    cursor: pointer;
    font-size: .88rem;
}
.cour-sig-label input { flex-shrink: 0; accent-color: var(--color-primary); }

.cour-rediger-editor {
    min-height: 350px;
    border: 1px solid var(--color-border);
    border-top: none;
    border-radius: 0 0 6px 6px;
    font-size: .9rem;
    background: var(--color-surface);
}

@media (max-width: 768px) {
    .cour-rediger-grid { grid-template-columns: 1fr; }
    /* Sur une colonne, « Sauvegarder / Aperçu / Générer le PDF »
       arrivaient avant l'objet et le corps, qu'on rédige d'abord. La
       colonne de réglages se dissout (display: contents) pour que ses
       cartes et ses boutons se rangent séparément : réglages en tête (le
       modèle pré-remplit le corps), rédaction, puis les boutons. */
    .cour-rediger-sidebar { display: contents; }
    .cour-rediger-sidebar > .card { order: 1; }
    .cour-rediger-main { order: 2; }
    .cour-sidebar-actions { order: 3; }
}

/* ── Courriers — Historique ── */
/* Quatre tuiles depuis que les emails ont la leur : figée à trois
   colonnes, la quatrième tombait seule à la ligne. En auto-fit, elles
   tiennent de front sur ordinateur, se partagent la place plus bas, et
   une tuile ajoutée demain ne se retrouvera pas orpheline. */
.cour-stats-grid { grid-template-columns: repeat(auto-fit, minmax(170px, 1fr)); margin-bottom: 1.25rem; }
/* ── Formulaire de filtres (empile verticalement ses sections) ── */
.cour-filtres-form {
    display: flex;
    flex-direction: column;
    gap: .8rem;
    align-items: stretch;
}

/* Ligne principale : recherche + statut + boutons */
.cour-filtres-main {
    display: flex;
    flex-wrap: wrap;
    gap: .5rem;
    align-items: center;
    width: 100%;
}
.cour-search-input { flex: 1 1 240px; min-width: 180px; }

/* Panneau filtres avancés (toggle via .is-open) */
.cour-filtres-advanced {
    display: none;
    width: 100%;
    padding-top: .8rem;
    border-top: 1px dashed var(--color-border, #e5e7eb);
}
.cour-filtres-advanced.is-open { display: block; }

.cour-filtres-adv-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(180px, 1fr));
    gap: .75rem;
}
.cour-filtre-group {
    display: flex;
    flex-direction: column;
    gap: .25rem;
    min-width: 0;  /* permet aux selects longs de se contracter */
}
.cour-filtre-group label {
    font-size: .78rem;
    color: var(--color-muted, #64748b);
    font-weight: 600;
}
.cour-filtre-group select {
    width: 100%;
    padding: .4rem .5rem;
    border: 1px solid var(--color-border, #e5e7eb);
    border-radius: 5px;
    font-size: .85rem;
    background: var(--color-surface, #fff);
}

/* Ligne bouton Export CSV (aligné à droite, sur sa propre ligne) */
.cour-filtres-export {
    display: flex;
    justify-content: flex-end;
    width: 100%;
    padding-top: .6rem;
    border-top: 1px dashed var(--color-border, #e5e7eb);
}

/* Responsive : sur mobile, tout en pleine largeur et empilé */
@media (max-width: 600px) {
    .cour-filtres-main { gap: .4rem; }
    /* La recherche garde sa ligne (facile à toucher) ; le menu de statut
       et « Filtrer » partagent la suivante, les autres boutons celle
       d'après — au lieu de quatre lignes pleine largeur. */
    .cour-filtres-main .cour-search-input { flex: 1 1 100%; min-width: 0; }
    .cour-filtres-main select { flex: 1 1 55%; min-width: 0; }
    /* 30 % et non 0 : avec une base nulle, « Plus de filtres » se serrait
       lui aussi sur la ligne du menu de statut. */
    .cour-filtres-main .btn { flex: 1 1 30%; min-width: 0; justify-content: center; }
    .cour-filtres-adv-grid { grid-template-columns: 1fr; gap: .5rem; }
    .cour-filtres-export { justify-content: stretch; }
    .cour-filtres-export .btn { width: 100%; }
}
.cour-hist-table td { vertical-align: middle; }
.cour-hist-date { white-space: nowrap; font-size: .85rem; }
.cour-hist-auteur { font-size: .75rem; }
.cour-hist-objet { font-weight: 500; font-size: .88rem; }
.cour-hist-ref {
    display: inline-block;
    font-family: 'Courier New', monospace;
    font-size: .72rem;
    color: var(--color-muted, #64748b);
    background: var(--color-surface-alt, #f1f5f9);
    padding: 1px 6px;
    border-radius: 4px;
    margin-top: 3px;
    letter-spacing: .02em;
}
.cour-ref-banner {
    margin-bottom: 1rem;
    font-family: 'Courier New', monospace;
    letter-spacing: .02em;
}
.cour-hist-actions { white-space: nowrap; text-align: right; }
.cour-hist-actions .table-mobile-actions { display: inline-flex; gap: .35rem; align-items: center; }
/* Auteur et modèle sous l'objet : téléphone seulement, l'ordinateur les
   a en colonnes. */
.cour-hist-detail-mobile { display: none; }
/* Tuile dont la liste est affichée en dessous (même repère que Actions). */
.cour-stats-grid .cour-stat--active { border-color: var(--color-primary); box-shadow: 0 0 0 1px var(--color-primary); }

/* Tuiles qui filtrent la liste (Actions, Courriers) : rien ne disait
   qu'on pouvait les toucher — l'utilisateur ne les a pas repérées. Un
   « › » permanent, pas seulement au survol : le doigt ne survole pas. */
.actions-stats .stat-card--link,
.cour-stats-grid .stat-card--link { position: relative; padding-right: 1.4rem; }
.actions-stats .stat-card--link::after,
.cour-stats-grid .stat-card--link::after {
    content: '›'; position: absolute; right: .55rem; top: 50%; transform: translateY(-50%);
    font-size: 1.2rem; line-height: 1; color: var(--color-muted);
}
.actions-stats .stat-card--link:hover::after,
.cour-stats-grid .stat-card--link:hover::after { color: var(--color-primary); }
@media (max-width: 600px) {
    /* Libellé lisible : à .6rem, « ENVOYÉS » ne se remarquait pas. Après
       la règle des tuiles de courriers, qui l'écraserait sinon. */
    .cour-stats-grid .stat-card .stat-label { font-size: .68rem; }
}
@media (max-width: 768px) {
    .cour-hist-detail-mobile { display: block; font-size: .75rem; font-weight: 400; color: var(--color-muted); margin-top: .2rem; }
}

@media (max-width: 600px) {
    .cour-stats-grid { grid-template-columns: repeat(3, 1fr); gap: .35rem; }
    .cour-stats-grid .stat-card { padding: .5rem .4rem; }
    .cour-stats-grid .stat-value { font-size: 1.05rem; }
    .cour-stats-grid .stat-label { font-size: .6rem; }
}

/* ── Courrier — Modal Aperçu ── */
.cour-preview-modal {
    display: none;
    position: fixed; inset: 0;
    background: rgba(0, 0, 0, .55);
    z-index: 9000;
    overflow-y: auto;
    padding: 20px 0;
}
.cour-preview-modal.is-open { display: block; }
.cour-preview-modal-box {
    background: #fff;
    max-width: 820px;
    margin: 20px auto;
    border-radius: 12px;
    box-shadow: 0 20px 50px rgba(0, 0, 0, .25);
    display: flex;
    flex-direction: column;
    max-height: calc(100vh - 40px);
    overflow: hidden;
}
.cour-preview-modal-head {
    display: flex;
    justify-content: space-between;
    align-items: center;
    padding: 14px 20px;
    border-bottom: 1px solid var(--color-border, #e2e8f0);
    background: var(--color-surface-alt, #f8fafc);
}
.cour-preview-modal-head h2 {
    font-size: 1.05rem; font-weight: 600; margin: 0;
}
.cour-preview-modal-close {
    background: transparent; border: none;
    font-size: 1.5rem; cursor: pointer;
    color: var(--color-muted, #64748b);
    padding: 4px 10px; border-radius: 6px;
}
.cour-preview-modal-close:hover { background: rgba(0,0,0,.05); color: #000; }
.cour-preview-modal-body {
    flex: 1;
    overflow-y: auto;
    padding: 30px 40px;
    background: #f4f5f7;
}
.cour-preview-modal-foot {
    display: flex;
    justify-content: flex-end;
    flex-wrap: wrap;
    gap: 10px;
    padding: 12px 20px;
    border-top: 1px solid var(--color-border, #e2e8f0);
    background: #fff;
}
.cour-preview-loading {
    text-align: center;
    padding: 40px 20px;
    color: var(--color-muted, #64748b);
    font-style: italic;
}

/* Page de courrier simulée dans la modal */
.cour-preview-page {
    background: #fff;
    padding: 25mm 20mm 20mm 20mm;
    box-shadow: 0 2px 10px rgba(0, 0, 0, .08);
    border-radius: 4px;
    font-family: 'Times New Roman', Times, serif;
    font-size: 11pt;
    color: #1a1a1a;
    line-height: 1.5;
    min-height: 500px;
}
.cour-preview-header {
    display: flex;
    justify-content: space-between;
    gap: 10mm;
    margin-bottom: 6mm;
}
.cour-preview-expediteur { flex: 1; }
.cour-preview-asso-nom { font-size: 13pt; font-weight: bold; margin-bottom: 2pt; }
.cour-preview-asso-president { font-size: 10pt; color: #555; margin-bottom: 4pt; }
.cour-preview-asso-coords { font-size: 9.5pt; color: #555; line-height: 1.6; }
.cour-preview-destinataire {
    text-align: right;
    min-width: 60mm;
    margin-top: 28mm;
}
.cour-preview-dest-nom { font-weight: bold; font-size: 11pt; }
.cour-preview-dest-service { font-size: 10pt; color: #555; }
.cour-preview-dest-adresse { font-size: 10pt; line-height: 1.6; margin-top: 3pt; }
.cour-preview-dest-manquant {
    color: #dc2626;
    font-style: italic;
    font-family: sans-serif;
    font-size: 10pt;
}
.cour-preview-date {
    text-align: right;
    font-size: 10.5pt;
    color: #555;
    margin-bottom: 8mm;
}
.cour-preview-objet { margin-bottom: 8mm; font-size: 11pt; }
.cour-preview-objet strong { font-weight: bold; }
.cour-preview-sep {
    border: none;
    border-top: 1px solid #ccc;
    margin-bottom: 8mm;
}
.cour-preview-corps {
    font-size: 11pt;
    line-height: 1.7;
    text-align: justify;
    margin-bottom: 12mm;
}
.cour-preview-corps p { margin-bottom: 6pt; }
.cour-preview-corps ul, .cour-preview-corps ol { margin: 4pt 0 4pt 20pt; }
.cour-preview-corps .ql-indent-1 { padding-left: 30pt; }
.cour-preview-corps .ql-indent-2 { padding-left: 60pt; }
.cour-preview-corps .ql-indent-3 { padding-left: 90pt; }
.cour-preview-empty { color: #dc2626; font-style: italic; }
.cour-preview-signatures {
    display: flex;
    justify-content: space-around;
    flex-wrap: wrap;
    gap: 8mm;
    margin-top: 14mm;
    padding-top: 6mm;
    border-top: 1px solid #ccc;
}
.cour-preview-sig-block {
    text-align: center;
    min-width: 50mm;
}
.cour-preview-sig-title { font-size: 10pt; font-weight: bold; margin-bottom: 2pt; }
.cour-preview-sig-name { font-size: 10pt; color: #555; margin-bottom: 12mm; }
.cour-preview-sig-line {
    border-top: 1px solid #ccc;
    width: 50mm;
    margin: 0 auto;
}

@media (max-width: 768px) {
    .cour-preview-modal-box { margin: 0; max-height: 100vh; border-radius: 0; }
    .cour-preview-modal { padding: 0; }
    .cour-preview-modal-body { padding: 15px; }
    .cour-preview-page { padding: 15mm 10mm; }
    .cour-preview-header { flex-direction: column; gap: 10mm; }
    .cour-preview-destinataire { text-align: left; margin-top: 0; }
}

/* ── Users — Edit layout ── */
.usr-edit-layout {
    display: flex !important;
    flex-direction: row !important;
    gap: 1.25rem;
    align-items: flex-start;
}
.usr-edit-main { flex: 1; min-width: 0; }
.usr-edit-main .user-form { max-width: 100%; }
.usr-edit-sidebar { width: 320px; flex-shrink: 0; }
.usr-edit-sidebar .user-form { max-width: 100%; }

/*  Les trois actions tiennent dans une colonne de 320 px : à leur
    largeur naturelle, chacune passait à la ligne avec un bord droit
    différent — un escalier de trois boutons. Elles prennent la largeur
    de la carte, et gardent donc le même bord des deux côtés.
    Écrit sur .usr-edit-sidebar et non sur .usr-actions-row : la même
    rangée, posée un jour ailleurs qu'en colonne, doit continuer de se
    lire côte à côte. */
.usr-edit-sidebar .usr-actions-row { flex-direction: column; align-items: stretch; gap: .5rem; }
.usr-edit-sidebar .usr-actions-row > form { display: flex; }
.usr-edit-sidebar .usr-actions-row > form > .btn,
.usr-edit-sidebar .usr-actions-row > .btn { width: 100%; }

/*  Le bouton du bas de la carte de présence suit la même largeur : sans
    cela, les deux cartes de la colonne se terminent sur deux boutons de
    tailles différentes. */
.usr-edit-sidebar .user-form > .btn,
.usr-edit-sidebar .usr-danger-zone .btn { width: 100%; }

@media (max-width: 900px) {
    .usr-edit-layout { flex-direction: column !important; }
    .usr-edit-sidebar { width: 100%; }
    /*  Passée sous le formulaire, la colonne fait toute la largeur de la
        page : trois boutons étirés sur 900 px seraient pires que
        l'escalier. Ils reprennent leur largeur naturelle et tiennent sur
        une ligne. */
    .usr-edit-sidebar .usr-actions-row { flex-direction: row; align-items: center; gap: .75rem; }
    .usr-edit-sidebar .usr-actions-row > form > .btn,
    .usr-edit-sidebar .usr-actions-row > .btn,
    .usr-edit-sidebar .user-form > .btn,
    .usr-edit-sidebar .usr-danger-zone .btn { width: auto; }
}

/*  « form-hint » était posée sur les deux phrases d'explication du
    formulaire des comptes sans qu'aucune règle ne l'habille : elles
    s'affichaient à la taille du texte courant, plus grosses que les
    <small class="text-muted"> qui jouent le même rôle trois champs plus
    haut. */
.form-hint { display: block; margin-top: .4rem; font-size: .78rem; color: var(--color-muted); }
.form-hint[hidden] { display: none; }

/*  L'état du compte, en tête de la carte d'actions : ce qui explique
    qu'une personne n'arrive pas à se connecter se lit là, et non plus
    seulement dans la liste. */
.usr-etat { list-style: none; margin: 0 0 1.25rem; padding: 0; font-size: .82rem; }
.usr-etat li { padding: .15rem 0; color: var(--color-muted); }
.usr-etat li:first-child { color: var(--color-text); font-weight: 500; }

/*  La suppression est définitive : elle se détache des actions
    courantes par un filet, comme ailleurs sur le site. Bouton neutre
    au texte rouge plutôt qu'un aplat — il ne doit pas attirer la main
    qui vient pour les trois autres. */
.usr-danger-zone { margin-top: 1.25rem; padding-top: 1rem; border-top: 1px solid var(--color-border); }
.usr-danger-zone small { display: block; margin-top: .5rem; font-size: .72rem; }
.usr-btn-danger { color: var(--color-danger); border-color: var(--color-danger); }
.usr-btn-danger:hover { background: var(--color-danger-lt); }

/*  Sur téléphone la ligne ne tient plus : on revient à la pile pleine
    largeur, comme .page-actions ailleurs sur le site. Écrit après la
    media query ci-dessus, sinon elle l'annulerait. */
@media (max-width: 768px) {
    .usr-edit-sidebar .usr-actions-row { flex-direction: column; align-items: stretch; gap: .5rem; }
    .usr-edit-sidebar .usr-actions-row > form > .btn,
    .usr-edit-sidebar .usr-actions-row > .btn,
    .usr-edit-sidebar .user-form > .btn,
    .usr-edit-sidebar .usr-danger-zone .btn { width: 100%; }
}

/* ============================================================
   ── Nouveautés session paramètres + courriers ──────────────
   ============================================================ */

/* ── Groupe de boutons dans l'en-tête de page (harmonisation) ── */
.page-actions-btns {
    display: flex;
    flex-wrap: wrap;
    gap: .5rem;
    align-items: center;
}
/*  640 px et non 600 : c'est le seuil auquel .page-actions fait déjà
    passer ses boutons en pleine largeur. Deux seuils pour le même geste
    laissaient, entre les deux, une bande de quarante pixels où les
    boutons reprenaient leur largeur naturelle et finissaient en
    escalier — le défaut que les deux règles cherchent à éviter. */
@media (max-width: 640px) {
    .page-actions-btns {
        width: 100%;          /* occupe toute la largeur sous le h1 */
        gap: .4rem;
    }
    .page-actions-btns .btn {
        flex: 1 1 calc(50% - .2rem);  /* 2 boutons par ligne en mobile */
        min-width: 0;
        padding: .5rem .6rem;
        font-size: .82rem;
        justify-content: center;
        white-space: nowrap;
    }
    /* Si un seul bouton : pleine largeur */
    .page-actions-btns .btn:only-child {
        flex: 1 1 100%;
    }
}

/* ── Sommaire sticky en haut des pages paramètres ── */
.params-toc {
    position: sticky;
    top: calc(var(--header-h, 56px) + 8px);
    z-index: 10;
    display: flex;
    flex-wrap: wrap;
    gap: .5rem;
    padding: .6rem .9rem;
    margin-bottom: 1.25rem;
    background: var(--color-surface, #fff);
    border: 1px solid var(--color-border, #e5e7eb);
    border-radius: 8px;
    box-shadow: 0 2px 6px rgba(0,0,0,.04);
}
.params-toc a {
    font-size: .82rem;
    padding: .35rem .7rem;
    border-radius: 5px;
    color: var(--color-text, #1f2937);
    text-decoration: none;
    transition: background .15s;
    white-space: nowrap;
}
.params-toc a:hover {
    background: var(--color-primary-light, #eef3ff);
    color: var(--color-primary, #1d4ed8);
}
@media (max-width: 640px) {
    .params-toc {
        display: grid;
        grid-template-columns: repeat(2, 1fr);
        gap: .4rem;
    }
    .params-toc a {
        font-size: .78rem;
        padding: .4rem .5rem;
        text-align: center;
        white-space: normal;
    }
}

/* ── Boutons d'action dans l'en-tête de page ── */
.params-header-actions {
    display: flex;
    gap: .5rem;
    flex-wrap: wrap;
}
@media (max-width: 600px) {
    /* Même motif que .page-actions-btns : 2 boutons par ligne plutôt
       qu'empilés en pleine largeur, pour ne pas repousser le contenu. */
    .params-header-actions { width: 100%; gap: .4rem; }
    .params-header-actions .btn {
        flex: 1 1 calc(50% - .2rem);
        min-width: 0;
        padding: .5rem .6rem;
        font-size: .78rem;
        justify-content: center;
        text-align: center;
        white-space: normal;
        line-height: 1.25;
    }
    .params-header-actions .btn:only-child { flex: 1 1 100%; }
}

/* ── Photo couverture PDF : aperçu ── */
.params-photo-preview {
    max-width: 200px;
    max-height: 120px;
    object-fit: cover;
    border-radius: 6px;
}
.params-photo-placeholder {
    width: 120px;
    height: 72px;
    font-size: .78rem;
    color: var(--color-muted, #64748b);
}

/* ── Case à cocher avec petit texte sous le label ── */
.checkbox-label {
    display: flex;
    align-items: flex-start;
    gap: .5rem;
    cursor: pointer;
    font-weight: normal;
}
.checkbox-label input[type="checkbox"] {
    margin-top: .25rem;
    flex-shrink: 0;
}
/* Dans un .form-group, la règle des libellés (display: block, plus
   précise) repoussait le texte sous la case, seule sur sa ligne. */
.form-group .checkbox-label { display: flex; font-weight: normal; }
.checkbox-label strong { display: block; }
.checkbox-label small {
    display: block;
    font-size: .78rem;
    font-weight: normal;
    margin-top: .1rem;
}

/* ── Page sauvegarde : statistiques d'export ── */
.backup-stats {
    margin: 1rem 0 1.25rem;
    padding: 1rem;
    background: var(--color-bg, #f8f9fb);
    border: 1px solid var(--color-border, #e5e7eb);
    border-radius: 8px;
}
.backup-stats-title {
    font-weight: 600;
    margin-bottom: .6rem;
    font-size: .9rem;
}
.backup-stats-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
    gap: .5rem;
    margin-bottom: .6rem;
}
.backup-stat {
    display: flex;
    align-items: baseline;
    gap: .5rem;
    padding: .4rem .6rem;
    background: #fff;
    border: 1px solid var(--color-border, #e5e7eb);
    border-radius: 5px;
    font-size: .82rem;
}
.backup-stat-num {
    font-weight: 700;
    color: var(--color-primary, #1d4ed8);
    min-width: 2.5em;
    text-align: right;
}
.backup-stat-label {
    color: var(--color-muted, #64748b);
    font-family: var(--font-mono, monospace);
    font-size: .76rem;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.backup-stats-total {
    font-size: .85rem;
    color: var(--color-muted, #64748b);
    padding-top: .5rem;
    border-top: 1px dashed var(--color-border, #e5e7eb);
}

/* ── Page sauvegarde : résultat d'import ── */
.backup-import-result {
    margin-top: 1rem;
    padding: .9rem 1rem;
    background: var(--color-success-light, #e8f5e9);
    border-left: 3px solid var(--color-success, #4caf50);
    border-radius: 5px;
    font-size: .85rem;
}
.backup-import-title {
    font-weight: 600;
    margin-bottom: .4rem;
}
.backup-import-result ul { margin: 0; padding-left: 1.2rem; }
.backup-import-result li { margin: .15rem 0; }

/* ── Empty state : harmonisation sans inline style ── */
.cour-empty-body {
    padding: 2rem;
}

/* ── Écran de confirmation d'envoi d'un courrier ── */
.cour-envoye-box {
    text-align: center;
    padding: 2rem 1.5rem;
}
.cour-envoye-icon {
    font-size: 3rem;
    margin-bottom: .5rem;
}
.cour-envoye-title {
    font-size: 1.15rem;
    font-weight: 600;
    color: var(--color-success, #2e7d32);
    margin-bottom: .5rem;
}
.cour-envoye-ref {
    display: inline-block;
    margin: .5rem 0 1rem;
    padding: .5rem 1rem;
    background: var(--color-success-light, #e8f5e9);
    border-radius: 6px;
    font-size: .95rem;
}
.cour-envoye-ref strong {
    font-family: var(--font-mono, monospace);
    font-size: 1.1rem;
    color: var(--color-success, #2e7d32);
}
.cour-envoye-desc {
    color: var(--color-muted, #64748b);
    font-size: .9rem;
    margin: 1rem 0 1.5rem;
    line-height: 1.7;
}
.cour-envoye-actions {
    display: flex;
    gap: .6rem;
    justify-content: center;
    flex-wrap: wrap;
}
@media (max-width: 600px) {
    .cour-envoye-actions .btn {
        flex: 1 1 100%;
    }
}

/* ============================================================
   REPORT D'EXERCICE — soldes d'ouverture / clôture
   Utilisé par tresorerie/rapports.php et tresorerie/rapport_ag.php.
   Grille 3 colonnes alignée sur .rpt-summary et .ag-exec-grid.
   ============================================================ */

.exo-solde-grid {
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    gap: 1rem;
    margin-bottom: 1.75rem;
}

.exo-solde-card {
    border-radius: var(--radius-lg);
    padding: 1.1rem 1.25rem;
    text-align: center;
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border-strong);
}

/* Carte centrale : la variation, c'est le chiffre qu'on lit en premier */
.exo-solde-card--pivot {
    background: var(--color-primary-lt);
    border-color: var(--color-primary-mid);
}

.exo-solde-label {
    font-size: .68rem;
    text-transform: uppercase;
    letter-spacing: 1.5px;
    font-weight: 600;
    color: var(--color-muted);
    margin-bottom: .35rem;
}

.exo-solde-val {
    font-size: 1.35rem;
    font-weight: 800;
    color: var(--color-text);
}

.exo-solde-val--pos { color: var(--color-success); }
.exo-solde-val--neg { color: var(--color-danger); }

.exo-solde-note {
    font-size: .7rem;
    color: var(--color-muted);
    margin-top: .3rem;
}

.exo-solde-warn {
    font-size: .72rem;
    font-weight: 600;
    color: var(--color-danger);
    margin-top: .3rem;
}

@media (max-width: 700px) {
    .exo-solde-grid { grid-template-columns: 1fr; }
}


/* ══════════════════════════════════════════════════════════
   MODULE ÉCOLE ARABE — classes utilitaires
   ══════════════════════════════════════════════════════════ */

/* Barre de filtres : champs alignés horizontalement, qui passent
   à la ligne sur mobile. À ne pas confondre avec .form-group, qui
   empile libellé et champ dans les formulaires de saisie. */
.ecole-filters {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: .6rem;
    margin-bottom: .9rem;
}
.ecole-filters label {
    font-size: .85rem;
    color: var(--color-muted);
    margin: 0;
    white-space: nowrap;
}
.ecole-filters input[type="text"],
.ecole-filters input[type="date"],
.ecole-filters input[type="number"],
.ecole-filters select {
    width: auto;
    min-width: 8rem;
    padding: .4rem .6rem;
    font-size: .9rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius-sm, 6px);
    background: var(--color-surface);
    color: var(--color-text);
}
.ecole-filters input[type="checkbox"] { width: auto; min-width: 0; margin-right: .3rem; }

/* Bouton « retirer les filtres », ajouté par footer.php quand un filtre
   est actif. Teinté : c'est la sortie de secours d'une liste devenue
   incompréhensible parce qu'on a oublié un filtre posé trois écrans
   plus tôt — elle doit se repérer sans être lue. */
.filtres-retirer {
    white-space: nowrap;
    color: var(--color-danger);
    border-color: var(--color-danger);
}
.filtres-retirer:hover { background: var(--color-danger-lt); color: var(--color-danger); }

/* Champs qui se lisent ensemble (un âge de … à …, deux boutons
   symétriques) : ils restent sur une même ligne même quand le reste de
   la barre s'empile.
   Sur ordinateur, le groupe n'est qu'un morceau de la barre parmi les
   autres : il se met à la suite du tri et ne prend que la largeur de
   son contenu. Deux cases de deux chiffres étalées sur un tiers d'écran
   chacune donnaient à l'âge l'importance visuelle d'un champ principal
   qu'il n'a pas. Le partage de la largeur est un comportement de
   téléphone, il est déplacé dans la media query plus bas. */
.ecole-filters-groupe {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: .5rem;
    /* Un <form> peut servir de groupe (le canal d'une relance et son
       bouton) : la marge que le navigateur lui donne d'office le
       désalignerait des commandes voisines. */
    margin: 0;
}
.ecole-filters-groupe > label { flex: 0 0 auto; }
/* Assez large pour deux chiffres et les flèches du navigateur : le
   min-width de 8rem commun à la barre de filtres est pensé pour des
   menus déroulants, pas pour un âge. */
.ecole-filters .ecole-filters-groupe > input:not([type="checkbox"]):not([type="radio"]) {
    flex: 0 0 auto; width: 5.5rem; min-width: 0;
}
.ecole-filters .ecole-filters-groupe > .btn  { flex: 0 0 auto; min-width: 0; }
/* Une zone d'aperçu encore vide ne doit pas compter pour un intervalle
   dans une colonne flex : elle laissait un blanc avant qu'on ait
   choisi quoi que ce soit. */
.ecole-filters > div:empty { display: none; }
/* Dernier élément d'une carte : sa marge basse double le rembourrage
   de la carte et creuse un vide entre deux blocs successifs. */
.ecole-filters:last-child { margin-bottom: 0; }

/* Sur petit écran, un select et une recherche à moitié larges, coincés
   côte à côte, lisaient mal : un champ de saisie garde donc sa ligne à
   lui, pleine largeur, plus facile à toucher du pouce.
   Les BOUTONS, eux, se partagent la ligne qui reste. La barre était
   auparavant en flex-direction: column, qui donnait une ligne entière
   au moindre « Filtrer » de sept lettres — et deux lignes depuis que
   « Retirer les filtres » vient s'y ajouter. Le passage au retour à la
   ligne automatique (flex-wrap) laisse ce qui est court se regrouper,
   sans rien changer sur ordinateur. */
@media (max-width: 640px) {
    .ecole-filters { align-items: center; }
    .ecole-filters label { width: 100%; }
    .ecole-filters select,
    .ecole-filters input[type="text"],
    .ecole-filters input[type="date"],
    .ecole-filters input[type="number"] {
        flex: 1 1 100%; width: 100%; min-width: 0;
    }
    .ecole-filters .btn { flex: 1 1 auto; width: auto; justify-content: center; }
    /* … sauf à l'intérieur d'un groupe, dont c'est justement la raison
       d'être : ses champs se partagent une ligne. */
    .ecole-filters .ecole-filters-groupe { flex: 1 1 100%; width: 100%; }
    .ecole-filters .ecole-filters-groupe > label { width: auto; }
    /* Largeurs de base plutôt que zéro : au-delà de trois ou quatre
       éléments (le bouton « Retirer les filtres » n'apparaît que filtre
       actif), la ligne se coupe en deux au lieu d'écraser les cases
       jusqu'à l'illisible. */
    .ecole-filters .ecole-filters-groupe > input { flex: 1 1 4rem; width: auto; min-width: 3.5rem; }
    .ecole-filters .ecole-filters-groupe > .btn  { flex: 1 1 7rem; width: auto; }
}

/* Zone d'action d'un écran de liste : cocher des élèves, choisir une
   classe, valider. Elle est posée juste sous la barre de filtres et lui
   ressemblait trait pour trait — mêmes champs, même gris — alors que
   l'une ne change que ce qu'on voit et que l'autre inscrit des dizaines
   d'élèves dans une classe. Fond teinté, filet de couleur à gauche et
   intitulé en toutes lettres : on ne valide plus une affectation en
   croyant filtrer. */
.ecole-barre-action {
    margin-top: .4rem;
    padding: .7rem .9rem;
    background: var(--color-primary-lt);
    border: 1px solid var(--color-primary-mid);
    border-left: 3px solid var(--color-primary);
    border-radius: var(--radius-sm, 6px);
}
.ecole-barre-action-titre {
    margin: 0 0 .6rem;
    font-size: .85rem;
    font-weight: 600;
    color: var(--color-text);
}
/* Un avertissement placé dans l'encadré explique la commande qui suit :
   il ne doit pas y être collé, et .ecole-sub n'a pas de marge basse. */
.ecole-barre-action > p:not(.ecole-barre-action-titre) { margin: 0 0 .6rem; }
/* Deux commandes distinctes à la suite (recalculer, puis écraser le
   barème) : sans écart elles formeraient un seul bloc et l'intitulé de
   la seconde se lirait comme la fin de la première. */
.ecole-barre-action + .ecole-barre-action { margin-top: .9rem; }

/* Question posée au retour d'un message de relance. Elle n'apparaît
   qu'après un clic sur un bouton de contact : une question affichée en
   permanence finit par ne plus être lue. Grisée et non colorée — c'est
   une question, pas une alerte. */
.ecole-trace {
    margin: .75rem 0 0;
    padding: .7rem .9rem;
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border-strong);
    border-radius: var(--radius-sm, 6px);
}
/* Le navigateur masque déjà [hidden], mais une règle d'affichage posée
   plus loin suffirait à le rendre visible : on le redit ici. */
.ecole-trace[hidden] { display: none; }
.ecole-trace-q { margin: 0 0 .6rem; font-size: .9rem; }

/* Sous-ligne grise sous une valeur de tableau, et paragraphes
   explicatifs sous les titres. */
.ecole-sub {
    font-size: .8rem;
    line-height: 1.35;
    margin: .15rem 0 0;
}

/* Formulaire d'une seule action, glissé dans une cellule de tableau
   à côté d'un autre bouton. */
.ecole-inline { display: inline-block; margin: 0; }

/* Groupe de boutons d'action dans une cellule. */
.ecole-actions { white-space: nowrap; }
.ecole-actions > * { display: inline-block; vertical-align: middle; margin-right: .25rem; }

/* Sur petit écran, le titre de l'en-tête et ses boutons d'action ne
   tiennent plus sur une seule ligne : ils débordaient hors de l'écran
   plutôt que de passer à la ligne. On les empile à la place. */
@media (max-width: 640px) {
    .card-header:has(.ecole-actions) { flex-wrap: wrap; row-gap: .5rem; }
    /* Plusieurs boutons de couleurs différentes, entassés en vrac sur
       une ligne trop étroite, lisaient comme un fouillis. Une colonne
       nette, un bouton par ligne, est plus calme et plus facile à
       toucher du pouce. */
    .card-header:has(.ecole-actions) .ecole-actions {
        white-space: normal; width: 100%;
        display: flex; flex-direction: column; gap: .4rem;
    }
    /* display:flex explicite : sans lui, la règle .ecole-actions > *
       plus haut (display:inline-block, même niveau de priorité mais
       écrite après .btn) l'emportait. Un <button> reste centré par
       défaut même sans flexbox, un lien <a> non — d'où le lien
       "Relancer" qui partait à gauche alors que les vrais boutons
       restaient centrés. */
    .card-header:has(.ecole-actions) .ecole-actions > * {
        display: flex; justify-content: center;
        margin: 0; width: 100%;
    }
}

/* Bloc masqué au chargement, révélé par JavaScript. */
.ecole-form-cache { display: none; }

/* Boutons en pied de modale : alignés à droite, séparés du contenu.
   Sans cette règle ils se collent au dernier champ. */
.modal-actions {
    display: flex;
    justify-content: flex-end;
    gap: .6rem;
    margin-top: 1.4rem;
    padding-top: 1rem;
    border-top: 1px solid var(--color-border);
}
.modal-actions .btn { min-width: 6rem; }
/*  Sur téléphone, les deux boutons du bas se partagent la largeur au lieu
    de se serrer à droite : « 📧 Envoyer à 21 membre(s) » ne tient pas à
    côté d'« Annuler » à 375 px, et l'un des deux passait à la ligne, seul
    et aligné à droite. Vaut pour toutes les fenêtres du site. */
@media (max-width: 768px) {
    .modal-actions { flex-wrap: wrap; }
    .modal-actions > .btn { flex: 1 1 calc(50% - .3rem); min-width: 0; justify-content: center; }
}

/* Badges manquants, sur le modèle des existants. */
.badge-info      { background: var(--color-info-lt);    color: var(--color-info); }
.badge-success   { background: var(--color-success-lt); color: var(--color-accent-dk); }
.badge-warning   { background: #fef3c7;                 color: #92400e; }
.badge-secondary { background: var(--color-surface-alt); color: var(--color-muted); }
[data-theme="dark"] .badge-warning { background: #422006; color: #fcd34d; }

/* ═══════════════════════════════════════════════════
   ÉCOLE — CARTES PLIABLES ET ACTIONS DE LIGNE
   ═══════════════════════════════════════════════════ */

/* Une carte pliable est un <details>, pas un bloc piloté par du
   JavaScript : l'état ouvert/fermé est tenu par le navigateur, il
   survit au rechargement de la page sans code, et la carte reste
   lisible même si le script ne part pas. */
.ecole-pliable { display: block; }

/* Le <summary> reste en display:block et c'est un enfant qui porte le
   flex : Safari, sur iOS notamment, gère mal un summary passé en
   display:flex — le marqueur revient, et sur les versions anciennes le
   pli cesse de s'ouvrir. */
.ecole-pliable > summary {
    padding: .85rem 1.25rem;
    border-bottom: 1px solid var(--color-border);
    cursor: pointer;
    list-style: none;
    transition: background var(--transition);
}
.ecole-pliable-entete {
    display: flex; align-items: center; justify-content: space-between;
    gap: .75rem;
}
/* Le triangle par défaut du navigateur, retiré des deux côtés : on
   pose le nôtre, aligné avec le titre. */
.ecole-pliable > summary::-webkit-details-marker { display: none; }
.ecole-pliable > summary::marker { content: ''; }
.ecole-pliable > summary:hover { background: var(--color-surface-alt); }

/* Repliée, la carte n'a plus de contenu sous son en-tête : la bordure
   basse deviendrait un trait dans le vide. */
.ecole-pliable:not([open]) > summary { border-bottom: none; }

.ecole-pliable-titre {
    display: flex; align-items: center; gap: .5rem;
    font-size: .95rem; font-weight: 600; margin: 0;
    /* Le titre porte aussi ce qui doit rester lisible carte repliée —
       un décompte, un montant en retard, un badge de relance. Sur un
       téléphone, trois badges à la suite d'un nom de famille sortent
       de l'écran s'ils ne peuvent pas passer à la ligne. */
    flex-wrap: wrap;
}
/*  Le libellé, quand il est long.

    Un en-tête est une rangée en flex-wrap, et flexbox décide de passer
    un élément à la ligne d'après sa largeur de CONTENU, avant toute
    réduction. « 💰 En caisse, toutes années scolaires confondues » ne
    tenant pas à côté du chevron, il partait sur sa propre ligne, le
    montant sur une troisième : le chevron se retrouvait seul en haut.

    flex-basis à zéro règle exactement ça — l'élément ne pèse plus rien
    au moment du calcul de la ligne, donc rien ne casse, puis il grandit
    dans la place restante et se replie tout seul à l'intérieur.
    min-width: 0 parce qu'un élément flex refuse par défaut de descendre
    sous la largeur de son plus long mot.

    À poser sur tout en-tête dont le libellé peut s'allonger ; ceux qui
    tiennent en deux mots s'en passent, un texte nu s'y comporte bien. */
.ecole-pliable-libelle { flex: 1 1 0; min-width: 0; }
.ecole-pliable-chevron {
    font-size: .7rem; color: var(--color-muted);
    transition: transform .2s; transform: rotate(-90deg);
    display: inline-block;
}
.ecole-pliable[open] .ecole-pliable-chevron { transform: rotate(0); }
/* Replis imbriqués (un bloc d'option contient le repli de ses élèves
   déjà placés) : la règle ci-dessus atteint TOUS les chevrons contenus,
   y compris ceux des replis fermés, qui pointaient alors vers le bas en
   annonçant le contraire de leur état. Un chevron suit le repli le plus
   proche de lui. Plus spécifique et écrite après, donc elle l'emporte. */
.ecole-pliable:not([open]) > summary .ecole-pliable-chevron { transform: rotate(-90deg); }

/* Bouton « Tout déplier », ajouté par footer.php devant un groupe de
   cartes pliables. Contrairement à celui des tableaux repliables, il
   sert aussi sur ordinateur : une liste de vingt familles se parcourt
   mal repliée quel que soit l'écran. */
.ecole-pliable-toggle-all { display: inline-flex; margin: 0 0 .75rem; }

/* ══ Les élèves déjà placés d'une option, repliés ══
   Le même mécanisme que les cartes pliables, mais ce n'en est pas une :
   c'est une ligne discrète sous un tableau. Elle reprend donc le retrait
   du tableau au lieu du rembourrage d'un en-tête de carte, et son titre
   le poids du texte courant — ce qui compte ici est le décompte, pas le
   titre. Écrit APRÈS .ecole-pliable, dont il surcharge deux valeurs. */
.ecole-pliable.ecole-opt-places {
    margin: .25rem 0 1rem;
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    background: var(--color-surface-alt);
}
.ecole-pliable.ecole-opt-places > summary { padding: .5rem .75rem; }
.ecole-pliable.ecole-opt-places .ecole-pliable-titre {
    font-size: .85rem; font-weight: 500; color: var(--color-muted);
}
/* Ouverte, le tableau qu'elle contient ne colle pas à ses bords. */
.ecole-pliable.ecole-opt-places[open] > .table-responsive { padding: 0 .75rem .5rem; }

/* Le décompte reste visible carte repliée : sans lui, replier revient
   à cacher l'information au lieu de la ranger. */
.ecole-pliable-compte {
    font-weight: 400; color: var(--color-muted); font-size: .78rem;
}

/* Boutons d'action d'une ligne de tableau, sur UNE seule rangée.
   Empilés verticalement ils doublaient la hauteur de chaque ligne du
   tableau des groupes. */
.ecole-actions-row {
    display: flex; align-items: center; justify-content: flex-end;
    gap: .3rem; flex-wrap: nowrap; white-space: nowrap;
}
.ecole-actions-row form { display: inline-flex; margin: 0; }
.ecole-actions-row .btn { padding: .3rem .55rem; }

/* Sur une CELLULE de tableau, surtout pas display:flex.
   Un <td> passé en conteneur flex sort de la mise en page du tableau :
   il ne s'étire plus à la hauteur de la rangée, et sa bordure basse se
   dessine à sa propre hauteur — d'où un trait de séparation décalé sous
   la colonne des boutons, alors qu'il est aligné partout ailleurs.
   La cellule reste donc une vraie cellule ; ce sont ses enfants qui
   s'alignent, en inline-flex. */
td.ecole-actions-row {
    display: table-cell;
    vertical-align: middle;
    text-align: right;
    white-space: nowrap;
}
td.ecole-actions-row > * {
    display: inline-flex;
    vertical-align: middle;
    margin-left: .3rem;
}
td.ecole-actions-row > *:first-child { margin-left: 0; }

/* Bouton réduit à son icône : carré, pour que quatre d'entre eux
   s'alignent sans que la colonne ne pousse le tableau. */
.ecole-btn-ico {
    min-width: 2rem; text-align: center; line-height: 1.2;
}

/* Menu « plus d'actions » d'une ligne (classe, cours...) : les actions
   secondaires restent accessibles sans multiplier les boutons visibles.
   Repris du motif .cour-pdf-dropdown des courriers. position: absolute
   sur le menu, position: relative sur son conteneur : sur iOS Safari,
   dans une table en overflow-x: auto, un menu mal positionné se fait
   rogner par le défilement horizontal. */
.ecole-menu { position: relative; display: inline-block; }
.ecole-menu-list {
    display: none;
    position: absolute;
    top: calc(100% + 4px);
    right: 0;
    background: var(--color-surface);
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    box-shadow: var(--shadow-md);
    z-index: 200;
    min-width: 220px;
    overflow: hidden;
}
.ecole-menu-list.open { display: block; }
/* Une carte coupe ce qui dépasse d'elle (overflow: hidden, pour que son
   contenu épouse ses coins arrondis). Le panneau d'un menu ouvert sur
   l'une des dernières lignes d'un tableau était donc tronqué au bord de
   la carte — les sections de la page Classes en sont toutes. On ne lève
   la coupure que le temps où un menu est ouvert : le reste du temps, la
   carte garde ses coins nets. Sans :has() (navigateur ancien), rien ne
   change par rapport à avant. */
.card:has(.ecole-menu-list.open) { overflow: visible; }
/*  Même coupure, même remède, pour les deux cadres qui portent un point de
    l'ordre du jour : ils coupent ce qui dépasse d'eux pour garder leurs
    coins arrondis, et rognaient donc le panneau « Qui s'en occupe ? » à
    deux lignes. La coupure n'est levée que le temps où un panneau est
    ouvert. À refaire pour tout conteneur en overflow: hidden qui reçoit un
    jour un menu. */
.pv-point:has(.ecole-menu-list.open),
.point-card:has(.ecole-menu-list.open) { overflow: visible; }
.ecole-menu-list > a,
.ecole-menu-list > button,
.ecole-menu-list form > button {
    display: flex; align-items: center; gap: .5rem; width: 100%;
    padding: .55rem .75rem; background: none; border: none;
    color: var(--color-text); text-decoration: none; text-align: left;
    font-size: .85rem; font-family: inherit; cursor: pointer;
    border-bottom: 1px solid var(--color-border);
}
.ecole-menu-list form:last-child > button,
.ecole-menu-list > a:last-child,
.ecole-menu-list > button:last-child { border-bottom: none; }
.ecole-menu-list > a:hover,
.ecole-menu-list > button:hover,
.ecole-menu-list form > button:hover { background: var(--color-surface-alt); }
/* Un <form> dans .ecole-actions-row est ailleurs mis en
   display: inline-flex (bouton compact sur la même ligne) — mais ici
   le formulaire est une ligne de menu, pas un bouton de rangée, il lui
   faut retrouver un display normal pour occuper toute la largeur. */
.ecole-menu-list form { display: block; margin: 0; }
/* Ligne destructrice d'un menu. Deux classes dans le sélecteur : la
   règle « .ecole-menu-list form > button » ci-dessus, plus précise
   qu'une classe seule, remettait sinon la couleur du texte — c'est ce
   qui laissait en noir le « Supprimer définitivement » d'Utilisateurs. */
.ecole-menu-list .ecole-menu-danger,
.ecole-menu-list .usr-menu-danger { color: var(--color-danger); }

/* Sur petit écran la rangée passe à la ligne plutôt que de forcer un
   défilement horizontal sur toute la table. */
@media (max-width: 640px) {
    .ecole-actions-row { flex-wrap: wrap; justify-content: flex-start; }
    /* La cellule n'étant pas flex, c'est le retour à la ligne du texte
       qu'on réautorise ici. */
    td.ecole-actions-row { white-space: normal; }
    /* Dans l'en-tête d'une carte pliable, les boutons partagent sinon
       la ligne avec le titre : à l'étroit, ils tombent l'un sous
       l'autre au lieu de rester côte à côte. Toute la largeur de la
       carte, sur leur propre ligne, ils s'alignent normalement. */
    .ecole-pliable-entete { flex-wrap: wrap; }
    .ecole-pliable-entete > .ecole-actions-row { flex-basis: 100%; justify-content: flex-end; }
    /* Repliée, une carte avec boutons se retrouvait plus haute qu'une
       carte sans bouton (ex. Enseignants vs Groupes) : la liste des
       cartes perdait son rythme. Les boutons ne servent qu'une fois
       la carte ouverte — ils n'ont pas à peser sur la vue repliée.
       Le sélecteur vise tout enfant qui n'est pas le titre : certains
       en-têtes n'ont qu'un bouton isolé, sans passer par
       .ecole-actions-row. */
    .ecole-pliable:not([open]) .ecole-pliable-entete > *:not(.ecole-pliable-titre) { display: none; }
}

/* Grille de la semaine type : une colonne par jour d'ouverture. Les
   colonnes se partagent la largeur à égalité, sinon un samedi chargé
   écrase un mercredi à un seul groupe. */
.ecole-semaine { table-layout: fixed; }
.ecole-semaine td { vertical-align: top; }
/* Sur mobile, une grille jour × créneaux ne se lit plus une fois les
   colonnes trop étroites pour leur contenu (essayé avec une largeur
   minimale : le contenu débordait d'une colonne sur l'autre). Une
   liste par jour, empilée, reste lisible à n'importe quelle largeur. */
.ecole-semaine-liste { display: none; }
@media (max-width: 768px) {
    .table-responsive:has(.ecole-semaine) { display: none; }
    .ecole-semaine-liste { display: block; }
}
.ecole-semaine-jour { margin-bottom: 1.25rem; }
.ecole-semaine-jour:last-child { margin-bottom: 0; }
.ecole-semaine-jour-titre {
    font-size: .78rem; font-weight: 600; text-transform: uppercase;
    letter-spacing: .04em; color: var(--color-text-tertiary);
    margin: 0 0 .5rem;
}
.ecole-semaine-case {
    border-left: 3px solid var(--color-primary);
    padding: .35rem .5rem;
    margin-bottom: .5rem;
    background: var(--color-surface-alt);
    border-radius: 0 var(--radius) var(--radius) 0;
}
.ecole-semaine-case:last-child { margin-bottom: 0; }

/* En-têtes de colonne cliquables. Ils doivent se distinguer d'un
   en-tête ordinaire — sinon personne ne devine qu'on peut cliquer —
   sans pour autant ressembler à un lien de navigation. */
.ecole-tri {
    color: inherit; text-decoration: none;
    border-bottom: 1px dotted var(--color-border);
}
.ecole-tri:hover { color: var(--color-primary); border-bottom-color: var(--color-primary); }
.ecole-tri-actif { color: var(--color-primary); font-weight: 600; border-bottom: none; }

/* ══ La fenêtre de répartition d'un groupe ══
   Elle a remplacé une carte qui s'insérait entre « Groupes » et
   « Cours en option » : la page entière se réorganisait pour montrer un
   seul groupe. Plus large que les autres fenêtres, parce qu'elle porte
   un tableau — élève, âge, famille, sa classe, et le menu de
   déplacement — et non un formulaire en colonne. */
.modal-box--repartition { max-width: 900px; }

/* Son ✕ est un lien et non un bouton : la fenêtre étant rendue par le
   serveur, elle doit aussi se refermer sans JavaScript. Il reprend donc
   l'allure du bouton qu'il remplace. */
a.modal-close { text-decoration: none; line-height: 1; }

/* Les actions qui suivent le groupe regardé (liste, feuille d'appel,
   prévenir), sur la même ligne que ses créneaux. */
.ecole-rep-infos {
    display: flex; flex-wrap: wrap; align-items: center; gap: .5rem;
    margin-bottom: .75rem;
}

/* Sur téléphone la fenêtre prend tout l'écran : à 375 px, une fenêtre
   centrée avec ses marges ne laisse pas la place d'un tableau, et
   répartir une classe est de toute façon un travail qu'on fait assis.
   Écrit APRÈS la règle de base, sans quoi elle l'écraserait. */
@media (max-width: 768px) {
    .modal-overlay:has(.modal-box--repartition) { padding: 0; }
    .modal-box--repartition {
        max-width: none; width: 100%;
        max-height: 100vh; min-height: 100vh;
        border-radius: 0;
    }
}

/* Cours en option : mêmes créneaux, même feuille d'appel qu'une classe,
   mais ils ne comptent pas dans les places. Un liseré distinct dans la
   semaine type évite de les lire comme des classes. */
.ecole-semaine-option { border-left-color: var(--color-info); }

/* ══ Un bloc par option, encadré et repliable ══
   Les options se suivaient sans séparation : deux tableaux de cours et
   deux listes d'élèves d'affilée, sans savoir où l'une finissait. Le
   cadre et le filet de gauche délimitent, le repli isole.

   Le filet est de la même teinte pour toutes les options, et non une
   couleur par option : le nom est écrit juste à côté, la couleur n'a
   pas à l'identifier — elle dit seulement où le bloc commence et
   s'arrête. C'est la teinte déjà donnée aux cours d'option dans la
   semaine type (.ecole-semaine-option), pour qu'ils se reconnaissent
   d'un écran à l'autre.
   Écrit APRÈS .ecole-pliable, dont il surcharge le rembourrage. */
.ecole-pliable.ecole-option-bloc {
    margin: 0 0 1.25rem;
    border: 1px solid var(--color-border);
    border-left: 3px solid var(--color-info);
    border-radius: var(--radius);
    overflow: hidden;              /* le filet suit les coins arrondis */
}
.ecole-pliable.ecole-option-bloc > summary {
    padding: .7rem 1rem;
    background: var(--color-surface-alt);
}
.ecole-pliable.ecole-option-bloc:not([open]) > summary { border-bottom: none; }

/* Le contenu retraité sous son en-tête : c'est l'indentation qui dit
   « tout ceci appartient à cette option ». */
.ecole-option-corps { padding: .9rem 1rem 1rem; }

/* Sur téléphone, la place manque pour un retrait de chaque côté : le
   cadre et le filet suffisent à délimiter. */
@media (max-width: 768px) {
    .ecole-option-corps { padding: .75rem .5rem .75rem; }
    .ecole-pliable.ecole-option-bloc > summary { padding: .7rem .6rem; }
}

/* Tuiles adhérents : effectif au-dessus, retards en dessous. Deux
   liens dans une même carte — d'où le conteneur en <div>, un <a> dans
   un <a> étant invalide. */
.adh-stat-lien {
    display: block; text-decoration: none; color: inherit;
    border-radius: var(--radius); transition: opacity .15s;
}
.adh-stat-lien:hover { opacity: .75; text-decoration: none; }

.adh-stat-retard {
    display: block; margin-top: .5rem; padding-top: .45rem;
    border-top: 1px solid var(--color-border);
    font-size: .78rem; font-weight: 600;
    color: var(--color-warning); text-decoration: none;
}
a.adh-stat-retard:hover { text-decoration: underline; }

/* « Tous à jour » n'est pas cliquable : il n'y a rien à filtrer. */
.adh-stat-retard--ok { color: var(--color-muted); font-weight: 500; }

/* ══════════════════════════════════════════════════════════
   IMPORT DE LISTE (École arabe) — ecole/import_eleves.php
   Aperçu en tableau compact plutôt qu'une carte par famille (le
   même principe que le rapprochement bancaire de trésorerie,
   .mk-table) : sur un fichier de rentrée à 50-100 familles, une
   carte pleine hauteur par famille ne laissait voir que 2-3 lignes
   à l'écran.
   ══════════════════════════════════════════════════════════ */
.imp-table td { vertical-align: top; padding: .55rem .7rem; }
.imp-td-famille { min-width: 140px; }
.imp-famille-nom { font-weight: 600; font-size: .86rem; }
.imp-td-famille .badge { display: inline-block; margin-top: .25rem; font-size: .62rem; }
.imp-note-herite { font-size: .68rem; color: var(--color-muted); margin-top: .2rem; cursor: help; }

.imp-td-adherent { min-width: 280px; }
.imp-select { width: 100%; max-width: 440px; font-size: .8rem; padding: .28rem .4rem; }
.imp-actions { display: flex; gap: .3rem; flex-wrap: wrap; margin-top: .3rem; align-items: center; }
.imp-actions input[type="text"] { flex: 1; min-width: 140px; font-size: .76rem; padding: .22rem .4rem; }
.imp-actions .btn { font-size: .7rem; padding: .22rem .5rem; }
.imp-manuel-note { font-size: .7rem; color: var(--color-muted); margin-top: .25rem; }
.imp-diff { font-size: .72rem; margin-top: .3rem; }
.imp-diff label { display: block; margin-bottom: .1rem; font-weight: 400; }
.imp-p2 { font-size: .74rem; margin-top: .35rem; padding-top: .3rem; border-top: 1px dashed var(--color-border); }
.imp-p2-conflit { display: block; color: var(--color-warning); margin-bottom: .15rem; }

.imp-td-enfants { min-width: 170px; }
.imp-enfant { display: block; font-size: .78rem; line-height: 1.55; white-space: nowrap; }

.imp-row--warn td { background: var(--color-warning-lt); }

@media (max-width: 768px) {
    .imp-select { max-width: 100%; }
    .imp-td-famille, .imp-td-adherent, .imp-td-enfants { min-width: 0; }
}

/* Zone de dépôt du fichier — même motif que .rp-upload-zone
   (tresorerie/rapprochement.php), sous son propre préfixe de module. */
.imp-upload-zone {
    display: flex; flex-direction: column; align-items: center; justify-content: center;
    gap: .75rem; padding: 2.5rem; border: 2px dashed var(--color-border);
    border-radius: var(--radius-lg); cursor: pointer; text-align: center;
    transition: border-color .2s, background .2s; background: var(--color-surface-alt);
}
.imp-upload-zone--drag { border-color: var(--color-primary); background: rgba(201,168,76,.08); }
.imp-upload-icon       { font-size: 2.5rem; }
.imp-upload-filename   { font-size: .8rem; color: var(--color-primary); font-weight: 600; }

/* ══════════════════════════════════════════════════════════
   APPEL (École arabe) — ecole/appel.php

   Le seul écran qu'un compte Enseignant peut ouvrir, et il s'utilise
   debout, téléphone en main, devant une classe. D'où trois partis
   pris qui ne se retrouvent nulle part ailleurs dans ce fichier :

   · les trois états sont des BOUTONS, pas une liste déroulante. Un
     menu demande deux gestes et cache le choix des autres élèves ;
   · ils sont COLORÉS (vert / ambre / rouge). On relit une colonne de
     pointage du coin de l'œil, pour trouver ce qui manque ;
   · rien n'est coché à l'ouverture, y compris visuellement — l'état
     « non renseigné » doit se voir, c'est ce qu'on vient compléter.

   Le style par défaut est celui de l'ordinateur ; l'empilement est
   dans la media query. Une classe de trente élèves sur un écran large
   doit rester une ligne par élève, pas trois.
   ══════════════════════════════════════════════════════════ */

/* Le choix de la séance : libellé et champ côte à côte. Le <span>
   remplace un <label for> — le champ est DANS le label, c'est lui qui
   porte l'association. */
.ecole-appel-champ { display: flex; align-items: center; gap: .45rem; }
.ecole-appel-champ > span {
    font-size: .85rem; color: var(--color-muted); white-space: nowrap;
}

.ecole-appel-entete { display: flex; align-items: center; justify-content: space-between; gap: .75rem; }

.ecole-appel-liste { list-style: none; margin: 0; padding: 0; }

.ecole-appel-eleve {
    display: flex; align-items: center; gap: .75rem;
    padding: .45rem 0;
    border-bottom: 1px solid var(--color-border);
}
.ecole-appel-eleve:last-child { border-bottom: none; }

.ecole-appel-nom { flex: 1; min-width: 0; font-size: .92rem; font-weight: 500; }

/* Un élève parti reste pointable mais ne doit pas se confondre avec
   les autres : il ne vient plus, et le pointer absent chaque semaine
   n'apprendrait rien à personne. */
.ecole-appel-eleve--parti .ecole-appel-nom { color: var(--color-muted); font-weight: 400; }

/* ── Les trois états ──
   Les <input> sont retirés de l'affichage sans être retirés du
   document : ils gardent le clavier et les lecteurs d'écran, alors
   qu'un display:none les aurait rendus inatteignables autrement qu'à
   la souris. */
.ecole-appel-statut { display: flex; gap: .25rem; flex-shrink: 0; }
.ecole-appel-statut input[type="radio"] {
    position: absolute; width: 1px; height: 1px;
    opacity: 0; pointer-events: none;
}
.ecole-appel-opt {
    display: inline-flex; align-items: center; justify-content: center;
    min-height: 2.1rem; padding: .3rem .7rem;
    font-size: .82rem; font-weight: 500; line-height: 1;
    color: var(--color-muted);
    background: var(--color-surface-alt);
    border: 1px solid var(--color-border);
    border-radius: var(--radius);
    cursor: pointer; user-select: none;
    transition: background var(--transition), color var(--transition), border-color var(--transition);
    margin: 0;
}
.ecole-appel-opt:hover { border-color: var(--color-border-strong); }

/* Le « — » est un choix comme les autres : il efface une croix posée
   par erreur. Étroit, parce qu'on le cherche rarement. */
.ecole-appel-opt--vide { min-width: 2.4rem; padding: .3rem .4rem; }

.ecole-appel-statut input:checked + .ecole-appel-opt--present {
    background: var(--color-accent-lt); border-color: var(--color-accent);
    color: var(--color-accent-dk); font-weight: 600;
}
.ecole-appel-statut input:checked + .ecole-appel-opt--retard {
    background: var(--color-warning-lt); border-color: var(--color-warning);
    color: var(--color-warning); font-weight: 600;
}
.ecole-appel-statut input:checked + .ecole-appel-opt--absent {
    background: var(--color-danger-lt); border-color: var(--color-danger);
    color: var(--color-danger); font-weight: 600;
}
.ecole-appel-statut input:checked + .ecole-appel-opt--vide {
    background: var(--color-surface-alt); border-color: var(--color-border-strong);
    color: var(--color-text-tertiary);
}
/* Le contour de focus vit sur le libellé, l'input étant invisible :
   sans ça, parcourir la liste au clavier n'affiche plus rien. */
.ecole-appel-statut input:focus-visible + .ecole-appel-opt {
    outline: 2px solid var(--color-ecole); outline-offset: 2px;
}

/* ── « prévenu » ──
   Grisée plutôt que masquée quand elle n'a pas de sens : la faire
   apparaître et disparaître changerait la hauteur de la ligne à
   chaque clic, et la liste sauterait sous le doigt. */
.ecole-appel-excuse {
    display: flex; align-items: center; gap: .3rem;
    flex-shrink: 0; width: 6rem;
    font-size: .78rem; color: var(--color-muted); margin: 0;
    cursor: pointer;
}
.ecole-appel-excuse input { width: auto; margin: 0; }
.ecole-appel-excuse.is-off { opacity: .3; cursor: default; }

.ecole-appel-pied {
    display: flex; align-items: center; justify-content: space-between;
    gap: .75rem; flex-wrap: wrap;
}

/* ── Téléphone ──
   Le nom passe au-dessus, et les trois états se partagent la largeur :
   c'est la seule façon d'avoir des cibles qu'on touche sans viser.
   Rien de tout cela ne s'applique sur ordinateur, où la ligne unique
   permet d'embrasser la classe entière d'un regard. */
@media (max-width: 640px) {
    .ecole-appel-eleve {
        flex-wrap: wrap;
        align-items: stretch;
        padding: .6rem 0;
    }
    .ecole-appel-nom { flex: 1 0 100%; margin-bottom: .4rem; }
    .ecole-appel-statut { flex: 1; }
    .ecole-appel-opt { flex: 1; min-height: 2.5rem; padding: .3rem .35rem; }
    .ecole-appel-opt--vide { flex: 0 0 2.6rem; }
    .ecole-appel-excuse { width: auto; padding-left: .5rem; }
    .ecole-appel-champ { flex: 1 0 100%; }
    .ecole-appel-champ select,
    .ecole-appel-champ input[type="date"] { flex: 1; min-width: 0; }
    .ecole-appel-pied .btn { flex: 1 0 100%; }
}

/* ── Assiduité — fiche famille (ecole/fiche.php) ──
   Un bloc par enfant plutôt qu'un tableau : la liste des dates
   manquées a besoin de toute la largeur, et .table-mobile aurait
   découpé le bloc en deux cartes sur téléphone. */
.ecole-assid-bloc {
    padding: .8rem 0;
    border-bottom: 1px solid var(--color-border);
}
.ecole-assid-bloc:first-of-type { padding-top: 0; }
.ecole-assid-bloc:last-of-type  { padding-bottom: 0; border-bottom: none; }

.ecole-assid-nom { font-size: .95rem; margin-bottom: .4rem; }
.ecole-assid-nom .text-muted { font-size: .82rem; margin-left: .4rem; }

.ecole-assid-chiffres {
    display: flex; flex-wrap: wrap; gap: .4rem;
    font-size: .82rem; margin-bottom: .2rem;
}
.ecole-assid-chiffre {
    display: inline-flex; align-items: baseline; gap: .25rem;
    padding: .2rem .55rem; border-radius: var(--radius);
    background: var(--color-surface-alt); color: var(--color-muted);
}
.ecole-assid-chiffre--present { background: var(--color-accent-lt); color: var(--color-accent-dk); }
.ecole-assid-chiffre--absent  { background: var(--color-danger-lt);  color: var(--color-danger); }
.ecole-assid-chiffre--retard  { background: var(--color-warning-lt); color: var(--color-warning); }

.ecole-assid-dates { display: flex; flex-wrap: wrap; gap: .3rem; margin-top: .4rem; }
.ecole-assid-date {
    font-size: .76rem; padding: .18rem .5rem; border-radius: var(--radius);
    background: var(--color-surface-alt); color: var(--color-muted);
    border-left: 3px solid var(--color-border-strong);
}
.ecole-assid-date--absent { border-left-color: var(--color-danger); }
.ecole-assid-date--retard { border-left-color: var(--color-warning); }

/* ── Assiduité — tableau d'une classe (ecole/assiduite.php) ──
   Posture « assis, plusieurs lignes à comparer » : cet écran est
   pensé pour un ordinateur et reste consultable sur téléphone en
   défilant, plutôt que découpé en cartes — une carte par élève
   perdrait précisément ce qu'on vient y chercher, la comparaison
   d'une colonne de séance d'un élève à l'autre. */
.ecole-assid-grille { border-collapse: collapse; }
.ecole-assid-grille th, .ecole-assid-grille td { text-align: center; }
.ecole-assid-grille th:first-child,
.ecole-assid-grille td:first-child { text-align: left; white-space: nowrap; }
.ecole-assid-seance { font-size: .68rem; line-height: 1.25; font-weight: 600; }
.ecole-assid-seance span { display: block; font-weight: 400; color: var(--color-text-tertiary); }
.ecole-assid-case { width: 2.2rem; font-size: .8rem; font-weight: 600; padding: .3rem .15rem; }
.ecole-assid-case--present { color: var(--color-accent); }
.ecole-assid-case--retard  { color: var(--color-warning); }
.ecole-assid-case--absent  { color: var(--color-danger); }
.ecole-assid-case--vide    { color: var(--color-text-tertiary); font-weight: 400; }
/* Une absence prévenue reste une absence : elle se distingue par un
   soulignement, pas par une autre couleur — sinon on la lirait comme
   une troisième catégorie, et elle serait comptée à part. */
.ecole-assid-case--excuse { text-decoration: underline; text-underline-offset: 2px; }
.ecole-assid-total { white-space: nowrap; font-size: .82rem; }

.ecole-assid-legende {
    display: flex; flex-wrap: wrap; gap: .75rem;
    font-size: .78rem; color: var(--color-muted); margin-top: .6rem;
}

/* ══════════════════════════════════════════════════════════════
   COTISATIONS — tuiles cliquables, année de la période, compte
   Écrit après les règles .cot-* existantes (vers 4400) : à force
   égale, la dernière règle écrite gagne.
   ══════════════════════════════════════════════════════════════ */

/* Les trois cases du haut mènent à la liste qu'elles comptent. Le « › »
   est permanent : au doigt, rien ne survole, un indice au survol ne se
   voit jamais sur téléphone. */
.cot-stats-grid .stat-card--link { text-decoration: none; color: inherit; display: block; }
.cot-stats-grid .cot-stat--active {
    border-color: var(--color-primary);
    box-shadow: 0 0 0 1px var(--color-primary);
}
.cot-stat-fleche { color: var(--color-muted); font-weight: 700; }

/* L'année de la période couverte : elle n'est plus un menu, c'est celle
   de la date du paiement. Même taille que les menus de mois voisins. */
.cot-periode-annee {
    font-size: .82rem; padding: 6px 8px;
    border: 1.5px solid transparent; color: var(--color-text);
}

/* Phrase d'aide sous le compte (« un virement arrive sur le compte
   bancaire »). Elle n'apparaît que lorsqu'elle a quelque chose à dire. */
.cot-compte-aide {
    display: block; margin-top: 4px;
    font-size: .72rem; color: var(--color-muted);
}
.cot-compte-aide:empty { display: none; }

/* ══════════════════════════════════════════════════════════════
   AIDE « ⓘ » DES RAPPORTS — includes/aide_financiere.php
   Le texte est dans la page dès le départ, simplement caché : trois
   lignes déjà connues ne valent pas un aller-retour réseau chez
   l'hébergeur. Ouverture et placement mutualisés dans app.js.
   ══════════════════════════════════════════════════════════════ */

.aide { display: inline; }

/* Un rond discret, qui ne prend pas le pas sur le chiffre qu'il
   accompagne. Son ::after élargit la cible tactile sans l'agrandir. */
.aide-btn {
    position: relative;
    display: inline-flex; align-items: center; justify-content: center;
    width: 17px; height: 17px; margin-left: .35rem;
    border: 1px solid var(--color-border); border-radius: 50%;
    background: var(--color-surface); color: var(--color-muted);
    font-family: var(--font); font-size: .68rem; font-weight: 700;
    font-style: italic; line-height: 1;
    text-transform: none; letter-spacing: normal;
    cursor: pointer; vertical-align: middle;
    transition: color .12s, border-color .12s;
}
.aide-btn::after {           /* cible tactile élargie, invisible */
    content: ""; position: absolute;
    top: -12px; right: -12px; bottom: -12px; left: -12px;
}
.aide-btn:hover,
.aide-btn[aria-expanded="true"] {
    color: var(--color-primary); border-color: var(--color-primary);
}

/* ── La bulle ──────────────────────────────────────────────────
   position: fixed, et non absolute : une bulle en absolu serait
   rognée par la première carte qui l'entoure — les cartes coupent ce
   qui dépasse d'elles pour garder leurs coins arrondis. En fixed elle
   échappe à tous ces découpages, et app.js la place sous le bouton
   en la ramenant dans l'écran si elle débordait.
   Elle flotte par-dessus la page : ouvrir une explication ne déplace
   plus rien autour, ce qui était insupportable au milieu d'un tableau.

   Un ⓘ peut désormais être posé n'importe où, y compris dans une carte qui
   porte un transform — toute carte animée à l'apparition (.stat-card) ou
   qui se soulève au survol. Un transform fait de la carte le repère de ce
   qui est en fixed à l'intérieur d'elle, et la bulle s'y plaçait de travers
   avant d'y être rognée ; app.js la sort donc dans <body> le temps de son
   affichage et la remet à sa place en refermant, pour qu'à l'impression
   elle sorte sous son propre chiffre. */
.aide-txt {
    position: fixed; left: 0; top: 0; z-index: 400;
    display: block;
    width: min(21rem, calc(100vw - 24px));
    margin: 0;
    padding: .7rem .85rem;
    border: 1px solid var(--color-border);
    border-left: 3px solid var(--color-primary);
    border-radius: var(--radius);
    background: var(--color-surface);
    color: var(--color-text);
    box-shadow: var(--shadow-md);
    font-size: .78rem; font-weight: 400; font-style: normal;
    line-height: 1.55; text-align: left;
    text-transform: none; letter-spacing: normal;
    hyphens: auto;
}
/* Plus spécifique que la règle ci-dessus (classe + attribut), donc
   l'attribut hidden l'emporte quel que soit l'ordre d'écriture. */
.aide-txt[hidden] { display: none; }

/* Une explication longue — celles du module école font deux paragraphes —
   dépasserait du bas de l'écran sur un téléphone, et la fin serait perdue
   sans que rien ne le dise. Plafonnée à la hauteur de la fenêtre, elle
   défile pour elle-même : on voit alors qu'il y a une suite. */
.aide-txt { max-height: min(24rem, calc(100vh - 24px)); overflow-y: auto; }

/* Les explications du module école sont écrites en paragraphes, celles des
   rapports financiers en texte simple : les deux se lisent dans la même bulle.
   Un <span> et non un <p>, parce que le rond se pose au bout d'un paragraphe
   et qu'un <p> dans un <p> est refermé d'office par le navigateur. */
.aide-txt .aide-p { display: block; }
.aide-txt .aide-p + .aide-p { margin-top: .55rem; }


/* ══════════════════════════════════════════════════════════════
   OPÉRATIONS — retour sur la ligne modifiée
   Après un enregistrement, la page revient sur #op-<id>. La ligne est
   décalée sous les barres fixes du haut (sinon elle arriverait cachée
   dessous) et teintée un instant, pour qu'on voie tout de suite laquelle
   on vient de corriger au milieu d'une liste filtrée.
   ══════════════════════════════════════════════════════════════ */
.ops-table tr.ops-row { scroll-margin-top: 120px; }
.ops-table tr.ops-row:target,
.ops-table tr.ops-row:target > td { background: var(--color-primary-lt); }


/* ════════════════════════════════════════════════════════════
   OPÉRATIONS — une ligne par opération, groupées par jour

   Motif repris des relevés bancaires : un bandeau de jour, le libellé en
   tête de ligne, le compte et la catégorie en petit dessous, le montant
   à droite. La colonne Date disparaît — sur une page de cinquante
   opérations elle ne prenait que six valeurs différentes, et huit fois
   la même sur le tableau de bord — et Compte et Catégorie cessent d'être
   deux colonnes à lire de gauche à droite.

   Un seul motif pour les deux largeurs : le téléphone avait déjà cette
   présentation (libellé puis ligne grise), l'ordinateur en avait une
   autre. Sert au tableau de bord comme à la page Opérations.

   ⚠ Ce bloc est écrit APRÈS la media query des opérations plus haut :
     ses règles de base doivent pouvoir être écrasées par sa propre
     media query, placée en fin de bloc.
   ════════════════════════════════════════════════════════════ */

/* Le bandeau de jour n'est pas une opération : il ne se survole pas, ne
   se coche pas, et ne devient pas une carte sur téléphone. */
.ops-table tr.ops-jour td {
    background: var(--color-primary-lt);
    color: var(--color-primary-dk);
    font-size: .76rem;
    font-weight: 700;
    letter-spacing: .02em;
    padding: .4rem .75rem;
    border-bottom: 1px solid var(--color-primary-mid);
}
.ops-table tr.ops-jour:hover td { background: var(--color-primary-lt); }

/* Libellé, repère de détail, et le montant sur téléphone (sur
   ordinateur il garde sa colonne, alignée à droite). */
.ops-ligne-haut {
    display: flex;
    align-items: baseline;
    gap: .4rem;
    flex-wrap: wrap;
}
.ops-ligne-haut .ops-desc { flex: 0 1 auto; }

/* Compte · catégorie, sous le libellé : ce qui était deux colonnes. */
.ops-ligne-meta {
    display: flex;
    align-items: center;
    gap: .4rem;
    flex-wrap: wrap;
    margin-top: .15rem;
}
.ops-ligne-compte { font-size: .75rem; color: var(--color-muted); }
/* Catégorie, « ✓ rapprochée » et 📎 regroupés : sur téléphone ils doivent
   pouvoir se poser d'un bloc, le compte partant seul dans l'en-tête de la
   carte. Le même écart qu'entre les éléments de .ops-ligne-meta, pour que
   la ligne se lise d'un trait comme avant ce regroupement. */
.ops-ligne-suite {
    display: inline-flex;
    align-items: center;
    gap: .4rem;
    flex-wrap: wrap;
    min-width: 0;
}
.ops-ligne-cat    { font-size: .72rem; }
.ops-ligne-rapproche {
    font-size: .7rem; color: var(--color-success); white-space: nowrap;
}

/* Le repère qui dit qu'il y a un adhérent et/ou une note, et qui les
   ouvre. Le chevron pivote pour dire dans quel sens ça va. */
.ops-detail-btn {
    background: none; border: none; cursor: pointer;
    padding: 0 .15rem;
    font-size: .8rem; line-height: 1;
    color: var(--color-muted);
    white-space: nowrap;
}
.ops-detail-btn:hover { color: var(--color-text); }
.ops-chevron {
    display: inline-block;
    transition: transform var(--transition);
}
.ops-detail-btn[aria-expanded="true"] .ops-chevron { transform: rotate(180deg); }

.ops-detail {
    margin-top: .35rem;
    padding: .4rem .55rem;
    background: var(--color-surface-alt);
    border-radius: var(--radius);
    font-size: .76rem;
    color: var(--color-muted);
}
.ops-detail-adh  { font-weight: 600; color: var(--color-text); }
.ops-detail-note { margin-top: .2rem; }
/* Classe + attribut : l'attribut hidden l'emporte quel que soit l'ordre
   d'écriture (même précaution que .aide-txt). */
.ops-detail[hidden] { display: none; }

/* Le 📎 posé dans la ligne double celui de la colonne Justificatif,
   masquée sur téléphone : il ne se montre donc que là. */
.ops-meta-justif { display: none; }

/* ── Le filet de compte ──

   Un trait de couleur au bord gauche de chaque ligne : bleu pour la
   banque, ambre pour une caisse, gris pour un transfert interne — qui
   ne change ni l'un ni l'autre. Les opérations d'un même compte étant
   déjà contiguës 92 % du temps, elles se lisent comme un bloc sans
   qu'aucune ligne ait été ajoutée pour les regrouper.

   Le nom du compte reste écrit sur chaque ligne : la couleur regroupe,
   elle ne remplace pas. Deux caisses partagent la même teinte, et une
   couleur seule ne se lit pas pour qui la distingue mal.

   Posé sur la première cellule et non sur la ligne : en
   border-collapse, la bordure d'un <tr> est arbitrée avec celles des
   cellules qu'il contient. */
.ops-row--banque    { --ops-filet: var(--color-info); }
.ops-row--caisse    { --ops-filet: var(--color-primary); }
.ops-row--transfert { --ops-filet: var(--color-muted); }

.ops-table tbody tr.ops-row > td:first-child {
    border-left: 3px solid var(--ops-filet, transparent);
}

@media (max-width: 768px) {
    .ops-table tr.ops-jour {
        display: block;
        background: transparent;
        border: 0;
        box-shadow: none;
        border-radius: 0;
        padding: .5rem 0 .1rem;
        margin: 0;
    }
    .ops-table tr.ops-jour td {
        display: block;
        background: transparent;
        border: 0;
        padding: 0 .15rem;
        width: 100% !important;
    }
    .ops-table tr.ops-jour td::before { display: none; }

    /* La cellule de l'opération est le corps de la carte : ni étiquette
       « OPÉRATION » devant, ni mise en colonnes — elle empile déjà ses
       trois blocs. Pas de filet sous elle non plus : sur le tableau de
       bord c'est la seule cellule visible, il ne séparerait rien, et sur
       la page Opérations la cellule Actions porte déjà le sien. */
    .ops-table tbody td[data-label="Opération"] {
        display: block;
        border-bottom: none;
        margin-bottom: 0;
        padding-bottom: .1rem;
    }
    .ops-table tbody td[data-label="Opération"]::before { display: none; }

    .ops-ligne-haut {
        align-items: flex-start;
        gap: .3rem .5rem;
    }
    .ops-ligne-haut .ops-desc { flex: 1 1 auto; }
    /* Le montant se colle à droite du libellé, comme sur un relevé. */
    .ops-ligne-haut .ops-mobile-montant { margin-left: auto; }

    .ops-meta-justif { display: inline-flex; align-items: center; gap: .2rem; }
}


/* ══════════════════════════════════════════════════════════════
   OPÉRATIONS SUR TÉLÉPHONE — l'en-tête de carte porte les commandes

   Une carte d'opération gardait une ligne entière en haut pour une case
   à cocher seule et centrée, et une ligne entière en bas pour ses deux
   boutons. Les trois se rejoignent sur la première ligne — case à
   cocher à gauche, compte au milieu, boutons à droite — et la carte
   perd ses deux lignes creuses.

   Fait en grille sur le <tr>, la cellule de l'opération passant en
   display: contents : la case à cocher, le compte et les boutons
   vivent dans trois cellules différentes, et aucune propriété ne peut
   les rapprocher sans effacer ce niveau. Le HTML n'est pas touché,
   donc l'affichage sur ordinateur est inchangé par construction.

   ⚠ Réservé aux lignes qui ont des boutons (:has). Sans eux — compte en
     lecture seule, « Dernières opérations » du tableau de bord — le
     compte se retrouverait seul sur sa ligne et coûterait justement
     celle qu'on économise ici. Un navigateur sans :has() garde la
     présentation précédente, sans rien casser.
   ══════════════════════════════════════════════════════════════ */
@media (max-width: 768px) {
    .ops-table tbody tr.ops-row:has(.ops-td-actions) {
        display: grid;
        grid-template-columns: auto 1fr auto;
        grid-template-areas:
            "sel    compte  actions"
            "desc   desc    desc"
            "suite  suite   suite"
            "detail detail  detail";
        align-items: center;
        column-gap: .5rem;
        row-gap: .15rem;
    }

    /* Les deux cellules qui gardent une boîte : elles perdent les filets
       et les marges qui les séparaient du reste de la carte, puisqu'elles
       sont maintenant DANS son en-tête. */
    tr.ops-row:has(.ops-td-actions) > .ops-td-sel {
        grid-area: sel;
        display: flex;
        align-items: center;
        padding: 0;
        margin-bottom: 0;
        border-bottom: none;
    }
    tr.ops-row:has(.ops-td-actions) > td[data-label="Actions"] {
        grid-area: actions;
        padding: 0 !important;
        margin-top: 0;
        border-top: none;
    }
    /* nowrap : un bouton qui passerait à la ligne rendrait la ligne
       d'en-tête plus haute que les deux lignes qu'elle remplace. */
    tr.ops-row:has(.ops-td-actions) .ops-actions {
        justify-content: flex-end;
        flex-wrap: nowrap;
    }

    /* La cellule de l'opération s'efface : ses blocs deviennent des
       éléments de la grille de la carte, et peuvent donc se placer
       ailleurs que les uns sous les autres. */
    tr.ops-row:has(.ops-td-actions) > td[data-label="Opération"] { display: contents; }
    tr.ops-row:has(.ops-td-actions) .ops-ligne-meta { display: contents; }

    /* Le compte se coupe plutôt que de pousser les boutons hors de
       l'écran : à 375 px, « 🔄 Hassan → Khalid » et les deux boutons
       tiennent tout juste, et c'est le compte qui peut céder — il se
       relit en entier dans la liste, les boutons non. */
    tr.ops-row:has(.ops-td-actions) .ops-ligne-compte,
    tr.ops-row:has(.ops-td-actions) .badge-transfert {
        grid-area: compte;
        justify-self: start;
        max-width: 100%;
        min-width: 0;
        overflow: hidden;
        text-overflow: ellipsis;
        white-space: nowrap;
    }

    /* Le libellé reprend toute la largeur, et se lit à gauche : la règle
       commune de .table-mobile pousse à droite les sous-lignes d'une
       cellule qui n'est pas la première, ce qui convient à une valeur
       courte, pas au corps d'une carte. Son filet remplace celui que
       portait la case à cocher. */
    tr.ops-row:has(.ops-td-actions) .ops-ligne-haut {
        grid-area: desc;
        text-align: left;
        border-top: 1px solid var(--color-border);
        padding-top: .4rem;
        margin-top: .2rem;
    }

    /* Catégorie, « ✓ rapprochée » et 📎 forment UN élément de grille,
       posé sur toute la largeur. Placés séparément, ils tombaient dans
       les colonnes de l'en-tête : le badge « Maison - Travaux » élargissait
       la colonne de la case à cocher et le compte n'avait plus la place
       de s'écrire (« Ha… »). */
    tr.ops-row:has(.ops-td-actions) .ops-ligne-suite {
        grid-area: suite;
        display: flex;
        align-items: center;
        gap: .4rem;
        flex-wrap: wrap;
        min-width: 0;
    }
    tr.ops-row:has(.ops-td-actions) .ops-meta-justif { margin-left: auto; }
    tr.ops-row:has(.ops-td-actions) .ops-detail      { grid-area: detail; }

    /* .table-mobile pousse à droite les sous-lignes d'une cellule qui
       n'est pas la première — bon pour une valeur courte, faux pour le
       corps d'une carte, où tout se lit à gauche. text-align se transmet
       aux enfants, y compris à travers un display: contents. */
    tr.ops-row:has(.ops-td-actions) > td[data-label="Opération"] > div { text-align: left; }
}

/* Sur téléphone, le filet de compte passe du bord de la cellule au bord
   de la CARTE : c'est la carte entière qui représente l'opération, et un
   trait posé à l'intérieur se lirait comme une décoration. Même motif que
   les lignes « À traiter » de l'accueil trésorerie : fond neutre, filet de
   couleur à gauche. */
@media (max-width: 768px) {
    .ops-table tbody tr.ops-row {
        border-left: 3px solid var(--ops-filet, var(--color-border));
    }
    .ops-table tbody tr.ops-row > td:first-child { border-left: none; }
}

/* Le décompte de la carte « À traiter », repliée d'office sur l'accueil
   trésorerie, prend le ton de l'alerte la plus grave qu'elle contient.
   Sans ça, replier ferait perdre l'urgence : « À traiter (3) » en gris ne
   dit pas qu'un écart de caisse attend. Posé APRÈS .ecole-pliable-compte,
   qui donne la taille et le poids et qu'on ne fait que teinter. */
.atraiter-compte--danger { color: var(--color-danger);  font-weight: 700; }
.atraiter-compte--warn   { color: var(--color-warning); font-weight: 700; }
.atraiter-compte--info   { color: var(--color-muted); }

/* ══════════════════════════════════════════════════════════════
   EXERCICES COMPTABLES — admin/exercices.php
   Ces valeurs étaient écrites dans le HTML (style="…"), dont une
   couleur en dur qui ne suivait pas le thème sombre.
   ══════════════════════════════════════════════════════════════ */

.exo-intro { margin: 0 0 .6rem; }
.exo-intro:last-child { margin-bottom: 0; }

/* Les deux écrans qu'on lit avant de clore, sous l'année. */
.exo-liens { display: flex; flex-wrap: wrap; gap: .6rem; margin-top: .25rem; font-size: .78rem; }

/* Le secondaire d'une cellule : entrées / sorties, période couverte. */
.exo-detail { font-size: .78rem; color: var(--color-muted); }

.exo-td-pointer { white-space: nowrap; }
.exo-td-histo   { font-size: .85em; }

/* Une réouverture se remarque : c'est le geste qui défait des comptes
   présentés. La teinte vient du thème (ambre en clair, ambre pâle en
   sombre) et non d'un #b45309 écrit en dur, illisible en mode sombre. */
.exo-reouverture { color: var(--color-warning); margin-top: .2rem; }

.exo-form { display: inline; }

/* La case « clore malgré tout » prend sa ligne au-dessus du bouton :
   c'est un aveu, pas une option qu'on coche sans la lire. */
.exo-forcer { display: block; font-size: .8em; margin-bottom: .3em; }
