/* LE FRONT-OFFICE demande.mayumbe.net — habillage v2 (14/08).
   Constat du test réel : « sommaire, pas accueillant, pas pro ».
   Réponse : l'identité Mayumbe Connecting (globe My rouge/bleu),
   la charte orange/noir de la maison, des coordonnées réelles
   visibles — un site qui dit qui il est. Aucune ressource externe
   (ni police, ni script tiers) : tout vient de demande.mayumbe.net. */

:root {
    /* L'orange OFFICIEL de mayumbe.net (le bouton « Prenons
       contact ») pour les accents ; une déclinaison plus profonde
       pour les fonds d'action (contraste AA avec du blanc). */
    --orange: #e67a22;
    --orange-fonce: #b35208;
    --noir: #16181d;
    --encre: #26282e;
    --gris-doux: #5f5f5f;
    --bleu: #26348b;
    --rouge: #d0212a;
    --creme: #f7f6f3;
    --carte: #ffffff;
    --trait: #e3e0d9;
    --vert: #1c7c3c;
    --vert-doux: #eaf6ee;
    --rouge-doux: #fdeeee;
    /* [LOT 4-5] LES CASES ET RADIOS ENCORE NATIFS sortaient en bleu
       système au milieu d'une charte orange/noir (audit du 18/08 :
       0 accent-color dans la feuille — la case « véhicule chargé »,
       les 4 radios de profil). L'orange FONCÉ et non l'orange clair :
       l'état coché dessine une coche BLANCHE sur ce fond — blanc sur
       #e67a22 mesure 2,93:1, sous les 3:1 d'un composant ; blanc sur
       #b35208 mesure 5,09:1, le même couple déjà retenu pour le focus
       et les boutons. Sans effet sur les tuiles : leur radio est à
       opacity 0, c'est la carte qui porte l'état. */
    accent-color: var(--orange-fonce);
}

* { box-sizing: border-box; }

/* La règle [hidden] du navigateur est d'origine UA : nos display
   d'auteur (label{display:block}, .cotes{display:grid}) la battaient
   et le masquage adaptatif des portes restait INERTE (vérification
   finale du 14/08 — « tester ce que l'écran MONTRE », encore). */
[hidden] { display: none !important; }

body {
    margin: 0;
    background: var(--creme);
    color: var(--encre);
    font: 16px/1.55 "Segoe UI", system-ui, -apple-system, Arial,
          sans-serif;
}

a { color: var(--bleu); }

/* ---- L'en-tête : le cartouche officiel de mayumbe.net ----------- */
.entete { background: var(--carte); border-bottom: 4px solid var(--orange); }
.entete-contenu {
    max-width: 980px;
    margin: 0 auto;
    padding: 14px 20px;
    display: flex;
    /* Le repli n'existait qu'en dessous de 720 px. Entre 721 et 980 —
       une tablette en portrait, un navigateur en demi-écran — le logo
       de 200 px, la baseline et les deux coordonnées restaient sur une
       ligne unique et se comprimaient. Le repli vaut à toute largeur ;
       au-dessus, il ne se déclenche simplement jamais. */
    flex-wrap: wrap;
    align-items: center;
    gap: 20px;
}
.lien-logo { flex: 0 0 auto; display: block; }
.logo { width: 200px; height: auto; display: block; }
.baseline {
    flex: 1 1 auto;
    min-width: 0;
    margin: 0;
    color: var(--gris-doux);
    font-size: .95rem;
}
/* LE TELEPHONE ET L'ADRESSE TIENNENT SUR UNE LIGNE (21/08/2026).
   Empilees, elles faisaient 53 px et c'est ELLES qui dictaient la
   hauteur de l'en-tete — le logo n'en fait que 38. Cote a cote, l'en-
   tete retombe sur la hauteur du logo. Mesure : 85 px -> 70 px.
   `flex-wrap` (regle de la maison) les rempile toute seule des que la
   largeur manque ; verifie a 760, 560 et 400 px, sans debordement. */
.contact-entete {
    display: flex;
    flex-wrap: wrap;
    justify-content: flex-end;
    gap: 2px 16px;
    text-align: right;
    font-size: .95rem;
}
.contact-entete p { margin: 0; }
.contact-entete a { text-decoration: none; font-weight: 600; }

/* ---- Le bandeau sombre : la promesse, entaillée d'orange comme
        le logo --------------------------------------------------- */
.bandeau-sombre {
    background:
        linear-gradient(115deg,
            var(--orange) 0, var(--orange) 84px,
            transparent 84px),
        linear-gradient(115deg,
            transparent 0, transparent 96px,
            var(--orange) 96px, var(--orange) 118px,
            transparent 118px),
        var(--noir);
    color: #f4f2ec;
}
/* Le bandeau porte l'identite de la maison : on le COMPRIME, on ne le
   retire pas. 28/24 -> 18/16 rend 18 px a la premiere porte. */
/* ── LE BANDEAU PRENAIT LE QUART DE L'ECRAN (21/08/2026) ─────────

   CONSTAT DE M. CHOKONTE, capture a l'appui : « pourquoi cette partie
   est si grande jusqu'a faire 1/5 de l'ecran ? »

   MESURE SUR LE SITE REEL, a 1280x720 : en-tete 85 px + bandeau
   118 px = 203 px, soit 28,2 % de la fenetre AVANT le premier
   contenu. Sur les 118 px du bandeau, le texte n'en occupait que 67 :
   43 % de vide.

   ET 32 DE CES PIXELS ETAIENT UN RESTE. `.slogan` portait
   `margin: 0 0 16px` — reserve pour la liste 1-2-3 (`.etapes`) qui la
   suivait. Cette liste a ete RETIREE le 14/08 (voir le commentaire
   plus bas) ; la marge, elle, est restee. Additionnee aux 16 px de
   padding du conteneur, cela faisait 32 px de vide sous la derniere
   ligne, pour un bloc qui n'existe plus.

   TROIS CORRECTIONS, MESUREES CHACUNE :
     · la marge morte du slogan      -16 px
     · padding 18/16 -> 14/14         -6 px
     · titre et slogan sur UNE ligne -29 px
     · contact sur une ligne         -15 px (en-tete)
   Total : 203 px -> 136 px, soit 18,9 %. Et le gain tient a toutes
   les largeurs (-53 px a 400 px), sans debordement horizontal.

   ON COMPRIME, ON NE RETIRE PAS : le bandeau porte l'identite de la
   maison — l'entaille orange du logo, la promesse, le slogan. C'est
   la doctrine posee le 14/08, et elle ne change pas. */
.bandeau-contenu {
    max-width: 980px;
    margin: 0 auto;
    padding: 14px 20px;
    /* Le titre et le slogan se rangent cote a cote quand la largeur le
       permet, et se rempilent sinon. `flex-wrap` est la regle de la
       maison — jamais de flex sans lui. */
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: 2px 18px;
}
.bandeau-contenu h1 { margin: 0; font-size: 1.55rem; }
/* La progression des demarches prend sa ligne entiere : sans cela,
   elle viendrait se coller au slogan. */
.bandeau-contenu .progression { flex: 1 0 100%; margin: 8px 0 0; }
.slogan {
    /* PAS DE MARGE BASSE : celle de 16 px servait `.etapes`, retiree
       le 14/08. Une marge qui survit a l'element qu'elle espacait est
       du vide que personne ne voit et que tout le monde subit. */
    margin: 0;
    color: var(--orange);
    font-size: 1.02rem;
    font-style: italic;
    letter-spacing: .3px;
}
/* (.etapes et .pastille — la liste 1-2-3 du bandeau v2 — retirées le
   14/08 : plus aucune page n'émet ce balisage. Les étapes du parcours
   stage vivent sous .formulaire-etapes / .etapes-navigation.) */

/* [LOT 4-5] LE BANDEAU COMPACT DES PAGES DE TÂCHE (§31).
   Le grand bandeau (28 px de marge haute, titre à 1,55 rem) est celui
   de l'ACCUEIL : il présente la maison. Sur une page de tâche, il
   repoussait le premier champ sous la ligne de flottaison d'un
   téléphone (~640 px utiles) sans rien dire de plus que le titre. Le
   compact rend cette place au formulaire et porte ce qui manquait :
   le retour métier unique — aucune page de tâche n'offrait de retour
   avant l'écran de confirmation (grep index.php sur les 6 pages : 0
   hors confirmation) — et le pictogramme de la porte franchie, le
   même dessin que l'accueil (registre pictos_demarches()).
   `flex-wrap` : règle de la maison, jamais de flex sans repli. */
.bandeau-demarche .bandeau-contenu { padding: 14px 20px 18px; }
.retour-demarche { margin: 0 0 10px; font-size: .92rem; }
/* Le blanc cassé de l'en-tête sombre (#f4f2ec : ~14:1 sur le noir) —
   le bleu des liens (--bleu) ne rendrait que ~1,6:1 sur ce fond. */
.retour-demarche a { color: #f4f2ec; }
.demarche-entete {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 6px 14px;
}
.demarche-picto { color: var(--orange); flex: 0 0 auto; }
.demarche-picto svg { width: 44px; height: 37px; display: block; }
.demarche-titres { flex: 1 1 16rem; min-width: 0; }
.bandeau-demarche h1 { font-size: 1.32rem; margin: 0; }
.bandeau-demarche .slogan { margin: 2px 0 0; font-size: .95rem; }
/* La progression vit dans le bandeau : le script du parcours défile
   vers le HAUT à chaque étape, l'œil retombe donc dessus. L'orange
   clair remplace ici l'orange foncé de la règle générale : sur le
   bandeau noir, --orange-fonce rendrait ~2,3:1 ; --orange mesure
   ~6,2:1 — le même couple que le slogan, déjà en place. */
.bandeau-demarche .progression { margin: 10px 0 0; color: var(--orange); }

/* ---- La carte du formulaire ------------------------------------- */
main { max-width: 860px; margin: 16px auto 32px; padding: 0 16px; }

/* LE CONTENU SUIT L'ECRAN (20/08, constat de M. Chokonte, mesure a
   l'appui : 1 060 px de vide sur 1 920 — 523 a gauche, 537 a droite —
   pour 860 px de contenu, soit 45 % de l'ecran utilise ; et la
   troisieme porte tombait 365 px SOUS la ligne de flottaison).
   « Dans ce type je propose toujours une VISION GLOBALE, meme dans les
   formulaires » : on elargit par PALIERS plutot qu'en fluide, pour que
   la ligne de texte ne devienne jamais illisible — 860 reste la mesure
   de reference en dessous de 1 400 px, la ou elle a ete calculee. */
@media (min-width: 1400px) {
    main { max-width: 1180px; }
    .bandeau-contenu { max-width: 1180px; }
}
@media (min-width: 1750px) {
    main { max-width: 1320px; }
    .bandeau-contenu { max-width: 1320px; }
}
.carte {
    background: var(--carte);
    border: 1px solid var(--trait);
    border-radius: 10px;
    padding: 26px 28px 30px;
    box-shadow: 0 2px 14px rgba(27, 27, 31, .07);
}
fieldset {
    border: 0;
    border-top: 1px solid var(--trait);
    margin: 18px 0 0;
    padding: 16px 0 0;
}
fieldset:first-of-type { border-top: 0; margin-top: 0; padding-top: 0; }
legend {
    font-weight: 700;
    color: var(--orange-fonce);
    font-size: 1.05rem;
    padding-right: 10px;
}
.facultatif { font-weight: 400; color: #6c6f78; font-size: .9rem; }
.requis { color: var(--rouge); }

label { display: block; margin: 10px 0 0; font-weight: 600; font-size: .95rem; }
/* Les champs date étaient laissés au rendu navigateur : dans une
   grille, la case était plus courte et plus basse que sa voisine —
   la « marche » que la charte de la maison pourchasse (passe adverse
   du 14/08). */
/* [LOT 4-5] `select` REJOINT LA LISTE (constat d'audit du 18/08 :
   « civilité non stylisée »). Le style équivalent vivait sous une
   classe à poser à la main (.select-sobre) et 2 selects sur 6
   l'oubliaient — civilité et canal de réponse, ceux du tronc commun,
   dans la grille où la taxonomie de largeur les aligne désormais avec
   nom et prénom : sans largeur à 100 %, la ligne promise serait
   bancale. Dans la liste, le défaut ne peut plus se reproduire à
   l'oubli près ; la classe manuelle est retirée (un seul mécanisme).
   Au passage les selects prennent le même gras 400 que les champs :
   `font: inherit` sous un label à 600 les rendait gras par accident. */
input[type="text"], input[type="tel"], input[type="email"],
input[type="date"], input[type="number"], select, textarea {
    display: block;
    width: 100%;
    margin-top: 5px;
    padding: 9px 11px;
    font: inherit;
    font-weight: 400;
    color: var(--encre);
    background: #fbfaf7;
    /* [LOT 4-5] LE BORD DU CHAMP EST CE QUI DIT « ICI ON ÉCRIT ».
       Mesure : #c9c5bb rendait 1,72:1 sur le blanc de la carte —
       WCAG 1.4.11 en demande 3 pour la limite d'un composant, et le
       fond du champ (#fbfaf7) ne se distingue de la carte que de
       1,03:1 : le trait était donc SEUL à dessiner la case. #8a8578
       mesure 3,68:1 sur blanc, 3,53:1 sur le champ, 3,40:1 sur le
       crème — il passe partout où un champ se pose. */
    border: 1px solid #8a8578;
    border-radius: 6px;
    transition: border-color .12s ease, background .12s ease;
}
/* [LOT 4-5] LE LISERÉ DE FOCUS SE MESURE, LUI AUSSI.
   L'orange de la charte (#e67a22) rendait 2,93:1 sur le blanc,
   2,81:1 sur le fond des champs, 2,71:1 sur le crème — sous les 3:1
   exigés d'un indicateur de focus. L'orange foncé, déjà dans la
   palette et déjà porté par les boutons d'action, rend 5,09:1. Il
   remplace l'orange clair PARTOUT où le focus se dessine ; la charte
   ne change pas, seul le trait qui doit se voir au clavier. */
input:focus, textarea:focus {
    outline: 2px solid var(--orange-fonce);
    outline-offset: 1px;
    background: #fff;
}
/* Une seule règle pour tout ce qui se parcourt au clavier sans être
   un champ de saisie : liens, boutons, dérouleurs, listes. Les portes
   de l'accueil, le pied de page et le « Ajouter des documents »
   n'avaient AUCUN liseré d'auteur — ils s'en remettaient au dessin du
   navigateur, qui disparaît sur un fond blanc dans plusieurs d'entre
   eux. Les inputs sont exclus à dessein : le radio des cartes-type est
   transparent et positionné hors flux, c'est sa carte qui montre le
   focus (règle .carte-type-boite plus bas). */
a:focus-visible, button:focus-visible, summary:focus-visible,
select:focus-visible {
    outline: 3px solid var(--orange-fonce);
    outline-offset: 2px;
}
textarea { resize: vertical; }
/* Le gris des exemples (« ex. chauffeur, comptable ») mesurait 2,60:1
   sur le fond des champs : illisible au soleil, hors norme (1.4.3).
   On reprend le gris des notes — le seul de la famille mesuré au-dessus
   de 4,5:1 (4,81:1 ici) — plutôt que d'en inventer un de plus. */
::placeholder { color: #6c6f78; }

/* [LOT 4-5] LA TAXONOMIE DE LARGEUR (§32) — xs / court / moyen /
   large / plein, posée SUR la grille qui existait déjà.

   `.deux-colonnes` passait tout en moitiés : une civilité de 12
   caractères recevait la même largeur qu'une adresse e-mail, et la
   ligne civilité vivait seule dans sa propre grille (une demi-ligne
   vide sous les yeux de tous les parcours). Plutôt qu'un SECOND
   mécanisme de grille (le piège payé deux fois dans ce dépôt), la
   même classe devient une grille de 12 pas où l'enfant SANS classe
   garde exactement sa moitié d'avant : span 6 de 12 avec le même
   écart de 22 px rend au pixel près l'ancien `1fr 1fr` — aucun
   parcours non retouché ne bouge.

   Les cinq largeurs, RECALCULÉES à la contre-passe du 18/08 (la
   première version de ce commentaire portait des pixels qui ne
   suivaient pas sa propre formule). La chaîne vraie : main 860 en
   border-box moins 2×16 de padding = 828 ; .carte moins 2×1 de bord
   et 2×28 de padding = 770 de contenu ; piste (770 − 11×22)/12
   = 44 px exactement :
     xs    = span 3 = 176 px — une date (jj/mm/aaaa ~140 px), un choix
             court « Présence » ;
     court = span 4 = 242 px — civilité, nom, prénom (3 × 4 = 12 :
             LA ligne demandée), téléphone, année, niveau ;
     moyen = span 6 = 374 px — la moitié d'avant, le défaut
             ((770 − 22)/2 = 374 : la preuve de l'équivalence) ;
     large = span 8 = 506 px — e-mail, nom d'école, expérience :
             ce qui se lit d'un tenant ;
     plein = toute la ligne (770 px) — les descriptions (textarea).
   Sous 721 px, le bloc petits écrans (plus BAS dans la feuille, donc
   vainqueur à spécificité égale) ramène TOUT en pleine largeur :
   à 360 px et sans JavaScript, une seule colonne, rien ne casse. */
.deux-colonnes {
    display: grid;
    grid-template-columns: repeat(12, 1fr);
    gap: 4px 22px;
}
.deux-colonnes > * { grid-column: span 6; }
.champ-xs { grid-column: span 3; }
.champ-court { grid-column: span 4; }
.champ-moyen { grid-column: span 6; }
.champ-large { grid-column: span 8; }
.champ-plein { grid-column: 1 / -1; }
.cotes {
    display: grid;
    grid-template-columns: repeat(4, 1fr);
    gap: 4px 14px;
}

.txt-note { color: #6c6f78; font-size: .88rem; margin: 8px 0 0; }
.centre { text-align: center; }

/* ---- Les 4 portes du besoin (parcours guidé) --------------------- */
.cartes-type {
    display: grid;
    grid-template-columns: repeat(4, 1fr);
    gap: 12px;
    margin-top: 12px;
}
.carte-type-boite { position: relative; }
.carte-type-boite input[type="radio"] {
    position: absolute;
    opacity: 0;
    inset: 0;
    pointer-events: none;
}
.carte-type {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 6px;
    text-align: center;
    padding: 16px 10px 13px;
    margin: 0;
    background: #fbfaf7;
    border: 2px solid var(--trait);
    border-radius: 10px;
    cursor: pointer;
    font-weight: 600;
    color: var(--encre);
    transition: transform .15s ease, border-color .15s ease,
                box-shadow .15s ease, background .15s ease;
}
.carte-type svg { width: 46px; height: 32px; color: var(--orange); }
.carte-type small { font-weight: 400; color: #6c6f78; }
.carte-type:hover {
    transform: translateY(-2px);
    border-color: var(--orange);
    box-shadow: 0 6px 16px rgba(230, 122, 34, .18);
}
.carte-type-boite input:checked + .carte-type {
    border-color: var(--orange);
    background: #fdf3ea;
    box-shadow: 0 4px 14px rgba(230, 122, 34, .22);
}
.carte-type-boite input:checked + .carte-type strong {
    color: var(--orange-fonce);
}
/* [LOT 4-5] « LEQUEL AI-JE CHOISI ? » NE SE RÉPONDAIT QU'EN COULEUR.
   Les trois marques de l'état choisi — bord orange, fond crème rosé,
   titre orange foncé — sont TOUTES des couleurs, et le radio qui porte
   vraiment l'état est à `opacity: 0`. Un daltonien deutan lit un bord
   orange et un bord beige comme le même trait ; en mode contraste forcé
   de Windows, le système remplace fonds et bords et l'état choisi
   devient INVISIBLE — sur l'écran qui décide de toute la démarche.

   La maison a déjà le remède, la barre d'étapes du suivi : « la pastille
   porte le sens ; la couleur seule ne suffirait pas ». On reprend la
   même coche, posée dans le coin plutôt qu'en fin de carte — un élément
   de flux ferait grandir la carte à la sélection et sauter la grille. */
.carte-type-boite input:checked + .carte-type::after {
    content: "\2713";
    position: absolute;
    top: 6px;
    right: 9px;
    font-weight: 700;
    color: var(--orange-fonce);
}
.carte-type-boite input:focus-visible + .carte-type {
    /* Orange foncé : 5,09:1 sur le blanc, contre 2,93:1 pour l'orange
       clair — le liseré doit se voir, pas seulement exister. */
    outline: 3px solid var(--orange-fonce);
    outline-offset: 2px;
}

/* ---- Les documents ---------------------------------------------- */
.zone-documents {
    /* Le pointillé est la limite de la zone de dépôt — même exigence de
       3:1 que les champs (il mesurait 1,72:1). */
    border: 2px dashed #8a8578;
    border-radius: 8px;
    padding: 14px 16px 12px;
    margin-top: 10px;
    background: #fbfaf7;
}
/* [LOT 4-5 §36] LES DEUX ACTIONS PORTENT LE MÊME COSTUME. L'audit du
   18/08 l'a mesuré : « Prendre une photo » restait une étiquette NUE
   (0 règle .etiquette-photo) à côté d'un bouton habillé. Le bouton
   photo (créé hidden dans bloc_documents, éveillé par le script)
   reprend les jetons du bouton voisin — une seule écriture. */
#bouton-documents, .bouton-photo {
    font: inherit;
    font-weight: 600;
    color: var(--bleu);
    background: #fff;
    border: 1px solid var(--bleu);
    border-radius: 6px;
    padding: 9px 16px;
    cursor: pointer;
}
#bouton-documents:hover, .bouton-photo:hover { background: #eef0fa; }
#bouton-documents:disabled, .bouton-photo:disabled {
    color: #9a9da6;
    border-color: #c9c5bb;
    cursor: default;
    background: #f2f1ec;
}
/* LA PHOTO NE SE PROPOSE QU'À QUI TIENT UN APPAREIL. Sur un
   ordinateur, `capture` n'ouvre rien : le contrôle promettait un
   appareil et livrait un sélecteur de fichiers (audit du 18/08). Les
   deux visages du geste — l'étiquette native (monde sans JavaScript)
   et le bouton habillé (monde avec) — restent donc éteints hors
   pointeur grossier ; le bureau reçoit le glisser-déposer en
   complément. La media query vient APRÈS : à spécificité égale,
   l'ordre tranche, et c'est voulu. */
.etiquette-photo { display: none; }
.bouton-photo { display: none; margin-left: 8px; }
@media (pointer: coarse) {
    .etiquette-photo { display: block; margin-top: 10px; }
    .bouton-photo { display: inline-block; }
    /* L'invitation au dépôt parle d'un geste de souris : elle se tait
       sous le doigt. */
    .indice-depot { display: none; }
}
/* Le survol d'un dépôt se signale par les jetons déjà en place — le
   bord passe plein en orange foncé (5,09:1), le fond reprend le crème
   rosé de l'état choisi des tuiles. Aucune couleur nouvelle. */
.zone-documents.zone-survolee {
    border-style: solid;
    border-color: var(--orange-fonce);
    background: #fdf3ea;
}
/* Le gris des notes (4,81:1 sur le fond des champs) — on n'en invente
   pas un de plus. */
.indice-depot {
    margin-left: 10px;
    color: #6c6f78;
    font-size: .88rem;
}
.liste-documents { list-style: none; margin: 10px 0 0; padding: 0; }
.liste-documents li {
    display: flex;
    /* Un nom de fichier long et le bouton « retirer » ne se marchent
       pas dessus : ils passent l'un sous l'autre. */
    flex-wrap: wrap;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    background: #fff;
    border: 1px solid var(--trait);
    border-radius: 6px;
    padding: 6px 10px;
    margin-top: 6px;
    font-size: .92rem;
}
/* Un nom de fichier de 150 caractères sans espace ne doit pas faire
   défiler la page (revue adverse) : il se replie. */
.liste-documents li span {
    min-width: 0;
    overflow-wrap: anywhere;
}
.liste-documents button {
    font: inherit;
    line-height: 1;
    border: 0;
    background: none;
    color: var(--rouge);
    font-weight: 700;
    cursor: pointer;
    padding: 4px 6px;
}
/* Le champ natif s'efface par clip, jamais display:none : il reste
   actionnable par script et par les aides techniques. */
.visuellement-cache {
    position: absolute;
    width: 1px;
    height: 1px;
    overflow: hidden;
    clip: rect(0 0 0 0);
    white-space: nowrap;
}

/* ---- L'envoi ----------------------------------------------------- */
.bouton-envoi {
    display: block;
    width: 100%;
    margin-top: 24px;
    padding: 14px;
    font: inherit;
    font-size: 1.12rem;
    font-weight: 700;
    color: #fff;
    /* orange foncé : le contraste AA (revue adverse du 14/08). */
    background: var(--orange-fonce);
    border: 0;
    border-radius: 8px;
    cursor: pointer;
}
.bouton-envoi {
    transition: background .15s ease, transform .1s ease;
}
.bouton-envoi:hover { background: #93390b; transform: translateY(-1px); }
.bouton-envoi:active { transform: translateY(0); }

/* ---- Messages ---------------------------------------------------- */
.erreurs {
    background: var(--rouge-doux);
    border: 1px solid #e4b2b2;
    border-left: 5px solid var(--rouge);
    border-radius: 8px;
    padding: 14px 18px;
    margin-bottom: 18px;
}
.erreurs h2 { margin: 0 0 6px; font-size: 1.05rem; color: #8f1d23; }
.erreurs ul { margin: 0; padding-left: 20px; }
.erreurs li { margin: 3px 0; overflow-wrap: anywhere; }

.confirmation {
    background: var(--vert-doux);
    border: 1px solid #bcdcc6;
    border-radius: 10px;
    padding: 30px 28px;
    text-align: center;
}
.coche {
    width: 58px;
    height: 58px;
    margin: 0 auto 10px;
    border-radius: 50%;
    background: var(--vert);
    color: #fff;
    font-size: 2rem;
    line-height: 58px;
    font-weight: 700;
}
.confirmation h2 { margin: 0 0 8px; color: var(--vert); }
.reference-bloc { font-size: 1.15rem; }
.reference-bloc strong {
    color: var(--orange-fonce);
    font-size: 1.5rem;
    letter-spacing: .5px;
}
.la-suite {
    text-align: left;
    max-width: 520px;
    margin: 18px auto 0;
    background: #fff;
    border: 1px solid var(--trait);
    border-radius: 8px;
    padding: 12px 20px 14px;
}
.la-suite h3 { margin: 4px 0 6px; font-size: 1rem; }
.la-suite ul { margin: 0; padding-left: 20px; }
.la-suite li { margin: 5px 0; }

/* ---- Le pot de miel (invisible pour un humain) ------------------- */
.piege {
    position: absolute;
    left: -9999px;
    top: -9999px;
}

/* ---- Le pied : les coordonnées réelles --------------------------- */
.pied { background: var(--noir); color: #cfccc2; margin-top: 30px; }
.pied a { color: #f0eee7; }
.pied-contenu {
    max-width: 980px;
    margin: 0 auto;
    padding: 26px 20px 30px;
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    gap: 26px;
    font-size: .92rem;
}
.logo-pied { width: 180px; height: auto; display: block; margin: 0 0 10px; }
.pied-titre {
    color: #fff;
    font-weight: 700;
    margin: 0 0 6px;
}
.pied p { margin: 0 0 4px; }
/* DEUX NUMEROS, DONC IL FAUT DIRE LEQUEL EST LEQUEL (06/09/2026).
   Le fixe a rejoint le mobile au pied de page : sans cette precision,
   le visiteur voit deux nombres et ne sait pas lequel appeler. */
.pied-precision {
    opacity: .7;
    font-size: .9em;
}

/* ---- Le guichet : les portes de démarche (accueil) --------------- */
/* [LOT 4-5] L'ACCUEIL PAR INTENTIONS (§30). La grille unique posait
   5 cartes sur 3 colonnes : 3 puis 2, la 3e cellule de la 2e ligne
   vide (constat d'audit du 18/08). Trois groupes remplacent la grille
   unique ; le titre du groupe dit le MOMENT du parcours. Son gris est
   celui des volets de rassurance (#55585f : 6,6:1 sur le crème) — on
   ne crée pas un gris de plus. */
.groupe-portes-titre {
    margin: 0 0 5px;
    font-size: .92rem;
    font-weight: 700;
    letter-spacing: .08em;
    text-transform: uppercase;
    color: #55585f;
}
.portes-grille {
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    gap: 16px;
    margin: 2px 0 12px;
}
/* Chaque groupe a autant de colonnes que de cartes : 1, 3 et 2 —
   la grille est pleine par construction, plus de trou à combler ni
   de 3+2 à assumer. Sous 720 px, la règle « .portes-grille : 1fr »
   du bloc petits écrans vient APRÈS dans la feuille : à spécificité
   égale, elle gagne et tout redevient une colonne. */
.portes-grille-1 { grid-template-columns: 1fr; }
.portes-grille-2 { grid-template-columns: repeat(2, 1fr); }
.porte-carte {
    display: flex;
    flex-direction: column;
    gap: 6px;
    padding: 16px 18px 14px;
    background: var(--carte);
    border: 1px solid var(--trait);
    border-left: 5px solid var(--orange);
    border-radius: 10px;
    text-decoration: none;
    color: var(--encre);
    box-shadow: 0 2px 10px rgba(27, 27, 31, .05);
    transition: transform .15s ease, box-shadow .15s ease,
                border-color .15s ease;
}
.porte-picto { display: block; color: var(--orange); }
.porte-picto svg { width: 48px; height: 40px; display: block; }
.porte-carte strong { font-size: 1.06rem; color: var(--noir); }
.porte-carte small { color: #6c6f78; line-height: 1.4; }
.porte-appel {
    margin-top: auto;
    padding-top: 8px;
    font-weight: 700;
    color: var(--orange-fonce);
    font-size: .92rem;
}
.porte-carte:hover {
    transform: translateY(-3px);
    box-shadow: 0 8px 22px rgba(230, 122, 34, .18);
    border-color: var(--orange);
}
/* [LOT 4-5] La porte seule du groupe « Commencer une démarche » est
   l'action commerciale principale (§30) : pleine largeur, titre et
   pictogramme plus grands. La hiérarchie tient par l'ORDRE et la
   TAILLE — pas par une couleur de plus, qui ne survivrait ni au
   daltonisme ni au contraste forcé (leçon des cartes-type). À 360 px,
   tout est déjà sur une colonne : cette porte reste première et plus
   grande, la hiérarchie ne dépend pas de la largeur. */
.portes-grille-1 .porte-carte { padding: 24px 22px 18px; }
.portes-grille-1 .porte-carte strong { font-size: 1.28rem; }
.portes-grille-1 .porte-carte small { font-size: 1rem; }
.portes-grille-1 .porte-picto svg { width: 60px; height: 50px; }
/* [RECETTE VISUELLE 18/08] Constaté au navigateur (M. Chokonté puis
   mesure : carte 828 px, dernier texte à 43 px du bord gauche) : la
   porte pleine largeur empilait picto, titre, sous-titre et appel à
   GAUCHE — plus de la moitié de la carte restait vide, et l'emphase
   lisait comme une erreur de grille. Sur écran large elle se COUCHE :
   picto | titre sur sous-titre | appel à droite — la largeur sert la
   lecture. Sous 721 px, rien ne change (empilement d'origine).
   GRILLE et non flex : strong et small sont frères dans le balisage,
   seules des zones nommées les empilent sans les envelopper. */
@media (min-width: 721px) {
    .portes-grille-1 .porte-carte {
        display: grid;
        grid-template-columns: auto 1fr auto;
        grid-template-areas:
            "picto titre appel"
            "picto sous  appel";
        align-items: center;
        column-gap: 24px;
        row-gap: 4px;
    }
    .portes-grille-1 .porte-picto { grid-area: picto; }
    .portes-grille-1 .porte-carte strong { grid-area: titre; align-self: end; }
    .portes-grille-1 .porte-carte small { grid-area: sous; align-self: start; }
    .portes-grille-1 .porte-appel {
        grid-area: appel;
        margin-top: 0;
        padding-top: 0;
        white-space: nowrap;
    }
}
.porte-doute {
    background: var(--carte);
    border: 1px dashed #c9c5bb;
    border-radius: 10px;
    padding: 12px 18px;
    margin-bottom: 22px;
}
.porte-doute summary {
    cursor: pointer;
    font-weight: 600;
    color: var(--bleu);
}
.porte-doute-corps { padding: 10px 2px 4px; }

/* L'OPTION << JE VIENS EN DEUX FOIS >> SE VOIT (06/09/2026).
   M. Chokonte : << le bouton et la note sont discrets, il faut
   utiliser la meme chose que les vols multiples >>. Sur un site de
   vols, le choix multi-destinations est une OPTION qu'on voit avant
   de remplir quoi que ce soit -- pas une ligne grise entre deux
   champs. Elle est donc encadree, et elle se colore quand elle est
   ouverte : l'oeil sait, sans lire, qu'un second bloc est declare. */
.periode-seconde {
    border: 1px solid var(--gris-bord, #d5d8dd);
    border-radius: 10px;
    padding: 10px 14px;
    margin: 6px 0 14px;
    background: #fbfbfc;
}
.periode-seconde > summary {
    cursor: pointer;
    font-weight: 600;
    color: var(--bleu);
    list-style-position: outside;
}
.periode-seconde[open] {
    border-color: var(--bleu);
    background: #fff;
}
/* LES DEUX DATES RENTRENT DANS LA GRILLE DU GUICHET, a la MEME
   largeur que celles du dessus : hors grille, elles s'etalaient sur
   toute la page et ecrasaient la premiere periode. */
.periode-seconde-corps { padding: 8px 0 2px; }
.periode-seconde-corps .txt-note { margin: 0 0 10px; }
.porte-doute-corps p { margin: 8px 0; }
.rassurance {
    display: grid;
    grid-template-columns: repeat(3, 1fr);
    gap: 16px;
    color: #55585f;
    font-size: .93rem;
    line-height: 1.45;
}
.rassurance strong { color: var(--noir); }

/* ---- Les parcours : compléments de formulaire -------------------- */
.cartes-type-5 { grid-template-columns: repeat(5, 1fr); }
/* [UX/UI UPGRADE] Les quatre profils tenaient sur UNE ligne sans
   autorisation de retour : a 360 px, « Un etablissement scolaire » et
   « Une administration » poussaient la page hors de l'ecran et
   fabriquaient une barre de defilement horizontale sur TOUT le
   document. C'est la famille de defaut que la maison connait deja :
   jamais de `flex` sans `flex-wrap`. */
.choix-profil {
    display: flex;
    flex-wrap: wrap;
    gap: 10px 26px;
    margin-top: 10px;
}
.choix-inline {
    display: flex;
    /* Une case à cocher suivie d'une phrase longue : la phrase se
       replie sous la case plutôt que d'élargir la page. */
    flex-wrap: wrap;
    align-items: center;
    gap: 8px;
    font-weight: 600;
    margin-top: 10px;
}
.choix-inline input { width: auto; margin: 0; }
/* (.select-sobre — le double manuel du style des selects — fondue dans
   la règle générale des champs, en tête de feuille : 2 selects sur 6
   l'oubliaient, l'audit du 18/08 a tranché « un seul geste ». Les 4
   emissions de la classe ont été retirées des pages en même temps.) */
.lien-retour { font-weight: 600; }

/* ---- Le parcours en étapes (stage) ------------------------------- */
.progression {
    font-weight: 700;
    color: var(--orange-fonce);
    margin: 0 0 4px;
}
/* [LOT 4-5] La barre du parcours portait « ← Étape précédente » et
   « Étape suivante → » côte à côte SANS autorisation de retour. À
   360 px, les deux libellés plus le pas de 14 px dépassent la largeur
   utile de la carte (360 − 32 de marge − 32 de padding = 296 px) et
   poussaient une barre de défilement horizontale sur toute la page.
   C'est la famille de défaut que la maison connaît : jamais de `flex`
   sans `flex-wrap`. Le retour à la ligne garde « précédent » à gauche
   et « suivant » à droite tant que ça tient, et les empile sinon. */
.etapes-navigation {
    display: flex;
    flex-wrap: wrap;
    justify-content: space-between;
    gap: 14px;
    margin-top: 22px;
}
.btn-etape {
    font: inherit;
    font-weight: 600;
    padding: 11px 20px;
    border-radius: 8px;
    border: 1px solid var(--trait);
    background: #fff;
    color: var(--encre);
    cursor: pointer;
    transition: background .15s ease;
}
.btn-etape:disabled { opacity: .45; cursor: default; }
.btn-etape-suivant {
    background: var(--orange-fonce);
    border-color: var(--orange-fonce);
    color: #fff;
}
.btn-etape-suivant:hover { background: #93390b; }

/* ---- Petits écrans ----------------------------------------------- */
@media (max-width: 720px) {
    .entete-contenu { flex-wrap: wrap; gap: 12px; }
    .baseline { order: 3; width: 100%; }
    .contact-entete { text-align: left; }
    .deux-colonnes { grid-template-columns: 1fr; }
    /* [LOT 4-5] La taxonomie de largeur s'efface : un enfant qui
       garderait `span 4` dans une grille à UNE colonne forcerait des
       pistes implicites — la page déborderait au lieu de s'empiler.
       Cette règle vit APRÈS les classes champ-* dans la feuille : à
       spécificité égale (0,1,0), c'est l'ordre qui tranche, et c'est
       voulu — à 360 px, tout est pleine largeur, sans exception. */
    .deux-colonnes > * { grid-column: 1 / -1; }
    .cotes { grid-template-columns: 1fr 1fr; }
    .cartes-type, .cartes-type-5 { grid-template-columns: 1fr 1fr; }
    .portes-grille { grid-template-columns: 1fr; }
    .rassurance { grid-template-columns: 1fr; }
    .pied-contenu { grid-template-columns: 1fr; }
    .carte { padding: 20px 16px 24px; }
}

/* =====================================================================
   L'ESPACE DU CLIENT (14/08/2026)

   La barre d'etapes que M. Chokonte a demandee en montrant une
   infographie de suivi : VERT pour ce qui est franchi, gris pour ce
   qui vient. On reutilise la palette de la maison (--vert, --trait,
   --gris-doux) : aucune couleur nouvelle n'est introduite.

   ELLE NE MENT PAS. Une etape n'est verte que si un champ de la base
   la prouve — la photo poussee par l'intranet porte le drapeau, ce
   fichier ne fait que le peindre.
   ===================================================================== */

.etapes-suivi {
    list-style: none;
    margin: 0 0 1.4rem;
    padding: 0;
    display: flex;
    flex-wrap: wrap;
    gap: .5rem;
}

.etapes-suivi li {
    position: relative;
    padding: .45rem .85rem .45rem 2rem;
    border-radius: 999px;
    font-size: .92rem;
    line-height: 1.25;
    border: 1px solid var(--trait);
}

/* La pastille porte le sens ; la couleur seule ne suffirait pas a un
   lecteur daltonien ni a une impression en noir et blanc. */
.etapes-suivi li::before {
    position: absolute;
    left: .7rem;
    font-weight: 700;
}

.etape-franchie {
    background: var(--vert-doux);
    border-color: var(--vert);
    color: var(--vert);
}
.etape-franchie::before { content: "\2713"; }   /* coche */

.etape-a-venir {
    background: var(--carte);
    color: var(--gris-doux);
}
.etape-a-venir::before { content: "\00B7"; }    /* point median */

.table-suivi {
    width: 100%;
    border-collapse: collapse;
    margin: 0 0 1rem;
}
.table-suivi th,
.table-suivi td {
    text-align: left;
    padding: .4rem .6rem;
    border-bottom: 1px solid var(--trait);
    vertical-align: top;
}
.table-suivi th {
    width: 42%;
    font-weight: 600;
    color: var(--gris-doux);
}

/* Le numero que le client va COPIER chez la compagnie : espace pour
   qu'on puisse le lire caractere par caractere au telephone.

   [LOT 4-5] CETTE REGLE VIVAIT EN DEUX EXEMPLAIRES, a 130 lignes
   d'ecart : celle-ci et une seconde `.numero-a-copier` dans le bloc
   « copier un numero » du 16/08. Elles ne se contredisaient pas — elles
   se completaient, ce qui est pire : on ne voyait pas qu'il fallait
   lire les deux pour connaitre l'apparence du numero. C'est le motif du
   16/08, « un second mecanisme ecrit la ou un existait deja ». Les deux
   sont fondues ici, la seconde a disparu. */
.numero-a-copier {
    font-family: ui-monospace, "Cascadia Mono", Consolas, monospace;
    font-size: 1.15rem;
    font-weight: 700;
    letter-spacing: .06em;
    background: var(--creme);
    border: 1px solid var(--trait);
    border-radius: 6px;
    padding: .5rem .8rem;
    display: inline-block;
    /* Un numero de connaissement de 20 caracteres ne pousse pas la
       page hors de l'ecran a 360 px : il se replie. */
    overflow-wrap: anywhere;
    user-select: all;
}

/* Le code d'acces s'ecrit en majuscules — la page le met deja en
   majuscules cote serveur (`strtoupper`), l'oeil doit voir la meme
   chose que ce qui partira. C'etait le SEUL `style=` en ligne du
   guichet ; une regle nommee se contrôle, un attribut de style non. */
.saisie-majuscules { text-transform: uppercase; }

.liste-pieces {
    margin: 0 0 1rem;
    padding-left: 1.2rem;
}
.liste-pieces li { margin-bottom: .3rem; }

/* [FIX ALIGNEMENT GUICHET] « Quitter mon espace » est devenu un vrai
   bouton de formulaire (la sortie passe en POST : un lien en GET se
   declenchait tout seul depuis une page tierce). Il doit rester un LIEN
   A L'OEIL — corriger une faille ne doit pas fabriquer un defaut
   d'affichage. Le formulaire s'aligne dans la phrase, le bouton perd
   tout son habillage de bouton. */
.en-ligne {
    display: inline;
    margin: 0;
}
.lien-nu {
    background: none;
    border: 0;
    padding: 0;
    font: inherit;
    color: var(--bleu);
    text-decoration: underline;
    cursor: pointer;
}
.lien-nu:hover { text-decoration: none; }
/* (Le liseré de focus vivait ici en double — il est désormais porté une
   seule fois par la règle `button:focus-visible` du haut de feuille,
   avec l'orange foncé mesuré à 5,09:1.) */

@media (max-width: 640px) {
    .etapes-suivi { flex-direction: column; }
    .etapes-suivi li { width: 100%; }
    .table-suivi th { width: 45%; }
}

/* =====================================================================
   LA CORRESPONDANCE, LES DEUX SENS (03/09/2026, audit de M. Chokonté,
   vérifié)

   Le fil d'un dossier n'avait AUCUNE règle : .liste-messages,
   .message-client, .non-lu, .marque-non-lu, .message-ok et
   .message-erreur étaient émis par suivi.php depuis le 21/08 sans
   qu'une ligne de cette feuille les nomme — une liste à puces, un
   « nouveau » en texte nu, une confirmation qui ne se distinguait pas
   du paragraphe voisin. Et le client, lui, n'y apparaissait jamais.

   DEUX VOIX, DEUX BORDS. La maison : carte blanche, liseré bleu (celui
   des liens). Le client : fond crème, liseré orange foncé. Le sens ne
   repose jamais sur la couleur seule : chaque entrée est signée
   (« Vous », ou l'objet du message) et l'état est écrit en lettres.
   Les pastilles tiennent le seuil des 4,5:1 mesuré sur la palette :
   vert sur vert doux 4,73:1, gris doux sur la carte 6,39:1, encre sur
   la crème 13,6:1. Aucune couleur nouvelle : les jetons du haut de
   feuille, et eux seuls.
   ===================================================================== */
.liste-messages {
    list-style: none;
    margin: 0 0 1.2rem;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: .6rem;
}
.liste-messages li {
    background: var(--carte);
    border: 1px solid var(--trait);
    border-left: 5px solid var(--bleu);
    border-radius: 8px;
    padding: .7rem .9rem;
}
/* Ce que la maison a publié et que le client n'a pas encore ouvert :
   le liseré vire à l'orange, et la marque « nouveau » le dit.
   (Les deux variantes se qualifient par la liste : à poids égal,
   `.liste-messages li` l'emportait sur `.message-vous` seul et le
   client restait blanc à liseré bleu — mesuré sur maquette, 03/09.) */
.liste-messages .message-client.non-lu { border-left-color: var(--orange); }
/* Ce que le client a écrit : l'autre voix. */
.liste-messages .message-vous {
    background: var(--creme);
    border-left-color: var(--orange-fonce);
}
.message-entete {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    gap: .25rem .6rem;
    margin: 0 0 .35rem;
}
.message-entete strong { color: var(--noir); }
.message-corps {
    margin: 0;
    overflow-wrap: anywhere;
}
/* Les marques : de petites pastilles, comme les étapes du suivi. */
.marque-non-lu,
.marque-etat {
    display: inline-block;
    padding: .1rem .55rem;
    border-radius: 999px;
    font-size: .8rem;
    line-height: 1.4;
    border: 1px solid var(--trait);
    background: var(--carte);
    color: var(--gris-doux);
}
.marque-non-lu {
    background: var(--vert-doux);
    border-color: var(--vert);
    color: var(--vert);
    text-transform: uppercase;
    letter-spacing: .04em;
}
/* L'état d'un message du client : gris tant que la maison n'est pas
   passée le prendre, vert une fois transmis. Le mot change avec la
   couleur — jamais la couleur seule. */
.marque-etat.transmis {
    background: var(--vert-doux);
    border-color: var(--vert);
    color: var(--vert);
}
/* La confirmation et le refus du formulaire de réponse : les fonds de
   .confirmation et .erreurs, sans en répéter les blocs entiers. */
.message-ok,
.message-erreur {
    border-radius: 8px;
    padding: .7rem .9rem;
    margin: 0 0 1rem;
}
.message-ok {
    background: var(--vert-doux);
    border-left: 5px solid var(--vert);
}
.message-erreur {
    background: var(--rouge-doux);
    border-left: 5px solid var(--rouge);
}

/* =====================================================================
   [UX/UI UPGRADE] — 16/08/2026
   Zones tactiles, mouvement, impression, et l'habillage des gestes
   ajoutés au guichet. Aucune bibliothèque : tout est natif.
   ================================================================== */

/* ---- 1. LE DOIGT A UNE TAILLE ------------------------------------
   44 px est la cible minimale recommandée (WCAG 2.5.5). Les champs et
   boutons du guichet descendaient sous cette barre sur mobile : un
   bouton « Envoyer » raté, c'est une demande perdue. On agit par
   `min-height` et non par une hauteur fixe — un libellé qui se replie
   doit pouvoir grandir. */
@media (pointer: coarse), (max-width: 720px) {
    /* [LOT 4-5] TROIS CIBLES MANQUAIENT À L'APPEL, et ce ne sont pas
       les moindres. « + Ajouter un ou plusieurs fichiers » est un
       `<button type="button">` : il échappait au sélecteur
       `button[type="submit"]` et restait à 38 px (9 px de marge
       intérieure × 2 + 20 px de ligne) — c'est la porte des pièces
       jointes. `.bouton` porte « Voir mon dossier » et « Ouvrir le
       suivi » de l'espace client. Le dérouleur « Je ne sais pas quelle
       démarche choisir » de l'accueil tenait sur ses 25 px de ligne.

       Le commentaire se tient HORS de la liste de sélecteurs : une
       liste mal formée fait tomber la règle ENTIÈRE en silence, et un
       défaut de cette famille ne se voit qu'au doigt, sur place. */
    .bouton-envoi,
    .btn-etape,
    .liste-documents button,
    #bouton-documents,
    .bouton-photo,
    .bouton,
    .porte-doute summary,
    button[type="submit"],
    input[type="text"], input[type="tel"], input[type="email"],
    input[type="number"], input[type="date"], input[type="file"],
    select, textarea {
        min-height: 44px;
    }
    /* Le libellé d'un radio ou d'une case EST la zone cliquable : il
       doit être aussi confortable que le point à viser. */
    .choix-inline,
    .carte-type,
    .liste-documents li label {
        min-height: 44px;
    }
    .choix-inline { padding: 4px 0; }
    /* UNE CIBLE A DEUX CÔTÉS. Le bouton qui retire une pièce ne porte
       qu'un « ✕ » (`_commun.php`, `retirer.textContent = '✕'`) : 6 px
       de marge intérieure de chaque côté d'un glyphe d'une dizaine de
       pixels font ~22 px de large. La hauteur seule ne suffisait donc
       pas — on rate le bouton, ou on efface la pièce du voisin. */
    .liste-documents button { min-width: 44px; }
    /* Le dérouleur est un bloc : sa largeur suit la carte, seule sa
       hauteur manquait. On l'obtient par la marge intérieure — surtout
       PAS par `display:flex`, qui efface le triangle de repli dans les
       navigateurs Chromium et retirerait justement le signe qui dit
       « ça s'ouvre ». */
    .porte-doute summary { padding: 10px 0; }
    /* [LOT 4-5 §34] Le titre du résumé est LA poignée de la barre
       repliée du bas d'écran : même règle des 44 px, même moyen (la
       marge intérieure, pas une hauteur figée). */
    .resume-demande summary { padding: 10px 0; }
}

/* ---- 2. LE MOUVEMENT SE DEMANDE, IL NE S'IMPOSE PAS ---------------
   Un vestibulaire sensible ne « préfère » pas moins d'animation : il
   en est malade. Le réglage système fait foi, sans exception. */
@media (prefers-reduced-motion: reduce) {
    *, *::before, *::after {
        animation-duration: .001ms !important;
        animation-iteration-count: 1 !important;
        transition-duration: .001ms !important;
        scroll-behavior: auto !important;
    }
}

/* ---- 3. LE BOUTON QUI TRAVAILLE ----------------------------------
   Pendant l'envoi, le bouton se désactive et le dit. Le disque tourne
   par une animation CSS — donc il s'arrête tout seul quand le réglage
   ci-dessus s'applique, et le TEXTE reste : l'information n'est jamais
   portée par le seul mouvement. */
.bouton-envoi[aria-busy="true"] {
    opacity: .75;
    cursor: progress;
}
.disque-envoi {
    display: inline-block;
    vertical-align: -2px;
    margin-right: .5rem;
    animation: tourne 900ms linear infinite;
}
@keyframes tourne { to { transform: rotate(360deg); } }

/* ---- 4. LE VOLUME CALCULÉ EN DIRECT ------------------------------- */
.volume-estime {
    margin: 6px 0 0;
    padding: 8px 12px;
    background: var(--vert-doux);
    border-left: 3px solid var(--vert);
    border-radius: 4px;
    font-size: .92rem;
}
.volume-estime:empty { display: none; }
.volume-estime strong { color: var(--noir); }

/* ---- 5. COPIER UN NUMÉRO ------------------------------------------ */
.ligne-copie {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 8px;
}
/* (La seconde définition de `.numero-a-copier` vivait ici — fondue
   dans l'unique règle de la section « espace du client ».) */
.bouton-copier {
    font: inherit;
    font-size: .88rem;
    padding: 6px 12px;
    min-height: 44px;
    background: var(--carte);
    color: var(--bleu);
    border: 1px solid var(--trait);
    border-radius: 6px;
    cursor: pointer;
}
.bouton-copier:hover { background: var(--creme); }
/* (Idem : `button:focus-visible` couvre celui-ci.) */

/* ---- 5 bis. LE BOUTON D'ACTION EN LIGNE ----------------------------
   CE QUI A ÉTÉ MESURÉ. `grep -rn 'class="bouton"'` rend DEUX appels —
   « Voir mon dossier » et « Ouvrir le suivi … », tous deux dans
   suivi.php — et `grep` sur cette feuille rend ZÉRO définition. La
   classe était donc inerte depuis l'origine : le bouton d'entrée de
   l'espace client sortait au dessin brut du navigateur (gris système,
   ~30 px de haut), et le lien « Ouvrir le suivi » s'affichait en
   simple lien bleu alors que la page l'annonce comme un bouton.

   ON N'EN INVENTE PAS UN DE PLUS : `.bouton-envoi` est le bouton de
   pied de formulaire (bloc, pleine largeur) et `.btn-etape-suivant`
   appartient au parcours en étapes. Il manquait le bouton d'action
   EN LIGNE ; il reprend exactement les mêmes jetons — orange foncé sur
   blanc, mesuré 5,09:1 — et la cible de 44 px de la maison. */
.bouton {
    display: inline-block;
    min-height: 44px;
    padding: 11px 20px;
    font: inherit;
    font-weight: 700;
    color: #fff;
    background: var(--orange-fonce);
    border: 0;
    border-radius: 8px;
    text-decoration: none;
    cursor: pointer;
    transition: background .15s ease;
}
.bouton:hover { background: #93390b; }

/* ---- 6. LES ÉTAPES QUI SE SUCCÈDENT -------------------------------
   Une transition COURTE : elle adoucit, elle ne fait pas attendre. */
.etape {
    transition: opacity 180ms ease-out, transform 180ms ease-out;
}
.etape.etape-entrante {
    opacity: 0;
    transform: translateY(6px);
}
/* La légende de l'étape reçoit le focus au changement : sans le
   `tabindex` posé par le script, un lecteur d'écran resterait sur le
   bouton « Suivant » et n'annoncerait rien de la nouvelle étape. Le
   liseré ne doit pas pour autant ressembler à un champ actif. */
.etape legend:focus { outline: none; }
.etape legend:focus-visible {
    outline: 3px solid var(--orange-fonce);
    outline-offset: 4px;
}

/* ---- 7. LE PAPIER -------------------------------------------------
   Une confirmation ou un suivi finit souvent imprimé et glissé dans un
   dossier. Ce qui ne sert qu'à l'écran disparaît ; ce qui fait foi
   reste. LES ÉTAPES SE LISENT EN NOIR ET BLANC : la barre de suivi
   colorée est doublée d'un mot, sinon une photocopie ne dit plus rien.
   (L'intranet a sa propre feuille d'impression — on ne la duplique
   pas, ces deux applications ne partagent aucun fichier.) */
@media print {
    /* [LOT 4-5] DEUX SÉLECTEURS NE DÉSIGNAIENT RIEN, et un troisième
       en cachait trop.

       `.bandeau` : aucune page n'émet cette classe — le bandeau sombre
       s'appelle `.bandeau-sombre` (grep : 1 émission dans _commun.php,
       0 pour `.bandeau`). Le bandeau noir partait donc à l'encre sur
       toutes les impressions.

       `.txt-note` : c'est la classe qui porte « Situation au 16/08 à
       09:12 » en bas de chaque dossier de l'espace client — la seule
       phrase qui dit au lecteur que sa feuille est une PHOTO DATÉE et
       non l'état du jour. La masquer à l'impression fabriquait un
       papier sans date, c'est-à-dire un papier qui ment par omission.
       Elle reste, en encre lisible. Les notes d'aide des formulaires
       disparaissent de toute façon avec leur `form`. */
    .entete, .pied, .bandeau-sombre, nav,
    form, .bouton-envoi, .btn-etape, .bouton-copier,
    .liste-documents button, .en-ligne,
    .volume-estime, .resume-demande {
        display: none !important;
    }
    .txt-note { color: #000; }
    body {
        background: #fff;
        color: #000;
        font-size: 11pt;
    }
    main { max-width: none; margin: 0; padding: 0; }
    .carte {
        border: 1px solid #000;
        box-shadow: none;
        padding: 10pt 12pt;
        /* Ni une carte ni un tableau ne se coupe en deux pages. */
        break-inside: avoid;
        page-break-inside: avoid;
    }
    .table-suivi, .table-suivi tr { break-inside: avoid; }
    .table-suivi th, .table-suivi td { border: 1px solid #666; }
    .etapes-suivi { display: block; }
    .etapes-suivi li {
        width: auto;
        background: none;
        border: 0;
        padding: 2pt 0;
    }
    /* Le mot avant la couleur : « franchie » / « à venir » sortent en
       toutes lettres, la pastille colorée ne suffit pas au papier.

       [LOT 4-5] LA MOITIÉ DE CETTE RÈGLE ÉTAIT MORTE. Elle visait
       `.etape-faite` ; suivi.php n'émet que `etape-franchie` ou
       `etape-a-venir` (une seule branche, ligne 200). Résultat mesuré :
       à l'impression, « à venir » s'écrivait et « franchie » non — et
       comme le fond coloré disparaît aussi au papier, une étape
       franchie devenait une étape sans mention, donc indistinguable
       d'une ligne neutre. Exactement le défaut que cette règle
       prétendait corriger. */
    .etape-franchie::after { content: " — franchie"; }
    .etape-a-venir::after { content: " — à venir"; }
    a[href^="http"]::after { content: " (" attr(href) ")"; font-size: 9pt; }
}

/* ------------------------------------------------------------------
   LE RÉCAPITULATIF AVANT ENVOI (lot 4-5)

   Le guichet envoyait sans montrer ce qu'il envoie. Le demandeur
   remplissait cinq blocs, cliquait, et voyait une référence : aucun
   moyen de vérifier, aucun moyen de se rappeler. La relecture est le
   geste le moins cher qui évite le plus d'allers-retours.

   IL NE S'AFFICHE QUE SI JAVASCRIPT RÉPOND. Sans lui, le formulaire
   part comme avant : une relecture qui EMPÊCHERAIT d'envoyer serait
   pire que pas de relecture, sur un guichet public qu'on rencontre
   depuis des téléphones anciens. ------------------------------------ */
.voile-recap {
    position: fixed;
    inset: 0;
    background: rgba(17, 24, 28, .62);
    display: flex;
    /* Le voile n'a qu'un enfant, mais la règle de la maison ne souffre
       pas d'exception : jamais de `flex` sans `flex-wrap`. Le jour où
       un second élément s'y glisse, il se replie au lieu d'écraser. */
    flex-wrap: wrap;
    align-items: center;
    justify-content: center;
    padding: 1rem;
    z-index: 60;
    overflow-y: auto;
}

.recap {
    background: #fff;
    border-radius: 12px;
    padding: 1.4rem 1.5rem;
    max-width: 34rem;
    width: 100%;
    max-height: 88vh;
    overflow-y: auto;
    box-shadow: 0 12px 40px rgba(0, 0, 0, .28);
}

.recap h2 { margin: 0 0 .9rem; font-size: 1.15rem; }

.recap-liste {
    margin: 0 0 1.2rem;
    display: grid;
    /* Deux colonnes sur grand écran, UNE seule dès qu'on manque de
       place : un récapitulatif illisible sur téléphone ne serait pas
       relu, et c'est justement là qu'on remplit ces formulaires. */
    grid-template-columns: minmax(9rem, 12rem) 1fr;
    gap: .35rem .9rem;
}

.recap-liste dt { color: #5a6a72; font-size: .92rem; }
.recap-liste dd {
    margin: 0;
    font-weight: 600;
    /* Une adresse ou une référence longue ne doit pas élargir la boîte
       au-delà de l'écran. */
    overflow-wrap: anywhere;
}

@media (max-width: 30rem) {
    .recap-liste { grid-template-columns: 1fr; gap: .1rem .9rem; }
    .recap-liste dd { margin-bottom: .55rem; }
}

.recap-gestes {
    display: flex;
    flex-wrap: wrap;
    gap: .7rem;
    justify-content: flex-end;
}

/* LE GESTE DE RETOUR EXISTE, ET IL EST AUSSI ATTEIGNABLE QUE L'AUTRE.
   Un récapitulatif d'où l'on ne peut que confirmer n'est pas une
   relecture, c'est un péage. Les deux boutons gardent la cible de
   44 px de la maison. */
.recap-gestes button {
    min-height: 44px;
    padding: .6rem 1.2rem;
    border-radius: 8px;
    font: inherit;
    font-weight: 600;
    cursor: pointer;
}

.bouton-secondaire {
    background: #fff;
    border: 1.5px solid #b9c6cc;
    color: #23323a;
}

.bouton-secondaire:hover { background: #f2f6f7; }

@media (prefers-reduced-motion: reduce) {
    .voile-recap, .recap { animation: none; transition: none; }
}

/* ------------------------------------------------------------------
   [LOT 4-5 §34] LE RÉSUMÉ « VOTRE DEMANDE » — transporter.php.

   Le parcours en étapes montre UN écran à la fois : au moment des
   documents, le trajet saisi deux écrans plus tôt est hors de vue.
   Ce panneau rejoue ce qui est DÉJÀ saisi, rien d'autre. C'est un
   seul <details> qui prend DEUX postures :

   · ≥ 1148 px — colonne épinglée à droite du formulaire, dépliée par
     le script. Le seuil n'est pas un goût : 828 px de formulaire (la
     largeur EXACTE d'aujourd'hui, celle dont la taxonomie de largeur
     déduit ses pas de 44 px) + 24 px d'écart + 264 px de colonne
     + 32 px de marges du main = 1148. Le <main> de la page s'élargit
     à ce total (classe avec-resume) : le formulaire ne cède PAS un
     pixel — c'est la condition pour toucher à cette page. La colonne
     est réservée même vide : la première ligne saisie ne pousse pas
     le formulaire.

   · en dessous — barre repliée collée au BAS de l'écran (sticky), le
     geste connu des paniers de commande : le titre reste visible, le
     détail vient au toucher, et une fois le formulaire dépassé la
     barre se range à sa place dans le flux.

   Sans JavaScript, le panneau reste [hidden] : il n'existe pas. --- */
.resume-demande {
    background: var(--carte);
    border: 1px solid var(--trait);
    border-radius: 10px;
    padding: 12px 16px 14px;
    box-shadow: 0 2px 10px rgba(27, 27, 31, .07);
}
.resume-demande summary {
    cursor: pointer;
    font-weight: 700;
    color: var(--orange-fonce);
}
.resume-liste { margin: 8px 0 0; }
/* Le gris des notes (4,81:1 sur le fond des champs, seul de la
   famille au-dessus de 4,5:1) — on n'en invente pas un de plus. */
.resume-liste dt { color: #6c6f78; font-size: .85rem; margin-top: 7px; }
.resume-liste dd {
    margin: 0;
    font-weight: 600;
    /* Une adresse e-mail ou une ville longue ne pousse pas la colonne
       de 264 px hors de l'écran : elle se replie. */
    overflow-wrap: anywhere;
}

@media (min-width: 1148px) {
    main.avec-resume { max-width: 1148px; }
    /* LES PALIERS DE LARGEUR VALENT AUSSI ICI (20/08). Les 1 148 px ont
       ete CALCULES pour que le formulaire ne cede pas un pixel a la
       colonne du resume (828 + 24 + 264 + 32). Mais cette regle est
       plus specifique que le palier general : la page de tache restait
       etroite pendant que l'accueil s'elargissait — 772 px de vide
       mesures a 1 920. Le formulaire gagne desormais ce que l'ecran
       offre ; la colonne du resume garde ses 264 px, et le formulaire
       ne perd toujours rien. La declaration vit APRES celle qu'elle
       corrige : a specificite egale, l'ordre tranche. */
    .corps-demarche {
        display: grid;
        /* minmax(0, 1fr) et non 1fr : un contenu insécable ne force
           jamais la colonne au-delà de sa piste. */
        grid-template-columns: minmax(0, 1fr) 16.5rem;
        gap: 0 24px;
        align-items: start;
    }
    .corps-demarche > .erreurs,
    .corps-demarche > form { grid-column: 1; }
    .corps-demarche > .resume-demande {
        grid-column: 2;
        /* La zone du panneau court sur les deux rangées possibles
           (erreurs + formulaire) : c'est DANS cette zone que sticky
           a le droit de glisser. */
        grid-row: 1 / span 2;
        position: sticky;
        top: 14px;
    }
}

@media (max-width: 1147.98px) {
    .resume-demande {
        position: sticky;
        bottom: 0;
        margin-top: 18px;
        border-radius: 10px 10px 0 0;
        box-shadow: 0 -3px 12px rgba(27, 27, 31, .14);
        /* Sous le voile du récapitulatif (60) : la relecture finale
           passe devant le rétroviseur. */
        z-index: 40;
    }
    /* Déplié sur un téléphone, le détail ne recouvre pas tout
       l'écran : il défile dans sa moitié basse. */
    .resume-liste { max-height: 45vh; overflow-y: auto; }
}

/* ------------------------------------------------------------------
   [LOT 4-5 §37] LA VALIDATION INLINE — l'habillage.

   Le message vit SOUS le champ (span créé vide par le script du
   socle, aria-live) ; il reprend le rouge de la palette : #d0212a
   mesure 5,3:1 sur le blanc de la carte et 5,1:1 sur le fond des
   champs — au-dessus des 4,5:1 du texte courant. Le label est à 600 :
   sans le 400 explicite, le reproche crierait plus fort que la
   question. ---------------------------------------------------------- */
.message-champ {
    display: block;
    color: var(--rouge);
    font-size: .88rem;
    font-weight: 400;
    margin-top: 4px;
}
.message-champ:empty { display: none; }
/* Le bord du champ signalé — DEUX écritures pour DEUX mondes, même
   trait. `aria-invalid` est posé par l'annonce inline (elle seule
   sait ce que le SERVEUR refuse) ; `:user-invalid` est le verdict
   NATIF du navigateur (required, type, pattern) après interaction —
   il travaille aussi sans notre script. La règle native vit SEULE :
   un navigateur qui ignore ce sélecteur jetterait toute liste qui le
   contient, et elle emporterait la règle aria avec elle. */
input[aria-invalid="true"], textarea[aria-invalid="true"] {
    border-color: var(--rouge);
}
input:user-invalid {
    border-color: var(--rouge);
}
select:user-invalid {
    border-color: var(--rouge);
}
textarea:user-invalid {
    border-color: var(--rouge);
}

/* [LOT 4-5 §37] La légende de l'astérisque ouvre chaque formulaire
   (bloc_jeton_et_piege) : elle perd la marge haute des notes — rien
   ne la précède — et garde un petit pas avant le premier bloc. */
.note-obligatoire { margin: 0 0 6px; }

/* Suite du palier de largeur : la page a resume epingle (voir le bloc
   @media 1148 ci-dessus). Ecrit en fin de feuille pour passer APRES
   `main.avec-resume { max-width: 1148px }`, de meme specificite. */
@media (min-width: 1400px) {
    main.avec-resume { max-width: 1180px; }
}
@media (min-width: 1750px) {
    main.avec-resume { max-width: 1320px; }
}
