:root{
  /* Couleurs SKHUB — les VRAIES, reprises du :root du site skhub.fr :
     --vert #43A074, --vert-d #165A2F, --vert-clair #E8F4EE, --jaune #FFFE78,
     accent corail --orange/--rose #E73B1A. Le logo ajoute un vert vif #50CC89.
     Rien n'est approché. Le vert vif #43A074 sert d'IDENTITÉ (accents, avatars,
     dégradés, puces) ; les boutons à texte blanc passent par --brand-fonce, plus
     foncé, pour rester lisibles (4,5:1) — #43A074 sous texte blanc n'est qu'à 3,25:1. */
  --brand:#43A074; --brand-2:#50CC89; --brand-3:#7BD9A8;
  --brand-fonce:#2C7B54;   /* vert profond : fond des boutons à texte blanc + survol */
  --yellow:#FFFE78; --yellow-ink:#5C5600;   /* le jaune du site, sans variante */
  --orange:#E73B1A; --rouge:#E73B1A;   /* l'accent corail de la marque */
  --rail:#165A2F; --rail-2:#1E7A47;   /* le vert foncé SKHUB (--vert-d du site) */
  /* ⚠️ LE RAIL RESTE VERT — essayé en clair le 27/08/2026, REFUSÉ le 28
     (Antonio : « la couleur du side reste vert »). La colonne claire est la
     règle des SaaS relevés, mais ici la colonne EST l'identité : c'est le seul
     endroit où le vert SKHUB tient toute la hauteur de l'écran. Ne pas
     refaire la bascule en croyant « moderniser » — elle a été vue et écartée.
     Ce qui est resté de ce passage : le logo EN COULEUR (posé sur une plaque
     claire, faute de quoi il serait vert sur vert), et les onglets qui ne
     vivent plus qu'en haut. */

  --bg:#F2F8F4; --surface:#fff; --surface-2:#F7FBF8; --surface-3:#EBF3EE;
  --text:#132018; --text-2:#4F6259; --text-3:#5A6F65;   /* 5,4:1 sur blanc, 4,8:1 sur teinte */
  --line:#DDEAE2; --line-2:#C3D8CC;

  /* ── Le vert de la NAVIGATION (demande d'Antonio, 13/08/2026) ─────────────
     #3bae79 est la couleur des indicateurs qui disent « vous êtes ici » :
     le trait sous l'onglet ouvert, le voile de l'application ouverte dans le
     rail, le cerne du focus. Il ne sert JAMAIS de couleur de texte : mesuré,
     #3bae79 sur blanc ne monte qu'à 2,8:1 (il en faut 4,5:1). Le libellé de
     l'onglet ouvert prend donc --vif-ink, la même teinte assombrie, à 5,3:1.
     Sur le rail vert foncé c'est l'inverse : #3bae79 plein n'y ferait que
     2,1:1, il n'y entre donc qu'en VOILE (le fond de la pastille active,
     texte blanc à 4,7:1) et le repère latéral reste jaune, à 5,6:1. */
  --vif:#3bae79;                       /* l'indicateur, jamais du texte */
  --vif-ink:#217A52;                   /* sa version lisible : 5,3:1 sur blanc */
  --vif-t:#E6F6EE;                     /* son voile clair */
  --vif-ring:rgba(59,174,121,.34);     /* son cerne */
  --vif-voile:rgba(59,174,121,.20);    /* son voile sur le rail foncé */
  /* La courbe de tous les mouvements de navigation : départ franc, arrivée
     posée. Déjà celle de la sous-navigation — un seul rythme pour tout. */
  --nav-courbe:cubic-bezier(.32,.72,0,1);

  /* Teintes de module : cinq nuances de vert et une jaune. */
  --t-verte:#DCF2E7;  --t-verte-i:#1A7A52;
  --t-menthe:#CDEDDD; --t-menthe-i:#146848;
  --t-sauge:#E2EFE7;  --t-sauge-i:#2F6449;
  --t-foret:#BFE6D3;  --t-foret-i:#0E5238;
  --t-jaune:#FFFE78;  --t-jaune-i:#5C5600;   /* le vrai jaune du site (#FFFE78), plus délavé */
  --t-bleue:#E0EAF6;  --t-bleue-i:#1A5497;
  --t-rouge:#FCE4DD;  --t-rouge-i:#B12C13;

  --ok:#1A7A52; --ok-bg:#DCF2E7;
  --att:#5C5600; --att-bg:#FFFE78;      /* le jaune de la marque (#FFFE78) */
  --alr:#C22E13; --alr-bg:#FCE4DD;      /* le corail de la marque (#E73B1A), assombri pour le texte (4,9:1) */
  --inf:#1A5497; --inf-bg:#E0EAF6;

  /* ── Palette HÉRITÉE de l'écosystème SKHUB (ciblage, console, dashboard comm,
     pilotage SKHUB) : ces outils déclarent encore l'ancien vert #28825A, le jaune
     #F8F878 et le rouge #C00020 dans LEUR :root. La charte est lue depuis UNITOOLS
     (tests/09), donc on garde ces valeurs reconnues le temps que ces outils migrent
     vers la palette du site. UNITOOLS ne s'en sert plus : jetons de compatibilité,
     pas des couleurs vivantes — à retirer une fois l'écosystème repeint. */
  --compat-1:#28825A; --compat-2:#3CB478; --compat-3:#5FCE96; --compat-4:#1F6A48;
  --compat-5:#F8F878; --compat-6:#C00020; --compat-7:#16553A; --compat-8:#1E6A45;
  --compat-9:#FBE3E6; --compat-10:#A5001B;

  --r:8px; --r-lg:12px; --r-xl:16px;
  --sh-1:0 1px 2px rgba(19,32,24,.04);
  --sh-2:0 1px 3px rgba(19,32,24,.07),0 6px 16px -6px rgba(19,32,24,.10);
  --sh-3:0 2px 6px rgba(19,32,24,.08),0 18px 40px -12px rgba(19,32,24,.20);
  --font:-apple-system,BlinkMacSystemFont,'Segoe UI',system-ui,Roboto,'Helvetica Neue',Arial,sans-serif;
  --mono:ui-monospace,SFMono-Regular,Menlo,Consolas,monospace;
}
*{margin:0;padding:0;box-sizing:border-box}
html{color-scheme:light}
body{font-family:var(--font);background:var(--bg);color:var(--text);font-size:13px;line-height:1.55;
  font-variant-numeric:tabular-nums;
  -webkit-font-smoothing:antialiased}
button,input,select,textarea{font:inherit;color:inherit}
button,[role=button],.uni,.modx,.chip,.tabx,.seg button,.cmd-row,.fil,.obj,.dem{cursor:pointer}
/* L'anneau de focus doit atteindre 3:1 (critere 1.4.11). --brand vaut
   desormais le vert vif #43A074 (3,25:1 sur blanc : ca passe, mais de justesse).
   On prend --brand-fonce (#2C7B54, 4,7:1) : meme famille de vert, anneau franc. */
:focus-visible{outline:2px solid var(--brand-fonce);outline-offset:1px;border-radius:3px}
svg{display:block;flex:none}
/* Un mot seul sur la dernière ligne d'un titre : le navigateur rééquilibre. */
h1,h2,h3,h4,h5,.card-title,.page-title,.dec .t,.obj .t{text-wrap:balance}
.card-sub,.msg span,.dec .d,.app p{text-wrap:pretty}
code,kbd{font-family:var(--mono);font-size:.88em;background:var(--surface-3);border-radius:4px;padding:1px 5px}
kbd{border:1px solid var(--line-2);box-shadow:0 1px 0 var(--line-2);font-size:11px;padding:2px 5px;
  color:var(--text-2)}
/* Un raccourci posé sur un bouton foncé garde son contraste. */
.btn-main kbd{background:rgba(0,0,0,.22);border-color:rgba(255,255,255,.26);
  box-shadow:none;color:#fff}
a{color:var(--t-verte-i)}
@media(prefers-reduced-motion:reduce){*,*::before,*::after{
  animation-duration:.01ms!important;transition-duration:.01ms!important}}

/* Icônes bicolores : forme pleine en fond, détails en trait par-dessus. */
/* Icônes pleines, monochromes : à 16-20 px dans une interface dense, un aplat
   se lit mieux qu'un trait, et ne dépend pas de l'épaisseur rendue par l'écran. */
svg[data-ic] path,svg[data-ic] circle,svg[data-ic] rect{fill:currentColor}
.ic-fg{fill:none;stroke:currentColor;stroke-width:1.7;stroke-linecap:round;stroke-linejoin:round}
/* Une icône qui remplace une autre ne doit pas apparaître d'un coup :
   opacité, échelle et flou lui donnent une matière. */
@keyframes icoEntre{from{opacity:0;scale:.82;filter:blur(3px)}to{opacity:1;scale:1;filter:blur(0)}}
.opt .ck svg,#st-b svg{animation:icoEntre .2s cubic-bezier(.34,1.56,.64,1)}

#shell{display:grid;grid-template-columns:92px 1fr;min-height:100vh}

/* ══════════ Rail des UNIVERS ══════════
   Antonio, 28/08/2026 : « fais vraiment comme celle dans Mobbin ». Le modèle
   relevé (Salesforce Lightning) porte à gauche une colonne ÉTROITE et sombre
   où chaque entrée est une icône avec son mot dessous, et en haut, sur fond
   clair, le nom de l'application suivi de ses sections en rangée.

   Transposé ici, TROIS niveaux à TROIS endroits, aucun répété — c'est la
   demande du 27/08, « je ne veux pas de doublon » :
     · le rail        : les sept UNIVERS (Général, Direction, Recrutement…) ;
     · la barre haute : les APPLICATIONS de l'univers ouvert (.modbar) ;
     · l'écran        : ses ONGLETS (.tabx-bar).

   Pourquoi les univers dans le rail, et non les vingt applications : à 76 px
   une entrée tient UN mot, pas « Contrats et financement » — et le modèle
   lui-même n'a que neuf entrées dans sa colonne. Aucune application ne s'en
   trouve rangée plus loin : elles sont toutes visibles en haut, à un clic,
   dès que leur univers est ouvert.

   Le rail reste VERT (Antonio, 28/08 : « la couleur du side reste vert ») :
   c'est le seul endroit où le vert SKHUB tient toute la hauteur de l'écran.
   Le logo, lui, a rejoint la barre blanche du haut — la place qu'occupe le
   nuage dans le modèle, et la seule où sa version EN COULEUR se lit. */
/* `overflow:visible` et non `hidden` : le menu du compte s'ouvre À CÔTÉ de la
   colonne, et un rail qui rogne le rognait — on cliquait, aria-expanded passait
   à vrai, et rien n'apparaissait. Ce n'est pas la colonne qui doit contenir le
   débordement, c'est la LISTE (#nav) qui défile dans sa propre boîte. */
.rail{background:linear-gradient(178deg,#1E7A47,#1B7241 340px);color:#fff;
  display:flex;flex-direction:column;align-items:center;padding:10px 6px 8px;
  position:sticky;top:0;height:100vh;overflow:visible;z-index:25}
/* C'est la LISTE qui defile, pas le rail entier — sans quoi le pied s'en va
   avec elle. min-height:0 est obligatoire : sans lui, un enfant flex refuse de
   passer sous la taille de son contenu et ne defile jamais. */
#nav{flex:0 1 auto;overflow-y:auto;min-height:0;width:100%;
  display:flex;flex-direction:column;gap:2px;scrollbar-width:none}
#nav::-webkit-scrollbar{display:none}

/* Texte lu mais non vu. Un repere purement graphique (un point, une barre)
   doit porter son equivalent ecrit, sinon l'information n'existe que pour qui
   voit — c'est le critere 1.3.1, et 1.4.1 quand la couleur fait le sens. */
.sr-seul{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;
  clip:rect(0 0 0 0);white-space:nowrap;border:0}

/* Une entrée d'univers : l'icône, le mot dessous. 60 px de haut — très au delà
   des 24 px du critère 2.5.8, et la même cible pour la souris que pour le
   doigt. Le libellé est en 9,5 px MAIS en blanc à 90 % sur le vert du rail
   (7,4:1) : la petite taille ne se paie pas en contraste. */
.uni{display:flex;flex-direction:column;align-items:center;justify-content:center;gap:5px;
  width:100%;min-height:60px;padding:8px 4px;border:none;background:none;border-radius:10px;
  color:rgba(255,255,255,.90);font-size:11px;font-weight:600;line-height:1.15;letter-spacing:.005em;
  text-align:center;position:relative;transition:background .18s,color .18s}
.uni .ic{display:block;line-height:0;color:rgba(255,255,255,.92)}
/* Le mot ne se coupe JAMAIS au milieu : `overflow-wrap:anywhere` donnait
   « Recruteme / nt » et « Administrat / ion ». La colonne s'est élargie à
   84 px pour que les sept noms tiennent entiers, sur une ou deux lignes. */
.uni .lbl{display:block;max-width:100%;overflow-wrap:normal;word-break:keep-all;hyphens:none}
.uni:hover{background:rgba(255,255,255,.10);color:#fff}
.uni.on,.uni.on:hover{background:var(--vif-voile);color:#fff;
  box-shadow:inset 0 0 0 1px rgba(255,255,255,.16)}
.uni.on .ic{color:var(--brand-3)}
/* Le repère reste JAUNE : sur ce vert foncé, #3bae79 plein ne ferait que
   2,1:1 quand le jaune monte à 5,6:1. Il est DANS l'entrée et non au bord du
   rail — la liste défile, et un enfant qui sort à gauche d'une boîte qui
   défile est rogné (le repère avait ainsi disparu de l'écran sans que
   personne le voie, la pastille, elle, se voyant). */
.uni.on::before{content:'';position:absolute;left:0;top:9px;bottom:9px;width:3px;
  border-radius:3px;background:var(--yellow);animation:marque .3s var(--nav-courbe)}
@keyframes marque{from{transform:scaleY(.15);opacity:0}to{transform:scaleY(1);opacity:1}}
/* Un point, pas un compte : « il y a quelque chose à voir dans cet univers ».
   Le nombre exact s'affiche dans l'écran, c'est là qu'on en fait quelque chose. */
.uni .pt{position:absolute;top:7px;right:8px;width:6px;height:6px;border-radius:50%;
  background:var(--yellow);box-shadow:0 0 0 2px rgba(0,0,0,.14)}

/* LE PIED VA AU BAS DE LA COLONNE (Antonio, 28/08/2026 : « mets en bas de
   page de la side navigation »). `margin-top:auto` le pousse tout en bas :
   sept univers ne remplissent pas 900 px de haut, et le compte flottait au
   milieu du vert, à hauteur du contenu.
   Il ne recouvre jamais la liste pour autant : c'est #nav qui défile dans sa
   boîte, le pied est un frère qui ne bouge pas — un élément épinglé, lui,
   passerait PAR-DESSUS la dernière entrée (essayé en août, vu à l'écran). */
.rail-foot{flex:none;width:100%;margin-top:auto;padding-top:10px;
  border-top:1px solid rgba(255,255,255,.14)}
/* Bouton d'installation (PWA), masqué tant que le navigateur ne le propose pas
   (révélé par app-installable.js sur beforeinstallprompt). */
.rail-install{display:block;width:100%;margin-bottom:8px;padding:6px 4px;font:inherit;
  font-size:11px;font-weight:600;line-height:1.2;color:#fff;background:rgba(255,255,255,.10);
  border:1px solid rgba(255,255,255,.22);border-radius:8px;cursor:pointer;text-align:center;
  transition:background .15s}
.rail-install:hover{background:rgba(255,255,255,.18)}
/* Le partage reprend la pilule de l'installation : deux gestes voisins, un
   seul dessin. L'icône est à 14 px, le cran « dans une ligne de texte » de
   l'échelle du 26/08 — le rail est étroit, une icône de 19 y pousserait le mot
   hors du bouton. */
.rail-partage{display:flex;align-items:center;justify-content:center;gap:6px}
.rail-partage svg{width:14px;height:14px;flex:none}
/* LA PHOTO EST EN BAS DU RAIL, ET ELLE Y EST SEULE (Antonio, 28/08/2026 :
   « la photo sur le side navigation mettre en bas », « je ne veux plus de
   doublon »). Elle était à DEUX endroits : en haut à droite de la barre, et
   ici — deux avatars de la même personne à trente centimètres, dont un seul
   ouvrait le menu. C'est le bouton du bas qui l'ouvre désormais ; celui de la
   barre a disparu. Le compte ferme la colonne, comme « Your Account » ferme
   celle du modèle.
   Le nom et la fonction restent écrits pour les lecteurs d'écran : ils ne
   tiendraient pas à 84 px, mais les retirer priverait quelqu'un de l'info. */
.me-zone{position:relative;width:100%}
.me{display:flex;flex-direction:column;align-items:center;gap:7px;width:100%;
  padding:11px 4px;border:none;background:none;border-radius:12px;font-family:inherit;
  color:rgba(255,255,255,.90);font-size:11px;font-weight:600;line-height:1.15;text-align:center;
  transition:background .18s}
/* « Mon compte » passe à la ligne au lieu d'être coupé — comme « Your Account »
   dans le modèle, qui tient sur deux lignes lui aussi. */
.me .lbl{display:block;max-width:100%}
.me:hover,.me[aria-expanded=true]{background:rgba(255,255,255,.10);color:#fff}
/* La photo n'est pas une pastille écrasée : 34 px, une tuile carrée autour
   d'elle et de son mot (Antonio, 28/08 : « la partie photo est devenue
   aplatie »). Un rond de 30 px dans un fond large et bas se lit comme un
   bouton compressé ; la tuile lui rend sa hauteur. */
/* Le menu s'ouvre À DROITE et VERS LE HAUT : en bas d'une colonne, il n'y a
   de place ni dessous, ni dedans. */
.me-zone .pop{left:calc(100% + 8px);right:auto;top:auto;bottom:0;transform-origin:left bottom}
.me .av{width:34px;height:34px;aspect-ratio:1;border-radius:50%;background:rgba(0,0,0,.26);
  display:grid;place-items:center;font-size:12px;font-weight:700;color:#fff;flex:none;
  overflow:hidden;position:relative}
/* Un liseré intérieur sombre détache la photo du vert, sans anneau rapporté. */
.me .av::after{content:'';position:absolute;inset:0;border-radius:50%;
  box-shadow:inset 0 0 0 1px rgba(0,0,0,.18);pointer-events:none}
.me .av img{width:100%;height:100%;object-fit:cover;display:block}

/* ══════════ Cadre ══════════ */
.main{min-width:0;display:flex;flex-direction:column}
/* La barre du haut porte le contexte et l'identité, pas la navigation :
   surface pleine, ombre basse, elle se détache du contenu comme la barre
   de gauche se détache par sa couleur. Deux rôles, deux traitements. */
.topbar{position:sticky;top:0;z-index:20;background:var(--surface);
  border-bottom:1px solid var(--line);box-shadow:0 1px 0 rgba(19,32,24,.04),0 2px 8px -4px rgba(19,32,24,.10);
  padding:0;display:flex;flex-direction:column;align-items:stretch;gap:0}
/* Trois colonnes, comme dans le modèle : la marque à gauche, la recherche AU
   MILIEU, les commandes du compte à droite. La grille 1fr / auto / 1fr est ce
   qui centre vraiment le champ — avec un flex, il se décale dès que la marque
   et les commandes n'ont pas la même largeur. */
.tb-ligne{display:grid;grid-template-columns:1fr minmax(0,auto) 1fr;
  align-items:center;gap:14px;padding:10px 24px}
.tb-ligne .tb-right{justify-self:end}
/* LA MARQUE EST ICI, PAS DANS LE RAIL (28/08/2026) : c'est la place qu'elle
   occupe dans le modèle, et la seule où le logo EN COULEUR se lit — il est
   vert, le rail aussi. Le mot UNITOOLS le suit, séparé d'un filet : SKHUB est
   la maison, UNITOOLS l'outil, ils ne se confondent pas. */
.tb-marque{display:flex;align-items:center;gap:10px;flex:none}
/* 132 px et non 104 : à l'écran, la marque se lisait comme une vignette de
   pied de page. C'est la seule chose de cette barre qui dit de QUI est l'outil,
   elle doit se voir en premier. */
.tb-marque img{width:132px;height:auto;display:block}
.tb-marque .t2{font-size:11px;font-weight:700;letter-spacing:.2em;color:var(--text-2);
  border-left:1px solid var(--line-2);padding-left:11px;white-space:nowrap}

/* La rangée des applications de l'univers ouvert — le « Sales | Leads Contacts
   Accounts » du modèle. Elle vit DANS la barre du haut, même plan blanc, même
   ombre : « où je suis » se lit d'un seul bloc, du logo jusqu'à l'onglet.
   L'onglet ouvert de l'ÉCRAN (.tabx-bar) est plus bas, plus petit et sur le
   fond de la page : deux rangées, deux poids, aucune confusion. */
/* ⚠️ ELLE PASSE A LA LIGNE, ELLE NE DEFILE PLUS (Antonio, 30/08/2026 : « au
   lieu de scroller vaut mieux qu'on descende a la ligne »). La Qualite porte
   dix-sept onglets : au dela de la largeur de l'ecran, les derniers — dont le
   « ? » — vivaient hors du champ, sans barre de defilement pour le dire
   (`scrollbar-width:none`). Un onglet qu'on ne voit pas et dont rien n'annonce
   l'existence n'est pas un onglet, c'est un ecran perdu.
   `amenerLActifDansLaVue()` reste : sans defilement il ne fait rien, et il
   redeviendra utile si une barre redevient etroite. */
.modbar{display:flex;flex-wrap:wrap;align-items:stretch;gap:2px;padding:0 24px;
  border-top:1px solid var(--line)}
.modbar .fam{display:flex;align-items:center;padding-right:15px;margin-right:7px;
  border-right:1px solid var(--line);font-size:14px;font-weight:680;letter-spacing:-.01em;
  color:var(--text);white-space:nowrap;flex:none}
.modx{position:relative;display:inline-flex;align-items:center;gap:7px;flex:none;
  border:none;background:none;padding:11px 13px 10px;font-size:13px;font-weight:550;
  color:var(--text-2);white-space:nowrap;min-height:42px;border-radius:8px 8px 0 0;
  transition:color .18s,background .18s}
.modx:hover{color:var(--text);background:rgba(19,32,24,.045)}
.modx.on,.modx.on:hover{color:var(--vif-ink);font-weight:650;background:none}
.modx.on::after{content:'';position:absolute;left:8px;right:8px;bottom:0;height:3px;
  border-radius:3px 3px 0 0;background:var(--vif)}
.modx .tag{font-size:11px;font-weight:600;letter-spacing:.1em;text-transform:uppercase;
  color:var(--text-3)}
.modx .pt{width:6px;height:6px;border-radius:50%;background:var(--yellow);
  box-shadow:0 0 0 1.5px var(--att)}

/* La recherche et le périmètre ont suivi la marque : ils ne tiennent pas dans
   une colonne de 76 px, et le modèle les porte aussi en haut. */
/* La recherche cède du terrain avant le compte : elle rétrécit (flex 0 1),
   les boutons de droite ne bougent pas. Sans cela, la photo de profil sortait
   de l'écran — le premier élément à disparaître était le DERNIER de la
   rangée, comme en août sur le fil d'Ariane. */
/* Le champ de recherche est une PASTILLE, pas une boîte : c'est la seule
   commande de saisie de cette barre, elle n'a rien à aligner avec les cadres
   de la page. Blanc sur le blanc de la barre, elle ne tiendrait pas — le fond
   teinté et le filet la posent, et le cerne vert la prend au survol comme au
   clavier (le focus compte autant que la souris). */
.cmd-open{display:flex;align-items:center;gap:9px;width:100%;max-width:440px;min-width:104px;
  justify-self:center;background:var(--surface-2);border:1px solid var(--line-2);
  border-radius:99px;padding:8px 14px;color:var(--text-3);font-size:13px;min-height:38px;
  transition:background .18s,border-color .18s,color .18s,box-shadow .18s}
.cmd-open:hover{background:var(--surface);border-color:var(--vif);color:var(--text);
  box-shadow:0 0 0 3px var(--vif-ring)}
.cmd-open:focus-visible{outline:none;background:var(--surface);border-color:var(--vif);
  color:var(--text);box-shadow:0 0 0 3px var(--vif-ring)}
.cmd-open kbd{border-radius:6px}
.cmd-open kbd{margin-left:auto;background:var(--surface);border-color:var(--line-2);
  box-shadow:none;color:var(--text-3)}
.scope{flex:none}
.scope .w{position:relative}
.scope select{background:var(--surface-2);border:1px solid var(--line);border-radius:9px;
  color:var(--text);font-size:12.5px;font-weight:550;padding:7px 28px 7px 10px;
  appearance:none;min-height:36px}
.scope select:hover{background:var(--surface-3)}
.scope .caret{position:absolute;right:9px;top:50%;transform:translateY(-50%);
  color:var(--text-3);pointer-events:none}
.crumb{font-size:11px;color:var(--text-3);margin-bottom:3px;letter-spacing:.01em}
.page-title{font-size:19px;font-weight:680;letter-spacing:-.02em;line-height:1.2}
/* Bandeau d'accueil « Welcome on board ». */
.bienvenue{display:flex;align-items:center;gap:14px;padding:15px 20px;margin-bottom:16px;
  background:linear-gradient(120deg,var(--brand-fonce),var(--rail));color:#fff;border-radius:14px}
.bienvenue .bv-em{font-size:26px;line-height:1;flex:none}
.bienvenue .bv-t{font-size:17px;font-weight:700;letter-spacing:-.01em}
.bienvenue .bv-s{font-size:12.5px;opacity:.86;margin-top:2px}
.tb-right{margin-left:auto;display:flex;align-items:center;gap:10px}

/* ══════════ LA BARRE NE POUSSE JAMAIS L'AVATAR DEHORS ══════════
   Antonio, 24/08/2026 : « sur les barres de fenêtre en Windows […] des fois
   ça cache les photos de profil ».

   Ce n'était pas Windows, c'était `min-width:auto` — la valeur PAR DÉFAUT
   d'un enfant de flex, qui lui interdit de descendre sous la largeur de son
   contenu. Le bloc de gauche (fil d'Ariane + titre) refusait donc de
   rétrécir : « Digitale et numérique · Chantiers » au-dessus de
   « Utilisateurs et droits » poussait `.tb-right` hors du cadre, et le
   premier élément à sortir de l'écran était le DERNIER de la rangée — la
   photo de profil. D'où « des fois » : cela dépend de l'écran ouvert et de
   la largeur de la fenêtre.

   Pourquoi Windows plus souvent que macOS : sa barre de défilement est
   TOUJOURS visible (~15 px de largeur utile en moins, là où macOS la
   superpose) et ses métriques de police sont un peu plus larges. Le même
   titre y déborde donc dans une fenêtre où il tient chez nous — c'est
   pourquoi Antonio ne le voyait pas et l'équipe si.

   Le correctif existait déjà… mais seulement sous 860 px (bloc 1.4.10 plus
   bas), c'est-à-dire jamais sur un poste de bureau. Il vaut à TOUTES les
   largeurs : le titre s'abrège, les commandes ne bougent pas. */
/* Le titre de l'écran ouvre la PAGE. Il n'a plus à tenir sur une ligne dans
   une barre partagée : il a la largeur du contenu, il peut donc redescendre
   au lieu d'être coupé par des points de suspension. */
.page-tete{min-width:0;margin-bottom:18px}
/* Titre effacé : la ligne ne garde que le bouton Retour, elle se resserre. */
.page-tete:has(.page-title.sr-seul){margin-bottom:10px}
.page-tete .crumb{min-width:0}
.page-tete #crumb{overflow-wrap:anywhere}
/* Les commandes (espace, cloche, compte) ne se compriment jamais : ce sont
   elles qu'on perdait. Le titre est ce qui doit céder — on le relit dans la
   page, l'avatar non. */
.tb-right{flex:none}

/* L'espace n'est pas un champ de formulaire, c'est une signature. Un fanion de sa
   couleur le porte, le nom suffit, et le chevron ne se montre qu'au survol. Ouvert,
   la commande prend la couleur de l'espace : elle EST le statut, pas un menu de plus.
   Le nom fixe (non-admin) utilise exactement la même forme : même famille, un cran
   plus calme, sans commande. */
.role-btn,.espace-fixe{position:relative;display:flex;align-items:center;gap:9px;
  background:none;border:none;padding:7px 12px 7px 10px;min-height:38px;border-radius:99px;
  color:var(--text);transition:background .18s cubic-bezier(.32,.72,0,1),color .18s}
.role-btn::before,.espace-fixe::before{content:'';width:3.5px;height:17px;border-radius:2px;
  flex:none;background:var(--espace,var(--brand-2));
  transition:height .2s cubic-bezier(.34,1.56,.64,1)}
.role-btn .l,.espace-fixe .l{font-size:13px;font-weight:620;color:inherit;white-space:nowrap;
  letter-spacing:-.005em}
.role-btn .chev{display:flex;color:currentColor;opacity:0;transform:translateX(-3px);
  transition:opacity .18s,transform .18s cubic-bezier(.32,.72,0,1)}
.role-btn:hover,.role-btn:focus-visible{background:var(--surface-2)}
.role-btn:hover .chev,.role-btn:focus-visible .chev{opacity:.55;transform:none}
.role-btn[aria-expanded=true]{background:var(--espace-fond,var(--t-verte));color:var(--espace)}
.role-btn[aria-expanded=true]::before{height:21px}
.role-btn[aria-expanded=true] .chev{opacity:1;transform:rotate(180deg)}
@media(max-width:860px){.role-btn .l,.espace-fixe .l{max-width:88px;overflow:hidden;
  text-overflow:ellipsis}}


/* TOUTE LA LARGEUR, GAUCHE ET DROITE (Antonio, 30/08/2026 : « domine la page
   gauche et droite en respectant les espaces »). Les 1360 px etaient une
   mesure de lecture posee le 25/08 ; elle est levee pour tous les ecrans, et
   ce sont les 24 px de gouttiere qui font desormais le seul retrait. */
.content{padding:24px 24px 64px;max-width:none;width:100%}
/* 1360 px est une MESURE DE LECTURE : elle protège les écrans où l'on lit
   (un compte rendu, un article, un tableau de contrats) d'une ligne de texte
   trop longue pour que l'œil retrouve la suivante. L'accueil ne lit rien : il
   MONTRE. Sur une machine de 1920, la mesure ne lui donnait qu'un tiers
   d'écran vide à droite. Antonio, 25/08/2026 : « domine bien toute la place,
   un vrai accueil d'outils. » Il prend donc la largeur — lui seul, et la
   règle reste entière pour les vingt autres écrans. */
.content.plein{max-width:none}
.view{display:none}.view.on{display:block;animation:up .28s cubic-bezier(.32,.72,0,1)}
/* Une liste qui apparaît d'un bloc paraît lourde : 70 ms entre chaque ligne,
   plafonnés à six pour que l'ensemble reste sous 400 ms. */
.view.on .chaine,.view.on .dec,.view.on .rk{animation:monteLeger .3s ease-out both}
.view.on .chaine:nth-child(1),.view.on .dec:nth-child(1),.view.on .rk:nth-child(1){animation-delay:0ms}
.view.on .chaine:nth-child(2),.view.on .dec:nth-child(2),.view.on .rk:nth-child(2){animation-delay:70ms}
.view.on .chaine:nth-child(3),.view.on .dec:nth-child(3),.view.on .rk:nth-child(3){animation-delay:140ms}
.view.on .dec:nth-child(4),.view.on .rk:nth-child(4){animation-delay:200ms}
.view.on .dec:nth-child(5),.view.on .rk:nth-child(5){animation-delay:250ms}
.view.on .dec:nth-child(n+6),.view.on .rk:nth-child(n+6){animation-delay:290ms}
@keyframes monteLeger{from{opacity:0;transform:translateY(8px)}to{opacity:1;transform:none}}
@keyframes up{from{opacity:0;transform:translateY(8px)}to{opacity:1;transform:none}}

/* Titre de section : hiérarchie typographique, pas une boîte de plus */
.sec{display:flex;align-items:baseline;gap:12px;margin:24px 0 8px}
.sec:first-child{margin-top:0}
.sec h2{font-size:12px;font-weight:650;letter-spacing:.09em;text-transform:uppercase;color:#247852;
  position:relative;padding-bottom:5px}
/* Le jaune souligne les titres de section : c'est son rôle dans la charte. */
.sec h2::after{content:'';position:absolute;left:0;bottom:0;width:100%;height:3px;border-radius:2px;
  background:var(--yellow)}
.sec .hint{font-size:12px;color:var(--text-3);font-weight:400}
.sec .line{flex:1;height:1px;background:var(--line)}
.sec .act{flex:none;display:flex;gap:7px;align-items:center}

/* ══════════ CHAÎNES — écran signature ══════════ */
.chaine{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-xl);
  overflow:hidden;margin-bottom:14px}
.chaine-hd{display:flex;align-items:center;gap:11px;padding:14px 18px 13px}
.chaine-hd .tile{display:grid;place-items:center;flex:none;width:22px}
.chaine-hd h3{font-size:15px;font-weight:620;letter-spacing:-.005em}
.chaine-hd p{font-size:12px;color:var(--text-3);margin-top:1px}
.chaine-hd .st{margin-left:auto;flex:none}

.flow{display:flex;padding:6px 18px 20px;overflow-x:auto}
.step{flex:1 1 0;min-width:106px;position:relative;padding:0 5px;text-align:center}
/* Le trait qui relie prend la couleur du maillon le plus faible des deux. */
.step::before{content:'';position:absolute;top:10px;left:-50%;right:50%;height:2px;
  background:var(--line-2);border-radius:2px}
.step:first-child::before{display:none}
.step.lien-att::before{background:var(--yellow)}
.step.lien-alr::before{background:#C00020;
  background-image:repeating-linear-gradient(90deg,#C00020 0 6px,transparent 6px 11px);background-color:transparent}
.step .pin{width:22px;height:22px;border-radius:50%;display:grid;place-items:center;margin:0 auto 9px;
  position:relative;z-index:1;border:2px solid var(--surface);background:var(--surface)}
.step .pin i{width:11px;height:11px;border-radius:50%;display:block}
.step.ok  .pin i{background:var(--brand-2);box-shadow:0 0 0 3px var(--ok-bg)}
.step.att .pin i{background:var(--yellow);box-shadow:0 0 0 3px var(--att-bg)}
.step.alr .pin i{background:#C00020;box-shadow:0 0 0 3px var(--alr-bg)}
.step .l{font-size:13px;font-weight:600;color:var(--text);line-height:1.35}
.step .s{font-size:11px;color:var(--text-3);line-height:1.4;margin-top:2px}
.step .m{display:inline-flex;margin-top:6px;font-size:11px;font-weight:600;border-radius:5px;padding:2px 7px}
.step.att .m{background:var(--att-bg);color:var(--att)}
.step.alr .m{background:var(--alr-bg);color:var(--alr)}
.step.ok .m{background:var(--ok-bg);color:var(--ok)}

.chaine-ft{border-top:1px solid var(--line);background:var(--surface-2);padding:11px 18px;
  font-size:12px;color:var(--text-2);display:flex;gap:10px;align-items:flex-start;line-height:1.6}
.chaine-ft .mi{flex:none;margin-top:1px}
.chaine-ft b{color:var(--text);font-weight:600}

/* Les deux colonnes de l'accueil et des écrans à panneau latéral */
/* minmax(0,336px) et non 336px : une colonne de grille a une taille minimale
   automatique egale a son contenu. Quand quelqu'un agrandit le TEXTE seul a
   200 % (critere 1.4.4), le panneau depassait de 20 px et la page se mettait
   a defiler horizontalement. minmax(0,…) autorise la colonne a se serrer et
   le texte a revenir a la ligne. */
.duo{display:grid;grid-template-columns:1fr minmax(0,336px);gap:16px;align-items:start}
.todo-it .t,.todo-it .s{overflow-wrap:anywhere}
.todo-it{display:flex;gap:10px;padding:12px 16px;border-bottom:1px solid var(--line);text-align:left;
  width:100%;min-width:0;background:none;border-left:none;border-right:none;border-top:none;
  transition:background .15s}
.todo-it:hover{background:var(--surface-2)}
.todo-it .b{min-width:0;flex:1;display:flex;flex-direction:column;gap:1px}
.todo-it .t{font-size:13px;font-weight:600;color:var(--text);line-height:1.4}
.todo-it .s{font-size:12px;color:var(--text-3);line-height:1.45;margin-top:2px}
/* En pleine largeur, une ligne de trois mots laissait 900 px de blanc à sa
   droite. On n'y met pas un décor : on y met l'information qui manquait —
   l'écran où le clic emmène. Elle disparaît sous 1100 px, où la place
   redevient un argument. */
.todo-it .dest{flex:none;align-self:center;display:flex;align-items:center;gap:7px;
  font-size:11.5px;font-weight:650;color:var(--text-3);white-space:nowrap;padding-left:14px}
.todo-it .dest svg{opacity:.55;transition:transform .2s,opacity .2s}
.todo-it:hover .dest{color:var(--vif-ink)}
.todo-it:hover .dest svg{opacity:1;transform:translateX(3px)}
@media(max-width:1100px){.todo-it .dest{display:none}}
.rk .todo-it:last-of-type{border-bottom:none}

/* ══════════ ACCUEIL — ce que tout le monde voit ══════════
   Trois blocs obligatoires, quel que soit l'espace (demande d'Antonio,
   13/08/2026) : la projection de la télévision, ce qui m'attend selon mon
   service, et l'apprentissage en France. Aucun n'est réservé à un rôle :
   ce sont les CONTENUS qui s'adaptent, jamais la présence du bloc. */
/* Les deux colonnes ouvrent chacune sur un titre de section. `.sec:first-child`
   leur retire la marge haute (règle générale, utile en tête d'écran) : on la
   rend à la grille, sinon les titres collent à la carte du dessus. */
.duo-bas{margin-top:24px;margin-bottom:4px}
/* Le rail de l'accueil porte quatre cartes de lecture, pas un encart : 24 px
   de plus suffisent à ce qu'un nom d'apprenti et une date tiennent sur la
   même ligne, ce qui n'était pas le cas à 336. */
.duo-acc{grid-template-columns:1fr minmax(0,380px)}
.duo-bas > .colg, .duo-bas > .cold{min-width:0}

/* ══ LA PROJECTION — le dessin de la télévision, en petit ═════════════════
   Antonio, 25/08/2026 : « mets comme l'écran de projection le design, avec le
   welcome on board ». L'accueil servait les MÊMES chiffres que le hall dans
   quatre cases bordées : une seule mesure, deux dessins. L'équipe ne
   reconnaissait pas, sur son écran, ce qu'elle voit passer dans le couloir.

   tv.php dessine par APLATS — règle d'Antonio, redite trois fois : « arrête de
   mettre des contours dans chaque information ». Trois champs de couleur
   disent à quel service appartient le chiffre : le papier au recrutement, le
   jaune à ce qui demande une action, le vert clair à la pédagogie. Aucune
   bordure à l'intérieur, aucun arrondi, aucune ombre. On reprend la règle
   telle quelle ; le seul trait qui reste est celui du cadre extérieur, parce
   qu'ici le panneau vit au milieu d'autres cartes, pas seul sur 1920 px.

   Le champ vert tient le dernier quart sur les DEUX rangées — mesure et liste
   — d'un seul tenant. C'est ce qui en fait un champ et non une case de plus.

   « Welcome on board » revient. Ici, et nulle part ailleurs. Il avait été
   retiré le 24/08 parce qu'il ouvrait l'accueil sur un souhait de bienvenue
   fixe, jamais touché par le script ; il n'est pas un bonjour à l'équipe,
   c'est le TITRE de la télévision. En tête de sa miniature, il redit
   exactement ce qu'il dit dans le hall. */
/* Les jetons de la charte, pas leur recopie : `--yellow` et `--yellow-ink`
   existent depuis toujours dans `:root`. Recopier `#FFFE78` ici, c'était
   garantir qu'une future retouche de charte corrigerait l'un et oublierait
   l'autre — et l'accueil cesserait de ressembler au hall, ce qui est son
   unique raison d'être. Seul le vert clair de la pédagogie est propre à ce
   panneau : il n'a pas encore de jeton, il en prend un ici. */
.proj{--pj-vert:#E8F4EE; --pj-jaune:var(--yellow); --pj-jaune-i:var(--yellow-ink);
  --pj-encre-jaune:#3E3A00; --pj-filet:rgba(19,32,24,.10);
  background:var(--surface);border:1px solid var(--line);border-radius:var(--r-xl);overflow:hidden}
.proj-tete{display:flex;align-items:flex-start;gap:24px;padding:18px 22px 16px}
.proj-tete .ti{flex:1;min-width:0}
.proj-tete h2{margin:0;font-size:30px;line-height:1;font-weight:900;letter-spacing:-.045em;
  color:var(--rail);text-transform:uppercase}
.proj-tete h2 .surlig{background:var(--pj-jaune);padding:.03em .13em .08em}
.proj-tete .ci{margin-top:9px;font-size:12.5px;font-weight:600;font-style:italic;
  color:var(--brand-fonce);line-height:1.4}
.proj-h{flex:none;text-align:right}
.proj-h .heure{font-size:27px;font-weight:900;line-height:.95;letter-spacing:-.04em;color:var(--rail);
  font-variant-numeric:tabular-nums}
.proj-h .jour{font-size:11.5px;font-weight:700;color:var(--text-2);margin-top:4px}
/* Le point de fraîcheur, repris de la télévision : vert quand les chiffres
   viennent de la base, éteint quand ce sont ceux de la démonstration. */
.proj-maj{display:inline-flex;align-items:center;gap:7px;font-size:11.5px;font-weight:650;
  color:var(--text-3);margin-top:6px}
.proj-maj i{width:7px;height:7px;border-radius:50%;background:var(--brand);flex:none}
.proj-maj.demo i{background:var(--yellow-ink);opacity:.45}
/* CHIFFRES FIGÉS (27/08/2026). Le voyant ne disait que « base branchée » ; il
   dit maintenant aussi « base branchée mais immobile », et il faut que ça se
   voie sans lire — `--alr` est le corail assombri, lisible sur le papier. */
.proj-maj.alerte{color:var(--alr)}
.proj-maj.alerte i{background:var(--alr);opacity:1}
.proj-tete .act{flex:none;padding-top:4px}

/* LE MUR A DEUX RANGS, PAS QUATRE CASES ÉGALES (Antonio, 27/08/2026 :
   « éviter que des pavés secondaires, comme jeunes à replacer, dominent le
   visuel en jaune ; privilégier contrats du mois »). Le mur posait quatre
   cases de MÊME LARGEUR et de même corps : à surface égale, c'est l'aplat
   jaune qui gagne, et l'œil tombait sur un chiffre d'appoint avant la mesure
   du mois.
   La télévision, elle, ne les a jamais mises au même rang : contrats et
   ruptures y portent le duo (mois, mois n-1, cumul), « à replacer » n'est
   qu'une tuile de côté (tv.php, zone recrutement). On rétablit SON dessin.

   ⚠️ LE RANG N'A PAS SUFFI. Le même jour, devant l'écran : « que le jaune se
   retrouve sur les contrats, pas sur les ruptures ». L'aplat était resté sur
   « jeunes à replacer », donc collé aux ruptures — et à l'œil c'est la
   couleur qui dit où regarder, pas la taille du chiffre. Le jaune est donc
   passé sur les contrats (`.tvk.jaune`), « à replacer » est revenu au papier,
   et les ruptures gardent leur chiffre corail. Un seul aplat jaune par mur :
   deux ne désigneraient plus rien. */
.tvmur{display:grid;grid-template-columns:1.32fr 1.32fr .96fr .96fr}
/* UNE CARTE QUI PORTE UN DÉTAIL SE TOUCHE (Antonio, 27/08/2026 : « le mieux
   c'est qu'on puisse toucher sur le visuel pour voir le détail des chiffres »).
   Seules celles qui ont vraiment quelque chose à montrer deviennent cliquables :
   un curseur qui promet un détail inexistant est pire qu'un bloc inerte. */
.tvk[data-ouvre]{cursor:pointer}
.tvk[data-ouvre]:hover{filter:brightness(.985)}
.tvk[data-ouvre]:focus-visible{outline:2px solid var(--rail);outline-offset:-2px}
.tvk[data-ouvre] .k::after{content:'›';margin-left:6px;font-weight:700;opacity:.55}
.tvk[aria-expanded="true"] .k::after{content:'⌄'}
/* Le tiroir : il vit SOUS le mur, pleine largeur, pour ne pas faire sauter la
   grille des quatre cartes quand il s'ouvre. */
.tvdet{margin:0 0 18px;border:1px solid var(--line);border-radius:var(--r-lg);
  background:var(--surface);padding:14px 18px;font-size:13px}
.tvdet h4{margin:0 0 9px;font-size:12px;letter-spacing:.09em;text-transform:uppercase;
  color:var(--text-2)}
.tvdet table{border-collapse:collapse;width:100%;max-width:520px}
.tvdet td{padding:4px 0;border-bottom:1px solid var(--line)}
.tvdet td:last-child{text-align:right;font-weight:700;font-variant-numeric:tabular-nums}
.tvdet tr:last-child td{border-bottom:0}
.tvdet .tot td{font-weight:800}
.tvdet .note{margin-top:9px;color:var(--text-3);font-size:12px;line-height:1.55}
.tvk{padding:17px 22px 20px;min-width:0;--tvk-n:46px}
.tvk.tete{--tvk-n:56px}
.tvk.appoint{--tvk-n:34px}
.tvk.jaune{background:var(--pj-jaune)}
.tvk.ped{background:var(--pj-vert)}
.tvk .k{font-size:11.5px;font-weight:800;letter-spacing:.1em;text-transform:uppercase;color:var(--text-2)}
.tvk.jaune .k{color:var(--pj-jaune-i)}
.tvk .v{display:flex;align-items:baseline;gap:9px;margin-top:9px}
.tvk .n{font-size:var(--tvk-n);font-weight:900;letter-spacing:-.05em;line-height:.92;color:var(--rail);
  font-variant-numeric:tabular-nums}
.tvk.rup .n{color:var(--alr)}
.tvk.jaune .n{color:var(--pj-encre-jaune)}
.tvk .u{font-size:12.5px;font-weight:700;color:var(--text-3)}
.tvk.jaune .u{color:var(--pj-jaune-i)}
.tvk .d{margin-top:9px;font-size:12px;color:var(--text-2);line-height:1.45}
.tvk.jaune .d{color:var(--pj-jaune-i)}
.tvk .d b{font-variant-numeric:tabular-nums;font-weight:750;color:var(--text)}
.tvk.jaune .d b{color:var(--pj-encre-jaune)}
/* Une variation n'a pas de sens en soi : trois contrats de plus est une bonne
   nouvelle, trois ruptures de plus non. Le sens est donc posé à la lecture
   (classes .bien / .mal), jamais déduit du signe. */
.tvk .ec{font-size:12px;font-weight:800;font-variant-numeric:tabular-nums}
.tvk .ec.bien{color:var(--ok)}
.tvk .ec.mal{color:var(--alr)}
.tvk .ec.plat{color:var(--text-3)}

/* Les listes : les rangs de la télévision, à l'échelle d'un écran de bureau.
   Le nom d'abord, le détail dessous — dans le hall on lit un nom à cinq
   mètres et sa formation à un mètre ; l'ordre de lecture ne change pas. */
.tvlistes{display:grid;grid-template-columns:2fr 1fr 1fr;border-top:1px solid var(--pj-filet)}
.tvl{padding:16px 22px 18px;min-width:0}
.tvl.ped{background:var(--pj-vert)}
.tvl h4{font-size:11px;font-weight:800;letter-spacing:.12em;text-transform:uppercase;color:var(--text-3);
  margin-bottom:10px;display:flex;align-items:baseline;gap:10px}
.tvl h4 .n{margin-left:auto;letter-spacing:.02em;font-size:12px;font-weight:800;color:var(--brand-fonce)}
.tvl ul{list-style:none;display:flex;flex-direction:column}
.tvl li{padding:7px 0;min-width:0}
.tvl li + li{border-top:1px solid var(--pj-filet)}
.tvl li b{display:block;font-size:14px;font-weight:800;letter-spacing:-.02em;color:var(--text);
  line-height:1.2;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.tvl li small{display:block;font-size:11.5px;font-weight:600;color:var(--text-2);margin-top:3px;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.tvl .rien{font-size:12.5px;font-weight:600;color:var(--text-2);line-height:1.45}

/* ══ UNE ICÔNE QUI SE VOIT ════════════════════════════════════════════════
   Antonio, 25/08/2026 : « utilise des icônes plus grandes et plus
   professionnelles ». Elles vivaient à 15 px, posées à même le fond. À cette
   taille une silhouette pleine devient une tache dont on ne lit plus le
   dessin, et rien ne dit de quelle famille elle relève. La tuile règle les
   deux : la teinte du module derrière, la même que dans le rail de
   navigation, donc le même repère.

   « Ajuste bien la taille des icônes » (26/08). Il y en avait DEUX — 20 px
   dans 34, et 18 dans 30 — plus les 19 px du rail de navigation et des
   chaînes : trois tailles de dessin pour un seul jeu, et l'œil le voit sans
   savoir pourquoi. Il n'en reste qu'UNE, 19 px, celle qui existait déjà
   partout ailleurs dans l'application, dans une tuile de 32. Le rapport
   dessin/tuile (0,59) est celui d'une icône d'application ; à 34 px la tuile
   pesait plus lourd que la ligne de texte de 13 px qu'elle annonce. */
.ict{display:grid;place-items:center;flex:none;width:32px;height:32px;border-radius:9px}
/* L'ÉCHELLE DE L'ACCUEIL, trois crans et pas dix :
     13 px — ce qui vit DANS une ligne de texte : flèche de destination,
             chevron d'un pli, flèche d'un titre de chaîne ;
     19 px — tout ce qui ANNONCE une ligne ou une carte : tuiles `.ict`,
             tuiles des chaînes, pastille de la cloche, pied d'une chaîne ;
     22 px — l'illustration d'un écran vide, qui n'annonce rien et occupe.
   Le reste de l'application porte encore 17, 15 et 14 par endroits : c'est
   un chantier à part, pas une exception à cette échelle. */

/* ══ LE RAIL DE DROITE — ce qui arrive, à côté de ce qu'on fait ═══════════
   Antonio, 25/08/2026 : « mets à droite les news, la publication du jour, les
   rapports de réunion selon les services ». L'accueil empilait tout dans une
   seule colonne : les comptes rendus repoussaient les chaînes trois écrans
   plus bas, pendant que la moitié droite de la page restait blanche.

   Le partage est simple et tient tout seul : à gauche ce qu'on FAIT (ce qui
   m'attend, les chaînes), à droite ce qui ARRIVE et qui se lit (nouveautés,
   publication du jour, comptes rendus, veille). Les quatre cartes du rail
   boivent aux mêmes sources que la cloche — jamais une source de plus, sinon
   la cloche et l'accueil finiraient par ne plus dire la même chose. */
.arail{display:flex;flex-direction:column;gap:14px}
.rk{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-xl);overflow:hidden}
.rk-hd{display:flex;align-items:center;gap:11px;padding:12px 14px;border-bottom:1px solid var(--line)}
.rk-hd h3{flex:1;min-width:0;font-size:13.5px;font-weight:680;letter-spacing:-.01em}
.rk-hd .n{flex:none;font-size:11px;font-weight:700;border-radius:6px;padding:2px 8px;
  background:var(--surface-3);color:var(--text-2);font-variant-numeric:tabular-nums}
.rk-ft{padding:10px 14px;border-top:1px solid var(--line)}
.rki{display:flex;gap:11px;width:100%;text-align:left;padding:11px 14px;background:none;
  border:none;border-bottom:1px solid var(--line);transition:background .15s}
.rki:last-of-type{border-bottom:none}
.rki:hover{background:var(--surface-2)}
.rki .b{flex:1;min-width:0}
.rki .t{display:block;font-size:13px;font-weight:620;color:var(--text);line-height:1.4}
/* Deux lignes de résumé : dans 360 px, la troisième pousse la ligne suivante
   hors de vue sans rien apprendre de plus. Le texte entier est à un clic. */
.rki .s{display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden;
  font-size:12px;color:var(--text-2);line-height:1.45;margin-top:3px}
.rki .m{display:block;font-size:11px;color:var(--text-3);margin-top:5px;
  font-variant-numeric:tabular-nums}
/* « Neuf » se voit sans se lire — mais une couleur seule ne dit rien à qui
   ne la voit pas (1.4.1), et --vif ne monte qu'à 2,79:1 sur blanc (1.4.11).
   La pastille prend donc --vif-ink, et le MOT l'accompagne dans le rendu,
   pour les lecteurs d'écran. C'est le motif déjà employé par le rail de
   navigation pour les décisions qui attendent. */
.rki.neuf .t::after{content:'';display:inline-block;width:6px;height:6px;border-radius:50%;
  background:var(--vif-ink);margin-left:7px;vertical-align:middle}
/* LA CARTE NE DÉFILE PLUS CHEZ ELLE (26/08). Elle était bornée à 380 px pour
   que sa longueur ne décide pas de celle de l'écran — et depuis que les SIX
   services y figurent, cette borne en cachait trois derrière un défilement
   interne. Antonio demandait précisément à les voir : « sur chaque service on
   devrait avoir compte rendu de réunion ».
   Ce qui borne la carte maintenant, c'est son CONTENU : une réunion par
   service, la plus récente, et son résumé sur une ligne. Le compte de chaque
   service dit combien il y en a, « Tout ouvrir » mène au reste. Une carte de
   rail résume, elle ne remplace pas l'écran. */
.rk-liste .rkj{position:sticky;top:0;z-index:1}
/* Dans le rail, un résumé tient sur UNE ligne : c'est un repère, pas une
   lecture. Le texte entier est à un clic, et il y a six services à montrer
   avant lui. */
.rk-liste .rki .s{-webkit-line-clamp:1}
.rk-vide{padding:15px 14px;font-size:12.5px;color:var(--text-3);line-height:1.55}
/* Un service sans réunion : une ligne, pas une carte vide. Elle occupe la
   même colonne que les réunions et se distingue d'elles par le ton, pas par
   un cadre — elle dit une absence, elle ne la met pas en scène. */
.rki-vide{padding:10px 14px;font-size:12px;color:var(--text-3);font-style:italic;
  border-bottom:1px solid var(--line)}
.rk .rki-vide:last-child{border-bottom:none}
.rk-vide b{color:var(--text-2);font-weight:650}
/* Le service d'un compte rendu se voit AVANT son titre : une teinte, un nom,
   un compte. C'est la règle du 17/08 — le boîtier dit le service, l'écran le
   montre — tenue dans la largeur du rail. */
.rkj{display:flex;align-items:center;gap:9px;padding:9px 14px 7px;background:var(--surface-2);
  border-bottom:1px solid var(--line);font-size:11.5px;font-weight:800;letter-spacing:.08em;
  text-transform:uppercase;color:var(--text-3)}
.rkj .pt{width:8px;height:8px;border-radius:3px;flex:none}
.rkj .n{margin-left:auto;letter-spacing:0;font-size:11px;color:var(--text-2);
  font-variant-numeric:tabular-nums}
/* L'heure d'une publication : une colonne fixe, pour que les heures
   s'alignent d'une ligne à l'autre au lieu de flotter derrière les titres. */
.rki .hh{flex:none;width:40px;font-size:12px;font-weight:750;color:var(--text-2);
  font-variant-numeric:tabular-nums;padding-top:1px}
.rki .hh.tard{color:var(--alr)}

/* Le corps d'un article de blog. Le seul endroit de l'application où l'on
   affiche de la prose longue : elle a besoin d'une mesure de ligne et d'un
   rythme vertical, que les cartes n'ont pas. Rien d'autre n'est stylé — les
   titres et les liens héritent. */
.art-corps{font-size:14.5px;line-height:1.68;color:var(--text);max-width:68ch}
.art-corps h2{font-size:16px;font-weight:650;margin:22px 0 8px}
.art-corps h3{font-size:14.5px;font-weight:650;margin:18px 0 6px}
.art-corps p{margin:0 0 12px}
.art-corps ul,.art-corps ol{margin:0 0 12px;padding-left:20px}
.art-corps li{margin:0 0 5px}
.art-corps blockquote{margin:0 0 12px;padding-left:14px;color:var(--text-2)}
.art-ligne{cursor:pointer}
.art-ligne:hover{background:var(--surface-2)}
.art-ligne.sel{background:var(--surface-2)}

/* L'apprentissage en France : de la lecture, pas un tableau de bord. */
.vei{display:block;width:100%;text-align:left;padding:13px 16px;border-bottom:1px solid var(--line);
  color:inherit;text-decoration:none}
.vei:last-of-type{border-bottom:none}
.vei .d{font-size:11px;color:var(--text-3);font-variant-numeric:tabular-nums}
.vei .t{display:block;font-size:13px;font-weight:600;color:var(--text);line-height:1.45;margin-top:3px}
.vei .o{display:block;font-size:11px;color:var(--text-3);margin-top:5px}
.vei:hover .t{color:var(--vif-ink);text-decoration:underline;text-underline-offset:2px}
/* ═══════ LA VEILLE EN CARTES HORIZONTALES ═══════
   Modèle relevé sur Mobbin (Matter, 28/08/2026) : une rangée de cartes, la
   source en gris au dessus du titre, une vignette qui l'identifie.

   ⚠️ LA VIGNETTE N'EST PAS UNE PHOTO, ET C'EST MESURÉ : `api/veille.php` rend
   `titre`, `url`, `date`, `origine` — il n'y a AUCUNE image dans le flux. En
   chercher une voudrait dire aller lire l'`og:image` de chaque article, donc
   une requête sortante par article, et un relais d'images comme `api/tuile.php`
   puisque `img-src 'self'` est fermé. Beaucoup de surface pour des photos
   d'illustration souvent hors sujet.
   On dessine donc ce qu'on SAIT : la source. Teinte stable, tirée de son nom,
   et ses initiales. Aucune requête, rien à proxifier, et jamais la mauvaise
   image en face du mauvais article. */
/* ⚠️ ELLE ÉTAIT SUR UNE SEULE LIGNE, AVEC UN DÉFILEMENT HORIZONTAL, ET ELLE
   NE PEUT PLUS L'ÊTRE (30/08/2026). Deux raisons arrivées le même jour :
   « Ce qui m'attend » et « Vue d'ensemble » ont quitté la colonne de gauche,
   où la veille se retrouve SEULE en face d'un rail de quatre cartes — une
   rangée de 200 px laisserait le bas de l'écran vide ; et le bloc lit
   désormais TROIS sources au lieu d'une, donc il a de quoi remplir. Les
   cartes se replient en lignes, `auto-fill` décide combien par ligne selon la
   largeur, et il n'y a plus rien à faire défiler de côté — un défilement
   horizontal cache ce qu'il contient, personne ne va le chercher. */
.vei-grille{display:grid;grid-template-columns:repeat(auto-fill,minmax(212px,1fr));
  gap:12px;padding:14px 16px}
.vei-c{display:flex;flex-direction:column;border:1px solid var(--line);
  border-radius:var(--r-lg);overflow:hidden;background:var(--surface);
  transition:border-color .2s,transform .2s}
.vei-c:hover{border-color:var(--vif);transform:translateY(-2px)}
/* ⚠️ IL Y AVAIT ICI UN PAVÉ DE 76 px PORTANT LES INITIALES DE LA SOURCE, ET
   C'ÉTAIT DEUX FOIS FAUX (vu à l'écran le 28/08/2026, après déploiement).
   1. AVEC UNE SEULE SOURCE, IL NE DIT RIEN. Le flux livré n'en avait qu'une
      (Ministère du Travail) : les cinq cartes portaient cinq « MT » identiques.
      Un aplat qui prend le tiers de la carte pour répéter la même chose cinq
      fois vole la place du titre, qui est la seule information.
      ⚠️ Ils sont TROIS depuis le 30/08/2026, et chacun porte sa marque
      hébergée : le pavé d'initiales ne revient pas pour autant — un logo de
      20 px sur la ligne de la source dit la même chose sans voler la place.
   2. LE JAUNE A UN SENS ICI. Dans cette charte il veut dire « ça demande un
      geste » (règles 12 et 20). Cinq aplats jaunes à côté du bloc « À traiter »
      entraient en concurrence avec de vraies actions. Une teinte décorative
      n'emprunte jamais une couleur qui signifie.
   Reste un filet de 4 px : il distingue les sources quand il y en a plusieurs,
   et se tait quand il n'y en a qu'une. */
.vei-c .band{height:4px;flex:none}
/* La marque de la source, quand on l'héberge. 20 px : c'est la taille à
   laquelle une marque se reconnaît sans devenir un pavé. Elle se pose SUR la
   ligne de la source, pas au dessus du titre — l'information reste le titre. */
.vei-c .src{display:flex;align-items:center;gap:6px;min-width:0}
.vei-c .src img{width:20px;height:20px;object-fit:contain;flex:none;border-radius:4px}
.vei-c .cps{padding:11px 13px 13px;display:flex;flex-direction:column;gap:5px;flex:1}
.vei-c .o{font-size:11.5px;color:var(--text-3);text-transform:uppercase;letter-spacing:.05em}
/* Le lien souligne tout ce qu'il contient : trois lignes soulignées d'un coup
   sont illisibles. Seul le titre le prend, et seulement au survol. */
.vei-c, .vei-c span{text-decoration:none}
.vei-c:hover .t{text-decoration:underline;text-underline-offset:2px}
/* Trois lignes au plus : au delà, les cartes de la rangée n'ont plus la même
   hauteur et l'œil ne compare plus rien. */
.vei-c .t{font-size:13px;font-weight:650;color:var(--text);line-height:1.4;
  display:-webkit-box;-webkit-line-clamp:3;-webkit-box-orient:vertical;overflow:hidden}
.vei-c:hover .t{color:var(--vif-ink)}
.vei-c .d{font-size:11px;color:var(--text-3);font-variant-numeric:tabular-nums;margin-top:auto}
@media (max-width:860px){
  .vei-grille{grid-template-columns:repeat(auto-fill,minmax(168px,1fr))}
}
.vei-pied{padding:12px 16px;border-top:1px solid var(--line);font-size:11.5px;color:var(--text-3);
  line-height:1.55}
.vei-pied a{color:var(--vif-ink)}

/* Très grand écran : le rail respire, la gauche prend le reste.

   LE RAIL SUR DEUX COLONNES A ÉTÉ ESSAYÉ ET RETIRÉ, mesures à l'appui, sur la
   machine d'Antonio (1920). Il partait d'un vrai constat — le rail est plus
   long que la colonne de gauche — mais il produisait l'écart inverse, et pire :

       une colonne de rail à 400 px .... gauche 1342, rail 1643, écart  302
       deux colonnes à 760 px, CR 380 .. gauche 1396, rail 1008, écart  388
       deux colonnes à 760 px, CR 300 .. gauche 1396, rail  928, écart  468

   Et il coûtait la lecture : on descend la première colonne, on remonte, on
   redescend. Un rail se lit de haut en bas. On garde donc une colonne, on lui
   donne 400 px au lieu de 380, et les 1206 px qui restent à gauche font du
   bien aux six étapes des chaînes.

   Ce qui reste de blanc en bas de la colonne courte n'est pas un défaut
   d'alignement : les deux colonnes ne portent pas la même chose, et il n'y a
   rien de vrai à mettre dessous. */
@media(min-width:1800px){
  .duo-acc{grid-template-columns:1fr minmax(0,400px)}
}

/* Grand écran : les chiffres prennent la place qu'ils ont dans le hall. Ce
   n'est pas de la décoration — un contrat du mois se lit de l'autre bout du
   plateau ouvert, comme sur la télévision. */
@media(min-width:1500px){
  .proj-tete h2{font-size:36px}
  .proj-tete .ci{font-size:13.5px}
  .proj-h .heure{font-size:32px}
  .tvk{padding:20px 26px 24px;--tvk-n:54px}
  .tvk.tete{--tvk-n:66px}
  .tvk.appoint{--tvk-n:40px}
  .tvl{padding:18px 26px 20px}
  .tvl li b{font-size:15px}
}
@media(max-width:1180px){
  .proj-tete{flex-wrap:wrap;gap:14px}
  .proj-tete h2{font-size:26px}
  .tvmur{grid-template-columns:repeat(2,1fr)}
  .tvlistes{grid-template-columns:1fr}
  .tvl + .tvl{border-top:1px solid var(--pj-filet)}
}
@media(max-width:720px){
  .tvmur{grid-template-columns:1fr}
  .tvk{padding:15px 18px 17px;--tvk-n:38px}
  .tvk.tete{--tvk-n:44px}
  .tvk.appoint{--tvk-n:30px}
  .proj-tete h2{font-size:23px}
}

/* ══════════ Composants ══════════ */
/* UN SEUL FOND BLANC, PAS DEUX APPLICATIONS (Antonio, 30/08/2026 : « je veux
   un fond unique blanc, qu'il n'y ait pas de séparation entre l'app et
   UNITOOLS »). Le cadre était habillé comme une carte : bordure, coins
   arrondis, fond propre. À l'intérieur, SA page pose ses propres blancs — d'où
   deux surfaces emboîtées, et une couture visible même sans trait.
   La carte qui ne porte QU'un cadre perd donc son habillage. Les autres n'y
   touchent pas : une carte qui porte du contenu à nous reste une carte. */
.card:has(> .card-bd.flush > iframe){background:none;border:0;border-radius:0}
.card:has(> .card-bd.flush > iframe) > .card-bd.flush > iframe{border-radius:0}
.card{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-xl)}
.card-hd{padding:16px;border-bottom:1px solid var(--line);display:flex;align-items:flex-start;gap:12px}
.card-bd{padding:16px}
.card-bd.flush{padding:0}
.card-title{font-size:15px;font-weight:620;letter-spacing:-.005em}
.card-sub{font-size:12px;color:var(--text-3);margin-top:3px;line-height:1.5;max-width:62ch}
.card-hd .act{margin-left:auto;flex:none;display:flex;gap:7px;align-items:center}
/* Un en-tête qui porte QUATRE boutons, un menu déroulant et une recherche ne
   tient plus sur une ligne : sans cela, le titre se retrouve écrasé sur une
   colonne de six caractères, un mot par ligne. Il passe alors à la ligne au
   lieu d'étrangler le titre. Constaté à l'écran le 27/08/2026 en ajoutant
   « Reprendre les entreprises d'accueil » au registre. */
.card-hd.enroule{flex-wrap:wrap}
.card-hd.enroule>div:first-child{flex:1 1 300px;min-width:0}
.card-hd.enroule .act{flex-wrap:wrap}

.grid{display:grid;gap:16px}
.g2{grid-template-columns:repeat(2,1fr)}
.g3{grid-template-columns:repeat(3,1fr)}
.g4{grid-template-columns:repeat(4,1fr)}
.split{display:grid;grid-template-columns:1.4fr 1fr;gap:16px;align-items:start}

/* ══ LIRE UN COMPTE RENDU ══════════════════════════════════════════════════
   La liste à gauche, le TEXTE à droite, et le texte occupe la place.
   Antonio, 20/08/2026 : « il faut que le compte rendu de chaque service soit
   un vrai compte rendu, pas un grand cockpit. » L'écran ouvrait sur quatre
   compteurs et un tableau : on y voyait COMBIEN de comptes rendus existaient,
   jamais ce qu'ils disaient. Les compteurs restent — en une ligne, sous les
   filtres, à leur vraie place : un repère, pas la destination. */
.lect{display:grid;grid-template-columns:320px 1fr;gap:16px;align-items:start}
@media(max-width:980px){.lect{grid-template-columns:1fr}}
.crl{max-height:62vh;overflow:auto}
.crj{font-size:11px;font-weight:650;color:var(--text-3);padding:12px 16px 4px;
  background:var(--surface);position:sticky;top:0;z-index:1}
.cri{display:flex;flex-direction:column;gap:3px;width:100%;text-align:left;cursor:pointer;
  padding:9px 16px;border:none;border-left:2px solid transparent;background:none;font:inherit}
.cri:hover{background:var(--surface-2)}
.cri.on{background:var(--surface-2);border-left-color:var(--brand-2)}
.cri .t{font-size:13px;font-weight:600;color:var(--text);line-height:1.35}
.cri .s{display:flex;flex-wrap:wrap;align-items:center;gap:6px;font-size:11.5px;color:var(--text-3)}
/* LA BANDE D'ÉTAT, EN TÊTE DU COMPTE RENDU (08/09/2026).
   Elle prend la place des onglets d'audience : il n'y a plus qu'une version.
   Elle DIT où en est le compte rendu — en attente, confirmé, retenu — et porte
   le geste, à droite, pour qui a le droit de le poser. Une ligne, pas une
   carte : c'est un état, pas un chapitre. */
.crv{display:flex;flex-wrap:wrap;align-items:center;gap:10px;
  padding:9px 12px;border:1px solid var(--line);border-radius:8px;background:var(--surface-2)}
.crv-d{font-size:11.5px;color:var(--text-3)}
.crv-a{display:flex;flex-wrap:wrap;gap:6px;margin-left:auto}
/* Le compte rendu d'entretien replié à côté de sa fiche. Un <details> natif :
   le pli est un comportement du navigateur, pas trois lignes de script. */
#fiche-cr{border:1px solid var(--line);border-radius:9px;background:var(--surface-2);padding:10px 12px}
#fiche-cr>summary{cursor:pointer;font-size:12.5px;font-weight:600;color:var(--text-2)}
#fiche-cr .crd{max-height:340px;overflow:auto}
/* LE CORPS : une mesure de lecture, pas la largeur de l'écran — et la
   typographie d'un DOCUMENT, pas d'une fiche.

   Antonio, 27/08/2026 : « les polices, et avoir une qualité rédactionnelle
   avec la mise en forme ». Le titre de section était une étiquette de 11 px en
   capitales grises, exactement la graisse des libellés de formulaire : sur
   cinq sections et deux pages de texte, l'ossature ne se voyait plus, et
   « Décisions prises » avait l'air plus faible que les phrases qu'il annonce.
   Les capitales FORCÉES effaçaient en prime les accents (« RESUME ») — le
   comble pour un titre qu'on vient d'accentuer à la source.

   Un titre de section se lit donc plus GROS que le texte, et une filière le
   sépare de la section précédente : c'est elle qui donne au compte rendu son
   rythme de page. */
.crd{font-size:13.8px;line-height:1.72;max-width:68ch;color:var(--text)}
.crd h4{font-size:14.5px;font-weight:700;letter-spacing:-.01em;color:var(--text);
  margin:26px 0 9px;padding-top:20px;border-top:1px solid var(--line)}
.crd h4:first-child{margin-top:0;padding-top:0;border-top:0}
.crd p{margin:0 0 11px}
/* Le relief que le modèle pose sur le QUI et le POUR QUAND d'une action. */
.crd b{font-weight:650;color:var(--text)}
.crd i{font-style:italic;color:var(--text-2)}
/* Les puces : n8n écrit les décisions et les actions en listes, et elles se
   lisaient en paragraphes collés. Le retrait tient dans la mesure de lecture,
   et la puce prend le vert d'identité — les tokens le réservent aux accents et
   aux puces, et elle ne porte aucun texte, donc aucun enjeu de contraste. */
.crd ul{margin:0 0 13px;padding-left:18px;list-style:none}
.crd li{position:relative;margin:0 0 7px}
.crd li:before{content:'';position:absolute;left:-14px;top:.66em;width:5px;height:5px;
  border-radius:50%;background:var(--brand)}
.crd ul:last-child,.crd p:last-child{margin-bottom:0}
.crc{display:flex;flex-wrap:wrap;gap:16px;font-size:12px;color:var(--text-3);
  padding:11px 16px;border-top:1px solid var(--line)}
.crc b{color:var(--text);font-weight:650;font-variant-numeric:tabular-nums}

/* ══ LA FILE DU JOUR ═══════════════════════════════════════════════════════
   « Qu'est-ce qui part aujourd'hui, et avec quel texte ? » Antonio, 21/08/2026.
   Une ligne par publication : le réseau, l'heure, le titre, le texte prêt à
   coller. Rien à chercher, rien à recomposer. Le texte est REPLIÉ par défaut —
   on l'ouvre pour le relire, on le copie sans l'ouvrir. */
.filj{font-size:11px;font-weight:650;color:var(--text-3);padding:14px 16px 4px}
.filj.alr{color:#C00020}
.filx{border-bottom:1px solid var(--line);padding:12px 16px}
.filx:last-child{border-bottom:none}
.filx .en{display:flex;align-items:center;gap:10px;flex-wrap:wrap}
.filx .h{font-size:12.5px;font-weight:650;color:var(--text);font-variant-numeric:tabular-nums;
  width:52px;flex:none}
.filx .t{font-size:13px;font-weight:600;color:var(--text);flex:1;min-width:180px}
.filx .ac{display:flex;gap:6px;margin-left:auto;flex:none}
.filx .tx{margin-top:9px;font-size:12.5px;line-height:1.6;color:var(--text-2);
  white-space:pre-wrap;max-height:150px;overflow:auto;padding:10px 12px;
  background:var(--surface-2);border-radius:8px}
.filx .tx[hidden]{display:none}
.stack{display:flex;flex-direction:column;gap:16px}
.mt{margin-top:16px}

/* Indicateur : chiffre + jauge, sans boîte lourde */
.stat{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg);padding:14px 15px}
.stat .k{font-size:12px;color:var(--text-3);font-weight:500}
.stat .v{font-size:24px;font-weight:680;letter-spacing:-.035em;margin:5px 0 2px;line-height:1;
  font-variant-numeric:tabular-nums}
.stat .v.na{color:var(--text-3);font-weight:400;font-size:24px}
.stat .v .u{font-size:15px;color:var(--text-3);font-weight:500;letter-spacing:0}
.stat .d{font-size:12px;color:var(--text-2)}
.gauge{height:4px;border-radius:99px;background:var(--surface-3);overflow:hidden;margin-top:9px}
.gauge i{display:block;height:100%;border-radius:99px;background:var(--brand-2);
  transition:width .6s cubic-bezier(.32,.72,0,1)}
.gauge.att i{background:var(--yellow)}.gauge.alr i{background:#C00020}

.badge{display:inline-flex;align-items:center;gap:5px;font-size:11px;font-weight:600;border-radius:6px;
  padding:3px 8px;white-space:nowrap;line-height:1.4}
.b-ok{background:var(--ok-bg);color:var(--ok)}
.b-att{background:var(--att-bg);color:var(--att)}
.b-alr{background:var(--alr-bg);color:var(--alr)}
.b-inf{background:var(--inf-bg);color:var(--inf)}
.b-mute{background:var(--surface-3);color:var(--text-3)}
.badge .pt{width:5px;height:5px;border-radius:50%;background:currentColor;flex:none}

.btn{display:inline-flex;align-items:center;justify-content:center;gap:7px;border:1px solid var(--line-2);
  background:var(--surface);color:var(--text);border-radius:9px;padding:9px 15px;font-size:13px;
  font-weight:550;min-height:40px;text-decoration:none;
  transition:background .18s,border-color .18s,box-shadow .18s}
.btn:hover{background:var(--surface-2);border-color:var(--text-3);box-shadow:var(--sh-2)}
.btn-main{background:var(--brand-fonce);border-color:var(--brand-fonce);color:#fff}
.btn-main:hover{background:#164E34;border-color:#164E34;color:#fff}
.btn:disabled{opacity:.45;cursor:not-allowed;box-shadow:none}
.btn-sm{padding:6px 11px;min-height:32px;font-size:12px}
/* Une action irreversible ne se signale pas par la couleur seule (1.4.1) :
   elle porte aussi le mot « Supprimer ». Le rouge n'est que le rappel. */
.btn-danger{color:var(--alr);border-color:#F3C6CC}
.btn-danger:hover:not(:disabled){background:var(--alr-bg);border-color:var(--alr);color:var(--alr)}
.btn-ico{padding:0;width:32px;min-height:32px}
.btn-row{display:flex;gap:9px;flex-wrap:wrap}

table{width:100%;border-collapse:collapse;font-size:13px}
th{font-size:11px;color:var(--text-3);text-align:left;font-weight:600;padding:10px 16px;
  border-bottom:1px solid var(--line);background:var(--surface-2)}
td{padding:12px 16px;border-bottom:1px solid var(--line);color:var(--text-2);vertical-align:middle}
tbody tr:last-child td{border-bottom:none}
tbody tr{transition:background .15s}
tbody tr:hover td{background:var(--surface-2)}
td b{color:var(--text);font-weight:600}
/* ═══ LE CONFORT DES TABLEAUX ═══════════════════════════════════════════
   Trente-cinq tableaux, dont plusieurs débordent : sur une liste de contrats
   ou d'entreprises, on fait défiler de côté et on perd la seule colonne qui
   dit DE QUI on parle. La colonne d'identité reste donc en place, et les
   en-têtes se trient.
   ⚠️ Ce commentaire annonçait aussi une en-tête collante, et une hauteur de
   barre mesurée pour la caler. Les deux ont été retirées le même jour, après
   l'avoir vu à l'écran : elles ne pouvaient pas marcher ici (voir plus bas).
   Le laisser tel quel aurait fait chercher un réglage qui n'existe plus. */
.tbl{overflow-x:auto}
/* ⚠️ PAS D'EN-TÊTE COLLANTE ICI, ET CE N'EST PAS UN OUBLI (mesuré à l'écran
   le 31/08/2026). La première version posait `position:sticky; top:<hauteur de
   la barre>` sur les `<th>`. Résultat vu à l'écran : l'en-tête est passée SOUS
   les lignes, en bas du tableau. La cause : `.tbl` porte `overflow-x:auto`, et
   un débordement horizontal fait de la boîte un CONTENEUR DE DÉFILEMENT à part
   entière — le `top` se mesure alors depuis le haut de cette boîte, pas depuis
   la page. Cent-cinq pixels plus bas que le haut du tableau, c'est-à-dire au
   milieu des données.
   Et la corriger à `top:0` ne servirait à rien : ces tableaux n'ont pas de
   hauteur bornée, donc ils ne défilent jamais verticalement à l'intérieur de
   leur boîte. Une en-tête collante n'a de sens que dans un tableau qui défile
   en lui-même — ce n'est pas le cas ici, et lui en donner un demanderait de
   fixer une hauteur à trente-cinq tableaux au jugé.
   Ce qui marche vraiment reste : la colonne d'identité figée quand ça déborde,
   et le tri. */
/* La colonne d'identité ne se fige que si le tableau déborde VRAIMENT :
   une ombre portée sur un tableau qui tient dans la page est un artifice qui
   n'aide personne, et qui se voit. `figerTableaux` pose la classe. */
.tbl.fige > table > tbody > tr > td:first-child,
.tbl.fige > table > thead > tr > th:first-child{position:sticky;left:0;z-index:2;
  background:var(--surface)}
.tbl.fige > table > thead > tr > th:first-child{z-index:4}
.tbl.fige.defile > table > tbody > tr > td:first-child,
.tbl.fige.defile > table > thead > tr > th:first-child{
  box-shadow:6px 0 8px -6px rgba(19,32,24,.22)}
/* Le tri : l'en-tête devient cliquable, et il DIT son état — la flèche seule
   se confond avec un décor, et un lecteur d'écran n'en tire rien. */
.tbl > table > thead > tr > th.tri{cursor:pointer;user-select:none;white-space:nowrap}
.tbl > table > thead > tr > th.tri:hover{color:var(--text)}
.tbl > table > thead > tr > th.tri::after{content:'';display:inline-block;width:0;height:0;
  margin-left:6px;vertical-align:middle;opacity:.28;
  border-left:4px solid transparent;border-right:4px solid transparent;
  border-top:5px solid currentColor}
.tbl > table > thead > tr > th.tri[aria-sort="ascending"]::after{opacity:1;
  border-top:none;border-bottom:5px solid currentColor}
.tbl > table > thead > tr > th.tri[aria-sort="descending"]::after{opacity:1}

.msg{border-radius:var(--r-lg);padding:12px 15px;font-size:13px;line-height:1.6;display:flex;gap:11px;
  align-items:flex-start;background:var(--surface-2);color:var(--text-2);border:1px solid var(--line)}
.msg b{color:var(--text);font-weight:600}
/* 75 caractères par ligne : au-delà, l'œil perd le début de la ligne suivante. */
.msg > span:last-child{max-width:82ch}
.msg .mi{flex:none;margin-top:1px;color:var(--text-3)}
.msg.ok{background:var(--ok-bg);border-color:color-mix(in srgb,var(--ok) 18%,transparent)}
.msg.ok .mi{color:var(--ok)}
.msg.att{background:var(--att-bg);border-color:color-mix(in srgb,var(--att) 20%,transparent)}
.msg.att .mi{color:var(--att)}
.msg.alr{background:var(--alr-bg);border-color:color-mix(in srgb,var(--alr) 20%,transparent)}
.msg.alr .mi{color:var(--alr)}
.msg.inf{background:var(--inf-bg);border-color:color-mix(in srgb,var(--inf) 18%,transparent)}
.msg.inf .mi{color:var(--inf)}

/* Composeur */
.composer{border:1px solid var(--line-2);border-radius:var(--r-lg);overflow:hidden}
.composer .head{display:flex;align-items:center;gap:8px;padding:9px 12px;border-bottom:1px solid var(--line);
  background:var(--surface-2);flex-wrap:wrap}
.composer .head .k{font-size:11px;color:var(--text-3);font-weight:600}
.composer textarea{width:100%;border:none;padding:14px;font-size:13px;line-height:1.65;resize:vertical;
  min-height:236px;background:var(--surface);display:block}
.composer .foot{display:flex;align-items:center;gap:8px;padding:9px 12px;border-top:1px solid var(--line);
  background:var(--surface-2);flex-wrap:wrap}
.cc{font-size:12px;color:var(--text-3);margin-left:auto;font-variant-numeric:tabular-nums}
.chip{display:inline-flex;align-items:center;gap:6px;font-size:12px;font-weight:550;border-radius:99px;
  padding:5px 12px;border:1px solid var(--line-2);color:var(--text-2);background:var(--surface);
  user-select:none;min-height:30px;transition:background .18s,border-color .18s,color .18s}
.chip:hover{border-color:var(--brand-2)}
.chip.on{background:var(--t-verte);border-color:var(--brand-2);color:var(--t-verte-i)}
.chip.off{opacity:.5;cursor:not-allowed}
.chip.off:hover{border-color:var(--line-2)}

.preview{border:1px solid var(--line);border-radius:var(--r-lg);padding:14px;background:var(--surface-2)}
.pv-head{display:flex;align-items:center;gap:10px;margin-bottom:10px}
.pv-av{width:34px;height:34px;border-radius:10px;background:linear-gradient(150deg,var(--brand-2),var(--brand));
  color:#fff;display:grid;place-items:center;font-size:11px;font-weight:700;flex:none}
.pv-n{font-size:13px;font-weight:600;color:var(--text)}
.pv-m{font-size:11px;color:var(--text-3)}
.pv-body{font-size:13px;line-height:1.65;white-space:pre-wrap;color:var(--text-2)}
.pv-img{margin-top:11px;height:100px;border:1.5px dashed var(--line-2);border-radius:var(--r);display:grid;
  place-items:center;color:var(--text-3);font-size:12px;gap:5px;text-align:center}

/* ⚠️ CETTE MISE EN FORME ETAIT RESERVEE A `.rail-info`, ET HUIT LIGNES S'EN
   PASSAIENT DEJA SANS QUE PERSONNE LE VOIE (mesure le 28/08/2026 : 51 `.row`
   sous `.rail-info`, 8 sous `.card-bd`). Sans regle, un `.row` retombe en
   `display:block` — le libelle et la valeur se collent, « Nom— » sur une
   ligne. Le defaut ne saute pas aux yeux : ca reste lisible, juste laid, et
   ca se decouvre en ouvrant un ecran neuf.
   Le motif libelle → valeur ne depend pas de l'endroit ou il vit : il vaut
   dans le rail comme dans une carte. La regle porte donc les deux, plutot
   qu'un `.rail-info` recopie autour de chaque carte. */
.rail-info .row, .card-bd .row{display:flex;gap:12px;font-size:13px;padding:8px 0;border-bottom:1px solid var(--line)}
.rail-info .row:last-child, .card-bd .row:last-child{border-bottom:none}
.rail-info .k, .card-bd .k{font-size:12px;color:var(--text-3);width:96px;flex:none}
.rail-info .v, .card-bd .v{flex:1;min-width:0;color:var(--text)}
.who-chip{display:inline-flex;align-items:center;gap:7px}
.who-chip .av{width:22px;height:22px;border-radius:7px;display:grid;place-items:center;font-size:11px;
  font-weight:700;flex:none;overflow:hidden}
/* Une photo remplit et arrondit la pastille (comme l'avatar de la barre), au
   lieu de déborder : sans cette règle, l'image gardait sa taille naturelle. */
.who-chip .av img,.capt .av img{width:100%;height:100%;object-fit:cover;border-radius:inherit;display:block}
/* Annuaire des utilisateurs : avatars plus grands et ronds, façon trombinoscope. */
#team .who-chip{gap:11px}
#team .who-chip .av{width:36px;height:36px;border-radius:50%;font-size:13px}
#team tbody td{vertical-align:middle}

/* Calendrier */
.cal-grid{display:grid;grid-template-columns:repeat(7,1fr);border-top:1px solid var(--line)}
.cal-dow{background:var(--surface-2);padding:8px;font-size:11px;color:var(--text-3);font-weight:600;
  text-align:center;border-right:1px solid var(--line);border-bottom:1px solid var(--line)}
.cal-dow:last-child{border-right:none}
.cal-cell{background:var(--surface);min-height:92px;padding:7px;display:flex;flex-direction:column;gap:4px;
  border-right:1px solid var(--line);border-bottom:1px solid var(--line)}
.cal-cell:nth-child(7n+7){border-right:none}
.cal-cell.pad,.cal-cell.wknd{background:var(--surface-2)}
.cal-cell.today{background:var(--t-verte);box-shadow:inset 0 0 0 1.5px var(--brand-2)}
.cal-d{font-size:11px;font-weight:600;color:var(--text-3);font-variant-numeric:tabular-nums}
.cal-cell.today .cal-d{color:var(--t-verte-i)}
.ev{font-size:11px;border-radius:6px;padding:3px 6px;overflow:hidden;white-space:nowrap;text-overflow:ellipsis;
  font-weight:550;display:flex;gap:4px}
/* L'heure était atténuée à 70 % : sur les trois teintes de pastille, cela
   la faisait tomber à 3,1 – 3,5:1, sous le seuil de 4,5. La hiérarchie se
   fait par la graisse, qui ne coûte rien au contraste. */
.ev b{font-variant-numeric:tabular-nums;font-weight:600;margin-right:3px}
.ev-li{background:var(--t-bleue);color:var(--t-bleue-i)}
.ev-fb{background:var(--t-sauge);color:var(--t-sauge-i)}
.ev-ig{background:var(--t-foret);color:var(--t-foret-i)}
.ev-bl{background:var(--t-menthe);color:var(--t-menthe-i)}
.ev-tk{background:var(--t-rouge);color:var(--t-rouge-i)}
.ev-yt{background:var(--t-jaune);color:var(--t-jaune-i)}

/* ═══ LES TROIS PAS D'ARRIVÉE ════════════════════════════════════════════
   Porté de la maquette du 31/08/2026. Ce bandeau ouvre l'accueil pour
   quelqu'un qui arrive : trois gestes courts, les mêmes pour les neuf
   services, et il DISPARAÎT une fois les trois faits — un parcours d'accueil
   qui reste à l'écran pour toujours devient du décor.
   ⚠️ La jauge et le « il reste » sont COMPTÉS sur l'état réel, jamais posés.
   C'est la règle qu'on a passé la journée à rétablir partout ailleurs : un
   chiffre affiché se mesure, sinon il ment un jour sans prévenir. */
.prise{background:linear-gradient(160deg,#1E7A47,#1B7241);color:#fff;
  border-radius:var(--r-xl);padding:18px 20px 16px;margin-bottom:18px}
.prise-tete{display:flex;align-items:center;gap:14px;margin-bottom:14px;flex-wrap:wrap}
.prise h2{font-size:16px;font-weight:700;margin:0;color:#fff;letter-spacing:-.01em}
.prise .sous{font-size:12.5px;color:rgba(255,255,255,.78);margin-top:2px}
.prise .reste{margin-left:auto;display:flex;align-items:center;gap:9px;
  font-size:11.5px;color:rgba(255,255,255,.82);white-space:nowrap}
.prise .jauge{width:96px;height:4px;border-radius:999px;
  background:rgba(255,255,255,.24);overflow:hidden;flex:none}
.prise .jauge i{display:block;height:100%;width:0;background:var(--t-jaune);
  border-radius:999px;transition:width .35s ease}
.pas-grille{display:grid;grid-template-columns:repeat(3,minmax(0,1fr));gap:10px}
@media (max-width:860px){.pas-grille{grid-template-columns:1fr}}
.pas{background:rgba(255,255,255,.12);border-radius:var(--r-lg);padding:13px 14px;
  display:flex;flex-direction:column;gap:5px}
.pas .n{display:flex;align-items:center;gap:8px;font-size:12px;font-weight:700;color:#fff}
/* ⚠️ UNE ICÔNE SANS TAILLE PREND TOUTE LA PLACE — la coche du pas fait
   remplissait sa carte dans la maquette. Vu à l'écran, jamais à la lecture. */
.pas .n svg{width:16px;height:16px;flex:none}
.pas .n > span{width:18px;height:18px;flex:none;display:grid;place-items:center;
  border-radius:50%;background:rgba(255,255,255,.22);font-size:10px;font-weight:700}
.pas .n em{margin-left:auto;font-style:normal;font-weight:500;font-size:11px;
  color:rgba(255,255,255,.7)}
.pas .d{font-size:11.5px;color:rgba(255,255,255,.78);line-height:1.45;margin-bottom:5px}
.pas .btn{align-self:flex-start;background:#fff;color:#1B7241;border:none;
  padding:6px 12px;font-size:12px;font-weight:700;border-radius:999px;cursor:pointer;
  display:inline-flex;align-items:center;gap:6px}
.pas .btn:hover{background:rgba(255,255,255,.88)}
.pas .btn svg{width:13px;height:13px}
.pas.fait{background:rgba(255,255,255,.07)}
.pas.fait .btn{background:rgba(255,255,255,.16);color:#fff;cursor:default}
.ev-in{background:var(--t-jaune);color:var(--t-jaune-i)}

.hb{display:flex;flex-direction:column;gap:12px}
.hb-row{display:grid;grid-template-columns:92px 1fr 56px;gap:12px;align-items:center;font-size:13px}
.hb-l{color:var(--text-2);font-weight:500}
.hb-t{height:20px;border-radius:6px;background:var(--surface-3);overflow:hidden}
.hb-t i{display:block;height:100%;border-radius:6px;background:linear-gradient(90deg,var(--brand),var(--brand-2));
  transition:width .6s cubic-bezier(.32,.72,0,1)}
.hb-v{text-align:right;font-weight:650;font-variant-numeric:tabular-nums}
.hb-v.na{color:var(--text-3);font-weight:400}

/* Matrice */
.mx th.rot{writing-mode:vertical-rl;transform:rotate(180deg);height:118px;padding:10px 4px;text-align:left;
  white-space:nowrap;vertical-align:bottom;transition:background .2s,color .2s}
.mx th.rot.moi{background:var(--t-verte);color:var(--t-verte-i);font-weight:700}
.mx td.c{text-align:center;padding:9px 4px}
.mx td.c.moi{background:color-mix(in srgb,var(--t-verte) 55%,transparent)}
.mx .cel{display:inline-grid;place-items:center;width:24px;height:24px;border-radius:7px;font-size:11px;
  font-weight:700}
.mx .yes{background:var(--ok-bg);color:var(--ok)}
.mx .ro{background:var(--inf-bg);color:var(--inf);font-size:11px}
.mx .no{color:var(--text-3)}   /* il signifie « aucun accès » : il doit se lire */
/* ⚠️ LE CADENAS RECULE, ET C'EST LA MESURE QUI LE DEMANDE. La matrice porte
   115 cases « aucun » contre 83 « écriture » : à opacité pleine, ce sont les
   portes FERMÉES qui prennent l'œil, alors qu'on vient y lire les portes
   ouvertes. Il doit se lire — d'où le contraste conservé — sans dominer. */
.mx .no svg{opacity:.42}
/* Servie par l'application, la case se coche : c'est un vrai bouton, et il doit
   se voir comme tel — sans quoi personne ne pense à cliquer dessus. Les cases
   que le serveur refuse (colonne Administration vue d'ailleurs) restent des
   <span> : elles ne prennent pas le focus et disent leur motif en infobulle. */
button.cel{border:1px solid transparent;font-family:inherit;cursor:pointer;padding:0;
  transition:transform .12s,box-shadow .2s,border-color .2s}
button.cel:hover{border-color:var(--line-2);box-shadow:var(--sh-1);transform:translateY(-1px)}
button.cel:focus-visible{outline:2px solid var(--brand);outline-offset:2px}
.mx .cel.fige{opacity:.45}

/* ══════════ Fiche d'une personne ══════════
   « Répartition des droits : il faut cliquer sur la personne, et c'est là
   qu'on a toutes les fonctionnalités, et affiner tous les users »
   (Antonio, 26/08/2026).

   La matrice répond à « qui a droit à cet écran ? ». Elle ne répond pas à
   « que peut faire Chloé ? » : il fallait suivre une colonne de vingt-cinq
   lignes en diagonale, et les gestes de son compte vivaient ailleurs, dans
   six boutons serrés au bout d'une ligne de tableau. La fiche renverse la
   question — une personne, ses écrans, son compte, au même endroit. */
.fp-row{cursor:pointer}
.fp-nom{background:none;border:none;font:inherit;padding:0;text-align:left;cursor:pointer;color:inherit}
.fp-nom:hover b{color:var(--vif-ink)}
.fp-nom:focus-visible{outline:2px solid var(--brand);outline-offset:2px;border-radius:6px}
.fp-hd{display:flex;align-items:center;gap:12px;padding:14px 15px;border-bottom:1px solid var(--line)}
.fp-hd .av{width:40px;height:40px;border-radius:11px;display:grid;place-items:center;
  font-size:14px;font-weight:700;flex:none;overflow:hidden}
.fp-hd .av img{width:100%;height:100%;object-fit:cover;border-radius:inherit;display:block}
.fp-id{min-width:0;flex:1}
.fp-id b{display:block;font-size:15px;font-weight:650;line-height:1.35}
.fp-id .s{display:block;font-size:12px;color:var(--text-3);overflow:hidden;
  text-overflow:ellipsis;white-space:nowrap}
.fp-corps{max-height:min(62vh,540px);overflow-y:auto}
.fp-bloc{padding:13px 15px;border-bottom:1px solid var(--line)}
.fp-bloc:last-child{border-bottom:none}
.fp-lg{font-size:11px;letter-spacing:.14em;text-transform:uppercase;color:var(--text-3);
  font-weight:650;margin-bottom:8px}
.fp-mod{display:flex;align-items:center;gap:12px;padding:7px 0;border-top:1px solid var(--line)}
.fp-mod:first-of-type{border-top:none}
.fp-mod .t{min-width:0;flex:1}
.fp-mod .t b{display:block;font-size:13px;font-weight:600;color:var(--text)}
.fp-mod .t .s{font-size:11px;color:var(--text-3)}
/* LE CRAN DE L'ECRAN (30/08/2026). Un ecran se lit comme ce qu'il est : un
   detail d'un module, pas un module de plus. D'ou le retrait a gauche, le
   corps plus petit, et le pli — treize ecrans deplies sous chacun des
   vingt-trois modules feraient une page qu'on ne lit plus. */
.fp-ecrs{margin:2px 0 4px}
.fp-ecrs>summary{cursor:pointer;font-size:11.5px;color:var(--text-3);padding:4px 0 4px 13px;
  list-style:none;user-select:none}
.fp-ecrs>summary::-webkit-details-marker{display:none}
.fp-ecrs>summary::before{content:'▸';display:inline-block;width:12px;margin-left:-13px;
  color:var(--text-3);transition:transform .15s}
.fp-ecrs[open]>summary::before{transform:rotate(90deg)}
.fp-ecrs>summary:hover{color:var(--text-2)}
.fp-ecrs>summary b{color:var(--text-2);font-weight:600}
.fp-mod.fp-ecr{padding:5px 0 5px 13px;border-top:1px dashed var(--line)}
.fp-mod.fp-ecr .t b{font-size:12px;font-weight:500;color:var(--text-2)}
/* Une case HERITEE se distingue d'une case tranchee : meme signe, trait
   pointille. Sans cela, regler le module semblerait ne rien changer. */
.mx-ecr>th{opacity:.9}
.cel.herite{border-style:dashed;opacity:.72}
.fp-seg{display:inline-flex;flex:none;border:1px solid var(--line-2);border-radius:8px;
  overflow:hidden;background:var(--surface-2)}
.fp-seg button{border:none;background:none;font:inherit;font-size:11.5px;font-weight:550;
  color:var(--text-2);padding:5px 9px;min-height:28px;cursor:pointer;border-left:1px solid var(--line);
  transition:background .15s,color .15s}
.fp-seg button:first-child{border-left:none}
.fp-seg button:hover:not(.on):not(:disabled){background:var(--surface-3)}
.fp-seg button:focus-visible{outline:2px solid var(--brand);outline-offset:-2px}
.fp-seg button:disabled{opacity:.4;cursor:default}
.fp-seg button.on{background:var(--brand-fonce);color:#fff}
/* « Comme son service » n'est pas une valeur de plus : c'est l'ABSENCE de
   décision. Elle se marque donc en creux, jamais en vert plein — sinon un
   droit hérité se lirait comme un droit posé à la main, et on cesserait de
   régler le service pour régler les personnes une par une. */
.fp-seg button.on.suit{background:var(--surface-3);color:var(--text);
  box-shadow:inset 0 0 0 1px var(--line-2)}
.fp-fige{flex:none;font-size:11px;color:var(--text-3);padding:5px 0;max-width:230px;text-align:right}
.fp-ft{display:flex;align-items:center;gap:10px;padding:11px 15px;border-top:1px solid var(--line);
  background:var(--surface-2);font-size:11.5px;color:var(--text-3)}
.fp-ft .sp{flex:1}
.fp-actes{display:flex;flex-wrap:wrap;gap:7px}

/* Fiches de suivi */
.dec{border:1px solid var(--line);border-radius:var(--r-lg);padding:14px 16px;background:var(--surface);
  display:flex;gap:13px;transition:box-shadow .2s,border-color .2s}
.dec:hover{box-shadow:var(--sh-2);border-color:var(--line-2)}
.dec .flag{display:grid;place-items:center;flex:none;width:20px;padding-top:1px}
.dec .body{min-width:0;flex:1}
.dec .h{display:flex;align-items:center;gap:9px;margin-bottom:5px;flex-wrap:wrap}
.dec .t{font-size:13px;font-weight:620;color:var(--text)}
.dec .d{font-size:13px;color:var(--text-2);line-height:1.6}
.dec .o{font-size:13px;color:var(--text-2);line-height:1.6;margin-top:9px;padding:9px 12px;
  background:var(--surface-2);border-radius:var(--r);border-left:2px solid var(--line-2)}
.dec .meta{font-size:11px;color:var(--text-3);margin-top:9px}

.srv{display:flex;align-items:center;gap:12px;padding:12px 16px;border-bottom:1px solid var(--line);
  transition:background .15s}
.srv:last-child{border-bottom:none}
.srv:hover{background:var(--surface-2)}
.srv .pulse{width:9px;height:9px;border-radius:50%;flex:none}
.srv .pulse.ok{background:var(--brand-2);box-shadow:0 0 0 3.5px var(--ok-bg)}
.srv .pulse.att{background:var(--yellow);box-shadow:0 0 0 3.5px var(--att-bg)}
.srv .pulse.alr{background:#C00020;box-shadow:0 0 0 3.5px var(--alr-bg)}
.srv .n{font-size:13px;font-weight:550;color:var(--text);flex:none;width:176px}
.srv .s{font-size:12px;color:var(--text-2);flex:1}
.srv .b{margin-left:auto;flex:none}

/* ══════════ Barre d'onglets — LE SEUL ENDROIT OÙ VIVENT LES ONGLETS ══════════
   Depuis le 27/08/2026, le rail ne les recopie plus (voir « il n'y a plus de
   sous-navigation dans le rail ») : cette rangée est la sous-navigation, et
   elle est en haut, en horizontal.
   Le dessin suit le modèle relevé sur Mobbin (Salesforce Lightning) : pas de
   pastille ni de cadre, une rangée de libellés posée sur un filet, et le
   TRAIT de l'onglet ouvert qui glisse d'un onglet à l'autre (.tabx-jauge).
   L'œil suit un mouvement au lieu de relire sept boutons pour trouver lequel
   a changé. Une pastille encadrée se lisait comme un composant de plus au
   milieu de la page ; un filet, lui, prolonge la barre du haut.
   Trois signes portent l'état, pas un seul : le trait vert #3bae79, le
   libellé en --vif-ink et sa graisse — plus aria-selected pour qui écoute.
   Un daltonien, un écran en plein soleil ou un lecteur d'écran s'en sortent.
   La jauge est un PLUS : tant que la barre n'a pas la classe `jauge-ok`
   (pas de JavaScript, ou vue encore cachée donc non mesurable), l'onglet
   ouvert porte lui-même son trait. On ne perd jamais l'onglet ouvert. */
/* L'AIDE PASSE DERRIERE UN « ? » (Antonio, 30/08/2026 : « ça gâche l'espace »).
   Ces paves expliquent d'ou viennent les chiffres, et ils sont justes — mais ils
   se lisent UNE fois et occupent la pleine largeur a CHAQUE ouverture de
   l'ecran. Le texte ne bouge pas d'un mot : il change de place. Il reste dans
   son panneau, avec l'onglet qu'il explique — sortir l'aide de son onglet
   obligerait a savoir de quel onglet elle parle. */
.msg.inf.aide{display:none}
.msg.inf.aide.on{display:flex;margin-bottom:16px}
/* ⚠️ `min-height:0` : SANS LUI LE « ? » EST UN OVALE, pas un rond (vu a
   l'ecran le 30/08/2026, Antonio : « arrondis bien l'icone du ? »). `.modx`
   impose `min-height:42px` a toute la barre ; `height:22px` ne l'annule pas,
   donc la boite faisait 24 de large sur 42 de haut et `border-radius:50%`
   dessinait fidelement une ellipse. Un rond se fait a boite CARREE.
   `line-height:1` pour la meme raison : le `?` centre sa boite, pas sa ligne. */
/* ⚠️ ET LE CENTRAGE EST OPTIQUE, PAS GEOMETRIQUE (30/08/2026, second passage).
   La boite est carree, le rond est donc juste — mesure : 24x24, rayon 50%.
   Le GLYPHE, lui, restait haut : « ? » n'a pas de jambage, mais la ligne en
   reserve la place dessous. Le signe se posait donc dans le tiers superieur
   d'un cercle qui, lui, est centre. Un `padding-top` de 2px le redescend d'un
   pixel (la grille recentre dans ce qui reste), et 15px de corps lui rendent
   la presence des icones voisines : a 13,5 il flottait dans son cercle. */
.modx.aidx{margin-left:8px;align-self:center;flex:none;
  width:24px;height:24px;min-height:0;padding:2px 0 0;line-height:1;
  border-radius:50%;border:1px solid var(--line-2);color:var(--text-3);
  font-size:15px;font-weight:700;display:grid;place-items:center}
.modx.aidx:hover{color:var(--text);border-color:var(--text-3)}
.modx.aidx[aria-expanded="true"]{background:var(--vif);border-color:var(--vif);color:#fff}
/* LES ONGLETS D'UN ECRAN MONTENT DANS LA BARRE DU HAUT (Antonio, 30/08/2026 :
   « toutes les onglets en bas, monte sur la nav d'en haut »). La barre reste
   dans le DOM — elle garde l'etat, les panneaux et le clavier — mais elle ne
   se dessine plus : ce sont les copies de `.modbar` qui la pilotent. On ne
   masque QUE les barres de premier niveau (`.view > .tabx-bar`) : celles qui
   vivent dans une carte sont des sous-onglets, elles restent chez elles. */
.view > .tabx-bar{display:none}
.modx.ongx{font-weight:600;color:var(--text-2)}
/* UN GROUPE D'ONGLETS NOMMÉ. Il se replie à l'intérieur de lui-même, ce qui
   garde son étiquette collée à ses onglets ; la barre, elle, se replie entre
   les groupes. Dix-sept onglets deviennent « treize écrans du pilotage » puis
   « quatre de la conformité », au lieu d'une liste qu'on lit jusqu'au bout
   pour savoir ce qu'elle contient. */
.modbar .ongrp{display:flex;flex-wrap:wrap;align-items:stretch;gap:2px;min-width:0}
.modbar .ongfam{align-self:center;flex:none;font-size:10px;font-weight:700;
  letter-spacing:.11em;text-transform:uppercase;color:var(--text-3);
  padding:0 11px 0 4px;margin-right:5px;border-right:1px solid var(--line);
  white-space:nowrap}
.modbar .ongrp + .ongrp .ongfam{padding-left:11px;margin-left:2px}
.modx.ongx.on{color:var(--text)}
.modbar .sep{align-self:center;width:1px;height:18px;margin:0 9px;
  background:var(--line);flex:none}
.tabx-bar{position:relative;display:flex;gap:2px;background:none;
  border:0;border-bottom:1px solid var(--line);border-radius:0;
  padding:0;margin:0 0 18px;overflow-x:auto;width:100%;max-width:100%;
  scrollbar-width:none;-webkit-overflow-scrolling:touch}
.tabx-bar::-webkit-scrollbar{display:none}
/* Le bord s'estompe du côté où il reste des onglets : la barre dit
   elle-même qu'elle continue, sans flèche rapportée. */
.tabx-bar.defile-g{-webkit-mask-image:linear-gradient(90deg,transparent 0,#000 30px,#000 100%);
  mask-image:linear-gradient(90deg,transparent 0,#000 30px,#000 100%)}
.tabx-bar.defile-d{-webkit-mask-image:linear-gradient(90deg,#000 0,#000 calc(100% - 30px),transparent 100%);
  mask-image:linear-gradient(90deg,#000 0,#000 calc(100% - 30px),transparent 100%)}
.tabx-bar.defile-g.defile-d{-webkit-mask-image:linear-gradient(90deg,transparent 0,#000 30px,#000 calc(100% - 30px),transparent 100%);
  mask-image:linear-gradient(90deg,transparent 0,#000 30px,#000 calc(100% - 30px),transparent 100%)}
/* Le trait vert : la signature de la navigation. Il est posé sur le filet du
   bas — `bottom:0`, donc juste au dessus du trait de la barre : la boîte
   défile en x, ce qui rogne tout ce qui déborderait en dehors. */
/* UNE BARRE EN RANGÉES NOMMÉES. Elle ne défile plus de côté : elle se replie,
   et chaque rangée porte son nom. Réservé aux barres qui en ont trop pour une
   ligne — ailleurs, le défilement reste le bon geste. */
.tabx-bar.rangs{flex-wrap:wrap;overflow-x:visible;row-gap:2px}
.tabx-bar.rangs::before,.tabx-bar.rangs::after{display:none}
.tabx-rang{flex:0 0 100%;font-size:10.5px;font-weight:700;letter-spacing:.12em;
  text-transform:uppercase;color:var(--muted);padding:12px 2px 3px;line-height:1}
.tabx-rang:first-child{padding-top:2px}
.tabx-jauge{position:absolute;top:auto;bottom:0;left:0;width:0;height:3px;
  border-radius:3px 3px 0 0;background:var(--vif);
  opacity:0;pointer-events:none;z-index:1;
  transition:transform .34s var(--nav-courbe),width .34s var(--nav-courbe),opacity .2s}
.tabx-bar.jauge-ok .tabx-jauge{opacity:1}
.tabx{position:relative;z-index:1;border:none;background:none;padding:11px 15px;font-size:13px;
  font-weight:550;color:var(--text-2);border-radius:8px 8px 0 0;white-space:nowrap;min-height:44px;
  transition:color .18s,background .18s,box-shadow .18s}
.tabx:hover{color:var(--text);background:rgba(19,32,24,.045)}
.tabx.on,.tabx.on:hover{color:var(--vif-ink);font-weight:650;background:none}
/* Repli : la barre n'a pas pu être mesurée, l'onglet porte lui-même son trait. */
.tabx-bar:not(.jauge-ok) .tabx.on{box-shadow:inset 0 -3px 0 var(--vif)}
.tabp{display:none}.tabp.on{display:block}
/* Bascule d'un graphique (contrats/ruptures). Classe distincte de .tabx pour
   ne PAS déclencher le gestionnaire d'onglets : elle ne change qu'une courbe. */
/* Même langage que la barre d'onglets, en plus petit : pastille blanche,
   trait vert, libellé lisible. Sans jauge glissante — deux boutons de
   largeur fixe n'ont rien à faire suivre du regard. */
.segx{display:inline-flex;gap:2px;background:var(--surface-3);border:1px solid var(--line);border-radius:10px;padding:3px}
.segx button{border:none;background:none;padding:6px 12px;font-size:12px;font-weight:600;color:var(--text-2);border-radius:7px;cursor:pointer;min-height:24px;transition:background .2s,color .2s,box-shadow .2s}
.segx button:hover{color:var(--text);background:rgba(19,32,24,.045)}
.segx button.on,.segx button.on:hover{background:var(--surface);color:var(--vif-ink);
  box-shadow:var(--sh-1),0 0 0 1px var(--vif-ring),inset 0 -2px 0 var(--vif)}
.pil-site{border:1px solid var(--line);background:var(--surface);border-radius:8px;padding:6px 28px 6px 10px;font-size:12px;font-weight:600;color:var(--text);min-height:24px;cursor:pointer;appearance:none;-webkit-appearance:none;background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='12' height='12' viewBox='0 0 24 24' fill='none' stroke='%23415245' stroke-width='2'%3E%3Cpath d='M6 9l6 6 6-6'/%3E%3C/svg%3E");background-repeat:no-repeat;background-position:right 8px center}
/* Petits graphiques de répartition (histogramme + anneaux). */
.chart-t{font-size:12px;font-weight:650;color:var(--text-2);margin-bottom:8px}
.chart-box{position:relative;height:220px}

.empty{text-align:center;padding:40px 22px;color:var(--text-3)}
.empty .ill{display:grid;place-items:center;margin:0 auto 13px;color:var(--line-2)}
.empty h4{font-size:15px;font-weight:620;color:var(--text-2);margin-bottom:6px}
.empty p{font-size:13px;max-width:440px;margin:0 auto;line-height:1.6}

/* Lecture seule */
/* L'apparence seulement : le vrai verrou est `disabled`, pose par
   gelerCommandes(). `pointer-events:none` reste pour les elements qui ne
   sont pas des boutons et ne peuvent donc pas etre desactives. */
.view.ro .btn:not(.nav-only),.view.ro .composer button,.view.ro .chip{opacity:.45}
.view.ro .chip:not(button),.view.ro .btn:disabled{pointer-events:none}
.view.ro textarea{background:var(--surface-2);color:var(--text-2);pointer-events:none}
.ro-bar{display:none;align-items:flex-start;gap:11px;background:var(--inf-bg);color:var(--text-2);
  border:1px solid color-mix(in srgb,var(--inf) 18%,transparent);border-radius:var(--r-lg);
  padding:12px 15px;margin-bottom:18px;font-size:13px;line-height:1.6}
.ro-bar .mi{color:var(--inf);flex:none;margin-top:1px}
.ro-bar b{color:var(--text);font-weight:600}
.view.ro .ro-bar{display:flex}


/* ══════════ Tickets et avancement ══════════ */
.prog{display:flex;height:8px;border-radius:99px;overflow:hidden;background:var(--surface-3);gap:2px}
.prog i{display:block;height:100%;transition:width .6s cubic-bezier(.32,.72,0,1)}
.prog .fait{background:var(--brand)}
.prog .cours{background:var(--brand-2)}
.prog .bloque{background:#C00020}
.prog .todo{background:var(--line-2)}
.leg{display:flex;gap:14px;flex-wrap:wrap;font-size:12px;color:var(--text-2);margin-top:9px}
.leg span{display:inline-flex;align-items:center;gap:5px}
.leg i{width:8px;height:8px;border-radius:3px;display:block}




/* Phases de la feuille de route */
.ph{display:flex;gap:14px;padding:14px 18px;border-bottom:1px solid var(--line);align-items:flex-start}
.ph:last-child{border-bottom:none}
.ph.en-cours{background:var(--t-verte)}
.ph-p{flex:none;width:74px;font-size:12px;font-weight:700;color:var(--text-3);padding-top:1px}
.ph.en-cours .ph-p{color:var(--t-verte-i)}
.ph-b{flex:1;min-width:0}
.ph-t{font-size:13px;font-weight:620;color:var(--text)}
.ph-s{font-size:13px;color:var(--text-2);line-height:1.55;margin-top:2px}
.ph-j{font-size:12px;color:var(--text-3);margin-top:6px;padding-left:10px;border-left:2px solid var(--line-2)}
.ph.en-cours .ph-j{border-left-color:var(--brand-2)}
.ph-e{flex:none}
@media(max-width:720px){.ph{flex-wrap:wrap}.ph-p{width:auto}}


/* ══════════ Lien d'évitement ══════════ */
.skip{position:absolute;left:-9999px;top:0;z-index:60;background:var(--brand-fonce);color:#fff;
  padding:11px 18px;border-radius:0 0 var(--r) 0;font-weight:600;font-size:13px}
.skip:focus{left:0}

/* ══════════ Boutons de la barre supérieure ══════════ */
.tb-btn{position:relative;display:grid;place-items:center;width:36px;height:36px;border-radius:9px;
  border:1px solid var(--line);background:var(--surface);color:var(--text-2);
  transition:background .15s,color .15s,border-color .15s}
.tb-btn:hover{background:var(--surface-2);color:var(--text);border-color:var(--line-2)}
.tb-btn[aria-expanded=true]{background:var(--t-verte);color:var(--t-verte-i);border-color:var(--brand-2)}
/* ⚠️ LES RÈGLES `#b-compte` ONT ÉTÉ RETIRÉES ICI le 28/08/2026. Elles
   habillaient la photo quand elle était un bouton rond dans la barre blanche :
   fond vert pâle, anneau intérieur, 50 % de rayon. La photo est descendue au
   bas du rail, où `.me` l'habille — mais un sélecteur d'ID l'emporte sur une
   classe : le vert pâle revenait par-dessus, et la photo se lisait comme une
   pastille écrasée sur le vert de la colonne. Un style qui suit un ÉLÉMENT
   doit déménager avec lui, ou disparaître. */
.tb-btn img{width:100%;height:100%;object-fit:cover;border-radius:50%;display:block}
#pc-av{overflow:hidden}
#pc-av img{width:100%;height:100%;object-fit:cover;display:block}
.tb-btn .pastille{position:absolute;top:5px;right:5px;width:8px;height:8px;border-radius:50%;
  background:var(--yellow);border:1.5px solid var(--surface)}

/* ══════════ Panneaux flottants ══════════ */
.pop{position:absolute;top:calc(100% + 8px);right:0;width:334px;background:var(--surface);
  border:1px solid var(--line-2);border-radius:var(--r-lg);box-shadow:var(--sh-3);z-index:30;
  overflow:hidden;
  /* Sortie plus courte et plus discrète que l'entrée : l'attention part déjà ailleurs. */
  opacity:0;visibility:hidden;transform:translateY(-6px) scale(.99);
  transition:opacity .12s ease-in,transform .12s ease-in,visibility 0s .12s}
.pop.on{opacity:1;visibility:visible;transform:none;
  transition:opacity .19s cubic-bezier(.32,.72,0,1),transform .19s cubic-bezier(.32,.72,0,1),visibility 0s}
.pop-hd{padding:12px 15px;border-bottom:1px solid var(--line);display:flex;align-items:center;gap:9px}
.pop-hd h4{font-size:13px;font-weight:620;flex:1}
.pop-hd .lien{font-size:12px;color:var(--t-verte-i);background:none;border:none;font-weight:600;min-height:24px;display:inline-flex;align-items:center;padding:0 4px}
.pop-bd{max-height:328px;overflow-y:auto}
.pop-ft{padding:10px 15px;border-top:1px solid var(--line);background:var(--surface-2)}
/* ══════════ La cloche : un visage, un fait, une heure ══════════
   Modèle repris du panneau de notifications d'Adobe (Antonio, 29/08/2026,
   référence Mobbin) : le point de ce qui n'est pas lu, la PHOTO de la personne
   avec la source en médaillon sur son coin, le fait, le détail, l'heure
   relative, et le chevron qui dit que la ligne mène quelque part. Les lignes
   se rangent par RUBRIQUE (« À traiter », puis par jour) et se filtrent par
   THÈME.

   Le panneau s'élargit pour ça : à 334 px, une photo de 34 px, un chevron et
   deux lignes de texte ne tenaient pas — le détail se coupait au troisième
   mot, c'est-à-dire avant d'avoir rien dit. Sur téléphone il reprend la règle
   commune des panneaux (bord à bord, plus bas). */
#p-notif{width:392px}
/* Une ligne est passée de deux à trois lignes de texte : à 328 px on n'en
   voyait plus que trois et demie, et le rangement par rubrique ne servait
   plus à rien puisqu'on ne voyait jamais deux rubriques à la fois. */
#p-notif .pop-bd{max-height:428px}

/* La barre de thème : elle est SOUS l'en-tête et pas dedans. Trois choses sur
   une ligne de 392 px (titre, « tout marquer », filtre) se serrent, et c'est
   le filtre qui perd — or c'est lui qu'on vient chercher quand la cloche est
   pleine. */
.nf-barre{display:flex;align-items:center;gap:8px;padding:8px 14px;
  border-bottom:1px solid var(--line);background:var(--surface-2)}
.nf-barre select{appearance:none;-webkit-appearance:none;font:inherit;font-size:12px;font-weight:600;
  color:var(--text);background:var(--surface);border:1px solid var(--line-2);border-radius:999px;
  padding:4px 26px 4px 11px;max-width:230px;cursor:pointer;
  /* Le chevron est dessiné dans le fond : un `select` dépouillé n'en a plus,
     et sans lui rien ne dit que la ligne s'ouvre. */
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='%235B6B62'%3E%3Cpath d='M6.6 9.1a1.2 1.2 0 0 1 1.7 0l3.7 3.6 3.7-3.6a1.2 1.2 0 1 1 1.7 1.7l-4.6 4.5a1.2 1.2 0 0 1-1.7 0L6.6 10.8a1.2 1.2 0 0 1 0-1.7Z'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 7px center;background-size:14px}
.nf-barre .cpt{margin-left:auto;font-size:11px;color:var(--text-3);white-space:nowrap}

/* La rubrique. Elle colle en haut pendant qu'on fait défiler : sinon, arrivé
   au milieu de « Plus tôt », on ne sait plus de quel jour on parle. */
.nf-sec{position:sticky;top:0;z-index:1;padding:9px 14px 5px;background:var(--surface);
  font-size:11.5px;font-weight:700;letter-spacing:.05em;text-transform:uppercase;color:var(--text-3);
  border-bottom:1px solid var(--line)}

.notif{display:flex;gap:10px;align-items:flex-start;padding:11px 13px 11px 7px;
  border-bottom:1px solid var(--line);width:100%;
  text-align:left;background:none;border-left:none;border-right:none;border-top:none;transition:background .15s}
.notif:last-child{border-bottom:none}
.notif:hover{background:var(--surface-2)}
/* CE QUI N'EST PAS LU SE MARQUE D'UN POINT, plus d'un aplat jaune sur toute
   la ligne. L'aplat passait derrière la photo et derrière le médaillon, qui
   portent déjà de la couleur : trois teintes sur trente pixels, on ne lisait
   plus laquelle voulait dire quoi. Le point tient la place même quand il est
   éteint, sinon les lignes lues se décalent de six pixels. */
.notif .pt{flex:none;width:6px;height:6px;border-radius:50%;margin-top:15px;background:transparent}
.notif.neuf .pt{background:var(--brand-2)}
.notif.neuf .t{font-weight:640}

/* Le visage. `place-items:center` centre l'unique enfant en flux (la photo ou
   les initiales) ; le médaillon est hors flux, il ne compte pas comme second. */
.nf-av{position:relative;flex:none;width:34px;height:34px;border-radius:11px;
  display:grid;place-items:center;font-size:12px;font-weight:700;line-height:1}
.nf-av img{width:34px;height:34px;object-fit:cover;border-radius:11px;display:block}
/* Le médaillon dit D'OÙ vient la ligne. Sans lui, deux notifications de la
   même personne se ressemblent trop pour être triées de l'œil. Le liseré
   reprend le fond du panneau : c'est ce qui le détache de la photo. */
.nf-bg{position:absolute;right:-3px;bottom:-3px;width:17px;height:17px;border-radius:50%;
  display:grid;place-items:center;border:2px solid var(--surface)}
.notif:hover .nf-bg{border-color:var(--surface-2)}

.notif .b{min-width:0;flex:1;display:flex;flex-direction:column;gap:2px}
.notif .t{font-size:13px;font-weight:520;color:var(--text);line-height:1.4;
  display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}
.notif .t b{font-weight:700}
.notif .s{font-size:12px;color:var(--text-3);line-height:1.45;
  display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}
/* L'heure relative. Tabulaire pour que « il y a 9 min » et « il y a 12 min »
   s'alignent d'une ligne à l'autre. */
.notif .q{font-size:11px;color:var(--text-3);margin-top:3px;font-variant-numeric:tabular-nums}
/* Le chevron n'apparaît qu'au survol : à l'arrêt, quinze chevrons font une
   colonne de bruit le long du panneau. Au clavier il suit le focus. */
.notif .ch{flex:none;align-self:center;color:var(--text-3);display:grid;place-items:center;
  opacity:0;transition:opacity .15s}
.notif:hover .ch,.notif:focus-visible .ch{opacity:1}
.opt{display:flex;align-items:center;gap:10px;padding:9px 15px;width:100%;text-align:left;background:none;
  border:none;font-size:13px;color:var(--text);transition:background .15s}
.opt:hover{background:var(--surface-2)}
.opt .ck{margin-left:auto;color:var(--brand-2)}
.opt.on{font-weight:600}
.pop-sep{height:1px;background:var(--line);margin:5px 0}

/* ══════════ Messages de confirmation ══════════ */
.toasts{position:fixed;bottom:22px;left:50%;transform:translateX(-50%);z-index:55;display:flex;
  flex-direction:column;gap:9px;align-items:center;pointer-events:none}
.toast{display:flex;align-items:center;gap:10px;background:var(--rail);color:#fff;border-radius:10px;
  padding:11px 17px;font-size:13px;font-weight:500;box-shadow:var(--sh-3);max-width:min(460px,92vw);
  pointer-events:auto;animation:monte .26s cubic-bezier(.32,.72,0,1)}
.toast .mi{color:var(--brand-3);flex:none}
.toast.alr .mi{color:#E8A29C}
.toast b{font-weight:650}
.toast.sort{animation:descend .22s ease forwards}
@keyframes monte{from{opacity:0;transform:translateY(14px) scale(.97)}to{opacity:1;transform:none}}
@keyframes descend{to{opacity:0;transform:translateY(10px) scale(.98)}}

/* ══════════ Recherche dans un tableau ══════════ */
.filtre{display:flex;align-items:center;gap:8px;background:var(--surface-2);border:1px solid var(--line-2);
  border-radius:9px;padding:0 11px;min-height:34px;max-width:270px;flex:1}
.filtre input{flex:1;border:none;background:none;font-size:13px;outline:none;min-width:0;padding:7px 0}
.filtre input::placeholder{color:var(--text-3)}
/* Le champ porte outline:none — c'est le cadre qui doit alors le dire. Sans
   cette règle, le seul arrêt de tabulation sans indicateur de tout l'outil. */
.filtre:focus-within{border-color:var(--brand);box-shadow:0 0 0 3px rgba(40,130,90,.22)}
.filtre .vider{border:none;background:none;color:var(--text-3);display:none;padding:0;min-width:24px;min-height:24px;align-items:center;justify-content:center}
.filtre.rempli .vider{display:inline-flex}
tr[hidden]{display:none}

/* ══════════ États vides et chargement ══════════ */
.vide{text-align:center;padding:34px 20px;color:var(--text-3)}
.vide .ill{display:grid;place-items:center;margin:0 auto 11px;color:var(--line-2)}
.vide h4{font-size:13px;font-weight:620;color:var(--text-2);margin-bottom:4px}
.vide p{font-size:12px;max-width:380px;margin:0 auto;line-height:1.55}

/* ══════════ Vagues de tournage ══════════ */
.vague{border:1px solid var(--line);border-radius:var(--r-lg);overflow:hidden;background:var(--surface)}
.vague-hd{display:flex;align-items:center;gap:10px;padding:11px 15px;background:var(--surface-2);
  border-bottom:1px solid var(--line)}
.vague-hd .t{font-size:13px;font-weight:650}
.vague-hd .d{font-size:12px;color:var(--text-3)}
.vague-hd .st{margin-left:auto}
.capt{display:flex;align-items:center;gap:11px;padding:10px 15px;border-bottom:1px solid var(--line)}
.capt:last-child{border-bottom:none}
.capt .av{width:26px;height:26px;border-radius:8px;display:grid;place-items:center;font-size:11px;
  font-weight:700;flex:none}
.capt .n{flex:1;min-width:0;font-size:13px;color:var(--text);font-weight:500}
.capt .q{flex:none;font-size:12px;color:var(--text-3);width:74px;text-align:right;
  font-variant-numeric:tabular-nums}
.capt .c{flex:none;width:132px;text-align:right}
@media(max-width:720px){.capt .q{display:none}}

/* ══════════ Barre de progression d'étape ══════════ */
.etapes{display:flex;gap:0;padding:2px 0}
.etape{flex:1;text-align:center;position:relative;padding:0 4px}
.etape::before{content:'';position:absolute;top:9px;left:-50%;right:50%;height:2px;background:var(--line-2)}
.etape:first-child::before{display:none}
.etape.ok::before{background:var(--brand-2)}
.etape .p{width:20px;height:20px;border-radius:50%;background:var(--surface-3);border:2px solid var(--surface);
  display:grid;place-items:center;margin:0 auto 7px;position:relative;z-index:1;font-size:11px;
  font-weight:700;color:var(--text-3)}
.etape.ok .p{background:var(--brand-fonce);color:#fff}
.etape.actif .p{background:var(--yellow);color:var(--rail);box-shadow:0 0 0 3px var(--t-jaune)}
.etape .l{font-size:12px;color:var(--text-2);line-height:1.35}
.etape.actif .l{color:var(--text);font-weight:600}

/* ══════════ Parcours de recrutement — le fil conducteur ══════════ */
/* La candidature de la source au placement. Chaque étape est un raccourci vers
   l'endroit où l'on agit ; la ligne les relie sans imposer un curseur unique —
   un pipeline a du monde à chaque étape. Les compteurs vivants restent dans les
   indicateurs, dessous : ici on montre le chemin, pas les chiffres. */
.parcours{display:flex;gap:0;background:var(--surface);border:1px solid var(--line);
  border-radius:var(--r-xl);padding:15px 6px 16px;overflow-x:auto;box-shadow:var(--sh-1)}
.parc{flex:1 1 0;min-width:150px;position:relative;padding:0 10px;text-align:center;
  background:none;border:none;color:inherit;display:flex;flex-direction:column;align-items:center;
  cursor:pointer}
/* La ligne entre deux pastilles, à hauteur de leur centre. */
.parc::before{content:'';position:absolute;top:16px;left:-50%;right:50%;height:2px;
  background:var(--line-2);border-radius:2px}
.parc:first-child::before{display:none}
.parc .rang{position:relative;z-index:1;width:34px;height:34px;border-radius:50%;
  display:grid;place-items:center;margin-bottom:10px;font-size:13px;font-weight:700;
  background:var(--t-verte);color:var(--t-verte-i);
  box-shadow:0 0 0 4px var(--surface);   /* casse la ligne au droit de la pastille */
  transition:background .18s,color .18s,transform .2s cubic-bezier(.34,1.56,.64,1)}
.parc:hover .rang,.parc:focus-visible .rang{background:var(--brand-fonce);color:#fff;transform:translateY(-2px)}
.parc .ti{font-size:13px;font-weight:640;color:var(--text);line-height:1.25;transition:color .18s}
.parc:hover .ti{color:var(--brand-fonce)}
.parc .de{font-size:11.5px;color:var(--text-3);line-height:1.4;margin-top:3px;max-width:17ch}
/* Le repère « où agir » n'apparaît qu'au survol : discret, mais toujours dans le DOM. */
.parc .va{display:inline-flex;align-items:center;gap:3px;margin-top:8px;font-size:11px;font-weight:600;
  color:var(--brand-fonce);opacity:0;transform:translateY(-2px);
  transition:opacity .18s,transform .18s}
.parc:hover .va,.parc:focus-visible .va{opacity:1;transform:none}
.parc:focus-visible{outline:none}
.parc:focus-visible .rang{box-shadow:0 0 0 4px var(--surface),0 0 0 6px var(--brand-fonce)}
@media(max-width:860px){.parcours{padding-left:14px;padding-right:14px}
  .parc{min-width:138px}.parc .va{opacity:1;transform:none}}


@media(max-width:860px){
  .rail{gap:2px;border-bottom:1px solid rgba(255,255,255,.10);
    box-shadow:0 2px 12px rgba(0,0,0,.18);scrollbar-width:none}
  .rail::-webkit-scrollbar{display:none}
  .uni{min-width:70px;font-size:11px}
  .tb-ligne{display:flex;flex-wrap:wrap;padding:9px 15px;gap:10px}
  .cmd-open{order:3;max-width:none}
  .modbar{padding:0 15px}
  .page-title{font-size:15px}
    .tb-right{gap:7px}
  .pop{position:fixed;left:12px;right:12px;top:auto;width:auto;max-width:none}
  /* Sans cette ligne, l'identifiant l'emporterait sur la classe et la cloche
     resterait à 392 px, hors de l'écran par la droite. */
  #p-notif{width:auto}
  .toasts{bottom:14px;left:12px;right:12px;transform:none;align-items:stretch}
  .toast{max-width:none}
  .flow{padding-left:14px;padding-right:14px}
  .step{min-width:124px}
  .card-hd{flex-wrap:wrap}
  .card-hd .act{margin-left:0;width:100%}
  .filtre{max-width:none}
  .duo{gap:14px}
}


@media(max-width:860px){
  /* Les lignes de service passent en colonnes : un libellé de 230 px ne tient pas. */
  .srv{flex-wrap:wrap;row-gap:5px;padding:12px 15px}
  .srv .n{width:auto!important;flex:1 1 auto;min-width:0}
  .srv .s{flex:1 1 100%;order:3}
  .srv .b{margin-left:auto}
  .capt{flex-wrap:wrap;row-gap:5px}
  .capt .c{width:auto;margin-left:auto}
  /* Grilles à largeur minimale : on autorise le défilement plutôt que le débordement. */
  .cal-grid{min-width:600px}
  .etapes{min-width:460px}
  .card-bd .etapes{margin:0 -2px}
  .rail-info .row, .card-bd .row{flex-wrap:wrap;row-gap:2px}
  .rail-info .k, .card-bd .k{width:100%}
  .dec{flex-wrap:wrap}
  .hb-row{grid-template-columns:78px 1fr 48px;gap:8px;font-size:12px}
  .tabx-bar{width:100%}
  .grid{gap:12px}
  .content{padding:16px 14px 44px}
  .sec{margin:20px 0 11px}
  .sec .hint{display:none}
}
/* Toute grille large reste défilable dans son propre conteneur. */
.etapes-wrap{overflow-x:auto}


/* ══════════ Dépôt et registre des autorisations ══════════ */
.depot{border:2px dashed var(--line-2);border-radius:var(--r-lg);padding:26px 20px;text-align:center;
  background:var(--surface-2);transition:border-color .18s,background .18s}
.depot:hover,.depot.survol{border-color:var(--brand-2);background:var(--t-verte)}
.depot .ic{color:var(--brand-2);display:grid;place-items:center;margin:0 auto 12px}
.depot h4{font-size:13px;font-weight:620;color:var(--text);margin-bottom:4px}
.depot p{font-size:12px;color:var(--text-3);line-height:1.55;max-width:360px;margin:0 auto 13px}
.depot .btn-row{justify-content:center}
.fiche{display:flex;align-items:center;gap:11px;padding:10px 15px;border-bottom:1px solid var(--line)}
.fiche:last-child{border-bottom:none}
.fiche .doc{width:30px;height:38px;border-radius:5px;border:1px solid var(--line-2);background:var(--surface-2);
  display:grid;place-items:center;flex:none;color:var(--text-3);font-size:11px;font-weight:700;letter-spacing:.04em}
.fiche .doc.ok{border-color:var(--brand-2);background:var(--t-verte);color:var(--t-verte-i)}
.fiche .b{flex:1;min-width:0;display:flex;flex-direction:column;gap:1px}
.fiche .n{font-size:13px;font-weight:600;color:var(--text)}
.fiche .m{font-size:12px;color:var(--text-3)}
.fiche .a{flex:none;display:flex;gap:6px;align-items:center}


/* ══════════ Calendrier manipulable ══════════ */
.cal-wrap{display:grid;grid-template-columns:1fr 300px;gap:16px;align-items:start}
@media(max-width:1100px){.cal-wrap{grid-template-columns:1fr}}

.cal-cell{position:relative;cursor:pointer}
.cal-cell:hover{background:var(--surface-2)}
.cal-cell.wknd:hover{background:var(--surface-3)}
.cal-cell.sel{box-shadow:inset 0 0 0 2px var(--brand);background:var(--t-verte)}
.cal-cell.survol{background:var(--t-jaune);box-shadow:inset 0 0 0 2px var(--yellow)}
.cal-cell:focus-visible{outline:none;box-shadow:inset 0 0 0 2px var(--brand)}
/* 24 × 24 : la taille de cible minimale du critère 2.5.8. Et `display:none`
   rendait ce bouton inatteignable au clavier — c'est `opacity` qui le cache
   maintenant, il garde donc sa place dans l'ordre de tabulation et se montre
   dès qu'il reçoit le focus. */
.cal-cell .plus{position:absolute;top:4px;right:4px;width:24px;height:24px;border-radius:6px;
  border:none;background:var(--brand);color:#fff;display:grid;place-items:center;font-size:13px;
  line-height:1;padding:0;opacity:0;transition:opacity .15s}
.cal-cell:hover .plus,.cal-cell.sel .plus,.cal-cell .plus:focus-visible{opacity:1}
.cal-cell .plus:focus-visible{outline:2px solid var(--brand);outline-offset:2px}
.cal-cell.pad .plus{display:none!important}

.ev{cursor:grab;user-select:none;transition:transform .12s,box-shadow .12s}
.ev:active{cursor:grabbing}
.ev:hover{transform:translateX(1px);box-shadow:0 1px 4px rgba(19,32,24,.16)}
.ev.deplace{opacity:.4}
.ev.brouillon{border:1px dashed currentColor;background:transparent!important}
.ev .sup{margin-left:auto;opacity:0;font-size:12px;line-height:1;padding:0 1px}
.ev:hover .sup{opacity:.65}
.ev .sup:hover{opacity:1}

.jour-panneau .vide-jour{text-align:center;padding:22px 12px;color:var(--text-3);font-size:12px}
.ev-ligne{display:flex;align-items:center;gap:9px;padding:9px 12px;border-bottom:1px solid var(--line)}
.ev-ligne:last-child{border-bottom:none}
.ev-ligne .pastille{width:8px;height:8px;border-radius:3px;flex:none}
.ev-ligne .h{font-size:12px;color:var(--text-3);width:38px;flex:none}
.ev-ligne .l{flex:1;min-width:0;font-size:13px;color:var(--text);font-weight:500}
/* Cette croix-ci est l'équivalent accessible de la petite croix des pastilles
   du calendrier (13,8 × 16 px) : c'est elle qui doit faire 24 × 24, sinon
   l'exception « un autre contrôle rend le même service » ne tient pas. */
.ev-ligne .x{border:none;background:none;color:var(--text-3);line-height:1;font-size:15px;
  width:24px;height:24px;min-height:24px;display:grid;place-items:center;border-radius:6px;padding:0}
.ev-ligne .x:hover{color:var(--alr)}

.form-ligne{display:flex;gap:8px;margin-bottom:8px}
.form-ligne input,.form-ligne select{flex:1;min-width:0;border:1px solid var(--line-2);border-radius:8px;
  padding:8px 10px;font-size:13px;background:var(--surface);min-height:36px}
.form-ligne input[type=time]{flex:0 0 96px}
/* Un nombre qui se saisit DANS un tableau (capacite des groupes). Il reprend le
   champ des formulaires, en plus court : la colonne ne doit pas s'elargir pour
   deux chiffres. La saisie s'enregistre a la sortie du champ — pas de bouton
   « Enregistrer » a chercher en bas d'un tableau de vingt lignes. */
.cap-n{width:64px;border:1px solid var(--line-2);border-radius:8px;padding:5px 7px;
  font-size:13px;background:var(--surface);min-height:30px;text-align:right}
.cap-n:focus{outline:2px solid var(--brand-2);outline-offset:-1px}
.cap-n.pose{border-color:var(--brand)}
.form-ligne input:focus,.form-ligne select:focus{outline:2px solid var(--brand-2);outline-offset:-1px}

/* Formulaires en sections (fiche d'entretien, placement) : les vrais formulaires
   de l'équipe. Classes partagées (.fiche-*), utilisées par t-fiche et t-placement. */
.fiche-sec{font-size:11px;letter-spacing:.12em;text-transform:uppercase;color:var(--brand-fonce);
  font-weight:700;margin:22px 0 13px;padding-bottom:7px;border-bottom:1px solid var(--line)}
.fiche-sec:first-child{margin-top:2px}
.fiche-grille{display:grid;grid-template-columns:repeat(auto-fit,minmax(220px,1fr));gap:13px 16px}
.fiche-champ{display:flex;flex-direction:column;gap:6px;min-width:0}
.fiche-champ.large{grid-column:1/-1}
.fiche-champ label{font-size:11px;font-weight:600;color:var(--text-2)}
.fiche-champ input,.fiche-champ select,.fiche-champ textarea{
  width:100%;font:inherit;font-size:13px;color:var(--text);background:var(--surface-2);
  border:1px solid var(--line-2);border-radius:var(--r);padding:9px 11px;min-height:40px}
.fiche-champ textarea{min-height:68px;resize:vertical;line-height:1.5}

/* Suggestion des jeunes (roster Edsquare) — la liste qui tombe sous le champ.
   Elle est posée par serveur.js, jamais écrite dans la maquette : c'est une
   donnée serveur, elle n'existe pas hors connexion. La ligne montre le nom en
   premier (c'est ce qu'on cherche) et, en dessous, la classe et l'entreprise —
   deux personnes peuvent porter le même prénom, c'est l'entreprise qui tranche. */
.sugg-jeunes{position:absolute;z-index:40;top:calc(100% + 4px);left:0;right:0;margin:0;padding:4px;
  list-style:none;max-height:264px;overflow-y:auto;background:var(--surface);
  border:1px solid var(--line-2);border-radius:var(--r-lg);box-shadow:var(--sh-2)}
.sugg-jeunes li{display:flex;flex-direction:column;gap:1px;padding:7px 10px;border-radius:var(--r);
  cursor:pointer;line-height:1.35}
.sugg-jeunes li:hover,.sugg-jeunes li.on{background:var(--surface-3)}
.sugg-jeunes li.on{box-shadow:inset 0 0 0 1px var(--vif-ring)}
.sugg-jeunes .n{font-size:13px;font-weight:620;color:var(--text)}
.sugg-jeunes .m{font-size:11.5px;color:var(--text-3)}
.fiche-champ input:focus,.fiche-champ select:focus,.fiche-champ textarea:focus{
  outline:none;border-color:var(--brand-2);background:var(--surface);box-shadow:0 0 0 3px rgba(60,180,120,.16)}
.fiche-auto{border-left:2px solid var(--brand-2)}   /* rempli depuis le compte rendu */

/* Suggestion depuis le registre entreprises : la base commerciale sert la
   saisie du placement au lieu de la faire refaire. La liste flotte sous le
   champ (le formulaire ne bouge pas quand elle s'ouvre), se ferme à Échap, et
   rien n'est repris sans un choix humain. */
.sug-champ{position:relative}
.sug-liste{position:absolute;top:100%;left:0;right:0;z-index:20;margin-top:5px;padding:5px;
  background:var(--surface);border:1px solid var(--line-2);border-radius:var(--r);
  box-shadow:var(--sh-3);max-height:min(46vh,290px);overflow-y:auto;display:none}
.sug-liste.on{display:block}
.sug-row{display:flex;align-items:baseline;gap:10px;width:100%;text-align:left;background:none;
  border:none;border-radius:8px;padding:8px 9px;font:inherit;font-size:13px;color:var(--text)}
.sug-row[aria-selected=true]{background:var(--surface-3)}
.sug-row .n{flex:1 1 auto;min-width:0;font-weight:600;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
/* La commune cède la place au nom : on choisit une entreprise par son nom. */
.sug-row .o{flex:0 1 auto;min-width:0;max-width:46%;font-size:11px;color:var(--text-3);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.sug-vide{padding:13px 10px;text-align:center;font-size:12px;color:var(--text-3)}
.sug-note{font-size:11px;line-height:1.5;color:var(--text-3)}
.sug-note b{color:var(--text-2)}

/* ══════════ La carte des entreprises ══════════
   Antonio, 27/08/2026 : « mets une carte de géolocalisation de toutes les
   entreprises ». Elle est DESSINÉE, pas tuilée : la politique de sécurité de
   l'application sert img-src 'self' et connect-src 'self', et chaque tuile
   d'un fond de plan enverrait l'adresse IP de la personne au tuilier — l'écart
   qu'on a fermé sur les librairies du pilotage. Le fond est un fichier à nous
   (assets/departements.json, contours publics simplifiés) ; le tracé est du
   SVG, produit dans le navigateur.

   Les couleurs sont celles des modules, pas une palette de plus : vert pour ce
   qui est en place, jaune pour ce qui demande un geste, corail pour ce qui est
   cessé. Le campus est un repère, pas une donnée : il est creux. */
/* ⚠️ LE CADRE EST VERT, ET C'EST LA SEULE PLACE OÙ LA MARQUE ENCADRE UNE
   DONNÉE. Antonio, 27/08/2026 : « mets en moderne avec contour vert, mets le
   logo vert fond blanc ». Un trait de 1,5 px et un halo très pâle : la carte
   se pose comme un objet dans la page, sans devenir un cadre décoratif. */
.crt-boite{position:relative;background:var(--surface-2);border:1.5px solid var(--brand);
  border-radius:var(--r-lg);overflow:hidden;isolation:isolate;
  box-shadow:0 0 0 4px var(--t-verte),0 2px 10px rgba(19,32,24,.06)}
/* LA CARTE A UNE HAUTEUR, PAS UN RAPPORT. Un vrai plan se cadre : sur un écran
   large, 620 px de dessin devenaient 760 px de haut et la légende passait sous
   la ligne de flottaison — on cliquait un point sans voir sa fiche. */
.crt-carte{height:min(70vh,620px);width:100%;background:var(--surface-3);z-index:0}
@media(max-width:900px){.crt-carte{height:min(62vh,460px)}}
.crt-fondmuet{margin:12px 14px 0}
/* ÉPURÉ : le MÊME plan, moins fort. On ne retire aucune rue — on cesse de les
   crier. Un fond qui domine, ce sont des points qu'on ne voit plus. */
.crt-carte.fond-epure .leaflet-tile-pane{filter:saturate(.42) contrast(.9) brightness(1.06)}
/* Le choix du fond : trois pastilles, en bas à gauche, là où les cartes du
   monde entier les mettent. */
.crt-fonds{position:absolute;left:12px;bottom:12px;z-index:805;display:flex;
  background:var(--surface);border:1px solid var(--line-2);border-radius:9px;padding:3px;
  box-shadow:var(--sh-1)}
.crt-fonds button{border:none;background:none;font-size:11.5px;font-weight:550;
  color:var(--text-2);padding:5px 11px;border-radius:6px;cursor:pointer;font-family:inherit}
.crt-fonds button.on{background:var(--t-verte);color:var(--brand-fonce,#2C7B54);font-weight:650}
.crt-fonds button:hover{color:var(--text)}
/* L'âge des données : discret tant qu'il est jeune, marqué dès qu'il vieillit. */
.crt-age{color:var(--text-3)}
.crt-age.vieux{color:var(--att);font-weight:600}
.crt-relire{border:none;background:none;color:var(--brand-fonce,#2C7B54);font-size:11.5px;
  font-weight:600;text-decoration:underline;padding:0;cursor:pointer;font-family:inherit}
.crt-relire:hover{color:var(--brand)}
/* Le PAQUET : plusieurs entreprises au même endroit. Il porte leur nombre, et
   sa couleur est celle de la famille dominante — neutre s'il y a des deux,
   plutôt que de trancher à leur place. */
/* LE SECTEUR : un contour vert, et un aplat qui ne cache rien. Un disque
   opaque effacerait le plan qu'on vient d'aller chercher. */
.crt-secteur{stroke:var(--brand);fill:var(--brand);stroke-dasharray:5 4}
.crt-secteur.dir{stroke:var(--brand-fonce,#2C7B54);stroke-dasharray:none;stroke-width:2}

.crt-paquet{display:grid;place-items:center;border-radius:50%;font-size:12px;font-weight:700;
  color:var(--text);background:var(--surface);border:2px solid var(--line-2);
  box-shadow:0 1px 5px rgba(19,32,24,.25);cursor:pointer}
.crt-paquet.acc{border-color:var(--brand);color:var(--brand-fonce,#2C7B54)}
.crt-paquet.con{border-color:var(--att);background:var(--att-bg);color:var(--yellow-ink)}
.crt-paquet.mix{border-style:dashed}
.crt-paquet:hover{border-width:3px}
/* Leaflet apporte sa feuille : on ne la surcharge que là où elle parlerait une
   autre langue que la nôtre (police, coins, ombres). */
.crt-carte.leaflet-container{font:inherit}
.crt-carte .leaflet-control-attribution{font-size:10px;background:rgba(255,255,255,.82);
  color:var(--text-3);padding:1px 6px}
.crt-carte .leaflet-control-attribution a{color:var(--text-2)}
.crt-carte .leaflet-popup-content-wrapper,.crt-carte .leaflet-tooltip{font:inherit}
/* LA COULEUR DIT LA RELATION, LA FORME DIT LA PRÉCISION DU POINT.
   Antonio, 27/08/2026 : « une carte avec les entreprises qui sont avec SKHUB
   et les contacts à contacter ». C'est la question qu'on pose à la carte : la
   couleur y répond. Ce qui était porté par la couleur avant — le point est
   celui du siège et non de l'établissement — passe à la FORME (un anneau) :
   il reste distinct, comme le veut la règle du 27/08, sans prendre la place
   de la seule chose qu'on vient chercher ici. */
/* ⚠️ `fill-opacity` EST POSÉ ICI, PAS PAR LEAFLET. Leaflet écrit ses couleurs
   en ATTRIBUTS de présentation (fill, stroke, fill-opacity .2) : une règle CSS
   les bat toutes, mais il faut les nommer — sans `fill-opacity:1`, les points
   sortaient délavés à 20 %. */
.crt-pt{color:var(--line-2);fill:currentColor;fill-opacity:1;stroke:var(--surface);
  stroke-width:1.1;cursor:pointer}
.crt-pt.acc{color:var(--brand)}                        /* un apprenti y travaille */
.crt-pt.con{color:var(--yellow);stroke:var(--att)}     /* à contacter */
.crt-pt.aut{color:var(--line-2)}                       /* ni l'un ni l'autre */
/* Les contrats n'ont pas répondu : on ne SAIT pas. Un point creux en pointillé
   ne se confond ni avec un partenaire ni avec un prospect. */
.crt-pt.ind{color:var(--text-3);fill:var(--surface);stroke:currentColor;stroke-dasharray:2.2 2.2}
.crt-pt.sg{fill:var(--surface);stroke:currentColor;stroke-width:2.2}
.crt-pt.con.sg{stroke:var(--att)}
/* Cessée au registre de l'État : un FAIT, qui prime sur toute nuance de
   contour — d'où les deux seuls `!important` de cette carte, ici et sur le
   point choisi. Le remplissage, lui, reste celui de la famille : une
   entreprise d'accueil dont l'établissement a fermé doit rester lisible comme
   une entreprise d'accueil, c'est précisément ce qui doit alerter. */
.crt-pt.ces{stroke:var(--orange)!important;stroke-width:2.2;stroke-dasharray:none}
.crt-pt.on{stroke:var(--text)!important;stroke-width:2.4;stroke-dasharray:none}
/* Le NOM de l'entreprise, sur la carte. Il n'apparaît que quand il reste
   lisible — filtre posé, ou zoom entré : quatre-vingts noms superposés ne
   nomment plus rien, ils grisent la Normandie. */
.crt-nom{font-size:11px;font-weight:620;fill:var(--text-2);paint-order:stroke;
  stroke:var(--surface);stroke-width:2.4px;stroke-linejoin:round;pointer-events:none}
/* LES CENTRES SKHUB PORTENT LA MARQUE, PAS UN ROND DE PLUS.
   Antonio, 27/08/2026 : « en rajoutant dans la map le logo SKHUB des centres
   SKHUB existants ». Un anneau creux se confondait avec un point de siège ; la
   marque ne se confond avec rien, et elle dit ce que ces repères sont — nos
   maisons, pas des données. Le disque blanc dessous garde le « b » lisible
   par dessus un département teinté. */
/* NOS CENTRES PORTENT LA MARQUE, PAS UN ROND DE PLUS (Antonio, 27/08/2026 :
   « en rajoutant dans la map le logo SKHUB des centres SKHUB existants »). Un
   anneau creux se confondait avec un point de siège ; la marque ne se confond
   avec rien, et elle dit ce que ces repères sont — nos maisons, pas des
   données. Le disque blanc dessous la garde lisible sur n'importe quel fond. */
/* LE REPÈRE D'UN CENTRE : la marque verte sur un rond BLANC, cerclé de vert.
   Pas un aplat vert avec un logo blanc — la marque est verte, elle se lit sur
   du blanc, et c'est ainsi qu'on la reconnaît partout ailleurs. */
.crt-lieu{background:#fff;border:2px solid var(--brand);border-radius:50%;
  box-shadow:0 2px 6px rgba(19,32,24,.20);display:grid;place-items:center;cursor:pointer;
  transition:box-shadow .15s,border-color .15s}
.crt-lieu:hover{border-color:var(--brand-fonce,#2C7B54);box-shadow:0 0 0 4px var(--t-verte),0 2px 8px rgba(19,32,24,.24)}
.crt-lieu img{width:12px;height:16px;pointer-events:none}
/* Une DIRECTION RÉGIONALE coiffe des centres : son repère est plus large et
   son trait plus appuyé. Même marque, deux rangs. */
.crt-lieu.dir{border-width:3px;border-color:var(--brand-fonce,#2C7B54);
  box-shadow:0 0 0 3px var(--t-verte),0 2px 8px rgba(19,32,24,.22)}
.crt-lieu.dir img{width:16px;height:21px}
/* Le nom d'un point : une étiquette de Leaflet, ramenée à nos jetons. */
.crt-nom-t.leaflet-tooltip{background:rgba(255,255,255,.86);border:none;box-shadow:none;
  padding:0 3px;font-size:11px;font-weight:620;color:var(--text-2);white-space:nowrap}
.crt-nom-t.leaflet-tooltip::before{display:none}
.crt-nom-t.dir{font-size:12.5px;color:var(--brand-fonce,#2C7B54)}
.crt-info.leaflet-tooltip{background:var(--rail);color:#fff;border:none;font-size:11.5px;
  padding:5px 8px;border-radius:7px;box-shadow:var(--sh-2);white-space:pre-line}
.crt-info.leaflet-tooltip::before{border-top-color:var(--rail)}
/* ⚠️ Au dessus des couches de Leaflet, qui montent a 400-700 : sans cela
   les commandes de zoom passaient SOUS le plan et ne se cliquaient plus. */
.crt-outils{position:absolute;top:10px;right:10px;display:flex;flex-direction:column;gap:5px;z-index:800}
.crt-outils button{width:32px;height:32px;display:grid;place-items:center;background:#fff;
  border:1px solid var(--line-2);border-radius:9px;font-size:15px;font-weight:700;
  color:var(--brand-fonce,#2C7B54);box-shadow:var(--sh-1);
  transition:border-color .15s,background .15s}
.crt-outils button:hover{border-color:var(--brand);background:var(--t-verte)}
/* Le bouton des secteurs reste ENFONCÉ quand ils sont affichés : un bouton qui
   bascule doit dire dans quel état il est, sans qu'on regarde la carte. */
.crt-outils button.on{background:var(--t-verte);border-color:var(--brand)}
.crt-leg{display:flex;flex-wrap:wrap;gap:6px 16px;padding:10px 14px;border-top:1px solid var(--line);
  background:var(--surface);font-size:11.5px;color:var(--text-3)}
.crt-leg i{display:inline-block;width:9px;height:9px;border-radius:50%;margin-right:5px;
  vertical-align:baseline}
.crt-leg i.creux{background:var(--surface)!important;border:2px solid var(--text-3);
  width:11px;height:11px;box-sizing:border-box}
/* La barre des familles : elle COMPTE et elle FILTRE. Deux gestes au même
   endroit, parce que c'est la même question — « montre-moi celles-là ». */
.crt-fam{display:flex;gap:8px;flex-wrap:wrap;padding:11px 14px;border-bottom:1px solid var(--line)}
.crt-fam button{display:inline-flex;align-items:center;gap:7px;border:1px solid var(--line-2);
  background:var(--surface);border-radius:99px;padding:5px 12px 5px 10px;font-size:12px;
  font-weight:550;color:var(--text-2);cursor:pointer;transition:border-color .15s,color .15s}
.crt-fam button:hover{border-color:var(--brand-2);color:var(--text)}
.crt-fam button.on{border-color:var(--brand);color:var(--text);font-weight:650;
  box-shadow:inset 0 0 0 1px var(--brand)}
.crt-fam button[disabled]{opacity:.45;cursor:default}
.crt-fam button i{width:9px;height:9px;border-radius:50%;background:var(--line-2);flex:none}
.crt-fam button i.acc{background:var(--brand)}
.crt-fam button i.con{background:var(--yellow);box-shadow:0 0 0 1px var(--att)}
.crt-fam button i.aut{background:var(--line-2)}
.crt-fam button i.tout{background:linear-gradient(90deg,var(--brand) 50%,var(--yellow) 50%)}
.crt-fam button b{font-weight:700;color:var(--text);font-variant-numeric:tabular-nums}
/* ── LA FICHE D'UNE ENTREPRISE : UN PANNEAU, PAS UNE BULLE ──────────────
   Antonio, 27/08/2026 : « lorsqu'on clique on aura les détails de
   l'entreprise, l'adresse, le dirigeant, les contacts et tout ». Une bulle de
   trois lignes ne porte pas ça. Le panneau se pose à DROITE de la carte, sur
   toute sa hauteur : il ne recouvre pas ce qu'on vient de cliquer (les points
   sont à gauche neuf fois sur dix), et il défile s'il déborde. Sur écran
   étroit il passe en bas, sur toute la largeur — la carte reste visible
   au-dessus. */
.crt-fiche{position:absolute;right:12px;top:12px;bottom:12px;width:min(330px,calc(100% - 24px));
  padding:13px 15px;background:var(--surface);border:1px solid var(--line-2);
  border-radius:var(--r);box-shadow:var(--sh-3);font-size:12px;line-height:1.5;display:none;
  z-index:820;overflow:auto;overscroll-behavior:contain}
.crt-fiche.on{display:block}
.crt-fiche .t{font-size:14px;font-weight:680;color:var(--text);margin:0 22px 8px 0;line-height:1.35}
.crt-fiche .m{color:var(--text-3)}
.crt-fiche .x{position:absolute;top:7px;right:8px;border:none;background:var(--surface);font-size:15px;
  line-height:1;color:var(--text-3);padding:3px 6px;border-radius:6px}
.crt-fiche .x:hover{background:var(--surface-3);color:var(--text)}
@media(max-width:900px){.crt-fiche{right:10px;left:10px;top:auto;bottom:10px;width:auto;max-height:52%}}

/* Le bandeau de relation : la seule chose qu'on vient chercher, en tête. */
.crt-rel{padding:7px 10px;border-radius:8px;margin-bottom:10px;font-size:12px;color:var(--text)}
.crt-rel b{font-weight:680}
.crt-rel .nb{display:block;margin-top:3px;font-size:11px;color:var(--text-3)}
.crt-rel.acc{background:var(--t-verte);box-shadow:inset 0 0 0 1px var(--brand-2)}
.crt-rel.con{background:var(--att-bg);color:var(--yellow-ink)}
.crt-rel.aut{background:var(--surface-3)}
.crt-rel.ind{background:var(--surface-3);color:var(--text-2)}

/* Le détail : une étiquette, une valeur. Une ligne sans valeur ne s'écrit pas
   du tout — une étiquette suivie du vide se lit comme une donnée perdue. */
.crt-det{margin:0}
.crt-det>div{display:grid;grid-template-columns:82px 1fr;gap:10px;padding:5px 0;
  border-top:1px solid var(--line)}
.crt-det>div:first-child{border-top:none}
.crt-det dt{font-size:11px;color:var(--text-3);line-height:1.5}
.crt-det dd{margin:0;color:var(--text-2);font-size:12px;word-break:break-word}
.crt-det dd b{color:var(--text);font-weight:620}
.crt-det .gris{color:var(--text-3)}
.crt-det .att{color:var(--att)}
.crt-det .alr{color:var(--alr)}

/* Les contacts en boutons : on est ici pour appeler. */
/* La jauge d'un objectif : elle ne remplace pas le chiffre, elle le double.
   Un pourcentage seul ne dit ni le réalisé ni la cible. */
.crt-jauge{height:6px;border-radius:99px;background:var(--surface-3);overflow:hidden;margin:4px 0 5px}
.crt-jauge i{display:block;height:100%;background:var(--brand);border-radius:99px}
.crt-act{display:flex;flex-wrap:wrap;gap:6px;margin-top:11px}
.crt-act.vide{font-size:11.5px;color:var(--text-3)}
.crt-b{display:inline-flex;align-items:center;gap:5px;border:1px solid var(--line-2);
  border-radius:8px;padding:5px 10px;font-size:11.5px;font-weight:600;color:var(--text-2);
  text-decoration:none;background:var(--surface);max-width:100%;overflow:hidden;
  text-overflow:ellipsis;white-space:nowrap}
.crt-b:hover{border-color:var(--brand);color:var(--brand)}

/* La boîte du clic stratégique : deux colonnes quand la place le permet, une
   seule sur téléphone. Elle réutilise `cf-champ` et `cf-saisie` : un champ de
   plus dans l'application, ce sont deux façons de dessiner un champ. */
.lieu-form{max-height:min(56vh,460px);overflow:auto;margin-top:4px;padding-right:4px}
.lieu-2{display:grid;grid-template-columns:1fr 1fr;gap:10px}
@media(max-width:560px){.lieu-2{grid-template-columns:1fr}}
.lieu-aide{margin:6px 0 0;font-size:11.5px;color:var(--text-3);line-height:1.5}
.cf-back.on{display:flex!important}
/* Le mode « je pose un point » : le curseur le dit, et la carte aussi. */
.crt-boite.pose .crt-carte,.crt-boite.pose .leaflet-grab{cursor:crosshair}
.crt-pose{position:absolute;left:12px;top:12px;z-index:810;display:none;align-items:center;gap:8px;
  background:var(--surface);border:1px solid var(--brand);border-radius:9px;padding:7px 11px;
  font-size:12px;font-weight:600;color:var(--text);box-shadow:var(--sh-2)}
.crt-boite.pose .crt-pose{display:flex}
.crt-pose button{border:none;background:none;color:var(--text-3);font-size:12px;
  text-decoration:underline;padding:0}
/* Le nom officiel s'affiche SOUS le nom de travail, jamais à sa place :
   l'écran signale l'écart, il ne le résout pas (règle n°3). */
.crt-off{display:block;margin-top:4px;padding-top:4px;border-top:1px dashed var(--line-2);
  font-size:11.5px;color:var(--text-2)}
.ecart-nom{font-size:11px;color:var(--att);font-weight:600}
/* L'ECART d'un KPI du Pilotage : la comparaison a la periode precedente, dans
   le conditionnement de son tableau de bord. La couleur dit le SENS, pas la
   direction : plus de contrats est bon, plus de ruptures ne l'est pas. */
/* SA CARTE, DANS NOS COULEURS. La structure est la sienne (`buildStatCard`) :
   libellé, valeur, comparaison a deux colonnes, tendance, sous-texte. La
   `colorClass` de gauche est son code visuel : '' neutre, success, warning,
   danger, secondary. */
.kpi-groupe{font-family:inherit;font-weight:700;font-size:14px;color:var(--text);
  margin:0 2px 10px;display:flex;align-items:center;gap:8px}
.kpi-carte{background:var(--surface);border:1px solid var(--line);border-radius:var(--r-lg);
  padding:16px 18px;border-left:3px solid var(--line-2);display:flex;flex-direction:column;gap:8px}
.kpi-carte.success{border-left-color:var(--ok)}
.kpi-carte.warning{border-left-color:var(--att)}
.kpi-carte.danger{border-left-color:var(--alr)}
.kpi-carte.secondary{border-left-color:var(--inf)}
.kpi-carte .lbl{font-size:12px;font-weight:600;color:var(--text-2)}
.kpi-carte .val{font-size:34px;font-weight:700;line-height:1;letter-spacing:-.02em;
  font-variant-numeric:tabular-nums}
.kpi-comp{display:flex;gap:18px;border-top:1px solid var(--line);padding-top:8px}
.kpi-comp .ci{display:flex;flex-direction:column;gap:1px}
.kpi-comp .cl{font-size:11.5px;color:var(--text-3);text-transform:uppercase;letter-spacing:.06em}
.kpi-comp .cv{font-size:15px;font-weight:600;font-variant-numeric:tabular-nums}
.kpi-trend{font-size:11.5px;font-weight:600;color:var(--text-3)}
.kpi-trend.up{color:var(--ok)}
.kpi-trend.down{color:var(--alr)}
.kpi-sous{font-size:11.5px;color:var(--text-3);line-height:1.45}
.kpi-vide{color:var(--text-3);font-size:13px;padding:14px 2px}

/* ═══ SON TABLEAU DE BORD, DANS NOS COULEURS ══════════════════════════════
   Sa disposition ne bouge pas d'un bloc : ce qui suit ne touche QUE la
   peinture. Sa feuille (`cfamc/assets/pilotage-porte.css`) est injectee a
   l'ouverture de l'ecran, donc APRES celle-ci dans le document — a
   specificite egale elle gagnerait. D'ou le `#v-pilotage` en tete de chaque
   regle : deux identifiants contre un, la notre passe devant sans avoir a
   crier `!important` sur quarante declarations.
   Ce qu'on repeint, et rien d'autre : le fond violet de son gabarit d'origine,
   la police, le vert (le sien est #28825A, le notre #43A074), les ombres
   portees a 30 px, et les rayons. Les libelles, l'ordre, les emojis de ses
   titres de groupe restent les siens — ce sont ses reperes, pas notre style. */
#v-pilotage #pil-cfamc{background:none;min-height:0;padding:0;font-family:var(--font);color:var(--text)}
#v-pilotage #pil-cfamc .container{max-width:none;margin:0}
/* Sa banniere « KPI Dashboard SKHUB · Suivi des contrats… » (le `.header` de
   son gabarit, avec l'emoji) fait DOUBLON avec le titre de l'ecran UNITOOLS
   juste au-dessus (« Pilotage SKHUB — Le tableau de bord de la direction… ») :
   c'est ce bloc a lui, pose sur le notre, qui donnait l'impression d'une appli
   greffee. On le masque — un seul titre, celui d'UNITOOLS. (Antonio, 29/08)
   ⚠️ Cette regle ne vaut QUE pour le tableau de bord natif (#pil-cfamc). Tant
   que la production sert son tableau dans un CADRE, aucune regle d'ici ne
   franchit la frontiere de l'iframe : c'est la feuille du mode embarque
   (app/cfamc/inc/bootstrap.php) qui masque la meme banniere la-bas. */
#v-pilotage #pil-cfamc .header{display:none}
#v-pilotage #pil-cfamc .dashboard{display:none}
#v-pilotage #pil-cfamc .dashboard.active{display:block}

/* La barre de ses onglets : la meme grammaire que `.tabx-bar` ailleurs. */
#v-pilotage #pil-cfamc .tabs-nav{background:var(--surface);border:1px solid var(--line);
  border-bottom:1px solid var(--line);border-radius:var(--r-lg) var(--r-lg) 0 0;box-shadow:none;top:0}
#v-pilotage #pil-cfamc .tab-btn{font-family:var(--font);color:var(--text-2);border-bottom:2px solid transparent;
  padding:13px 16px;transition:color .15s var(--nav-courbe),border-color .15s var(--nav-courbe)}
#v-pilotage #pil-cfamc .tab-btn:hover{color:var(--text);background:var(--surface-2)}
#v-pilotage #pil-cfamc .tab-btn.active{color:var(--brand-fonce);border-bottom-color:var(--vif)}

/* ⚠️ `.content` EXISTE DES DEUX COTES, et c'est le SEUL nom qui fuit
   reellement (mesure du 29/08 : sur 36 noms de classe communs aux deux
   feuilles, les 35 autres demandent un selecteur compose que son balisage ne
   presente pas). Le notre pose `max-width:1360px` — la mesure de lecture des
   ecrans d'UNITOOLS — et lui n'en pose aucune : sa page de contenu se
   retrouvait donc bornee a 1360 px au milieu d'une barre d'onglets pleine
   largeur. Vu a l'ecran, pas devine. */
#v-pilotage #pil-cfamc .content{background:var(--surface);border:1px solid var(--line);border-top:0;
  border-radius:0 0 var(--r-lg) var(--r-lg);padding:22px;max-width:none;width:auto}

/* Ses cartes d'indicateur. Le filet de gauche reste : c'est SON code couleur
   (neutre, success, warning, danger, secondary), et il porte du sens. */
#v-pilotage #pil-cfamc .stat-card{background:var(--surface);border:1px solid var(--line);
  border-left:3px solid var(--brand);border-radius:var(--r-lg);box-shadow:none;padding:16px 18px}
#v-pilotage #pil-cfamc .stat-card:hover{transform:none}
#v-pilotage #pil-cfamc .stat-card.success{border-left-color:var(--ok)}
#v-pilotage #pil-cfamc .stat-card.warning{border-left-color:var(--att)}
#v-pilotage #pil-cfamc .stat-card.danger{border-left-color:var(--alr)}
#v-pilotage #pil-cfamc .stat-card.secondary{border-left-color:var(--inf)}
#v-pilotage #pil-cfamc .stat-label{color:var(--text-2);font-size:12px;font-weight:600}
#v-pilotage #pil-cfamc .stat-value{color:var(--text);font-variant-numeric:tabular-nums;letter-spacing:-.02em}
#v-pilotage #pil-cfamc .stat-subtext{color:var(--text-3)}
#v-pilotage #pil-cfamc .comparison{border-top:1px solid var(--line);padding-top:12px}
/* Ses deux cases de comparaison etaient sur #f8f9ff, un bleu tres pale du
   gabarit d'origine. C'est la seule teinte froide de l'ecran : elle passe sur
   notre fond de surface. La disposition (deux colonnes) ne bouge pas. */
#v-pilotage #pil-cfamc .comp-item{background:var(--surface-2);border:1px solid var(--line);
  border-radius:var(--r)}
#v-pilotage #pil-cfamc .comp-label{color:var(--text-3)}
#v-pilotage #pil-cfamc .comp-value{color:var(--text);font-variant-numeric:tabular-nums}
#v-pilotage #pil-cfamc .trend{color:var(--text-3);font-weight:600}
#v-pilotage #pil-cfamc .trend.up{color:var(--ok)}
#v-pilotage #pil-cfamc .trend.down{color:var(--alr)}
#v-pilotage #pil-cfamc .table-scroll{border:1px solid var(--line);border-radius:var(--r)}

#v-pilotage #pil-cfamc .kpi-group-title{color:var(--brand-fonce);font-family:var(--font)}
#v-pilotage #pil-cfamc .section-title{color:var(--text);font-family:var(--font)}
#v-pilotage #pil-cfamc .section-subtitle,
#v-pilotage #pil-cfamc .sourcing-status{color:var(--text-3)}

#v-pilotage #pil-cfamc .chart-container,
#v-pilotage #pil-cfamc .summary-table-wrap{background:var(--surface);border:1px solid var(--line);
  border-radius:var(--r-lg);box-shadow:none}
#v-pilotage #pil-cfamc .chart-title{color:var(--text);font-family:var(--font)}

/* Ses tableaux. Le site zebre les siens et le theme y ajoute des filets : ici
   on garde une seule ligne de separation, comme sur `.tbl` partout ailleurs. */
#v-pilotage #pil-cfamc .summary-table th{background:var(--surface-3);color:var(--text-2);
  border-bottom:1px solid var(--line-2)}
#v-pilotage #pil-cfamc .summary-table td{border-bottom:1px solid var(--line);color:var(--text)}
#v-pilotage #pil-cfamc .summary-table tr:hover td{background:var(--surface-2)}

/* Ses boutons : la pilule d'UNITOOLS, et le vert profond sous texte blanc
   (#43A074 sous du blanc ne monte qu'a 3,25:1). */
#v-pilotage #pil-cfamc .export-btn,
#v-pilotage #pil-cfamc .reset-btn{font-family:var(--font);background:var(--brand-fonce);color:#fff;
  border-radius:999px;padding:8px 15px;font-size:12.5px;font-weight:600;border:0}
#v-pilotage #pil-cfamc .export-btn:hover,
#v-pilotage #pil-cfamc .reset-btn:hover{background:var(--rail-2)}
#v-pilotage #pil-cfamc .kpi-btn{font-family:var(--font);border:1px solid var(--line);background:var(--surface);
  color:var(--text-2);border-radius:999px}
#v-pilotage #pil-cfamc .kpi-btn.active{background:var(--brand-fonce);color:#fff;border-color:var(--brand-fonce)}
#v-pilotage #pil-cfamc .filters select,
#v-pilotage #pil-cfamc .filter-group select{font-family:var(--font);border:1px solid var(--line);
  border-radius:9px;padding:7px 10px;background:var(--surface);color:var(--text)}
#v-pilotage #pil-cfamc .filter-group label{color:var(--text-2);font-size:12px;font-weight:600}

#v-pilotage #pil-cfamc .info-banner,
#v-pilotage #pil-cfamc .success-message{background:var(--surface-2);border:1px solid var(--line);
  border-radius:var(--r);color:var(--text-2)}
#v-pilotage #pil-cfamc .error{background:#FDECE8;border:1px solid #F3C4B8;border-radius:var(--r);color:#8A2410}
/* ⚠️ SA ZONE DE DEPOT NE S'AFFICHE PAS ICI, et c'est la meme decision que
   dans le cadre (le pont la masquait deja) : l'onglet « Mise a jour des
   donnees » en porte une, et deux zones de depot dans la meme barre d'onglets,
   c'est la certitude qu'un jour quelqu'un importera deux fois. Le balisage
   reste en place — son code y ecrit au demarrage, et le retirer le ferait
   tomber. Chez Franck, sur sa propre page, elle garde sa place. */
#v-pilotage #pil-cfamc #uploadSection,
#v-pilotage #pil-cfamc #bascule-import{display:none!important}
#v-pilotage #pil-cfamc .upload-section{background:var(--surface);border:1px solid var(--line);
  border-radius:var(--r-lg);box-shadow:none;padding:20px}
#v-pilotage #pil-cfamc .upload-box{border:2px dashed var(--line-2);border-radius:var(--r);background:var(--surface-2)}

.vue-bascule{display:flex;background:var(--surface-3);border:1px solid var(--line);border-radius:9px;padding:3px}
.vue-bascule button{border:none;background:none;font-size:12px;font-weight:550;color:var(--text-2);
  padding:5px 11px;border-radius:6px;min-height:28px}
.vue-bascule button.on{background:var(--surface);color:var(--brand);font-weight:650;box-shadow:var(--sh-1)}

.sem-grille{display:grid;grid-template-columns:52px repeat(7,1fr);border-top:1px solid var(--line)}
.sem-h{background:var(--surface-2);font-size:11px;color:var(--text-3);text-align:right;padding:4px 7px 0;
  border-right:1px solid var(--line);border-bottom:1px solid var(--line)}
.sem-c{min-height:38px;border-right:1px solid var(--line);border-bottom:1px solid var(--line);
  padding:3px;position:relative}
.sem-c:nth-child(8n+1){background:var(--surface-2)}
.sem-c.wknd{background:var(--surface-2)}
.sem-c.survol{background:var(--t-jaune)}


/* ══════════ Manipulation des publications ══════════ */
.ev{position:relative}
.ev .sup{opacity:.45}                       /* la croix reste visible, pas seulement au survol */
.ev:hover .sup,.ev.actif .sup{opacity:1}
.ev.actif{box-shadow:0 0 0 2px var(--brand);z-index:2}
.ev.coupe{opacity:.45;border:1px dashed currentColor}
.ev.copie{animation:pulse-copie .5s ease}
@keyframes pulse-copie{0%{box-shadow:0 0 0 0 var(--brand-2)}100%{box-shadow:0 0 0 8px transparent}}

.menu-ctx{position:fixed;z-index:45;background:var(--surface);border:1px solid var(--line-2);
  border-radius:10px;box-shadow:var(--sh-3);padding:5px;min-width:196px;
  opacity:0;visibility:hidden;transform:scale(.97);
  transition:opacity .1s ease-in,transform .1s ease-in,visibility 0s .1s}
.menu-ctx.on{opacity:1;visibility:visible;transform:none;
  transition:opacity .15s cubic-bezier(.32,.72,0,1),transform .15s cubic-bezier(.32,.72,0,1),visibility 0s}
.menu-ctx button{display:flex;align-items:center;gap:10px;width:100%;text-align:left;border:none;
  background:none;padding:8px 10px;border-radius:7px;font-size:13px;color:var(--text)}
.menu-ctx button:hover{background:var(--surface-2)}
.menu-ctx button.danger{color:var(--alr)}
.menu-ctx button.danger:hover{background:var(--alr-bg)}
.menu-ctx button kbd{margin-left:auto;font-size:11px}
.menu-ctx button:disabled{opacity:.4}
.menu-ctx .sep{height:1px;background:var(--line);margin:4px 0}

.presse{display:flex;align-items:center;gap:9px;padding:9px 12px;background:var(--t-jaune);
  border:1px solid var(--yellow);border-radius:9px;font-size:12px;color:var(--yellow-ink);
  margin-bottom:12px}
.presse b{font-weight:650}
.presse button{margin-left:auto;border:none;background:none;color:var(--yellow-ink);font-size:15px;
  line-height:1;min-width:24px;min-height:24px;display:inline-flex;align-items:center;justify-content:center}


/* ══════════ Objectifs ══════════ */
.obj{display:flex;align-items:center;gap:14px;padding:14px 16px;border-bottom:1px solid var(--line)}
.obj:last-child{border-bottom:none}
.obj .b{flex:1;min-width:0}
.obj .t{font-size:13px;font-weight:600;color:var(--text)}
.obj .s{font-size:12px;color:var(--text-3);margin-top:2px}
.obj .jauge{flex:none;width:170px}
.obj .ch{flex:none;width:88px;text-align:right;font-size:19px;font-weight:680;letter-spacing:-.02em}
.obj .ch small{display:block;font-size:11px;font-weight:500;color:var(--text-3);letter-spacing:0}
.obj .ec{flex:none;width:104px;text-align:right}
.obj .obj-act{flex:none;display:flex;gap:6px;align-items:center}
.obj .obj-act button{border:1px solid var(--line-2);background:var(--surface);border-radius:7px;
  padding:5px 10px;font-size:11px;font-weight:600;color:var(--text-2);cursor:pointer;
  transition:border-color .15s,color .15s}
.obj .obj-act button:hover{border-color:var(--brand-2);color:var(--text)}
.obj .obj-act button.sup:hover{border-color:var(--alr);color:var(--alr)}
@media(max-width:1080px){.obj{flex-wrap:wrap;row-gap:8px}.obj .jauge{flex:1 1 100%;order:5;width:auto}
  .obj .ch{margin-left:auto}.obj .obj-act{order:6}}

/* ══════════ Demandes entre services ══════════ */
.dem{display:flex;gap:13px;padding:14px 16px;border-bottom:1px solid var(--line);align-items:flex-start}
.dem:last-child{border-bottom:none}
.dem:hover{background:var(--surface-2)}
.dem .sens{flex:none;width:19px;padding-top:2px}
.dem .b{flex:1;min-width:0}
.dem .t{font-size:13px;font-weight:600;color:var(--text);line-height:1.4}
.dem .d{font-size:12px;color:var(--text-2);line-height:1.5;margin-top:3px}
.dem .m{font-size:11px;color:var(--text-3);margin-top:6px;display:flex;gap:10px;flex-wrap:wrap;align-items:center}
.dem .act{flex:none;display:flex;flex-direction:column;gap:6px;align-items:flex-end}
.fleche-svc{display:inline-flex;align-items:center;gap:5px;font-size:11px;font-weight:600}
.fleche-svc .p{width:6px;height:6px;border-radius:2px}

/* Pièces jointes d'une demande : discrètes tant qu'il n'y en a pas, lisibles
   dès qu'il y en a. Le nom de la pièce est celui que la personne a déposé —
   il peut être long : on le coupe plutôt que d'étirer la carte. */
.pj{display:flex;gap:7px;flex-wrap:wrap;align-items:center;margin-top:8px}
.pj-i,.pj-add{display:inline-flex;align-items:center;gap:5px;font-size:11px;font-weight:550;
  border:1px solid var(--line-2);border-radius:7px;padding:3px 8px;background:var(--surface);
  color:var(--text-2);max-width:230px;text-decoration:none;transition:border-color .2s,color .2s}
.pj-i span{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.pj-i:hover,.pj-add:hover{border-color:var(--brand);color:var(--brand)}
.pj-add{cursor:pointer;font-family:inherit;border-style:dashed}
.pj-i:focus-visible,.pj-add:focus-visible{outline:2px solid var(--brand);outline-offset:2px}

.suivi{display:flex;gap:0;margin-top:9px}
.suivi span{flex:1;height:3px;background:var(--line);border-radius:99px;margin-right:3px}
.suivi span:last-child{margin-right:0}
.suivi span.fait{background:var(--brand-2)}
.suivi span.refus{background:var(--alr)}


/* ══════════ IL N'Y A PLUS DE SOUS-NAVIGATION DANS LE RAIL ══════════
   Antonio, 27/08/2026 : « les sous thèmes en horizontale en haut, je ne veux
   pas de doublon. »
   Le rail recopiait sous l'application ouverte les onglets de son écran
   (.sous-nav / .sous-item), alors que ces mêmes onglets sont déjà en haut de
   la page, en horizontal (.tabx-bar). La même liste, deux fois, à trente
   centimètres l'une de l'autre, avec deux dessins différents pour dire le
   même état : on ne savait plus laquelle faisait foi, et l'entrée ouverte
   poussait les autres familles hors du champ.
   Les onglets vivent donc en UN seul endroit, la barre horizontale de leur
   écran — c'est la partition du modèle relevé sur Mobbin (Salesforce
   Lightning), poussée jusqu'au bout le 28/08 : la colonne porte les univers,
   la rangée du haut leurs applications, l'écran ses onglets.
   Ce qui reste : `ongletsDe()` sert toujours la palette ⌘K et les liens
   profonds (#module/onglet). C'est le RENDU dans le rail qui a disparu, pas
   la connaissance des onglets. */
.crumb{cursor:default}
/* min-height:24px : c'est la taille de cible minimale du critère 2.5.8.
   Le fil d'Ariane mesurait 17 px de haut. */
.crumb button:not(.retour){border:none;background:none;color:var(--text-2);font-size:11px;
  padding:0;min-height:24px;display:inline-flex;align-items:center;
  text-decoration:underline;text-underline-offset:2px;text-decoration-color:var(--line-2)}
.crumb button:not(.retour):hover{color:var(--brand)}
/* (plus de .sous-nav à masquer : le rail ne recopie plus les onglets) */


/* ══════════ Fiches formation ══════════ */
.fil-liste{display:flex;flex-direction:column}
.fil{display:flex;align-items:center;gap:12px;padding:12px 16px;border-bottom:1px solid var(--line);
  width:100%;text-align:left;background:none;border-left:none;border-right:none;border-top:none;
  transition:background .14s}
.fil:last-child{border-bottom:none}
.fil:hover{background:var(--surface-2)}
.fil.on{background:var(--t-verte)}
.fil .sig{flex:none;width:52px;font-size:12px;font-weight:700;color:var(--t-verte-i);
  letter-spacing:.02em}
.fil .b{flex:1;min-width:0}
.fil .t{font-size:13px;font-weight:600;color:var(--text);line-height:1.35}
.fil .s{font-size:11px;color:var(--text-3);margin-top:1px}
.fil .n{flex:none}

.bloc-comp{border:1px solid var(--line);border-radius:var(--r-lg);padding:13px 15px;background:var(--surface-2)}
.bloc-comp .num{display:inline-grid;place-items:center;width:22px;height:22px;border-radius:50%;
  background:var(--brand-fonce);color:#fff;font-size:11px;font-weight:700;margin-bottom:8px}
.bloc-comp h3{font-size:12px;font-weight:650;color:var(--text);line-height:1.4;margin-bottom:7px}
.bloc-comp ul{list-style:none;display:flex;flex-direction:column;gap:5px}
.bloc-comp li{font-size:12px;color:var(--text-2);line-height:1.5;padding-left:13px;position:relative}
.bloc-comp li::before{content:'';position:absolute;left:0;top:7px;width:4px;height:4px;border-radius:50%;
  background:var(--line-2)}


/* ══════════ Navigation : historique et retour ══════════ */
.retour{display:flex;align-items:center;gap:5px;border:none;background:none;color:var(--text-2);
  font-size:11px;padding:2px 6px 2px 2px;border-radius:6px;margin-left:-4px;transition:color .15s,background .15s}
.retour:hover{color:var(--brand);background:var(--surface-2)}
.retour:disabled{opacity:0;pointer-events:none}
.crumb{display:flex;align-items:center;gap:2px}
/* Un séparateur entre le retour et le fil d'Ariane : sans lui les deux libellés
   se lisent comme une seule phrase. */
.retour:not(:disabled)+#crumb::before{content:'';display:inline-block;width:1px;height:11px;
  background:var(--line-2);margin:0 8px -1px 4px}
.retour .t{max-width:190px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}

.cmd-row .ou{font-size:11px;color:var(--text-3);flex:none;max-width:150px;overflow:hidden;
  text-overflow:ellipsis;white-space:nowrap}
.cmd-row .marq{background:var(--t-jaune);color:var(--t-jaune-i);border-radius:3px;padding:0 2px}


/* En production, une personne n'a qu'un espace : le déroulant n'existe que pour
   l'administration. Les autres voient le nom de leur espace, sans commande. */
.espace-fixe{cursor:default}
.quitter{display:flex;align-items:center;gap:6px;border:1px dashed var(--line-2);background:none;
  color:var(--text-3);font-size:11px;padding:5px 10px;border-radius:99px;min-height:30px;
  transition:color .15s,border-color .15s}
.quitter:hover{color:var(--brand);border-color:var(--brand-2)}


/* Un compte se ferme d'ici, pas dans phpMyAdmin un vendredi soir. */
.act-cpt{text-align:right;white-space:nowrap}
.act-cpt .btn{margin-left:6px}
tr.inactif td{opacity:.55}
tr.inactif .badge{filter:grayscale(1)}

/* Un écran qui n'est pas encore raccordé le dit, en haut, avant tout le reste.
   Un chiffre faux présenté comme vrai est plus dangereux qu'un écran vide. */
/* Analyse automatique du pilotage : lectures de direction calculées, rendues en
   petites fiches (pastille de ton + intitulé + valeur + explication courte). */
.ana-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(240px,1fr));gap:12px}
.ana-item{border:1px solid var(--line);border-radius:var(--r-lg);padding:12px 14px;display:flex;gap:10px;align-items:flex-start}
.ana-item .ana-dot{width:9px;height:9px;border-radius:50%;margin-top:6px;flex:none;background:var(--text-3)}
.ana-item .ana-t{font-size:11px;color:var(--text-3);text-transform:uppercase;letter-spacing:.04em}
.ana-item .ana-v{font-weight:640;margin:2px 0;color:var(--text)}
.ana-item .ana-d{font-size:12.5px;color:var(--text-2);line-height:1.45}
.ana-hausse .ana-dot{background:var(--ok)}
.ana-baisse .ana-dot{background:var(--att)}
.ana-alerte .ana-dot{background:var(--rouge)}
.non-raccorde{display:flex;align-items:flex-start;gap:10px;margin-bottom:16px;
  padding:11px 14px;border-radius:var(--r);font-size:13px;line-height:1.5;
  background:var(--t-jaune);color:var(--t-jaune-i);border:1px solid #E9E9A6}
.non-raccorde .mi{flex:none;display:flex;margin-top:1px}
.non-raccorde b{font-weight:650}

/* Un renvoi ne se déguise pas en bouton : c'est le mot lui-même qui mène, souligné
   d'un trait qui s'épaissit au survol. Hors de l'espace connecté, il reste du texte
   avec un pointillé — la mention est vraie, la porte n'existe pas pour vous. */
.renvoi{display:inline;font:inherit;color:inherit;background:none;border:none;padding:0;
  text-align:left;text-decoration:underline;text-decoration-color:var(--brand-3);
  text-underline-offset:3px;text-decoration-thickness:1.5px;
  transition:color .15s,text-decoration-color .15s}
.renvoi:hover,.renvoi:focus-visible{color:var(--brand);text-decoration-color:var(--brand)}
.renvoi .fl{display:inline-flex;vertical-align:-1px;margin-left:4px;opacity:0;width:0;
  transition:opacity .15s,width .15s,margin .15s}
.renvoi:hover .fl,.renvoi:focus-visible .fl{opacity:.75;width:12px}
.renvoi.hors{text-decoration-style:dotted;text-decoration-color:var(--line-2);
  color:var(--text-2);cursor:default}

/* Chaque étape d'une chaîne mène à l'écran qui la traite : la chaîne devient
   une carte qu'on parcourt, pas un schéma qu'on regarde. */
.step.va{cursor:pointer}
.step.va .l{transition:color .15s}
.step.va:hover .l{color:var(--brand)}
.step.va:hover .pin i{transform:scale(1.25)}
.step .pin i{transition:transform .18s cubic-bezier(.34,1.56,.64,1)}
.step.va:focus-visible{outline:2px solid var(--brand);outline-offset:4px;border-radius:8px}
/* Une étape qui se joue dans un autre espace était atténuée à 72 % —
   et c'est cette atténuation, elle seule, qui faisait tomber six couples de
   couleurs sous le seuil de 4,5:1 (mesuré : 3,05 pour le sous-titre, 3,66
   pour le badge jaune). Le texte reste donc à pleine encre ; « ce n'est pas
   chez vous » se dit par le curseur et par le trait, pas en effaçant. */
.step.hors .l{color:var(--text-2)}
.step.hors .l{cursor:default}
.chaine-hd .tile{cursor:default}
.chaine-hd.va{cursor:pointer}
.chaine-hd.va:hover h3{color:var(--brand)}
.chaine-hd h3{transition:color .15s}
.chaine-hd .aller{margin-left:8px;color:var(--text-3);opacity:0;transition:opacity .15s,transform .15s}
.chaine-hd.va:hover .aller{opacity:1;transform:translateX(2px)}

/* ══════════ Palette de commandes ══════════ */
.cmd-back{position:fixed;inset:0;z-index:50;background:rgba(20,28,24,.42);backdrop-filter:blur(3px);
  display:flex;align-items:flex-start;justify-content:center;padding:14vh 20px 20px;
  opacity:0;visibility:hidden;transition:opacity .12s ease-in,visibility 0s .12s}
.cmd-back.on{opacity:1;visibility:visible;transition:opacity .17s ease-out,visibility 0s}
@keyframes fade{from{opacity:0}to{opacity:1}}
.cmd{width:100%;max-width:560px;background:var(--surface);border:1px solid var(--line-2);
  border-radius:14px;box-shadow:var(--sh-3);overflow:hidden;
  transform:translateY(-8px) scale(.985);transition:transform .12s ease-in}
.cmd-back.on .cmd{transform:none;transition:transform .21s cubic-bezier(.32,.72,0,1)}
@keyframes pop{from{opacity:0;transform:translateY(-10px) scale(.98)}to{opacity:1;transform:none}}
.cmd-in{display:flex;align-items:center;gap:10px;padding:13px 15px;border-bottom:1px solid var(--line)}
.cmd-in input{flex:1;border:none;background:none;font-size:15px;outline:none}
.cmd-in input::placeholder{color:var(--text-3)}
.cmd-list{max-height:min(52vh,380px);overflow-y:auto;padding:6px}
.cmd-grp{font-size:11px;letter-spacing:.14em;text-transform:uppercase;color:var(--text-3);
  font-weight:650;padding:9px 10px 5px}
.cmd-row{display:flex;align-items:center;gap:11px;padding:9px 10px;border-radius:9px;width:100%;
  text-align:left;background:none;border:none;font-size:13px}
.cmd-row[aria-selected=true]{background:var(--surface-3)}
.cmd-row .tile{display:grid;place-items:center;flex:none;width:17px}
.cmd-row .t{flex:1;min-width:0;font-weight:550;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cmd-row .h{font-size:11px;color:var(--text-3);flex:none}
.cmd-ft{border-top:1px solid var(--line);padding:9px 15px;font-size:11px;color:var(--text-3);
  display:flex;gap:14px;background:var(--surface-2)}
.cmd-empty{padding:26px 16px;text-align:center;color:var(--text-3);font-size:13px}

/* CONFIRMER-CSS-DEBUT ══════ Confirmation — une question, ce qu'elle emporte, deux issues ══════

   Onze gestes de l'application demandaient confirmation par un `confirm()` du
   navigateur. Trois choses qu'un `confirm()` ne sait pas faire, et qui comptent
   precisement ici :
     · il ne MONTRE PAS ce sur quoi on agit. « Retirer cette annonce ? » ne dit
       pas laquelle. L'objet est desormais nomme, sur sa propre ligne ;
     · son bouton dit « OK », jamais le geste. Ici le bouton porte le VERBE
       (« Supprimer », « Remettre ») — le rouge n'est qu'un rappel, la couleur
       ne porte jamais l'information seule (1.4.1) ;
     · il se clique sans lire. Pour l'irreversible, l'option `saisie` demande
       d'ecrire ce qui est attendu, et le bouton reste INERTE tant que cela ne
       correspond pas : on n'autorise pas avant, plutot que de refuser apres.

   ⚠️ CE BLOC EST AUTONOME, ET IL DOIT LE RESTER. `outils/construire.py` le
   recopie dans `app/assets/confirmer.css` pour les pages qui vivent hors de
   l'application et n'ont pas cette feuille : E-SKHUB, et la Poche de la
   direction, qui a ses propres couleurs en dur. D'ou deux regles :
     · chaque jeton porte SON REPLI — `var(--alr, #C22E13)` — sinon la boite
       sortirait sans couleur sur une page qui ne declare pas la palette ;
     · les boutons sont a elle (`.cf-ok`), jamais `.btn` : `.btn` vit dans
       unitools.css, que ces pages ne chargent pas.

   L'issue neutre (« Annuler ») est un bouton de texte, sans cadre : elle ne se
   dispute pas l'oeil avec l'action. L'action est a DROITE, en dernier, la ou la
   main va. Forme reprise d'un dessin de reference (Perplexity, « Delete
   session? »), ramenee aux jetons de la maison. */
.cf-back{position:fixed;inset:0;z-index:70;background:rgba(20,28,24,.42);backdrop-filter:blur(3px);
  display:flex;align-items:center;justify-content:center;padding:20px;
  opacity:0;transition:opacity .14s ease-in}
.cf-back.on{opacity:1;transition:opacity .17s ease-out}
.cf{width:100%;max-width:412px;background:var(--surface,#fff);border:1px solid var(--line,#DDEAE2);
  border-radius:14px;box-shadow:0 18px 46px rgba(19,32,24,.20),0 2px 6px rgba(19,32,24,.07);
  padding:20px 22px 15px;transform:translateY(8px) scale(.985);transition:transform .14s ease-in;
  font:14px/1.6 var(--police,system-ui,-apple-system,'Segoe UI',Roboto,sans-serif);
  text-align:left}
.cf-back.on .cf{transform:none;transition:transform .21s cubic-bezier(.32,.72,0,1)}
.cf h2{font-size:16px;font-weight:640;color:var(--text,#132018);line-height:1.35;margin:0 0 7px;
  letter-spacing:0}
.cf p{font-size:13.5px;color:var(--text-2,#4F6259);line-height:1.6;margin:0}
/* L'objet sur SA ligne, en couleur de texte pleine : c'est lui qu'on relit
   avant de cliquer, pas la phrase qui l'entoure. */
.cf .cf-objet{display:block;margin-top:4px;color:var(--text,#132018);font-weight:600;
  overflow-wrap:anywhere}
.cf-saisie{display:block;margin-top:14px;font-size:12px;color:var(--text-3,#5A6F65)}
.cf-champ{width:100%;margin-top:6px;border:1px solid var(--line-2,#C3D8CC);border-radius:8px;
  padding:9px 10px;font-size:13px;background:var(--surface,#fff);color:var(--text,#132018);
  font-family:inherit}
.cf-actes{display:flex;justify-content:flex-end;align-items:center;gap:4px;margin-top:19px}
.cf-annuler,.cf-ok{min-height:40px;border-radius:9px;font-size:13px;font-weight:550;
  font-family:inherit;cursor:pointer;transition:background .18s,border-color .18s,color .18s}
.cf-annuler{background:none;border:none;color:var(--text-2,#4F6259);padding:0 13px}
.cf-annuler:hover{background:var(--surface-3,#EBF3EE);color:var(--text,#132018)}
/* Le plein n'existait pas : `.btn-danger` est un CONTOUR, fait pour vivre dans
   une barre d'actions parmi d'autres boutons. Dans la boite, l'action est seule
   et deja decidee — elle se pose en plein. */
.cf-ok{padding:0 16px;border:1px solid var(--brand-fonce,#2C7B54);
  background:var(--brand-fonce,#2C7B54);color:#fff}
.cf-ok:hover:not(:disabled){background:#164E34;border-color:#164E34}
.cf-ok.cf-rouge{border-color:var(--alr,#C22E13);background:var(--alr,#C22E13)}
.cf-ok.cf-rouge:hover:not(:disabled){background:#A32610;border-color:#A32610}
.cf-ok:disabled{opacity:.45;cursor:not-allowed}
/* CONFIRMER-CSS-FIN */

@media(max-width:1180px){.duo{grid-template-columns:1fr}}
@media(max-width:1100px){.g4,.g3{grid-template-columns:repeat(2,1fr)}.split{grid-template-columns:1fr}}
@media(max-width:860px){
  #shell{grid-template-columns:1fr}
  /* La colonne devient une bande : les univers passent en rangée, le pied et
     le périmètre s'effacent — la barre du haut les porte déjà. */
  .rail{position:static;height:auto;flex-direction:row;overflow-x:auto;align-items:center;padding:6px 8px}
  #nav{flex-direction:row;overflow-y:visible;overflow-x:auto}
  .rail-foot,.scope{display:none}
  .uni{width:auto;flex:none;margin:0 1px}
  .uni.on::before{display:none}
  .tb-marque img{width:88px}
  .tb-marque .t2{display:none}
  .cmd-open{max-width:160px}
  .content{padding-left:15px;padding-right:15px}
  .g2,.g3,.g4{grid-template-columns:1fr}
  .rs-hint{display:none}
  body{font-size:15px}
}

/* ═══════════════════════════════════════════════════════════════════════
   1.4.10 — REDIMENSIONNEMENT

   A 320 px de large (le seuil du critere), les vingt ecrans debordaient,
   jusqu'a +469 px : il fallait defiler horizontalement pour lire une ligne.

   La cause n'etait pas une largeur fixe quelque part. C'est `min-width:auto`,
   la valeur PAR DEFAUT d'un enfant de flex ou de grille : elle interdit a la
   boite de descendre sous la taille de son contenu. Une barre d'onglets de
   622 px poussait donc toute la page, alors qu'elle savait deja defiler
   toute seule.

   D'ou les deux moities de ce bloc :
   1. autoriser chaque conteneur a devenir plus etroit que son contenu ;
   2. rendre le defilement horizontal aux quelques cadres qui ont vraiment
      besoin de largeur — tableaux, barres d'onglets, diagrammes de chaine,
      calendrier. Le critere 1.4.10 les excepte explicitement (« les parties
      du contenu qui necessitent une disposition en deux dimensions ») a
      condition que ce soit LE CADRE qui defile, pas la page.

   Mesure : 20 ecrans sur 20 debordaient, 0 sur 20 apres.
   ═══════════════════════════════════════════════════════════════════════ */
@media(max-width:860px){
  .main, .topbar, .topbar > *, .tb-right, .tb-right > *, .page-title, #crumb,
  .content, .view, .duo, .split, .stack, .g2, .g3, .g4,
  .duo > *, .split > *, .stack > *, .g2 > *, .g3 > *, .g4 > *,
  .card, .card > *, .card-hd, .card-hd > *, .card-bd, .card-bd > *,
  .sec, .sec > *, .filtre, .filtre > *, .tbl, .tbl > *, .etapes{min-width:0}

  .topbar{flex-wrap:wrap;row-gap:8px}
  .card-hd{flex-wrap:wrap}
  .card-hd .act{margin-left:0}
  .card-sub{max-width:100%}
  .sec .line{display:none}

  /* Les cadres qui gardent leur largeur — et defilent dans leur boite.
     La barre d'onglets, elle, garde sa barre de défilement masquée : ce
     sont les bords estompés qui disent qu'elle continue. */
  .tabx-bar{overflow-x:auto}
  /* La barre de segments du Pilotage porte six écrans depuis le 24/08/2026
     (Documentation et Piste d'audit repris chez Franck). Elle défile DANS SA
     BOÎTE plutôt que d'élargir la page — même exception 1.4.10 que les
     onglets et les tableaux. */
  .segx{max-width:100%;overflow-x:auto}
  .tbl{overflow-x:auto;max-width:100%}
  .tbl table{width:max-content;min-width:100%}
  .flow,.etapes-wrap,.cal-wrap{max-width:100%;overflow-x:auto}
}