/* ════════════════════════════════════════════════════════════════════
   AMÉLIORATIONS DU 13/09 — chargé APRÈS styles.css, il le complète.
   Tout ce qui a changé ce jour-là est ici : il se lit d'un trait et se
   retire d'un coup (retirer la ligne <link> dans index.html).
   Sources : analyse-21tsi-2026-09-13 et ses consignes du même soir.
   ════════════════════════════════════════════════════════════════════ */


/* ── LES DEUX AGENCEMENTS — SA RÈGLE ────────────────────────────────
   « Pas de justification ni d agencement à droite. » Un bloc est :
     · À GAUCHE, aligné à gauche, sur un panneau flou à gauche ;
     · ou CENTRÉ ET POSÉ EN BAS, SANS fond flou (sa consigne du 14/09) —
       seulement un voile qui monte du bas, pour que le texte reste lisible.
   Les étapes qui portent leur propre grille (« large ») restent à gauche.
   ⚠️ Les marges des enfants sont forcées : plusieurs sont posées en ligne
   par le script (`style.margin = '… 0 …'`) et remettraient le bloc à gauche. */
.etape[data-zone="centre"] { grid-template-rows: 1fr auto 0fr; padding-bottom: calc(var(--f7) + var(--f4)); }
.etape[data-zone="centre"] > .dedans { max-width: min(var(--colonne), 64%); margin: 0 auto; text-align: center; }
.etape[data-zone="centre"] > .dedans > * { margin-left: auto !important; margin-right: auto !important; }
/* 18/09 : les étiquettes aussi — la 2ᵉ ligne (« Rencontres ») restait calée à gauche */
.etape[data-zone="centre"] .rangee,
.etape[data-zone="centre"] .etiquettes { justify-content: center; }
.etape[data-zone="centre"] .devise { padding-left: 0; border-left: 0; }
@media (max-width: 1000px) {
  .etape[data-zone="centre"] > .dedans { max-width: var(--colonne); }
}

/* LE PANNEAU FLOU — la règle de la référence (21tsi `.panel`, flou 20 px),
   derrière les blocs À GAUCHE seulement. Le script ajuste sa largeur au
   bloc affiché, une fois par étape. Constant tant que le bloc est là. */
#panneau {
  left: 0; right: auto; width: 64vw;
  /* 35 % et non 14 % : audit d accessibilité du 13/09 — le script retire le
     voile de lisibilité derrière ces blocs ; à 14 % un texte blanc sur une
     photo claire tombait vers 3,1:1 (seuil 4,5:1). Calculé à ~4,8:1. */
  background: color-mix(in srgb, var(--noir) 35%, transparent);
  clip-path: polygon(0 0, 0 0, 0 100%, 0 100%);
  transition: clip-path 1.2s cubic-bezier(0.19, 1, 0.22, 1), width .8s cubic-bezier(0.19, 1, 0.22, 1);
}
#panneau.actif { clip-path: polygon(0 0, 100% 0, 100% 100%, 0 100%); }
/* (14/09 : le bandeau flou des blocs centrés, #panneau-bas, est retiré —
   sa consigne : « les éléments centrés, pas de fond flou ».) */
@media (max-width: 1000px) {
  #panneau { display: block; }
  #panneau { width: 100vw !important; }
}


/* ── UNE SEULE VOIX ─────────────────────────────────────────────────
   21tsi : une famille, casse normale (286 textes sur 295), graisse fine
   (300 sur 222). Titres et grands textes quittent capitales et gras ;
   petites étiquettes, rubriques et boutons les gardent, comme là-bas. */
.titre { text-transform: none; font-weight: 300; letter-spacing: -.03em; line-height: 1.02; }
.titre b { font-weight: 500; }
.sous { text-transform: none; font-weight: 400; letter-spacing: -.02em; line-height: 1.1; }
.devise { text-transform: none; font-weight: 300; letter-spacing: -.015em; line-height: 1.22; }
.fait b, .vie b, .famille-geant b, .famille-nom, .cours-tete h4, .salle b, .coach-corps h3,
.compris > div, .question h3, .grille-jour > b, .marche > b, .dossier-nom, .repli h1, .repli h2 {
  text-transform: none; font-weight: 400; letter-spacing: -.015em;
}
.creneau-nom { text-transform: none; font-weight: 500; letter-spacing: 0; }
.chiffre b, .tarif-geant b, .prix b { font-weight: 300; }
.gal-nom, .parcours-ligne b { font-weight: 500; }
#ch-nombre, .marche > .micro, .fente-lettre { font-weight: 200; }
.ch-sigle, .marque-nom { font-weight: 700; }
.lien { font-weight: 600; }
.lien.ici { font-weight: 700; }
.pastille { font-weight: 600; }
.texte { line-height: 1.42; }


/* ── LE CARTOUCHE DANS LES PAGES DE FIN ─────────────────────────────
   Mesuré : le formulaire défilait SOUS les rubriques. Dans la suite, le
   cartouche prend un fond flou. */
#cartouche::after {
  content: ''; position: absolute; inset: calc(-1px - var(--sommet)) 0 auto 0; z-index: -1;
  /* bottom et non height : sous 1100 px le cartouche est en hauteur auto,
     une hauteur fixe laissait son bas découvert (audit du 13/09) */
  bottom: calc(-1 * var(--f3));
  background: color-mix(in srgb, var(--noir) 55%, transparent);
  -webkit-backdrop-filter: blur(20px); backdrop-filter: blur(20px);
  border-bottom: 1px solid var(--filet);
  opacity: 0; visibility: hidden; pointer-events: none;
  transition: opacity .5s var(--gout), visibility 0s linear .5s;
}
html.dans-la-suite #cartouche::after { opacity: 1; visibility: visible; transition: opacity .5s var(--gout), visibility 0s; }


/* ── LE REPÈRE D AVANCEMENT ─────────────────────────────────────────
   « 01 ──── 05 » en bas à gauche : l étape en cours dans l écran, et
   combien il y en a. 26 étapes, et rien ne disait où l on en était. */
#repere {
  position: fixed; left: var(--marge); bottom: calc(var(--f5) + env(safe-area-inset-bottom, 0px)); z-index: 40;
  display: flex; align-items: center; gap: var(--f3); pointer-events: none;
  font: 600 var(--t1)/1 var(--police); letter-spacing: .14em; text-transform: uppercase;
  color: var(--ivoire); font-variant-numeric: tabular-nums;
  transition: opacity .5s var(--gout);
}
.repere-barre { position: relative; width: clamp(64px, 11vw, 170px); height: 1px; background: var(--filet); overflow: hidden; }
.repere-barre i { position: absolute; inset: 0; background: var(--terra); transform: scaleX(0); transform-origin: left center; }
.repere-t, .repere-nom { color: var(--ivoire); }   /* --faible sur photo : ~2,1:1, relevé par l audit */
.repere-nom { margin-left: var(--f2); }
html.dans-la-suite #repere, html.menu-ouvert #repere, #repere.discret { opacity: 0; }
/* pas de repère tant que l écran de chargement est là (relevé par l audit
   UI/UX du 14/09 : à 390 px « 01 — 03 » passait sur « Préparation de la séance ») */
#chargement:not(.parti) ~ #repere { opacity: 0; visibility: hidden; }
html:not(.anime) #repere, html.vue-simple #repere { display: none; }


/* ── LE CADRAN ──────────────────────────────────────────────────────
   La signature de la référence — des cercles gradués qui tournent, un
   chiffre qui défile — dessinée en cadran de chronomètre, au CENTRE (sa
   règle : rien à droite). Au-dessus des photos, sous le texte. */
#cadran {
  position: absolute; left: 50%; top: 50%; width: min(92vmin, 860px); height: auto; aspect-ratio: 1;
  transform: translate(-50%, -50%); overflow: hidden; pointer-events: none; opacity: .5;
  /* overflow: hidden — le cercle et son chiffre tiennent dans la boîte
     (rayon 105 sur 110). ⚠️ Soupçonné le 13/09 d élargir la page du
     téléphone : FAUX, vérifié par élimination (cadran masqué, la page
     restait à 595 px). Le coupable était la grille des pages de fin, plus bas. */
  transition: opacity .8s var(--gout);
}
.cadran-tourne { transform-box: view-box; transform-origin: 50% 50%; will-change: transform; }
.cadran-cercle { fill: none; stroke: color-mix(in srgb, var(--ivoire) 34%, transparent); stroke-width: .45; }
.cadran-cercle--int { stroke-dasharray: 1.5 3; }
.cadran-trait { stroke: color-mix(in srgb, var(--ivoire) 42%, transparent); stroke-width: .45; }
.cadran-croix { stroke: var(--ivoire); stroke-width: .6; }
.cadran-chiffre { fill: var(--ivoire); font: 500 5.5px var(--police); letter-spacing: .08em; }
html.dans-la-suite #cadran { opacity: .15; }
@media (max-width: 720px) { #cadran { width: 100vw; opacity: .28; } }


/* ── LA DEVISE, MOT À MOT ───────────────────────────────────────────
   Repris du manifeste de la référence : chaque mot s allume l un après
   l autre, sur la cascade de son étape. ⚠️ La fenêtre est calculée sur
   ce qui RESTE de la cascade (1 − --d) : un mot dont le départ tomberait
   après --e = 1 resterait éteint pour toujours — erreur déjà commise une
   fois sur ce site (voir LIRE-MOI, « la contrainte qui commande le calcul »). */
.devise .mm { display: inline-block; }
html.anime .devise .mm {
  --reste-d: calc(1 - var(--d, 0));
  --a: clamp(0, calc((var(--e, 0) - var(--d, 0) - var(--i, 0) * var(--reste-d) * .55) / max(.08, calc(var(--reste-d) * .3))), 1);
  opacity: calc(.16 + .84 * var(--a));
}
html.anime .etape.bouge .devise .mm { filter: blur(calc((1 - var(--a)) * 10px)); }


/* ── LES BOUTONS AIMANTÉS ───────────────────────────────────────────
   `translate` est une propriété à part : elle ne se bat pas avec les
   `transform` de l animation d entrée. Posée par le script, souris seule. */
.bouton { transition: color .45s var(--gout), border-color .45s var(--gout), translate .5s cubic-bezier(0.19, 1, 0.22, 1); }
.pastille { transition: border-color .45s var(--gout), color .45s var(--gout), translate .5s cubic-bezier(0.19, 1, 0.22, 1); }
/* la flèche suit le pointeur un peu plus que son bouton : de la profondeur */
.bouton .fleche, .pastille .fleche {
  translate: calc(var(--ax, 0) * 5px) calc(var(--ay, 0) * 4px);
  transition: transform .5s var(--gout), translate .5s cubic-bezier(0.19, 1, 0.22, 1);
}


/* ── LE CURSEUR « CIBLE DE FRAPPE » (14/09) ─────────────────────────
   Posé par le script, à la souris seulement (voir brancheCurseur). L anneau
   est la patte d ours, le point est le poing. Trois propriétés distinctes
   qui se composent sans se marcher dessus : la POSITION en `translate`,
   l ÉTIREMENT de vitesse en `transform`, la PRESSION du clic en `scale`. */
html.curseur-actif, html.curseur-actif * { cursor: none !important; }
html.curseur-actif :is(input:not([type="checkbox"]):not([type="radio"]), textarea) { cursor: text !important; }
html.curseur-actif video { cursor: auto !important; }

#curseur { position: fixed; left: 0; top: 0; width: 0; height: 0; z-index: 400; pointer-events: none; transition: opacity .25s ease; }
#curseur.cache, html:not(.curseur-actif) #curseur { opacity: 0; }

.cur-anneau {
  position: absolute; left: 0; top: 0; width: 38px; height: 38px; box-sizing: border-box;
  display: grid; place-items: center;
  border: 1.5px solid color-mix(in srgb, var(--ivoire) 80%, transparent); border-radius: 50%;
  transition: scale .5s cubic-bezier(.34, 1.56, .64, 1), border-color .3s ease, background-color .3s ease, opacity .3s ease;
}
/* les quatre repères : midi, trois, six et neuf heures — la cible et le chrono */
.cur-anneau i { position: absolute; inset: 0; rotate: calc(var(--n) * 90deg); transition: rotate .55s var(--gout), opacity .3s ease; }
.cur-anneau i::before {
  content: ''; position: absolute; left: 50%; top: -8px;
  width: 1.5px; height: 5px; margin-left: -.75px; background: var(--ivoire); transition: background-color .3s ease;
}
.cur-point {
  position: absolute; left: -3px; top: -3px; width: 6px; height: 6px;
  border-radius: 50%; background: var(--terra);
  transition: scale .3s var(--gout), opacity .2s ease;
}
.cur-mot { font: 700 var(--t1)/1 var(--police); letter-spacing: .14em; text-transform: uppercase; color: var(--sur-terra); opacity: 0; transition: opacity .25s ease; }

/* sur un lien : l anneau grossit, se teinte, et ses repères pivotent en croix */
#curseur[data-etat="clic"] .cur-anneau { border-color: var(--terra); background-color: color-mix(in srgb, var(--terra) 14%, transparent); }
#curseur[data-etat="clic"] .cur-anneau i { rotate: calc(var(--n) * 90deg + 45deg); }
#curseur[data-etat="clic"] .cur-anneau i::before { background: var(--terra); }
/* sur un bouton : l anneau épouse sa forme, le poing se range */
#curseur[data-etat="colle"] .cur-anneau { border-color: var(--terra); }
#curseur[data-etat="colle"] .cur-point,
#curseur[data-etat="voir"] .cur-point { scale: 0; }
#curseur:is([data-etat="colle"], [data-etat="voir"]) .cur-anneau i { opacity: 0; }
/* sur une image de la bibliothèque : une pastille pleine qui dit « Voir » */
#curseur[data-etat="voir"] .cur-anneau { border-color: var(--terra); background-color: var(--terra); }
#curseur[data-etat="voir"] .cur-mot { opacity: 1; }
#curseur[data-etat="bloque"] .cur-anneau { border-style: dashed; opacity: .5; }
#curseur[data-etat="natif"] :is(.cur-anneau, .cur-point) { opacity: 0; }
/* l appui : l anneau encaisse, le poing grossit */
#curseur.appuye .cur-anneau { scale: .7; transition-duration: .09s; }
#curseur.appuye .cur-point { scale: 1.8; }

/* l impact : une onde et huit éclats, comme un coup dans la patte */
.cur-impact { position: absolute; left: 0; top: 0; width: 0; height: 0; }
/* ⚠️ MESURÉ LE 14/09 (animation figée, agrandie ×4) : avec une accélération
   « expo », tout le trajet se faisait dans les 100 premières ms et l impact
   était déjà presque transparent à 140 ms — les éclats n étaient que des
   points. L opacité TIENT maintenant jusqu à la moitié, le trajet est plus
   long et les éclats plus épais. */
.cur-impact::before {
  content: ''; position: absolute; left: -16px; top: -16px; width: 32px; height: 32px; box-sizing: border-box;
  border: 2px solid var(--terra); border-radius: 50%;
  animation: cur-onde .6s ease-out forwards;
}
.cur-impact i {
  position: absolute; left: -1.5px; top: 0; width: 3px; height: 12px; border-radius: 3px;
  background: var(--terra); transform-origin: 1.5px 0; rotate: calc(var(--n) * 45deg + 22.5deg);
  animation: cur-eclat .55s ease-out forwards;
}
.cur-impact--fort i { height: 16px; }
.cur-impact--fort::before { animation-duration: .75s; }
@keyframes cur-eclat {
  0%   { transform: translateY(14px) scaleY(1);  opacity: 1; }
  50%  { transform: translateY(30px) scaleY(.9); opacity: 1; }
  100% { transform: translateY(42px) scaleY(.2); opacity: 0; }
}
@keyframes cur-onde {
  0%   { scale: .4;  opacity: 1; }
  45%  { scale: 1.5; opacity: .85; }
  100% { scale: 2.4; opacity: 0; }
}


/* ── LE MENU DU TÉLÉPHONE ───────────────────────────────────────────
   Mesuré à 390 px : la marque passait sur deux lignes, sur « Accueil »,
   et « Contact » sortait de l écran. Sous 1000 px, les six rubriques
   s ouvrent en plein écran : même flou que les panneaux, entrée en 0,8 s
   (la courbe de la référence), rubriques en cascade. Fermé, le menu est
   `visibility: hidden` : hors du clavier et du lecteur d écran. */
#p-menu { display: none; }
.menu-traits { position: relative; width: 16px; height: 8px; }
.menu-traits i { position: absolute; left: 0; right: 0; height: 1.5px; background: currentColor;
  transition: transform .5s cubic-bezier(0.19, 1, 0.22, 1), top .5s cubic-bezier(0.19, 1, 0.22, 1); }
.menu-traits i:first-child { top: 0; }
.menu-traits i:last-child { top: 6.5px; }
html.menu-ouvert .menu-traits i:first-child { top: 3.25px; transform: rotate(45deg); }
html.menu-ouvert .menu-traits i:last-child { top: 3.25px; transform: rotate(-45deg); }

@media (max-width: 1000px) {
  :root { --haut: 76px; }
  .cartouche-dedans { grid-template-columns: auto minmax(0, 1fr) auto; }
  .marque, .pastilles { position: relative; z-index: 2; }
  #p-langue, #p-theme, #p-contact { display: none; }
  #p-menu { display: inline-flex; }

  #nav {
    position: fixed; inset: 0; z-index: 1; order: initial; grid-column: auto;
    display: flex; flex-direction: column; justify-content: center; align-items: flex-start; gap: var(--f2);
    padding: calc(var(--haut) + var(--f5)) var(--marge) calc(var(--f7) + 64px);
    overflow: auto;
    background: color-mix(in srgb, var(--noir) 55%, transparent);
    -webkit-backdrop-filter: blur(20px); backdrop-filter: blur(20px);
    clip-path: polygon(0 0, 0 0, 0 100%, 0 100%);
    visibility: hidden;
    transition: clip-path .8s cubic-bezier(0.19, 1, 0.22, 1), visibility 0s linear .8s;
  }
  html.menu-ouvert #nav {
    clip-path: polygon(0 0, 100% 0, 100% 100%, 0 100%); visibility: visible;
    transition: clip-path .8s cubic-bezier(0.19, 1, 0.22, 1), visibility 0s;
  }
  #nav .lien {
    min-height: 48px; font-size: var(--t7); font-weight: 300; letter-spacing: -.02em; text-transform: none;
    opacity: 0; transform: translateY(24px);
    transition: color .45s var(--gout), opacity .6s var(--gout), transform .8s cubic-bezier(0.19, 1, 0.22, 1);
  }
  #nav .lien.ici { font-weight: 500; }
  html.menu-ouvert #nav .lien { opacity: 1; transform: none; transition-delay: calc(.12s + var(--i, 0) * 60ms); }

  /* menu ouvert : les trois pastilles descendent en bas de l écran, à
     gauche ; le bouton de fermeture reste là où le doigt vient de toucher */
  html.menu-ouvert .pastilles {
    position: fixed; left: var(--marge); right: var(--marge); bottom: calc(var(--f5) + env(safe-area-inset-bottom, 0px));
    z-index: 3; flex-wrap: wrap; justify-content: flex-start;
  }
  html.menu-ouvert #p-langue, html.menu-ouvert #p-theme, html.menu-ouvert #p-contact { display: inline-flex; }
  html.menu-ouvert #p-menu { position: fixed; top: var(--f2); right: var(--marge); }
  html.menu-ouvert { overflow: hidden; }
}


/* ── « UN KLUB, PAS UNE SALLE DE SPORT » : PLUS DE CARTE ORPHELINE (15/09)
   Ses mots : « le week-end sportif tout seul en bas, ce n est pas joli ».
   En auto-fit, les cinq cartes tombaient en 3 + 2 et laissaient une case
   vide à droite. Maintenant trois en haut, deux en bas qui prennent toute
   la largeur : une composition voulue, sans trou. */
@media (min-width: 721px) {
  .vie:has(> div:nth-child(5):last-child) { grid-template-columns: repeat(6, minmax(0, 1fr)); }
  .vie:has(> div:nth-child(5):last-child) > div { grid-column: span 2; }
  .vie:has(> div:nth-child(5):last-child) > div:nth-child(n+4) { grid-column: span 3; }
}
.etape[data-zone="centre"] .vie > div { padding-inline: var(--f3); }


/* ── LES SOUS-SECTIONS DES RUBRIQUES (15/09) ────────────────────────
   Un clic sur une rubrique ouvre la liste de ses étapes (voir
   brancheSousMenus). Bureau : elle tombe sous la rubrique, sur le flou des
   panneaux. Téléphone : elle se déplie dans le menu plein écran. */
/* ⚠️ MESURÉ LE 15/09 : posée dans le flux, la flèche ajoutait 12 px par
   rubrique et la barre débordait de 14 px à 1440. Elle est posée à côté du
   mot, sans prendre de place : la barre garde sa largeur d avant. */
/* ⚠️ VU SUR LA CAPTURE LE 15/09 : une flèche à mi-hauteur touchait le point
   de la rubrique en cours, posé à gauche de la suivante (« ACCUEIL ⌄• KLUB »).
   Le signe est donc un « + » en EXPOSANT, en haut du mot, là où le point
   n est pas ; il pivote en « × » quand la liste est ouverte. */
.lien::after {
  content: ''; position: absolute; left: calc(100% + 3px); top: 1px;
  width: 7px; height: 7px; pointer-events: none;
  background: linear-gradient(currentColor, currentColor) center / 100% 1.5px no-repeat,
              linear-gradient(currentColor, currentColor) center / 1.5px 100% no-repeat;
  opacity: .6;
  transition: transform .45s var(--gout), opacity .3s ease;
}
.lien[aria-expanded="true"] { color: var(--ivoire); }
.lien.ici[aria-expanded="true"] { color: var(--terra); }
.lien[aria-expanded="true"]::after { transform: rotate(135deg); opacity: 1; }

.sous-menu { display: none; }
.sous-lien {
  display: grid; grid-template-columns: 2.2em minmax(0, 1fr); align-items: baseline; align-content: center; column-gap: var(--f2);
  min-height: 44px; padding: 11px var(--f4);
  font: 400 var(--t3)/1.3 var(--police); color: var(--sourd);
  transition: color .3s ease, background-color .3s ease;
}
.sous-n { font: 600 var(--t1)/1 var(--police); letter-spacing: .12em; color: var(--faible); transition: color .3s ease; }
.sous-lien:hover, .sous-lien:focus-visible { color: var(--ivoire); background-color: color-mix(in srgb, var(--ivoire) 7%, transparent); }
.sous-lien:hover .sous-n { color: var(--terra); }
.sous-lien.ici, .sous-lien.ici .sous-n { color: var(--terra); }
.sous-menu.ouvert .sous-lien { animation: sous-entree .55s cubic-bezier(0.19, 1, 0.22, 1) both; animation-delay: calc(.08s + var(--i, 0) * 45ms); }
@keyframes sous-entree { from { opacity: 0; transform: translateY(-8px); } to { opacity: 1; transform: none; } }
@keyframes sous-rideau { from { clip-path: inset(0 0 100% 0); } to { clip-path: inset(0 0 -2px 0); } }

@media (min-width: 1001px) {
  .sous-menu.ouvert {
    display: block; position: fixed; z-index: 5;
    width: min(340px, calc(100vw - 32px)); padding-block: var(--f2);
  }
  /* ⚠️ MESURÉ LE 15/09 : le rideau d ouverture était posé sur la liste
     elle-même. Un clip-path découpe AUSSI la zone cliquable : pendant ses
     0,7 s, un clic rapide sur une entrée du bas traversait la liste et
     tombait sur la page dessous (un chiffre, un dossier…). Le rideau ne
     porte plus que le FOND ; les entrées sont cliquables dès l ouverture. */
  .sous-menu.ouvert::before {
    content: ''; position: absolute; inset: 0; z-index: -1; pointer-events: none;
    background: color-mix(in srgb, var(--noir) 72%, transparent);
    -webkit-backdrop-filter: blur(20px); backdrop-filter: blur(20px);
    border-top: 1px solid var(--terra);
    animation: sous-rideau .7s cubic-bezier(0.19, 1, 0.22, 1) both;
  }
}
@media (min-width: 1001px) and (max-width: 1260px) {
  /* ici la barre est une rangée qui défile de côté : la flèche de la dernière rubrique doit rester dedans */
  #nav { padding-right: var(--f3); }
  /* 18/09 : la barre passe sur toute la largeur mais gardait la rangée du
     sigle (grid-row: 2 de la règle de base) — « ACCUEIL » écrivait sur
     « FBI KLUB » (vu à 1100 px). Sigle et pastilles en haut, rubriques dessous. */
  .marque, .pastilles { grid-row: 1; }
  #nav { grid-row: 2; }
}
@media (max-width: 1000px) {
  /* `safe` : une liste dépliée plus haute que l écran ne se fait pas couper par le haut */
  #nav { justify-content: safe center; }
  #nav .sous-menu.ouvert { display: grid; align-self: stretch; margin: 0 0 var(--f3) var(--f1); border-left: 1px solid var(--terra); }
  #nav .sous-lien { font-size: var(--t4); }
  #nav .lien::after { width: 12px; height: 12px; left: calc(100% + 8px); top: 8px; }
  /* ⚠️ VU SUR LA CAPTURE LE 15/09 : une rubrique dépliée allonge le menu et
     « Équipe », « Rejoindre » passaient SOUS les pastilles fixées en bas.
     Un fond sous les pastilles cache ce qui défile dessous, et le menu garde
     assez de marge basse pour remonter sa dernière ligne au-dessus. */
  html.menu-ouvert #nav { padding-bottom: calc(var(--f5) + 170px + env(safe-area-inset-bottom, 0px)); }
  html.menu-ouvert .pastilles::before {
    content: ''; position: fixed; left: 0; right: 0; bottom: 0; z-index: -1; pointer-events: none;
    height: calc(var(--f5) * 2 + 120px + env(safe-area-inset-bottom, 0px));
    background: linear-gradient(to top, var(--noir) 72%, transparent);
  }
  /* même chose en haut : un menu défilé passait sous « FBI KLUB » (vu sur la capture) */
  html.menu-ouvert .marque::before {
    content: ''; position: fixed; left: 0; right: 0; top: 0; z-index: -1; pointer-events: none;
    height: calc(var(--haut) + var(--f3));
    background: linear-gradient(to bottom, var(--noir) 72%, transparent);
  }
}


/* ── LE BLOQUEUR DE MOLETTE (15/09) ─────────────────────────────────
   Trois traits en bas de l écran, un par cran : au troisième, on passe à
   l étape suivante (voir brancheMolette). */
#molette {
  position: fixed; left: 50%; bottom: 20px; z-index: 98; translate: -50% 0;
  display: flex; gap: 6px; pointer-events: none;
  opacity: 0; transition: opacity .3s ease;
}
#molette.vu { opacity: 1; }
#molette i {
  width: 22px; height: 2px; border-radius: 2px;
  background: color-mix(in srgb, var(--ivoire) 32%, transparent);
  transition: background-color .2s ease, scale .35s cubic-bezier(.34, 1.56, .64, 1);
}
#molette i.plein { background: var(--terra); scale: 1 1.8; }

@media (prefers-reduced-motion: reduce) {
  .sous-menu.ouvert, .sous-menu.ouvert::before, .sous-menu.ouvert .sous-lien { animation: none !important; }
  .lien::after, #molette, #molette i { transition: none !important; }
}


/* ════ LE TÉLÉPHONE : DÉFILEMENT NATUREL (16/09) ═══════════════════
   Mesuré à 390 × 844 : 11 étapes sur 27 dépassaient l écran et la scène
   collante (100vh, qui bouge avec la barre d adresse) coupait leur fin.
   Sous 720 px, les étapes se suivent dans le flux : rien n est rogné, rien
   ne saute. Chacune se construit quand elle arrive (brancheTelephone) :
   la cascade --e, enregistrée ci-dessous, passe de 0 à 1 en une seconde.
   Ce qui changeait selon l étape (panneau flou, voile, cadran qui tourne,
   repère d étape) devient CONSTANT : c étaient les « choses volatiles ». */
/* initial-value 0 : exactement la valeur de repli `var(--e, 0)` d avant l enregistrement — rien ne change ailleurs */
@property --e { syntax: '<number>'; inherits: true; initial-value: 0; }

/* La cascade --e suit le défilement avec un peu de retard : une étape se
   construit en un peu moins d une seconde au lieu de passer d un coup, puis
   se fige. (--e est enregistrée ci-dessus : elle est animable.)
   16/09 (nuit) — ÉQUILIBRE : 1,6 s avait fini par sembler bloquer le scroll,
   1 s tient l accord avec le glissement raccourci (glisseVers, site.js). */
html.anime .etape { transition: --e 1s cubic-bezier(.3, .55, .25, 1); }
@media (prefers-reduced-motion: reduce) { html.anime .etape { transition: none; } }

@media (max-width: 720px) {
  html.telephone .slide { height: auto; }
  html.telephone .scene { position: static; height: auto; overflow: visible; }
  html.telephone .etape {
    position: relative; inset: auto; min-height: 0;
    padding-top: calc(var(--haut) + var(--f4)); padding-bottom: var(--f6);
    pointer-events: auto; opacity: 1 !important; transform: none !important;
    transition: --e 1.2s cubic-bezier(.3, .55, .25, 1);   /* 16/09 nuit : équilibre (1,8 s semblait bloquer le scroll) */
  }
  html.telephone .slide .etape + .etape { padding-top: var(--f6); }
  html.telephone .etape.a-reveler:not(.vue) { --e: 0 !important; }
  /* un bloc « centré posé en bas » n a plus d écran à remplir : il se pose simplement */
  html.telephone .etape[data-zone] { display: block; }
  /* ⚠️ capture du 16/09 : au téléphone, les blocs alternaient gauche et
     centre à chaque étape, et le filet d un œillet centré sur deux lignes
     partait seul à droite. Une seule règle au téléphone : tout à gauche. */
  html.telephone .etape[data-zone="centre"] > .dedans { max-width: none; margin: 0; text-align: left; }
  html.telephone .etape[data-zone="centre"] > .dedans > * { margin-left: 0 !important; margin-right: 0 !important; }
  html.telephone .etape[data-zone="centre"] .rangee,
  html.telephone .etape[data-zone="centre"] .etiquettes { justify-content: flex-start; }
  /* le fond : un seul voile constant, lisible partout */
  html.telephone #panneau, html.telephone #cadran, html.telephone #repere { display: none !important; }
  html.telephone #lisibilite { background: color-mix(in srgb, var(--noir) 58%, transparent) !important; }
  /* ⚠️ capture du 16/09 : en défilant, le texte passait SOUS la marque et
     le bouton Menu, qui n avaient qu un fondu — les deux se mélangeaient.
     Au téléphone, le cartouche a un vrai fond, flou. */
  html.telephone #cartouche::before {
    inset: 0; height: auto; opacity: 1;
    background: color-mix(in srgb, var(--noir) 86%, transparent);
    -webkit-backdrop-filter: blur(14px); backdrop-filter: blur(14px);
  }
  /* ⚠️ audit du 16/09 : la jauge de la fiche fait 1 px de haut et son
     compteur (« Encore 3 à renseigner ») débordait sur la ligne suivante.
     Le trait devient une bordure, le compteur prend sa place en dessous. */
  html.telephone .fiche-jauge { height: auto; background: none; border-top: 1px solid var(--filet); }
  html.telephone .fiche-jauge i { height: 1px; margin-top: -1px; }
  /* le bouton d adhésion : « trop serré » (sa remarque du 16/09) — en minuscules, aéré, sur toute la largeur */
  html.telephone .fiche-adhesion {
    display: flex; justify-content: center; width: 100%; height: auto; min-height: 52px;
    padding: 12px var(--f4); text-transform: none; letter-spacing: .01em; font-size: var(--t3); line-height: 1.3; text-align: center;
  }
  /* ⚠️ audit du 16/09 : la page du téléphone faisait 400 px pour 390 — on
     pouvait la faire glisser de côté. Aucun bloc seul n en était la cause
     (élimination sans coupable unique) : le glissement horizontal est coupé. */
  html.telephone, html.telephone body { overflow-x: clip; }
  /* les photos en bandeau (« Les rendez-vous + », « Plus de quatre-vingts ») :
     entières au téléphone, plus rognées (sa remarque du 16/09) */
  html.telephone .photo-large .cadre { height: auto; }
  html.telephone .photo-large .cadre > img { height: auto; object-fit: contain; }
  /* la liste des cours n a plus d ascenseur interne : elle se lit en descendant */
  html.telephone .liste-cours { max-height: none; overflow: visible; -webkit-mask-image: none; mask-image: none; }
  /* Karine : photo centrée (« trop justifiée à droite ») */
  html.telephone .photo-karine { justify-self: center; width: 100%; }
  html.telephone .photo-karine .cadre { width: min(100%, 320px); height: auto; aspect-ratio: 2 / 3; }
  /* l équipe : deux cartes par rangée, on voit tout le monde en descendant peu */
  html.telephone .equipe { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--f2); }
  html.telephone .coach--carte .coach-corps { padding: var(--f2); }
  html.telephone .coach-nom { font-size: var(--t4); }
  html.telephone .coach-mot { font-size: var(--t2); }
}
@media (max-width: 720px) and (prefers-reduced-motion: reduce) {
  html.telephone .etape { transition: none; }
}


/* ════ SAISON 2026-2027 (16/09) ════════════════════════════════════
   Les écrans refaits à sa demande : Qi Gong & Kundalini, le trousseau en
   grand, Karine au format de sa photo, les cartes et pages de l équipe,
   les deux affiches ensemble, les contacts, HelloAsso. */

/* les affiches cliquables (Qi Gong & Kundalini, Saison 10 & planning) */
.affiches-duo { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--f4); max-width: 920px; }
/* 16/09 (sa demande) : « pas de cadre aux affiches, seulement le bouton en logo qui permet de voir en grand » */
.doc-bouton { position: relative; display: block; width: 100%; padding: 0; border: 0; background: none; }
.doc-bouton img { display: block; width: 100%; height: clamp(260px, 60vh, 640px); object-fit: contain; transition: transform .8s var(--gout); }
.doc-bouton:hover { border-color: var(--terra); }
.doc-bouton:hover img { transform: scale(1.02); }
.doc-bouton:focus-visible { outline: 2px solid var(--terra); outline-offset: 3px; }
/* le bouton-logo « voir en grand » : une pastille ronde dans le coin, rien d autre */
.doc-loupe {
  position: absolute; right: var(--f2); bottom: var(--f2); width: 46px; height: 46px; border-radius: 50%;
  display: grid; place-items: center; background: var(--terra); color: var(--sur-terra);
  box-shadow: 0 6px 18px rgba(0, 0, 0, .35); transition: transform .45s var(--gout);
}
.doc-bouton:hover .doc-loupe, .doc-bouton:focus-visible .doc-loupe { transform: scale(1.12); }

/* la page Qi Gong & Kundalini */
.qg-page { display: grid; grid-template-columns: minmax(0, 1.1fr) minmax(0, 0.9fr); gap: var(--f6); align-items: center; }
.qg-page .doc-bouton img { height: clamp(240px, 54vh, 580px); }
.qg-bloc > * + * { margin-top: var(--f2); }
.qg-bloc + .qg-bloc { margin-top: var(--f4); padding-top: var(--f4); border-top: 1px solid var(--filet); }
.qg-quand { font-size: var(--t4); line-height: 1.4; }
.lien-tel { display: inline-block; color: var(--terra); font-weight: 600; }

/* le trousseau en grand */
.trousseau--grand { grid-template-columns: minmax(0, 1fr) minmax(0, 1fr); gap: var(--f6); align-items: center; border: 0; }
.trousseau--grand .cadre--doc { aspect-ratio: auto; height: auto; }
.trousseau--grand .cadre--doc > img { width: 100%; height: auto; max-height: 78vh; object-fit: contain; }
.trousseau--grand > div:last-child { padding: 0; }
.trousseau--grand .trousseau-texte .texte { margin-top: var(--f4); }

/* Karine : le cadre au format de sa photo (2:3) — plus rien n est rogné */
.photo-karine { justify-self: center; }
.photo-karine .cadre { width: auto; height: clamp(360px, 70vh, 680px); aspect-ratio: 2 / 3; max-width: 100%; margin-inline: auto; }
.photo-karine .cadre > img { object-position: 50% 50%; }
/* le rôle touchait le bas du nom (capture du 16/09) */
.photo-karine + div .titre--petit + .micro { margin-top: var(--f2); }
.parcours-liste { list-style: none; margin: var(--f2) 0 0; padding: 0; border-top: 1px solid var(--filet); }
.parcours-liste li { padding: 8px 0; border-bottom: 1px solid var(--filet); font-size: var(--t3); line-height: 1.4; }

/* les cartes de l équipe : un bouton qui ouvre la page de chacune */
.equipe { grid-template-columns: repeat(auto-fit, minmax(min(100%, 190px), 1fr)); }
.coach--carte { display: flex; flex-direction: column; width: 100%; padding: 0; text-align: left; color: inherit; }
.coach--carte:hover, .coach--carte:focus-visible { border-color: var(--terra); }
.coach--carte:focus-visible { outline: 2px solid var(--terra); outline-offset: 3px; }
.coach-photo { position: relative; display: block; aspect-ratio: 1 / 1; overflow: hidden; background: color-mix(in srgb, var(--ivoire) 6%, transparent); }
/* 20/09 : les portraits des cartes étaient en couleur alors que les mêmes
   visages sont en noir et blanc dans l organigramme et sur les fiches. */
.coach-photo img { position: absolute; inset: 0; width: 100%; height: 100%; object-fit: cover; object-position: 50% 30%; filter: grayscale(1) contrast(1.05); transition: transform .8s var(--gout), filter .7s var(--gout); }
.coach--carte:hover .coach-photo img, .coach--carte:focus-visible .coach-photo img { filter: none; }
.coach--carte:hover .coach-photo img { transform: scale(1.04); }
.coach-initiale { position: absolute; inset: 0; display: grid; place-items: center; font: 200 clamp(3rem, 7vw, 5rem)/1 var(--police); color: var(--sourd); }
.coach--carte .coach-corps { display: flex; flex-direction: column; flex: 1; padding: var(--f3); }
.coach-nom { font-family: var(--police); font-weight: 400; font-size: var(--t5); letter-spacing: -.015em; }
.coach-role { margin: var(--f1) 0 var(--f2); color: var(--terra); }
.coach-mot { font-size: var(--t3); line-height: 1.45; color: var(--ivoire); }
.coach-ouvrir { margin-top: auto; padding-top: var(--f3); color: var(--sourd); }

/* la boîte : page personnelle ou affiche en grand */
.boite-vue { width: min(1120px, 100vw); max-width: 100vw; max-height: 100vh; margin: auto; padding: 0; border: 0; background: var(--noir); color: var(--ivoire); overflow: hidden; }
.boite-vue::backdrop { background: rgba(6, 5, 5, .88); }
.boite-vue:not([open]) { display: none; }
.boite-vue[open] { display: grid; grid-template-rows: auto minmax(0, 1fr); }
.boite-fermer { justify-self: end; margin: var(--f3) var(--f3) 0 0; }
/* ⚠️ audit a11y du 16/09 : sur l affiche en grand (boîte transparente), le
   bouton était posé sur le voile sombre — illisible en ambiance jour (1,2:1) */
.boite-vue--image .boite-fermer { background: var(--noir); }
.boite-corps:focus-visible { outline: 2px solid var(--terra); outline-offset: -2px; }
.boite-corps { overflow: auto; padding: var(--f3) var(--f5) var(--f5); }
.boite-vue--image { width: auto; background: transparent; }
.boite-vue--image .boite-corps { display: grid; place-items: center; padding: 0 var(--f3) var(--f3); }
.boite-image { display: block; width: auto; height: auto; max-width: min(92vw, 1000px); max-height: calc(100vh - 96px); object-fit: contain; }
.boite-vue--profil .boite-corps { display: grid; grid-template-columns: minmax(0, .8fr) minmax(0, 1.2fr); gap: var(--f5); align-items: start; }
.profil-photo { position: sticky; top: 0; aspect-ratio: 1 / 1; overflow: hidden; }
.profil-photo img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 30%; }
.profil-photo--vide { display: grid; place-items: center; background: color-mix(in srgb, var(--ivoire) 6%, transparent); font: 200 clamp(4rem, 12vw, 9rem)/1 var(--police); color: var(--sourd); }
.profil-texte > * + * { margin-top: var(--f3); }
.profil-texte > h3.micro { margin-top: var(--f5); }
.profil-tel { height: 48px; }
.profil-devise { font-size: var(--t5); font-weight: 300; line-height: 1.35; }
.profil-avis blockquote { margin: 0; padding: 6px 0 6px var(--f3); border-left: 2px solid var(--terra); font-style: italic; color: var(--sourd); }
.profil-avis blockquote + blockquote { margin-top: var(--f2); }

/* l affiche : les trois numéros */
/* ⚠️ MESURÉ LE 16/09 : empilés, les trois numéros faisaient déborder
   l affiche de 32 px sous un écran de 900 px. Ils sont en ligne. */
.affiche-tel { display: flex; flex-wrap: wrap; align-items: baseline; column-gap: var(--f4); row-gap: 2px; }
.affiche-tel > .micro { flex-basis: 100%; }
.affiche-tel a { display: inline-block; font-size: var(--t3); white-space: nowrap; }
.affiche-tel-nom { margin-right: .4em; color: var(--sourd); font-weight: 400; }

/* le tarif détaillé, HelloAsso dans la fiche, « Contactez-les » */
.tarif-detail { margin-top: var(--f3); }
.fiche-adhesion { margin-top: var(--f4); }
/* ⚠️ capture du 16/09 : `.fiche > p { font-size: var(--t4) }` l emportait
   sur `.micro` — les mentions de la fiche s affichaient en grandes capitales
   (« Les champs marqués d une étoile… » l était déjà avant). */
.fiche > p.micro { font-size: var(--t1); line-height: 1.6; }
.fiche-adhesion-mot { margin-top: var(--f2); }
.fiche > p.micro.fiche-adhesion-mot { font-size: var(--t2); text-transform: none; letter-spacing: normal; }   /* une phrase, pas une étiquette (a11y) */
.contacts-equipe { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 200px), 1fr)); gap: var(--f2); }
.contacts-equipe h3 { grid-column: 1 / -1; }
.contact-personne { display: grid; gap: 4px; padding: var(--f3); border: 1px solid var(--filet); transition: border-color .3s ease; }
.contact-personne:hover, .contact-personne:focus-visible { border-color: var(--terra); }
.contact-personne b { font-weight: 600; font-size: var(--t4); }
/* la page Contact (16/09) */
.page-contact .contact-bloc > h3 { margin-bottom: var(--f2); }
.page-contact .contacts { margin-top: 0; }
.contact-salles { display: grid; grid-template-columns: repeat(auto-fit, minmax(min(100%, 260px), 1fr)); gap: var(--f2); }
.contact-salle { display: grid; gap: 4px; padding: var(--f3); border: 1px solid var(--filet); }
.contact-salle b { font-weight: 600; font-size: var(--t4); }

/* ⚠️ LA PAGE « QUESTIONS ET INSCRIPTION » SUR ORDINATEUR (16/09).
   Capture du 15/09 à 1440 et 1024 px : `.suite-page > * { grid-row: 2 }`
   rangeait le titre, les questions et les contacts CÔTE À CÔTE en trois
   colonnes étroites — le défaut corrigé le 13/09 au téléphone seulement.
   La page s empile maintenant à toutes les largeurs ; les questions
   passent sur deux colonnes sur grand écran. */
@media (min-width: 721px) {
  .suite-page { display: flex; flex-direction: column; justify-content: center; padding-block: var(--f7); }
  .suite-page > * { grid-row: auto; }
  .suite-page > * + * { margin-top: var(--f5); }
}
@media (min-width: 1001px) {
  .questions { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); column-gap: var(--f6); }
}

@media (max-width: 1000px) {
  .qg-page { grid-template-columns: 1fr; gap: var(--f5); }
  .trousseau--grand { grid-template-columns: 1fr; gap: var(--f4); }
}
@media (max-width: 720px) {
  .affiches-duo { gap: var(--f2); }
  .doc-bouton img, .qg-page .doc-bouton img { height: auto; }
  /* ⚠️ MESURÉ LE 16/09 : en grille, la rangée de la photo valait 0 px
     (hauteur tirée du seul aspect-ratio, largeur en %) — le texte partait
     au même endroit et la photo le recouvrait. Au téléphone : un empilement. */
  .boite-vue--profil .boite-corps { display: block; padding-inline: var(--f3); }
  .boite-vue--profil .profil-texte { margin-top: var(--f4); }
  /* ⚠️ capture du 16/09 : collante, la photo restait en haut et recouvrait
     le nom et le bouton d appel quand la page défilait */
  .boite-vue--profil .profil-photo { position: static; width: min(100%, 260px); }
  .photo-karine .cadre { height: clamp(320px, 62vh, 520px); }
}
@media (prefers-reduced-motion: reduce) {
  .doc-bouton img, .coach-photo img { transition: none !important; }
}


/* ── L AFFICHE TIENT DANS UN ÉCRAN──────────────────────────────────
   Mesuré à 1440 × 900 : son bloc descendait à 107 % de la hauteur —
   « Planning & infos », le téléphone et les légendes des QR codes étaient
   coupés (c était déjà le cas avant le 13/09). On resserre les espaces
   sur grand écran seulement ; sur téléphone la page défile de toute façon. */
@media (min-width: 1001px) {
  .affiche-clair { gap: var(--f5); margin-top: var(--f4); }
  .affiche-salle { padding-top: var(--f2); }
  .affiche-jour { margin-top: var(--f3); }
  .affiche-jour span { margin-top: 1px; }
  .affiche-pied { margin-top: var(--f4); gap: var(--f4); }
  .affiche-essai { margin-top: var(--f2); }
  .qr img { width: 72px; height: 72px; }
}

/* ── RIEN NE DÉBORDE SUR TÉLÉPHONE ──────────────────────────────────
   Mesuré à 390 px : les quatre familles occupaient 118 % de la largeur,
   un grand titre 101 %. */
@media (max-width: 720px) {
  .famille-geant { flex-wrap: wrap; column-gap: var(--f3); row-gap: 2px; }
  .famille-geant b { min-width: 0; font-size: clamp(var(--t5), 8vw, var(--t6)); }
  .famille-geant > .micro:last-child { flex-basis: 100%; margin-left: calc(var(--f5) + var(--f3)); text-align: left; }
  .titre--geant { font-size: clamp(2.3rem, 11.5vw, var(--t8)); }
  .titre { overflow-wrap: anywhere; hyphens: auto; }
  /* mesuré : « Les champs marqués d une étoile sont obligatoires » tenait
     sur UNE ligne (width: max-content) — 664 px, et toute la page du
     téléphone passait à 707 px de large, marque sortie de l écran */
  .fiche > p.micro { width: auto; max-width: 100%; }
  /* ⚠️ LE VRAI COUPABLE DU TÉLÉPHONE, trouvé par élimination (on masque
     chaque bloc et on regarde la largeur retomber) : la page « questions et
     contacts » pose TOUS ses enfants sur la même rangée de sa grille
     (`.suite-page > * { grid-row: 2 }`). Faute de colonnes déclarées, la
     grille les rangeait CÔTE À CÔTE — titre 196 px, questions 126 px,
     contacts 251 px — et la page du téléphone passait à 595 px. Antérieur
     au 13/09. Sur téléphone, la page redevient un simple empilement. */
  .suite-page { display: block; min-height: 0; padding-block: var(--f6); }
  .suite-page > * + * { margin-top: var(--f5); }
}


/* ── LES TROIS DERNIERS ÉCRANS, PETIT À PETIT (14/09) ───────────────
   Posé par `detaillerFin()` : les LIGNES (.pl-*) se tracent de gauche à
   droite, puis les TEXTES (.pp) apparaissent un à un. Le filet d origine
   devient transparent et son dessin est repris par un fond de 1 px dont la
   largeur suit la cascade — la mise en page ne bouge pas d un pixel. */
html.anime .etape[data-detail] .pp {
  --pt: clamp(0, calc((var(--e, 0) - var(--dt, 0)) * 9), 1);
  opacity: var(--pt);
}
/* 16/09 : le texte MONTE du bas jusqu à sa place (1,4 em au lieu de 0,6 — la montée se voit) */
html.anime .etape[data-detail] .pp--bloc { transform: translate3d(0, calc((1 - var(--pt)) * 1.4em), 0); }
html.anime .etape[data-detail] :is(.pl-haut, .pl-bas, .pl-deux) {
  --pl: clamp(0, calc((var(--e, 0) - var(--dl, 0)) * 5), 1);
  background-repeat: no-repeat; background-origin: border-box;
}
html.anime .etape[data-detail] .pl-haut {
  border-top-color: transparent !important;
  background-image: linear-gradient(var(--tc), var(--tc));
  background-size: calc(var(--pl) * 100%) var(--tw); background-position: left top;
}
html.anime .etape[data-detail] .pl-bas {
  border-bottom-color: transparent !important;
  background-image: linear-gradient(var(--tc), var(--tc));
  background-size: calc(var(--pl) * 100%) var(--tw); background-position: left bottom;
}
html.anime .etape[data-detail] .pl-deux {
  border-top-color: transparent !important; border-bottom-color: transparent !important;
  background-image: linear-gradient(var(--tc), var(--tc)), linear-gradient(var(--tc), var(--tc));
  background-size: calc(var(--pl) * 100%) var(--tw), calc(var(--pl) * 100%) var(--tw);
  background-position: left top, left bottom;
}

/* « CHOISISSEZ VOTRE TERRAIN », PLUS TRAVAILLÉ : les villes se dévoilent de
   gauche à droite, les cours glissent en place, le badge d essai et les
   QR codes grandissent en arrivant. */
html.anime .etape[data-detail="affiche"] .affiche-ville.pp { clip-path: inset(0 calc((1 - var(--pt)) * 100%) 0 0); }
html.anime .etape[data-detail="affiche"] .affiche-jour span.pp { transform: translate3d(calc((1 - var(--pt)) * -14px), 0, 0); }
html.anime .etape[data-detail="affiche"] .affiche-essai.pp { transform: scale(calc(.82 + .18 * var(--pt))); transform-origin: left center; }
html.anime .etape[data-detail="affiche"] .qr.pp { transform: scale(calc(.8 + .2 * var(--pt))); transform-origin: center bottom; }
html.anime .etape[data-detail="affiche"] .affiche-devise.pp { clip-path: inset(0 calc((1 - var(--pt)) * 100%) 0 0); }


/* ── LA BIBLIOTHÈQUE D IMAGES — DEUX DÉFAUTS MESURÉS (14/09) ────────
   1 · Fermée, elle restait affichée en fond : `.galerie { display: flex }`
       écrasait le masquage qu un <dialog> fermé reçoit du navigateur.
       Mesuré : `open: false`, et pourtant plein écran, visible. */
.galerie:not([open]) { display: none; }
/* 2 · En plein écran on ne pouvait plus sortir à la souris : la scène
       n était pas étirée à sa rangée, la vidéo gardait sa hauteur
       naturelle et poussait la légende et « Retour à la grille » HORS de
       l écran (mesuré à 1440 × 900 : le clic de retour tombait sur la
       vidéo). La scène tient maintenant sa rangée, la pièce tient dans la
       scène sans être déformée, et les boutons restent au-dessus. */
.gal-scene { align-self: stretch; overflow: hidden; }
.gal-scene img, .gal-scene video { max-height: 100%; object-fit: contain; }
.gal-scene video { width: auto; height: 100%; max-width: min(100%, 1180px); }
.gal-retour, .gal-legende, .gal-nav { position: relative; z-index: 3; }


/* ── MOUVEMENT RÉDUIT ───────────────────────────────────────────────  */
@media (prefers-reduced-motion: reduce) {
  #panneau, #nav, #nav .lien, .menu-traits i, .bouton, .pastille { transition: none !important; }
  html.anime .devise .mm { opacity: 1; filter: none; }
}


/* ── LES RENDEZ-VOUS + : UNE ÉTIQUETTE, UNE DÉFINITION (18/09) ──────
   Sa demande : un clic sur une étiquette affiche sa définition. La fiche
   se pose SUR la photo (bandeau flou du haut) : l étape ne s allonge pas,
   rien ne passe sous le bas de l écran. */
button.etiquette { background: transparent; cursor: pointer; min-height: 44px; }
button.etiquette:focus-visible { outline: 2px solid var(--terra); outline-offset: 3px; }
button.etiquette.ici { border-color: var(--terra); color: var(--sur-terra); background: var(--terra); }
.photo-large--fiche { position: relative; }
.etiquette-def {
  position: absolute; left: 0; right: 0; top: 0; z-index: 2;
  padding: var(--f4) var(--f5) var(--f5); text-align: left;
  background: color-mix(in srgb, var(--noir) 70%, transparent);
  -webkit-backdrop-filter: blur(18px); backdrop-filter: blur(18px);
  border-top: 1px solid var(--terra);
  animation: fiche-entre .6s cubic-bezier(0.19, 1, 0.22, 1) both;
}
.etiquette-def-tete { display: flex; align-items: baseline; gap: var(--f3); }
.etiquette-def-tete b { font: 700 var(--t5)/1.1 var(--police); letter-spacing: -.018em; text-transform: uppercase; }
.etiquette-def .micro { display: block; margin: var(--f2) 0 var(--f3); }
.etiquette-def .texte { max-width: 62ch; }
@keyframes fiche-entre { from { opacity: 0; transform: translateY(-10px); } to { opacity: 1; transform: none; } }
@media (prefers-reduced-motion: reduce) { .etiquette-def { animation: none; } }
@media (max-width: 720px) {
  .etiquette-def { position: static; padding: var(--f4) var(--f3); }
}


/* ── L ORGANIGRAMME DE LA BRIGADE (18/09, redessiné le 18/09 au soir) ──
   Sa remarque sur « Cinq rôles, une équipe » : « elle me semble très vide ».
   Puis : « plus joli, plus graphique — les lignes de liaison ne se touchent
   pas ». Mesuré : la barre allait de 12,5 % à 87,5 % alors que les centres
   des cases, décalés par les gouttières, tombent ~5 px plus loin.
   LA RÈGLE MAINTENANT : les liaisons sont UNE rangée (.org-liens) qui
   partage la grille des cases (même --n, même gouttière --g). Le tronc, la
   barre et les descentes vivent dans la même boîte : ils se touchent par
   construction, à toute largeur. Chaque descente finit sur le portrait rond
   de sa case, posé à cheval sur le bord haut. Rien ne bouge au survol (une
   case qui monte décrocherait son trait). */
.organigramme {
  --n: 4; --g: var(--f3); --ph: 64px;
  --trait: color-mix(in srgb, var(--terra) 80%, transparent);
  display: grid;
}
.org-tete { display: flex; justify-content: center; }

/* les liaisons */
.org-liens { position: relative; display: grid; grid-template-columns: repeat(var(--n), minmax(0, 1fr)); column-gap: var(--g); height: calc(2 * var(--f4)); }
.org-liens::before { content: ''; position: absolute; left: calc(50% - .5px); top: 0; width: 1px; height: calc(50% + .5px); background: var(--trait); }
.org-liens::after {
  content: ''; position: absolute; z-index: 1; left: 50%; top: 50%; width: 9px; height: 9px; margin: -4.5px 0 0 -4.5px;
  border-radius: 50%; background: var(--terra);
  box-shadow: 0 0 0 0 color-mix(in srgb, var(--terra) 55%, transparent);
  animation: org-ping 2.8s cubic-bezier(0.19, 1, 0.22, 1) infinite;
}
.org-liens > span { position: relative; }
.org-liens > span::before { content: ''; position: absolute; top: calc(50% - .5px); height: 1px; left: calc(-.5 * var(--g)); right: calc(-.5 * var(--g)); background: var(--trait); }
.org-liens > span:first-child::before { left: calc(50% - .5px); }
.org-liens > span:last-child::before { right: calc(50% - .5px); }
.org-liens > span::after { content: ''; position: absolute; left: calc(50% - .5px); top: calc(50% - .5px); bottom: 0; width: 1px; background: var(--trait); }
@keyframes org-ping {
  0%   { box-shadow: 0 0 0 0 color-mix(in srgb, var(--terra) 55%, transparent); }
  70%  { box-shadow: 0 0 0 14px color-mix(in srgb, var(--terra) 0%, transparent); }
  100% { box-shadow: 0 0 0 0 color-mix(in srgb, var(--terra) 0%, transparent); }
}

/* les cases */
.org-rang { display: grid; grid-template-columns: repeat(var(--n), minmax(0, 1fr)); gap: var(--g); }
.org-noeud {
  position: relative; display: flex; flex-direction: column; align-items: center; gap: 4px;
  min-height: 44px; margin-top: calc(var(--ph) / 2);
  padding: calc(var(--ph) / 2 + var(--f3)) var(--f3) calc(var(--f5) + var(--f1));
  text-align: center; color: var(--ivoire); cursor: pointer;
  border: 1px solid var(--filet);
  background: color-mix(in srgb, var(--noir) 55%, transparent);
  -webkit-backdrop-filter: blur(14px); backdrop-filter: blur(14px);
  transition: border-color .45s var(--gout), background-color .45s var(--gout);
}
/* un filet terracotta qui se déroule sur le haut de la case au survol */
.org-noeud::after {
  content: ''; position: absolute; left: -1px; right: -1px; top: -1px; height: 2px; background: var(--terra);
  transform: scaleX(0); transition: transform .6s var(--gout);
}
.org-noeud:hover, .org-noeud:focus-visible { border-color: color-mix(in srgb, var(--terra) 70%, transparent); background: color-mix(in srgb, var(--noir) 72%, transparent); }
.org-noeud:hover::after, .org-noeud:focus-visible::after { transform: scaleX(1); }
.org-noeud:focus-visible { outline: 2px solid var(--terra); outline-offset: 3px; }

/* le portrait rond, à cheval sur le bord haut — c est là qu arrive le trait */
.org-photo {
  /* -1 px : la case a une bordure, sans lui le portrait tombait 1 px sous le trait (mesuré) */
  position: absolute; z-index: 2; left: 50%; top: calc(var(--ph) / -2 - 1px);
  width: var(--ph); height: var(--ph); margin-left: calc(var(--ph) / -2);
  display: grid; place-items: center; overflow: hidden; border-radius: 50%;
  border: 1px solid var(--terra); background: var(--noir);
  box-shadow: 0 0 0 3px var(--noir), 0 0 0 4px color-mix(in srgb, var(--terra) 40%, transparent);
  transition: box-shadow .5s var(--gout);
}
.org-photo img { width: 100%; height: 100%; object-fit: cover; object-position: 50% 22%; filter: grayscale(1) contrast(1.05); transition: filter .6s var(--gout); }
.org-photo b { font: 300 calc(var(--ph) * .45)/1 var(--police); color: var(--terra); }
.org-noeud:hover .org-photo img, .org-noeud:focus-visible .org-photo img { filter: none; }
.org-noeud:hover .org-photo, .org-noeud:focus-visible .org-photo { box-shadow: 0 0 0 3px var(--noir), 0 0 0 5px var(--terra); }

.org-id { display: flex; flex-direction: column; align-items: center; gap: 4px; }
.org-nom { font: 400 var(--t5)/1.1 var(--police); letter-spacing: -.015em; }
.org-role { color: var(--ivoire); opacity: .72; }
.org-ligne { margin-top: var(--f2); font-size: var(--t2); line-height: 1.45; }
.org-ouvrir {
  position: absolute; left: 0; right: 0; bottom: var(--f2); color: var(--terra);
  opacity: .75; transition: opacity .4s var(--gout), letter-spacing .5s var(--gout);
}
.org-noeud:hover .org-ouvrir, .org-noeud:focus-visible .org-ouvrir { opacity: 1; letter-spacing: .16em; }

/* la commissaire : une case en largeur, portrait à gauche */
.org-tete .org-noeud {
  --ph: 84px;
  flex-direction: row; align-items: center; gap: var(--f4); text-align: left;
  width: min(100%, 680px); margin-top: 0; padding: var(--f4) var(--f5) var(--f4) var(--f4);
}
.org-tete .org-photo { position: relative; top: auto; left: auto; margin: 0; flex: none; }
.org-tete .org-id { align-items: flex-start; flex: none; }
.org-tete .org-ligne { margin-top: 0; padding-left: var(--f4); border-left: 1px solid var(--filet); font-size: var(--t3); }
.org-tete .org-ouvrir { left: auto; right: var(--f4); bottom: var(--f1); }

.org-chute { margin-top: var(--f3); max-width: 60ch; }

/* la frise des états de service : un trait continu, les points posés dessus */
.frise { position: relative; list-style: none; margin: var(--f6) 0 0; padding: 0; display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); }
.frise::before { content: ''; position: absolute; left: 0; right: 0; top: 0; height: 1px; background: var(--filet); }
.frise li { position: relative; padding: var(--f3) var(--f3) 0 0; }
.frise li::before { content: ''; position: absolute; top: -3px; left: 0; width: 7px; height: 7px; border-radius: 50%; background: var(--terra); }
/* aujourd hui : le dernier point bat comme le nœud de l organigramme */
.frise li:last-child::before { animation: org-ping 2.8s cubic-bezier(0.19, 1, 0.22, 1) infinite; }
.frise b { display: block; font: 600 var(--t1)/1 var(--police); letter-spacing: .12em; text-transform: uppercase; color: var(--terra); }
.frise span { display: block; margin-top: 6px; font-size: var(--t2); line-height: 1.35; }
/* la frise passe sur la partie claire de la photo : une ombre douce la garde lisible */
.frise b, .frise span { text-shadow: 0 1px 2px rgba(0, 0, 0, .55), 0 0 14px rgba(0, 0, 0, .5); }
html[data-ambiance="jour"] .frise b, html[data-ambiance="jour"] .frise span { text-shadow: none; }

@media (max-width: 1000px) and (min-width: 721px) {
  .org-noeud { padding-inline: var(--f2); }
  .org-nom { font-size: var(--t4); }
}
/* un écran d ordinateur peu haut (1280 × 800, 1100 × 820) : tout tient sans défiler (mesuré) */
@media (max-height: 880px) and (min-width: 721px) {
  .organigramme { --ph: 52px; }
  .org-tete .org-noeud { --ph: 68px; padding-block: var(--f3); }
  .org-liens { height: calc(2 * var(--f3)); }
  .org-noeud { padding-top: calc(var(--ph) / 2 + var(--f2)); padding-bottom: var(--f5); }
  .org-ligne { margin-top: var(--f1); }
  .organigramme + .sous, .org-chute { font-size: var(--t3); }
}
/* au téléphone : une colonne, les portraits à gauche, reliés par une épine */
@media (max-width: 720px) {
  .organigramme { --ph: 56px; position: relative; gap: var(--f3); }
  .organigramme::before {
    content: ''; position: absolute; z-index: 0; top: calc(var(--f3) + var(--ph) / 2); bottom: var(--f5);
    left: calc(var(--f3) + 1px + var(--ph) / 2 - .5px); width: 1px; background: var(--trait);
  }
  .org-liens { display: none; }
  .org-rang { grid-template-columns: 1fr; }
  .org-noeud, .org-tete .org-noeud {
    --ph: 56px; flex-direction: row; align-items: flex-start; text-align: left; gap: var(--f3);
    width: 100%; margin-top: 0; padding: var(--f3) var(--f3) var(--f5);
    background: color-mix(in srgb, var(--noir) 88%, transparent);
  }
  .org-photo, .org-tete .org-photo { position: relative; top: auto; left: auto; margin: 0; flex: none; }
  .org-noeud > .org-id, .org-tete .org-id { align-items: flex-start; }
  /* le texte passe sous l identité, à droite du portrait */
  .org-noeud { display: grid; grid-template-columns: var(--ph) minmax(0, 1fr); }
  .org-photo { grid-row: span 2; }
  .org-ligne, .org-tete .org-ligne { margin-top: var(--f1); padding-left: 0; border-left: 0; font-size: var(--t2); }
  .org-ouvrir, .org-tete .org-ouvrir { left: calc(var(--f3) + var(--ph) + var(--f3)); right: auto; bottom: var(--f2); opacity: 1; }
  .frise { grid-template-columns: repeat(2, minmax(0, 1fr)); row-gap: var(--f3); }
}
@media (prefers-reduced-motion: reduce) {
  .org-liens::after, .frise li:last-child::before { animation: none; }
  .org-noeud, .org-noeud::after, .org-photo, .org-photo img, .org-ouvrir { transition: none; }
}


/* ── LA FICHE DE L AGENT (18/09) ────────────────────────────────────
   Sa demande : la page d une coach « plus graphique, dynamique,
   interactive ». La photo passe au noir et blanc du site, sous le cadran ;
   elle reprend ses couleurs au survol. Onglets, dépositions qui défilent,
   et le passage d un agent à l autre. */
.profil-photo { isolation: isolate; }
.profil-photo img { filter: grayscale(1) contrast(1.06); transition: filter .9s var(--gout), transform 1.4s var(--gout); }
.profil-photo:hover img { filter: none; transform: scale(1.03); }
/* les équerres terracotta aux quatre coins */
.profil-photo::before, .profil-photo::after {
  content: ''; position: absolute; z-index: 2; width: 26px; height: 26px; pointer-events: none;
  border: 0 solid var(--terra);
}
.profil-photo::before { top: 10px; left: 10px; border-top-width: 2px; border-left-width: 2px; }
.profil-photo::after { right: 10px; bottom: 10px; border-right-width: 2px; border-bottom-width: 2px; }
/* le cadran du klub, qui tourne lentement sur le portrait */
.profil-cadran {
  position: absolute; z-index: 1; inset: 12%; width: 76%; height: 76%; pointer-events: none;
  fill: none; stroke: var(--terra); stroke-width: .5; opacity: .55;
  animation: cadran-tourne 38s linear infinite; transition: opacity .6s var(--gout);
}
.profil-cadran .pc-pointille { stroke-dasharray: 1.2 2.4; stroke: var(--ivoire); opacity: .6; }
.profil-photo:hover .profil-cadran { opacity: .15; }
@keyframes cadran-tourne { to { transform: rotate(360deg); } }
.profil-matricule {
  position: absolute; z-index: 2; left: 14px; bottom: 12px; padding: 5px 9px;
  background: color-mix(in srgb, var(--noir) 70%, transparent); color: var(--ivoire); letter-spacing: .14em;
}
.profil-fiche { color: var(--ivoire); opacity: .7; letter-spacing: .14em; }

/* les onglets */
.profil-onglets { display: flex; flex-wrap: wrap; gap: var(--f4); margin-top: var(--f5) !important; border-bottom: 1px solid var(--filet); }
.profil-onglets [role="tab"] {
  position: relative; min-height: 44px; padding: 0; background: none; border: 0; cursor: pointer;
  font: 600 var(--t2)/1 var(--police); letter-spacing: .1em; text-transform: uppercase; color: var(--ivoire); opacity: .6;
  transition: opacity .3s var(--gout), color .3s var(--gout);
}
.profil-onglets [role="tab"]::after {
  content: ''; position: absolute; left: 0; right: 0; bottom: -1px; height: 2px; background: var(--terra);
  transform: scaleX(0); transform-origin: left; transition: transform .5s var(--gout);
}
.profil-onglets [role="tab"]:hover { opacity: 1; }
.profil-onglets [role="tab"][aria-selected="true"] { opacity: 1; color: var(--terra); }
.profil-onglets [role="tab"][aria-selected="true"]::after { transform: scaleX(1); }
.profil-onglets [role="tab"]:focus-visible { outline: 2px solid var(--terra); outline-offset: 4px; }
.profil-panneau { animation: panneau-entre .55s cubic-bezier(0.19, 1, 0.22, 1) both; }
.profil-panneau > * + * { margin-top: var(--f3); }
@keyframes panneau-entre { from { opacity: 0; transform: translateY(8px); } to { opacity: 1; transform: none; } }

/* les états de service : une frise verticale, numérotée, qui se déroule */
.etats { list-style: none; margin: 0; padding: 0; position: relative; }
.etats::before { content: ''; position: absolute; left: 1.05em; top: 6px; bottom: 6px; width: 1px; background: var(--filet); }
.etats li {
  position: relative; display: grid; grid-template-columns: 2.1em minmax(0, 1fr); gap: var(--f3); align-items: baseline;
  padding: 9px 0; font-size: var(--t3); line-height: 1.4;
  animation: etat-entre .6s cubic-bezier(0.19, 1, 0.22, 1) both; animation-delay: calc(var(--i, 0) * 70ms);
}
.etats-n {
  position: relative; z-index: 1; justify-self: center; padding: 3px 0;
  background: var(--noir); font: 600 var(--t1)/1 var(--police); letter-spacing: .08em; color: var(--terra);
}
.etats li:hover > span:last-child { color: var(--terra); }
@keyframes etat-entre { from { opacity: 0; transform: translateX(-10px); } to { opacity: 1; transform: none; } }

/* les dépositions, une à la fois */
.depositions { position: relative; padding: var(--f4) 0 0 var(--f6); }
.depo-guillemet { position: absolute; left: 0; top: -.08em; font: 200 5.5rem/1 var(--police); color: var(--terra); }
.depo-texte { margin: 0; min-height: 4.2em; font: 300 var(--t4)/1.4 var(--police); font-style: italic; }
.depo-texte.entre { animation: panneau-entre .5s cubic-bezier(0.19, 1, 0.22, 1) both; }
.depo-nav { display: flex; align-items: center; gap: var(--f3); margin-top: var(--f4); }
.depo-nav .pastille { width: 44px; height: 44px; padding: 0; justify-content: center; }
.depo-compte { letter-spacing: .14em; font-variant-numeric: tabular-nums; }

/* d un agent à l autre */
.profil-suite { display: grid; grid-template-columns: 1fr 1fr; gap: var(--f3); margin-top: var(--f6) !important; padding-top: var(--f4); border-top: 1px solid var(--filet); }
.profil-voisin {
  display: flex; flex-direction: column; align-items: flex-start; gap: 4px; min-height: 44px; padding: var(--f2) 0;
  background: none; border: 0; color: var(--ivoire); cursor: pointer; text-align: left;
}
.profil-voisin--suiv { align-items: flex-end; text-align: right; }
.profil-voisin b { font: 400 var(--t5)/1.1 var(--police); letter-spacing: -.015em; transition: color .3s var(--gout); }
.profil-voisin:hover b, .profil-voisin:focus-visible b { color: var(--terra); }
.profil-voisin:focus-visible { outline: 2px solid var(--terra); outline-offset: 4px; }

/* au doigt aussi, le noir et blanc du site : la photo ouverte en grand, elle, est en couleur */
@media (prefers-reduced-motion: reduce) {
  .profil-cadran, .profil-panneau, .etats li, .depo-texte.entre { animation: none; }
  .profil-photo img { transition: none; }
}
/* la fiche garde sa hauteur d un onglet à l autre : sans ça la boîte,
   centrée, sautait de haut en bas à chaque clic */
@media (min-width: 721px) { .boite-vue--profil[open] { height: min(100vh, 860px); } }


/* ── LES BIBLIOTHÈQUES PHOTO, À LA DA DU SITE (18/09) ───────────────
   Sa demande : « améliorer les bibliothèques photo pour qu elles
   correspondent à la DA du site ». Le site est en noir et blanc avec des
   accents terracotta ; les dossiers mêlaient couleur et noir et blanc, et
   les vignettes en attente étaient des cases noires.
   · noir et blanc partout, la couleur revient au survol et au focus ;
   · équerres terracotta aux coins de la tuile survolée ;
   · le numéro de la pièce dans sa discipline, en haut à gauche ;
   · la première pièce d une discipline prend double place ;
   · une trame qui balaie la tuile tant que l image n est pas arrivée,
     puis l image entre en fondu, à son rang. */

/* les couvertures des trois dossiers */
.dossier-vue img { filter: grayscale(1) contrast(1.05); transition: transform .7s var(--gout), filter .8s var(--gout); }
.dossier:hover .dossier-vue img, .dossier:focus-visible .dossier-vue img { filter: none; }

/* la grille : un rythme de planche, pas un damier */
.gal-grille { grid-auto-flow: dense; }
@media (min-width: 721px) {
  .tuile--une { grid-column: span 2; grid-row: span 2; }
}
.gal-groupe { padding-bottom: var(--f2); border-bottom: 1px solid var(--filet); }
.gal-groupe::before { content: ''; display: inline-block; width: 7px; height: 7px; margin-right: var(--f2); border-radius: 50%; background: var(--terra); vertical-align: middle; }
.gal-groupe { justify-content: flex-start; gap: 0; }
.gal-compte-groupe { margin-left: auto; }

/* la tuile en attente : une trame qui balaie */
.tuile {
  background:
    linear-gradient(100deg, transparent 30%, color-mix(in srgb, var(--ivoire) 7%, transparent) 50%, transparent 70%) 0 0 / 250% 100% no-repeat,
    color-mix(in srgb, var(--ivoire) 4%, var(--noir));
  animation: tuile-attente 1.6s linear infinite;
}
.tuile.charge { animation: none; background: var(--noir); }
@keyframes tuile-attente { from { background-position: 150% 0, 0 0; } to { background-position: -150% 0, 0 0; } }

/* l image : noir et blanc, entre en fondu à son rang, reprend ses couleurs au survol */
.tuile img { opacity: 0; filter: grayscale(1) contrast(1.05); transition: transform .6s var(--gout), opacity .6s var(--gout), filter .6s var(--gout); }
.tuile.charge img { opacity: .9; transition-delay: 0s, calc(var(--k, 0) * 45ms), 0s; }
.tuile:hover img, .tuile:focus-visible img { opacity: 1; filter: none; transform: scale(1.06); }
.tuile--absente.charge img { opacity: .45; }

/* les équerres, dessinées au survol */
.tuile::before, .tuile::after {
  content: ''; position: absolute; z-index: 2; width: 18px; height: 18px; pointer-events: none;
  border: 0 solid var(--terra); opacity: 0; transform: scale(.6);
  transition: opacity .35s var(--gout), transform .5s var(--gout);
}
.tuile::before { top: 8px; left: 8px; border-top-width: 2px; border-left-width: 2px; transform-origin: top left; }
.tuile::after { right: 8px; bottom: 8px; border-right-width: 2px; border-bottom-width: 2px; transform-origin: bottom right; }
.tuile:hover::before, .tuile:hover::after, .tuile:focus-visible::before, .tuile:focus-visible::after { opacity: 1; transform: none; }

/* le numéro de la pièce */
.tuile-n {
  position: absolute; z-index: 2; top: 8px; right: 10px; pointer-events: none;
  font-weight: 600; letter-spacing: .12em; color: var(--ivoire); text-shadow: 0 1px 8px rgba(0, 0, 0, .7);
  opacity: .75; transition: color .3s var(--gout), opacity .3s var(--gout);
}
.tuile:hover .tuile-n, .tuile:focus-visible .tuile-n { color: var(--terra); opacity: 1; }

@media (prefers-reduced-motion: reduce) {
  .tuile { animation: none; }
  .tuile img, .tuile::before, .tuile::after { transition: none; }
}


/* ── LA TABLETTE EN PORTRAIT (18/09) ─────────────────────────────────
   Mesuré à 768 × 1024 (outils/banc-tient-ecran.js) : entre 721 et 900 px
   les trois dossiers s empilaient, et la photo de Karine passait au-dessus
   de son texte — deux étapes plus hautes que l écran, même réduites.
   La largeur suffit pour les garder côte à côte ; on n empile qu au
   téléphone, où les étapes défilent dans le flux. */
@media (min-width: 721px) and (max-width: 900px) {
  .dossiers { grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--f3); }
  .dossier-vue { height: clamp(150px, 22vh, 240px); }
}
@media (min-width: 721px) and (max-width: 860px) {
  .duo--or { grid-template-columns: minmax(0, .85fr) minmax(0, 1.15fr); gap: var(--f4); }
}


/* ── LES PHOTOS DU SITE, TOUTES AU MÊME TRAITEMENT (20/09) ──────────
   Sa remarque : « toutes les slides doivent avoir le même niveau visuel ».
   Mesuré sur les 27 planches : les fonds, les portraits, les dossiers et
   les bibliothèques sont en noir et blanc — mais deux photos posées DANS
   une étape restaient en couleur (le kayak de « Plus de quatre-vingts »,
   les agents de « Les rendez-vous + »), et cassaient la série.
   Elles passent donc au noir et blanc, et reprennent leurs couleurs au
   survol, comme les portraits de l'organigramme et les vignettes.
   ⚠️ Les DOCUMENTS gardent leurs couleurs : une affiche Qi Gong, un flyer
   Kundalini, le planning papier ou un QR code se lisent en couleur —
   c'est leur impression, pas une photo du klub. */
.cadre:not(.cadre--doc) > img,
.cadre:not(.cadre--doc) > video {
  filter: grayscale(1) contrast(1.04);
  transition: transform 1.4s var(--gout), filter .8s var(--gout);
}
.cadre:not(.cadre--doc):hover > img,
.cadre:not(.cadre--doc):hover > video { filter: none; }
@media (prefers-reduced-motion: reduce) {
  .cadre:not(.cadre--doc) > img, .cadre:not(.cadre--doc) > video { transition: none; }
}


/* ── UN SEUL TITRE D ÉTAPE (20/09) ──────────────────────────────────
   Sa remarque : « gère mieux les titres des sessions ». Ils étaient écrits
   de deux façons (h3.sous à 41,9 px, titre--moyen à 67,8 px) : les étapes
   ne se ressemblaient pas. Une seule taille, une seule respiration, et le
   même mouvement de mots que les grands titres. */
.titre--etape { font-size: clamp(var(--t7), 3.6vw, var(--t8)); line-height: 1.06; margin: 0 0 var(--f5); }
.titre--etape + .texte, .titre--etape + .micro { margin-top: calc(-1 * var(--f2)); }
@media (max-height: 880px) and (min-width: 721px) { .titre--etape { font-size: var(--t7); margin-bottom: var(--f4); } }
@media (max-width: 720px) { .titre--etape { font-size: var(--t6); margin-bottom: var(--f4); } }


/* ── LES ÉVÉNEMENTS DE L'AFFICHE (22/09) ────────────────────────────
   Sa règle : en cours comme en planning, seuls les éléments des 4 affiches.
   « Un klub, pas une salle de sport » ne garde que les marches, les soirées
   et les rencontres du planning, et sa chute telle quelle. */
.vie:has(> div:nth-child(3):last-child) { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.vie-chute { margin-top: var(--f5); letter-spacing: .14em; }
@media (max-width: 720px) { .vie:has(> div:nth-child(3):last-child) { grid-template-columns: 1fr; } }

/* 22/09 — ERGONOMIE : « tout doit être visible ». Le détail des cours n'est
   plus une boîte à faire défiler sous un fondu (on voyait 2 cours de Cardio
   sur 5, sans rien qui dise qu'il y en avait d'autres) : la liste s'affiche
   en entier, sur deux colonnes quand la place le permet ; ajusteEtapes()
   réduit l'étape si elle dépasse encore l'écran. */
@media (min-width: 721px) {
  .liste-cours { max-height: none; overflow: visible; -webkit-mask-image: none; mask-image: none; padding-bottom: 0;
    display: grid; grid-template-columns: repeat(auto-fill, minmax(min(100%, 17rem), 1fr)); column-gap: var(--f5); }
  .liste-cours .cours { padding: var(--f3) 0; }
}
.actions-rejoindre { margin-top: var(--f5); gap: var(--f3); flex-wrap: wrap; }
.salle .lien-tel { display: inline-block; margin-top: var(--f2); }
/* 22/09 — chaque cours se lit d'un coup d'œil (nom, jour, heure, salle) ;
   la description tient en 3 lignes et se déplie au clic. */
@media (min-width: 721px) {
  .liste-cours .cours p { display: -webkit-box; -webkit-box-orient: vertical; -webkit-line-clamp: 3; overflow: hidden; }
  .liste-cours .cours.deplie p { -webkit-line-clamp: unset; display: block; }
  .liste-cours .cours { cursor: pointer; }
  .liste-cours .cours:focus-visible { outline: 2px solid var(--terra, currentColor); outline-offset: 2px; }
}
/* 22/09 — le QR HelloAsso dans « Comment ça se passe », étape 02 */
.qr--marche { justify-items: start; margin-top: var(--f3); width: max-content; }

/* 22/09 — « PLUS QU'UN KLUB, UN KLAN » (sa demande : moins neutre, jouer sur
   les tailles et les couleurs). Titre en grand, « un klan » en rouge ;
   l'article en étiquette rouge, le mot en très grand, le texte adouci ;
   un filet rouge coiffe chaque colonne ; la chute de l'affiche en accent. */
.titre--etape.titre--klan { font-size: clamp(var(--t8), 5.2vw, var(--t10)); line-height: 1; margin-bottom: 0; }
.vie--klan { border-top: 0; column-gap: var(--f5); }
.etape .vie.vie--klan .vie-item { border-bottom: 0; border-top: 2px solid var(--terra); padding: var(--f4) var(--f3) 0; }
.vie--klan .vie-art { display: block; letter-spacing: .18em; margin-bottom: var(--f1); }
.vie--klan b { font-size: clamp(var(--t6), 2.8vw, var(--t8)); line-height: 1; letter-spacing: -.025em; }
.vie--klan p { color: var(--faible); font-size: var(--t4); margin-top: var(--f3); }
.vie-chute { font-family: var(--police); font-weight: 700; font-size: clamp(var(--t5), 2vw, var(--t6));
  color: var(--terra); text-transform: uppercase; letter-spacing: .06em; margin-top: var(--f6); }
@media (max-height: 880px) and (min-width: 721px) {
  .titre--etape.titre--klan { font-size: var(--t9); }
  .vie--klan b { font-size: var(--t7); }
}
@media (max-width: 720px) {
  .titre--etape.titre--klan { font-size: var(--t8); }
  .vie--klan { row-gap: var(--f4); }
  .vie--klan b { font-size: var(--t6); }
  .vie-chute { font-size: var(--t4); }
}
.marche-lien { display: inline-block; margin-top: var(--f3); }

/* 23/09 — FIN DE RUBRIQUE : le site dit pourquoi il ne bouge plus (sa demande :
   le défilement ne change plus de catégorie). */
.fin-rubrique { position: fixed; left: 50%; bottom: calc(var(--f5) + env(safe-area-inset-bottom, 0px));
  transform: translate(-50%, 8px); z-index: 60; margin: 0; padding: var(--f2) var(--f4);
  border: 1px solid var(--terra); border-radius: 999px; background: var(--ecran-fort); backdrop-filter: blur(10px);
  letter-spacing: .08em; text-align: center; max-width: min(92vw, 34rem);
  opacity: 0; pointer-events: none; transition: opacity .28s ease, transform .28s ease; }
.fin-rubrique.vu { opacity: 1; transform: translate(-50%, 0); }
@media (prefers-reduced-motion: reduce) { .fin-rubrique { transition: none; } }

/* 23/09 soir — téléphone : la rubrique en cours, à côté de la marque */
.marque-ici { display: none; }
html.telephone .marque-nom { white-space: nowrap; }
html.telephone .marque-ici { display: inline; white-space: nowrap; margin-left: 0; padding-left: var(--f2); border-left: 1px solid var(--terra);
  font: 500 var(--t1)/1 var(--police); letter-spacing: .14em; text-transform: uppercase; color: var(--terra); }
html.telephone .marque-s { display: none; }
