/* ══════════════════════════════════════════════════════════════
   Article Single — Page de contenu individuel
   ══════════════════════════════════════════════════════════════

   @grammaire v2

   97 LITTERAUX RETIRES, en trois familles qui ne se traitent pas pareil :

   · L'IMPRESSION (31). Dix gris pour trois roles — #000, #333, #444, #555,
     #666, #888, #999, #ccc, #ddd, #eee. Personne ne decide qu'une meta
     s'imprime en #666 ici et en #888 la : c'est de la reecriture, pas un
     choix. Trois jetons les remplacent (`--print-ink`, `--print-ink-soft`,
     `--print-ink-muted`), plus un filet et un aplat. Quelques valeurs bougent
     donc d'un ou deux crans de gris a l'impression, et c'est le but.

   · LES VALEURS A RENDU CONSTANT (52). `#fff` vers `--surface-2`, les voiles
     et ombres `rgba()` vers un `color-mix` sur le jeton de meme valeur. Aucun
     pixel ne change.

   · LA PALETTE EGAREE (14). `#dc2626`, `#ca8a04`, `#2563eb` et leurs teintes
     sont des couleurs TAILWIND, presentes dans huit feuilles du depot a cote
     de la palette de marque. Elles passent aux jetons de marque
     (`--color-danger`, `--color-warning`, `--color-info`) — une marque n'a
     qu'une palette.

     A L'ECRAN, RIEN NE CHANGE : ces quatorze litteraux vivent tous dans
     `.resource-single__badge--*` et `.resource-single__cover-placeholder--*`,
     que AUCUN gabarit n'emet. Verifie par grep sur `templates/`. J'avais
     d'abord annonce ce changement comme « le seul visible » de la migration ;
     il ne l'est pas, il n'est visible nulle part. Ces regles sont mortes, et
     c'est un lot a part que de les retirer.

   Les six `@media (max-width: X.9375em)` passent en syntaxe de plage : le
   pendant a decimale laisse un trou d'un dixieme de pixel. */

/* PAS DE REMBOURRAGE BAS. Le bandeau d'abonnement suit TOUTES les pages
   publiques et porte deja sa propre respiration : les deux s'ajoutaient en
   112 px de blanc entre la derniere carte et la lettre du reseau, pour 30 px
   entre celle-ci et le pied — le bandeau paraissait pousse vers le bas,
   detache de la page sans etre rattache au pied. Mesure du 2026-08-31 sur la
   fiche de glossaire et le centre d'aide.

   L'ecart appartient a ce qui SEPARE, pas a ce qui precede : meme regle que
   pour les etiquettes de la barre de liste, et que pour les deux sections d'une
   fiche corrigees le meme jour. */
.article-single {
    padding-bottom: 0;
}

/* Hero image — caled sur `--container-max` (largeur du mega-menu / `.container`)
   pour aligner les bords du hero sur ceux de la barre de navigation. */
.article-single__hero {
    position: relative;
    width: 100%;
    max-width: var(--container-max);
    margin-inline: auto;
    min-height: 20rem;
    max-height: 32rem;
    overflow: hidden;
    background: var(--color-bg-light);
}

.article-single__hero img {
    width: 100%;
    height: 100%;
    min-height: 20rem;
    max-height: 32rem;
    object-fit: cover;
}

@media (min-width: 40em) {
    .article-single__hero {
        min-height: 24rem;
        max-height: 36rem;
    }

    .article-single__hero img {
        min-height: 24rem;
        max-height: 36rem;
    }
}

/* Breadcrumb intégré au hero — overlay haut avec dégradé pour lisibilité */
.article-single__hero-top {
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    background: linear-gradient(to bottom, color-mix(in srgb, var(--color-shade) 55%, transparent) 0%, transparent 100%);
    padding-bottom: var(--spacing-md);
    z-index: 1;
}

/* Override des couleurs du breadcrumb canonique quand il vit dans le hero */
.article-single__hero-top .breadcrumb-bar {
    background: transparent;
    display: block;
}

.article-single__hero-top .breadcrumb__list {
    padding-top: var(--spacing-sm);
    padding-bottom: 0;
}

.article-single__hero-top .breadcrumb__item,
.article-single__hero-top .breadcrumb__item--active {
    color: color-mix(in srgb, var(--color-on-primary) 85%, transparent);
}

.article-single__hero-top .breadcrumb__item a {
    color: color-mix(in srgb, var(--color-on-primary) 75%, transparent);
}

.article-single__hero-top .breadcrumb__item a:hover {
    color: var(--surface-2);
}

.article-single__hero-top .breadcrumb__item:not(:last-child)::after {
    color: color-mix(in srgb, var(--color-on-primary) 40%, transparent);
}

/* Overlay sombre en bas du hero (titre + meta) */
.article-single__hero-overlay {
    position: absolute;
    bottom: 0;
    left: 0;
    right: 0;
    background: linear-gradient(to top, color-mix(in srgb, var(--color-shade) 85%, transparent) 0%, color-mix(in srgb, var(--color-shade) 60%, transparent) 40%, color-mix(in srgb, var(--color-shade) 20%, transparent) 70%, transparent 100%);
    padding-top: 6rem;
    padding-bottom: var(--spacing-lg);
}

/* Meta dans le hero (badge type + date) */
.article-single__hero-meta {
    display: flex;
    align-items: center;
    gap: var(--spacing-sm);
    margin-bottom: var(--spacing-sm);
}

.article-single__hero-type {
    display: inline-flex;
    align-items: center;
    padding: 0.1875rem 0.625rem;
    border-radius: 100px;
    font-size: var(--font-size-xs);
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    background: color-mix(in srgb, var(--color-on-primary) 20%, transparent);
    color: var(--surface-2);
    backdrop-filter: blur(4px);
}

.article-single__hero-date {
    font-size: var(--font-size-sm);
    color: color-mix(in srgb, var(--color-on-primary) 80%, transparent);
}

/* Titre dans le hero */
.article-single__hero-title {
    font-size: var(--font-size-2xl);
    font-weight: 700;
    line-height: var(--line-height-tight);
    color: var(--surface-2);
    margin: 0;
    text-shadow: 0 1px 3px color-mix(in srgb, var(--color-shade) 30%, transparent);
}

@media (min-width: 40em) {
    .article-single__hero-title {
        font-size: var(--font-size-3xl);
    }
}

@media (min-width: 64em) {
    .article-single__hero-title {
        font-size: var(--font-size-4xl);
        max-width: 48rem;
    }
}

/* Chapô / lead paragraph (intégré à la colonne principale, contraint à sa largeur) */
/* Aucun filet sous le chapô : il porte déjà sa propre distinction — italique,
   plus grand, gris — et la ligne suivante est du texte courant noir. Le trait
   ajoutait une seconde règle horizontale à quelques dizaines de pixels de
   celle qui ferme l'en-tête, sans rien dire de plus qu'elles ne disent déjà.
   L'espace suffit à séparer. */
.article-single__lead-text {
    margin: 0 0 var(--spacing-xl);
    font-size: var(--font-size-lg);
    line-height: var(--line-height-base);
    color: var(--color-text-light);
    font-style: italic;
}

@media (min-width: 40em) {
    .article-single__lead-text {
        font-size: 1.1875rem;
    }
}

/* Layout : contenu + sidebar droite.
   Padding-top reduit : la card hero porte deja un `margin-bottom`
   `--spacing-xl`, doubler avec `--spacing-xl` ici creusait un creux
   visuel entre le hero et le body. `--spacing-sm` suffit a separer
   sans rompre la lecture. */
/* Aucune largeur propre ni retrait latéral : le contenu s'aligne sur son
   en-tête, qui est posé dans le `.container` de la page.
   Il portait `max-width: 72rem` + un retrait de 16 px, soit une colonne 64 px
   plus étroite que l'en-tête au-dessus — décalage visible dès qu'un fond ou
   une card marque le bord de l'en-tête, et écarts de largeur entre une fiche
   actualité et une page institutionnelle qui portent pourtant le même
   contenu. */
/* Le layout est posé DANS un `.container`, comme celui de la page
   institutionnelle : c'est ce qui aligne le contenu sur le bord de l'en-tête.
   Il portait ses propres bornes (`max-width: 72rem` + retrait de 16 px), soit
   une colonne 64 px plus étroite que la card au-dessus — décalage visible, et
   largeurs différentes entre une fiche actualité et une page pour un contenu
   de même nature. Rejouer les bornes du conteneur à la main, c'est aussi
   rejouer ses points de rupture : mieux vaut l'utiliser. */
/* ── LA CARTE DE L'ARTICLE ──
   Un seul cadre, de la ligne de qualification aux etiquettes, comme la maquette.
   Le rembourrage est genereux parce que la carte porte du TEXTE LONG : le meme
   rembourrage qu'une carte de liste collerait les paragraphes au filet.

   Il se resserre sous le palier telephone, ou 48 px de chaque cote laisseraient
   moins de la moitie de la largeur au texte. */
/* La colonne de TEXTE est bornee, pas la carte : les titres, les figures et les
   encarts prennent toute sa largeur, le texte suivi s'arrete a la mesure. Sans
   cela, a 1000 px — la ou le rail disparait — la ligne montait a 854 px. */
/* LA BORNE EST SUR LE TEXTE, PAS SUR LA CARTE — et c'est un aller-retour :
   posee sur la carte, `ch` s'y resout avec la police de la CARTE et non celle du
   corps, ce qui l'a ramenee a 637 px au lieu des ~800 attendus. L'unite `ch` ne
   veut dire quelque chose que la ou la police du texte s'applique.

   La maquette borne elle aussi le texte seul : les titres et les figures vont au
   bord de la carte, les paragraphes s'arretent avant. */
.article-single__body {
    max-width: var(--measure-prose);
    /* LE CORPS D'UN ARTICLE SE LIT PLUS GRAND. La maquette pose 17,5 px, le site
       rendait 16 : a mesure egale (68 signes), un corps plus petit donne une
       colonne plus etroite ET un texte plus dense — c'est ce qui faisait paraitre
       la largeur « trop contrainte » alors que le nombre de signes etait juste.

       18 px et non 17,5 : c'est le cran `lg` de l'echelle. Inventer une valeur
       intermediaire pour coller au pixel pres a la maquette ajouterait une taille
       hors gamme, que rien ne ferait bouger le jour ou l'echelle bouge.

       Porte par le CORPS D'ARTICLE seul, pas par `.prose-content` : le meme
       composant sert l'aide, les minisites et les pages institutionnelles, ou
       rien ne dit que le texte est du long format. */
    font-size: var(--font-size-lg);
}

/* ── LA CARTE DE SIGNATURE ──
   Un cadre leger, pas une carte de premier plan : elle ferme l'article, elle ne
   le concurrence pas. D'ou un filet et aucune ombre — la charte n'admet qu'une
   ombre par vue, et c'est la carte de l'article qui la porte.

   Les initiales plutot qu'un portrait : une commission n'a pas de visage, et un
   sigle se lit a toutes les tailles sans charger d'image. */
.author-card {
    display: flex;
    align-items: flex-start;
    gap: var(--spacing-md);
    padding: var(--spacing-lg);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
}

/* L'avatar est la brique `ui-avatar` : il n'a plus de regle propre. Sept
   definitions du meme rond existaient dans le depot, celle-ci comprise. */

.author-card__text {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-xs);
    min-width: 0;
}

.author-card__name {
    margin: 0;
    font-family: var(--font-title);
    font-size: var(--font-size-lg);
    font-weight: 700;
    color: var(--color-primary-dark);
}

.author-card__role {
    margin: 0;
    font-size: var(--font-size-sm);
    line-height: var(--line-height-base);
    color: var(--color-text-light);
    max-width: 60ch;
}

.author-card__link {
    align-self: flex-start;
    font-size: var(--font-size-sm);
    font-weight: 600;
    color: var(--color-primary);
}

/* ── PRECEDENT / SUIVANT ──
   Deux colonnes de meme rang. `auto-fit` avec un plancher : sous la largeur ou
   les deux tiennent, elles passent l'une sous l'autre — un lien de 120 px de
   large ne se lit plus. */
.article-nav {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(min(100%, 15rem), 1fr));
    gap: var(--spacing-md);
}

.article-nav__link {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-xs);
    padding: var(--spacing-md) var(--spacing-lg);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    text-decoration: none;
    transition: border-color var(--motion-1) var(--easing-standard);
}

/* LE SENS : icone et sur-titre sur une ligne, alignes sur le texte et non sur
   la boite. La fleche n'est pas un ornement, c'est ce qui distingue les deux
   liens l'un de l'autre — le libelle le dit aussi, mais on lit la direction
   avant de lire le mot. */
.article-nav__direction {
    display: flex;
    align-items: center;
    gap: var(--spacing-xs);
    color: var(--color-text-light);
}

/* Le suivant pousse sa fleche a DROITE du sur-titre : la rangee se lit alors
   comme ce qu'elle est, deux directions opposees depuis un meme point. */
.article-nav__link--next .article-nav__direction {
    justify-content: flex-end;
}

.article-nav__link--next {
    text-align: right;
}

.article-nav__link:hover {
    border-color: var(--color-primary);
}

/* LE SUIVANT S'ALIGNE A DROITE, et ce n'est pas decoratif : un lien « suivant »
   pointe vers l'avant, donc son texte doit finir la ou l'oeil va. Aligne a
   gauche, la fleche du sur-titre pointait vers un bord de carte vide. */
.article-nav__link--next {
    align-items: flex-end;
    text-align: right;
}

.article-nav__title {
    font-family: var(--font-title);
    font-size: var(--font-size-base);
    font-weight: 700;
    line-height: var(--line-height-tight);
    color: var(--color-primary-dark);
    text-wrap: pretty;
}

/* La case vide TIENT SA COLONNE quand il n'y a qu'un voisin : sans elle, le
   lien restant s'etalerait sur toute la largeur et se lirait comme une banniere
   plutot que comme l'une des deux directions. */
.article-nav__empty {
    display: block;
}

/* ── LES ETIQUETTES DE PIED ──
   Une colonne a gouttiere, comme partout : l'intitule puis la rangee. Elles
   s'enroulent, et c'est voulu — un article peut en porter six. */
.article-single__tags {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-sm);
}

.article-single__tags-list {
    display: flex;
    flex-wrap: wrap;
    gap: var(--spacing-sm);
}

.article-single__card {
    /* 32 ET NON 48. `ui-card` — la carte de tout le site — porte 32 ; celle-ci
       en portait 48, et personne ne pouvait le voir depuis un seul fichier.
       L'ecart passe inapercu sur un article de deux mille mots ; il saute aux
       yeux sur une reponse de deux lignes, ou 48 px de blanc au-dessus et
       au-dessous pesaient plus que le texte. Le modele est le meme pour les
       deux — actualite, fiche de ressource, terme de glossaire, question
       frequente — donc son rembourrage aussi. */
    padding: var(--spacing-xl);
    /* UNE COLONNE A GOUTTIERE UNIQUE, et non une pile de marges. La carte
       enchaine l'en-tete, le corps, les zones et la rangee de partage ; chacun
       portait sa propre marge, donc quatre valeurs a tenir d'accord (20, 32, 24
       mesures) et une fusion de marges a chaque jonction.

       Un `gap` unique les remplace : il ne fusionne pas, et il n'a qu'un endroit
       ou etre change. Meme geste que `.content-list__main`, et c'est le meme
       jeton — le rythme d'une page du site ne depend pas de la page. */
    display: flex;
    flex-direction: column;
    gap: var(--spacing-lg);
}

/* Les blocs de la carte ne portent plus d'ecart propre : c'est la gouttiere de
   la colonne qui le donne. Sans cette remise a zero, l'ancienne marge s'AJOUTE
   au `gap` au lieu de le remplacer. */
.article-single__card > * {
    margin-block: 0;
}

@media (width < 48em) {
    .article-single__card {
        padding: var(--spacing-lg);
    }
}

/* 24 px sous le fil d'Ariane, et non 8. La fiche ouvre sur une CARTE, qui a
   besoin de se detacher du fond ; a 8 px elle collait au fil et les deux se
   lisaient comme un seul bloc. C'est aussi la gouttiere que la page pose
   partout ailleurs — le rythme d'une page ne change pas parce qu'on change de
   gabarit. */
.article-single__layout {
    padding: var(--spacing-lg) 0 0;
}

@media (min-width: 64em) {
    /* 20 rem (320 px) et non 16,25 : c'est la largeur de la maquette, et le rail
       porte desormais deux blocs — le suivi de lecture et le prochain
       rendez-vous. A 260 px, les titres du sommaire cassaient sur trois lignes
       et la date du rendez-vous se serrait contre son mois.

       La page institutionnelle a la MEME largeur depuis le 2026-08-29 : elle
       rend ce squelette, et deux largeurs de rail sur deux pages de la meme
       grammaire est precisement la divergence que la migration supprime. */
    .article-single__layout {
        display: grid;
        grid-template-columns: 1fr 20rem;
        /* 24 et non 48 : le rail est un APPUI, pas une seconde colonne de
           lecture. A 48 px il flottait detache de l'article, et la page se
           lisait comme deux pages voisines. La maquette pose la meme gouttiere
           que partout ailleurs sur le site. */
        gap: var(--spacing-lg);
    }

}

/* >= 80em : on insère le rail de partage vertical en première colonne,
   UNIQUEMENT pour les layouts qui portent réellement un `.reading-share-rail`
   (article, page, formation). Les autres réutilisateurs de
   `.article-single__layout` (event, dossier) restent à 2 colonnes — sinon
   leur colonne principale serait écrasée dans les 3rem du rail absent. */
@media (min-width: 80em) {
    .article-single__layout:has(.reading-share-rail) {
        grid-template-columns: 3rem 1fr 15rem;
        gap: var(--spacing-xl);
    }
}

/* Pas de plafond propre : la colonne prend la largeur que lui donne la grille,
   exactement comme celle de la page institutionnelle. Un `max-width` ici la
   rendait plus étroite de 12 px que sa voisine, pour la même grille. */
.article-single__main {
    min-width: 0;
    /* UNE COLONNE A GOUTTIERE UNIQUE, comme la carte qu'elle contient. Les
       blocs empiles ici — carte de lecture, bandeau d'assistance, zones de
       rebond — portaient chacun leur propre marge, donc autant de valeurs a
       tenir d'accord, et une fusion de marges a chaque jonction.

       Les marges des enfants sont neutralisees DEPUIS LE CONTENEUR et non
       retirees a la source : `helpcenter__cta` est aussi inclus hors de cette
       colonne (accueil du centre d'aide, page de rubrique), ou sa marge reste
       le seul ecart qui l'espace. */
    display: flex;
    flex-direction: column;
    gap: var(--rhythm-block);
}

.article-single__main > * {
    margin-block: 0;
}

/* Header (fallback sans hero image) */
.article-single__header {
    padding-top: var(--spacing-xl);
    padding-bottom: var(--spacing-xl);
    border-bottom: 1px solid var(--color-border);
    margin-bottom: var(--spacing-xl);
}

.article-single__meta {
    display: flex;
    align-items: center;
    gap: var(--spacing-sm);
    margin-bottom: var(--spacing-md);
}

.article-single__date {
    font-size: var(--font-size-sm);
    color: var(--color-text-light);
}

.article-single__title {
    font-size: var(--font-size-2xl);
    font-weight: 700;
    line-height: var(--line-height-tight);
    color: var(--color-text);
    margin-bottom: var(--spacing-md);
}

@media (min-width: 40em) {
    .article-single__title {
        font-size: var(--font-size-3xl);
    }
}

@media (min-width: 64em) {
    .article-single__title {
        font-size: var(--font-size-4xl);
    }
}

/* Body */
/* PLUS DE REMBOURRAGE BAS : il s'ajoutait a la gouttiere de la carte, qui donne
   desormais tous les ecarts de la colonne. Meme regle que pour l'en-tete en
   `plain` — un bloc pose dans une colonne a gouttiere n'en declare aucun. */

.article-single__zone {
    padding-top: var(--spacing-xl);
    border-top: 1px solid var(--color-border);
}

/* ══════════════════════════════════════════════════════════════
   Article Sidebar — TOC + Partage + Citer (sticky droite)
   ══════════════════════════════════════════════════════════════ */

.article-sidebar {
    display: none;
}

@media (min-width: 64em) {
    .article-sidebar {
        display: block;
        position: relative;
    }
}

/* ── LE RAIL QUI PORTE DES SORTIES NE DISPARAIT PAS SOUS LE PALIER ──
   Le `display: none` ci-dessus vaut pour un rail de SOMMAIRE : sur telephone,
   une table des matieres double le titre qu'on est en train de lire, et la
   masquer ne coute rien.

   Il ne vaut pas pour un rail qui porte les seules SORTIES d'une fiche. Le cas
   mesure : une entree de glossaire tient en trois lignes, son rail porte ses
   termes voisins et le signalement d'une definition fausse — masques, la fiche
   redevient l'impasse qu'elle etait avant qu'on lui donne des voisins.

   Empile plutot que masque : il tombe sous la colonne de lecture, ou il se lit
   comme la suite naturelle d'une page courte. */
.article-sidebar--stacked {
    display: block;
}

@media (width < 64em) {
    .article-sidebar--stacked {
        margin-top: var(--spacing-xl);
    }

    /* Collant n'a aucun sens en pile : la carte se figerait au milieu du
       defilement, sur une page qui n'a plus de seconde colonne. */
    .article-sidebar--stacked .article-sidebar__sticky {
        position: static;
    }
}

/* Le rail porte desormais DEUX blocs — le sommaire puis le prochain rendez-vous —
   donc une colonne a gouttiere unique plutot que deux elements colles.

   6 rem et non 5 : la barre condensee occupe 86 px du haut de la fenetre, pas 56.
   A 80 px le sommaire passait SOUS elle de six pixels des qu'on defilait. Meme
   correction que sur le rail de la liste, meme cause. */
.article-sidebar__sticky {
    position: sticky;
    top: 6rem;
    max-height: calc(100vh - 7rem);
    overflow-y: auto;
    display: flex;
    flex-direction: column;
    gap: var(--spacing-md);
}

/* Header du sommaire : titre « Sommaire » + toggle replier sur la MÊME ligne.
   Replié, le titre disparaît (x-show) et le toggle se cale à droite pour
   hugger la marge du rail réduit. */
.article-sidebar__header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--spacing-sm);
    margin-bottom: var(--spacing-sm);
}

.article-sidebar--collapsed .article-sidebar__header {
    justify-content: flex-end;
}

.article-sidebar__header .article-sidebar__section-title {
    margin-bottom: 0;
}

/* Toggle plier/déplier — petit bouton rond aligné sur la ligne « Sommaire ».
   Replié, l'aside se réduit à la largeur du bouton (grid-template-columns
   ... auto), seul le toggle reste pour rouvrir. */
.article-sidebar__toggle {
    flex-shrink: 0;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 1.75rem;
    height: 1.75rem;
    padding: 0;
    border: 1px solid var(--color-border);
    border-radius: 50%;
    background: var(--surface-2);
    color: var(--color-text-light);
    cursor: pointer;
    transition: color 0.15s ease, border-color 0.15s ease;
}

.article-sidebar__toggle:hover {
    color: var(--color-primary);
    border-color: var(--color-primary);
}

/* Asides à structure historique (formation, event, dossier) : le toggle est
   un enfant DIRECT de `.article-sidebar` (pas dans un `.article-sidebar__header`).
   On lui rend son ancrage sticky + alignement à droite que le refactor de
   l'aside CMS avait retirés. L'article CMS, lui, niche son toggle dans
   `.article-sidebar__sticky > .article-sidebar__header` — ce sélecteur
   enfant-direct ne le matche donc pas. */
.article-sidebar > .article-sidebar__toggle {
    position: sticky;
    top: 5rem;
    margin-left: auto;
    margin-bottom: var(--spacing-sm);
    z-index: 2;
}

@media (min-width: 64em) {
    .article-sidebar {
        display: flex;
        flex-direction: column;
    }
}

/* État replié : seul le header (donc le toggle pour rouvrir) reste visible.
   Le titre « Sommaire » et la liste TOC sont masqués par `x-show` côté markup ;
   l'aside se réduit à la largeur du toggle via grid-template-columns ... auto. */
.article-sidebar--collapsed .article-sidebar__toc-wrap { display: none !important; }

@media (min-width: 64em) {
    .article-single__layout:has(.article-sidebar--collapsed) {
        grid-template-columns: 1fr auto;
    }
}

@media (min-width: 80em) {
    .article-single__layout:has(.reading-share-rail):has(.article-sidebar--collapsed) {
        grid-template-columns: 3rem 1fr auto;
    }
}

/* .article-sidebar__section-title → déplacé dans content.css (composant transversal) */

.article-sidebar__sep {
    border: none;
    border-top: 1px solid var(--color-border);
    margin: var(--spacing-md) 0;
}

.article-sidebar__sep--toc {
    display: block;
}

/* Partage */
/* ── LE BLOC DE REBOND D'UNE COLONNE D'APPUI ──

   La maquette « Page actualite ANCESU » pose trois blocs dans cette colonne, et
   AUCUN ne porte d'image : un voile blanc, un filet colore, un titre, puis des
   lignes. C'est la grammaire de l'aside de ce site, et une carte a vignette y
   etait etrangere — d'ou le retrait des visuels cote gabarit.

   LE VOILE, PAS LA CARTE. `rgba(255, 255, 255, .62)` sans bordure ni ombre :
   l'aside accompagne la lecture, il ne pose pas d'objets qui lui disputent
   l'attention. C'est exactement la surface de `_rail_card`, qui traduit deja
   ces memes blocs pour les pages de liste. */
.article-sidebar__section {
    padding: var(--spacing-lg) var(--spacing-lg) var(--spacing-md);
    border-radius: var(--radius-md);
    background: color-mix(in srgb, var(--color-on-primary) 62%, transparent);
}

/* La feuille perd son cadre : c'est le bloc qui porte desormais la surface, et
   deux cadres emboites a 320 px de large font un objet dans un objet. Restent
   les filets de separation, qui disent que les trois lignes sont un corpus et
   non trois cartes posees. */
.article-sidebar__section .media-cards--sheet {
    border: 0;
    border-radius: 0;
    background: none;
}

.article-sidebar__section .media-cards--sheet .media-card {
    padding-block: var(--spacing-ms);
}

/* LE CORPS PERD LE REMBOURRAGE DE LA CARTE AUTONOME. Il le porte pour une carte
   qui se suffit a elle-meme ; dans une feuille, la rangee porte deja le sien et
   les deux s'ajoutent. Mesure avant : rangee de 103 px pour un titre de 21 et
   un pied de 23, soit 32 px sans emploi. */
.article-sidebar__section .media-card__body {
    padding: 0;
}

.article-sidebar__section .media-cards--sheet .media-card:hover {
    background: none;
}

/* Le lien de fin s'aligne sur les lignes, pas sur le bord du voile. */
.article-sidebar__section > .btn {
    margin-top: var(--spacing-xs);
    padding-inline: 0;
}

/* ── UN REBOND QUI NE VIT QUE QUAND LA COLONNE D'APPUI N'EST PAS LA ──

   `.article-sidebar` est masquee sous 64em — toute la colonne, pas seulement le
   sommaire. Une fiche qui confie ses rebonds au rail les perd donc entierement
   au telephone. Cette section les rend alors en pied, et disparait des que le
   rail reapparait : les deux ne coexistent jamais.

   Mesure sur /dossiers/sse avant la regle : trois cartes a 1024 px, ZERO a 900,
   et plus aucun chemin vers un autre dossier. */
@media (width >= 64em) {
    .article-single__related--stacked-only {
        display: none;
    }
}

.article-sidebar__section {
    margin-bottom: 0;
}

.article-sidebar__actions {
    display: flex;
    gap: var(--spacing-xs);
}

.article-sidebar__btn {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 2rem;
    height: 2rem;
    border: none;
    border-radius: var(--radius-sm);
    color: var(--color-text-light);
    background: var(--color-bg-light);
    cursor: pointer;
    transition: color 0.15s ease, background-color 0.15s ease;
}

.article-sidebar__btn:hover {
    color: var(--surface-2);
    background: var(--color-primary);
}

/* ══════════════════════════════════════════════════════════════
   Rail de partage vertical (marge gauche) — desktop large (>= 80em)
   Partagé par la fiche article (grille) et la fiche page (flex). Sous
   80em : `display:none` — le partage reste dans le hero + la barre mobile.
   ══════════════════════════════════════════════════════════════ */
.reading-share-rail { display: none; }

@media (min-width: 80em) {
    .reading-share-rail {
        display: block;
        grid-column: 1; /* article (grille) : 1re colonne ; ignoré en flex (page) */
    }

    .reading-share-rail__sticky {
        position: sticky;
        top: 6rem;
        display: flex;
        flex-direction: column;
        align-items: center;
    }

    .reading-share-rail__buttons { gap: var(--spacing-sm); }

    .reading-share-rail__buttons .share-buttons__btn {
        width: 2.25rem;
        height: 2.25rem;
        border: 1px solid var(--color-border);
        border-radius: 50%;
        background: var(--surface-2);
        color: var(--color-text-light);
    }

    .reading-share-rail__buttons .share-buttons__btn:hover {
        color: var(--surface-2);
        background: var(--color-primary);
        border-color: var(--color-primary);
    }

    /* Le rail gauche reprend le partage sur ces fiches : on masque les boutons
       de partage du hero (>= 80em) pour éviter le doublon. Le fil d'Ariane reste. */
    .list-hero--article .list-hero__share-buttons,
    .list-hero--page .list-hero__share-buttons,
    .list-hero--event .list-hero__share-buttons,
    .list-hero--dossier .list-hero__share-buttons {
        display: none;
    }
}

/* ══════════════════════════════════════════════════════════════
   Jauge de progression de lecture — ligne fine fixée en HAUT du viewport,
   AU-DESSUS de la navbar (z > 1000), couleur vert ANCESU. Se remplit selon
   le % de contenu lu (scaleX piloté par le composant Alpine `readingBar`).
   Pas de fond de piste : à 0 % la barre est invisible. Décorative (aria-hidden).
   ══════════════════════════════════════════════════════════════ */
.reading-progress {
    position: fixed;
    top: 0;
    left: 0;
    right: 0;
    height: 3px;
    z-index: var(--z-navbar-attached);
    pointer-events: none;
}

.reading-progress__fill {
    display: block;
    height: 100%;
    width: 100%;
    background: var(--color-section-ancesu);
    transform-origin: left center;
    transform: scaleX(0);
    transition: transform 0.1s linear;
}

/* Marque-page « à ajouter » : petit badge « + » vert sur le bouton bookmark
   tant que le contenu n'est PAS marqué (classe --active absente). Une fois
   marqué, le badge disparaît et l'icône se remplit. Couvre toutes les
   surfaces de partage des fiches (hero, rail gauche, barre mobile). */
.share-buttons__btn--bookmark { position: relative; }

.share-buttons__btn--bookmark:not(.share-buttons__btn--active)::after {
    content: '+';
    position: absolute;
    top: -3px;
    right: -3px;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 0.85rem;
    height: 0.85rem;
    font-size: 0.6rem;
    font-weight: 700;
    line-height: 1;
    color: var(--surface-2);
    background: var(--color-section-ancesu);
    border-radius: 50%;
    pointer-events: none;
}

/* ══════════════════════════════════════════════════════════════
   Resource Single — page de détail ressource
   ══════════════════════════════════════════════════════════════ */
.resource-single { max-width: 80rem; margin: 0 auto; }

/* Layout 2 colonnes : aside (infos) + main (viewer) */
.resource-single__layout {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-xl);
}

@media (min-width: 64em) {
    .resource-single__layout--with-viewer {
        display: grid;
        grid-template-columns: 18rem 1fr;
        gap: var(--spacing-xl);
        align-items: start;
    }
}

/* Aside : sticky sur desktop */
.resource-single__aside {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-md);
}

@media (min-width: 64em) {
    .resource-single__layout--with-viewer .resource-single__aside {
        position: sticky;
        top: 5rem;
    }
}

/* Main : conserve `min-width: 0` defensive pour les viewers qui ont
   leur propre min-width (PDF iframe). L'alignement avec le hero est
   desormais porte par la grille englobante `.library-show__layout`. */
.resource-single__main { min-width: 0; }

/* Couverture */
.resource-single__cover-img {
    border-radius: var(--radius-md);
    overflow: hidden;
    background: linear-gradient(135deg, var(--color-bg-light) 0%, var(--color-neutral-soft) 100%);
    border: 1px solid color-mix(in srgb, var(--color-shade) 6%, transparent);
    aspect-ratio: 3/4;
    max-width: 14rem;
}
.resource-single__cover-img img { width: 100%; height: 100%; object-fit: contain; }

.resource-single__cover-placeholder {
    display: flex;
    align-items: center;
    justify-content: center;
    aspect-ratio: 3/4;
    border-radius: var(--radius-md);
    max-width: 14rem;
}
.resource-single__cover-placeholder--pdf { background: color-mix(in srgb, var(--color-danger) 8%, var(--surface-2)); color: var(--color-danger); }
.resource-single__cover-placeholder--video { background: color-mix(in srgb, var(--color-warning) 12%, var(--surface-2)); color: var(--color-warning); }
.resource-single__cover-placeholder--link { background: color-mix(in srgb, var(--color-info) 8%, var(--surface-2)); color: var(--color-info); }
.resource-single__cover-placeholder--default { background: var(--color-bg-light); color: var(--color-text-light); }

.resource-single__meta { display: flex; align-items: center; gap: var(--spacing-xs); margin-bottom: var(--spacing-sm); }

.resource-single__badge {
    display: inline-flex;
    padding: 0.125rem 0.5rem;
    border-radius: var(--radius-sm);
    font-size: 0.6875rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
}
.resource-single__badge--pdf { background: color-mix(in srgb, var(--color-danger) 8%, var(--surface-2)); color: var(--color-danger); }
.resource-single__badge--video { background: color-mix(in srgb, var(--color-warning) 12%, var(--surface-2)); color: var(--color-warning); }
.resource-single__badge--link { background: color-mix(in srgb, var(--color-info) 8%, var(--surface-2)); color: var(--color-info); }

.resource-single__date { font-size: var(--font-size-xs); color: var(--color-text-light); }

.resource-single__title { font-size: 1.5rem; font-weight: 700; line-height: 1.3; margin-bottom: var(--spacing-sm); }

.resource-single__excerpt { font-size: var(--font-size-sm); color: var(--color-text-light); line-height: 1.5; margin-bottom: var(--spacing-md); }

.resource-single__file-meta {
    display: flex;
    align-items: center;
    gap: var(--spacing-xs);
    font-size: var(--font-size-xs);
    color: var(--color-text-light);
    margin-bottom: var(--spacing-md);
}
.resource-single__filename { display: inline-flex; align-items: center; gap: 0.25rem; }
.resource-single__filename + .resource-single__filesize::before { content: '·'; margin-right: var(--spacing-xs); }

/* Actions */
.resource-single__actions { display: flex; align-items: center; gap: var(--spacing-sm); flex-wrap: wrap; margin-top: auto; }

.resource-single__btn {
    display: inline-flex;
    align-items: center;
    gap: var(--spacing-xs);
    padding: 0.5rem 1rem;
    border-radius: var(--radius-md);
    font-size: var(--font-size-sm);
    font-weight: 600;
    text-decoration: none;
    border: 1px solid var(--color-border);
    color: var(--color-text);
    background: var(--surface-2);
    cursor: pointer;
    transition: background 0.15s ease, border-color 0.15s ease;
}
.resource-single__btn:hover { background: var(--color-bg-light); }

.resource-single__btn--primary {
    background: var(--color-primary);
    color: var(--surface-2);
    border-color: var(--color-primary);
}
.resource-single__btn--primary:hover { background: var(--color-primary-dark); border-color: var(--color-primary-dark); }

.resource-single__share { display: flex; align-items: center; gap: var(--spacing-xs); }
.resource-single__share-label { font-size: var(--font-size-xs); font-weight: 600; color: var(--color-text-light); margin-right: var(--spacing-xs); }
.resource-single__share-btn {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 2.25rem;
    height: 2.25rem;
    border-radius: 50%;
    border: 1px solid var(--color-border);
    color: var(--color-text-light);
    transition: color 0.15s ease, background 0.15s ease;
}
.resource-single__share-btn:hover { color: var(--surface-2); background: var(--color-primary); border-color: var(--color-primary); }

/* Viewer intégré — wrapper neutre. La containerisation est appliquée
   par variant : image/audio/external bornés à 80ch pour rester aérés,
   video pleine largeur du main pour permettre l'embed 16/9 (YouTube
   iframe ou `<video>` natif). PDF garde sa pleine largeur via
   `.pdf-viewer` (selector distinct). */
.resource-single__viewer {
    margin-bottom: var(--spacing-xl);
    border-radius: var(--radius-md);
    overflow: hidden;
    border: 1px solid var(--color-border);
}

.resource-single__viewer--image,
.resource-single__viewer--audio,
.resource-single__viewer--external,
.resource-single__viewer--office {
    max-width: 80ch;
}

/* Office sans preview PDF générée — card téléchargement propre.
   Icône + libellé + bouton, alignement horizontal, peu verbeuse. */
.office-fallback {
    display: flex;
    align-items: center;
    gap: var(--spacing-md);
    padding: var(--spacing-lg);
    background: var(--color-primary-light);
}
.office-fallback__icon {
    flex-shrink: 0;
    color: var(--color-primary);
}
.office-fallback__body { flex: 1; min-width: 0; }
.office-fallback__title {
    margin: 0 0 var(--spacing-xs) 0;
    font-weight: 600;
    color: var(--color-text);
}
.office-fallback__hint {
    margin: 0;
    font-size: 0.875rem;
    color: var(--color-text-light);
}

/* Vidéo embeddable (YouTube iframe ou `<video>` HTML5) — ratio 16/9
   responsive, prend toute la largeur du main pour un rendu immersif
   aligné sur le viewer PDF. */
.resource-single__viewer--video iframe,
.resource-single__viewer--video video {
    width: 100%;
    aspect-ratio: 16 / 9;
    height: auto;
    display: block;
    border: 0;
}

/* Legacy — overridden by stage layout */

/* ══════════════════════════════════════════════════════════════
   Resource Vidéo — layout pleine largeur style Grafikart
   ══════════════════════════════════════════════════════════════ */
.resource-video { max-width: none; }

.resource-video__header {
    display: flex;
    align-items: flex-start;
    justify-content: space-between;
    gap: var(--spacing-md);
    margin-bottom: var(--spacing-lg);
}

.resource-video__info { flex: 1; min-width: 0; }
.resource-video__title { font-size: 1.5rem; font-weight: 700; line-height: 1.3; margin: var(--spacing-xs) 0; }
.resource-video__excerpt { font-size: var(--font-size-sm); color: var(--color-text-light); line-height: 1.5; margin: 0; }

/* Stage : player + bouton toggle + chapitres côte à côte */
.resource-video__stage {
    display: flex;
    margin-bottom: var(--spacing-xl);
    border: 1px solid var(--color-border);
    overflow: hidden;
    height: 80vh;
    min-height: 30rem;
}

.resource-video__player { flex: 1; min-width: 0; transition: flex 0.3s ease; }

/* Bouton toggle vertical entre player et chapitres */
.resource-video__sidebar-toggle {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 1.5rem;
    flex-shrink: 0;
    border: none;
    background: var(--color-bg-light);
    border-left: 1px solid var(--color-border);
    border-right: 1px solid var(--color-border);
    color: var(--color-text-light);
    cursor: pointer;
    transition: background 0.15s ease, color 0.15s ease;
}
.resource-video__sidebar-toggle:hover { background: var(--color-neutral-soft); color: var(--color-text); }

/* Chapitres panneau droit — pleine hauteur */
.resource-video__chapters {
    width: 20rem;
    flex-shrink: 0;
    background: var(--surface-2);
    display: flex;
    flex-direction: column;
}

.resource-video__chapters-header {
    padding: var(--spacing-sm) var(--spacing-md);
    font-size: var(--font-size-xs);
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: var(--color-text-light);
    border-bottom: 1px solid var(--color-border);
    flex-shrink: 0;
}

.resource-video__chapters-list {
    list-style: none;
    padding: 0;
    margin: 0;
    flex: 1;
    overflow-y: auto;
}

/* Panneau PDF — infos + citation */
.resource-pdf__panel { padding: var(--spacing-md); display: flex; flex-direction: column; gap: var(--spacing-md); height: 100%; }

.resource-pdf__file-info { font-size: var(--font-size-xs); color: var(--color-text-light); }
.resource-pdf__filename { display: flex; align-items: center; gap: 0.25rem; font-weight: 600; color: var(--color-text); margin-bottom: 0.125rem; }
.resource-pdf__filesize { font-size: var(--font-size-xs); color: var(--color-text-light); }

/* Citation affichée directement */
/* Bloc référence + QR code */
.resource-pdf__ref { display: flex; gap: var(--spacing-sm); margin-top: auto; }
.resource-pdf__qr-code { flex-shrink: 0; }
.resource-pdf__qr-code svg { width: 4.5rem; height: 4.5rem; display: block; }
.resource-pdf__ref-body { flex: 1; min-width: 0; }
.resource-pdf__cite-label { display: block; font-size: var(--font-size-xs); font-weight: 700; text-transform: uppercase; letter-spacing: 0.04em; color: var(--color-text-light); margin-bottom: 0.125rem; }
.resource-pdf__cite-text { font-size: 0.6875rem; line-height: 1.4; color: var(--color-text-light); font-style: italic; margin: 0; }

.resource-pdf__ref-actions { display: flex; align-items: center; gap: var(--spacing-xs); margin-top: var(--spacing-xs); }
.resource-pdf__ref-sep { color: var(--color-border); font-size: var(--font-size-xs); }
.resource-pdf__cite-copy {
    font-size: var(--font-size-xs);
    font-weight: 500;
    color: var(--color-primary);
    background: none;
    border: none;
    cursor: pointer;
    padding: 0;
}
.resource-pdf__cite-copy:hover { text-decoration: underline; }

.resource-video__mobile-toggle {
    display: none;
    align-items: center;
    gap: var(--spacing-xs);
    margin-top: var(--spacing-sm);
    padding: var(--spacing-xs) 0;
    border: none;
    background: none;
    font-size: var(--font-size-xs);
    font-weight: 500;
    color: var(--color-text-light);
    cursor: pointer;
}
.resource-video__mobile-toggle:hover { color: var(--color-primary); }

.resource-video__header-actions { display: flex; align-items: center; gap: var(--spacing-sm); flex-shrink: 0; }

/* Viewer PDF pleine hauteur dans le stage */
.resource-single__pdf-viewer { width: 100%; height: 100%; min-height: 30rem; border: none; }

@media (width < 64em) {
    .resource-video__stage { flex-direction: column; height: auto; min-height: auto; }
    .resource-video__sidebar-toggle { display: none; }
    .resource-video__chapters { width: 100%; border-top: 1px solid var(--color-border); }
    .resource-video__header-actions { flex-wrap: wrap; }
    .resource-single__pdf-viewer { width: 100%; min-height: 24rem; height: 50vh; }
    .resource-video__player { min-height: 14rem; }

    .resource-video__mobile-toggle { display: inline-flex; }
}

@media (min-width: 64em) {
    .resource-video__mobile-toggle { display: none; }
}

@media (width < 48em) {
    .resource-video__header { flex-direction: column; }
    .resource-video__title { font-size: 1.25rem; }
}

/* Legacy — garder pour compat */

.resource-single__video-wrapper {
    position: relative;
    width: 100%;
    padding-bottom: 56.25%;
    overflow: hidden;
}
.resource-single__video-wrapper iframe { position: absolute; top: 0; left: 0; width: 100%; height: 100%; border: 0; }

/* Chapitrage */
.resource-single__chapters {
    margin-top: var(--spacing-md);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    overflow: hidden;
}

.resource-single__chapters-title {
    display: flex;
    align-items: center;
    gap: var(--spacing-xs);
    padding: var(--spacing-sm) var(--spacing-md);
    font-size: var(--font-size-xs);
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: var(--color-text-light);
    background: var(--color-bg-light);
    border-bottom: 1px solid var(--color-border);
    margin: 0;
}

.resource-single__chapters-list { list-style: none; padding: 0; margin: 0; }

.resource-single__chapter { border-bottom: 1px solid var(--color-border); }
.resource-single__chapter:last-child { border-bottom: none; }

.resource-single__chapter-link {
    display: flex;
    align-items: center;
    gap: var(--spacing-md);
    padding: var(--spacing-sm) var(--spacing-md);
    text-decoration: none;
    color: inherit;
    transition: background 0.15s ease;
    cursor: pointer;
}
a.resource-single__chapter-link:hover { background: var(--color-bg-light); }

.resource-single__chapter--active .resource-single__chapter-link {
    background: color-mix(in srgb, var(--color-section-cesu) 6%, transparent);
    border-left: 3px solid var(--color-primary);
}

.resource-single__chapter-time {
    font-family: monospace;
    font-size: var(--font-size-xs);
    font-weight: 600;
    color: var(--color-primary);
    min-width: 3rem;
    flex-shrink: 0;
}

.resource-single__chapter-title {
    font-size: var(--font-size-sm);
    color: var(--color-text);
}


.resource-single__aside-section { margin-top: var(--spacing-md); }
.resource-single__aside-label {
    display: block;
    font-size: var(--font-size-xs);
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    color: var(--color-text-light);
    margin-bottom: var(--spacing-xs);
}

/* Contenu éditorial — largeur contrainte pour la lisibilité prose. */
/* `.resource-single__content` A DISPARU avec le second emplacement du corps
   editorial : le gabarit en portait deux, l'un au-dessus du visualiseur et
   l'autre en dessous, et une condition decidait page par page lequel servait.
   Il n'y en a plus qu'un, la carte « Presentation ». */

/* Citer */
.resource-single__cite { padding: var(--spacing-md) 0; border-top: 1px solid var(--color-border); margin-bottom: var(--spacing-xl); }

.resource-single__cite-toggle {
    display: flex;
    align-items: center;
    gap: var(--spacing-xs);
    font-size: var(--font-size-xs);
    font-weight: 600;
    color: var(--color-text-light);
    background: none;
    border: none;
    cursor: pointer;
}
.resource-single__cite-toggle:hover { color: var(--color-text); }

.resource-single__cite-panel { margin-top: var(--spacing-sm); padding: var(--spacing-sm); background: var(--color-bg-light); border-radius: var(--radius-sm); }
.resource-single__cite-text { font-size: 0.6875rem; line-height: 1.5; color: var(--color-text-light); }
.resource-single__cite-copy {
    display: inline-flex;
    align-items: center;
    gap: 0.25rem;
    margin-top: var(--spacing-xs);
    font-size: var(--font-size-xs);
    color: var(--color-primary);
    background: none;
    border: none;
    cursor: pointer;
}

/* Ressources liées — card visuelle pour amener du rythme à la fin de
   fiche, containerisée sur 72rem comme le reste du site. Fond teinté
   `--color-primary-light` (sans border) pour casser la monotonie blanche
   du body sans surcharger visuellement. */
/* Enveloppe CLAIRE, comme le « A lire aussi » d'une actualite, le « Autres
   dossiers » d'un dossier et le « Autres portraits » d'un portrait. Elle
   portait un aplat `--color-primary-light` : un pave lavande en pied, sous une
   carte navy en tete — deux surfaces de marque sur la meme page, dont la
   seconde pese plus lourd que ce qu'elle annonce. C'est aussi la seule des
   quatre a en avoir un, ce qui la faisait lire comme un objet different.
   La marge laterale s'AJOUTE a la borne (`box-sizing: border-box`), sinon le
   contenu du bloc rentre de 16 px par rapport au reste de la page. */
/* PLUS DE LARGEUR NI DE GOUTTIERE PROPRES : le bloc est desormais pose dans le
   `.container` de la page, comme les autres. Il se bornait a 72 rem quand la
   colonne de lecture en fait 74,5 — ses cartes commencaient donc 20 px a droite
   du titre de la page, ecart visible sur toute la largeur de l'ecran.

   AUCUN ecart au-dessus : le rembourrage de pied de la grille le donne deja.
   Le bloc en cumulait trois — 64 px de marge, 48 de rembourrage propre, plus
   les 48 de la grille au-dessus. */
.resource-single__related {
    margin-top: 0;
}

/* L'EN-TETE LOCAL DE CE BLOC EST PARTI (2026-08-29) : quatre regles pour un
   titre en capitales et un lien « tout voir », que `_section_header` rend
   partout ailleurs, avec en plus le sur-titre et le trait de rubrique que la
   maquette demande. Le commentaire qu'elles portaient disait s'aligner sur
   « les trois autres blocs de rebond du site » ; ces trois-la etaient deja
   passes a la brique. */

/* ── LA GRILLE DES REBONDS ──
   `repeat(auto-fit, minmax(17.5rem, 1fr))`, la grille de la maquette : elle
   pose autant de colonnes que la largeur en accepte, sans palier a declarer.
   Trois rebonds tiennent sur une ligne a 1 440 px, deux a 1 024, un sur
   telephone.

   LES ONZE REGLES DE `.library-related-card` SONT PARTIES : ce bloc dessinait
   sa propre carte a image — vignette carree a gauche, pictogramme de type,
   titre sur deux lignes — cinquieme du genre dans un depot qui avait deja
   ramene les quatre autres au composant 60. C'est `_media_card` qui rend ces
   cartes, en echelle verticale, avec le sigle de format a la place du visuel
   quand la ressource n'en a pas. */
.library-show__related-grid {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(17.5rem, 1fr));
    gap: var(--spacing-md);
}

/* ── Related — cards sans bande grise ── */
.article-single__related {
    /* UN SEUL ECART, celui du rythme de page. La marge de 64 et le rembourrage
       de 48 s'AJOUTAIENT — 112 px entre la carte et « Sur le meme sujet »,
       sans filet entre les deux pour justifier le second. Le rembourrage ne
       separait rien, il doublait la marge. */
    margin-top: var(--rhythm-block);
}

.article-single__related-container {
    max-width: 72rem;
    margin: 0 auto;
    padding: 0 var(--spacing-md);
}

.article-single__related-title {
    font-size: var(--font-size-xl);
    font-weight: 300;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    color: var(--color-text);
    margin-bottom: var(--spacing-lg);
}

.article-single__related-grid {
    display: grid;
    grid-template-columns: 1fr;
    gap: var(--spacing-lg);
}

@media (min-width: 40em) {
    .article-single__related-grid {
        grid-template-columns: repeat(2, 1fr);
    }
}

@media (min-width: 64em) {
    .article-single__related-grid {
        grid-template-columns: repeat(3, 1fr);
    }
}

/* ══════════════════════════════════════════════════════════════
   Article TOC items (réutilisés dans la sidebar droite)
   ══════════════════════════════════════════════════════════════ */

/* .article-sidebar__toc, .article-toc__* → déplacés dans content.css (composant transversal) */

/* ══════════════════════════════════════════════════════════════
   Print header/footer — masqués à l'écran
   ══════════════════════════════════════════════════════════════ */

.print-header,
.print-footer {
    display: none;
}

/* ══════════════════════════════════════════════════════════════
   Article mobile — hero compact

   La bulle de partage qui remplace l'ancienne bande `.article-mobile-bar`
   vit desormais dans `styles/components/share-fab.css` : elle est partagee
   par toutes les fiches (article, page, evenement, formation, ressource,
   CESU), dont certaines ne chargent pas cette feuille.
   ══════════════════════════════════════════════════════════════ */

@media (width < 64em) {
    .article-single__hero { min-height: 15rem; max-height: 22rem; }
}

/* ══════════════════════════════════════════════════════════════
   Print — Styles d'impression (format document)
   ══════════════════════════════════════════════════════════════ */

@media print {
    /* La typo papier de base (font-family, font-size, line-height) et
       la mise en page `@page` (marges, footer numérotation, en-tête
       courant à partir de la page 2) viennent de
       `styles/components/print.css`. On laisse cette brique faire
       autorité — pas de duplication ici. */

    /* ── Masquer éléments écran ──
       Les hides universels (`.navbar`, `.breadcrumb-bar`, `.bottom-nav`,
       `.cookie-consent`, `.skip-link`, `.site-footer`, `.sf-toolbar`)
       viennent désormais de `styles/components/print.css`. On garde ici
       seulement ce qui est propre aux fiches éditoriales (hero, sidebar
       partage/citer/print, articles liés, barre mobile sticky). */
    .article-sidebar,
    .article-single__related,
    .article-single__hero,
    .article-single__header,
    .share-fab,
    .reading-progress,
    .reading-share-rail,
    .list-filters,
    .page-transition-bar {
        display: none !important;
    }

    /* ── Newsletter minisite — impression ── */
    .nl-minisite-header__bar,
    .nl-minisite__sidebar,
    .nl-minisite-header__actions {
        display: none !important;
    }

    .nl-minisite-header {
        padding-top: 0;
    }

    .nl-minisite-hero {
        display: none !important;
    }

    .nl-minisite__content .container {
        padding-top: 0 !important;
        padding-bottom: 0 !important;
    }

    .nl-minisite-header {
        padding-top: 0 !important;
    }

    /* En-tête bibliographique : logo | titre + meta | QR code */
    .nl-minisite__print-biblio {
        display: flex !important;
        align-items: center;
        gap: 1em;
        margin: 1.5em 0 1em;
        padding: 0.75em 0;
        border-top: 1px solid var(--print-rule);
        border-bottom: 1px solid var(--print-rule);
    }

    .nl-minisite__print-biblio-logo {
        flex-shrink: 0;
    }

    .nl-minisite__print-biblio-logo img {
        width: auto;
        height: 60px;
    }

    .nl-minisite__print-biblio-info {
        flex: 1;
        min-width: 0;
    }

    .nl-minisite__print-biblio-title {
        display: block;
        font-size: 12pt;
        font-weight: 700;
        color: var(--print-ink);
        line-height: 1.3;
    }

    .nl-minisite__print-biblio-meta {
        display: block;
        font-size: 8pt;
        color: var(--print-ink-soft);
        margin-top: 0.15em;
    }

    .nl-minisite__print-biblio-url {
        display: block;
        font-size: 7pt;
        color: var(--print-ink-muted);
        word-break: break-all;
        margin-top: 0.15em;
    }

    .nl-minisite__print-biblio-qr {
        flex-shrink: 0;
    }

    .nl-minisite__print-biblio-qr svg {
        width: 60px;
        height: 60px;
    }

    .nl-minisite-hero__topic {
        background: none;
        color: var(--color-primary);
        border: 1px solid var(--color-primary);
        font-size: 7pt;
        padding: 0 0.4em;
    }

    .nl-minisite__layout {
        display: block;
    }

    .nl-minisite__body {
        max-width: none;
    }

    .nl-minisite__content .prose-content {
        font-size: 10pt;
        line-height: 1.35;
    }

    .nl-minisite__content .prose-content p {
        margin-bottom: 0.5em;
    }

    .nl-minisite__content .prose-content ul,
    .nl-minisite__content .prose-content ol {
        padding-left: 1.5em;
        margin-bottom: 0.5em;
    }

    .nl-minisite__content .prose-content ul {
        list-style-type: disc;
    }

    .nl-minisite__content .prose-content ol {
        list-style-type: decimal;
    }

    .nl-minisite__content .prose-content li {
        margin-bottom: 0.2em;
    }

    .nl-minisite__content .prose-content li ul,
    .nl-minisite__content .prose-content li ol {
        margin-top: 0.2em;
        margin-bottom: 0;
    }

    .nl-minisite__content .prose-content blockquote {
        border-left: 3px solid var(--print-ink-soft);
        background: none;
        padding: 0.5em 1em;
        font-size: 9pt;
        font-style: italic;
    }

    .nl-minisite__content .prose-content table {
        font-size: 8.5pt;
        page-break-inside: avoid;
    }

    .nl-minisite__content .prose-content th,
    .nl-minisite__content .prose-content td {
        padding: 0.25em 0.5em;
        border: 1px solid var(--print-rule);
    }

    .nl-minisite__content .prose-content th {
        background: var(--print-surface);
        font-weight: 600;
    }

    .nl-minisite__content .prose-content h2 {
        font-size: 14pt;
        font-weight: 700;
        margin-top: 1.5em;
        page-break-after: avoid;
    }

    .nl-minisite__content .prose-content h3 {
        font-size: 12pt;
        font-weight: 600;
        margin-top: 1em;
        page-break-after: avoid;
    }

    .nl-minisite__content .prose-content img {
        max-width: 80%;
        page-break-inside: avoid;
    }

    .nl-minisite__content .prose-content a {
        color: var(--print-ink);
        text-decoration: underline;
    }

    .nl-minisite__content .prose-content a::after {
        content: " (" attr(href) ")";
        font-size: 7.5pt;
        color: var(--print-ink-muted);
        word-break: break-all;
    }

    /* Annexe contenus référencés en pied de newsletter */
    .nl-minisite__print-qr {
        display: block !important;
        margin-top: 2em;
        page-break-inside: avoid;
    }

    /* Contenus référencés — annexe */
    .nl-minisite__print-refs {
        margin-top: 1.5em;
        padding-top: 1em;
        border-top: 1px solid var(--print-rule);
    }

    .nl-minisite__print-refs-title {
        display: block;
        font-size: 10pt;
        font-weight: 700;
        color: var(--print-ink);
        margin-bottom: 0.75em;
    }

    .nl-minisite__print-refs-list {
        display: grid;
        grid-template-columns: 1fr 1fr;
        gap: 0.75em 1.5em;
    }

    .nl-minisite__print-ref {
        display: flex;
        align-items: center;
        gap: 0.5em;
        page-break-inside: avoid;
    }

    .nl-minisite__print-ref-qr svg {
        width: 50px;
        height: 50px;
        flex-shrink: 0;
    }

    .nl-minisite__print-ref-title {
        display: block;
        font-size: 8pt;
        font-weight: 600;
        color: var(--print-ink);
    }

    .nl-minisite__print-ref-url {
        display: block;
        font-size: 6.5pt;
        color: var(--print-ink-muted);
        word-break: break-all;
    }

    /* ── Article : supprimer le layout grid ── */
    .article-single {
        padding: 0;
    }

    .article-single__layout {
        display: block;
        max-width: none;
        padding: 0;
    }

    .article-single__main {
        max-width: none;
    }

    /* Chapô (rendu une seule fois sur papier, ici uniquement — la cartouche
       print ne l'embarque pas pour éviter le doublon). Densifié. */
    .article-single__lead-text {
        font-size: 9pt;
        line-height: 1.4;
        padding-bottom: 0.4em;
        margin-bottom: 0.6em;
        color: var(--print-ink-soft);
        border-bottom-color: var(--print-ink-muted);
    }

    /* ── Contenu prose · densifié pour limiter le nombre de pages ── */
    .prose-content {
        font-size: 8.5pt;
        line-height: 1.4;
    }

    .prose-content > * + * {
        margin-top: 0.5em;
    }

    .prose-content h2 {
        font-size: 11pt;
        margin-top: 1em;
        margin-bottom: 0.3em;
        page-break-after: avoid;
    }

    .prose-content h3 {
        font-size: 10pt;
        margin-top: 0.75em;
        margin-bottom: 0.25em;
        page-break-after: avoid;
    }

    .prose-content h4 {
        font-size: 9pt;
        margin-top: 0.6em;
        margin-bottom: 0.15em;
        page-break-after: avoid;
    }

    .prose-content img {
        max-width: 70%;
        max-height: 20em;
        page-break-inside: avoid;
    }

    .prose-content figure {
        page-break-inside: avoid;
    }

    .prose-content blockquote {
        border-left: 3px solid var(--print-ink-soft);
        background: none;
        padding: 0.5em 1em;
        font-size: 9pt;
    }

    .prose-content table {
        font-size: 8.5pt;
        page-break-inside: avoid;
    }

    .prose-content pre {
        font-size: 8pt;
        border: 1px solid var(--print-rule);
        background: none;
        page-break-inside: avoid;
    }

    /* Liens : afficher l'URL */
    .prose-content a[href^="http"]::after {
        content: " [" attr(href) "]";
        font-size: 0.75em;
        color: var(--print-ink-muted);
        word-break: break-all;
    }

    /* ── Print footer ── */
    .print-footer {
        display: block;
        margin-top: 2em;
    }

    .print-footer__rule {
        border: none;
        border-top: 1px solid var(--print-rule);
        margin-bottom: 0.75em;
    }

    .print-footer__cite {
        font-size: 8pt;
        color: var(--print-ink-soft);
        line-height: 1.4;
    }

    .print-footer__url {
        font-size: 7.5pt;
        color: var(--print-ink-muted);
        margin-top: 0.25em;
    }

    /* ── FAQ print ── */
    .helpcenter__sidebar,
    .helpcenter__back,
    .helpcenter__cta,
    .helpcenter__rating,
    .helpcenter__report,
    .helpcenter__report-toggle,
    .helpcenter__report-thanks,
    .helpcenter__answer-tag,
    .helpcenter__cat-header,
    .helpcenter__entry-link-btn {
        display: none !important;
    }
    /* .btn-print masque par sa propre rule @media print dans components/btn-print.css. */

    .helpcenter__container { max-width: none; }

    .helpcenter__layout { display: block !important; }

    /* Bandeau bibliographique */
    .helpcenter__print-biblio {
        display: flex !important;
        align-items: center;
        gap: 1em;
        margin: 1.5em 0 1em;
        padding: 0.75em 0;
        border-top: 1px solid var(--print-rule);
        border-bottom: 1px solid var(--print-rule);
    }

    .helpcenter__print-biblio-logo img { height: 60px; width: auto; }

    .helpcenter__print-biblio-info { flex: 1; min-width: 0; }
    .helpcenter__print-biblio-title { display: block; font-size: 12pt; font-weight: 700; color: var(--print-ink); }
    .helpcenter__print-biblio-meta { display: block; font-size: 8pt; color: var(--print-ink-soft); margin-top: 0.15em; }
    .helpcenter__print-biblio-url { display: block; font-size: 7pt; color: var(--print-ink-muted); word-break: break-all; margin-top: 0.15em; }

    .helpcenter__print-biblio-qr { flex-shrink: 0; }
    .helpcenter__print-biblio-qr svg { width: 60px; height: 60px; }

    .helpcenter__print-biblio { margin-bottom: 1.5em; }

    .helpcenter__entry {
        padding-bottom: 0.75em;
        margin-bottom: 0.75em;
        page-break-inside: avoid;
    }

    .helpcenter__entry-title { font-size: 12pt; font-weight: 700; margin-top: 0.75em; margin-bottom: 0.25em; }

    .helpcenter__entry .prose-content { font-size: 9pt; line-height: 1.3; }
    .helpcenter__entry .prose-content p { margin-bottom: 0.3em; }

    .helpcenter__answer-date { font-size: 7pt; color: var(--print-ink-muted); }

    .helpcenter__entry-footer { justify-content: flex-start; }
}

/* ══════════════════════════════════════════════════════════════
   Library Show — fiche ressource publique (show.html.twig)
   Structure : topbar standalone (breadcrumb + share) sur fond
   teinte compact, puis grille englobante a 2 cols >= 48em (rail
   vignette + CTA sticky | main titre + description + viewer +
   body). Le rail reste visible pendant tout le scroll de la fiche
   grace a `position: sticky` sur `.library-show__rail-inner`.
   ══════════════════════════════════════════════════════════════ */

/* PAS de fond propre. La bande de tete vient du degrade de `.front-main`
   (app.css), comme sur toutes les autres pages — meme convention que
   `hero.css`, `search.css`, `adhesion.css` et `page-shell.css`.

   La fiche portait ici son propre fond teinte : un aplat blanc plus un radial
   `--color-primary-light` sur 24 rem, ecrit pour la mise en page d'avant (une
   barre de service, un rail de vignette et des puces sous le titre) qui n'existe
   plus depuis le passage a `_content_header`. Il se superposait au degrade de
   `.front-main` : deux bandes de tete de teintes differentes et de longueurs de
   fondu differentes, l'une repeinte en blanc par-dessus l'autre, sous une meme
   carte navy. C'est ce qui donnait cet enchainement bizarre entre la barre de
   navigation et la carte. Releve 2026-08-18. */

/* Topbar wrap : conteneur transparent (le fond gradient est porte par
   `.library-show`), juste un padding-top defensif. */
.library-show__topbar-wrap {
    padding-top: var(--spacing-xs);
}

/* Topbar : breadcrumb a gauche, label « Partager : » + boutons +
   bookmark a droite. Padding-top porte par le topbar pour que les
   baselines breadcrumb / label coincident. */
.library-show__topbar {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: var(--spacing-md);
    padding: var(--spacing-sm) var(--spacing-md) var(--spacing-sm) 0;
    flex-wrap: wrap;
}
.library-show__topbar > :first-child { flex: 1 1 auto; min-width: 0; }
.library-show__topbar .breadcrumb-bar { background: transparent; border: 0; margin-bottom: 0; }
.library-show__topbar .breadcrumb__list { padding: 0; }

.library-hero__share {
    display: flex;
    align-items: center;
    gap: var(--spacing-sm);
    flex-shrink: 0;
}
.library-hero__share-label {
    color: var(--color-text-light);
    font-size: var(--font-size-xs);
}

/* Variant `--hero` du composant share-buttons : style ghost calé sur
   `.sidebar-reading-time__btn` (sidebar fiche article) — sans bordure,
   hover subtil (color primary + bg-light), 1.75rem ronds. Plus propre
   que le défaut bordé du composant share. Séparateur vertical avant
   le bookmark (mêlé aux share ici, contrairement à la fiche article). */
.share-buttons--hero .share-buttons__btn {
    width: 1.75rem;
    height: 1.75rem;
    border: 0;
    background: transparent;
}
.share-buttons--hero .share-buttons__btn:hover:not(:disabled) {
    color: var(--color-primary);
    background: var(--color-bg-light);
}
.share-buttons--hero .share-buttons__btn--bookmark.share-buttons__btn--active {
    color: var(--color-primary);
    background: transparent;
}
.share-buttons--hero .share-buttons__btn--bookmark.share-buttons__btn--active:hover {
    background: var(--color-bg-light);
}
.share-buttons--hero .share-buttons__btn--bookmark {
    position: relative;
    margin-left: var(--spacing-sm);
}
.share-buttons--hero .share-buttons__btn--bookmark::before {
    content: '';
    position: absolute;
    left: calc(var(--spacing-sm) / -2);
    top: 50%;
    transform: translate(-50%, -50%);
    height: 1.25rem;
    width: 1px;
    background: var(--color-border);
}

/* Breadcrumb : le dernier crumb (lien courant, sans href) tronque a
   28ch avec ellipsis pour eviter qu'un titre long ne pousse la barre
   share hors ecran. */
.library-show__topbar .breadcrumb__item:last-child > span,
.library-show__topbar .breadcrumb__item:last-child > a {
    display: inline-block;
    max-width: 28ch;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    vertical-align: bottom;
}

/* Champs d'identification d'une ressource (reference legale, editeur, ISBN,
   revue, DOI…). En LIGNES sur la fiche, la ou la carte les compacte : ici on
   les lit, on ne les survole pas. Chaque paire tient d'un trait — une grille a
   deux colonnes alignerait les valeurs entre elles et creuserait un couloir de
   blanc apres les intitules courts. */
.resource-single__facts {
    margin: var(--spacing-lg) 0 0;
    display: flex;
    flex-direction: column;
    gap: 0.3rem;
    font-size: var(--font-size-sm);
    line-height: 1.5;
}

.resource-single__fact {
    display: flex;
    flex-wrap: wrap;
    gap: 0.35rem;
    min-width: 0;
}

.resource-single__fact dt {
    color: var(--color-text-light);
    font-weight: 500;
}

.resource-single__fact dt::after {
    content: ' :';
}

.resource-single__fact dd {
    margin: 0;
    color: var(--color-text);
    min-width: 0;
    overflow-wrap: anywhere;
}

/* ── LE TEXTE DE REFERENCE, quand il vit ailleurs ──
   Une bande grise d'une phrase tenait cette place. Sur un texte reglementaire,
   « ou vit le texte et qui en fait foi » EST l'information de la page : la
   maquette lui donne une carte, un titre et une action, et c'est ce qu'elle
   merite. La carte vient de `_titled_card`, il ne reste ici que son corps. */
.resource-source__text {
    margin: 0;
    font-size: var(--font-size-base);
    line-height: 1.7;
    color: var(--color-text);
    max-width: 64ch;
}

/* L'action dans un cadre voile : elle sort du site, et le panneau le dit avant
   qu'on clique plutot qu'apres. */
.resource-source__cta {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: var(--spacing-md);
    padding: var(--spacing-md);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--color-bg-light);
}

.resource-source__cta-text {
    flex: 1 1 14rem;
    min-width: 0;
    margin: 0;
    font-size: var(--font-size-sm);
    line-height: 1.5;
    color: var(--color-text-light);
}

.resource-source__cta-btn {
    flex: none;
}

/* ── LE TITRE PREND TOUTE LA CARTE ──
   `content-header__title` se borne a 24 signes par ligne, mesure juste pour un
   en-tete qui partage sa largeur avec une mosaique ou un chiffre-cle. La fiche
   ressource n'a ni l'un ni l'autre : son en-tete est une carte de 1 192 px avec
   un titre a gauche et RIEN a droite, et un intitule de document de quatre-
   vingts signes y tombait sur quatre lignes contre un demi-ecran de blanc.

   40 signes, pas la pleine largeur : au-dela, un titre de trois lignes se relit
   mal parce que l'oeil perd le debut de la ligne suivante. C'est la mesure des
   titres d'affiche, pas celle d'un paragraphe. */
.content-header--resource .content-header__title {
    max-width: 40ch;
}

/* ── L'ECART SOUS L'EN-TETE ──
   Il en cumulait deux : le rembourrage bas de l'en-tete editorial, puis celui
   de la grille. 48 px entre la carte de titre et la premiere carte, contre 24
   entre toutes les autres — l'en-tete se lisait comme detache de sa page. */
.library-show__layout {
    padding-top: 0;
}

/* LA GRILLE VIENT DE `.article-single__layout`, comme sur toute fiche du site.
   Cette classe-ci n'ajoute plus que le rembourrage de pied : la fiche ressource
   posait sa propre grille depuis l'epoque du rail lateral, et depuis son retrait
   elle ne servait qu'a borner une colonne unique — un doublon de la regle que
   `article-single__layout` applique deja quand aucune colonne d'appui n'existe. */
.library-show__layout {
    /* 32 et non 48 : c'est le SEUL ecart entre la colonne de lecture et les
       rebonds, la section n'en ajoutant aucun. A 48 il se lisait comme une fin
       de page, alors que « Voir aussi » appartient encore a la fiche. */
    padding-bottom: var(--spacing-xl);
}

/* ── La colonne d'appui d'une ressource RESTE sur telephone ──
   Celle d'un article se masque sous 64 em, et c'est justifie : un sommaire de
   lecture et deux rebonds se passent de place. Ici la colonne porte le format,
   le poids, la reference et la licence — ce qu'on vient chercher AVANT
   d'ouvrir un fichier, et d'autant plus sur un telephone ou l'ouvrir coute.

   Regle SANS palier, posee apres celles de `.article-sidebar` : une media query
   n'ajoute aucune specificite, donc c'est l'ordre d'ecriture qui tranche, a
   toutes les largeurs. */
.library-show__aside {
    display: block;
}

/* Sous le palier de la grille a deux colonnes, la colonne passe SOUS le corps :
   la coller en haut de fenetre l'y figerait en travers de la lecture, et sa
   hauteur maximale en ferait une boite a defilement dans la page. */
@media (width < 64em) {
    .library-show__aside .article-sidebar__sticky {
        position: static;
        max-height: none;
        overflow-y: visible;
    }
}

/* ── Les personnes d'une ressource ──
   Un nom par ligne, sa qualite dessous en plus discret. La liste ne porte
   aucune puce : ce sont des signatures, pas une enumeration. */
.library-persons {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: var(--spacing-md);
}

.library-persons__item {
    display: flex;
    flex-direction: column;
    gap: 0.15rem;
    min-width: 0;
}

.library-persons__name {
    font-family: var(--font-title);
    font-size: var(--font-size-base);
    font-weight: 700;
    line-height: 1.3;
    color: var(--color-primary-dark);
}

.library-persons__role {
    font-size: var(--font-size-sm);
    line-height: 1.45;
    color: var(--color-text-light);
}

.library-persons__note {
    margin: 0;
    font-size: var(--font-size-sm);
    line-height: 1.5;
    color: var(--color-text-light);
}

/* ── Reutilisation ──
   Le nom de la licence en chasse fixe : c'est une REFERENCE, pas de la prose,
   et le site marque partout cette distinction de la meme facon. */
.library-reuse__licence {
    margin: 0;
    font-family: var(--font-data);
    font-size: var(--font-size-sm);
    font-weight: 500;
    color: var(--color-primary-dark);
}

.library-reuse__text {
    margin: 0;
    font-size: var(--font-size-sm);
    line-height: 1.5;
    color: var(--color-text-light);
}

/* Les regles `.resource-cite__*` ont ete retirees le 2026-08-30 : le bloc de
   citation est passe dans la brique partagee `components/_cite_card.html.twig`,
   qui emporte sa propre feuille. Elles vivaient ICI, c'est-a-dire dans une zone
   que seule la fiche ressource charge — ce qui rendait le bloc increuvable
   ailleurs, et c'est precisement ce qui a fait ecrire un second dessin quand le
   minisite evenement en a eu besoin. */


.library-show__main {
    min-width: 0;
    display: flex;
    flex-direction: column;
    gap: var(--spacing-lg);
}

.library-hero__cover {
    position: relative;
    width: 100%;
    max-width: 11rem;
    aspect-ratio: 3 / 4;
    border-radius: var(--radius-md);
    overflow: hidden;
    background: var(--surface-2);
    border: 1px solid var(--color-border);
    box-shadow: 0 4px 16px -6px color-mix(in srgb, var(--color-primary-dark) 18%, transparent), 0 1px 3px color-mix(in srgb, var(--color-primary-dark) 6%, transparent);
}

/* Vidéo/replay : le thumbnail (YouTube etc.) est en 16/9, le cover doit
   matcher pour éviter les bandes blanches. `object-fit: cover` pour
   remplir parfaitement (le thumbnail YouTube standard est exactement
   16/9, zéro crop visible). Le fond bascule sur le noir vidéo. */
.library-hero__cover--video {
    aspect-ratio: 16 / 9;
    background: var(--print-ink);
}

.library-hero__cover-img {
    width: 100%;
    height: 100%;
    object-fit: contain;
    display: block;
}

.library-hero__cover--video .library-hero__cover-img {
    object-fit: cover;
}

.library-hero__cover-icon {
    width: 100%;
    height: 100%;
    display: flex;
    align-items: center;
    justify-content: center;
    color: var(--color-primary);
    background: linear-gradient(160deg, var(--color-bg) 0%, color-mix(in srgb, var(--color-primary) 8%, var(--color-bg)) 100%);
}

.library-hero__cover-badge {
    position: absolute;
    left: var(--spacing-sm);
    bottom: var(--spacing-sm);
    padding: 0.1875rem 0.5rem;
    border-radius: var(--radius-sm);
    background: var(--color-text);
    color: var(--surface-2);
    font-size: 0.6875rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.04em;
}

.library-hero__body {
    min-width: 0;
    display: flex;
    flex-direction: column;
    gap: var(--spacing-sm);
}

.library-hero__eyebrow {
    margin: 0;
    color: var(--color-text-light);
    font-size: var(--font-size-xs);
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.06em;
}

.library-hero__eyebrow-link {
    color: inherit;
    text-decoration: none;
}
.library-hero__eyebrow-link:hover { color: var(--color-primary); text-decoration: underline; }

/* Tags chips cliquables (vers /ressources?tag=…) — sous le titre. */
.library-hero__tags {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-wrap: wrap;
    gap: 0.375rem;
}

/* Style aligné sur `.library-card__tag` du listing /ressources : radius-sm,
   fond neutre `bg-light` + bordure, hover bascule sur la couleur primary.
   Pas de full-rounded (999px) qui ferait dissonance avec le reste. */
.library-hero__tag {
    display: inline-flex;
    align-items: center;
    padding: var(--spacing-xs) var(--spacing-sm);
    border-radius: var(--radius-sm);
    background: var(--color-bg-light);
    color: var(--color-text-light);
    border: 1px solid var(--color-border);
    font-size: 0.75rem;
    font-weight: 500;
    line-height: 1.3;
    text-decoration: none;
    transition: background-color 0.15s ease, color 0.15s ease, border-color 0.15s ease;
}

.library-hero__tag:hover,
.library-hero__tag:focus-visible {
    background: var(--color-primary-light);
    color: var(--color-primary);
    border-color: var(--color-primary);
    outline: none;
}

.library-hero__title {
    margin: 0;
    font-size: clamp(1.5rem, 2.5vw + 1rem, 2.25rem);
    font-weight: 700;
    line-height: 1.2;
    color: var(--color-text);
}

/* LE CHAPO REPLIABLE DE LA FICHE RESSOURCE EST PARTI (2026-08-29). Le chapo
   passe par `lead` de l'en-tete editorial, comme sur toutes les autres fiches ;
   ces sept regles etaient le seul chapo du site a se replier, pour un champ que
   l'edition borne deja a quelques lignes. */

.library-hero__chips {
    list-style: none;
    margin: var(--spacing-xs) 0 0;
    padding: 0;
    display: flex;
    flex-wrap: wrap;
    gap: 0.375rem;
}

.library-hero__chip {
    display: inline-flex;
    align-items: center;
    gap: 0.375rem;
    padding: var(--spacing-xs) var(--spacing-sm);
    border-radius: var(--radius-sm);
    background: var(--surface-2);
    border: 1px solid var(--color-border);
    color: var(--color-text-light);
    font-size: 0.75rem;
    font-weight: 500;
    line-height: 1.3;
    white-space: nowrap;
}

.library-hero__chip svg { color: var(--color-text-light); flex-shrink: 0; }

/* CTA download sous la vignette : centre, largeur de la colonne (11rem). */
.library-hero__actions {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-sm);
}

.library-hero__cta {
    width: 100%;
    justify-content: center;
}

/* Citation imprimable — invisible à l'écran, visible sur impression.
   QR + texte de référence pour citer la ressource papier. Les actions
   interactives (copier, télécharger QR) sont retirées : à l'impression
   elles n'ont pas de sens. */
.library-print-cite { display: none; }

@media print {
    .library-print-cite {
        display: flex;
        gap: 1rem;
        align-items: flex-start;
        padding: 0.75rem 0;
        margin-top: 1rem;
        border-top: 1px solid var(--print-rule);
        font-size: 9pt;
        break-inside: avoid;
    }
    .library-print-cite__qr { flex-shrink: 0; width: 3rem; height: 3rem; }
    .library-print-cite__qr svg { width: 100%; height: 100%; }
    .library-print-cite__body { flex: 1; min-width: 0; }
    .library-print-cite__label {
        display: block;
        font-size: 7pt;
        font-weight: 700;
        text-transform: uppercase;
        letter-spacing: 0.04em;
        color: var(--print-ink-soft);
        margin-bottom: 0.25rem;
    }
    .library-print-cite__text { margin: 0; line-height: 1.4; color: var(--print-ink-soft); }
}

@media (width < 48em) {
    .library-hero__topbar { padding-right: var(--spacing-sm); }
    .library-hero__share { padding-bottom: var(--spacing-sm); }
    .library-hero__share-label { display: none; }
    .library-hero .breadcrumb__item:last-child > span,
    .library-hero .breadcrumb__item:last-child > a { max-width: 18ch; }
}

/* ══════════════════════════════════════════════════════════════
   VISUALISEUR PDF — maquette « Ressource ANCESU PDF »
   ══════════════════════════════════════════════════════════════

   Barre de commandes, document flanque de son rail de vignettes, pied
   d'annonce. Les pages sont dessinees par `assets/pdf-viewer.js` : l'iframe
   native imposait le chrome du navigateur, que la page ne peut pas commander.

   Le rayon est celui des cartes voisines, et la carte est PLEINE — le document
   forme lui-meme ses bords, comme une carte batie autour d'un visuel. */
.pdf-viewer {
    border: 1px solid var(--color-border);
    border-radius: var(--radius-lg);
    overflow: hidden;
    background: var(--surface-2);
    display: flex;
    flex-direction: column;
}

/* ── La barre de commandes ──
   Elle s'enroule : a 390 px, huit commandes et un champ de recherche ne
   tiennent pas sur une ligne, et les tasser produirait des cibles sous les
   44 px que la charte impose a ce qui se touche. */
.pdf-viewer__toolbar {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: var(--spacing-sm);
    padding: var(--spacing-ms) var(--spacing-md);
    border-bottom: 1px solid var(--color-border);
    background: var(--color-bg-light);
}

.pdf-viewer__group {
    display: flex;
    align-items: center;
    gap: var(--spacing-2xs);
    flex: none;
}

/* Les actions de sortie — telecharger, plein ecran — sont poussees a droite
   tant qu'il reste de la place, et repassent a la ligne sinon. */
.pdf-viewer__group--end {
    margin-left: auto;
    gap: var(--spacing-sm);
}

.pdf-viewer__btn {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 2.25rem;
    height: 2.25rem;
    flex: none;
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--surface-2);
    color: var(--color-primary);
    cursor: pointer;
    transition: background-color var(--transition-fast), border-color var(--transition-fast);
}

.pdf-viewer__btn:hover {
    background: var(--color-primary-light);
    border-color: var(--color-primary);
}

.pdf-viewer__pager {
    gap: var(--spacing-sm);
    padding-left: var(--spacing-2xs);
}

/* UN CHAMP, ET NON UN AFFICHAGE : atteindre la page 62 d'un referentiel de
   quatre-vingt-dix-sept pages demandait soixante et un clics sur le chevron.
   Les fleches natives du champ nombre sont retirees — elles doublent les deux
   boutons voisins et n'ont pas leur taille de cible. */
.pdf-viewer__page-input {
    width: 3.25rem;
    height: 2.25rem;
    padding: 0 var(--spacing-2xs);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--surface-2);
    color: var(--color-primary-dark);
    font-family: var(--font-data);
    font-size: var(--font-size-xs);
    text-align: center;
    appearance: textfield;
}

.pdf-viewer__page-input::-webkit-outer-spin-button,
.pdf-viewer__page-input::-webkit-inner-spin-button {
    appearance: none;
    margin: 0;
}

.pdf-viewer__page-total {
    font-family: var(--font-data);
    font-size: var(--font-size-xs);
    color: var(--color-text-light);
    white-space: nowrap;
}

.pdf-viewer__divider {
    width: 1px;
    height: 1.5rem;
    flex: none;
    background: var(--color-border);
}

.pdf-viewer__zoom {
    min-width: 3.5rem;
    text-align: center;
    font-family: var(--font-data);
    font-size: var(--font-size-2xs);
    color: var(--color-primary-dark);
}

.pdf-viewer__search {
    display: flex;
    align-items: center;
    gap: var(--spacing-sm);
    flex: 1 1 12rem;
    min-width: 8rem;
    height: 2.25rem;
    padding: 0 var(--spacing-ms);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    background: var(--surface-2);
    color: var(--color-text-light);
}

.pdf-viewer__search-input {
    flex: 1;
    min-width: 0;
    border: 0;
    background: none;
    color: var(--color-text);
    font-size: var(--font-size-xs);
}

.pdf-viewer__search-input:focus {
    outline: none;
}

.pdf-viewer__search-result {
    flex: none;
    font-family: var(--font-data);
    font-size: var(--font-size-2xs);
    color: var(--color-text-light);
    white-space: nowrap;
}

.pdf-viewer__download {
    white-space: nowrap;
}

/* ── Le document et son rail ── */
.pdf-viewer__body {
    display: flex;
    align-items: stretch;
    min-height: 40rem;
    max-height: 80vh;
}

.pdf-viewer__rail {
    flex: none;
    width: 8.25rem;
    padding: var(--spacing-ms) var(--spacing-sm);
    border-right: 1px solid var(--color-border);
    background: var(--color-bg-light);
    display: flex;
    flex-direction: column;
    gap: var(--spacing-ms);
    overflow-y: auto;
}

.pdf-viewer__vignette {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: var(--spacing-2xs);
    flex: none;
    padding: var(--spacing-2xs);
    border: 2px solid transparent;
    border-radius: var(--radius-md);
    background: none;
    cursor: pointer;
}

.pdf-viewer__vignette.is-active {
    border-color: var(--color-primary);
    background: var(--surface-2);
}

/* Le cadre tient la place de la vignette AVANT son dessin, a la proportion
   d'une page A4 : sans lui le rail se rallonge sous le doigt pendant qu'on le
   fait defiler, et chaque miniature qui arrive deplace les suivantes. */
.pdf-viewer__vignette-cadre,
.pdf-viewer__vignette-toile {
    display: block;
    width: 100%;
    aspect-ratio: 210 / 297;
    border-radius: var(--radius-sm);
    background: var(--surface-2);
    border: 1px solid var(--color-border);
}

.pdf-viewer__vignette-toile {
    height: auto;
    aspect-ratio: auto;
}

.pdf-viewer__vignette-numero {
    font-family: var(--font-data);
    font-size: var(--font-size-2xs);
    color: var(--color-text-light);
}

/* Le fond du plateau est plus sombre que la page : c'est ce qui detache la
   feuille blanche et lui donne son ombre portee. */
.pdf-viewer__scene {
    flex: 1;
    min-width: 0;
    display: flex;
    justify-content: center;
    align-items: flex-start;
    padding: var(--spacing-lg);
    background: var(--color-neutral-soft);
    overflow: auto;
}

.pdf-viewer__canvas {
    display: block;
    max-width: 100%;
    border-radius: var(--radius-sm);
    background: var(--surface-2);
    box-shadow: 0 18px 44px -24px color-mix(in srgb, var(--color-primary-dark) 55%, transparent);
}

.pdf-viewer__footer {
    display: flex;
    align-items: center;
    gap: var(--spacing-md);
    flex-wrap: wrap;
    padding: var(--spacing-ms) var(--spacing-md);
    border-top: 1px solid var(--color-border);
    background: var(--color-bg-light);
    font-size: var(--font-size-xs);
    color: var(--color-text-light);
}

.pdf-viewer__annonce {
    font-family: var(--font-data);
    font-size: var(--font-size-2xs);
}

.pdf-viewer__hint {
    margin-left: auto;
}

/* ── Quand la bibliotheque ne charge pas ──
   Le pied SUFFIT : il porte le lien vers le document, qui ne depend d'aucun
   script. On retire ce qui ne peut plus rien faire — une barre de commandes
   inerte et un plateau vide se lisent comme une panne, alors que le fichier
   reste a un clic. */
.pdf-viewer.is-failed .pdf-viewer__toolbar,
.pdf-viewer.is-failed .pdf-viewer__body {
    display: none;
}

.pdf-viewer:fullscreen {
    border-radius: 0;
}

.pdf-viewer:fullscreen .pdf-viewer__body {
    max-height: none;
    height: calc(100vh - 7rem);
}

/* ── Sous 48 em : le rail de vignettes disparait ──
   132 px de miniatures sur un ecran de 390 laissent 190 px au document, ou
   plus rien ne se lit. La navigation reste entiere : chevrons, champ de page
   et recherche. */
@media (width < 48em) {
    .pdf-viewer__rail {
        display: none;
    }

    .pdf-viewer__body {
        min-height: 24rem;
        max-height: 70vh;
    }

    .pdf-viewer__scene {
        padding: var(--spacing-ms);
    }

    .pdf-viewer__hint {
        margin-left: 0;
    }
}

/* ══════════════════════════════════════════════════════════════
   Replay metadata — sous-template `library/_metadata/_replay.html.twig`
   Affiché sous le viewer iframe YouTube. Cale à 70ch comme le body
   éditorial pour rester aéré (l'iframe vidéo a sa pleine largeur).
   ══════════════════════════════════════════════════════════════ */
.replay-meta {
    max-width: 70ch;
    margin-top: 0;
    margin-bottom: var(--spacing-xl);
}

.replay-meta__info {
    display: grid;
    grid-template-columns: 1fr;
    gap: var(--spacing-sm);
    margin: 0 0 var(--spacing-lg);
    padding: var(--spacing-md);
    background: var(--color-bg-light);
    border-radius: var(--radius-md);
}

@media (min-width: 30em) {
    .replay-meta__info {
        grid-template-columns: repeat(2, 1fr);
    }
}

.replay-meta__row {
    display: flex;
    flex-direction: column;
    gap: 0.125rem;
    margin: 0;
}

.replay-meta__row dt {
    font-size: var(--font-size-xs);
    color: var(--color-text-light, var(--color-text-light));
    font-weight: 500;
    text-transform: uppercase;
    letter-spacing: 0.04em;
}

.replay-meta__row dd {
    font-size: 0.95rem;
    margin: 0;
    color: var(--color-text);
}

.replay-meta__link {
    display: inline-flex;
    align-items: center;
    gap: 0.3rem;
    color: var(--color-primary);
    text-decoration: none;
    font-weight: 500;
}

.replay-meta__link:hover {
    text-decoration: underline;
}

.replay-meta__section {
    margin-bottom: var(--spacing-lg);
}

.replay-meta__section-title {
    font-size: 1rem;
    font-weight: 600;
    margin: 0 0 var(--spacing-sm);
    color: var(--color-text);
}

.replay-meta__trainings {
    list-style: none;
    padding: 0;
    margin: 0;
}

.replay-meta__trainings li {
    padding: var(--spacing-xs) 0;
    border-bottom: 1px solid var(--color-border);
    color: var(--color-text);
}

.replay-meta__trainings li:last-child {
    border-bottom: none;
}

/* « Autour de cette session » — ressources du même créneau. Calé sur
   `.replay-meta__section` pour ne pas introduire un second vocabulaire visuel
   dans la même colonne. */
/* Le titre local a disparu : le bloc est une carte a en-tete comme les autres
   de cette colonne, et c'est `_titled_card` qui porte desormais son sur-titre,
   son titre et son filet. Il rendait un `h2` a 1 rem en graisse 600, la ou la
   charte pose le titre de carte en `--font-title` a `--font-size-2xl` : le seul
   titre de niveau 2 du site a ne pas ressembler aux autres. */
.session-resources {
    margin-top: var(--spacing-lg);
}

.session-resources__list {
    list-style: none;
    padding: 0;
    margin: 0;
}

.session-resources__item {
    border-bottom: 1px solid var(--color-border);
}

.session-resources__item:last-child {
    border-bottom: none;
}

.session-resources__link {
    display: flex;
    align-items: center;
    gap: var(--spacing-xs);
    padding: var(--spacing-xs) 0;
    color: var(--color-text);
    text-decoration: none;
}

.session-resources__link:hover,
.session-resources__link:focus-visible {
    color: var(--color-primary);
    text-decoration: underline;
}

/* ──────────────────────────────────────────────────────────────
   Speaker cards — intervenants d'un replay.
   Grille responsive (1 col mobile, 2 cols >= 30em) avec un avatar
   initiales à gauche et nom/affiliation/role à droite.
   ────────────────────────────────────────────────────────────── */
.speaker-grid {
    list-style: none;
    padding: 0;
    margin: 0;
    display: grid;
    grid-template-columns: 1fr;
    gap: var(--spacing-sm);
}

@media (min-width: 30em) {
    .speaker-grid {
        grid-template-columns: repeat(2, 1fr);
    }
}

.speaker-card {
    /* La card peut être un `<li>` simple (pas de bio publique) ou contenir
       un `<a class="speaker-card__link">` qui couvre toute la surface. Dans
       les deux cas le rendu visuel est identique — le hover plus marqué est
       porté par `.speaker-card__link:hover` (cf. plus bas). */
    padding: 0;
    background: var(--color-bg-light);
    border: 1px solid var(--color-border);
    border-radius: var(--radius-md);
    transition: border-color 0.15s ease, box-shadow 0.15s ease;
    overflow: hidden;
}

.speaker-card:hover {
    border-color: color-mix(in srgb, var(--color-primary) 35%, var(--color-border));
    box-shadow: 0 2px 8px -4px color-mix(in srgb, var(--color-primary-dark) 12%, transparent);
}

/* Layout interne — appliqué soit directement sur la `<li>` (pas de lien),
   soit sur le `<a>` quand la bio publique existe (cible cliquable couvrant
   toute la surface, alignée avec le contenu). */
.speaker-card,
.speaker-card__link {
    display: flex;
    align-items: flex-start;
    gap: var(--spacing-sm);
}

.speaker-card__link {
    padding: var(--spacing-sm) var(--spacing-md);
    color: inherit;
    text-decoration: none;
    width: 100%;
    transition: background-color 0.12s ease;
}

/* Quand la card est un simple `<li>` sans lien : conserver le padding via
   un sélecteur d'absence pour éviter d'avoir deux niveaux de padding. */
.speaker-card:not(:has(.speaker-card__link)) {
    padding: var(--spacing-sm) var(--spacing-md);
}

.speaker-card__link:hover,
.speaker-card__link:focus-visible {
    background: color-mix(in srgb, var(--color-primary) 5%, transparent);
    outline: none;
}

.speaker-card__link:focus-visible {
    box-shadow: inset 0 0 0 2px color-mix(in srgb, var(--color-primary) 50%, transparent);
}

.speaker-card__avatar {
    flex-shrink: 0;
    width: 2.75rem;
    height: 2.75rem;
    border-radius: 50%;
    background: linear-gradient(135deg, color-mix(in srgb, var(--color-primary) 85%, white) 0%, var(--color-primary) 100%);
    color: var(--surface-2);
    display: flex;
    align-items: center;
    justify-content: center;
    font-weight: 700;
    font-size: 0.875rem;
    letter-spacing: 0.02em;
    box-shadow: inset 0 -2px 4px color-mix(in srgb, var(--color-shade) 10%, transparent);
}

.speaker-card__initials {
    line-height: 1;
}

.speaker-card__body {
    min-width: 0;
    flex: 1;
    display: flex;
    flex-direction: column;
    gap: 0.125rem;
}

.speaker-card__name {
    margin: 0;
    font-weight: 600;
    color: var(--color-text);
    font-size: 0.9375rem;
    line-height: 1.3;
    display: flex;
    flex-wrap: wrap;
    gap: 0.25rem;
    align-items: baseline;
}

.speaker-card__civility {
    color: var(--color-text-light, var(--color-text-light));
    font-weight: 500;
    font-size: 0.8125rem;
}

.speaker-card__affiliation {
    margin: 0;
    font-size: 0.8125rem;
    color: var(--color-text-light, var(--color-text-light));
    line-height: 1.35;
}

.speaker-card__role {
    display: inline-flex;
    align-items: center;
    margin-top: 0.25rem;
    padding: 0.0625rem 0.5rem;
    border-radius: var(--radius-sm);
    background: color-mix(in srgb, var(--color-primary) 12%, transparent);
    color: var(--color-primary);
    font-size: 0.6875rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: 0.04em;
    align-self: flex-start;
}

/* ──────────────────────────────────────────────────────────────
   Video stage — replay layout : player YouTube + panneau
   chapitres côte à côte sur desktop (≥62em), empilés sur mobile.
   Le wrapper porte le scope Alpine `seek()` ; chaque lien chapitre
   dispatch `yt-seek` localement (bubble vers le wrapper, listener
   y appelle `seekTo` via postMessage sur l'iframe YouTube).
   Le panneau chapitres reste fond blanc épuré (zéro card) : titre +
   bouton toggle + liste navigable. Plié par défaut sur mobile,
   déplié sur desktop pour rester immédiatement consultable.
   ────────────────────────────────────────────────────────────── */
/* UNE SEULE CARTE POUR LE LECTEUR ET SES CHAPITRES — composant 27. Ils
   formaient deux blocs separes par une gouttiere : le panneau flottait a cote
   du lecteur comme un rail de page, alors qu'il appartient a la video. Reunis
   sous un cadre, avec le panneau sur le gris chaud et un filet qui les separe,
   on lit un objet, pas deux voisins.

   `overflow: hidden` : c'est lui qui fait mordre le rayon sur l'iframe et sur
   le panneau, sans avoir a le repeter sur chacun. */
/* ── LE PLATEAU EMPILE, il ne partage plus ──
   Le chapitrage vivait dans une colonne de 18 rem a droite du lecteur. Sur la
   colonne de lecture d'une fiche — 848 px — il laissait 550 px a la video et
   coupait ses propres horodatages : « 0:28 » rendait « ):28 ». La maquette pose
   les chapitres SOUS la video, dans une carte a eux.

   Plus de cadre ni de fond propres non plus : le plateau n'enveloppe plus deux
   objets, il les met l'un au-dessus de l'autre, et chacun porte sa forme — le
   lecteur son 16/9, la carte de chapitres celle de toutes les cartes de la
   colonne. Le wrapper ne sert donc plus qu'au scope Alpine et a la gouttiere.

   La marge basse part avec : la colonne est un conteneur flex a gouttiere. */
.video-stage {
    display: flex;
    flex-direction: column;
    gap: var(--spacing-lg);
    min-width: 0;
}

/* Repli quand la lecture des videos sur place est refusee dans la modale de
   consentement. Il occupe la place du lecteur : un message pose sous un cadre
   vide se lit comme une panne, au meme endroit il se lit comme une reponse. */
/* ── LE PLATEAU DE CONSENTEMENT ──
   La maquette pose un 16/9 hachure a la place de la video, et un panneau au
   centre. Le rapport compte : c'est LUI qui dit « il y a une video ici ». Le
   bandeau de texte qui tenait cette place faisait trois centimetres de haut et
   se lisait comme une note de bas de page, sur une fiche dont la video EST le
   sujet.

   Le motif vient de `ui-hatch`, la brique partagee, dont les trois entrees se
   redeclarent ici pour le passer dans le marine de la marque. C'est exactement
   ce que sa documentation prevoit. */
.video-stage__consent {
    --hatch-ground: var(--color-primary-dark);
    --hatch-ink: color-mix(in srgb, var(--color-primary-dark) 88%, var(--color-shade));
    --hatch-band: 0.625rem;

    display: grid;
    place-items: center;
    aspect-ratio: 16 / 9;
    padding: var(--spacing-lg);
    border-radius: var(--radius-lg);
    overflow: hidden;
}

.video-stage__consent[hidden] { display: none; }

/* Le voile blanc detache le panneau du motif sans l'opacifier : le hachure
   reste lisible derriere, ce qui garde au plateau son caractere d'emplacement
   de video plutot que de fond decoratif. */
.video-stage__consent-panel {
    max-width: 30rem;
    display: flex;
    flex-direction: column;
    gap: var(--spacing-ms);
    padding: var(--spacing-lg);
    border: 1px solid color-mix(in srgb, var(--color-on-primary) 22%, transparent);
    border-radius: var(--radius-md);
    background: color-mix(in srgb, var(--color-on-primary) 8%, transparent);
    backdrop-filter: blur(2px);
}

.video-stage__consent-title {
    margin: 0;
    font-family: var(--font-title);
    font-size: var(--font-size-lg);
    font-weight: 700;
    line-height: 1.3;
    color: var(--color-on-primary);
}

.video-stage__consent-text {
    margin: 0;
    font-size: var(--font-size-sm);
    line-height: 1.55;
    color: var(--color-on-navy);
}

.video-stage__consent-actions {
    display: flex;
    flex-wrap: wrap;
    gap: var(--spacing-sm);
    padding-top: var(--spacing-2xs);
}

.video-stage__consent-link {
    font-size: var(--font-size-xs);
    color: var(--color-on-navy-muted);
}

/* Sous 48 em, le panneau ne tient pas dans un 16/9 de 358 px de large : le
   rapport cede, la hauteur suit le contenu. Garder le cadre aurait coupe les
   boutons, ce qui est exactement l'inverse du but. */
@media (width < 48em) {
    .video-stage__consent {
        aspect-ratio: auto;
        padding: var(--spacing-md);
    }
}

/* Une iframe sans `src` occupe quand meme sa place — 557 px de cadre vide
   mesures sur une fiche de rediffusion. Elle n'est posee qu'a l'accord, donc
   elle ne se dessine qu'a partir de la. */
iframe[data-video-embed]:not([src]) { display: none; }

/* « Pas encore repondu » et « refuse » ne se disent pas pareil : la premiere
   phrase explique, la seconde constate. Le drapeau vit sur `<html>`, pose par
   `assets/app.js` des la lecture du choix. */
.video-stage__refus-refus { display: none; }

/* `block` et non `inline` : ces deux phrases sont desormais des PARAGRAPHES du
   panneau, pas deux fragments d'une meme ligne. En `inline`, la seconde ne
   prenait pas la gouttiere du panneau et se collait aux boutons. */
.consentement-repondu .video-stage__refus-attente { display: none; }
.consentement-repondu .video-stage__refus-refus { display: block; }



/* Un `<button>` qui ouvre la modale, pas un lien : il ne mene nulle part. Il
   est dessine comme le lien voisin pour que la phrase se lise d'un trait. */
.video-stage__refus-lien {
    padding: 0;
    border: 0;
    background: none;
    font: inherit;
    color: var(--color-primary);
    text-decoration: underline;
    text-underline-offset: 3px;
    cursor: pointer;
}

.video-stage__player {
    /* Reset hérité du `.resource-single__viewer` générique : la
       margin-bottom est déjà portée par `.video-stage` wrapper.
       `position:relative` pour ancrer le bouton « ré-ouvrir
       chapitres » qui se positionne en absolute top-right. */
    margin-bottom: 0;
    min-width: 0;
    position: relative;
}

/* Bouton flottant pour ré-ouvrir le panneau chapitres une fois plié.
   Reste discret (semi-transparent sombre) pour ne pas masquer l'image
   du player. */
/* `.video-stage__chapters-reopen` EST PARTI : ce bouton flottant ne servait
   qu'a rouvrir un panneau lateral qu'on pouvait plier pour elargir la video.
   Sous la video, un chapitrage ne dispute plus sa largeur a personne — il n'y
   a plus rien a plier, donc plus rien a rouvrir. */

/* La carte de chapitres n'a PLUS DE FORME PROPRE : `_titled_card` la lui donne,
   comme aux autres cartes de la colonne. Les quatre regles retirees ici lui
   posaient un fond gris, un filet a gauche ou en haut selon le palier, et une
   position collante — trois traitements qui n'avaient de sens que dans une
   colonne laterale. */

/* L'EN-TETE LOCAL DU CHAPITRAGE EST PARTI, avec son bouton de repli : c'est
   `_titled_card` qui porte desormais le sur-titre « Navigation », le titre
   « Chapitres » et le filet, comme toutes les autres cartes de la colonne. */

/* ── LES RANGEES DU CHAPITRAGE, a la forme de la maquette ──
   Un filet au-dessus de chaque rangee, l'horodatage en chasse fixe a gauche, le
   titre en titrage. C'est la meme grammaire que le sommaire d'un document et
   que les faits de la colonne d'appui : un repere chiffre s'aligne d'une ligne
   a l'autre, donc il est en chasse fixe.

   Plus de defilement propre ni de hauteur bornee : c'etaient les contraintes
   d'un panneau lateral colle. Dans une carte du fil de lecture, la liste
   s'etend. */
.video-stage__chapters-list {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
}

.video-stage__chapters-link {
    display: grid;
    grid-template-columns: auto minmax(0, 1fr);
    align-items: baseline;
    gap: var(--spacing-sm) var(--spacing-md);
    padding: var(--spacing-ms) 0;
    border-top: 1px solid var(--color-border);
    color: var(--color-text);
    text-decoration: none;
    line-height: 1.4;
    transition: color var(--transition-fast);
}

/* Pas de filet sur la premiere : l'intitule de la carte la borne deja. */
.video-stage__chapters-item:first-child .video-stage__chapters-link {
    border-top: 0;
}

.video-stage__chapters-link:hover,
.video-stage__chapters-link:focus-visible {
    color: var(--color-primary);
    outline: none;
    text-decoration: none;
}

.video-stage__chapters-link:focus-visible {
    box-shadow: 0 0 0 2px color-mix(in srgb, var(--color-primary) 40%, transparent);
}

.video-stage__chapters-time {
    font-family: var(--font-data);
    font-size: var(--font-size-xs);
    font-weight: 500;
    color: var(--color-primary);
}

.video-stage__chapters-label {
    font-family: var(--font-title);
    font-size: var(--font-size-base);
    font-weight: 700;
    line-height: 1.35;
    color: var(--color-primary-dark);
    overflow-wrap: anywhere;
}


/* Un sommaire SANS entree ne s'affiche pas. La liste est remplie cote client
   par `articleToc` en scannant les titres du corps : sur une page qui n'en a
   aucun — une fiche d'evenement dont tout le contenu est une grille de
   rediffusions — elle reste vide, et seul le mot « Sommaire » restait, en
   tete d'un panneau qui ne menait nulle part.

   `:has()` plutot qu'un drapeau Alpine : la condition porte sur le DOM reel
   apres remplissage, donc elle reste juste quel que soit le chemin qui a
   rempli la liste. */
.article-sidebar__toc:has(.article-toc__list:empty) {
    display: none;
}

/* Et si le panneau lateral n'a RIEN a montrer — ni entree de sommaire, ni
   bloc (lieu, agenda, inscription) — il disparait en entier, bouton
   d'ouverture compris. Masquer le seul sommaire ne suffisait pas : restait un
   bouton « Afficher la barre laterale » qui prenait sa place et n'ouvrait sur
   rien. Une commande qui ne commande rien est pire qu'un panneau vide. */
.article-sidebar:not(:has(.article-sidebar__section)):not(:has(.article-toc__list li)) {
    display: none;
}

/* Le contenu reprend alors toute la largeur : sans cela la grille garderait la
   gouttiere et la colonne du panneau, et le texte resterait cale a gauche
   d'un vide. */
.article-single__layout:not(:has(.article-sidebar__section)):not(:has(.article-toc__list li)):not(:has(.reading-share-rail)) {
    /* BORNEE et centree, pas `1fr` : sans colonne de sommaire, le texte prenait
       les 1 216 px du conteneur, soit environ cent cinquante signes par ligne
       quand l'oeil en suit soixante a soixante-quinze. Meme mesure que partout
       ailleurs sur le site, et plus large que la colonne d'un article AVEC
       sommaire (908 px) — donc aucun contenu ne se resserre.

       Le cas ne concernait pas que la fiche portrait : tout article dont le
       corps ne porte aucun titre de niveau 2 tombait deja dedans.

       `:not(:has(.reading-share-rail))` : sans cette exclusion, un layout qui
       porte encore le rail de partage vertical voyait sa grille reduite a UNE
       colonne — et le rail, premier element de la grille, remontait AU-DESSUS
       du titre, centre au milieu de la page. Cinq pastilles de partage
       flottant dans le vide. Constate sur la fiche question du centre d'aide
       le 2026-08-18 ; regression introduite le matin meme avec cette regle. */
    grid-template-columns: min(100%, 62rem);
    justify-content: center;
}
