/* =========================================================================
   Thinance — système de design
   Un seul fichier, en CSS pur. Organisation :
     1. Jetons (variables) : couleurs, typo, espacements, rayons, ombres
     2. Thème sombre (suit le système, ou le choix fait avec le bouton)
     3. Base (reset léger, typographie, focus)
     4. Mise en page de l'application (barre du haut, navigation)
     5. Composants (boutons, champs, pastilles, barres de budget, etc.)
     6. Écrans (connexion, tableau de bord, opérations)
   Règle CSP : aucun attribut style="" dans le HTML (la politique de
   sécurité les bloquera). Tout passe par des classes de ce fichier.
   ========================================================================= */

/* ---------- 1. Jetons ---------- */
:root {
  color-scheme: light;

  /* Couleurs de base (mode clair) */
  --bg: #eef0f5;            /* fond général, gris bleuté froid */
  --surface: #ffffff;       /* panneaux */
  --surface-2: #f5f6fa;     /* zones secondaires, survol */
  --border: #dde1ea;
  --text: #1a1d29;          /* encre */
  --text-muted: #5c6273;
  --track: #e4e7ef;         /* fond des barres de progression */

  /* Accent : prune. Rare en finance, se distingue du vert/orange/rouge. */
  --accent: #5b3fa6;
  --accent-hover: #4a3190;
  --accent-soft: #ece7fa;
  --on-accent: #ffffff;

  /* États de budget */
  --ok: #23824a;            /* sous le plafond */
  --ok-soft: #e2f3e8;
  --warn: #a6560a;          /* texte orange (contraste suffisant sur blanc) */
  --warn-bar: #e8892b;      /* barre orange, à partir de 80 % */
  --warn-soft: #fcefdf;
  --danger: #c0352b;        /* dépassement, à partir de 100 % */
  --danger-soft: #fbe6e3;

  /* Couleurs des catégories (pastilles et graphiques) */
  --cat-logement: #4c5fd5;
  --cat-courses: #2e9e6b;
  --cat-transport: #0b8bc9;
  --cat-restos: #e0662e;
  --cat-abonnements: #b04aa0;
  --cat-shopping: #c99a12;
  --cat-loisirs: #7c5ad9;
  --cat-sante: #d24767;
  --cat-cadeaux: #9c6b3a;
  --cat-frais: #6b7280;
  --cat-autres-dep: #5f7a8a;
  --cat-a-classer: #a3a7b0;
  --cat-salaire: #23824a;
  --cat-aides: #5e9c2f;
  --cat-famille: #2e9c8c;
  --cat-autres-rev: #7a9a4a;
  --cat-epargne: #0e7c9b;

  /* Typographie : pile de polices système (rien à télécharger, pas de CDN) */
  --font: system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
  --text-xs: 0.75rem;
  --text-sm: 0.875rem;
  --text-base: 1rem;
  --text-lg: 1.125rem;
  --text-xl: 1.375rem;
  --text-2xl: 1.75rem;
  --text-hero: clamp(3rem, 14vw, 4.5rem);

  /* Espacements (échelle de 4 px) */
  --space-1: 0.25rem;
  --space-2: 0.5rem;
  --space-3: 0.75rem;
  --space-4: 1rem;
  --space-5: 1.5rem;
  --space-6: 2rem;
  --space-7: 3rem;
  --space-8: 4rem;

  /* Rayons : plus l'élément est grand, plus il est arrondi */
  --radius-sm: 8px;
  --radius-md: 12px;
  --radius-lg: 20px;
  --radius-pill: 999px;

  /* Ombres : très légères en clair, remplacées par des bordures en sombre */
  --shadow-1: 0 1px 2px rgb(26 29 41 / 6%);
  --shadow-2: 0 8px 24px rgb(26 29 41 / 10%);

  /* Mouvement */
  --duration: 180ms;
  --ease: cubic-bezier(0.2, 0.7, 0.2, 1);

  --nav-height: 64px;
}

/* ---------- 2. Thème sombre ----------
   Les valeurs sombres sont écrites deux fois :
   - dans la media query : quand le système est en sombre et que je n'ai
     rien choisi (ou que j'ai choisi « sombre ») ;
   - dans [data-theme="dark"] : quand j'ai choisi « sombre » avec le bouton
     alors que le système est en clair. */
@media (prefers-color-scheme: dark) {
  :root:not([data-theme="light"]) {
    color-scheme: dark;
    --bg: #14131b;
    --surface: #1d1b26;
    --surface-2: #262433;
    --border: #34313f;
    --text: #eceaf3;
    --text-muted: #a29eb2;
    --track: #2f2c3b;
    --accent: #a794f2;
    --accent-hover: #bbaef6;
    --accent-soft: #2e2846;
    --on-accent: #14131b;
    --ok: #5cc98a;
    --ok-soft: #1b3226;
    --warn: #f0a04b;
    --warn-bar: #f0a04b;
    --warn-soft: #3a2b18;
    --danger: #f07468;
    --danger-soft: #3d201e;
    --cat-logement: #8e9cf3;
    --cat-courses: #5fd3a0;
    --cat-transport: #5bbdeb;
    --cat-restos: #f59466;
    --cat-abonnements: #e085d0;
    --cat-shopping: #e8c24e;
    --cat-loisirs: #ae94f3;
    --cat-sante: #f0819a;
    --cat-cadeaux: #cfa06f;
    --cat-frais: #9aa1ad;
    --cat-autres-dep: #93aebd;
    --cat-a-classer: #7d8290;
    --cat-salaire: #5cc98a;
    --cat-aides: #9bd46a;
    --cat-famille: #6fd2c2;
    --cat-autres-rev: #afcb7e;
    --cat-epargne: #55c3e0;
    --shadow-1: none;
    --shadow-2: 0 8px 24px rgb(0 0 0 / 40%);
  }
}
:root[data-theme="dark"] {
  color-scheme: dark;
  --bg: #14131b;
  --surface: #1d1b26;
  --surface-2: #262433;
  --border: #34313f;
  --text: #eceaf3;
  --text-muted: #a29eb2;
  --track: #2f2c3b;
  --accent: #a794f2;
  --accent-hover: #bbaef6;
  --accent-soft: #2e2846;
  --on-accent: #14131b;
  --ok: #5cc98a;
  --ok-soft: #1b3226;
  --warn: #f0a04b;
  --warn-bar: #f0a04b;
  --warn-soft: #3a2b18;
  --danger: #f07468;
  --danger-soft: #3d201e;
  --cat-logement: #8e9cf3;
  --cat-courses: #5fd3a0;
  --cat-transport: #5bbdeb;
  --cat-restos: #f59466;
  --cat-abonnements: #e085d0;
  --cat-shopping: #e8c24e;
  --cat-loisirs: #ae94f3;
  --cat-sante: #f0819a;
  --cat-cadeaux: #cfa06f;
  --cat-frais: #9aa1ad;
  --cat-autres-dep: #93aebd;
  --cat-a-classer: #7d8290;
  --cat-salaire: #5cc98a;
  --cat-aides: #9bd46a;
  --cat-famille: #6fd2c2;
  --cat-autres-rev: #afcb7e;
  --cat-epargne: #55c3e0;
  --shadow-1: none;
  --shadow-2: 0 8px 24px rgb(0 0 0 / 40%);
}

/* ---------- 3. Base ---------- */
*,
*::before,
*::after {
  box-sizing: border-box;
}

html {
  -webkit-text-size-adjust: 100%;
}

body {
  margin: 0;
  background: var(--bg);
  color: var(--text);
  font-family: var(--font);
  font-size: var(--text-base);
  line-height: 1.5;
  -webkit-font-smoothing: antialiased;
}

h1,
h2,
h3,
p {
  margin: 0;
}

h1 {
  font-size: var(--text-2xl);
  line-height: 1.2;
  letter-spacing: -0.01em;
}

h2 {
  font-size: var(--text-lg);
  line-height: 1.3;
}

a {
  color: var(--accent);
  text-underline-offset: 0.2em;
}

svg {
  display: block;
}

/* Icônes au trait : leur couleur suit celle du texte */
.i {
  fill: none;
  stroke: currentColor;
  stroke-width: 1.8;
  stroke-linecap: round;
  stroke-linejoin: round;
}

/* Focus clavier bien visible, uniquement à la navigation clavier */
:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
  border-radius: var(--radius-sm);
}

/* Texte lu par les lecteurs d'écran mais invisible à l'écran */
.visually-hidden {
  position: absolute;
  width: 1px;
  height: 1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
}

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

/* Montants : chiffres à chasse fixe pour qu'ils s'alignent en colonne */
.amount {
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.amount.is-positive {
  color: var(--ok);
}

/* Respecte le réglage « réduire les animations » du système */
@media (prefers-reduced-motion: reduce) {
  *,
  *::before,
  *::after {
    animation-duration: 0.01ms !important;
    transition-duration: 0.01ms !important;
  }
}

/* ---------- 4. Mise en page de l'application ---------- */
.app {
  min-height: 100dvh;
}

.topbar {
  position: sticky;
  top: 0;
  z-index: 10;
  display: flex;
  align-items: center;
  gap: var(--space-3);
  padding: var(--space-3) var(--space-4);
  background: color-mix(in srgb, var(--bg) 88%, transparent);
  backdrop-filter: blur(10px);
}

.topbar .brand {
  margin-right: auto;
}

.brand {
  display: inline-flex;
  align-items: center;
  gap: var(--space-2);
  color: var(--text);
  font-weight: 700;
  font-size: var(--text-lg);
  text-decoration: none;
}

.brand-mark {
  width: 28px;
  height: 28px;
  color: var(--accent);
}

.page {
  width: 100%;
  max-width: 1120px;
  margin: 0 auto;
  padding: var(--space-2) var(--space-4) calc(var(--nav-height) + var(--space-6));
}

.page-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: var(--space-3);
  margin-bottom: var(--space-5);
}

/* Navigation : barre en bas sur téléphone, colonne à gauche sur ordinateur.
   "li > a" cible seulement les rubriques, pas le lien du logo (.brand). */
.nav {
  position: fixed;
  inset: auto 0 0 0;
  z-index: 20;
  height: var(--nav-height);
  background: var(--surface);
  border-top: 1px solid var(--border);
  padding-bottom: env(safe-area-inset-bottom);
}

.nav .brand {
  display: none;
}

.nav ul {
  display: grid;
  grid-template-columns: repeat(5, 1fr);
  height: 100%;
  margin: 0;
  padding: 0;
  list-style: none;
}

.nav li > a {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 2px;
  height: 100%;
  color: var(--text-muted);
  font-size: 0.6875rem;
  font-weight: 600;
  text-decoration: none;
}

.nav li > a svg {
  width: 22px;
  height: 22px;
}

.nav li > a[aria-current="page"] {
  color: var(--accent);
}

@media (min-width: 960px) {
  .app {
    display: grid;
    grid-template-columns: 232px 1fr;
  }

  .nav {
    position: sticky;
    top: 0;
    height: 100dvh;
    padding: var(--space-5) var(--space-3);
    border-top: 0;
    border-right: 1px solid var(--border);
  }

  .nav .brand {
    display: inline-flex;
    padding: 0 var(--space-3) var(--space-5);
  }

  .nav ul {
    display: flex;
    flex-direction: column;
    gap: var(--space-1);
    height: auto;
  }

  .nav li > a {
    flex-direction: row;
    justify-content: flex-start;
    gap: var(--space-3);
    padding: var(--space-2) var(--space-3);
    border-radius: var(--radius-md);
    font-size: var(--text-sm);
    transition: background var(--duration) var(--ease);
  }

  .nav li > a:hover {
    background: var(--surface-2);
    color: var(--text);
  }

  .nav li > a[aria-current="page"] {
    background: var(--accent-soft);
  }

  .topbar .brand {
    visibility: hidden;
  }

  .page {
    padding: var(--space-2) var(--space-6) var(--space-7);
  }
}

/* ---------- 5. Composants ---------- */

/* Boutons */
.btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: var(--space-2);
  min-height: 44px; /* taille de cible confortable au doigt */
  padding: 0 var(--space-5);
  border: 1px solid transparent;
  border-radius: var(--radius-md);
  font: inherit;
  font-weight: 600;
  text-decoration: none;
  cursor: pointer;
  transition: background var(--duration) var(--ease), transform var(--duration) var(--ease);
}

.btn:active {
  transform: scale(0.98);
}

.btn-primary {
  background: var(--accent);
  color: var(--on-accent);
}

.btn-primary:hover {
  background: var(--accent-hover);
}

.btn-secondary {
  background: var(--surface);
  border-color: var(--border);
  color: var(--text);
}

.btn-secondary:hover {
  background: var(--surface-2);
}

.btn-ghost {
  background: transparent;
  color: var(--accent);
}

.btn-ghost:hover {
  background: var(--accent-soft);
}

.btn-danger {
  background: var(--danger);
  color: #fff;
}

.btn-small {
  min-height: 32px;
  padding: 0 var(--space-3);
  font-size: var(--text-sm);
  border-radius: var(--radius-sm);
}

.btn-block {
  width: 100%;
}

.icon-btn {
  display: inline-grid;
  place-items: center;
  width: 40px;
  height: 40px;
  border: 1px solid var(--border);
  border-radius: var(--radius-pill);
  background: var(--surface);
  color: var(--text);
  cursor: pointer;
}

.icon-btn:hover {
  background: var(--surface-2);
}

.icon-btn svg {
  width: 20px;
  height: 20px;
}

/* Bouton de thème : affiche la lune en clair, le soleil en sombre */
.theme-toggle .icon-sun {
  display: none;
}

:root[data-theme="dark"] .theme-toggle .icon-sun {
  display: block;
}

:root[data-theme="dark"] .theme-toggle .icon-moon {
  display: none;
}

@media (prefers-color-scheme: dark) {
  :root:not([data-theme]) .theme-toggle .icon-sun {
    display: block;
  }

  :root:not([data-theme]) .theme-toggle .icon-moon {
    display: none;
  }
}

/* Champs de formulaire */
.field {
  display: grid;
  gap: var(--space-2);
}

.field label {
  font-size: var(--text-sm);
  font-weight: 600;
}

.input,
.select {
  width: 100%;
  min-height: 44px;
  padding: 0 var(--space-4);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  background: var(--surface);
  color: var(--text);
  font: inherit;
  transition: border-color var(--duration) var(--ease), box-shadow var(--duration) var(--ease);
}

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

.input[aria-invalid="true"] {
  border-color: var(--danger);
}

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

.field-error {
  font-size: var(--text-sm);
  color: var(--danger);
}

/* Champ avec bouton intégré (afficher le mot de passe) */
.input-group {
  position: relative;
}

.input-group .input {
  padding-right: 6.5rem;
}

.input-group .btn {
  position: absolute;
  top: 6px;
  right: 6px;
}

/* Messages (erreur, succès) */
.alert {
  display: flex;
  gap: var(--space-3);
  align-items: flex-start;
  padding: var(--space-3) var(--space-4);
  border-radius: var(--radius-md);
  font-size: var(--text-sm);
}

.alert svg {
  flex: none;
  width: 20px;
  height: 20px;
  margin-top: 1px;
}

.alert-error {
  background: var(--danger-soft);
  color: var(--danger);
}

.alert-success {
  background: var(--ok-soft);
  color: var(--ok);
}

.alert strong {
  display: block;
  color: var(--text);
}

/* Panneau : conteneur principal de contenu */
.panel {
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-1);
  padding: var(--space-5);
}

.panel-head {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--space-3);
  margin-bottom: var(--space-4);
}

.panel-head a {
  font-size: var(--text-sm);
  font-weight: 600;
}

/* Pastilles de catégorie : un point coloré + le nom, fond teinté */
.cat {
  --c: var(--cat-a-classer);
  display: inline-flex;
  align-items: center;
  gap: 6px;
  max-width: 100%;
  padding: 2px 10px 2px 8px;
  border-radius: var(--radius-pill);
  background: color-mix(in srgb, var(--c) 14%, transparent);
  color: var(--text);
  font-size: var(--text-xs);
  font-weight: 600;
  white-space: nowrap;
}

.cat::before {
  content: "";
  flex: none;
  width: 8px;
  height: 8px;
  border-radius: 50%;
  background: var(--c);
}

/* « À classer » : contour en pointillés pour attirer l'œil sans alarmer */
.cat.c-a-classer {
  background: transparent;
  outline: 1px dashed var(--c);
  outline-offset: -1px;
}

.dot {
  --c: var(--cat-a-classer);
  display: inline-block;
  flex: none;
  width: 10px;
  height: 10px;
  border-radius: 50%;
  background: var(--c);
}

.c-logement { --c: var(--cat-logement); }
.c-courses { --c: var(--cat-courses); }
.c-transport { --c: var(--cat-transport); }
.c-restos { --c: var(--cat-restos); }
.c-abonnements { --c: var(--cat-abonnements); }
.c-shopping { --c: var(--cat-shopping); }
.c-loisirs { --c: var(--cat-loisirs); }
.c-sante { --c: var(--cat-sante); }
.c-cadeaux { --c: var(--cat-cadeaux); }
.c-frais { --c: var(--cat-frais); }
.c-autres-dep { --c: var(--cat-autres-dep); }
.c-a-classer { --c: var(--cat-a-classer); }
.c-salaire { --c: var(--cat-salaire); }
.c-aides { --c: var(--cat-aides); }
.c-famille { --c: var(--cat-famille); }
.c-autres-rev { --c: var(--cat-autres-rev); }
.c-epargne { --c: var(--cat-epargne); }

/* Barres de budget : élément natif <progress> (accessible, sans style="")
   Couleur selon l'état : ok < 80 % ≤ attention < 100 % ≤ dépassement */
.progress {
  --bar: var(--ok);
  appearance: none;
  display: block;
  width: 100%;
  height: 8px;
  border: 0;
  border-radius: var(--radius-pill);
  background: var(--track);
  overflow: hidden;
}

.progress::-webkit-progress-bar {
  background: var(--track);
  border-radius: var(--radius-pill);
}

.progress::-webkit-progress-value {
  background: var(--bar);
  border-radius: var(--radius-pill);
}

.progress::-moz-progress-bar {
  background: var(--bar);
  border-radius: var(--radius-pill);
}

.progress.is-warn { --bar: var(--warn-bar); }
.progress.is-over { --bar: var(--danger); }

.status {
  font-size: var(--text-sm);
  color: var(--text-muted);
}

.status.is-warn { color: var(--warn); font-weight: 600; }
.status.is-over { color: var(--danger); font-weight: 600; }

/* Sélecteur de mois */
.month-switcher {
  display: inline-flex;
  align-items: center;
  gap: var(--space-1);
  padding: 4px;
  border: 1px solid var(--border);
  border-radius: var(--radius-pill);
  background: var(--surface);
}

.month-switcher .icon-btn {
  width: 32px;
  height: 32px;
  border: 0;
}

.month-switcher span {
  min-width: 7.5rem;
  text-align: center;
  font-weight: 600;
  font-size: var(--text-sm);
}

/* Montant mis en valeur : les euros en grand, les centimes en retrait.
   C'est l'élément signature de l'interface. */
.money {
  display: inline-flex;
  align-items: baseline;
  font-variant-numeric: tabular-nums;
  font-weight: 750;
  letter-spacing: -0.035em;
  line-height: 1;
}

.money .cents {
  margin-left: 0.04em;
  font-size: 0.42em;
  font-weight: 650;
  letter-spacing: 0;
  color: var(--text-muted);
}

.money-hero {
  font-size: var(--text-hero);
}

.money-md {
  font-size: var(--text-2xl);
}

/* État vide : illustration + phrase utile + action */
.empty {
  display: grid;
  justify-items: center;
  gap: var(--space-3);
  padding: var(--space-7) var(--space-4);
  text-align: center;
}

.empty svg {
  width: 120px;
  height: auto;
  margin-bottom: var(--space-2);
}

.empty-paper { fill: var(--accent-soft); }
.empty-lines { color: var(--accent); }
.empty-badge-bg { fill: var(--surface); stroke: var(--accent); }
.empty-badge { color: var(--accent); }

.empty p {
  max-width: 34ch;
  color: var(--text-muted);
}

/* ---------- 6. Écrans ---------- */

/* --- Connexion --- */
.login {
  display: grid;
  min-height: 100dvh;
}

.login-aside {
  display: none;
}

.login-main {
  display: grid;
  place-items: center;
  padding: var(--space-6) var(--space-4);
}

.login-card {
  width: 100%;
  max-width: 400px;
  display: grid;
  gap: var(--space-5);
}

.login-card .brand {
  font-size: var(--text-xl);
}

.login-card .brand-mark {
  width: 36px;
  height: 36px;
}

.login-form {
  display: grid;
  gap: var(--space-4);
}

.login-note {
  display: flex;
  gap: var(--space-2);
  font-size: var(--text-sm);
  color: var(--text-muted);
}

.login-note svg {
  flex: none;
  width: 18px;
  height: 18px;
  margin-top: 2px;
}

.login-theme {
  position: fixed;
  top: var(--space-4);
  right: var(--space-4);
}

@media (min-width: 900px) {
  .login {
    grid-template-columns: minmax(380px, 5fr) 6fr;
  }

  .login-aside {
    display: flex;
    flex-direction: column;
    justify-content: space-between;
    padding: var(--space-7);
    background: var(--accent);
    color: var(--on-accent);
  }

  .login-aside .brand {
    color: inherit;
  }

  .login-aside .brand-mark {
    color: inherit;
  }

  .login-aside h2 {
    max-width: 16ch;
    font-size: clamp(1.75rem, 3vw, 2.5rem);
    line-height: 1.15;
    letter-spacing: -0.02em;
  }

  .login-aside p {
    max-width: 36ch;
    margin-top: var(--space-4);
    opacity: 0.85;
  }

  /* Le mois en 31 barres : une barre par jour de dépenses */
  .month-bars {
    width: 100%;
    max-width: 420px;
    height: auto;
    color: var(--on-accent);
  }

  .month-bars rect {
    fill: currentColor;
    opacity: 0.85;
  }

  /* Jours pas encore passés */
  .month-bars .mb-future {
    opacity: 0.3;
  }

  .login-card .brand {
    display: none;
  }
}

/* --- Tableau de bord --- */
.dash {
  display: grid;
  gap: var(--space-5);
}

.hero {
  display: grid;
  gap: var(--space-3);
  padding: var(--space-2) 0 var(--space-3);
}

.hero-label {
  font-size: var(--text-lg);
  color: var(--text-muted);
}

/* Jauge du mois : la barre = part des revenus déjà partie,
   le trait vertical = où en est le mois (jour 28 sur 31) */
.pace {
  display: grid;
  gap: var(--space-2);
  max-width: 560px;
}

.pace-gauge {
  width: 100%;
  height: 14px;
  border-radius: var(--radius-pill);
  overflow: hidden;
}

.pace-track { fill: var(--track); }
.pace-fill {
  fill: var(--ok);
  transform-origin: left center;
  animation: grow 700ms var(--ease) both;
}
.pace-fill.is-warn { fill: var(--warn-bar); }
.pace-fill.is-over { fill: var(--danger); }
.pace-today { stroke: var(--text); stroke-width: 2; }

@keyframes grow {
  from { transform: scaleX(0); }
  to { transform: scaleX(1); }
}

.pace-legend {
  display: flex;
  justify-content: space-between;
  gap: var(--space-3);
  font-size: var(--text-sm);
  color: var(--text-muted);
}

/* Revenus / dépenses / épargne : un seul panneau découpé en trois */
.stats {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  padding: 0;
}

.stat {
  display: grid;
  align-content: start;
  gap: var(--space-1);
  padding: var(--space-4) var(--space-3);
}

@media (min-width: 480px) {
  .stat {
    padding: var(--space-4);
  }
}

.stat + .stat {
  border-left: 1px solid var(--border);
}

.stat-label {
  display: flex;
  align-items: center;
  gap: 6px;
  font-size: var(--text-sm);
  color: var(--text-muted);
}

.stat .amount {
  font-size: var(--text-lg);
  font-weight: 700;
}

.stat-note {
  font-size: var(--text-xs);
  color: var(--text-muted);
}

/* Liste des budgets */
.budgets {
  display: grid;
  gap: var(--space-4);
  margin: 0;
  padding: 0;
  list-style: none;
}

.budget {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: var(--space-2) var(--space-3);
  align-items: center;
}

.budget-name {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  font-weight: 600;
}

.budget-figures {
  font-size: var(--text-sm);
  color: var(--text-muted);
}

.budget-figures strong {
  color: var(--text);
}

.budget .progress,
.budget .status {
  grid-column: 1 / -1;
}

.budget .status {
  margin-top: -2px;
}

.no-cap {
  margin-top: var(--space-5);
  padding-top: var(--space-4);
  border-top: 1px solid var(--border);
  display: grid;
  gap: var(--space-2);
  font-size: var(--text-sm);
}

.no-cap-row {
  display: flex;
  align-items: center;
  gap: var(--space-2);
}

.no-cap-row .amount {
  margin-left: auto;
}

/* Graphique en anneau */
.donut-wrap {
  display: grid;
  grid-template-columns: 140px 1fr;
  gap: var(--space-5);
  align-items: center;
}

.donut {
  width: 140px;
  height: 140px;
}

.donut circle {
  fill: none;
  stroke-width: 5;
}

.donut .donut-hole-label {
  fill: var(--text-muted);
  font-size: 4px;
  font-weight: 600;
}

.donut .donut-hole-value {
  fill: var(--text);
  font-size: 6px;
  font-weight: 750;
}

.seg-logement { stroke: var(--cat-logement); }
.seg-courses { stroke: var(--cat-courses); }
.seg-restos { stroke: var(--cat-restos); }
.seg-transport { stroke: var(--cat-transport); }
.seg-abonnements { stroke: var(--cat-abonnements); }
.seg-loisirs { stroke: var(--cat-loisirs); }
.seg-shopping { stroke: var(--cat-shopping); }
.seg-autres { stroke: var(--cat-autres-dep); }

.legend {
  display: grid;
  gap: var(--space-2);
  margin: 0;
  padding: 0;
  list-style: none;
  font-size: var(--text-sm);
}

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

.legend .amount {
  margin-left: auto;
  color: var(--text-muted);
}

/* Graphique en barres budget / dépensé */
.bars {
  width: 100%;
  height: auto;
}

/* Le plafond est dessiné en pointillés PAR-DESSUS la barre dépensée,
   pour qu'on voie où il se trouve même en cas de dépassement */
.bars .bar-budget { fill: none; stroke: var(--text-muted); stroke-width: 1.5; stroke-dasharray: 3 3; }
.bars .bar-spent { fill: var(--ok); }
.bars .bar-spent.is-warn { fill: var(--warn-bar); }
.bars .bar-spent.is-over { fill: var(--danger); }
.bars .bar-label { fill: var(--text-muted); font-size: 10px; text-anchor: middle; }
.bars .axis { stroke: var(--border); }

.bars-legend {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-4);
  margin-top: var(--space-3);
  font-size: var(--text-xs);
  color: var(--text-muted);
}

.bars-legend span {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}

.key {
  display: inline-block;
  width: 12px;
  height: 12px;
  border-radius: 3px;
  background: var(--ok);
}

.key-budget {
  background: transparent;
  border: 1.5px dashed var(--text-muted);
}

@media (max-width: 380px) {
  .donut-wrap {
    grid-template-columns: 1fr;
    justify-items: center;
  }

  .legend {
    width: 100%;
  }
}

@media (min-width: 960px) {
  .dash {
    grid-template-columns: 7fr 5fr;
    align-items: start;
  }

  .hero,
  .stats,
  .dash-wide {
    grid-column: 1 / -1;
  }

  .dash-side {
    display: grid;
    gap: var(--space-5);
  }
}

/* --- Liste d'opérations --- */
.filters {
  display: grid;
  gap: var(--space-3);
  margin-bottom: var(--space-5);
}

.search {
  position: relative;
}

.search svg {
  position: absolute;
  top: 50%;
  left: var(--space-4);
  width: 18px;
  height: 18px;
  color: var(--text-muted);
  transform: translateY(-50%);
  pointer-events: none;
}

.search .input {
  padding-left: 2.75rem;
}

.chips {
  display: flex;
  gap: var(--space-2);
  overflow-x: auto;
  margin: 0;
  padding: 2px;
  list-style: none;
  scrollbar-width: none;
}

.chip {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  min-height: 36px;
  padding: 0 var(--space-4);
  border: 1px solid var(--border);
  border-radius: var(--radius-pill);
  background: var(--surface);
  color: var(--text);
  font: inherit;
  font-size: var(--text-sm);
  font-weight: 600;
  white-space: nowrap;
  cursor: pointer;
}

.chip[aria-pressed="true"] {
  background: var(--text);
  border-color: var(--text);
  color: var(--bg);
}

.chip .count {
  font-variant-numeric: tabular-nums;
  opacity: 0.7;
}

.summary {
  display: flex;
  flex-wrap: wrap;
  gap: var(--space-2) var(--space-5);
  margin-bottom: var(--space-4);
  font-size: var(--text-sm);
  color: var(--text-muted);
}

.summary strong {
  color: var(--text);
}

.day {
  margin-bottom: var(--space-5);
}

.day-head {
  display: flex;
  justify-content: space-between;
  padding: 0 var(--space-1) var(--space-2);
  font-size: var(--text-sm);
  font-weight: 600;
  color: var(--text-muted);
}

.ops {
  margin: 0;
  padding: 0;
  list-style: none;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  box-shadow: var(--shadow-1);
  overflow: hidden;
}

.op {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: var(--space-1) var(--space-3);
  align-items: center;
  padding: var(--space-3) var(--space-4);
}

.op + .op {
  border-top: 1px solid var(--border);
}

.op-label {
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  font-weight: 600;
}

.op .amount {
  font-weight: 700;
  text-align: right;
}

.op-meta {
  display: flex;
  align-items: center;
  gap: var(--space-2);
  min-width: 0;
}

.op-meta .op-date {
  display: none;
}

.op-action {
  justify-self: end;
}

/* Opération à classer : légère teinte pour la repérer dans la liste */
.op.is-unsorted {
  background: color-mix(in srgb, var(--accent-soft) 45%, transparent);
}

/* Virement d'épargne : montant atténué, il ne compte pas comme dépense */
.op.is-saving .amount {
  color: var(--cat-epargne);
}

.op-note {
  font-size: var(--text-xs);
  color: var(--text-muted);
}

@media (min-width: 720px) {
  .filters {
    grid-template-columns: 1fr 220px;
  }

  .filters .chips {
    grid-column: 1 / -1;
  }

  .op {
    grid-template-columns: minmax(0, 1fr) 200px 120px;
    padding: var(--space-3) var(--space-5);
  }

  .op-meta {
    grid-column: 2;
    grid-row: 1;
  }

  .op .amount {
    grid-column: 3;
    grid-row: 1;
  }

  .op-label-wrap {
    grid-column: 1;
    grid-row: 1;
    min-width: 0;
  }
}

/* --- Navigation : rubriques des jalons suivants, grisées --- */
.nav .is-soon {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 2px;
  height: 100%;
  color: var(--text-muted);
  font-size: 0.6875rem;
  font-weight: 600;
  opacity: 0.45;
  cursor: not-allowed;
}

.nav .is-soon svg {
  width: 22px;
  height: 22px;
}

@media (min-width: 960px) {
  .nav .is-soon {
    flex-direction: row;
    justify-content: flex-start;
    gap: var(--space-3);
    padding: var(--space-2) var(--space-3);
    font-size: var(--text-sm);
  }
}

/* --- Bouton de déconnexion (formulaire POST, avec jeton CSRF) --- */
.logout-form {
  margin: 0;
}

/* --- Page d'erreur --- */
.error-card {
  min-height: 60dvh;
  align-content: center;
}

.error-card .brand {
  display: inline-flex;
}

.error-code {
  margin-bottom: var(--space-2);
  color: var(--text-muted);
  font-weight: 600;
}

/* --- Page de diagnostic --- */
code {
  padding: 1px 6px;
  border-radius: 6px;
  background: var(--surface-2);
  font-size: 0.9em;
  overflow-wrap: anywhere;
}

.diag {
  display: grid;
  gap: var(--space-5);
  max-width: 760px;
}

.diag-list {
  display: grid;
  gap: var(--space-4);
  margin: 0;
}

.diag-row {
  display: grid;
  gap: var(--space-1);
}

.diag-row dt {
  font-size: var(--text-sm);
  font-weight: 600;
}

.diag-row dd {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: var(--space-2) var(--space-3);
  margin: 0;
  font-size: var(--text-sm);
}

@media (min-width: 720px) {
  .diag-row {
    grid-template-columns: 260px 1fr;
  }
}
