/* Identité visuelle « Kraft » (B1), posée le 22/09 au soir, retenue parmi
   six maquettes (canevas « PickOne — propositions de mise en page ») : les
   listes et les cadeaux sont des ÉTIQUETTES CADEAU — coin coupé, trou pour
   la ficelle, liseré de couleur en pied — posées sur un fond papier. Ce qui
   est offert porte un CACHET daté, ce qui attend une décision est un
   POST-IT, et les petites mentions sont écrites à la main.

   Palette tirée du logo, comme la première passe : encre, corail, vert du
   badge-coche, jaune-ruban. Le corail des ACTIONS est assombri (#B8382A) :
   le #E14F3D du logo, en bouton plein sous du texte blanc ou en lien sur le
   papier, plafonne vers 3,9:1 — sous les 4,5:1 demandés pour du texte
   courant. Il reste celui des liserés et du cœur, où il n'y a rien à lire.

   Polices AUTO-HÉBERGÉES (static/cadeaux/polices/, licence OFL à côté) :
   pas d'appel à Google Fonts, donc pas d'adresse IP de visiteur envoyée à
   un tiers — et une page de partage qui s'affiche pareil hors ligne. */
@font-face {
  font-family: "Lora"; font-weight: 700; font-style: normal; font-display: swap;
  src: url("polices/lora-700.9c4d5c38f969.woff2") format("woff2");
}
@font-face {
  font-family: "Figtree"; font-weight: 400; font-style: normal; font-display: swap;
  src: url("polices/figtree-400.7bfd10a3def3.woff2") format("woff2");
}
@font-face {
  font-family: "Figtree"; font-weight: 600; font-style: normal; font-display: swap;
  src: url("polices/figtree-600.4376f5953b85.woff2") format("woff2");
}
@font-face {
  font-family: "Figtree"; font-weight: 700; font-style: normal; font-display: swap;
  src: url("polices/figtree-700.70aaa6879de5.woff2") format("woff2");
}
@font-face {
  font-family: "Caveat"; font-weight: 700; font-style: normal; font-display: swap;
  src: url("polices/caveat-700.9700119a3654.woff2") format("woff2");
}

:root {
  color-scheme: light dark;
  --fond: #F4EDE1;          /* le papier */
  --carte: #FFFBF3;         /* une étiquette, un formulaire */
  --texte: #22201C;
  --discret: #6B665C;
  --trait: #E0D5C2;
  --trou: #D8C9AE;          /* le bord du trou de ficelle, les liserés neutres */
  --kraft: #8A5A2B;         /* l'encre des mentions écrites à la main */
  --accent: #B8382A;        /* les actions : boutons pleins, liens */
  --sur-accent: #FFFFFF;    /* le texte posé sur l'accent */
  --corail: #E14F3D;        /* le liseré d'un coup de cœur, le cœur */
  --succes: #14803D;
  --alerte: #9a3412;
  --postit: #FEF1B8;
  --postit-encre: #6A4A00;
  --postit-trait: #D9C27A;
  --ombre: rgba(80, 60, 20, 0.12);
  /* Le ruban doré d'un cadeau offert (24/09) : --ruban pour ce qui décore
     (ruban, liseré, fond du bouton, sous une encre sombre), --ruban-encre
     pour ce qui se lit (le cachet, la ligne « Offert le … ») — le doré
     lui-même plafonne sous 3:1 sur le papier. */
  --ruban: #E0A82E;
  --ruban-encre: #7A5200;
  /* Couleurs du mot "One" dans le logo d'en-tête : vert (badge) sur fond
     clair, corail sur fond sombre -- comme ".gift" dans le logo complet.
     "Pick" suit la même bascule : encre, puis jaune-ruban. */
  --marque-pick: #22201C;
  --marque-un: #14803D;
  /* La couverture kraft d'un carnet (une liste, voir .liste), son dos et
     sa tranche. */
  --couverture: #C99A6B;
  --couverture-dos: #A97B4F;
  --couverture-bord: #9C7046;
}
@media (prefers-color-scheme: dark) {
  /* Le papier devient un carton sombre ; l'accent s'éclaircit pour rester
     lisible, et le texte des boutons pleins passe à l'encre. */
  :root {
    --fond: #1E1B17; --carte: #2A2620; --texte: #F5F1E8; --discret: #A8A192;
    --trait: #3D372E; --trou: #4A4236; --kraft: #D9B98C;
    --accent: #FF7A63; --sur-accent: #22201C; --corail: #FF7A63;
    --succes: #5CC285; --alerte: #fca976;
    --postit: #3F3517; --postit-encre: #FADD7A; --postit-trait: #6A5A2A;
    --ombre: rgba(0, 0, 0, 0.35);
    --ruban: #E8B84A; --ruban-encre: #FADD7A;
    --marque-pick: #FADD7A; --marque-un: #FF7A63;
    --couverture: #6B4A2C; --couverture-dos: #54391F; --couverture-bord: #3E2A17;
  }
}

* { box-sizing: border-box; }
/* Une règle posant `display` peut l'emporter sur l'attribut [hidden] selon
   sa spécificité et son ordre : posé une bonne fois, comme sur soireejeux. */
[hidden] { display: none !important; }
body {
  margin: 0; background: var(--fond); color: var(--texte);
  font: 16px/1.5 Figtree, system-ui, -apple-system, "Segoe UI", sans-serif;
}
a { color: var(--accent); }

/* -- L'en-tête ------------------------------------------------------------ */

header {
  display: flex; align-items: center; justify-content: space-between; gap: 16px;
  flex-wrap: wrap;
  padding: 14px 20px;
}
@media (min-width: 720px) { header { padding: 16px 32px; } }
@media (min-width: 1080px) { header { padding: 18px 48px; } }
header form { display: flex; align-items: center; gap: 12px; margin: 0; }
.marque {
  display: flex; align-items: center; gap: 10px;
  font-family: Lora, Georgia, serif; font-weight: 700; font-size: 1.35rem;
  color: inherit; text-decoration: none;
}
.marque-icone { display: block; width: 34px; height: 34px; flex: none; }
.marque-texte { color: var(--marque-pick); }
.marque-un { color: var(--marque-un); }
.marque-domaine { color: var(--discret); }
.qui { font-size: .95rem; }
.lien {
  background: none; border: 0; padding: 0; font: inherit; font-size: .9rem;
  color: var(--accent); text-decoration: underline; cursor: pointer;
  white-space: nowrap;
}

/* -- La page -------------------------------------------------------------- */

main { max-width: 680px; margin: 0 auto; padding: 16px 20px 56px; }
@media (min-width: 720px) {
  main { max-width: 920px; padding: 20px 32px 64px; }
}
@media (min-width: 1080px) {
  main { max-width: 1240px; padding: 24px 48px 72px; }
}
h1 {
  font-family: Lora, Georgia, serif; font-weight: 700;
  font-size: 2.1rem; line-height: 1.1; letter-spacing: -.01em;
  margin: 0 0 20px;
}
@media (min-width: 720px) { h1 { font-size: 2.8rem; } }
h2 {
  font-family: Lora, Georgia, serif; font-weight: 700;
  font-size: 1.45rem; line-height: 1.2; margin: 36px 0 16px;
}
h3 { font-family: Lora, Georgia, serif; font-weight: 700; }

/* Ce qui est « écrit à la main » : les mentions courtes seulement (pour
   qui est une liste, un coup de cœur, un aparté à côté d'un titre). Jamais
   un paragraphe — Caveat se lit mal au-delà de quelques mots. */
.manuscrit {
  font-family: Caveat, "Segoe Print", cursive; font-weight: 700;
  font-size: 1.4rem; line-height: 1.15; color: var(--kraft);
}
.entete-section .manuscrit { font-size: 1.35rem; }
p.manuscrit { margin: 0; }
/* Le titre d'une page, surmonté d'une mention à la main (« la liste de
   Céline »). */
.surtitre { display: block; margin: 0 0 2px; }
h1 + .detail { margin-top: -12px; margin-bottom: 20px; }

.detail { margin: 0; color: var(--discret); font-size: .94rem; }
.attente { color: var(--alerte); }
.avertissement {
  margin: 10px 0 0; padding: 10px 12px; border-radius: 8px; font-size: .9rem;
  color: var(--alerte); background: color-mix(in srgb, var(--alerte) 10%, transparent);
}
.vide { font-family: Caveat, cursive; font-weight: 700; font-size: 1.4rem; color: var(--kraft); }
.retour { margin: 0 0 6px; }
.retour a { color: var(--kraft); font-size: .95rem; font-weight: 600; text-decoration: none; }
.retour a:hover { text-decoration: underline; }

/* -- Les étiquettes ------------------------------------------------------- */

/* Un seul conteneur pour les listes de « Mes listes », les cadeaux d'une
   liste et ceux de la page de partage : une colonne sur mobile, autant
   qu'il en tient ensuite. */
.grille-cartes { display: grid; gap: 20px; }
@media (min-width: 640px) {
  .grille-cartes { grid-template-columns: repeat(auto-fill, minmax(240px, 1fr)); gap: 24px; }
}

/* L'étiquette elle-même. Le coin coupé est un clip-path : il rogne aussi
   toute ombre et tout contour posés sur l'élément, d'où un survol et un
   focus signalés par la couleur du papier plutôt que par une ombre. Le trou
   de ficelle est un ::before, le liseré de couleur une bordure basse (que
   le clip-path épargne, il ne coupe que les coins du haut). */
.cadeau {
  position: relative;
  display: flex; flex-direction: column; gap: 4px;
  min-height: 190px;
  padding: 42px 20px 18px;
  background: var(--carte);
  border-bottom: 5px solid var(--trou);
  clip-path: polygon(24px 0, calc(100% - 24px) 0, 100% 24px, 100% 100%, 0 100%, 0 24px);
}
.cadeau::before {
  content: ""; position: absolute; top: 14px; left: 50%; margin-left: -8px;
  width: 16px; height: 16px; border-radius: 50%;
  background: var(--fond); box-shadow: inset 0 0 0 2px var(--trou);
}
.liste h3, .cadeau h3 { margin: 0; font-size: 1.3rem; line-height: 1.2; }
.liste h3 a, .cadeau h3 a { color: inherit; text-decoration: none; }
.liste h3 a:hover { text-decoration: underline; }
/* Ce qui se lit en bas de l'étiquette : actions, prix, alerte. */
.liste .pied, .cadeau .pied {
  margin-top: auto; padding-top: 10px;
  display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 6px 14px;
}
.pied .liens { display: flex; flex-wrap: wrap; gap: 4px 14px; font-size: .92rem; font-weight: 600; }
.prix { font-size: 1.25rem; font-weight: 700; }

/* Le liseré d'un coup de cœur. */
.cadeau.coup-de-coeur { border-bottom-color: var(--corail); }

/* Les listes sont des CARNETS (25/09, piste A retenue par Arnaud parmi
   quatre) : une couverture kraft reliée à gauche (l'ombre intérieure fait
   le dos), un élastique vertical à la couleur du rôle (::after), et le
   contenu sur une page crème. Ni coin coupé ni trou de ficelle : ceux-là
   sont aux cadeaux, et c'est ce qui distingue les deux d'un coup d'œil.
   --role porte la couleur : corail pour moi, vert je gère, alerte quand
   personne ne la gère. */
.liste {
  --role: var(--trou);
  position: relative;
  display: flex; flex-direction: column;
  min-height: 200px;
  padding: 20px 36px 18px 30px;
  background: var(--couverture);
  border-radius: 4px 14px 14px 4px;
  box-shadow: inset 12px 0 0 var(--couverture-dos), 0 2px 0 var(--couverture-bord), 0 10px 20px var(--ombre);
}
.liste::after {
  content: ""; position: absolute; top: 0; bottom: 0; right: 16px;
  width: 8px; border-radius: 2px; background: var(--role);
}
.liste-page {
  display: flex; flex-direction: column; gap: 4px; flex-grow: 1;
  padding: 14px 14px 16px; border-radius: 6px;
  background: var(--carte); box-shadow: 0 1px 0 rgba(0, 0, 0, .10);
}
.liste h3 { margin: 0; font-size: 1.3rem; line-height: 1.2; }
.liste h3 a { color: inherit; text-decoration: none; }
.liste h3 a:hover { text-decoration: underline; }
.liste.pour-moi { --role: var(--corail); }
.liste.geree { --role: var(--succes); }
.liste.orpheline { --role: var(--alerte); }

/* Carte entièrement cliquable (voir site.js) : le curseur, et le carnet
   qui se soulève d'un cran, l'annoncent. Sans JS, l'attribut reste là sans
   effet et le titre fait le travail. */
.liste[data-carte-lien] { cursor: pointer; transition: transform .15s, box-shadow .15s; }
.liste[data-carte-lien]:hover,
.liste[data-carte-lien]:focus-within {
  transform: translateY(-2px);
  box-shadow: inset 12px 0 0 var(--couverture-dos), 0 2px 0 var(--couverture-bord), 0 14px 26px var(--ombre);
}

.coeur { color: var(--corail); }
.statut { font-weight: 600; }
/* Le statut d'un cadeau qui reste à offrir — « Disponible » ou
   « Disponible à la maison » — s'écrit à la main (25/09, demandé par
   Arnaud) : une mention de deux ou trois mots, ce pour quoi Caveat est
   fait. Même habit sur la page de modification, pour le seul statut
   Disponible ; « Offert » garde le sien. */
.statut,
.statut-actuel.statut-disponible {
  font-family: Caveat, "Segoe Print", cursive; font-weight: 700;
  font-size: 1.3rem; line-height: 1.15;
}
.statut-actuel.statut-disponible { font-size: 1.5rem; }
/* Une petite alerte à l'intérieur d'une étiquette (propositions à
   examiner) : une pastille pleine plutôt qu'une phrase en couleur. */
.etiquette-alerte {
  display: inline-block; margin: 0;
  padding: 3px 10px; border-radius: 999px; font-size: .85rem; font-weight: 700;
  color: var(--alerte); background: color-mix(in srgb, var(--alerte) 12%, transparent);
}

/* L'étiquette en pointillés qui crée : « + Créer ma liste », « + Ajouter
   un cadeau ». Même taille que ses voisines, pas de coin coupé — elle
   n'existe pas encore. */
.etiquette-nouvelle {
  min-height: 190px;
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 4px;
  padding: 16px; text-align: center; text-decoration: none;
  border: 2px dashed var(--trou); border-radius: 6px; color: var(--kraft);
}
/* Sur « Mes listes », l'emplacement vide a la silhouette d'un carnet. */
.grille-cartes .liste ~ .etiquette-nouvelle,
.grille-cartes .vide ~ .etiquette-nouvelle { border-radius: 4px 14px 14px 4px; }
.etiquette-nouvelle .manuscrit { font-size: 1.75rem; }
.etiquette-nouvelle .detail { font-size: .88rem; }
.etiquette-nouvelle:hover { border-color: var(--kraft); background: color-mix(in srgb, var(--carte) 50%, transparent); }

/* -- Les post-it : ce qui attend une décision ---------------------------- */

/* Propositions à examiner, listes à gérer, invitations, demandes
   d'inscription : même geste partout (accepter ou refuser), même papier.
   Légèrement de travers, jamais deux fois dans le même sens. */
.propositions { display: grid; gap: 16px; }
@media (min-width: 720px) {
  .propositions { grid-template-columns: repeat(auto-fill, minmax(320px, 1fr)); gap: 20px; }
}
.propositions > h2, .propositions > .detail, .propositions > .entete-section { grid-column: 1 / -1; }
.propositions > h2 { margin-bottom: 0; }
.propositions .proposition {
  padding: 16px 18px; background: var(--postit); color: var(--texte);
  box-shadow: 0 8px 16px var(--ombre);
  transform: rotate(-.8deg);
}
.propositions .proposition:nth-of-type(even) { transform: rotate(.6deg); }
.propositions .proposition .detail { color: color-mix(in srgb, var(--texte) 70%, var(--postit)); }
.propositions .proposition p { margin: 0 0 12px; }
.propositions .actions { display: flex; flex-wrap: wrap; gap: 8px; }
.propositions .actions form { margin: 0; }
.propositions button[type="submit"].bouton-secondaire { border-color: var(--postit-trait); }

/* -- Les formulaires ------------------------------------------------------ */

/* Une fiche, pas une étiquette : pleine largeur de `main` (revu le 22/09,
   plus de plafond en pixels), coins à peine arrondis. */
.formulaire {
  padding: 20px 22px 22px; border-radius: 6px;
  background: var(--carte);
  box-shadow: 0 1px 0 var(--trait);
}

/* Nom, enseigne (qui porte un texte d'aide long) restent en pleine
   largeur ; lien, prix et cases vivent dans .champs-courts, en flexbox :
   le flex-grow redistribue toujours toute la largeur entre les champs
   présents sur la ligne, quel que soit leur nombre. */
.formulaire-cadeau .champs-courts { display: flex; flex-wrap: wrap; gap: 14px 16px; }
.formulaire-cadeau .champs-courts > p { flex: 1 1 200px; margin: 0; }
.formulaire-cadeau .champs-courts + button[type="submit"] { margin-top: 18px; }
.formulaire p { margin: 0 0 16px; }
.formulaire label { display: block; margin-bottom: 4px; font-size: .9rem; font-weight: 600; color: var(--discret); }
.formulaire input, .formulaire textarea, .formulaire select {
  width: 100%; min-height: 44px; padding: 9px 12px; font: inherit;
  border: 1px solid var(--trait); border-radius: 8px;
  background: var(--fond); color: var(--texte);
}
.formulaire textarea { resize: vertical; }
.formulaire input:focus-visible, .formulaire textarea:focus-visible, .formulaire select:focus-visible {
  outline: 2px solid var(--accent); outline-offset: 1px; border-color: transparent;
}
.email-propose { cursor: pointer; font-family: inherit; }
.formulaire input[type="checkbox"] { width: 18px; min-height: 0; height: 18px; accent-color: var(--accent); }
.champ-case { display: flex; align-items: center; }
.formulaire .etiquette-case {
  display: flex; align-items: center; gap: 8px; margin: 0;
  font-size: .95rem; font-weight: 400; color: var(--texte); cursor: pointer;
}
.formulaire .etiquette-case input[type="checkbox"] { margin: 0; }

/* Les erreurs et les textes d'aide d'un formulaire, que Django ne met pas
   en forme : rattachés au champ dont ils parlent, en alerte et en discret. */
.formulaire .errorlist {
  margin: 0 0 6px; padding: 0; list-style: none;
  color: var(--alerte); font-size: .9rem;
}
.formulaire .helptext {
  display: block; margin-top: 4px; color: var(--discret); font-size: .85rem;
}

/* -- Les boutons ---------------------------------------------------------- */

button[type="submit"] {
  min-height: 44px; padding: 10px 20px; font: inherit; font-weight: 700; cursor: pointer;
  border: 0; border-radius: 999px; background: var(--accent); color: var(--sur-accent);
}
button[type="submit"]:hover { filter: brightness(1.08); }
/* `button[type="submit"]` (spécificité 0,1,1) l'emporterait sur une classe
   seule (0,1,0) : les variantes reprennent donc le type pour être sûres de
   gagner, plutôt que de compter sur l'ordre des règles. */
button[type="submit"].bouton-secondaire {
  padding: 10px 18px; font-weight: 600;
  border: 1px solid var(--trait); background: transparent; color: var(--texte);
}
/* La seule action irréversible du site mérite un bouton qui ne ressemble
   à aucun autre : l'alerte, jamais l'accent. */
button[type="submit"].bouton-danger {
  padding: 10px 18px; font-weight: 600;
  border: 1px solid var(--alerte);
  background: color-mix(in srgb, var(--alerte) 12%, transparent);
  color: var(--alerte);
}
/* Un lien qui a la forme d'un bouton plein : il mène vers une page, il ne
   soumet rien, mais il ouvre l'action principale de sa section. Le
   sélecteur porte le nom de balise : sans lui, `.lien` et celle-ci se
   départageraient à l'ordre du fichier. */
a.bouton-lien {
  display: inline-flex; align-items: center; min-height: 40px;
  padding: 8px 18px; font-size: .92rem; font-weight: 700;
  border-radius: 999px; background: var(--accent); color: var(--sur-accent);
  text-decoration: none; white-space: nowrap;
}
a.bouton-lien:hover { filter: brightness(1.08); }

/* « Se déconnecter » : `button[type="submit"]` (0,1,1) l'emporte sur
   `.lien` seule (0,1,0), et la classe n'annulait donc rien — le bouton
   s'est affiché des jours en plein accent. Le sélecteur reprend le type,
   comme .bouton-secondaire et .bouton-danger ; un test garde cette règle. */
button[type="submit"].lien {
  min-height: 0; background: none; border: 0; border-radius: 0; padding: 0;
  font: inherit; font-size: .9rem; font-weight: 400;
  color: var(--accent); text-decoration: underline;
}

/* -- Partage, confirmations ---------------------------------------------- */

/* Le lien de partage : un champ en lecture seule, copié au clic (site.js). */
.partage-lien {
  display: block; width: 100%; max-width: 520px; min-height: 44px; padding: 9px 14px; font: inherit;
  border: 1px dashed var(--trou); border-radius: 999px;
  background: var(--carte); color: var(--texte); cursor: pointer;
}
.partage-confirmation, .confirmation {
  margin: 8px 0 0; padding: 8px 12px; border-radius: 8px; font-size: .88rem;
  color: var(--succes); background: color-mix(in srgb, var(--succes) 12%, transparent);
}
/* « Lien copié ! » se pose PAR-DESSUS le bout droit du champ plutôt que
   dessous (25/09) : dans le flux, il poussait tout ce qui suit de sa
   hauteur pendant deux secondes, puis le laissait retomber — la page
   sautait à chaque copie. Hors du flux, il n'occupe aucune place ; le
   conteneur prend la largeur plafonnée du champ pour que « à droite »
   veuille dire au bout du champ, pas au bout de l'écran. */
.partage-champ { position: relative; max-width: 520px; }
.partage-confirmation {
  position: absolute; top: 50%; right: 6px; transform: translateY(-50%);
  margin: 0; padding: 6px 12px; border-radius: 999px; pointer-events: none;
  background: var(--carte); box-shadow: inset 0 0 0 999px color-mix(in srgb, var(--succes) 12%, transparent);
}


/* -- En-têtes de section, suppression ------------------------------------ */

/* Le titre d'une section et ce qui l'accompagne sur la même ligne : un
   bouton (« Créer ma liste »), ou un aparté écrit à la main. Ils reviennent
   l'un sous l'autre quand la ligne ne suffit plus. */
.entete-section {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: 8px 16px; flex-wrap: wrap;
}
.entete-section > h1, .entete-section > h2 { margin-bottom: 16px; }
.entete-section .aparte { flex: 1 1 auto; }
/* Deux boutons dans un même en-tête (« Modifier », « Gestionnaires ») :
   groupés, pour que l'espace libre reste entre le titre et eux. */
.boutons-entete { display: flex; flex-wrap: wrap; gap: 8px; margin-bottom: 16px; }
/* « Supprimer la liste », au même niveau que « Modifier » (25/09) : même
   contour que .bouton-danger, pas un bouton plein — il ne supprime rien
   lui-même, il ouvre la page de confirmation. */
a.bouton-lien.bouton-supprimer {
  border: 1px solid var(--alerte); color: var(--alerte);
  background: color-mix(in srgb, var(--alerte) 12%, transparent);
}

.actions-suppression {
  display: flex; flex-wrap: wrap; align-items: center; gap: 12px; margin-top: 16px;
}
.actions-suppression form { margin: 0; }
.suppression { margin-top: 40px; }
.suppression a { color: var(--alerte); }

.cadeau form { margin: 8px 0 0; }
.cadeau button[type="submit"].lien { font-size: .92rem; font-weight: 600; text-decoration: none; }

/* -- Notifications -------------------------------------------------------- */

.notifications { display: grid; gap: 10px; }
.notifications .notification {
  margin: 0; padding: 12px 16px; border-radius: 6px; font-size: .95rem;
  background: var(--postit);
}
.notifications .notification a { color: inherit; font-weight: 700; }
.notification-date {
  display: block; font-size: .8rem; color: var(--discret); margin-bottom: 2px;
}
/* Une notification déjà lue reste — c'est tout l'objet de la page — mais
   ne se signale plus : du papier ordinaire au lieu du post-it. */
.notifications .notification.deja-lue {
  background: transparent; box-shadow: inset 0 0 0 1px var(--trait);
}

/* -- Le menu du compte ---------------------------------------------------- */

/* <details>/<summary> : le navigateur ouvre, ferme et gère le clavier tout
   seul, site.js n'ajoute que la fermeture au clic extérieur et à Échap. */
.menu-compte { position: relative; }
.menu-compte > summary {
  display: flex; align-items: center; gap: 10px;
  min-height: 44px; padding: 4px 6px 4px 14px;
  border: 1px solid var(--trait); border-radius: 999px;
  background: var(--carte);
  cursor: pointer; list-style: none;
}
/* Le triangle par défaut de <summary> : deux notations, aucune n'étant
   comprise partout. L'avatar et le chevron du gabarit le remplacent. */
.menu-compte > summary::-webkit-details-marker { display: none; }
.menu-compte > summary::marker { content: ""; }
.menu-compte > summary:hover { border-color: var(--trou); }
.menu-compte > summary:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
.menu-chevron { color: var(--discret); font-size: .8rem; }
.menu-compte[open] .menu-chevron { transform: rotate(180deg); }
/* L'initiale, dans un rond au vert du badge. */
.avatar {
  display: inline-flex; align-items: center; justify-content: center;
  width: 32px; height: 32px; border-radius: 50%;
  background: var(--succes); color: #FFFFFF; font-weight: 700; font-size: .95rem;
}
@media (prefers-color-scheme: dark) { .avatar { color: #1E1B17; } }

/* Le volet : détaché du flux pour ne pas pousser l'en-tête, aligné à
   droite pour rester dans la page sur mobile. */
.menu-compte-volet {
  position: absolute; right: 0; top: calc(100% + 8px); z-index: 20;
  min-width: 230px;
  display: flex; flex-direction: column;
  padding: 6px; border-radius: 10px;
  background: var(--carte);
  box-shadow: 0 0 0 1px var(--trait), 0 12px 28px var(--ombre);
}
.menu-compte-volet a,
.menu-compte-volet button[type="submit"] {
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  width: 100%; min-height: 40px; padding: 9px 12px; border-radius: 6px;
  font-size: .95rem; text-align: left; text-decoration: none; color: var(--texte);
}
.menu-compte-volet a:hover,
.menu-compte-volet button[type="submit"]:hover {
  background: color-mix(in srgb, var(--accent) 10%, transparent); filter: none;
}
/* La déconnexion, dernière entrée : un trait la sépare des trois autres —
   c'est la seule qui ne mène pas à une page du site. Son formulaire perd
   le `display: flex` de `header form`. */
.menu-compte-volet form {
  display: block; margin: 4px 0 0; padding-top: 4px;
  border-top: 1px solid var(--trait);
}
.menu-compte-volet button[type="submit"].lien {
  font-size: .95rem; color: var(--texte); text-decoration: none; cursor: pointer;
}

/* Le décompte des notifications non lues (voir cadeaux.context_processors)
   : dans le résumé du menu, visible sur toutes les pages, et sur l'entrée
   qui y mène. */
.pastille {
  display: inline-block; min-width: 20px; padding: 1px 7px; border-radius: 999px;
  background: var(--accent); color: var(--sur-accent);
  font-size: .78rem; font-weight: 700; line-height: 1.45; text-align: center;
}

/* -- Retouches propres à certaines pages --------------------------------- */

/* La page des gestionnaires réutilise la grille des post-it, mais les
   gestionnaires en place n'attendent aucune décision : du papier ordinaire,
   droit. Seules les invitations en attente restent des post-it. */
.propositions.personnes .proposition {
  background: var(--carte); transform: none; box-shadow: 0 1px 0 var(--trait);
}
.propositions.personnes button[type="submit"].bouton-secondaire { border-color: var(--trait); }
.propositions > .avertissement, .propositions > .vide { grid-column: 1 / -1; }

.cadeau .manuscrit.succes { color: var(--succes); }

/* Page d'une liste : le lien de partage et les gestionnaires, côte à côte
   dès qu'il y a la place. */
.outils-liste { display: grid; gap: 0 32px; }
@media (min-width: 900px) { .outils-liste { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
.outils-liste h2 { margin-top: 20px; margin-bottom: 8px; }
.outils-liste .detail + .detail { margin-top: 6px; }
.outils-liste .partage-champ { margin-top: 10px; }
.prix-texte { color: var(--texte); }

/* Le pied d'une étiquette est souvent un <p> : sa marge basse de
   navigateur ajoutait un vide sous le bouton. Et sur une seule colonne,
   la hauteur minimale ne sert plus à aligner des voisines — elle ne fait
   que creuser des trous : réservée aux grilles à plusieurs colonnes. */
.liste .pied, .cadeau .pied { margin-bottom: 0; }
@media (max-width: 639px) {
  .liste, .cadeau { min-height: 0; }
  .etiquette-nouvelle { min-height: 110px; }
}

/* -- Déjà acheté (24/09, revu le 25/09) ----------------------------------- */

/* « Disponible à la maison », en vert, à la place de « Disponible » (25/09,
   formulation d'Arnaud ; « Disponible ET déjà acheté ! » la veille, la
   seconde moitié à la main) : c'est ce qui dit à qui l'offre de ne pas
   l'acheter. Un filet vert sur le bord
   gauche de l'étiquette la signale de loin, dans la grille. L'ombre est
   intérieure : le clip-path du coin coupé rognerait une ombre portée. */
.a-la-maison { color: var(--succes); font-weight: 700; }
/* Sur la page pour offrir, le statut et la consigne forment un bloc à part,
   entre le texte d'introduction et le formulaire. */
.maison-offrir { margin: 14px 0 18px; padding-left: 12px; border-left: 4px solid var(--succes); }
.maison-offrir p { margin: 0 0 4px; }
.cadeau.deja-achete { box-shadow: inset 5px 0 0 var(--succes); }

/* -- Offert (24/09) ------------------------------------------------------- */

/* « Marquer offert » en toutes lettres, sur la page de modification : un
   bouton doré, ni l'accent (il n'y a rien de risqué) ni le secondaire (c'est
   l'aboutissement du cadeau). Sur les étiquettes, c'est une icône. Un lien
   sur la page de modification (il mène au formulaire « par qui »), un
   bouton sur ce formulaire : même habit. */
button[type="submit"].bouton-offert,
a.bouton-lien.bouton-offert { background: var(--ruban); color: #22201C; }

/* La section des offerts : détachée de la grille par un trait de
   découpe, un paquet emballé par cadeau. */
.section-offerts { margin-top: 48px; padding-top: 4px; border-top: 2px dashed var(--trou); }
.section-offerts h2 .compte {
  display: inline-block; margin-left: 4px; padding: 2px 10px; border-radius: 999px;
  font-family: Figtree, system-ui, sans-serif; font-size: .95rem; vertical-align: middle;
  color: var(--ruban-encre); background: color-mix(in srgb, var(--ruban) 22%, transparent);
}

/* L'étiquette d'un cadeau offert : papier teinté d'or, un ruban vertical
   sur le côté (le texte se décale pour le laisser passer), le liseré doré,
   et un cachet de la poste daté en travers du coin.

   En bloc plutôt qu'en flex, pour que le cachet FLOTTE : le titre et la
   ligne « Offert le … » s'enroulent autour de lui au lieu de passer
   dessous — un cachet en position absolue les recouvrait dès que le titre
   tenait sur une ligne (vu sur capture). */
.offerts-grille .cadeau.offert {
  display: block;
  min-height: 0;
  padding-left: 48px;
  border-bottom-color: var(--ruban);
  background:
    linear-gradient(90deg,
      transparent 18px,
      var(--ruban) 18px, var(--ruban) 30px,
      transparent 30px),
    color-mix(in srgb, var(--ruban) 10%, var(--carte));
}
/* Un mot long à côté du cachet (« déguisement ») sautait sous lui et
   laissait un trou dans le titre (vu sur capture). Un titre un cran plus
   petit — ce sont des archives, plus discrètes que ce qui reste à offrir —
   et la césure française en renfort, là où le navigateur la connaît. */
.offerts-grille .cadeau.offert h3 { font-size: 1.1rem; hyphens: auto; }
.statut-offert { color: var(--ruban-encre); font-weight: 600; margin-top: 4px; }
.cadeau.offert .pied-offert {
  clear: both; display: flex; flex-wrap: wrap; align-items: baseline;
  justify-content: space-between; gap: 4px 14px; padding-top: 12px;
  font-size: .92rem; font-weight: 600;
}
.cadeau.offert .pied-offert form { margin: 0; }

.cachet {
  float: right; margin: -16px -6px 6px 10px; transform: rotate(-14deg);
  width: 70px; height: 70px; border-radius: 50%;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  color: var(--ruban-encre);
  border: 3px solid currentColor;
  box-shadow: inset 0 0 0 3px color-mix(in srgb, var(--carte) 85%, transparent),
              inset 0 0 0 5px currentColor;
  background: color-mix(in srgb, var(--carte) 70%, transparent);
  pointer-events: none;
}
.cachet-mot { font-size: .74rem; font-weight: 700; letter-spacing: .1em; text-transform: uppercase; }
.cachet-date { font-size: .7rem; font-weight: 600; font-variant-numeric: tabular-nums; }

/* « Voir 10 de plus » : un bouton en creux, et où l'on en est. */
.plus-offerts { display: flex; flex-wrap: wrap; align-items: center; gap: 8px 14px; margin: 24px 0 0; }
a.bouton-lien.bouton-plus {
  background: transparent; color: var(--texte); border: 1px solid var(--trait);
}
a.bouton-lien.bouton-plus[aria-busy="true"] { opacity: .6; pointer-events: none; }

/* -- La page de modification : le statut (24/09) ------------------------- */

/* Sous le formulaire des informations, une fiche de plus : où en est le
   cadeau, et les gestes qui le font bouger. */
.statut-cadeau {
  margin-top: 28px; padding: 18px 22px 20px; border-radius: 6px;
  background: var(--carte); box-shadow: 0 1px 0 var(--trait);
}
.statut-cadeau h2 { margin: 0 0 8px; }
.statut-actuel { margin: 0 0 4px; font-size: 1.15rem; font-weight: 700; }
.statut-actuel.statut-offert { color: var(--ruban-encre); }
.actions-statut { display: flex; flex-wrap: wrap; align-items: center; gap: 10px; margin: 14px 0 8px; }
.actions-statut form, .actions-statut p { margin: 0; }

/* -- Les icônes d'action d'un cadeau (24/09) ------------------------------ */

/* Œil, cadeau, stylo : en ligne sous l'étiquette, toutes du même rond
   cerné (choix d'Arnaud : ni liseré de couleur, ni fond doré pour
   offrir). 42px : une cible confortable au
   doigt. Le nom de chaque geste est dans aria-label et title. Le sélecteur
   des boutons reprend le type, comme .bouton-secondaire : sinon
   `button[type="submit"]` (0,1,1) imposerait son fond plein. */
.cadeau .icones { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; margin-top: 12px; }
.cadeau .icones form { margin: 0; }
.cadeau .pied-offert .icones { margin-top: 0; }
a.icone, button[type="submit"].icone {
  display: inline-flex; align-items: center; justify-content: center;
  width: 42px; height: 42px; min-height: 0; padding: 0;
  border: 1px solid var(--trait); border-radius: 999px;
  background: transparent; color: var(--accent);
  cursor: pointer; text-decoration: none;
}
a.icone:hover, button[type="submit"].icone:hover {
  background: color-mix(in srgb, var(--accent) 10%, transparent); filter: none;
}
a.icone:focus-visible, button[type="submit"].icone:focus-visible {
  outline: 2px solid var(--accent); outline-offset: 2px;
}
.icone-svg {
  width: 20px; height: 20px; fill: none; stroke: currentColor;
  stroke-width: 2; stroke-linecap: round; stroke-linejoin: round;
}

/* Le nom du cadeau et celui de la boutique, quand ils mènent au site
   marchand : l'encre du texte, un souligné en pointillés qui annonce le
   lien sans crier, plein au survol. */
.cadeau a.vers-marchand {
  color: inherit; text-decoration: underline dotted; text-decoration-thickness: 1px;
  text-underline-offset: 3px;
}
.cadeau a.vers-marchand:hover { text-decoration-style: solid; }

/* -- La catégorie d'un cadeau (25/09) ------------------------------------- */

/* Sur l'étiquette : une grande icône au trait, en filigrane dans le fond,
   côté droit, centrée en hauteur (revu le 25/09 à la demande d'Arnaud :
   d'abord petite, en haut à droite). `z-index: -1` la glisse SOUS le texte sans passer sous
   le papier : le clip-path de l'étiquette crée un contexte d'empilement,
   dont le fond se peint toujours en premier. Ni clic ni survol. */
.cadeau .categorie {
  position: absolute; z-index: -1; top: 50%; right: 12px; transform: translateY(-50%);
  display: inline-flex; color: var(--texte); opacity: .09;
  pointer-events: none;
}
.cadeau .categorie .icone-svg { width: 104px; height: 104px; stroke-width: 1.5; }
/* Sur une étiquette offerte, plus basse, un filigrane un peu plus petit,
   centré lui aussi. */
.offerts-grille .cadeau.offert .categorie .icone-svg { width: 84px; height: 84px; }

/* Le mot de la catégorie devant le nom du cadeau (« BD », « Lego »,
   « JdS »…) : plus petit, à l'encre kraft, comme une mention ajoutée. */
.prefixe-categorie {
  font-size: .72em; font-weight: 700; letter-spacing: .04em; color: var(--kraft);
  vertical-align: .08em; margin-right: .15em;
}

/* Dans les formulaires : cinq boutons radio habillés en pastilles, l'icône
   dans un carré arrondi et son nom en dessous. Le rond du bouton radio est
   masqué mais reste là, pour le clavier et les lecteurs d'écran. Les
   sélecteurs reprennent `.formulaire` : `.formulaire label` et
   `.formulaire input` imposeraient sinon leur bloc et leur pleine largeur. */
.formulaire .choix-categorie { border: 0; padding: 0; margin: 0 0 16px; min-width: 0; }
.formulaire .choix-categorie legend {
  padding: 0; margin-bottom: 6px; font-size: .9rem; font-weight: 600; color: var(--discret);
}
/* Cinq colonnes, toujours sur une seule ligne (25/09 : en flex, le
   cinquième passait seul dessous sur mobile) ; chaque colonne rétrécit
   jusqu'au carré de l'icône, jamais au-delà de 72px. */
.formulaire .categories {
  display: grid; grid-template-columns: repeat(5, minmax(0, 72px)); gap: 6px;
}
.formulaire .categorie-choix {
  position: relative; display: flex; flex-direction: column; align-items: center; gap: 4px;
  min-width: 0; margin: 0; cursor: pointer;
}
.formulaire .categorie-choix input[type="radio"] {
  position: absolute; top: 0; left: 0; width: 1px; height: 1px; min-height: 0;
  margin: 0; padding: 0; opacity: 0;
}
.formulaire .categorie-case {
  display: flex; align-items: center; justify-content: center;
  width: 46px; height: 46px; border-radius: 10px;
  border: 1px solid var(--trait); background: var(--fond); color: var(--discret);
  transition: background-color .15s, color .15s, border-color .15s;
}
.formulaire .categorie-choix:hover .categorie-case { color: var(--texte); }
.formulaire .categorie-choix input:checked + .categorie-case {
  color: var(--accent); border-color: var(--accent);
  background: color-mix(in srgb, var(--accent) 10%, var(--carte));
  box-shadow: inset 0 0 0 1px var(--accent);
}
.formulaire .categorie-choix input:focus-visible + .categorie-case {
  outline: 2px solid var(--accent); outline-offset: 2px;
}
.formulaire .categorie-nom {
  font-size: .8rem; font-weight: 400; line-height: 1.2; text-align: center; color: var(--discret);
}
.formulaire .categorie-choix input:checked ~ .categorie-nom { color: var(--texte); font-weight: 600; }

/* -- La page de présentation (25/09) ------------------------------------- */

/* Pour qui arrive sans être connecté, sur / et sur /connexion : l'accroche
   et l'explication à gauche, la connexion dans la colonne de droite, qui
   reste à l'écran pendant qu'on lit. En dessous de 900px tout s'empile,
   la connexion juste après l'accroche (l'ordre du HTML) : qui revient pour
   se connecter n'a pas à traverser toute l'explication. */
.presentation { display: grid; gap: 28px; }
@media (min-width: 900px) {
  .presentation {
    grid-template-columns: minmax(0, 1fr) 360px;
    grid-template-areas: "accroche connexion" "suite connexion";
    column-gap: 56px; row-gap: 0; align-items: start;
  }
  .presentation-accroche { grid-area: accroche; }
  .presentation-suite { grid-area: suite; }
  .presentation-connexion { grid-area: connexion; position: sticky; top: 24px; }
}
.presentation h1 { max-width: 16em; }
.presentation-chapeau { margin: 0; font-size: 1.15rem; max-width: 36em; color: var(--discret); }
.presentation-connexion h2 { margin: 0 0 16px; }
.presentation-connexion .formulaire { box-shadow: 0 1px 0 var(--trait), 0 6px 20px var(--ombre); }
.presentation-connexion button[type="submit"] { width: 100%; }
.presentation-inscription { margin-top: 12px; }

/* Les trois étapes : trois petites fiches, le numéro écrit à la main. */
.presentation-etapes {
  display: grid; gap: 14px; margin: 0; padding: 0; list-style: none;
}
@media (min-width: 640px) { .presentation-etapes { grid-template-columns: repeat(3, minmax(0, 1fr)); } }
.presentation-etapes li {
  padding: 14px 16px 16px; border-radius: 6px;
  background: var(--carte); box-shadow: 0 1px 0 var(--trait);
}
.presentation-etapes .manuscrit { display: block; font-size: 2rem; line-height: 1; color: var(--corail); }
.presentation-etapes h3 { margin: 6px 0 6px; font-size: 1.05rem; line-height: 1.25; }
.presentation-etapes p { margin: 0; font-size: .94rem; color: var(--discret); }

/* L'esprit du site : une liste de principes, chacun ouvert par son idée en
   gras, un filet vert à gauche comme une marge annotée. */
.presentation-principes { margin: 0; padding: 0; list-style: none; max-width: 42em; }
.presentation-principes li {
  margin: 0 0 14px; padding-left: 14px; border-left: 3px solid var(--succes);
}
.presentation-principes strong { display: block; }

/* Qui est connecté trouve, à la place de la connexion, son nom et les
   entrées du menu du compte : « Mes listes » en bouton plein (c'est là
   qu'il allait), les deux autres pages en lignes comme dans le volet de
   l'en-tête, la déconnexion détachée par un trait. */
.presentation-compte .manuscrit { margin: 0 0 4px; }
.presentation-compte h2 { display: flex; align-items: center; gap: 10px; }
.presentation-compte-liens { display: flex; flex-direction: column; gap: 2px; }
.presentation-compte-liens a.bouton-lien { justify-content: center; margin-bottom: 8px; }
.presentation-compte-liens a:not(.bouton-lien),
.presentation-compte-liens button[type="submit"].lien {
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  width: 100%; min-height: 40px; padding: 9px 12px; border-radius: 6px;
  font-size: .95rem; text-align: left; text-decoration: none; color: var(--texte);
}
.presentation-compte-liens a:not(.bouton-lien):hover,
.presentation-compte-liens button[type="submit"].lien:hover {
  background: color-mix(in srgb, var(--accent) 10%, transparent); filter: none;
}
.presentation-compte-liens form {
  margin: 4px 0 0; padding-top: 4px; border-top: 1px solid var(--trait);
}

/* -- Les réglages d'une liste, repliés (25/09) --------------------------- */

/* Sur la page d'une liste, modifier, supprimer, partager et les
   gestionnaires se replient derrière un engrenage, à droite du titre.
   Le <summary> est posé en absolu à hauteur du titre (qui lui laisse la
   place) ; le volet se déplie dessous, dans le flux. Même rond que les
   gestes d'un cadeau (a.icone), en plein quand le volet est ouvert. */
.entete-liste { position: relative; }
.entete-liste > h1 { padding-right: 56px; }
.reglages-liste > summary {
  position: absolute; top: 2px; right: 0;
  display: inline-flex; align-items: center; justify-content: center;
  width: 44px; height: 44px; border: 1px solid var(--trait); border-radius: 999px;
  color: var(--accent); cursor: pointer; list-style: none;
}
@media (min-width: 720px) { .reglages-liste > summary { top: 8px; } }
.reglages-liste > summary::-webkit-details-marker { display: none; }
.reglages-liste > summary:hover { background: color-mix(in srgb, var(--accent) 10%, transparent); }
.reglages-liste > summary:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
.reglages-liste[open] > summary { background: var(--accent); border-color: var(--accent); color: var(--sur-accent); }
.reglages-liste > summary .icone-svg { transition: transform .2s; }
.reglages-liste[open] > summary .icone-svg { transform: rotate(60deg); }
.reglages-volet {
  margin: 0 0 16px; padding: 16px 20px 20px; border-radius: 6px;
  background: var(--carte); box-shadow: 0 1px 0 var(--trait);
}
.reglages-volet .boutons-entete { margin-bottom: 0; }
.reglages-volet .outils-liste h2 { margin-top: 18px; }
.reglages-volet .outils-liste .detail + .detail { margin-top: 12px; }
