/* AERO — expérience immersive originale, vocabulaire « cockpit de nuit » :
   fond quasi noir, HUD vert, typographie display géante, chapitres qui se
   révèlent au défilement au-dessus d'un globe radar permanent.
   Clash Display pour les titres, General Sans pour le corps (Fontshare),
   monospace système pour les étiquettes HUD. */

:root {
  --nuit:    #04060b;
  --panneau: rgba(232, 236, 241, .04);
  --trait:   rgba(232, 236, 241, .14);
  --texte:   #e8ecf1;
  --sourd:   #8b94a3;
  --hud:     #7dffa0;
  --hud-25:  rgba(125, 255, 160, .25);
  --ambre:   #ffb454;

  --display: "Clash Display", ui-sans-serif, system-ui, sans-serif;
  --corps:   "General Sans", ui-sans-serif, system-ui, sans-serif;
  --mono:    ui-monospace, "Cascadia Mono", Consolas, monospace;
}

*, *::before, *::after { box-sizing: border-box; }

html { scroll-behavior: smooth; }

body {
  margin: 0;
  background: var(--nuit);
  color: var(--texte);
  font-family: var(--corps);
  font-size: 16px;
  line-height: 1.6;
  -webkit-font-smoothing: antialiased;
  overflow-x: clip;
}

::selection { background: var(--hud); color: var(--nuit); }
:focus-visible { outline: 2px solid var(--hud); outline-offset: 3px; }

/* ---------------------------------------------------------------- grain */

body::after {
  content: "";
  position: fixed;
  inset: 0;
  z-index: 60;
  pointer-events: none;
  opacity: .05;
  background-image: url("data:image/svg+xml,<svg xmlns='http://www.w3.org/2000/svg' width='120' height='120'><filter id='g'><feTurbulence baseFrequency='.85' numOctaves='2'/></filter><rect width='120' height='120' filter='url(%23g)' opacity='.6'/></svg>");
}

/* ------------------------------------------------------------ préloader */

/* Trois actes. Acte I : compteur géant vert + statuts qui tournent.
   Acte II (.fini) : le compteur s'efface, AERO se révèle lettre à lettre.
   Acte III (.ouvre) : les deux volets glissent, le globe apparaît. */
#chargeur {
  position: fixed;
  inset: 0;
  z-index: 100;
  display: grid;
  place-content: center;
  text-align: center;
}
/* CELUI QUI A DÉJÀ EMBARQUÉ NE LE VOIT JAMAIS. La marque est posée par
   le petit script de l'en-tête, donc avant le premier rendu : `display:
   none`, sans transition, sinon le compteur clignote une image à chaque
   rechargement. La règle `html.pret` ci-dessous, elle, sert à la FIN du
   théâtre et garde son délai pour laisser les volets finir leur course. */
html.sans-chargeur #chargeur { display: none; }

/* le loader ne disparaît qu'une fois les volets arrivés au bout de leur
   course, avec de la marge — sinon la fin du geste est tranchée net */
html.pret #chargeur {
  visibility: hidden;
  transition: visibility 0s 1.5s;
  /* Le rideau reste peint le temps de finir sa course, mais il ne doit
     plus RIEN intercepter dès la première image : sinon le doigt tombe sur
     un volet invisible au lieu de la page ou du globe. */
  pointer-events: none;
}

/* ---- acte 0 : la porte d'embarquement (le geste qui autorise le son) */
#charg-porte {
  position: relative;
  display: grid;
  gap: 1.4rem;
  justify-items: center;
  transition: opacity .45s ease, translate .45s ease;
}
#chargeur.embarque #charg-porte { opacity: 0; translate: 0 -26px; pointer-events: none; }
.charg-marque-mini {
  margin: 0;
  font-family: var(--display);
  font-size: 1.3rem;
  font-weight: 600;
  letter-spacing: .35em;
}
.charg-marque-mini span { color: var(--hud); font-size: .6em; vertical-align: super; }
/* le bouton d'entrée est une carte d'embarquement : partie BOARD, ligne de
   déchirure perforée, talon avec code-barres balayé par un laser au survol */
#btn-embarquer {
  position: relative;
  display: flex;
  align-items: stretch;
  padding: 0;
  background: rgba(232, 236, 241, .045);
  border: 1px solid var(--trait);
  border-radius: 16px;
  color: var(--texte);
  cursor: pointer;
  backdrop-filter: blur(8px);
  transition: translate .25s, rotate .25s, border-color .25s, box-shadow .25s;
  animation: billet-respire 3s ease-in-out infinite;
}
#btn-embarquer:hover, #btn-embarquer:focus-visible {
  translate: 0 -3px;
  rotate: -1.2deg;
  border-color: var(--hud-25);
  box-shadow: 0 18px 50px rgba(125, 255, 160, .16);
}
@keyframes billet-respire {
  0%, 100% { box-shadow: 0 0 0 0 rgba(125, 255, 160, 0); }
  50%      { box-shadow: 0 10px 34px rgba(125, 255, 160, .12); }
}
.be-gauche {
  display: grid;
  gap: .2rem;
  padding: 1.05rem 1.6rem 1rem;
  text-align: left;
}
.be-gauche b {
  font-family: var(--display);
  font-size: 1.3rem;
  font-weight: 600;
  letter-spacing: .3em;
}
.be-gauche i {
  font-style: normal;
  font-family: var(--mono);
  font-size: 9px;
  letter-spacing: .26em;
  color: var(--hud);
}
.be-dechirure {
  position: relative;
  width: 0;
  border-left: 1.5px dashed var(--trait);
}
.be-dechirure::before, .be-dechirure::after {
  content: "";
  position: absolute;
  left: -7.5px;
  width: 13px; height: 13px;
  border-radius: 50%;
  background: var(--nuit);
  border: 1px solid var(--trait);
}
.be-dechirure::before { top: -8px; }
.be-dechirure::after { bottom: -8px; }
.be-talon {
  position: relative;
  display: grid;
  place-content: center;
  padding: 0 1.3rem;
  overflow: hidden;
  border-radius: 0 16px 16px 0;
}
.be-code {
  width: 58px; height: 36px;
  border-radius: 4px;
  opacity: .85;
  background: repeating-linear-gradient(90deg,
    var(--texte) 0 2px, transparent 2px 5px,
    var(--texte) 5px 6px, transparent 6px 10px,
    var(--texte) 10px 13px, transparent 13px 16px);
}
.be-laser {
  position: absolute;
  left: 10px; right: 10px;
  height: 2px;
  top: 18%;
  background: var(--hud);
  box-shadow: 0 0 10px var(--hud);
  opacity: 0;
  animation: laser-scan 1.5s ease-in-out infinite;
}
#btn-embarquer:hover .be-laser, #btn-embarquer:focus-visible .be-laser { opacity: 1; }
@keyframes laser-scan { 0%, 100% { top: 15%; } 50% { top: 82%; } }

/* un vol réel dans le flux : le point vert du direct */
.flux-reel > span:first-child { color: var(--hud); }
/* une route de démonstration : elle habite le globe, elle ne se fait pas
   passer pour un claim — liseré éteint et ligne en retrait */
.flux-demo { border-left-color: var(--trait); opacity: .62; }
.flux-demo > span:nth-child(2) { color: var(--sourd); }
/* un vol pas encore parti : liseré et statut en ambre */
.flux-prevu { border-left-color: var(--ambre); }
.flux-prevu > span:nth-child(2) { color: var(--ambre); }
/* un déblocage de cache : la ligne trésor, ambre des deux côtés */
.flux-cache { border-left-color: var(--ambre); cursor: default; }
.flux-cache > span { color: var(--ambre); }
/* un vol revendiqué : quelqu'un a posé son wallet dessus, il recevra des
   RWA à l'époque. La ligne reste cliquable — on va voir le vol. */
.flux-claim { border-left-color: var(--hud); background: rgba(125, 255, 160, .05); }
.flux-claim > span:first-child { color: var(--hud); }
/* le mur des conversions : untel vient de gagner ses miles */
.flux-miles { cursor: default; }
.flux-miles > span { color: var(--hud); }
/* la ligne reine : miles devenus actions, signés par le keeper */
.flux-rwa {
  cursor: default;
  border-left-color: var(--hud);
  background: rgba(125, 255, 160, .07);
}
.flux-rwa > span { color: var(--hud); font-weight: 600; }

/* L'avion qui vole sur le globe : un glyphe SVG à nous — pas un emoji,
   que Windows peindrait en orange en ignorant la couleur demandée. */
/* Le conteneur est piloté par le moteur du globe, qui y réécrit sa
   translation à chaque image : on ne lui pose AUCUNE transformation, sinon
   les deux écritures se battent et l'avion scintille de biais. Le nez
   tourne sur l'enfant. */
.avion-vol {
  pointer-events: none;
  line-height: 0;
}
.avion-nez {
  display: block;
  line-height: 0;
  will-change: transform;
}
.avion-vol svg {
  display: block;
  fill: var(--hud);
  filter: drop-shadow(0 0 4px rgba(125, 255, 160, .85));
}
/* Les avions ne reçoivent JAMAIS le pointeur : sinon un glissement qui
   démarre sur un glyphe n'atteint pas le canevas et la planète refuse de
   tourner — c'était une des façons dont le globe « s'arrêtait » sous le
   doigt. La sélection se fait au plus proche, côté canevas. */
/* L'AVION SUIVI DOIT SE VOIR. Il est posé sur son propre trait, vert vif
   et épais : sans contour sombre il s'y dissout. Deux ombres portées
   sombres serrées dessinent ce contour, la troisième pose le halo. */
.avion-vol.vise svg {
  fill: #fff;
  scale: 2;
  filter:
    drop-shadow(0 0 1px #04060b) drop-shadow(0 0 1px #04060b)
    drop-shadow(0 0 2px #04060b) drop-shadow(0 0 7px rgba(255, 255, 255, .95));
}
/* position estimée, faute de signal : le glyphe pulse doucement pour
   dire qu'on extrapole au lieu de mesurer */
.avion-vol.estime svg { opacity: .55; animation: estime 1.8s ease-in-out infinite; }
@keyframes estime { 50% { opacity: .18; } }
#btn-silence {
  background: none;
  border: 0;
  color: var(--sourd);
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .3em;
  cursor: pointer;
}
#btn-silence:hover { color: var(--texte); }

/* ---- le compteur-instrument : cadran gradué, aiguille, anneau vert */
.cadran {
  position: relative;
  width: min(272px, 62vw);
  margin: .4rem auto 0;
}
.cadran svg { display: block; width: 100%; overflow: visible; }
#cadran-arc {
  filter: drop-shadow(0 0 7px rgba(125, 255, 160, .45));
}
.cadran-centre {
  position: absolute;
  inset: 0;
  display: grid;
  place-content: center;
  gap: .05rem;
}
.cadran-centre #charg-pct { font-size: clamp(2.5rem, 7.5vw, 3.9rem); }
.cadran-unite {
  margin: 0;
  font-family: var(--mono);
  font-size: 9px;
  letter-spacing: .38em;
  color: var(--sourd);
  text-align: center;
}
#charg-alt {
  margin: 1.15rem 0 .25rem;
  font-family: var(--display);
  font-size: 1.15rem;
  font-weight: 600;
  letter-spacing: .14em;
  color: var(--texte);
  font-variant-numeric: tabular-nums;
}
.instruments {
  margin: 0 0 .4rem;
  display: flex;
  justify-content: center;
  gap: 1.7rem;
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .18em;
  color: var(--sourd);
  font-variant-numeric: tabular-nums;
}

/* le compteur n'apparaît qu'une fois embarqué */
.charg-centre { opacity: 0; pointer-events: none; }
#chargeur.embarque .charg-centre { opacity: 1; transition: opacity .6s ease .3s; }

.charg-volet {
  position: absolute;
  left: 0; right: 0;
  height: 50.5%;
  background: var(--nuit);
  /* long et décéléré : le rideau se pose, il ne claque pas */
  transition: translate 1.3s cubic-bezier(.7, 0, .18, 1);
}
.cv-haut { top: 0; border-bottom: 1px solid var(--hud-25); }
.cv-bas  { bottom: 0; }
#chargeur.ouvre .cv-haut { translate: 0 -101%; }
#chargeur.ouvre .cv-bas  { translate: 0 101%; }

.charg-centre {
  position: relative;
  display: grid;
  gap: .4rem;
  transition: opacity .5s ease, translate .5s ease;
}
#chargeur.fini .charg-centre { opacity: 0; translate: 0 -34px; }

#charg-etat {
  margin: 0 0 .6rem;
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .34em;
  color: var(--sourd);
  min-height: 1.2em;
}
#charg-pct {
  margin: 0;
  font-family: var(--display);
  font-size: clamp(4rem, 14vw, 9rem);
  font-weight: 600;
  line-height: 1;
  letter-spacing: -.02em;
  color: var(--hud);
  font-variant-numeric: tabular-nums;
}
.charg-piste {
  width: min(320px, 60vw);
  height: 1px;
  margin: 1.6rem auto 0;
  background: var(--trait);
}
#charg-barre { width: 0%; height: 100%; background: var(--hud); }
.charg-sous {
  margin: 1.2rem 0 0;
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .3em;
  color: var(--sourd);
}

/* le wordmark de l'acte II : chaque lettre monte dans sa fenêtre */
.charg-mot {
  position: absolute;
  inset: 0;
  margin: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: .08em;
  font-family: var(--display);
  font-size: clamp(3.4rem, 12vw, 8rem);
  font-weight: 600;
  letter-spacing: .12em;
  color: var(--texte);
  pointer-events: none;
}
.charg-mot span { display: block; overflow: hidden; }
.charg-mot i {
  display: block;
  font-style: normal;
  translate: 0 110%;
  transition: translate .65s cubic-bezier(.2, .8, .2, 1);
}
#chargeur.fini .charg-mot i { translate: 0 0; }
#chargeur.fini .charg-mot span:nth-child(2) i { transition-delay: .07s; }
#chargeur.fini .charg-mot span:nth-child(3) i { transition-delay: .14s; }
#chargeur.fini .charg-mot span:nth-child(4) i { transition-delay: .21s; }
#chargeur.ouvre .charg-mot {
  opacity: 0;
  translate: 0 -30px;
  scale: 1.05;
  transition:
    opacity .9s ease .05s,
    translate 1.2s cubic-bezier(.22, 1, .36, 1),
    scale 1.2s cubic-bezier(.22, 1, .36, 1);
}

/* --------------------------------------------------------- vol d'ouverture */

#intro-vol {
  position: fixed;
  inset: 0;
  z-index: 40;               /* au-dessus du contenu, sous le HUD */
  pointer-events: none;
  opacity: 0;
  transition: opacity .8s ease;
}
#intro-vol.joue { opacity: 1; }
#intro-vol.fini { opacity: 0; }
#intro-vol svg { width: 100%; height: 100%; }

/* ------------------------------------------------------------- cadre HUD */

.hud-coin {
  position: fixed;
  z-index: 50;
  width: 22px; height: 22px;
  border: 1px solid var(--hud-25);
  pointer-events: none;
}
.hc-1 { top: 14px; left: 14px;  border-right: 0; border-bottom: 0; }
.hc-2 { top: 14px; right: 14px; border-left: 0;  border-bottom: 0; }
.hc-3 { bottom: 14px; left: 14px;  border-right: 0; border-top: 0; }
.hc-4 { bottom: 14px; right: 14px; border-left: 0;  border-top: 0; }

.hud-haut, .hud-bas {
  position: fixed;
  left: 0; right: 0;
  z-index: 51;
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 1.4rem 2.2rem;
  /* Ces bandes traversent tout l'écran : elles ne doivent JAMAIS attraper
     la souris — sinon elles volent le survol de tout ce qui passe dessous
     (le bouton retour clignotait à cause de ça). Seuls leurs enfants
     cliquables la reprennent. */
  pointer-events: none;
}
.hud-haut > *, .hud-bas > * { pointer-events: auto; }
.hud-bas > * { pointer-events: none; }   /* coords et % : affichage pur */
.hud-haut { top: 0; }
.hud-bas  { bottom: 0; font-family: var(--mono); font-size: 11px; letter-spacing: .18em; color: var(--sourd); }

.marque {
  font-family: var(--display);
  font-size: 1.15rem;
  font-weight: 600;
  letter-spacing: .3em;
  color: var(--texte);
  text-decoration: none;
}
.marque span { color: var(--hud); font-size: .6em; vertical-align: super; letter-spacing: 0; }

#btn-son {
  display: inline-flex;
  align-items: center;
  gap: .6rem;
  padding: .5rem 1rem;
  background: rgba(4, 6, 11, .55);
  border: 1px solid var(--trait);
  border-radius: 999px;
  color: var(--sourd);
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .22em;
  cursor: pointer;
  transition: color .2s, border-color .2s;
}
#btn-son:hover { color: var(--texte); }
#btn-son[aria-pressed="true"] { color: var(--hud); border-color: var(--hud-25); }
.son-barres { display: inline-flex; align-items: flex-end; gap: 2px; height: 10px; }
.son-barres i {
  width: 2px; height: 3px;
  background: currentColor;
  animation: egaliseur 1.1s ease-in-out infinite paused;
}
#btn-son[aria-pressed="true"] .son-barres i { animation-play-state: running; }
.son-barres i:nth-child(2) { animation-delay: -.3s; }
.son-barres i:nth-child(3) { animation-delay: -.6s; }
.son-barres i:nth-child(4) { animation-delay: -.9s; }
@keyframes egaliseur { 0%, 100% { height: 3px; } 50% { height: 10px; } }

/* ----------------------------------------------------------------- globe */

#globe {
  position: fixed;
  inset: 0;
  z-index: 0;
}
/* Assombrit le globe derrière le texte, s'éclaircit vers le radar. */
.voile-globe {
  position: fixed;
  inset: 0;
  z-index: 1;
  pointer-events: none;
  background: radial-gradient(120% 90% at 50% 50%, transparent 30%, rgba(4, 6, 11, .78) 100%);
}

main { position: relative; z-index: 2; }

/* ----------------------------------------------------------------- héros */

.heros {
  min-height: 100svh;
  display: flex;
  flex-direction: column;
  justify-content: center;
  padding: 0 clamp(1.2rem, 6vw, 6rem);
}
.kicker {
  margin: 0 0 1.2rem;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: .34em;
  color: var(--hud);
}
.heros h1 {
  margin: 0;
  font-family: var(--display);
  font-weight: 600;
  font-size: clamp(3rem, 11vw, 9.5rem);
  line-height: .98;
  letter-spacing: -.025em;
  text-transform: uppercase;
}
.heros h1 em { font-style: normal; color: var(--hud); }
.heros h1 .ligne { display: block; overflow: hidden; }
.curseur { font-style: normal; color: var(--ambre); animation: pouls-curseur 1.4s steps(2) infinite; }
@keyframes pouls-curseur { 50% { opacity: 0; } }

.heros-sous {
  max-width: 34rem;
  margin: 1.8rem 0 2.2rem;
  color: var(--sourd);
  font-size: 1.05rem;
}
.heros-actions {
  display: flex;
  flex-wrap: wrap;
  gap: .8rem;
  align-items: center;
}
.cta {
  align-self: flex-start;
  padding: .85rem 1.7rem;
  border: 1px solid var(--hud-25);
  border-radius: 999px;
  color: var(--hud);
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: .26em;
  text-decoration: none;
  transition: background .2s, color .2s, filter .2s;
}
.cta:hover { background: var(--hud); color: var(--nuit); }
/* la porte principale : le scan, en plein */
.cta-plein {
  background: var(--hud);
  color: var(--nuit);
  border-color: transparent;
  box-shadow: 0 10px 30px rgba(125, 255, 160, .22);
}
.cta-plein:hover { filter: brightness(1.1); }

/* Le CTA-billet : une carte d'embarquement miniature, pleine couleur. Les
   encoches de perforation sont peintes couleur de nuit pour mordre dedans. */
.cta-billet {
  position: relative;
  display: inline-flex;
  align-items: stretch;
  background: var(--hud);
  color: var(--nuit);
  border-radius: 14px;
  text-decoration: none;
  box-shadow: 0 12px 34px rgba(125, 255, 160, .25);
  transition: translate .22s, rotate .22s, box-shadow .22s, filter .22s;
}
.cta-billet:hover {
  translate: 0 -3px;
  rotate: -1.4deg;
  filter: brightness(1.06);
  box-shadow: 0 18px 44px rgba(125, 255, 160, .35);
}
.cb-gauche {
  display: grid;
  gap: .12rem;
  padding: .8rem 1.25rem .75rem;
  text-align: left;
}
.cb-gauche b {
  font-family: var(--display);
  font-size: 1.02rem;
  font-weight: 600;
  letter-spacing: .18em;
}
.cb-gauche i {
  font-style: normal;
  font-family: var(--mono);
  font-size: 8.5px;
  letter-spacing: .22em;
  color: rgba(4, 6, 11, .62);
}
.cb-dechirure {
  position: relative;
  width: 0;
  border-left: 1.5px dashed rgba(4, 6, 11, .35);
}
.cb-dechirure::before, .cb-dechirure::after {
  content: "";
  position: absolute;
  left: -6.5px;
  width: 11px;
  height: 11px;
  border-radius: 50%;
  background: var(--nuit);
}
.cb-dechirure::before { top: -6px; }
.cb-dechirure::after { bottom: -6px; }
.cb-talon {
  position: relative;
  display: grid;
  place-content: center;
  padding: 0 1rem;
  overflow: hidden;
  border-radius: 0 14px 14px 0;
}
.cb-code {
  width: 40px;
  height: 26px;
  border-radius: 3px;
  opacity: .9;
  background: repeating-linear-gradient(90deg,
    var(--nuit) 0 2px, transparent 2px 4px,
    var(--nuit) 4px 7px, transparent 7px 9px,
    var(--nuit) 9px 10px, transparent 10px 13px);
}
.cb-laser {
  position: absolute;
  left: 7px;
  right: 7px;
  height: 2px;
  top: 20%;
  background: #fff;
  box-shadow: 0 0 8px #fff;
  opacity: 0;
  animation: laser-scan 1.4s ease-in-out infinite;
}
.cta-billet:hover .cb-laser { opacity: .9; }

/* Le CTA-radar : l'écope qui balaie, le blip qui s'allume au passage.
   Mêmes métriques internes que le billet → même hauteur, sans magie. */
.cta-radar {
  display: inline-flex;
  align-items: center;
  gap: .9rem;
  padding: .8rem 1.35rem .75rem 1rem;
  background: rgba(4, 6, 11, .5);
  border: 1px solid var(--hud-25);
  border-radius: 14px;
  text-decoration: none;
  backdrop-filter: blur(6px);
  transition: translate .22s, border-color .22s, box-shadow .22s;
}
.cta-radar:hover {
  translate: 0 -3px;
  border-color: var(--hud);
  box-shadow: 0 14px 36px rgba(125, 255, 160, .16);
}
.cr-scope {
  position: relative;
  width: 34px;
  height: 34px;
  flex: none;
  border-radius: 50%;
  border: 1px solid var(--hud-25);
  background: radial-gradient(circle, transparent 52%, rgba(125, 255, 160, .16) 54%, transparent 58%);
  overflow: hidden;
}
.cr-scope i {
  position: absolute;
  inset: 0;
  background: conic-gradient(from 0deg, rgba(125, 255, 160, .55), transparent 70deg, transparent 360deg);
  animation: cr-balaye 2.6s linear infinite;
}
.cr-scope b {
  position: absolute;
  top: 26%;
  left: 60%;
  width: 4px;
  height: 4px;
  border-radius: 50%;
  background: var(--hud);
  box-shadow: 0 0 6px var(--hud);
  animation: cr-blip 2.6s linear infinite;
}
@keyframes cr-balaye { to { rotate: 360deg; } }
@keyframes cr-blip { 0%, 12% { opacity: 1; } 30%, 100% { opacity: .15; } }
.cr-texte { display: grid; gap: .12rem; text-align: left; }
.cr-texte b {
  font-family: var(--display);
  font-size: 1.02rem;
  font-weight: 600;
  letter-spacing: .18em;
  color: var(--hud);
}
.cr-texte i {
  font-style: normal;
  font-family: var(--mono);
  font-size: 8.5px;
  letter-spacing: .22em;
  color: var(--sourd);
}

.hud-droite { display: flex; align-items: center; gap: .6rem; }
.hud-scan {
  padding: .5rem 1rem;
  background: rgba(125, 255, 160, .12);
  border: 1px solid var(--hud-25);
  border-radius: 999px;
  color: var(--hud);
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .22em;
  text-decoration: none;
  transition: background .2s, color .2s;
}
.hud-scan:hover { background: var(--hud); color: var(--nuit); }

/* ---- L'ADRESSE DU CONTRAT, aux deux endroits.
   Tant qu'elle n'existe pas, la pilule est éteinte : bordure seule, texte
   sourd, pas de main au survol. Posée, elle s'allume et un clic la copie.
   `font-variant-numeric` garde les chiffres alignés entre 0x99EC et cA29. */
.hud-ca {
  cursor: pointer;
  font-variant-numeric: tabular-nums;
}
.hud-ca[aria-disabled="true"] {
  cursor: default;
  background: transparent;
  color: var(--sourd);
  border-style: dashed;
}
.hud-ca[aria-disabled="true"]:hover { background: transparent; color: var(--sourd); }
.hud-ca.copie { background: var(--hud); color: var(--nuit); }

.ca-mobile {
  display: none;                /* le HUD s'en charge sur grand écran */
  width: 100%;
  align-items: center;
  justify-content: space-between;
  gap: 1rem;
  padding: .7rem 1rem;
  background: rgba(4, 6, 11, .5);
  border: 1px dashed var(--hud-25);
  border-radius: 12px;
  color: var(--sourd);
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .2em;
  backdrop-filter: blur(6px);
}
.ca-mobile .ca-valeur { font-variant-numeric: tabular-nums; color: inherit; }
.ca-mobile:not([aria-disabled="true"]) {
  border-style: solid;
  color: var(--hud);
  cursor: pointer;
}
.ca-mobile.copie { background: var(--hud); color: var(--nuit); border-color: var(--hud); }

/* ---- L'INSTRUMENT D'ÉPOQUE.
   Un cadran : la piste, l'arc du temps écoulé, et l'avion qui le parcourt —
   un tour complet par époque. À droite, le compte à rebours en chiffres
   tabulaires (ils ne sautent pas d'une seconde à l'autre). En bas, le
   compteur d'avions du protocole et le nombre d'airdrops déjà partis.
   Le panneau est d'abord un bloc du flux, pleine largeur sous l'adresse du
   contrat ; sur grand écran il se détache et flotte à droite du héros. */
.epoque {
  width: 100%;
  display: grid;
  grid-template-columns: auto 1fr;
  grid-template-areas: "cadran texte" "bas bas";
  align-items: center;
  column-gap: 1.1rem;
  row-gap: .75rem;
  padding: .95rem 1.1rem .9rem;
  background: rgba(4, 6, 11, .58);
  border: 1px solid var(--hud-25);
  border-radius: 16px;
  backdrop-filter: blur(8px);
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .2em;
  color: var(--sourd);
  position: relative;
}
/* les deux encoches de coin, comme celles du HUD */
.epoque::before, .epoque::after {
  content: "";
  position: absolute;
  width: 12px; height: 12px;
  border: 1px solid var(--hud);
  opacity: .7;
}
.epoque::before { top: -1px; left: -1px; border-right: 0; border-bottom: 0; border-radius: 16px 0 0 0; }
.epoque::after  { bottom: -1px; right: -1px; border-left: 0; border-top: 0; border-radius: 0 0 16px 0; }

.ep-cadran {
  grid-area: cadran;
  position: relative;
  width: 74px; height: 74px;
}
.ep-cadran svg { width: 100%; height: 100%; display: block; overflow: visible; }
.ep-piste { fill: none; stroke: rgba(232, 236, 241, .12); stroke-width: 3; }
.ep-arc {
  fill: none;
  stroke: var(--hud);
  stroke-width: 3;
  stroke-linecap: round;
  stroke-dasharray: 339.29;          /* 2π × 54 */
  stroke-dashoffset: 339.29;
  filter: drop-shadow(0 0 6px rgba(125, 255, 160, .55));
  transition: stroke-dashoffset 1s linear;
}
.ep-avion { fill: var(--hud); transition: transform 1s linear; transform-origin: 60px 60px; }
.ep-centre {
  position: absolute; inset: 0;
  display: grid; place-items: center;
  font-size: 11px;
  letter-spacing: .08em;
  color: var(--texte);
  font-variant-numeric: tabular-nums;
}

.ep-texte { grid-area: texte; display: flex; flex-direction: column; gap: .3rem; min-width: 0; }
.ep-etiquette { display: inline-flex; align-items: center; gap: .55rem; color: var(--hud); letter-spacing: .3em; }
.ep-blip {
  width: 7px; height: 7px;
  border-radius: 50%;
  background: var(--hud);
  box-shadow: 0 0 0 0 rgba(125, 255, 160, .6);
  animation: ep-blip 1.6s ease-out infinite;
}
@keyframes ep-blip { 70% { box-shadow: 0 0 0 7px rgba(125, 255, 160, 0); } 100% { box-shadow: 0 0 0 0 rgba(125, 255, 160, 0); } }
.ep-temps {
  font-family: var(--display);
  font-size: 2.35rem;
  font-weight: 600;
  line-height: 1;
  letter-spacing: -.01em;
  color: var(--texte);
  font-variant-numeric: tabular-nums;
}
.ep-temps.ep-cloture { color: var(--ambre); animation: pouls-curseur 1s steps(2) infinite; }
.ep-sous { letter-spacing: .18em; line-height: 1.6; }

.ep-bas {
  grid-area: bas;
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  gap: .8rem 1.2rem;
  flex-wrap: wrap;
  padding-top: .7rem;
  border-top: 1px dashed var(--hud-25);
  color: var(--texte);
}
.ep-vols i { color: var(--hud); font-style: normal; margin-right: .45rem; }
.ep-vols b, .ep-tours b {
  font-family: var(--display);
  font-size: 1.05rem;
  font-weight: 600;
  letter-spacing: 0;
  color: var(--hud);
  font-variant-numeric: tabular-nums;
  margin-right: .25rem;
}
/* un vol qui arrive fait sursauter le compteur */
.ep-vols b.ep-tic { animation: ep-tic .5s ease-out; }
@keyframes ep-tic { 0% { color: #fff; translate: 0 -3px; } 100% { color: var(--hud); translate: 0 0; } }
.ep-tours { color: var(--sourd); }

@media (min-width: 1100px) {
  .heros { position: relative; }
  .epoque {
    position: absolute;
    right: clamp(1.2rem, 6vw, 6rem);
    bottom: 6.6rem;
    width: 23rem;
  }
}

.lien-scan {
  width: fit-content;
  margin: -0.4rem 0 1.2rem;
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .24em;
  color: var(--hud);
  text-decoration: none;
  border-bottom: 1px dashed var(--hud-25);
  padding-bottom: .2rem;
}
.lien-scan:hover { border-bottom-style: solid; }
.indice-scroll {
  position: absolute;
  bottom: 4.6rem;
  left: 50%;
  translate: -50% 0;
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .4em;
  color: var(--sourd);
  animation: descendre 2.2s ease-in-out infinite;
}
@keyframes descendre { 0%, 100% { translate: -50% 0; opacity: .5; } 50% { translate: -50% 8px; opacity: 1; } }

/* ------------------------------------------------------- voyage au scroll */

/* Quatre hauteurs d'écran de défilement ; la scène reste collée pendant que
   l'avion parcourt sa route et que les jalons s'allument. */
.voyage { height: 430vh; position: relative; }
/* La scène n'est PAS en sticky : fixe plein écran, allumée par le script
   pendant la traversée de la section — la même mécanique éprouvée que le
   globe. Le sticky a trop de façons silencieuses de mourir. */
.voyage-scene {
  position: fixed;
  inset: 0;
  height: 100svh;
  overflow: clip;
  background: rgba(4, 6, 11, .55);
  opacity: 0;
  pointer-events: none;
  transition: opacity .45s ease;
}
.voyage-scene.visible { opacity: 1; }
.voyage-ciel { position: absolute; inset: 0; width: 100%; height: 100%; }

.jalon {
  position: absolute;
  max-width: 21rem;
  opacity: 0;
  translate: 0 26px;
  transition: opacity .55s ease, translate .55s ease;
}
.jalon.actif { opacity: 1; translate: 0 0; }
.jalon-alt {
  margin: 0 0 .6rem;
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .34em;
  color: var(--hud);
}
.jalon h3 {
  margin: 0 0 .6rem;
  font-family: var(--display);
  font-weight: 600;
  font-size: clamp(1.6rem, 3.6vw, 2.6rem);
  line-height: 1.04;
  letter-spacing: -.015em;
  text-transform: uppercase;
}
.jalon p:last-child { margin: 0; color: var(--sourd); font-size: .95rem; }

.j-1 { left: 7%;  top: 14%; }
.j-2 { right: 7%; bottom: 16%; }
.j-3 { left: 7%;  bottom: 18%; }
.j-4 { right: 7%; top: 26%; text-align: right; }

/* (les réglages mobiles des jalons vivent dans le bloc mobile global) */

/* ------------------------------------------------------------- chapitres */

.chapitre, .radar, .claims {
  min-height: 92svh;
  display: flex;
  flex-direction: column;
  justify-content: center;
  padding: 6rem clamp(1.2rem, 6vw, 6rem);
  max-width: 1100px;
}
.chap-num {
  margin: 0 0 1rem;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: .34em;
  color: var(--hud);
}
.chapitre h2, .radar h2, .claims h2 {
  margin: 0 0 1.2rem;
  font-family: var(--display);
  font-weight: 600;
  font-size: clamp(2.2rem, 6.5vw, 5rem);
  line-height: 1.02;
  letter-spacing: -.02em;
  text-transform: uppercase;
}
.chap-txt, .claims-txt { max-width: 32rem; margin: 0 0 2.4rem; color: var(--sourd); }

/* ------------------------------------------------ billet dessiné en CSS */

.billet {
  width: min(430px, 92vw);
  padding: 1.1rem 1.25rem 1.25rem;
  background: var(--panneau);
  border: 1px solid var(--trait);
  border-radius: 18px;
  backdrop-filter: blur(8px);
  font-family: var(--mono);
}
.billet-haut {
  display: flex;
  justify-content: space-between;
  font-size: 10px;
  letter-spacing: .22em;
  color: var(--sourd);
  padding-bottom: .9rem;
  border-bottom: 1px dashed var(--trait);
}
.b-vert { color: var(--hud); }
.billet-corps {
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 1.1rem 0;
}
.billet-corps b { display: block; font-family: var(--display); font-size: 2.3rem; font-weight: 600; letter-spacing: .02em; }
.billet-corps i { font-style: normal; font-size: 9.5px; letter-spacing: .3em; color: var(--sourd); }
.billet-avion { color: var(--hud); font-size: 1.2rem; }
.billet-infos {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: .6rem;
  padding: .9rem 0 1rem;
  border-top: 1px dashed var(--trait);
  font-size: 9px;
  letter-spacing: .18em;
  color: var(--sourd);
}
.billet-infos b { display: block; margin-top: .25rem; font-size: 12px; color: var(--texte); letter-spacing: .06em; }
/* le code-barres : des bandes, générées, à nous */
.billet-code {
  height: 44px;
  border-radius: 6px;
  background: repeating-linear-gradient(90deg,
    var(--texte) 0 2px, transparent 2px 5px,
    var(--texte) 5px 6px, transparent 6px 11px,
    var(--texte) 11px 14px, transparent 14px 17px);
  opacity: .85;
}

/* ------------------------------------------------------------ stats 02 */

.stats {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
  gap: 1px;
  background: var(--trait);
  border: 1px solid var(--trait);
  border-radius: 18px;
  overflow: hidden;
  max-width: 760px;
}
.stat {
  min-width: 0;                 /* une case de grille ne s'élargit pas : le chiffre s'y adapte */
  padding: 1.6rem 1.4rem;
  background: rgba(4, 6, 11, .72);
  backdrop-filter: blur(8px);
}
.stat-val {
  display: block;
  font-family: var(--display);
  /* borné par la largeur : quatre cases côte à côte sur 760 px font 190 px
     chacune, et « 999,999 » en 2,4 rem n'y tenait pas */
  font-size: clamp(1.45rem, 1.1rem + 1.2vw, 2.4rem);
  overflow-wrap: anywhere;
  font-weight: 600;
  letter-spacing: -.02em;
  color: var(--texte);
  font-variant-numeric: tabular-nums;
}
.stat-nom { font-family: var(--mono); font-size: 9.5px; letter-spacing: .26em; color: var(--sourd); }

/* ------------------------------------------------------------- parts 03 */

.parts {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(210px, 1fr));
  gap: 1rem;
  max-width: 820px;
}
.part {
  padding: 1.4rem 1.3rem 1.2rem;
  background: var(--panneau);
  border: 1px solid var(--trait);
  border-radius: 18px;
  backdrop-filter: blur(8px);
  transition: border-color .25s, translate .25s;
}
.part:hover { border-color: var(--hud-25); translate: 0 -4px; }
.part-tick { font-family: var(--mono); font-size: 11px; letter-spacing: .3em; color: var(--hud); }
/* Le logo de la maison, ramené au blanc comme ailleurs sur le site. */
.part-logo {
  display: block;
  height: 20px;
  width: auto;
  max-width: 10rem;
  object-fit: contain;
  object-position: left;
  filter: brightness(0) invert(1);
  opacity: .8;
}
/* Firefly n'a pas de logo librement diffusé : son nom, dans notre fonte */
.part-mot {
  font-family: var(--mono);
  font-size: 13px;
  letter-spacing: .3em;
  line-height: 20px;
  color: var(--texte);
  filter: none;
  opacity: 1;
}
.part-adr {
  display: block;
  margin-top: .9rem;
  font-family: var(--mono);
  font-size: 9px;
  letter-spacing: .14em;
  color: var(--sourd);
  opacity: .7;
}
.part b { display: block; margin: .8rem 0 .2rem; font-family: var(--display); font-size: 2rem; font-weight: 600; }
.part b i { font-style: normal; font-size: .45em; color: var(--sourd); letter-spacing: .2em; }
.part-nom { font-family: var(--mono); font-size: 9px; letter-spacing: .22em; color: var(--sourd); }
.part-barre { height: 3px; margin-top: 1.1rem; background: var(--trait); border-radius: 999px; overflow: hidden; }
.part-barre b { display: block; width: var(--v, 40%); height: 100%; margin: 0; background: var(--hud); border-radius: 999px; }

/* La note sous les paniers : la règle en une ligne, et le lien vers le
   manuel pour qui veut le détail. */
.chap-note {
  max-width: 40rem;
  margin: 1.4rem 0 0;
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .18em;
  line-height: 1.9;
  color: var(--sourd);
}
.chap-note a { color: var(--hud); text-decoration: none; white-space: nowrap; }
.chap-note a:hover { text-decoration: underline; }

/* D'où viennent les quatre nombres du chapitre 02 : le passeport de cet
   appareil, ou les totaux du protocole. On le DIT, sinon on laisse croire
   que ce sont les siens. */
.stats-source {
  margin: .9rem 0 0;
  font-family: var(--mono);
  font-size: 9.5px;
  letter-spacing: .24em;
  color: var(--sourd);
}

/* ---------------------------------------------------- carte de cache 03 */

.cache {
  width: min(430px, 92vw);
  padding: 1.15rem 1.25rem 1.25rem;
  background: var(--panneau);
  border: 1px solid var(--trait);
  border-radius: 18px;
  backdrop-filter: blur(8px);
  font-family: var(--mono);
}
.cache-haut {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  font-size: 10px;
  letter-spacing: .2em;
  color: var(--sourd);
  padding-bottom: .9rem;
  border-bottom: 1px dashed var(--trait);
}
.cache-coord {
  margin: 1rem 0 .3rem;
  font-family: var(--display);
  font-size: 1.6rem;
  font-weight: 600;
  letter-spacing: .02em;
  color: var(--texte);
}
.cache-indice { margin: 0 0 1.1rem; font-size: 11.5px; letter-spacing: .08em; color: var(--sourd); }
.cache-jauge {
  height: 6px;
  border-radius: 999px;
  background: var(--trait);
  overflow: hidden;
}
.cache-jauge b {
  display: block;
  width: var(--v, 30%);
  height: 100%;
  background: linear-gradient(90deg, var(--hud), var(--ambre));
  border-radius: 999px;
}
.cache-pied {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  margin-top: .6rem;
  font-size: 9.5px;
  letter-spacing: .18em;
  color: var(--sourd);
}

/* ---------------------------------------------------------------- radar */

.compteurs {
  display: flex;
  flex-wrap: wrap;
  gap: 2.4rem;
  margin: 0 0 2rem;
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .24em;
  color: var(--sourd);
}
.compteurs b {
  display: block;
  font-family: var(--display);
  font-size: 2rem;
  font-weight: 600;
  letter-spacing: -.01em;
  color: var(--texte);
  font-variant-numeric: tabular-nums;
}

.radar-note {
  margin: -1rem 0 .9rem;
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .26em;
  color: var(--ambre);
}

/* l'interrupteur du ciel réel */
#btn-ciel {
  width: fit-content;
  margin: 0 0 1.2rem;
  padding: .55rem 1.15rem;
  background: transparent;
  border: 1px solid var(--trait);
  border-radius: 999px;
  color: var(--sourd);
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .24em;
  cursor: pointer;
  transition: color .2s, border-color .2s;
}
#btn-ciel:hover { color: var(--texte); }
#btn-ciel[aria-pressed="true"] { color: var(--hud); border-color: var(--hud-25); }

/* les avions réels : plus petits, bleutés, sans halo appuyé */
.avion-vol.reel svg { fill: #b8cfe8; filter: drop-shadow(0 0 3px rgba(184, 207, 232, .55)); }

/* Sur mobile, le ciel réel peut afficher des dizaines de glyphes : chaque
   ombre portée est une passe de flou de plus à chaque image. On les coupe
   là où elles coûtent le plus et se voient le moins. */
@media (pointer: coarse) {
  .avion-vol.reel svg { filter: none; }
}

/* Le dernier claim, sous les compteurs : un statut en direct, pas un
   bouton. Le wallet y est masqué, comme partout ailleurs. */
.dernier-claim {
  margin: -.4rem 0 .9rem;
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .18em;
  color: var(--hud);
}
.dernier-claim b { color: var(--texte); font-weight: 500; }
.dernier-claim span { color: var(--sourd); }

/* La fiche du vol suivi : route réelle, distance réelle, avancement. */
#fiche-vol {
  position: fixed;
  left: clamp(1rem, 5vw, 3rem);
  bottom: clamp(1rem, 5vh, 3rem);
  z-index: 3;
  display: grid;
  gap: .3rem;
  padding: .85rem 1.1rem;
  max-width: min(74vw, 22rem);
  font-family: var(--mono);
  font-size: .74rem;
  letter-spacing: .06em;
  color: var(--sourd);
  background: rgba(4, 6, 11, .72);
  border: 1px solid rgba(125, 255, 160, .22);
  border-radius: 2px;
  backdrop-filter: blur(6px);
  pointer-events: none;
}
/* Suivre n'importe quel vol par son numéro. */
#recherche-vol {
  max-width: 480px;
  margin: 0 0 1.1rem;
  font-family: var(--mono);
}
#recherche-vol label {
  display: block;
  margin-bottom: .45rem;
  font-size: 10px;
  letter-spacing: .24em;
  color: var(--sourd);
}
.rv-ligne { display: flex; gap: .5rem; }
#num-vol {
  flex: 1;
  min-width: 0;
  padding: .7rem .9rem;
  background: var(--panneau);
  border: 1px solid var(--trait);
  border-left: 2px solid var(--hud-25);
  border-radius: 12px;
  color: var(--texte);
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: .14em;
  text-transform: uppercase;
}
#num-vol::placeholder { color: var(--sourd); text-transform: none; letter-spacing: .08em; }
#num-vol:focus { outline: none; border-color: var(--hud); border-left-color: var(--hud); }
#recherche-vol button {
  padding: .7rem 1.1rem;
  background: none;
  border: 1px solid var(--hud-25);
  border-radius: 12px;
  color: var(--hud);
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: .18em;
  cursor: pointer;
  transition: background .2s, color .2s;
}
#recherche-vol button:hover { background: var(--hud); color: var(--nuit); }
#recherche-vol button[disabled] { opacity: .5; cursor: progress; }
#rv-etat {
  min-height: 1.1em;
  margin: .5rem 0 0;
  font-size: 10.5px;
  letter-spacing: .1em;
  color: var(--sourd);
}
#rv-etat.rv-rate { color: #ffb454; }
/* pendant un suivi, le panneau s'efface comme le reste */
.radar #recherche-vol { transition: opacity .45s ease, translate .45s ease; }
html.suivi #recherche-vol, html.ciel #recherche-vol {
  opacity: 0;
  translate: -26px 0;
  pointer-events: none;
}
html.suivi #recherche-vol input, html.suivi #recherche-vol button,
html.ciel #recherche-vol input, html.ciel #recherche-vol button {
  pointer-events: none;
}

/* L'attribut « hidden » ne suffit pas : le display posé juste au-dessus
   écrase celui de la feuille du navigateur, et la fiche restait affichée
   après BACK TO FLIGHTS. */
#fiche-vol[hidden] { display: none; }
/* les vols frères proposés quand le numéro cherché n'émet pas */
#fiche-vol { pointer-events: none; }
#fiche-vol .autre-vol {
  display: inline-block;
  margin: .15rem .25rem 0 0;
  padding: .2rem .5rem;
  border: 1px solid var(--hud-25);
  border-radius: 999px;
  color: var(--hud);
  font-weight: 500;
  cursor: pointer;
  pointer-events: auto;
}
#fiche-vol .autre-vol:hover { background: var(--hud); color: var(--nuit); }
#fiche-vol b { color: var(--hud); font-weight: 600; letter-spacing: .1em; }
#fiche-vol i { display: block; margin-top: .15rem; font-style: normal; font-size: .92em; color: var(--sourd); }
html.suivi-reel #fiche-vol { border-color: rgba(184, 207, 232, .3); }
html.suivi-reel #fiche-vol b { color: #dcebff; }
#flux { display: flex; flex-direction: column; gap: .55rem; max-width: 480px; min-height: 15rem; }
.flux-item {
  display: flex;
  justify-content: space-between;
  align-items: center;
  gap: 1rem;
  padding: .75rem 1rem;
  background: var(--panneau);
  border: 1px solid var(--trait);
  border-left: 2px solid var(--hud);
  border-radius: 12px;
  backdrop-filter: blur(8px);
  color: var(--texte);
  font-family: var(--mono);
  font-size: 11.5px;
  letter-spacing: .12em;
  text-align: left;
  cursor: pointer;
  transition: border-color .2s, background .2s, translate .2s;
  animation: flux-entre .5s cubic-bezier(.2, .8, .3, 1) both;
}
.flux-item:hover { border-color: var(--hud-25); background: rgba(125, 255, 160, .05); translate: 2px 0; }
.flux-item > span:nth-child(2) { color: var(--sourd); margin-left: auto; }
.flux-suivre {
  color: var(--ambre);
  font-size: 9.5px;
  letter-spacing: .22em;
  opacity: 0;
  transition: opacity .2s;
}
.flux-item:hover .flux-suivre, .flux-item:focus-visible .flux-suivre { opacity: 1; }
@keyframes flux-entre { from { opacity: 0; translate: 0 10px; } }

/* Pendant le suivi d'un vol : le voile s'efface, le globe est la vedette —
   et tout le panneau de gauche se retire pour lui laisser la scène. */
.voile-globe { transition: opacity .7s ease; }
html.suivi .voile-globe { opacity: .28; }

.radar .chap-num, .radar h2, .compteurs, .radar-note, #btn-ciel, #flux {
  transition: opacity .45s ease, translate .45s ease;
}
html.suivi .radar .chap-num,
html.suivi .radar h2,
html.suivi .compteurs,
html.suivi .radar-note,
html.suivi #btn-ciel,
html.suivi #flux {
  opacity: 0;
  translate: -26px 0;
  pointer-events: none;
}
/* Les vols de la liste sont des <button>, et la règle générale plus bas
   (« main button { pointer-events: auto } ») les réarme un par un : le
   « pointer-events: none » posé sur #flux ne s'hérite pas contre une
   déclaration explicite. Résultat, une liste devenue invisible continuait
   d'avaler le doigt sur toute une bande de l'écran, et la planète ne
   tournait pas. Il faut viser les boutons eux-mêmes. */
html.suivi #flux .flux-item,
html.ciel #flux .flux-item { pointer-events: none; }

/* le bouton de retour, seul maître à bord pendant le suivi */
#btn-retour-vols {
  position: fixed;
  left: 50%;
  bottom: 3.6rem;   /* au-dessus de la ligne de coordonnées du HUD */
  translate: -50% 0;
  z-index: 61;
  padding: .85rem 1.7rem;
  background: rgba(4, 6, 11, .6);
  border: 1px solid var(--hud-25);
  border-radius: 999px;
  color: var(--hud);
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: .26em;
  cursor: pointer;
  backdrop-filter: blur(10px);
  opacity: 0;
  pointer-events: none;
  transition: opacity .45s ease .25s, background .2s, color .2s;
}
#btn-retour-vols:hover { background: var(--hud); color: var(--nuit); }
html.suivi #btn-retour-vols { opacity: 1; pointer-events: auto; }

/* en suivi, le pied se retire aussi : scène nue */
.pied { transition: opacity .4s ease; }
html.suivi .pied { opacity: 0; pointer-events: none; }

/* En suivi, TOUT le reste de la page s'écarte — pas seulement le panneau
   du radar. Sans ça, les cartes du chapitre précédent restaient posées
   par-dessus le globe, puisque le défilement est gelé là où il était. */
html.suivi main > *:not(.radar) { opacity: 0; pointer-events: none; }
html.suivi main > * { transition: opacity .45s ease; }

/* SUIVI = scène verrouillée : le site ne défile plus (le doigt appartient
   à la planète), et rien d'écrit ne traîne — seul BACK TO FLIGHTS libère. */
html.suivi, html.suivi body { overflow: hidden; }
/* Le touch-action du canevas se règle en JS (majPriseGlobe) : le
   contrôleur de caméra le pose en style EN LIGNE, qu'une règle d'ici ne
   peut pas battre. Ne pas le remettre ici, ça ne marcherait pas. */
html.suivi .lien-scan { opacity: 0; pointer-events: none; }
.lien-scan { transition: opacity .3s ease; }

/* Le bloc de gauche du HUD : la marque, puis X. */
.hud-gauche { display: flex; align-items: center; gap: .85rem; }
.hud-x {
  display: grid;
  place-content: center;
  width: 30px; height: 30px;
  border: 1px solid var(--trait);
  border-radius: 999px;
  color: var(--sourd);
  transition: color .2s, border-color .2s, background .2s;
}
.hud-x svg { display: block; fill: currentColor; }
.hud-x:hover, .hud-x:focus-visible { color: var(--nuit); background: var(--hud); border-color: var(--hud); }



/* CIEL ALLUMÉ = on explore le trafic réel : la planète prend le doigt, et
   tout ce qui pourrait l'intercepter s'écarte. Sans ça, viser un avion qui
   passe derrière le lien de scan ouvrait la page de scan au lieu d'ouvrir
   l'itinéraire du vol. Le bouton LIVE SKY, lui, reste : c'est la sortie. */
html.ciel #flux, html.ciel .lien-scan, html.ciel .compteurs {
  opacity: 0;
  pointer-events: none;
  transition: opacity .3s ease;
}

/* La planète se manipule à la main : le contenu laisse passer la souris
   partout où il n'y a pas un vrai contrôle — les clics et la molette
   traversent les textes jusqu'au globe. */
main { pointer-events: none; }
main a, main button, main input, main textarea, main label { pointer-events: auto; }
#globe { cursor: grab; }
#globe:active { cursor: grabbing; }

/* --------------------------------------------------------------- bande */

.pied {
  padding: 3.5rem clamp(1.2rem, 6vw, 6rem) 5.5rem;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: .18em;
  color: var(--sourd);
}
.pied p { margin: .3rem 0; }

/* ------------------------------------------------- apparitions au scroll */

.app { opacity: 0; translate: 0 30px; }
.app-vu {
  opacity: 1;
  translate: 0 0;
  transition: opacity .9s cubic-bezier(.17, .67, .3, .99), translate .9s cubic-bezier(.17, .67, .3, .99);
}

/* Le mouvement s'éteint si le système le demande — sauf dérogation posée
   par site.js (html.avec-anim, ou ?anim dans l'URL). */
@media (prefers-reduced-motion: reduce) {
  html:not(.avec-anim) { scroll-behavior: auto; }
  html:not(.avec-anim) *, html:not(.avec-anim) *::before, html:not(.avec-anim) *::after {
    transition-duration: .01ms !important;
    animation: none !important;
  }
}

/* ---------------------------------------------------------------- mobile */

/* Tactile : pas de survol — TRACK ⌖ doit se voir tout seul. */
@media (hover: none) {
  .flux-suivre { opacity: 1; }
}

@media (max-width: 640px) {
  /* HUD serré, avec les zones de sécurité des encoches */
  .hud-haut { padding: max(.9rem, env(safe-area-inset-top)) 1rem .9rem; }
  .hud-bas {
    padding: .9rem 1rem max(.9rem, env(safe-area-inset-bottom));
    font-size: 10px;
    letter-spacing: .12em;
  }
  .marque { font-size: 1rem; letter-spacing: .24em; }
  #btn-son { padding: .45rem .85rem; font-size: 9.5px; letter-spacing: .16em; }

  /* héros : avec l'instrument d'époque, le contenu dépasse un écran de
     téléphone — centré, il glissait sous le HUD. Il part donc du haut. */
  .heros {
    justify-content: flex-start;
    padding-top: calc(5.4rem + env(safe-area-inset-top));
    padding-bottom: 6rem;
  }
  .heros-actions { width: 100%; }
  .cta-billet { flex: 1 1 100%; justify-content: space-between; }
  .cta-radar { flex: 1 1 100%; }
  /* l'adresse du contrat passe sous le radar, et quitte le HUD trop serré */
  .ca-mobile { display: flex; }
  .hud-ca { display: none; }
  .heros-sous { font-size: .98rem; }
  .indice-scroll { bottom: 3.4rem; }

  /* le voyage : plus court au pouce, jalons alternés haut/bas — deux jalons
     voisins ne se marchent jamais dessus, même sur 320 px */
  .voyage { height: 330vh; }
  .jalon { max-width: 15rem; }
  .jalon h3 { font-size: 1.45rem; }
  .jalon p:last-child { font-size: .85rem; }
  .j-1 { top: 12%; left: 6%; }
  .j-2 { right: 6%; bottom: 20%; top: auto; }
  .j-3 { left: 6%; top: 12%; bottom: auto; }
  .j-4 { right: 6%; bottom: 20%; top: auto; }

  /* chapitres */
  .chapitre, .radar, .claims { padding: 4.5rem 1.2rem; min-height: auto; }
  .chap-txt { font-size: .95rem; }
  .billet-infos { grid-template-columns: repeat(2, 1fr); gap: .8rem .6rem; }
  .billet-corps b { font-size: 1.7rem; }

  /* radar */
  .compteurs { gap: 1.3rem; }
  .compteurs b { font-size: 1.6rem; }
  .radar-note { letter-spacing: .16em; }
  .flux-item { font-size: 10.5px; padding: .7rem .8rem; gap: .6rem; }
  #btn-retour-vols {
    bottom: max(3.2rem, calc(env(safe-area-inset-bottom) + 1.2rem));
    /* Pas pleine largeur : il reste du globe de chaque côté, sinon toute
       la bande basse — là où le pouce se pose — n'est plus glissable. */
    width: auto;
    max-width: calc(100% - 2.4rem);
    padding: .85rem 1.4rem;
  }
  /* le bouton de retour prend toute la largeur en bas : la fiche se pose
     au-dessus de lui, en une bande compacte plutôt qu'en colonne */
  #fiche-vol {
    left: 1.2rem;
    right: 1.2rem;
    bottom: max(7.6rem, calc(env(safe-area-inset-bottom) + 5.6rem));
    max-width: none;
    display: flex;
    flex-wrap: wrap;
    gap: .25rem 1rem;
    padding: .7rem .9rem;
    font-size: .68rem;
  }
  #fiche-vol b { flex-basis: 100%; }

  .pied { padding-bottom: 4rem; }
}

/* les tout petits écrans */
@media (max-width: 380px) {
  .instruments { gap: .9rem; flex-wrap: wrap; justify-content: center; }
  .be-gauche { padding: .9rem 1.1rem .85rem; }
  .be-gauche b { font-size: 1.05rem; letter-spacing: .22em; }
  .be-talon { padding: 0 .9rem; }
  .charg-sous { letter-spacing: .2em; }
}

/* ---------------------------------------------------------------- iOS
   LE ZOOM QU'ON N'A PAS DEMANDÉ. Safari agrandit de force la page quand
   on touche un champ dont le texte fait moins de 16 px, et il n'en
   revient pas tout seul : l'écran reste décalé, le globe sort du cadre.
   Aucune option de viewport n'y change quoi que ce soit depuis iOS 10,
   et `maximum-scale` interdirait au passage le zoom à deux doigts, qui
   lui est légitime. La seule parade est la taille du texte saisi : on la
   force à 16 px dès qu'on est au doigt, partout où l'on écrit.
   Les sélecteurs sont nommés un par un parce qu'un `#num-vol` plus haut
   dans le fichier battrait une règle générique. */
@media (pointer: coarse) {
  input, textarea, select { font-size: 16px; }
  #num-vol, #champ-wallet, .scan-champ { font-size: 16px; }
}

/* ------------------------------------------------- le mur des claims
   Le registre vivant en bas de page. Même vocabulaire que le flux du
   radar, mais une liste à part : ici on ne montre pas des trajets, on
   montre des gens — masqués — et ce qu'ils ont reçu. */
/* La section prend la mise en page des chapitres — même largeur, même
   marge de gauche, même hauteur d'écran : elle s'aligne sur le reste du
   site au lieu de flotter au milieu. */
.claims { position: relative; z-index: 2; }
#mur-claims { display: grid; gap: .6rem; max-width: 46rem; }
.claim-ligne {
  display: grid;
  grid-template-columns: 1fr auto;
  gap: .3rem 1rem;
  width: 100%;
  padding: .85rem 1.1rem;
  /* Un panneau PLEIN, pas le verre du reste du site : ces lignes se
     lisent par-dessus la planète, et le 4 % de blanc habituel laissait
     passer les continents au milieu des adresses. */
  background: rgba(6, 10, 18, .82);
  backdrop-filter: blur(10px);
  border: 1px solid var(--trait);
  border-left: 2px solid var(--hud);
  border-radius: 12px;
  color: var(--texte);
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: .12em;
  text-align: left;
  cursor: pointer;
  animation: flux-entre .5s ease both;
  transition: border-color .2s, background .2s, translate .2s;
}
.claim-ligne:hover { border-color: var(--hud-25); background: rgba(14, 30, 22, .88); translate: 2px 0; }
.claim-qui { color: var(--hud); }
.claim-route { color: var(--sourd); font-size: 10px; }
/* La colonne est OBLIGATOIRE ici : une case qui fixe sa ligne est posée
   AVANT les autres par la grille, et sans colonne elle prenait la
   première — l'état passait à gauche et le reste à droite. */
.claim-etat {
  grid-column: 2;
  grid-row: 1 / 3;
  align-self: center;
  color: var(--sourd);
  font-size: 9.5px;
  text-align: right;
}
.claim-largue .claim-etat { color: var(--hud); }
/* l adresse est sous le seuil de detention : on le dit en ambre, la teinte
   que le site reserve deja a ce qui attend (flux-prevu, ep-cloture). */
.claim-attente { border-left-color: var(--ambre); }
.claim-attente .claim-etat { color: var(--ambre); }
/* la ligne d'exemple : la forme exacte de ce qui s'écrira, en sourdine */
.claim-exemple { border-left-color: var(--trait); opacity: .72; cursor: default; }
.claim-exemple:hover { translate: 0; background: rgba(6, 10, 18, .82); border-color: var(--trait); }
.claims-note {
  margin: 1.2rem 0 0;
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: .2em;
  color: var(--sourd);
}
@media (max-width: 640px) {
  .claim-ligne { grid-template-columns: 1fr; }
  .claim-etat { grid-column: auto; grid-row: auto; text-align: left; }
}

/* ------------------------------------------------------- LE BANDEAU DU BAS
   Une bande FINE, fixe, qui ne bouge pas : l'univers dans lequel ce
   projet se place — ce qu'on suit dans le ciel et ce qu'on distribue.
   Les marques sont dessinées ici, en SVG monochrome : aucun fichier de
   marque copié, aucune requête vers un tiers, et le trait suit la
   palette du cockpit au lieu de plaquer huit chartes graphiques.
   La mention « not affiliated » n'est pas une précaution de style :
   aucune de ces maisons n'est partenaire, et le bandeau ne doit pas
   laisser croire le contraire. */
:root { --bandeau-h: 42px; }

.bandeau {
  position: fixed;
  left: 0; right: 0; bottom: 0;
  z-index: 52;
  height: var(--bandeau-h);
  /* Trois colonnes, celle du milieu au centre de l'ÉCRAN : le libellé de
     gauche ne pousse plus la rangée de logos vers la droite, et la
     colonne fantôme de droite lui répond. Avec un simple flex, les logos
     se décalaient de la largeur du libellé. */
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  gap: 1.2rem;
  padding: 0 1.2rem;
  background: rgba(4, 6, 11, .82);
  backdrop-filter: blur(10px);
  border-top: 1px solid var(--trait);
  font-family: var(--mono);
  font-size: 9.5px;
  letter-spacing: .2em;
  color: var(--sourd);
  transition: opacity .4s ease;
}
.bandeau-titre { color: var(--hud); white-space: nowrap; justify-self: start; }


/* Le rail : une seule ligne, jamais deux, et il se serre avant de
   déborder — le bandeau doit rester fin quoi qu'il arrive. */
.bandeau-rail {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: clamp(.9rem, 2.6vw, 2.2rem);
  min-width: 0;
  overflow: hidden;
}
.bandeau-marque {
  display: inline-flex;
  align-items: center;
  gap: .4rem;
  white-space: nowrap;
  opacity: .55;
  transition: opacity .25s ease, color .25s ease;
}
.bandeau-marque:hover { opacity: 1; color: var(--hud); }
/* Les logos sont des fichiers de marque, avec leurs couleurs propres.
   Sur une bande de nuit, huit chartes côte à côte se battent : on les
   ramène tous au blanc, ce qui est un usage monochrome courant et rend
   la rangée lisible. L'opacité fait le reste, et le survol rend sa
   présence à la marque visée. */
.bandeau-marque img {
  display: block;
  height: 16px;
  width: auto;
  max-width: 108px;
  filter: brightness(0) invert(1);
}
/* Les proportions n'ont rien à voir d'une marque à l'autre : un insigne
   rond et un mot long ne se règlent pas à la même hauteur. On corrige à
   l'œil, marque par marque. */
.m-nasa img { height: 13px; }   /* le « worm » : un mot, pas un insigne */
.m-starlink img { height: 25px; }   /* mot minuscule sous la marque */
.m-rocketlab img { height: 20px; }
.m-boeing img { height: 17px; }
.m-robinhood img { height: 15px; }
/* Firefly n'a pas de logo librement diffusé : son nom, dans notre fonte */
.bandeau-mot { font-size: 13px; letter-spacing: .22em; }

/* La ligne HUD du bas se relève d'autant : les deux ne se marchent pas
   dessus. */
.hud-bas { padding-bottom: calc(1.4rem + var(--bandeau-h)); }

/* En suivi de vol, tout s'efface pour le globe — le bandeau s'estompe
   sans disparaître, la page garde son cadre. */
html.suivi .bandeau { opacity: .3; }

@media (max-width: 680px) {
  :root { --bandeau-h: 38px; }
  .bandeau {
    grid-template-columns: 1fr;   /* plus de libellé : la rangée prend tout */
    gap: .8rem;
    padding: 0 .8rem;
    font-size: 8.5px;
    letter-spacing: .14em;
  }
  .bandeau-titre { display: none; }
  .bandeau-rail { gap: .5rem; }   /* cinq marques dans 390 px, sans coller aux bords */
  .bandeau-marque img { height: 14px; }
  .m-starlink img { height: 22px; }
  .m-rocketlab img { height: 17px; }
  .m-nasa img { height: 11px; }
  .bandeau-mot { font-size: 11px; }
  /* sur un téléphone, on garde les trois RWA et les deux demandés :
     mieux vaut cinq marques lisibles que huit serrées */
  .bandeau-marque:nth-child(n+6) { display: none; }
}

/* ---- LES DONS, sous le mur des claims. Même panneau plein que les lignes
   de claims : ça se lit par-dessus la planète. */
.dons-panneau {
  max-width: 46rem;
  padding: 1.1rem 1.2rem 1rem;
  background: rgba(6, 10, 18, .82);
  backdrop-filter: blur(10px);
  border: 1px solid var(--trait);
  border-left: 2px solid var(--hud);
  border-radius: 14px;
}
.dons-grille {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(9rem, 1fr));
  gap: 1rem 1.4rem;
  margin-bottom: 1rem;
}
.dons-grille div { display: grid; gap: .25rem; }
.dons-grille span {
  font-family: var(--display);
  font-size: clamp(1.15rem, 4vw, 1.7rem);
  font-weight: 600;
  letter-spacing: -.01em;
  font-variant-numeric: tabular-nums;
}
.dons-grille i {
  font-style: normal;
  font-family: var(--mono);
  font-size: 9.5px;
  letter-spacing: .18em;
  color: var(--sourd);
}
.dons-liste { margin: 0; padding: 0; list-style: none; display: grid; gap: .45rem; }
.dons-liste li {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: .4rem .9rem;
  padding-top: .5rem;
  border-top: 1px solid var(--trait);
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: .12em;
  color: var(--sourd);
}
.dons-liste b { color: var(--texte); font-weight: 500; font-variant-numeric: tabular-nums; }
.dons-liste code { font-size: 9.5px; opacity: .75; word-break: break-all; }
.dons-liste a { color: var(--hud); text-decoration: none; margin-left: auto; }
.dons-liste a:hover { text-decoration: underline; }
