/*
 * Surcouche « noir moderne » pour le thème reveal.js « black ».
 *
 * À charger en plus du thème black (et non à sa place) :
 *
 *   [reveal_hugo]
 *   theme = "black"
 *   custom_css = "css/noir-moderne.css"
 *
 * Règle d'or : rien ici ne modifie la police, sa taille, l'interlignage,
 * les marges ou les espacements du texte. Les retours à la ligne restent
 * donc strictement identiques à ceux du thème black. Tous les effets
 * (lueurs, ombres, dégradés, animations) sont purement visuels.
 */

:root {
  --nm-accent: #00A2FF;
  --nm-accent-2: #56C1FF;
  --nm-accent-3: #7B61FF;
  --nm-fond-centre: #1c1f26;
  --nm-fond-bord: #0d0e12;
  --nm-filet: rgba(255, 255, 255, 0.14);
  --nm-ease: cubic-bezier(0.22, 1, 0.36, 1);
}

/*********************************************
 * FOND
 * Toujours très sombre (luminance moyenne proche du #191919 d'origine),
 * avec un léger vignettage pour donner de la profondeur.
 *********************************************/
body {
  background-color: #15171c;
  background-image: radial-gradient(ellipse 120% 90% at 50% 40%,
                    var(--nm-fond-centre) 0%,
                    #15171c 55%,
                    var(--nm-fond-bord) 100%);
  background-attachment: fixed;
}

::selection {
  color: #fff;
  background: rgba(0, 162, 255, 0.45);
}

/*********************************************
 * TITRES
 * Même police, même taille, mêmes majuscules : on ajoute seulement
 * une lueur discrète et un filet d'accent animé sous le titre.
 *********************************************/
.reveal h1,
.reveal h2,
.reveal h3,
.reveal h4 {
  text-shadow: 0 0 28px rgba(0, 162, 255, 0.28);
}

/* Filet sous les titres « libres » (pas ceux déjà encadrés à la main).
   Il est positionné en absolu dans la marge sous le titre :
   il ne décale rien verticalement. */
.reveal .slides section > h1:not([style]),
.reveal .slides section > h2:not([style]),
.reveal .slides section > h3:not([style]) {
  position: relative;
}

.reveal .slides section > h1:not([style])::after,
.reveal .slides section > h2:not([style])::after,
.reveal .slides section > h3:not([style])::after {
  content: "";
  position: absolute;
  left: 50%;
  bottom: -12px;
  width: 3.2em;
  height: 4px;
  margin-left: -1.6em;
  border-radius: 4px;
  background: linear-gradient(90deg, var(--nm-accent-3), var(--nm-accent), var(--nm-accent-2));
  box-shadow: 0 0 14px rgba(0, 162, 255, 0.55);
  transform-origin: center;
}

.reveal .slides section.present > h1:not([style])::after,
.reveal .slides section.present > h2:not([style])::after,
.reveal .slides section.present > h3:not([style])::after {
  animation: nm-filet 0.9s var(--nm-ease) 0.15s both;
}

/* Les h4 (« Expérience : », « Exemple : »…) : simple soulignement fin. */
.reveal .slides section > h4:not([style]) {
  text-decoration: underline;
  text-decoration-color: rgba(0, 162, 255, 0.7);
  text-decoration-thickness: 3px;
  text-underline-offset: 0.25em;
}

@keyframes nm-filet {
  from { transform: scaleX(0); opacity: 0; }
  to   { transform: scaleX(1); opacity: 1; }
}

/*********************************************
 * PUCES
 * La puce native est conservée (donc elle occupe exactement la même
 * place qu'avant) mais rendue invisible ; une puce dessinée est
 * superposée à son emplacement.
 *********************************************/
.reveal ul > li {
  position: relative;
}

.reveal ul > li::marker {
  color: transparent;
}

.reveal ul > li::before {
  content: "";
  position: absolute;
  /* Emplacement de la puce native en « list-style-position: inside »
     (cas de tous les cours de seconde, avec le retrait suspendu
     text-indent: -1em / padding-left: 1em). */
  left: 0.04em;
  top: 0.5em;
  width: 0.3em;
  height: 0.3em;
  border-radius: 0.09em;
  transform: rotate(45deg);
  background: linear-gradient(135deg, var(--nm-accent-2), var(--nm-accent));
  box-shadow: 0 0 10px rgba(0, 162, 255, 0.7);
  pointer-events: none;
}

/* Sous-listes : losange creux, plus discret. */
.reveal ul ul > li::before {
  background: transparent;
  border: 2px solid var(--nm-accent-2);
  box-shadow: none;
  box-sizing: border-box;
}

/* Listes numérotées : numéros simplement colorés. */
.reveal ol > li::marker {
  color: var(--nm-accent);
  font-weight: 600;
}

/*********************************************
 * MOTS IMPORTANTS (.imp et gras coloré)
 * Lueur dans la couleur du mot (qu'elle vienne de .imp ou d'un style
 * en ligne), sans changer ni la graisse ni la taille.
 * Même traitement pour le gras coloré : <b>/<strong> ou <span> en
 * font-weight:bold portant une couleur en ligne (sauf le blanc).
 *********************************************/
.reveal .imp,
.reveal :is(b, strong, span[style*="bold" i])[style*="color" i]:not([style*="white" i], [style*="#fff;" i], [style$="#fff" i], [style*="#ffffff" i]) {
  text-shadow: 0 0 16px rgba(0, 162, 255, 0.35);
  text-shadow: 0 0 16px color-mix(in srgb, currentColor 45%, transparent);
}

/* Petit « flash » lumineux quand un mot important apparaît. */
.reveal .slides section .fragment.imp.visible.current-fragment,
.reveal .slides section .fragment.visible.current-fragment .imp,
.reveal .slides section :is(b, strong, span[style*="bold" i]).fragment.visible.current-fragment[style*="color" i]:not([style*="white" i], [style*="#fff;" i], [style$="#fff" i], [style*="#ffffff" i]),
.reveal .slides section .fragment.visible.current-fragment :is(b, strong, span[style*="bold" i])[style*="color" i]:not([style*="white" i], [style*="#fff;" i], [style$="#fff" i], [style*="#ffffff" i]) {
  animation: nm-eclat 1.1s var(--nm-ease);
}

@keyframes nm-eclat {
  0%   { text-shadow: 0 0 0 transparent; }
  35%  { text-shadow: 0 0 22px currentColor, 0 0 6px currentColor; }
  100% { text-shadow: 0 0 16px color-mix(in srgb, currentColor 45%, transparent); }
}

/*********************************************
 * FRAGMENTS
 * Mêmes déclencheurs qu'avant, mais transitions plus douces
 * (courbe « ease-out » marquée, léger flou à l'apparition).
 *********************************************/
.reveal .slides section .fragment {
  transition: opacity 0.55s var(--nm-ease),
              transform 0.55s var(--nm-ease),
              filter 0.55s var(--nm-ease),
              color 0.3s ease,
              text-shadow 0.4s ease;
}

.reveal .slides section .fragment.fade-up {
  transform: translate(0, 24px);
}

.reveal .slides section .fragment.fade-up:not(.visible) {
  filter: blur(3px);
}

.reveal .slides section .fragment.fade-up.visible {
  transform: none;
  filter: none;
}

/*********************************************
 * ENCADRÉS
 * Les encadrés déjà présents dans les cours (div à fond coloré,
 * div ou h3 bordés) gardent leurs dimensions exactes : on ajoute
 * coins arrondis, reflet et ombre portée.
 *********************************************/
.reveal .slides div[style*="background-color"] {
  border-radius: 14px;
  background-image: linear-gradient(160deg,
                    rgba(255, 255, 255, 0.16) 0%,
                    rgba(255, 255, 255, 0) 45%,
                    rgba(0, 0, 0, 0.18) 100%);
  box-shadow: 0 12px 32px rgba(0, 0, 0, 0.55),
              inset 0 1px 0 rgba(255, 255, 255, 0.25);
}

.reveal .slides div[style*="border:"],
.reveal .slides div[style*="border :"],
.reveal .slides h3[style*="border"] {
  border-radius: 14px;
  box-shadow: 0 0 24px rgba(255, 255, 255, 0.08),
              inset 0 0 24px rgba(255, 255, 255, 0.04);
}

/* Encadrés « prêts à l'emploi » pour de futurs cours.
   Le padding reproduit celui des encadrés existants
   (15px 10px 20px 10px) : mêmes coupures de lignes. */
.reveal .encadre,
.reveal .encadre-def,
.reveal .encadre-attention,
.reveal .encadre-rq {
  display: inline-block;
  padding: 15px 10px 20px 10px;
  border-radius: 14px;
  color: #fff;
  box-shadow: 0 12px 32px rgba(0, 0, 0, 0.55),
              inset 0 1px 0 rgba(255, 255, 255, 0.2);
}

.reveal .encadre {
  background: linear-gradient(160deg, #1d93d6, #0063a0);
}

.reveal .encadre-def {
  background: linear-gradient(160deg, #ff7a66, #d9402b);
}

.reveal .encadre-attention {
  background: linear-gradient(160deg, #ff9a2e, #d45f00);
}

.reveal .encadre-rq {
  background: rgba(255, 255, 255, 0.06);
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.18);
  color: inherit;
}

/*********************************************
 * CITATIONS
 * Même boîte qu'avant : la barre d'accent est une ombre interne,
 * elle ne prend donc aucune place.
 *********************************************/
.reveal blockquote {
  background: rgba(255, 255, 255, 0.05);
  border-radius: 12px;
  box-shadow: inset 4px 0 0 var(--nm-accent),
              0 10px 30px rgba(0, 0, 0, 0.45);
}

/*********************************************
 * TABLEAUX
 * Mêmes marges internes ; seuls les filets et l'en-tête changent.
 *********************************************/
.reveal table th,
.reveal table td {
  border-bottom-color: var(--nm-filet);
}

.reveal table thead th {
  background: rgba(0, 162, 255, 0.12);
  border-bottom: 1px solid var(--nm-accent);
}

/*********************************************
 * LIENS
 *********************************************/
.reveal a {
  color: var(--nm-accent-2);
  text-decoration: none;
  background-image: linear-gradient(currentColor, currentColor);
  background-size: 0% 2px;
  background-position: 0 100%;
  background-repeat: no-repeat;
  transition: background-size 0.3s var(--nm-ease), color 0.15s ease;
}

.reveal a:hover {
  color: #9bdcff;
  background-size: 100% 2px;
  text-shadow: none;
}

/* Les liens placés dans un mot important prennent sa couleur. */
.reveal .imp a {
  color: inherit;
}

/*********************************************
 * CODE (au cas où)
 *********************************************/
.reveal pre {
  border-radius: 12px;
  box-shadow: 0 12px 32px rgba(0, 0, 0, 0.55);
}

.reveal pre code {
  border-radius: 12px;
}

/*********************************************
 * QUESTIONS
 * /js/noir-moderne.js repère les moments de participation (phrases en
 * « ? », consignes à l'infinitif…) et dessine derrière chaque ligne un
 * cadre .nm-q en position absolue : aucune balise autour du texte,
 * aucun mot déplacé. Pour exclure un passage : class="pas-question" ;
 * pour forcer un bloc : class="question".
 *********************************************/
.reveal .nm-q-hote {
  isolation: isolate;        /* le cadre passe derrière le texte */
}

.reveal .nm-q {
  position: absolute;
  z-index: -1;
  pointer-events: none;
  border-radius: 0.32em;
  background: rgba(123, 97, 255, 0.3);
  box-shadow: inset 0 -3px 0 rgba(165, 148, 255, 0.95);
  transition: opacity 0.4s ease;
}

.reveal .nm-q.nm-q-cache {
  opacity: 0;
}

/*********************************************
 * CARTES DE PROPOSITIONS
 *********************************************/
/* Cartes de propositions :
     <ol class="vote">
     <li class="fragment">…</li>
     <li class="fragment juste">…</li>   (la bonne réponse)
     …
     </ol>
     <div class="fragment revele"></div>
   Chaque carte arrive à son tour avec un zoom ; le fragment « revele »
   placé après la liste illumine la bonne réponse et estompe les autres.
   Sans « revele » ni « juste », les cartes servent de simple pari. */
.reveal ol.vote {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 0.5em 0.7em;
  width: 92%;
  margin: 0.5em auto;
  padding: 0;
  list-style: none;
  counter-reset: vote;
  font-size: 0.75em;
  text-align: center;
}

.reveal ol.vote > li {
  counter-increment: vote;
  position: relative;
  /* Pas de flex : formules MathJax et texte restent dans le même flux.
     Centrage vertical par align-content (navigateurs récents ; sinon
     le texte est simplement en haut de la case). */
  display: block;
  align-content: center;
  box-sizing: border-box;
  width: auto;
  min-height: 2.4em;
  margin: 0;
  padding: 0.3em 1.2em 0.3em 2.3em;
  border-radius: 14px;
  background: rgba(255, 255, 255, 0.06);
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, 0.16);
  transition: opacity 0.5s ease, background 0.5s ease, box-shadow 0.5s ease;
}

.reveal ol.vote > li::before {
  content: counter(vote);
  position: absolute;
  left: 0.55em;
  top: 50%;
  width: 1.3em;
  height: 1.3em;
  margin-top: -0.65em;
  border-radius: 50%;
  line-height: 1.3em;
  text-align: center;
  font-weight: 700;
  color: #fff;
  background: linear-gradient(135deg, var(--nm-accent-2), var(--nm-accent));
  box-shadow: 0 0 10px rgba(0, 162, 255, 0.6);
}

/* Nombre impair de cartes : la dernière est centrée. */
.reveal ol.vote > li:last-child:nth-child(odd) {
  grid-column: 1 / -1;
  justify-self: center;
  width: calc(50% - 0.35em);
}

/* Arrivée des cartes : zoom avec un léger rebond. */
.reveal .slides section ol.vote > li.fragment {
  transform: scale(0.55);
  filter: none;
  transition: opacity 0.35s ease,
              transform 0.55s cubic-bezier(0.34, 1.56, 0.64, 1),
              background 0.5s ease,
              box-shadow 0.5s ease;
}

.reveal .slides section ol.vote > li.fragment.visible {
  transform: none;
}

/* Illumination de la bonne réponse. */
.reveal .slides section ol.vote:has(~ .revele.visible) > li.juste {
  background: rgba(97, 216, 54, 0.16);
  box-shadow: inset 0 0 0 2px #61D836, 0 0 26px rgba(97, 216, 54, 0.45);
}

.reveal .slides section ol.vote:has(~ .revele.visible) > li.juste::before {
  background: #61D836;
  box-shadow: 0 0 12px rgba(97, 216, 54, 0.8);
}

.reveal .slides section ol.vote:has(~ .revele.visible) > li:not(.juste) {
  opacity: 0.35;
}

/* Le déclencheur lui-même ne prend aucune place. */
.reveal .revele {
  height: 0;
  margin: 0;
}

/* Correction / réponse attendue. */
.reveal .corr {
  color: #61D836;
}

/*********************************************
 * INTERFACE : barre de progression, flèches, numéro de diapo
 *********************************************/
.reveal .progress {
  height: 4px;
  background: rgba(255, 255, 255, 0.06);
  color: var(--nm-accent);
}

.reveal .progress span {
  background: linear-gradient(90deg, var(--nm-accent-3), var(--nm-accent), var(--nm-accent-2));
  box-shadow: 0 0 12px rgba(0, 162, 255, 0.8);
  transition: width 0.8s var(--nm-ease);
}

.reveal .controls {
  color: var(--nm-accent);
}

.reveal .slide-number {
  background: rgba(255, 255, 255, 0.06);
  border-radius: 8px;
  color: rgba(255, 255, 255, 0.6);
}

/*********************************************
 * Accessibilité : on coupe les animations si l'ordinateur le demande.
 *********************************************/
@media (prefers-reduced-motion: reduce) {
  .reveal .slides section .fragment {
    filter: none !important;
  }
  .reveal .slides section.present > h1::after,
  .reveal .slides section.present > h2::after,
  .reveal .slides section.present > h3::after {
    animation: none;
  }
  .reveal .slides section .fragment.visible.current-fragment,
  .reveal .slides section .fragment.visible.current-fragment * {
    animation: none !important;
  }
}
