/* Sombre par défaut : on regarde un terminal, et l'œil passe des heures dessus. */
:root {
  --fond: #14161a;
  --fond-carte: #1c1f26;
  --fond-creux: #0e1013;
  --bord: #2c313b;
  --texte: #e4e7ec;
  --attenue: #9aa3b2;
  --accent: #6ea8fe;
  --vert: #57d38c;
  --rouge: #f2777a;
  --ambre: #e8c26b;
  --rayon: 8px;
  --mono: ui-monospace, "JetBrains Mono", "Cascadia Code", Menlo, Consolas, monospace;
}
* { box-sizing: border-box; }
body {
  margin: 0;
  background: var(--fond);
  color: var(--texte);
  font: 15px/1.55 system-ui, -apple-system, "Segoe UI", Roboto, sans-serif;
}
a { color: var(--accent); }
header {
  display: flex; align-items: baseline; gap: 1rem;
  padding: .85rem 1.25rem; border-bottom: 1px solid var(--bord);
  background: var(--fond-carte);
}
header h1 { font-size: 1.05rem; margin: 0; letter-spacing: .02em; }
header h1 small { color: var(--attenue); font-weight: 400; margin-left: .5rem; }
header .qui { margin-left: auto; color: var(--attenue); font-size: .85rem; }
main { max-width: 1400px; margin: 0 auto; padding: 1.25rem; }

.grille { display: grid; gap: 1rem; grid-template-columns: repeat(auto-fill, minmax(300px, 1fr)); }
.carte {
  background: var(--fond-carte); border: 1px solid var(--bord);
  border-radius: var(--rayon); padding: 1rem; display: flex; flex-direction: column; gap: .5rem;
}
.carte h3 { margin: 0; font-size: 1rem; }
.carte p { margin: 0; color: var(--attenue); font-size: .9rem; }
/* Le bouton descend au pied de la carte, et lui seul prend la place qu'une voisine plus
   haute laisse dans la rangée. Un `flex: 1` sur les paragraphes la répartissait entre eux —
   dont celui des étiquettes, qui étirait alors ses pastilles en bulles hautes : vu sur le
   catalogue le 14 septembre 2026, une carte sur deux selon la hauteur de sa voisine. */
.carte > button.primaire { margin-top: auto; }
.meta {
  display: flex; flex-wrap: wrap; gap: .35rem .5rem; align-items: center;
  font-size: .78rem; color: var(--attenue);
}
/* Une pastille ou « 15 min » ne se coupent pas en deux : c'est la ligne qui passe à la
   suivante, pas le mot. */
.meta > * { white-space: nowrap; }
.pastille {
  border: 1px solid var(--bord); border-radius: 999px; padding: .1rem .55rem;
  text-transform: uppercase; letter-spacing: .04em; font-size: .7rem;
}
.pastille.facile { color: var(--vert); border-color: color-mix(in srgb, var(--vert) 40%, transparent); }
.pastille.moyen { color: var(--ambre); border-color: color-mix(in srgb, var(--ambre) 40%, transparent); }
.pastille.difficile, .pastille.expert { color: var(--rouge); border-color: color-mix(in srgb, var(--rouge) 40%, transparent); }

/* Le thème, à côté de la difficulté. Volontairement plus discret qu'elle : la difficulté
   se lit d'abord, le thème répond à « lequel des huit ». */
.pastille.theme { text-transform: none; letter-spacing: 0; color: var(--attenue); }

/* La barre de filtres du catalogue. Elle tient sur une ligne tant qu'elle peut, et se
   replie plutôt que de déborder — huit thèmes plus quatre difficultés ne tiennent pas sur
   un écran étroit. */
.filtres {
  display: flex; flex-wrap: wrap; gap: .75rem 1.25rem; align-items: center;
  margin: 0 0 .9rem;
}
.filtres .choix { display: flex; flex-wrap: wrap; gap: .35rem; }
.filtres .tri { font-size: .82rem; color: var(--attenue); display: flex; gap: .4rem; align-items: center; }
button.etiquette {
  background: var(--fond-creux); border: 1px solid var(--bord); color: var(--attenue);
  border-radius: 999px; padding: .2rem .7rem; font-size: .78rem;
}
button.etiquette:hover { color: var(--texte); }
button.etiquette .etat { font-size: .72rem; opacity: .75; }
button.etiquette.actif {
  color: var(--texte); border-color: color-mix(in srgb, var(--accent) 55%, transparent);
  background: color-mix(in srgb, var(--accent) 12%, var(--fond-creux));
}
.filtres .recherche { font-size: .82rem; color: var(--attenue); display: flex; gap: .4rem; align-items: center; }
.filtres .recherche input {
  font: inherit; background: var(--fond-creux); color: var(--texte);
  border: 1px solid var(--bord); border-radius: 6px; padding: .25rem .6rem; min-width: 15rem;
}
.filtres .recherche input:focus { outline: none; border-color: var(--accent); }

/* Dire qu'on filtre, et non laisser croire que le catalogue a rétréci. */
.filtre-actif { margin: 0 0 .8rem; }

/* Les étiquettes d'une carte : cliquables, mais elles ne doivent pas concurrencer le
   titre. Plus petites que la barre de filtres, et sans fond tant qu'on ne les survole
   pas — une carte de catalogue en porte jusqu'à cinq. */
.etiquettes { display: flex; flex-wrap: wrap; gap: .3rem; margin: 0; align-content: flex-start; align-items: center; }
button.etiquette.menue {
  background: transparent; padding: .05rem .45rem; font-size: .72rem;
  border-color: color-mix(in srgb, var(--bord) 70%, transparent);
}
button.etiquette.menue:hover { background: var(--fond-creux); border-color: var(--accent); }

/* Un scénario déjà réussi reste dans la liste, en retrait : le retirer ferait un
   catalogue qui rétrécit à mesure qu'on progresse, et on relit volontiers ce qu'on a
   fait. */
.pastille.reussi { color: var(--vert); border-color: color-mix(in srgb, var(--vert) 40%, transparent); }
.carte.faite h3 { color: var(--attenue); }

button {
  font: inherit; cursor: pointer; border-radius: 6px; padding: .45rem .9rem;
  border: 1px solid var(--bord); background: #262b34; color: var(--texte);
}
button:hover:not(:disabled) { border-color: var(--accent); }
button:disabled { opacity: .5; cursor: not-allowed; }
button.primaire { background: var(--accent); border-color: var(--accent); color: #0b1220; font-weight: 600; }
button.discret { background: transparent; }

/* L'atelier : énoncé à gauche, terminal à droite. Le terminal prend la place.

   Sur un écran large, l'atelier sort du gabarit de 1400 px que suit le reste du site : un
   catalogue de cartes n'a que faire de la largeur, un énoncé et un terminal côte à côte
   si. La colonne de l'énoncé suit la largeur — un tiers — sans descendre sous 26rem ni
   dépasser 48rem, où une ligne de texte cesse d'être lisible. Le plafond de 2400 px garde
   au terminal des lignes qu'on lit encore d'un regard sur un écran ultra-large. */
main:has(.atelier) { max-width: 2400px; }
.atelier {
  display: grid; gap: 1rem; align-items: start;
  grid-template-columns: minmax(20rem, clamp(26rem, 34%, 48rem)) minmax(0, 1fr);
}
@media (max-width: 900px) { .atelier { grid-template-columns: 1fr; } }
.panneau { background: var(--fond-carte); border: 1px solid var(--bord); border-radius: var(--rayon); }
.panneau > .entete {
  display: flex; align-items: center; gap: .75rem; flex-wrap: wrap;
  padding: .7rem 1rem; border-bottom: 1px solid var(--bord);
}
.panneau > .corps { padding: 1rem; }
.enonce { max-height: 46vh; overflow: auto; }
.enonce h2 { font-size: 1.05rem; margin: 1.1rem 0 .4rem; }
/* Une commande qu'on ne voit pas en entier est une commande qu'on recopie fausse : les blocs
   passent à la ligne plutôt que de défiler sous une barre qu'on ne remarque pas. Le retour
   est visuel seulement — un copier-coller rend la ligne d'origine. */
.enonce pre {
  background: var(--fond-creux); border: 1px solid var(--bord); border-radius: 6px;
  padding: .7rem .85rem; overflow-x: auto; font: 13px/1.5 var(--mono);
  white-space: pre-wrap; overflow-wrap: anywhere;
}
.enonce code { font: 13px/1.4 var(--mono); background: var(--fond-creux); padding: .1rem .3rem; border-radius: 4px; }
.enonce blockquote { margin: .6rem 0; padding-left: .9rem; border-left: 3px solid var(--bord); color: var(--attenue); }

#terminal { height: 62vh; min-height: 320px; padding: .5rem; background: #000; border-radius: 0 0 var(--rayon) var(--rayon); }
.chrono { font: 600 1rem/1 var(--mono); }
.chrono.urgent { color: var(--rouge); }
.etat { font-size: .85rem; color: var(--attenue); }

.verdict { margin-top: .85rem; padding: .75rem .9rem; border-radius: 6px; border: 1px solid var(--bord); }
.verdict.reussi { border-color: var(--vert); color: var(--vert); }
.verdict.echoue { border-color: var(--ambre); }
.verdict.erreur { border-color: var(--rouge); color: var(--rouge); }
.verdict ul { margin: .5rem 0 0; padding-left: 1.1rem; color: var(--texte); }
.indices li { margin-bottom: .35rem; }
.vide { color: var(--attenue); padding: 2rem 0; text-align: center; }

/* ------------------------------------------------------------------ accueil */
.titre-section {
  font-size: .8rem; text-transform: uppercase; letter-spacing: .08em;
  color: var(--attenue); font-weight: 600; margin: 1.75rem 0 .75rem;
}
.titre-section:first-child { margin-top: .25rem; }
.carte.eteinte { opacity: .62; }
.bandeau {
  background: color-mix(in srgb, var(--accent) 12%, var(--fond-carte));
  border: 1px solid color-mix(in srgb, var(--accent) 35%, var(--bord));
  border-radius: var(--rayon); padding: .9rem 1rem; margin-bottom: .5rem;
}
.actions { display: flex; gap: .5rem; flex-wrap: wrap; margin-top: .6rem; }
.fil { margin-bottom: .75rem; }

form { display: flex; flex-direction: column; gap: .5rem; margin-top: .75rem; }
input {
  padding: .5rem .6rem; border-radius: 6px; border: 1px solid var(--bord);
  background: var(--fond-creux); color: var(--texte); font: inherit;
}
input:focus-visible, button:focus-visible { outline: 2px solid var(--accent); outline-offset: 1px; }
#err { color: var(--rouge); min-height: 1.2em; }

/* ----------------------------------------------------------------- parcours */
.pastille.examen { color: var(--rouge); border-color: color-mix(in srgb, var(--rouge) 45%, transparent); }
.jauge {
  height: 6px; border-radius: 999px; background: var(--fond-creux);
  border: 1px solid var(--bord); overflow: hidden; margin: .75rem 0 .4rem;
}
.jauge > div { height: 100%; background: var(--vert); transition: width .4s ease; }

.etapes { list-style: none; margin: 1rem 0 0; padding: 0; display: flex; flex-direction: column; gap: .6rem; }
.etape {
  display: flex; gap: .85rem; padding: .85rem 1rem;
  border: 1px solid var(--bord); border-radius: var(--rayon); background: var(--fond-creux);
}
.etape > div { flex: 1; }
.etape strong { display: block; }
.etape .meta { margin: .4rem 0 .55rem; }
.etape .marque {
  flex: 0 0 1.8rem; height: 1.8rem; border-radius: 50%; display: grid; place-items: center;
  border: 1px solid var(--bord); font: 600 .85rem/1 var(--mono); color: var(--attenue);
}
.etape.reussie { border-color: color-mix(in srgb, var(--vert) 45%, transparent); }
.etape.reussie .marque { color: var(--vert); border-color: var(--vert); }
.etape.verrouillee { opacity: .6; }
.verrou { margin: 0; font-style: italic; }

/* ------------------------------------------- tableaux et formulaires, partagés
   Ils servaient d'abord à l'administration ; le classement, la progression et le profil
   les emploient à l'identique. Les garder en double aurait fini par les faire diverger. */
table { width: 100%; border-collapse: collapse; font-size: .9rem; }
th, td { text-align: left; padding: .45rem .6rem; border-bottom: 1px solid var(--bord); }
th { color: var(--attenue); font-weight: 600; font-size: .78rem; text-transform: uppercase; letter-spacing: .04em; }
td.fin, th.fin { text-align: right; }
tbody tr:hover { background: var(--fond-creux); }
tr.absent td { color: var(--attenue); }
code { font: 12px/1.4 var(--mono); }

.formulaire { display: grid; grid-template-columns: repeat(auto-fit, minmax(15rem, 1fr)); gap: .75rem 1rem; }
.formulaire label { display: flex; flex-direction: column; gap: .25rem; font-size: .85rem; color: var(--attenue); }
.formulaire .large { grid-column: 1 / -1; }
.formulaire input, .formulaire select { color: var(--texte); }
select {
  padding: .45rem .5rem; border-radius: 6px; border: 1px solid var(--bord);
  background: var(--fond-creux); color: var(--texte); font: inherit;
}

/* --------------------------------------------------------------- communauté */
header .qui { display: flex; gap: .9rem; align-items: baseline; }
button.lien {
  background: none; border: none; padding: 0; color: var(--accent);
  font: inherit; text-decoration: underline; text-underline-offset: 2px; cursor: pointer;
}
button.lien:hover { color: var(--texte); }

label.case { flex-direction: row; align-items: flex-start; gap: .55rem; }
label.case input { width: auto; margin-top: .2rem; flex: 0 0 auto; }
label.case span { color: var(--attenue); font-size: .85rem; line-height: 1.45; }

/* `.carte .repere` et non `.repere` seul : `.carte p` l'emportait en spécificité, et le repère
   s'affichait à la taille du résumé qu'il est censé suivre discrètement. */
.repere, .carte .repere { margin: 0; font-size: .8rem; }
textarea {
  padding: .5rem .6rem; border-radius: 6px; border: 1px solid var(--bord);
  background: var(--fond-creux); color: var(--texte); font: 13px/1.5 var(--mono);
  resize: vertical;
}
tr.moi td { background: color-mix(in srgb, var(--accent) 14%, transparent); font-weight: 600; }
tr.peu-sur td { color: var(--attenue); }
