/*!
 * Courrier-DCMP — animations et transitions.
 *
 * Complement de style.css. Trois principes :
 *
 *  1. SOBRIETE. C'est une application administrative, consultee toute la
 *     journee. Les mouvements sont courts (150-320 ms) et de faible amplitude ;
 *     une animation qu'on remarque est une animation ratee.
 *
 *  2. AUCUN CONTENU INVISIBLE. Toutes les entrees utilisent
 *     animation-fill-mode: backwards : l'element est dans son etat final des
 *     que l'animation se termine, et visible si elle ne demarre jamais. Une
 *     feuille de style qui echoue ne doit pas vider l'ecran.
 *
 *  3. RESPECT DU REGLAGE SYSTEME. prefers-reduced-motion desactive tout.
 *     Ce n'est pas un detail de confort : les mouvements declenchent des
 *     vertiges chez une partie des utilisateurs.
 *
 * Prefixe "an-" pour ne rien ecraser de l'existant.
 */

/* ── Courbes et durees ─────────────────────────────────────── */
:root {
  --an-court: 180ms;
  --an-moyen: 300ms;
  --an-long: 420ms;
  --an-entree: 520ms;          /* entrees de cartes : laisser le temps a l'oeil */

  /* cubic-bezier(0.22, 1, 0.36, 1) demarrait tres vite puis freinait sec :
     les cartes semblaient surgir. Cette courbe-ci monte progressivement. */
  --an-sortie: cubic-bezier(0.25, 0.46, 0.45, 0.94);
  --an-doux: cubic-bezier(0.4, 0, 0.2, 1);
  --an-souple: cubic-bezier(0.33, 0.68, 0.35, 1);
}

/* ── Keyframes ─────────────────────────────────────────────── */
@keyframes an-monte      { from { opacity: 0; transform: translateY(8px); }  to { opacity: 1; transform: none; } }
@keyframes an-fondu      { from { opacity: 0; }                              to { opacity: 1; } }
@keyframes an-glisseD    { from { opacity: 0; transform: translateX(-7px); }  to { opacity: 1; transform: none; } }
/* Le scale() modifiait la taille apparente : c'est le mouvement que l'oeil
   detecte le plus. Remplace par une translation de 6 px, imperceptible en
   soi mais suffisante pour donner le sens de lecture. */
@keyframes an-echelle    { from { opacity: 0; transform: translateY(6px); }    to { opacity: 1; transform: none; } }
@keyframes an-battement  { 0%,100% { transform: scale(1); } 50% { transform: scale(1.09); } }

/* ── Defilement ────────────────────────────────────────────── */
/* Les paginations renvoient vers #alertes et #evenements : sans cela,
   le navigateur saute brutalement au milieu de la page. */
html { scroll-behavior: smooth; }
/* Marge pour que l'ancre ne se colle pas sous l'en-tete fixe */
[id] { scroll-margin-top: 80px; }

/* ── Entree de page ────────────────────────────────────────── */
/*
 * SUPPRIMEE, et voici pourquoi.
 *
 * Toute animation qui part de opacity:0 laisse l'element invisible tant
 * qu'elle n'a pas demarre. Si elle ne demarre jamais — feuille chargee en
 * retard, element hors ecran, animation interrompue par un recalcul de
 * style — le bloc reste transparent en permanence. C'est ce qui faisait
 * disparaitre la vue Kanban de tracking.php, enfant direct de .content-area.
 *
 * Une transition, elle, ne se declenche que sur changement d'etat : elle ne
 * peut jamais rendre un element invisible. Tout ce qui reste dans ce fichier
 * repose donc sur des transitions, pas sur des animations d'entree.
 */

/* ── Cartes ────────────────────────────────────────────────── */
/*
 * Version simple, et c'est deliberé.
 *
 * J'avais tente une ombre portee par un pseudo-element avec will-change,
 * pour confier l'animation au GPU. Mauvaise idee : will-change cree un
 * calque de composition permanent, que le navigateur detruit et recree
 * quand l'opacite retombe a zero. Ce cycle faisait disparaitre puis
 * reapparaitre la carte au retrait du curseur.
 *
 * Une transition d'ombre sur la carte elle-meme coute un repaint, mais
 * sur UN SEUL element a la fois — celui qu'on survole. C'est negligeable,
 * et surtout cela ne cree ni ne detruit aucun calque : aucun clignotement
 * possible.
 *
 * Les saccades constatees auparavant venaient d'ailleurs : les barres de
 * progression animees en largeur et les graphiques traces pendant
 * l'apparition des cartes. Ces deux causes sont traitees plus bas et dans
 * assets/js/spark.js.
 */
.stat-card, .card, .dash-card, .gx-card, .sec-card, .pl-card {
  transition: box-shadow 300ms ease-out;
}
.stat-card:hover, .card:hover, .dash-card:hover,
.gx-card:hover, .sec-card:hover, .pl-card:hover {
  box-shadow: 0 6px 18px rgba(15, 23, 42, .09);
}
.stat-card[data-href] { cursor: pointer; }

/* ── Tableaux ──────────────────────────────────────────────── */
.table tbody tr {
  transition: background-color var(--an-court) var(--an-doux);
}
.table tbody tr:hover { background-color: var(--bg-hover, rgba(15, 23, 42, .025)); }
.table tbody tr[onclick], .table tbody tr[data-href] { cursor: pointer; }

/* ── Boutons ───────────────────────────────────────────────── */
.btn {
  transition: background-color var(--an-court) var(--an-doux),
              border-color var(--an-court) var(--an-doux),
              color var(--an-court) var(--an-doux),
              box-shadow var(--an-court) var(--an-doux),
              transform 120ms var(--an-souple);
}
.btn:active:not(:disabled) { transform: scale(.985); }
.btn:disabled { transition: none; }

/* ── Navigation laterale ───────────────────────────────────── */
.nav-link {
  transition: background-color var(--an-court) var(--an-doux),
              color var(--an-court) var(--an-doux);
}
/* padding-left forcait un recalcul de mise en page a chaque image.
   translateX produit le meme effet visuel, en composition GPU. */
.nav-link > * { transition: transform var(--an-moyen) var(--an-souple); }
.nav-link:hover:not(.active) > * { transform: translateX(3px); }

/* ── Formulaires ───────────────────────────────────────────── */
.form-control, .form-select {
  transition: border-color var(--an-court) var(--an-doux),
              box-shadow var(--an-court) var(--an-doux),
              background-color var(--an-court) var(--an-doux);
}
.form-control:focus, .form-select:focus { box-shadow: 0 0 0 3px rgba(0, 133, 63, .13); }

/* ── Messages et alertes ───────────────────────────────────── */
/* Les messages apparaissent sans animation : meme raison. */

/* ── Compteur de notifications ─────────────────────────────── */
#notif-count:not(:empty), .notif-badge:not(:empty) {
  animation: an-battement 560ms var(--an-souple);
}

/* ── Pastilles et etiquettes ───────────────────────────────── */
.badge, .sec-badge, .pl-tag, .dcmp-toast .tag {
  transition: background-color var(--an-court) var(--an-doux),
              color var(--an-court) var(--an-doux);
}

/* ── Barres de progression ─────────────────────────────────── */
/* Le remplissage animait la propriete width, qui declenche un recalcul de
   mise en page a chaque image — et ces barres se remplissent au chargement,
   exactement quand les cartes apparaissent. Deux animations couteuses en
   meme temps sur le meme fil : c'est la que les images se perdaient.
   Les barres s'affichent maintenant a leur valeur finale. */

/* ── Liens ─────────────────────────────────────────────────── */
a:not(.btn):not(.nav-link) { transition: color var(--an-court) var(--an-doux); }

/* ── Tri des colonnes ──────────────────────────────────────── */
th.dcmp-tri { transition: color var(--an-court) var(--an-doux); }
th.dcmp-tri::after { transition: opacity var(--an-court) var(--an-doux),
                                 color var(--an-court) var(--an-doux); }

/* ── Panneaux depliants ────────────────────────────────────── */
.collapse:not(.show) { display: none; }
.collapsing { transition: height var(--an-long) var(--an-doux); }



/* ── Accessibilite du focus clavier ────────────────────────── */
:focus-visible {
  outline: 2px solid var(--sn-vert, #00853F);
  outline-offset: 2px;
  transition: outline-offset var(--an-court) var(--an-doux);
}

/* ══════════════════════════════════════════════════════════════
   REGLAGE SYSTEME — priorite absolue
   Les mouvements provoquent vertiges et nausees chez une partie
   des utilisateurs. Quand le systeme demande a les reduire, on
   supprime tout : plus aucune animation, plus aucune transition.
   ══════════════════════════════════════════════════════════════ */
@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation-duration: 0.01ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.01ms !important;
    scroll-behavior: auto !important;
  }
  .nav-link:hover:not(.active) > * { transform: none; }
}

/* Impression : aucune animation, aucun effet */
@media print {
  *, *::before, *::after { animation: none !important; transition: none !important; }
}
