:root {
  /* Couleurs de la marque : les mêmes en thème clair et en thème sombre. La palette du logo de
     Moon Bloom Village : prune (cadres, encre), mauve (filets), pétale (fenêtres), rose (sélection),
     pervenche (boutons principaux), lavande (boutons secondaires). */
  --color-sun: #d074d6;      /* (le rose des fleurs du logo : la sélection, le focus) */
  --color-sun-dark: #a94db0;
  --color-leaf: #4f8a3d;
  --color-leaf-dark: #386b2a;
  --color-earth: #3a2a55;
  --color-earth-rgb: 58, 42, 85; /* pour rgba(var(--color-earth-rgb), …) */
  --color-ink: #2a1f3d;   /* encre des bulles et étiquettes posées sur la carte */
  --color-tomato: #c1442e; /* pastilles « à faire » de la carte */

  /* Les fenêtres et les cartes flottantes (les noms « bois » datent du premier thème) (mêmes couleurs dans les deux thèmes). */
  --wood-ink: #3a2a55;       /* texte sur le bois */
  --wood-dark: #1e1530;      /* cuir du Livre, contours sombres */
  --wood-light: #9673a7;     /* filet clair intérieur */
  --wood-glow: rgba(150, 115, 167, 0.9);
  --wood-cream: #fbf3ff;     /* fond des cartes dans le bois */
  --wood-paper: #f1e3f7;     /* fond des boutons dans le bois */
  --wood-bg-rgb: 251, 243, 255;
  --prune: #3a2a55;            /* bandeaux de titre, enseignes */
  --rose: #d074d6;             /* ce qui est choisi : onglet, jour, outil */
  --rose-pale: #f0d4f2;
  --pervenche-filet: #7480d6;  /* le filet clair du bouton principal (--accent, pervenche) */
  --lavande: #b2bfff;          /* les boutons secondaires */
  --lavande-filet: #dfe4ff;
  --lavande-encre: #2a2f5e; /* fond crème, rgba(var(--wood-bg-rgb), …) */

  /* Thème clair (contrastes AA mesurés : texte ≥ 4,5:1, contours ≥ 3:1 ; vert et rouge un
     peu plus foncés que la marque, ambre lisible pour les pastilles). */
  --bg: #f8f2fb;
  --bg-elevated: #ffffff;
  --bg-header: #f4e9f9;
  --bg-muted: #efe4f4;
  --text: var(--color-ink);
  --text-muted: #6e5a80;
  --border: #dccbe6;
  --accent: #444f9f;
  --accent-contrast: #ffffff;
  --accent-secondary: var(--color-sun);
  --danger: #b23a25;
  --danger-contrast: #ffffff;
  --warn-text: #855400;
  --focus: #444f9f;
  --shadow: 0 1px 3px rgba(35, 26, 40, 0.12);
  --radius: 12px;
  --inv-icon-bg: #ffffff;

  /* Mise en page : --dock, ce qui reste en bas de l'écran (la zone sûre des téléphones à
     encoche) ; --menu-tab, la languette du menu latéral ; --header-h, plus de bandeau en
     haut : la carte occupe tout l'écran. */
  --dock: env(safe-area-inset-bottom, 0px);
  --menu-tab: 22px;
  --header-h: 0px;

  /* Empilement (z-index) des couches posées sur la page, du bas vers le haut. Les z-index
     plus petits (2, 3, 6) qui restent dans le fichier sont locaux à une carte ou au Livre. */
  --z-stage: 5;        /* #farm-stage, #map-stage : la carte en plein écran */
  --z-debug: 40;       /* #god-bar (Options, god mode) */
  --z-hud: 45;         /* .player-card (à gauche) et .hud (à droite) : jamais l'un sur l'autre */
  --z-fab: 50;         /* .sleep-fab (à droite) et .tool-bar (au milieu) : côte à côte */
  --z-menu: 55;        /* .side-menu, au-dessus des boutons flottants */
  --z-banner: 60;      /* .consent-banner (en bas) et .tuto (la bulle, au-dessus du bandeau) */
  --z-window: 90;      /* .window-layer : fenêtres de la carte */
  --z-test: 95;        /* .test-panel (le mode test), au-dessus des fenêtres */
  --z-hud-over: 95;    /* la carte flottante, estompée, par-dessus une fenêtre ouverte */
  --z-modal: 100;      /* .modal-backdrop (#modal-root) : toujours au-dessus des fenêtres */
  --z-toast: 200;      /* #toast-root : les messages, tout en haut */
}

@media (prefers-color-scheme: dark) {
  :root {
    --bg: #19161a;
    --bg-elevated: #211d24;
    --inv-icon-bg: #322c36;
    --bg-header: #241c28;
    --bg-muted: #252028;
    --text: #e9e1ee;
    --text-muted: #aa9cb2;
    --border: #332a38;
    --accent: #9aa3ee;
    --accent-contrast: #141833;
    --accent-secondary: var(--color-sun);
    --danger: #ea7a61;
    --danger-contrast: #2a0d06;
    --warn-text: var(--color-sun);
    --focus: var(--color-sun);
    --shadow: 0 1px 3px rgba(0, 0, 0, 0.4);
  }
}

* { box-sizing: border-box; }

html, body {
  margin: 0;
  padding: 0;
  background: var(--bg);
  color: var(--text);
  /* la police du jeu (assets/police_dialogue.woff, scripts/police/police_dialogue.py), partout ;
     sans gras ni italique fabriqués. Ses lettres sont plus grandes que celles d'une police
     ordinaire de même taille : font-size-adjust les ramène à la hauteur d'x de l'interface
     (texte de 16 px → lettres de 12 px, un pixel de la police = 1,5 px) ; les fenêtres
     (.modal) gardent leurs tailles exactes, 16 et 24 px. */
  font-family: 'Ferme Dialogue', -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
  font-synthesis: none;
  font-size-adjust: ex-height 0.47;
}
input, select, textarea { font-family: inherit; }

/* La configuration d'une nouvelle partie (écran « Ta famille », js/ui/stage.js) : rien que ses
   fenêtres (#modal-root), les messages et le bandeau des traceurs ; ni carte ni interface du jeu. */
body.configuration > :not(#modal-root, #toast-root, #consent-banner, script) { display: none !important; }

/* Le masquage du défilement horizontal est sur html seul : avec overflow sur html ET body,
   body devient un conteneur de défilement et le bandeau « sticky » ne reste plus en haut.
   Le zoom à deux doigts reste permis (pas de maximum-scale dans jeu.html) ; le double appui
   ne zoome pas la page (touch-action: manipulation, ici et sur les boutons : un double appui
   rapide reste deux appuis). Les cartes (#farm-stage, #map-stage : touch-action: none)
   gèrent elles-mêmes tous leurs gestes. */
html {
  overflow-x: hidden;
  touch-action: manipulation;
}

body { padding-bottom: calc(88px + var(--dock)); } /* menu du bas + bouton « Zzz » : la fin du contenu passe au-dessus du bouton */

button {
  font-family: inherit;
  font-size: 1rem;
  touch-action: manipulation;
}

.icon-btn {
  min-width: 44px;
  min-height: 44px;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  background: var(--bg-elevated);
  color: var(--text);
  font-size: 1.2rem;
  display: flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
}

.icon-btn:active { transform: translateY(1px); }

main {
  padding: 16px;
  max-width: 720px;
  margin: 0 auto;
}

/* Menu latéral rabattable, à gauche (il remplace le menu du bas) : les icônes les unes
   au-dessus des autres, dans le cadre bois des cartes flottantes. Fermé, il glisse hors de
   l'écran et n'en dépasse que sa languette (triangle en pixel art pointé vers la droite). */

.side-menu {
  position: fixed;
  left: 0;
  top: 50%;
  z-index: var(--z-menu);
  display: flex;
  align-items: center;
  transform: translate(calc(-100% + var(--menu-tab)), -50%);
  transition: transform 0.2s ease-out;
}
.side-menu.open { transform: translate(0, -50%); }
@media (prefers-reduced-motion: reduce) { .side-menu { transition: none; } }

.bottom-nav {
  display: flex;
  flex-direction: column;
  gap: 2px;
  padding: 6px 6px 6px calc(6px + env(safe-area-inset-left));
  background: rgba(var(--wood-bg-rgb), 0.82);
  border: 3px solid var(--color-earth);
  border-left: 0;
  border-radius: 0 8px 8px 0;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 2px 6px rgba(0, 0, 0, 0.3);
}
.side-menu:not(.open) .bottom-nav { visibility: hidden; transition: visibility 0s 0.2s; }

.nav-btn {
  position: relative;
  width: 52px;
  height: 52px;
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 0;
  border: 2px solid transparent;
  border-radius: 6px;
  background: transparent;
  color: var(--wood-ink);
  font: inherit;
  cursor: pointer;
}
.nav-btn.active { background: rgba(var(--color-earth-rgb), 0.22); border-color: var(--color-earth); }
.nav-btn:active { transform: translateY(1px); }
.nav-icon { position: relative; font-size: 1.6rem; line-height: 1; }
.nav-label { position: absolute; width: 1px; height: 1px; overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; } /* icônes seules : le nom est dans l'infobulle */

/* La languette : collée au bord droit du menu, elle dépasse seule de l'écran quand il est fermé. */
.side-tab {
  position: relative;
  width: var(--menu-tab);
  height: 56px;
  margin-left: -3px; /* recouvre la bordure du menu : un seul cadre */
  padding: 0;
  display: grid;
  place-items: center;
  background: rgba(var(--wood-bg-rgb), 0.88);
  border: 3px solid var(--color-earth);
  border-left: 0;
  border-radius: 0 8px 8px 0;
  box-shadow: inset -2px 0 0 var(--wood-glow), 2px 2px 4px rgba(0, 0, 0, 0.3);
  cursor: pointer;
}
.side-tab::after { content: ""; position: absolute; inset: -6px -16px -6px 0; } /* zone d'appui de 44 px environ */
.side-tab-arrow { fill: #4a2c5b; transition: transform 0.2s; }
.side-menu.open .side-tab-arrow { transform: scaleX(-1); } /* ouvert : le triangle montre le sens de la fermeture */
.side-tab:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
.side-tab-badge {
  position: absolute;
  top: -8px;
  right: -8px;
  min-width: 18px;
  padding: 0 4px;
  border-radius: 999px;
  background: var(--danger);
  color: var(--danger-contrast);
  font-size: 0.7rem;
  font-weight: 700;
  line-height: 18px;
  text-align: center;
}

.nav-badge {
  position: absolute;
  top: -6px;
  right: -12px;
  min-width: 18px;
  padding: 0 5px;
  border-radius: 999px;
  background: var(--danger);
  color: var(--danger-contrast);
  font-size: 0.7rem;
  font-weight: 700;
  line-height: 18px;
  text-align: center;
}

.ferme-links {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  margin: 4px 0 12px;
}

.ferme-link {
  flex: 1 1 auto;
  min-height: 44px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  padding: 0 14px;
  border-radius: 999px;
  border: 1px solid var(--border);
  background: var(--bg-muted);
  color: var(--text);
  font: inherit;
  font-weight: 600;
  cursor: pointer;
}

.notif-list {
  list-style: none;
  margin: 12px 0 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 8px;
}

.notif {
  display: flex;
  align-items: center;
  gap: 12px;
  width: 100%;
  min-height: 44px;
  padding: 10px 14px;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  border-left-width: 5px;
  background: var(--bg-muted);
  color: var(--text);
  font: inherit;
  text-align: left;
  cursor: pointer;
}

.notif.p1 { border-left-color: var(--danger); }
.notif.p2 { border-left-color: var(--color-sun-dark); }
.notif.p3 { border-left-color: var(--accent); }
.notif-icon { font-size: 1.4rem; }
.notif-text { flex: 1 1 auto; min-width: 0; font-weight: 600; }
.notif-go { color: var(--text-muted); font-size: 1.4rem; }
.notif-empty { padding: 12px 0; }

/* Version 1.3 : le courrier. Une lettre non lue se remarque ; la lettre ouverte est une
   feuille de papier (mêmes couleurs en thème clair et en thème sombre). */
.notif.mail { border-left-color: #7d479c; }
.notif.mail.lu { opacity: 0.8; }
.notif.mail:not(.lu) { background: #f1e2f9; color: #291a32; border-color: #aa80c3; border-left-color: #7d479c; }
.notif.mail:not(.lu) .notif-where { color: #523c5f; }
.mail-new { display: inline-block; margin-left: 8px; padding: 1px 8px; border-radius: 999px; background: #7d479c; color: #ffffff; font-size: 0.72rem; font-weight: 700; vertical-align: middle; }
.mail-title { margin-top: 18px; }
.modal.letter { background: #f2e8f8; color: #291a32; border: 1px solid #c1abce; }
.modal.letter h2 { color: #291a32; }
.letter-place { margin: 0 0 4px; text-align: right; font-style: italic; color: #523c5f; }
.letter-body { margin: 10px 0; font-family: inherit; font-size: 1.02rem; line-height: 1.55; }
.letter-body p { margin: 0 0 10px; }
.letter-sign { margin: 0 0 14px; text-align: right; font-family: inherit; font-style: italic; font-size: 1.05rem; }
.letter-gifts { display: flex; flex-direction: column; gap: 4px; margin-bottom: 14px; padding: 10px 12px; border: 1px dashed #7d479c; border-radius: var(--radius); background: #f6eefb; }
.letter-gifts .muted { color: #523c5f; }
.letter-gift-list { font-size: 1.05rem; font-weight: 700; }

.panel {
  background: var(--bg-elevated);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  padding: 20px 16px;
}

.panel h2 {
  margin: 0 0 8px;
  font-size: 1.2rem;
}

.panel p.hint {
  color: var(--text-muted);
  margin: 0;
}

.btn {
  min-height: 44px;
  padding: 0 18px;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  background: var(--bg-muted);
  color: var(--text);
  cursor: pointer;
  font-weight: 600;
}

.btn.primary {
  background: var(--accent);
  border-color: var(--accent);
  color: var(--accent-contrast);
}

.btn.danger {
  background: var(--danger);
  border-color: var(--danger);
  color: var(--danger-contrast);
}

/* FLU-38 : action rare et destructrice, en contour seulement */
.btn.danger-outline {
  background: transparent;
  border: 2px solid var(--danger);
  color: var(--danger);
}

.btn:disabled {
  opacity: 0.5;
  cursor: not-allowed;
}

.row {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  align-items: center;
}

.stack { display: flex; flex-direction: column; gap: 12px; }

textarea, input[type="text"], input[type="email"] {
  width: 100%;
  min-height: 44px;
  padding: 10px;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  background: var(--bg-muted);
  color: var(--text);
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 0.85rem;
}

.modal-backdrop {
  position: fixed;
  inset: 0;
  background: rgba(0, 0, 0, 0.45);
  display: flex;
  align-items: flex-end;
  justify-content: center;
  z-index: var(--z-modal);
  padding: 0;
}

@media (min-width: 640px) {
  .modal-backdrop { align-items: center; padding: 16px; }
}

.modal {
  background: var(--bg-elevated);
  border-radius: var(--radius) var(--radius) 0 0;
  width: 100%;
  max-width: 480px;
  max-height: 85vh;
  overflow-y: auto;
  padding: 20px 16px 28px;
  box-shadow: var(--shadow);
}

/* Essai : la police dessinée à la main (scripts/police/police_dialogue.py) dans les fenêtres de
   dialogue. Un pixel du dessin fait 2 px de l'écran (16 px), 3 dans les titres (24 px) : des tailles
   entières, pour des lettres nettes. Pas de gras ni d'italique imités (la police n'en a
   pas) ; les emojis et les caractères absents de la police passent à la suivante. */
@font-face {
  font-family: 'Ferme Dialogue';
  src: url('../assets/police_dialogue.woff') format('woff');
  font-display: swap;
}
.modal {
  font-family: 'Ferme Dialogue', -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
  font-synthesis: none;
  font-size-adjust: none;
  line-height: 1.5;
}
.modal :is(p, li, span, div, strong, b, em, small, label, button, input, select, textarea, td, th, summary, a, h3, h4) { font-family: inherit; font-size: 16px; font-weight: normal; font-style: normal; }
.modal :is(h1, h2, .item-title strong),
.modal :is(h1, h2, .item-title strong) * { font-size: 24px; font-weight: normal; }
.modal .item-icon { font-size: 2.6rem; }

/* Version 1.1 : fenêtre « Modifier » d'un membre de la famille, et menu du Moulin. */
.member-name { overflow-wrap: anywhere; }
.member-preview {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 10px 12px;
  margin-bottom: 12px;
  border: 1px solid var(--border);
  border-radius: var(--radius);
  background: var(--bg-muted);
  font-size: 1.15rem;
}
.member-preview .portrait-emoji { font-size: 2.6rem; }
.member-field { gap: 6px; }
.member-modal input.member-input {
  font-family: inherit;
  font-size: 1.05rem;
}
.choice-row { gap: 8px; flex-wrap: wrap; }
.choice-btn { flex: 1 1 120px; gap: 8px; }
.choice-emoji { font-size: 1.5rem; line-height: 1; }
.choice-btn.active {
  border-color: var(--accent);
  box-shadow: 0 0 0 2px var(--accent);
  font-weight: 700;
}
.choice-btn:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
.mill-stock { display: flex; flex-wrap: wrap; gap: 6px 18px; font-size: 1.05rem; }

/* Version 1.2 : composer la famille, animaux de compagnie. */
.family-edit-btn { margin: 0 0 8px; }
.ration-title-end { gap: 6px; align-items: center; flex-wrap: nowrap; }
.ration-title .num { white-space: nowrap; }
.help-title { display: flex; align-items: center; justify-content: space-between; gap: 8px; }
.family-add { gap: 8px; flex-wrap: wrap; margin: 10px 0 4px; }
.family-add .btn { flex: 1 1 150px; }
.member-leave { margin-top: 14px; padding-top: 12px; border-top: 1px solid var(--border); gap: 6px; }
.pet .portrait-emoji { font-size: 2rem; }

@media (min-width: 640px) {
  .modal { border-radius: var(--radius); }
}

.modal h2 {
  margin-top: 0;
}

.modal-close {
  float: right;
}

/* Le panneau du mode test (js/ui/testmode.js) : par-dessus la carte et les onglets, ouvert par
   « 🧪 Test » du menu latéral, fermé par son ✕ ; il défile seul. */
.test-panel {
  position: fixed;
  z-index: var(--z-test);
  top: calc(8px + env(safe-area-inset-top));
  right: 8px;
  bottom: calc(8px + env(safe-area-inset-bottom));
  width: min(560px, calc(100vw - 16px));
  overflow-y: auto;
  overscroll-behavior: contain;
  border: 1px dashed var(--border);
  border-radius: var(--radius);
  padding: 8px 12px 16px;
  background: var(--bg-muted);
  box-shadow: 0 4px 16px rgba(0, 0, 0, 0.35);
}
.test-panel[hidden] { display: none; }
.test-panel-head { position: sticky; top: -8px; z-index: 1; display: flex; align-items: center; justify-content: space-between; gap: 8px; padding: 8px 0; background: var(--bg-muted); }
.test-panel-head h2 { margin: 0; font-size: 1.1rem; }
.test-panel #test-qty { width: 5em; }
.test-panel details summary {
  cursor: pointer;
  font-weight: 600;
  padding: 8px 0;
  min-height: 44px;
  display: flex;
  align-items: center;
}

.state-dump {
  white-space: pre-wrap;
  word-break: break-all;
  font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
  font-size: 0.75rem;
  background: var(--bg-elevated);
  border: 1px solid var(--border);
  border-radius: var(--radius);
  padding: 10px;
  max-height: 260px;
  overflow-y: auto;
}

/* ---------- Lot 1 : cartes, appareils, interrupteurs, Dormir ---------- */

.cards {
  display: grid;
  grid-template-columns: 1fr;
  gap: 12px;
}

@media (min-width: 640px) {
  .cards { grid-template-columns: 1fr 1fr; }
}

.card {
  display: flex;
  flex-direction: column;
  gap: 8px;
  text-align: left;
  width: 100%;
  min-width: 0;
  padding: 14px 16px;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  background: var(--bg-muted);
  color: var(--text);
  font: inherit;
}

button.card { cursor: pointer; min-height: 44px; }
button.card:active { transform: translateY(1px); }

.card-title {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  font-weight: 700;
  font-size: 1.05rem;
}

.card-title .chevron { color: var(--text-muted); font-weight: 400; }

.big {
  font-size: 1.4rem;
  font-weight: 700;
  font-variant-numeric: tabular-nums;
}

.muted { color: var(--text-muted); font-size: 0.9rem; }

/* ---------- bandeau de choix sur le suivi ---------- */
.consent-banner {
  position: fixed;
  left: 0; right: 0; bottom: 0;
  z-index: var(--z-banner);
  padding: 14px 16px calc(14px + env(safe-area-inset-bottom));
  background: var(--bg-elevated);
  color: var(--text);
  border-top: 1px solid var(--border);
  box-shadow: 0 -2px 10px rgba(35, 26, 40, 0.15);
  display: flex;
  flex-direction: column;
  gap: 10px;
}
a.btn { display: inline-flex; align-items: center; text-decoration: none; }
.consent-banner p { margin: 0; font-size: 0.92rem; line-height: 1.45; }
.consent-banner a { color: var(--accent); font-weight: 600; }
.consent-banner .row .btn { flex: 1; }
@media (min-width: 720px) {
  .consent-banner { flex-direction: row; align-items: center; justify-content: center; gap: 24px; }
  .consent-banner p { max-width: 640px; }
  .consent-banner .row .btn { flex: none; min-width: 120px; }
}
.num { font-variant-numeric: tabular-nums; }

.alert {
  color: var(--danger);
  font-weight: 600;
  font-size: 0.9rem;
}

.chip {
  display: inline-flex;
  align-items: center;
  min-height: 24px;
  padding: 0 10px;
  border-radius: 999px;
  border: 1px solid var(--border);
  background: var(--bg-elevated);
  font-size: 0.85rem;
  font-weight: 600;
  white-space: nowrap;
}

.chip.panne { background: var(--danger); border-color: var(--danger); color: var(--danger-contrast); }
.chip.warn { border-color: var(--danger); color: var(--danger); }
.chip.res.manque { border-color: var(--danger); color: var(--danger); }

.visually-hidden {
  position: absolute;
  width: 1px;
  height: 1px;
  overflow: hidden;
  clip: rect(0 0 0 0);
  white-space: nowrap;
}

.bar {
  display: block;
  height: 10px;
  border-radius: 999px;
  background: var(--bg-elevated);
  border: 1px solid var(--border);
  overflow: hidden;
}

.bar-fill {
  display: block;
  height: 100%;
  background: var(--accent);
}

.bar-fill.warn { background: #e8b030; }
.bar-fill.bad { background: var(--danger); }

.switch {
  display: inline-flex;
  align-items: center;
  gap: 10px;
  min-height: 44px;
  padding: 0 14px 0 6px;
  border-radius: 999px;
  border: 2px solid var(--danger);
  background: var(--danger);
  color: var(--danger-contrast);
  font-weight: 700;
  cursor: pointer;
}

.switch .knob {
  width: 32px;
  height: 32px;
  border-radius: 50%;
  background: #fff;
  box-shadow: var(--shadow);
}

.switch[aria-checked="true"] {
  background: var(--accent);
  border-color: var(--accent);
  color: var(--accent-contrast);
  flex-direction: row-reverse;
  padding: 0 6px 0 14px;
}

.switch:disabled {
  opacity: 0.55;
  cursor: not-allowed;
}

.switch:focus-visible, .btn:focus-visible, .card:focus-visible, .nav-btn:focus-visible, .ferme-link:focus-visible {
  outline: 3px solid var(--color-sun);
  outline-offset: 2px;
}

.device-actions {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
  align-items: center;
}

.device-actions .btn { padding: 0 12px; }

.device-list { display: flex; flex-direction: column; gap: 12px; margin: 12px 0; }

.screen-head {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-bottom: 12px;
}

.screen-head h2 { margin: 0; }

/* Bouton « Zzz » (Dormir) : rond, flottant en bas à droite de l'écran, au-dessus du menu
   du bas, sur tous les onglets. Désactivé, il affiche les secondes restantes. */
.sleep-fab {
  position: fixed;
  right: calc(12px + env(safe-area-inset-right));
  bottom: calc(var(--dock) + 12px);
  z-index: var(--z-fab);
  display: flex;
  align-items: center;
  gap: 8px;
  pointer-events: none; /* seuls le bouton et la pastille reçoivent les appuis */
}

.sleep-fab > * { pointer-events: auto; }

.sleep-fab .sleep-btn {
  position: relative;
  width: 64px;
  height: 64px;
  padding: 0;
  border: 0;
  border-radius: 50%;
  background: none;
  color: #fff;
  cursor: pointer;
  filter: drop-shadow(0 3px 4px rgba(0, 0, 0, 0.35));
}

/* Le bouton est un dessin (assets/art.png : sleep-on, sleep-off) ; en attente, les secondes
   restantes sont écrites en police pixel par-dessus la lune grise. */
.sleep-fab .sleep-art { --s: 64px; position: absolute; inset: 0; }
.sleep-fab .sleep-btn:active { transform: translateY(2px); }
.sleep-fab .sleep-btn:disabled { cursor: not-allowed; }
.sleep-fab .sleep-btn:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }

.report-list { list-style: none; margin: 12px 0; padding: 0; display: flex; flex-direction: column; gap: 8px; }

.btn.btn-pill { border-radius: 999px; min-width: 44px; }

select {
  min-height: 44px;
  border-radius: var(--radius);
  border: 1px solid var(--border);
  background: var(--bg-muted);
  color: var(--text);
  padding: 0 8px;
  font: inherit;
  max-width: 100%;
}

.toast {
  position: fixed;
  bottom: calc(84px + var(--dock));
  left: 16px;
  right: 16px;
  max-width: 480px;
  margin: 0 auto;
  background: var(--text);
  color: var(--bg);
  padding: 12px 16px;
  border-radius: var(--radius);
  box-shadow: var(--shadow);
  z-index: var(--z-toast);
  text-align: center;
}

/* ---------- Lot 2 : potager, famille, inventaire, aperçu du repas ---------- */

.section-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 8px;
  margin: 4px 0 10px;
}

.section-head h3, .section-title { margin: 0; font-size: 1.05rem; }
.section-title { margin-top: 22px; margin-bottom: 10px; }

.plots {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 8px;
}

@media (min-width: 640px) {
  .plots { grid-template-columns: repeat(3, minmax(0, 1fr)); }
}

.plot { padding: 10px; gap: 8px; }
.plot.mature { border-color: var(--accent); border-width: 2px; }
.plot .btn { width: 100%; padding: 0 8px; font-size: 0.92rem; }
.plot-foot { margin-top: 12px; }
/* Fiche de parcelle (et de frigo) : « #n » en police pixel, le nom, l'icône ; la jauge ;
   une rangée de boutons d'icônes. */
.plot-head { display: flex; align-items: center; gap: 6px; min-width: 0; font-weight: 700; }
.plot-num { flex: none; opacity: 0.7; }
.plot-name { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.plot-ico { flex: none; }
.plot-ico .px { --pxs: 32px; vertical-align: middle; }
.plot.empty .plot-name { color: var(--text-muted); font-weight: 600; }
.plot-btns { display: flex; gap: 6px; }
.plot-btns .btn { flex: 1; min-width: 0; }
.icon-btn-px { padding: 0; min-height: 44px; }
.icon-btn-px .px { --pxs: 32px; vertical-align: middle; }
.icon-btn-px.done { background: var(--bg-muted); box-shadow: inset 0 0 0 2px var(--accent); }
.icon-btn-px:disabled .px { filter: grayscale(0.7); opacity: 0.6; }
.icon-btn-px.done:disabled .px { filter: none; opacity: 1; }

.portraits {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 8px;
  margin: 12px 0;
}

@media (min-width: 640px) {
  .portraits { grid-template-columns: repeat(4, minmax(0, 1fr)); }
}

/* Les cartes des membres, deux par ligne */
.member-rows { list-style: none; margin: 8px 0 12px; padding: 0; display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 6px; }
.member-row { flex-direction: row; flex-wrap: wrap; align-items: center; gap: 8px; padding: 8px; }
.member-row .portrait-emoji { font-size: 1.9rem; flex: none; }
.member-row-text { flex: 1 1 0; min-width: 0; display: flex; flex-direction: column; gap: 2px; }
.member-row-text .chip { align-self: flex-start; }
.faim-jauge { display: flex; align-items: center; gap: 6px; font-size: 0.85rem; }
.faim-jauge .bar { flex: 1 1 auto; min-width: 40px; height: 6px; }
/* en mode modification, les boutons passent sur leur propre ligne, sous le prénom */
.member-row-btns { display: flex; flex-direction: row; gap: 4px; flex: 1 0 100%; justify-content: flex-end; }
.member-row-btns .btn { min-width: 44px; padding: 0 10px; }
.portrait { align-items: flex-start; }
.portrait .btn { width: 100%; padding: 0 8px; font-size: 0.92rem; }
.portrait-emoji { font-size: 2.2rem; line-height: 1.1; }
.portrait .bar { width: 100%; }

.inv-group { margin: 12px 0 20px; }
.inv-group h3 { margin: 0 0 8px; font-size: 1.05rem; }

.inv-row {
  display: flex;
  flex-direction: column;
  gap: 6px;
  padding: 12px 0;
  border-top: 1px solid var(--border);
}

.inv-main {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  font-weight: 600;
}

/* Inventaire en cases, comme un sac de jeu vidéo : le dessin de l'objet, sa quantité en
   police pixel en bas à droite ; un point rouge si une partie périt cette nuit. */
.inv-slots {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(58px, 1fr));
  gap: 6px;
  margin: 4px 0 14px;
}
.inv-slot {
  position: relative;
  aspect-ratio: 1;
  min-width: 0;
  padding: 0;
  display: grid;
  place-items: center;
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  background: rgba(92, 64, 108, 0.22);
  box-shadow: inset 2px 2px 0 rgba(42, 28, 50, 0.35), inset -2px -2px 0 rgba(241, 226, 249, 0.5);
  cursor: pointer;
}
.inv-slot:active { transform: translateY(1px); }
.inv-slot:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 1px; }
.inv-slot-icon { font-size: 2rem; line-height: 1; }
.inv-slot-icon .px { --pxs: 32px; vertical-align: top; } /* 16 px doublés : des pixels entiers */
.inv-slot-qty { position: absolute; right: 3px; bottom: 3px; filter: drop-shadow(1px 1px 0 #1e1424) drop-shadow(-1px 0 0 #1e1424); }
.inv-slot-qty .pxt { --p: 2px; }
.inv-slot.soon { border-color: var(--danger); }
.inv-slot-soon { position: absolute; top: 3px; left: 3px; width: 8px; height: 8px; border-radius: 50%; background: var(--danger); box-shadow: 0 0 0 2px var(--wood-cream); }
.inv-fridge { margin: 0 0 8px; font-weight: 700; }
/* la fenêtre du frigo (js/ui/frigo.js) : ce qui périt cette nuit, la case « + », le tiroir « Ranger au frais » */
.frigo-urgent { margin-bottom: 10px; background: #ecdcf5; border-color: var(--danger); }
.frigo-plus { border-style: dashed; background: rgba(241, 226, 249, 0.35); }
.frigo-plus .inv-slot-icon { font-size: 1.8rem; font-weight: 700; color: var(--color-earth); }
.frigo-plus.on { border-style: solid; border-color: var(--color-sun); }
.inv-slot.choisi { border-color: var(--color-sun); box-shadow: 0 0 0 3px var(--color-sun), inset 2px 2px 0 rgba(42, 28, 50, 0.35); }
.frigo-tiroir { margin: 10px 0; }
.frigo-choisi { display: flex; align-items: center; gap: 10px; margin-top: 8px; }
.frigo-choisi .item-icon { font-size: 2rem; }
.frigo-soon { color: var(--danger); }
.frigo-qte { display: flex; align-items: center; gap: 8px; margin: 6px 0; flex-wrap: wrap; }
.frigo-qte .num { font-size: 1.4rem; min-width: 2ch; text-align: center; }
.frigo-curseur { flex: 1; min-width: 120px; accent-color: var(--color-sun); }
.inv-fridge.warm { color: var(--danger); }
.inv-all { width: 100%; margin-bottom: 8px; }

/* Les onglets de l'inventaire : des icônes seules, en haut de la fenêtre. */
.inv-tabs { display: flex; gap: 6px; flex-wrap: wrap; margin: 0 0 10px; }
.window-head .inv-tabs { margin: 0; flex: 1 1 auto; min-width: 0; align-items: center; gap: 3px; flex-wrap: nowrap; } /* jusqu'à cinq onglets, le « ? » et ✕ sur une ligne */
.inv-tab {
  width: 46px;
  height: 44px;
  display: grid;
  place-items: center;
  padding: 0;
  border: 2px solid transparent;
  border-radius: 6px;
  background: none;
  font-size: 1.6rem;
  line-height: 1;
  cursor: pointer;
}
.inv-tab .px { --pxs: 32px; vertical-align: top; }
.inv-tab.active { border-color: var(--color-earth); background: rgba(var(--color-earth-rgb), 0.22); }
.inv-tab:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 1px; }

/* Fenêtre flottante (l'Inventaire) : centrée, sans toucher les bords, hauteur selon le contenu. */
.window-layer.flottante { align-items: center; padding: 16px 12px; }
.stage-window.flottante {
  height: auto;
  max-height: min(78vh, 560px);
  max-height: min(78dvh, 560px);
  max-width: 460px;
  border-radius: 8px;
}
.stage-window.bois.flottante { border-bottom: 3px solid var(--color-earth); }
.stage-window.flottante .window-head { min-height: 0; padding: 6px 8px 6px 10px; }

/* Le cadre bois des cartes flottantes, commun aux fenêtres de dialogue « bois » (fiche d'un
   objet de l'inventaire…, dont celles des cartes : la gare, les étals, le tronc creux) et aux
   fenêtres de la carte « bois » (Famille…) : les couleurs de l'interface y sont redéfinies (crème et bois, en
   clair comme en sombre) ; cartes, boutons et textes suivent. */
.modal.bois,
.stage-window.bois {
  --bg: rgba(var(--wood-bg-rgb), 0.98);
  --bg-elevated: var(--wood-cream);
  --bg-muted: var(--wood-paper);
  --border: #d9bde6;
  --text: var(--wood-ink);
  --text-muted: #6e5a80;
  /* (le vert, le rouge et l'ambre du thème clair : ceux du sombre, faits pour un fond sombre,
     ne se lisent pas sur le crème) */
  --accent: #444f9f;
  --accent-contrast: #ffffff;
  --danger: #b23a25;
  --danger-contrast: #ffffff;
  --warn-text: #855400;
  background: var(--bg);
  color: var(--text);
  border: 3px solid var(--color-earth);
}
.modal.bois {
  border-radius: 8px;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 8px 24px rgba(0, 0, 0, 0.4);
}
.modal.bois .btn:not(.primary):not(.danger),
.stage-window.bois .btn:not(.primary):not(.danger) { border: 2px solid var(--color-earth); background: var(--lavande); color: var(--lavande-encre); box-shadow: inset 0 0 0 2px var(--lavande-filet); }
.modal.bois .btn.primary,
.stage-window.bois .btn.primary { border: 2px solid var(--color-earth); box-shadow: inset 0 0 0 2px var(--pervenche-filet); }
.item-modal { max-width: 360px; }
.modal-backdrop:has(.item-modal) { align-items: center; padding: 16px; } /* une carte au milieu de l'écran */
.modal-backdrop:has(.item-modal) .modal { border-radius: 8px; }
.modal-backdrop:has(.accueil-modal) { align-items: center; padding: 16px; } /* l'accueil d'une nouvelle partie : au milieu de l'écran */
.modal-backdrop:has(.accueil-modal) .modal { border-radius: 8px; }
.item-head { display: flex; align-items: center; gap: 12px; margin-bottom: 10px; }
.item-icon {
  flex: none;
  width: 64px;
  height: 64px;
  display: grid;
  place-items: center;
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  background: rgba(92, 64, 108, 0.22);
  font-size: 2.6rem;
  line-height: 1;
}
.item-icon .px { --pxs: 48px; vertical-align: top; }
.item-title { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.item-title strong { font-size: 1.15rem; }
.item-lines { list-style: none; margin: 0 0 12px; padding: 0; display: flex; flex-direction: column; gap: 4px; font-size: 0.92rem; }
.item-actions { gap: 6px; flex-wrap: wrap; margin-bottom: 10px; }
.item-actions .btn { flex: 1 1 auto; }

.plant-choice {
  display: flex;
  flex-direction: column;
  align-items: flex-start;
  gap: 2px;
  width: 100%;
  padding: 8px 14px;
  text-align: left;
}

.modal .stack { margin: 12px 0; }

/* ---------- Lot 3 : inventaire par lots, Marché ---------- */

/* Sous-onglets (Maison, Inventaire, Marché) : toujours une seule rangée. À partir de quatre
   onglets sur un téléphone, seul l'onglet ouvert affiche son nom (voir plus bas). */
.subtabs {
  display: flex;
  flex-wrap: nowrap;
  gap: 6px;
  margin: 12px 0 8px;
}

.subtab-btn {
  flex: 1 1 auto;
  min-width: 44px;
  min-height: 44px;
  padding: 0 6px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: 4px;
  border-radius: 999px;
  border: 1px solid var(--border);
  background: var(--bg-muted);
  color: var(--text-muted);
  cursor: pointer;
  font-weight: 600;
  font-size: 0.92rem;
  overflow: hidden;
}

.subtab-btn.active {
  background: var(--accent);
  border-color: var(--accent);
  color: var(--accent-contrast);
}


.subtab-btn:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }

.shop-row {
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 12px 0;
  border-top: 1px solid var(--border);
}

.shop-row > .btn { width: 100%; }
.shop-row.unavailable > :not(.btn) { opacity: 0.7; }

.qty-row { gap: 8px; }
.qty-row .qty { min-width: 2.5ch; text-align: center; font-weight: 700; font-size: 1.1rem; }


/* ---------- Lot 6 : Pâturage et moutons ---------- */

.sheep.ready { border-color: var(--accent); border-width: 2px; background: var(--bg-elevated); }
.sheep .device-actions .btn { flex: 1 1 130px; }

/* ---------- Lot 5 : ateliers (Ferme) et Livre de recette ---------- */

/* Le bloc « En préparation » d'un atelier (js/ui/cuisine.js preparationHtml) : le plat qui cuit, les places
   de la file ; la croix, un petit rond posé dans le coin de sa case. */
.prep-tete { display: flex; justify-content: space-between; align-items: baseline; font-size: 0.85rem; margin: 2px 0 6px; }
.prep-encours { display: flex; align-items: center; gap: 10px; padding: 8px; border: 2px solid #a380b7; border-radius: 10px; background: rgba(242, 229, 250, 0.6); }
.prep-encours.libre { justify-content: center; min-height: 48px; font-size: 0.85rem; }
.prep-ico { position: relative; flex: none; width: 44px; height: 44px; display: grid; place-items: center; font-size: 26px; border: 2px solid #8f69a5; border-radius: 8px; background: #d8c1e6; }
.prep-txt { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 2px; font-size: 0.9rem; }
.prep-txt small { font-size: 0.75rem; opacity: 0.75; }
.prep-file { display: grid; grid-template-columns: repeat(var(--places, 9), minmax(0, 40px)); gap: 6px; margin-top: 8px; }
.prep-place { position: relative; aspect-ratio: 1; max-width: 44px; display: grid; place-items: center; font-size: 18px; border: 2px dashed #b499c4; border-radius: 7px; }
.prep-place.pleine { border-style: solid; border-color: #8f69a5; background: #d8c1e6; }
.prep-croix {
  position: absolute; top: -6px; right: -6px; width: 18px; height: 18px; min-height: 0; padding: 0;
  display: grid; place-items: center; border-radius: 50%; border: 1px solid #f2e5fa;
  background: #8a3020; color: #fff; font-size: 10px; line-height: 1; cursor: pointer;
}
.prep-croix::before { content: ''; position: absolute; inset: -8px; }   /* (une cible plus grande au doigt) */
.prep-place .prep-croix { width: 16px; height: 16px; top: -5px; right: -5px; font-size: 9px; }
.prep-croix:focus-visible { outline: 2px solid var(--accent); outline-offset: 1px; }
.menu-atelier .prep { display: flex; flex-direction: column; gap: 4px; }

/* La grille des recettes (leurs icônes) et la fiche de la recette choisie (renderStationFenetre). */
.plats-grille { display: grid; grid-template-columns: repeat(auto-fill, minmax(66px, 1fr)); gap: 8px; }
.plats-grille .plat-case { max-width: 96px; }
.plat-case {
  position: relative; aspect-ratio: 1; min-height: 0; padding: 0; display: grid; place-items: center;
  border: 2px solid #8f69a5; border-radius: 10px; background: #f2e5fa; box-shadow: 0 2px 0 #a380b7; cursor: pointer;
}
.plat-case .plat-ico { font-size: 30px; line-height: 1; }
.plat-case.non .plat-ico { opacity: 0.45; filter: grayscale(0.35) brightness(1.15); }
.plat-case.non { box-shadow: none; background: #f1e6f7; }
.plat-case.verrou .plat-ico { opacity: 0.35; filter: grayscale(1) brightness(1.2); }
.plat-case.verrou { box-shadow: none; background: #f1e6f7; border-color: #b499c4; }
.plat-cadenas { position: absolute; right: 3px; bottom: 2px; font-size: 12px; }
.plat-case.choisi { border-color: #2f6a2a; box-shadow: 0 0 0 3px #9cc77a; }
/* combien de fois la recette peut partir avec le stock : une pastille ambre au coin haut */
.plat-nombre { position: absolute; top: -6px; right: -6px; min-width: 19px; height: 19px; padding: 0 4px; border-radius: 10px; border: 1px solid #f2e5fa; background: #e9a530; color: #2a1c32; font-size: 11px; line-height: 17px; text-align: center; }
/* les recettes à débloquer regroupées : « 🔒 +n » (un appui les déplie) */
.plat-case.plat-groupe { border-style: dashed; }
.plat-case.plat-groupe .plat-ico { font-size: 20px; opacity: 0.6; filter: none; }
.plat-plus { position: absolute; right: 5px; bottom: 2px; font-size: 11px; color: #5f476d; }
.fiche-recette { margin-top: 10px; padding: 9px 10px; border: 2px solid #a380b7; border-radius: 10px; background: rgba(242, 229, 250, 0.6); }
.fiche-recette h4 { margin: 0 0 2px; font-size: 1rem; font-weight: normal; }
.fiche-recette > p { margin: 0 0 6px; font-size: 0.8rem; }
.fiche-ingr { display: flex; flex-wrap: wrap; gap: 6px; margin-bottom: 8px; }
.fiche-ingr .ingr { display: inline-flex; gap: 4px; padding: 3px 8px; border-radius: 12px; border: 1px solid #9cc77a; background: #e9f1dc; font-size: 0.8rem; }
.fiche-ingr .ingr.manque { border-color: #d98f78; background: #ebdef2; }
.fiche-lancer { display: flex; gap: 8px; align-items: center; }
.fiche-lancer > .btn { flex: 1; }
.fiche-pas { display: inline-flex; align-items: center; gap: 4px; }
.fiche-pas .btn { min-width: 34px; padding-inline: 0; }
.fiche-pas .num { min-width: 22px; text-align: center; }

.recipes {
  display: flex;
  flex-direction: column;
  gap: 12px;
}

.recipe.ready { border-color: var(--accent); border-width: 2px; background: var(--bg-elevated); }
.recipe.unavailable .card-title, .recipe.unavailable .muted { opacity: 0.75; }
.recipe .btn { width: 100%; }

.ingredients {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 3px;
  font-size: 0.95rem;
  font-variant-numeric: tabular-nums;
}

.ingredients .missing { color: var(--danger); font-weight: 600; }

/* ---------- Lot 7 : arbre des technologies et automatisations ---------- */

.chips { display: inline-flex; flex-wrap: wrap; gap: 6px; justify-content: flex-end; }
.branch { margin: 8px 0 22px; }
.branch-head { display: flex; align-items: center; justify-content: space-between; gap: 8px; margin: 0 0 10px; }
.branch-head h3 { margin: 0; font-size: 1.1rem; }
/* FLU-28 : branches repliables */
summary.branch-head { cursor: pointer; list-style: none; min-height: 44px; flex-wrap: wrap; }
summary.branch-head::-webkit-details-marker { display: none; }
summary.branch-head h3::before { content: '▸'; display: inline-block; margin-right: 6px; transition: transform 0.15s; }
.branch[open] > summary.branch-head h3::before { transform: rotate(90deg); }
.branch:not([open]) { margin-bottom: 8px; }
.branch-nodes { display: flex; flex-direction: column; gap: 12px; }
.tech-node .desc { font-size: 0.95rem; }
.tech-node.available { border-color: var(--accent); border-width: 2px; background: var(--bg-elevated); }
.tech-node.owned { border-color: var(--accent); }
.tech-node.locked .card-title, .tech-node.locked .desc { opacity: 0.75; }
.tech-node .btn { width: 100%; }
.prereqs { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 3px; font-size: 0.95rem; }
.prereqs .missing { color: var(--danger); font-weight: 600; }
.level-row { display: flex; flex-direction: column; gap: 6px; padding: 10px 14px; border-radius: var(--radius); border: 1px dashed var(--border); }
.level-row .level-line, .card .level-line { display: flex; align-items: center; justify-content: space-between; gap: 8px; flex-wrap: wrap; font-weight: 600; }
.level-chips { display: flex; flex-wrap: wrap; gap: 6px; }
.level-row .chip { white-space: normal; }
.chip.auto { border-color: var(--accent); color: var(--accent); }
.fridge.cold { border-color: var(--accent); }
.fridge.warm { border-color: var(--danger); border-width: 2px; }
.tree.adult { border-color: var(--accent); }
.tree.free { border-style: dashed; }
.semis-choice { justify-content: flex-start; text-align: left; height: auto; min-height: 44px; padding: 8px 12px; flex-direction: column; align-items: flex-start; gap: 2px; }
.semis-choice > span { display: block; }
.semis-choice[aria-pressed="true"] { border-color: var(--accent); border-width: 2px; }

/* ---------- Lot 9 : chapitres et autonomie ---------- */

.level-check { color: var(--accent); font-weight: 700; }
#levels-title:focus { outline: none; }
/* FLU-30 : progression vers le niveau suivant, sous « Niv. » */
.level-ind { position: relative; overflow: hidden; }
.level-ind-bar { position: absolute; left: 4px; right: 4px; bottom: 3px; height: 3px; border-radius: 2px; background: var(--bg-muted); }
.level-ind-bar > span { display: block; height: 100%; border-radius: 2px; background: var(--accent); }
.chapter-card { border-color: var(--accent); border-width: 2px; background: var(--bg-elevated); margin-bottom: 12px; }
.objectives { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 10px; }
.objective { display: flex; flex-direction: column; gap: 4px; }
.objective-line { display: flex; justify-content: space-between; align-items: baseline; gap: 8px; }
.objective.ok .objective-label { color: var(--accent); font-weight: 700; }
.objective-value { font-variant-numeric: tabular-nums; font-weight: 600; white-space: nowrap; }
.unlock-list { list-style: none; margin: 8px 0 12px; padding: 0; display: flex; flex-direction: column; gap: 6px; }
.unlock-list li { padding: 8px 12px; border-radius: var(--radius); border: 1px solid var(--accent); background: var(--bg-muted); }
.modal h3 { margin: 12px 0 4px; font-size: 1.05rem; }
#chapter-close { margin-top: 16px; }
.chart { display: block; width: 100%; max-width: 480px; height: auto; }
.chart-grid { stroke: var(--border); stroke-width: 1; }
.chart-label { fill: var(--text-muted); font-size: 9px; }
.chart-empty { fill: var(--text-muted); font-size: 10px; }
.chart-bar { fill: var(--accent); }
.chart-target { stroke: var(--danger); stroke-width: 1.5; stroke-dasharray: 4 3; }
.chart-curve { fill: none; stroke: var(--accent); stroke-width: 2; stroke-linejoin: round; }
.chart-raw { fill: none; stroke: var(--text-muted); stroke-width: 1; opacity: 0.55; }
.chart-death { fill: var(--danger); opacity: 0.18; }
.sim-result { display: flex; flex-direction: column; gap: 8px; padding: 10px; background: var(--bg-elevated); border: 1px solid var(--border); border-radius: var(--radius); }
.sim-result p { margin: 0; font-size: 0.85rem; }
.perf-rapport { margin: 0; padding: 10px; max-height: 50vh; overflow: auto; white-space: pre-wrap; word-break: break-word; font-size: 0.75rem; background: var(--bg-elevated); border: 1px solid var(--border); border-radius: var(--radius); user-select: text; }
.perf-rapport[hidden] { display: none; }

/* ---------- Lot 11 : accessibilité (contrastes, focus, cibles de 44 px) ---------- */

/* Contrastes AA mesurés (les couleurs : :root, en haut du fichier) : ambre lisible pour les
   pastilles, anneau de focus visible sur tous les fonds. */
.chip.badge { border-color: var(--warn-text); color: var(--warn-text); }
.chart-bar.full { fill: var(--warn-text); }
.chapter-card.done, .station.busy { border-color: var(--warn-text); }
/* le lot 6 : l'étape de la ferme sous le titre, la récompense du chapitre, le jeu libre */
.chapitre-etape { font-style: italic; }
.chapitre-recompense, .jeu-libre { list-style: none; padding: 0; margin: 6px 0; display: grid; gap: 4px; }
.chapitre-recompense-titre { display: block; margin-top: 6px; }

:where(button, a[href], input, select, textarea, summary, [tabindex]):focus-visible {
  outline: 3px solid var(--focus);
  outline-offset: 2px;
}
/* Une fenêtre sans bouton à mettre en avant prend elle-même le focus (modal.js) : sans anneau. */
#modal-root [role="dialog"][tabindex="-1"]:focus { outline: none; }

.check-row { min-height: 44px; gap: 12px; cursor: pointer; }
.check-row input[type="checkbox"] { width: 24px; height: 24px; margin: 0; accent-color: var(--accent); }

/* ---------- Lot 11 : notifications ---------- */

#toast-root {
  position: fixed;
  left: 16px;
  right: 16px;
  bottom: calc(84px + var(--dock));
  z-index: var(--z-toast);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 8px;
  pointer-events: none;
}

#toast-root .toast {
  position: static;
  width: 100%;
  max-width: 480px;
  margin: 0;
  pointer-events: auto;
  font-weight: 600;
}

#toast-root .toast.alerte {
  background: var(--danger);
  color: var(--danger-contrast);
}

/* Notification qui mène au menu concerné : un bouton, sur toute la largeur. */
#toast-root .toast-link {
  border: 0;
  font: inherit;
  font-weight: 600;
  cursor: pointer;
}
#toast-root .toast-link:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
.toast-go { display: inline-block; margin-left: 4px; font-weight: 800; }

/* ---------- Dessins en pixel art (assets/art.png, js/ui/pixel-art.js) ---------- */

/* Une case de 32×32 de la planche, affichée à la taille --s (64 px : ×2 ; 32 px : ×1).
   --art-sheet et --art-cols sont posés par pixel-art.js (adresse avec empreinte). */
.art {
  --s: 64px;
  display: block;
  width: var(--s);
  height: var(--s);
  flex: none;
  background: var(--art-sheet) no-repeat;
  background-size: calc(var(--art-cols) * var(--s)) auto;
  background-position: calc(var(--ax) * -1 * var(--s)) calc(var(--ay) * -1 * var(--s));
  image-rendering: pixelated;
}
.art-icon { --s: 32px; display: inline-block; vertical-align: -9px; margin-right: 6px; }
.plot-art { margin: 0 auto; }
.card-art-row { display: flex; align-items: flex-end; gap: 10px; }
.egg-art { --s: 32px; }
.art-hidden { visibility: hidden; }

/* Police pixel : chaque glyphe est une case de assets/police.png (rangée 0 sombre, rangée 1
   blanche avec .light). --p : taille d'un pixel. */
.pxt { --p: 3px; --row: 0; display: inline-flex; gap: var(--p); align-items: flex-end; vertical-align: middle; line-height: 0; }
.pxt.light { --row: 1; }
.pxt i {
  display: block;
  width: calc(var(--gw) * var(--p));
  height: calc(var(--font-h) * var(--p));
  background: var(--font-sheet) no-repeat;
  background-size: calc(var(--font-w) * var(--p)) calc(var(--font-h) * 2 * var(--p));
  background-position: calc(var(--gx) * -1 * var(--p)) calc(var(--row) * var(--font-h) * -1 * var(--p));
  image-rendering: pixelated;
}
@media (prefers-color-scheme: dark) { .pxt { --row: 1; } }

/* Jauge en cases : un cadre sombre de 3 px, une case par cran, pleine ou creuse. */
.pxgauge {
  display: flex;
  gap: 3px;
  padding: 3px;
  background: #2e2235;
  box-shadow: inset 0 3px 0 #1b1320;
  height: 21px;
  border-radius: 0;
}
.pxgauge i { flex: 1; background: #544060; box-shadow: inset 0 3px 0 #44324e; }
.pxgauge i.on { background: #5aa83c; box-shadow: inset 0 3px 0 #8cd06a, inset 0 -3px 0 #3d7a2a; }
.pxgauge.full i.on { background: #9352b8; box-shadow: inset 0 3px 0 #f8d878, inset 0 -3px 0 #6c388a; }
.pxgauge.low i.on { background: #c8503a; box-shadow: inset 0 3px 0 #ec8a6e, inset 0 -3px 0 #8a2e22; }
.pxgauge.off i { opacity: 0.55; }

/* ---------- Lot 11 : aide des bâtiments ---------- */

.help-btn {
  min-width: 44px;
  width: 44px;
  padding: 0;
  border-radius: 50%;
  font-weight: 700;
  font-size: 1.1rem;
  line-height: 1;
  flex: none;
}

.card-title .chips { flex-wrap: nowrap; align-items: center; }
.help-list { margin: 8px 0 16px; padding: 0; list-style: none; display: flex; flex-direction: column; gap: 10px; }
.help-list li { padding: 10px 12px; border-radius: var(--radius); background: var(--bg-muted); border: 1px solid var(--border); }
.help-list strong { display: block; margin-bottom: 2px; }
.help-head { display: flex; align-items: center; gap: 12px; }
.help-head h2 { margin: 0; }

/* ---------- Lot 11 : bulles d'aide de la première partie ---------- */

.tuto {
  position: fixed;
  left: 16px;
  right: 16px;
  bottom: calc(118px + var(--dock));
  z-index: var(--z-banner);
  max-width: 560px;
  margin: 0 auto;
  padding: 14px 16px 12px;
  border-radius: var(--radius);
  border: 2px solid var(--accent);
  background: var(--bg-elevated);
  color: var(--text);
  box-shadow: 0 6px 24px rgba(0, 0, 0, 0.25);
}

.tuto::after {
  content: "";
  position: absolute;
  bottom: -9px;
  left: 50%;
  width: 16px;
  height: 16px;
  background: var(--bg-elevated);
  border-right: 2px solid var(--accent);
  border-bottom: 2px solid var(--accent);
  transform: translateX(-50%) rotate(45deg);
}

.tuto.up::after { display: none; }
/* Bulle « Dormir » : calée à droite, la pointe au-dessus du bouton « Zzz » ; elle descend
   près du bouton quand le bandeau de choix sur le suivi n'occupe plus le bas de l'écran. */
.tuto:not(.up) { margin-right: 0; }
body:not(:has(#consent-banner)) .tuto:not(.up) { bottom: calc(86px + var(--dock)); }
.tuto:not(.up)::after { left: auto; right: 16px; transform: rotate(45deg); }
.tuto h2 { margin: 0 0 4px; font-size: 1.05rem; display: flex; justify-content: space-between; gap: 8px; }
.tuto p { margin: 0 0 10px; font-size: 0.95rem; }
.tuto .row { justify-content: flex-end; }
body.has-tuto { padding-bottom: calc(300px + var(--dock)); }

.tuto-target {
  scroll-margin-top: 140px;
  outline: 3px dashed var(--accent);
  outline-offset: 4px;
  border-radius: var(--radius);
  animation: tuto-pulse 1.6s ease-in-out infinite;
}

.more { margin-top: 12px; }
.more > summary { cursor: pointer; min-height: 44px; display: flex; align-items: center; font-weight: 600; }
.more[open] > summary { margin-bottom: 8px; }

.market-help > summary { font-weight: 400; gap: 8px; }

.tuto-ring {
  outline: 3px solid var(--accent);
  outline-offset: 3px;
  animation: tuto-ring 1.2s ease-in-out infinite;
}

/* FLU-20 : l'anneau qui montre l'élément à toucher (immobile si les animations sont réduites) */
@keyframes tuto-ring {
  0%, 100% { outline-offset: 3px; outline-color: var(--accent); }
  50% { outline-offset: 7px; outline-color: color-mix(in srgb, var(--accent) 40%, transparent); }
}

@keyframes tuto-pulse {
  0%, 100% { outline-color: var(--accent); }
  50% { outline-color: transparent; }
}

/* ---------- le didacticiel d'une nouvelle partie (js/ui/didacticiel.js) ----------
   Une bulle de bois en bas de l'écran (en haut quand ce qu'elle montre est en bas), au-dessus
   des fenêtres de la carte ; ce qu'il faut toucher porte un anneau doré qui pulse ; sous le
   hublot, en haut à droite, les compteurs de ce qu'il reste à réunir. */
.didac-bulle {
  position: fixed;
  left: 16px;
  right: 16px;
  bottom: calc(150px + env(safe-area-inset-bottom));
  z-index: var(--z-test);
  max-width: 400px;
  margin: 0 auto;
  padding: 8px 10px 6px;
  --text: var(--wood-ink);
  --text-muted: #5d426c; /* le texte sombre du bois, en clair comme en sombre */
  --accent: #444f9f;
  --danger: #b23a25;
  --warn-text: #4a275e;
  color: var(--text);
  background: rgba(var(--wood-bg-rgb), 0.96);
  border: 3px solid var(--color-earth);
  border-radius: 8px;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 6px 18px rgba(0, 0, 0, 0.3);
  font-family: 'Ferme Dialogue', sans-serif;
  font-size-adjust: none;
  font-size: 14px;
  line-height: 1.35;
}
/* la barre d'outils rangée : la bulle descend à sa place */
body:has(#tool-bar:not(.open)) .didac-bulle:not(.haut):not(.reduite) { bottom: calc(76px + env(safe-area-inset-bottom)); }
/* sur le personnage (au bord de la carte : js/carte/ferme/camera.js stepBulleDidacticiel) : transparente,
   et les appuis passent au travers, sauf sur ses boutons */
.didac-bulle { transition: bottom 0.2s ease-out, opacity 0.2s; }
#didacticiel-root.transparente .didac-bulle:not(.reduite) { opacity: 0.35; pointer-events: none; }
#didacticiel-root.transparente .didac-bulle:not(.reduite) button { pointer-events: auto; }
@media (prefers-reduced-motion: reduce) { .didac-bulle { transition: none; } }
.didac-bulle.haut { bottom: auto; top: calc(var(--player-h, 120px) + 16px + env(safe-area-inset-top)); }
.didac-bulle p { margin: 0 0 4px; }
.didac-bulle b { font-weight: normal; color: var(--color-earth); text-decoration: underline; text-decoration-thickness: 2px; text-underline-offset: 3px; }
.didac-pied { display: flex; flex-wrap: wrap; align-items: center; justify-content: flex-end; gap: 6px 10px; }
.didac-pied .btn { margin-left: auto; }
.didac-pied .muted { font-size: 12px; white-space: nowrap; }
.didac-passer { margin-right: auto; }
.didac-pied .btn { font-size: 14px; min-height: 32px; padding: 4px 12px; }
.didac-passer { flex: none; white-space: nowrap; padding: 2px 0; border: 0; background: none; color: var(--text-muted); font: inherit; font-size: 12px; text-decoration: underline; cursor: pointer; }
.didac-replier { flex: none; min-width: 32px; min-height: 28px; padding: 0 6px; border: 2px solid var(--color-earth); border-radius: 6px; background: transparent; color: var(--wood-ink); font: inherit; font-size: 14px; cursor: pointer; }
/* une fenêtre ouverte : la bulle réduite à une ligne, en bas de l'écran (un appui la déplie) */
.didac-bulle.reduite { bottom: calc(12px + env(safe-area-inset-bottom)); padding: 0; }
.didac-reduite { display: flex; align-items: center; gap: 8px; width: 100%; min-height: 36px; padding: 4px 10px; border: 0; background: none; color: inherit; font: inherit; font-size: 13px; text-align: left; cursor: pointer; }
.didac-reduite-texte { flex: 1; min-width: 0; overflow: hidden; white-space: nowrap; text-overflow: ellipsis; }
.didac-reduite .muted { font-size: 12px; white-space: nowrap; }
.didac-chevron { flex: none; color: var(--color-earth); }
.didac-compteurs {
  position: fixed;
  top: calc(140px + env(safe-area-inset-top));
  right: calc(8px + env(safe-area-inset-right));
  z-index: var(--z-hud);
  display: flex;
  flex-direction: column;
  align-items: flex-end;
  gap: 4px;
  pointer-events: none;
}
.didac-compteur {
  padding: 3px 8px;
  background: rgba(var(--wood-bg-rgb), 0.94);
  border: 2px solid var(--color-earth);
  border-radius: 6px;
  color: var(--wood-ink); /* le texte sombre du bois, en clair comme en sombre */
  font-family: 'Ferme Dialogue', sans-serif;
  font-size-adjust: none;
  font-size: 16px;
  white-space: nowrap;
}
.didac-compteur.ok { border-color: #2f8a3a; background: #d9f2c9; color: #1f5a28; }

/* les objectifs du jour (js/ui/objectifs.js) : une pastille sous l'horloge (sous la boussole quand elle est là),
   le carnet qui s'ouvre en la touchant, et la bulle de « Montre-moi » (celle du didacticiel : .didac-bulle) */
.obj-pastille {
  position: fixed;
  top: calc(140px + env(safe-area-inset-top));
  right: calc(8px + env(safe-area-inset-right));
  z-index: var(--z-hud);
  min-height: 36px;
  padding: 4px 12px;
  background: rgba(var(--wood-bg-rgb), 0.96);
  border: 3px solid var(--color-earth);
  border-radius: 18px;
  color: var(--wood-ink);
  font-family: 'Ferme Dialogue', sans-serif;
  font-size-adjust: none;
  font-size: 16px;
  white-space: nowrap;
  cursor: pointer;
}
.obj-pastille.fini { border-color: #2f8a3a; background: #d9f2c9; color: #1f5a28; }
.obj-carnet {
  position: fixed;
  top: calc(184px + env(safe-area-inset-top));
  right: calc(8px + env(safe-area-inset-right));
  z-index: var(--z-hud);
  width: min(360px, calc(100vw - 16px));
  max-height: calc(100vh - 260px);
  overflow-y: auto;
  padding: 12px 14px;
  background: rgba(var(--wood-bg-rgb), 0.98);
  border: 3px solid var(--color-earth);
  border-radius: 12px;
  color: var(--wood-ink);
  box-shadow: 0 4px 0 rgba(42, 28, 50, 0.3);
}
.obj-carnet h2 { margin: 0; font-size: 19px; }
.obj-intro { margin: 2px 0 8px; font-size: 14px; color: var(--text-muted); }
.obj-liste { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 10px; }
.obj-ligne { display: flex; align-items: center; gap: 8px; }
.obj-case { flex: none; display: grid; place-items: center; width: 24px; height: 24px; border: 2px solid var(--color-earth); border-radius: 6px; background: #fff; color: #fff; font-size: 16px; }
.obj-ligne.fait .obj-case { background: #3d8b3d; border-color: #2f6e2f; }
.obj-icone { flex: none; }
.obj-texte { flex: 1; min-width: 0; display: flex; flex-direction: column; font-size: 15px; }
.obj-texte small { font-size: 12px; color: var(--text-muted); }
.obj-ligne.fait .obj-libelle { color: var(--text-muted); text-decoration: line-through; }
.obj-compte { flex: none; font-size: 15px; }
.obj-ligne.fait .obj-compte { color: #2f6e2f; }
.obj-changer { flex: none; min-width: 36px; min-height: 36px; border: 2px solid var(--color-earth); border-radius: 8px; background: transparent; color: var(--wood-ink); font: inherit; font-size: 18px; cursor: pointer; }
.obj-pied { display: flex; flex-wrap: wrap; align-items: center; gap: 8px 10px; margin-top: 12px; }
.obj-pied .btn { min-height: 40px; }
.obj-recompense { font-size: 13px; }
.obj-fermer { margin-left: auto; min-width: 40px; min-height: 40px; border: 2px solid var(--color-earth); border-radius: 8px; background: transparent; color: var(--wood-ink); font: inherit; cursor: pointer; }
.didac-ring { /* ce qu'il faut toucher brille : une lueur blanche qui respire lentement (pas d'anneau) */
  position: relative;
  z-index: 1;
  border-radius: 10px;
  animation: didac-ring 2s ease-in-out infinite;
}
@keyframes didac-ring {
  0%, 100% { box-shadow: 0 0 8px 3px rgba(255, 255, 255, 0.6), inset 0 0 10px rgba(255, 255, 255, 0.55); filter: brightness(1.05); }
  50% { box-shadow: 0 0 16px 7px rgba(255, 255, 255, 0.95), inset 0 0 14px rgba(255, 255, 255, 0.85); filter: brightness(1.18); }
}
.didac-lueur { /* ce que le didacticiel montre sans le faire toucher (les graines offertes) : la même lueur */
  border-radius: 10px;
  animation: didac-ring 2s ease-in-out infinite;
}
@media (prefers-reduced-motion: reduce) { .didac-ring, .didac-lueur { animation: none; box-shadow: 0 0 12px 5px rgba(255, 255, 255, 0.8); } }
/* pendant le didacticiel : ni l'ancienne bulle d'aide ni la puce du chapitre */
body.didacticiel .stage-chip:not(.hoe):not(.compact), body.didacticiel #tuto-root { display: none; }

/* ---------- Lot 11 : À propos ---------- */

.about-rules { margin: 8px 0 16px; padding-left: 20px; display: flex; flex-direction: column; gap: 6px; }
.about-version { font-variant-numeric: tabular-nums; }

/* ---------- Lot 11 : rendu par tranches et animations ---------- */

/* Chaque tranche de la Ferme est mise à jour à part ; elle n'ajoute aucune boîte. */
.slot { display: contents; }

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after {
    animation: none !important;
    transition: none !important;
    scroll-behavior: auto !important;
  }
}
/* ---------- Carte Phaser : zone entre le bandeau et le menu du bas ---------- */
#farm-stage {
  position: fixed;
  left: 0;
  right: 0;
  top: var(--header-h);
  bottom: var(--dock);
  z-index: var(--z-stage);
  overflow: hidden;
  background: #6a8157;
  touch-action: none; /* le doigt fait glisser la carte, pas la page */
  -webkit-user-select: none;
  user-select: none;
  -webkit-touch-callout: none; /* appui long (citerne) : pas de menu du système */
}
#farm-stage[hidden] { display: none; }
/* La taille réelle du canvas (× densité de l'écran) est gérée par farm-stage.js. */
#farm-stage canvas { display: block; width: 100% !important; height: 100% !important; image-rendering: pixelated; cursor: grab; }
body.has-stage main { display: none; }
/* Une autre carte que la ferme (js/carte/jeu.js : #map-stage), à la place de celle de la ferme ; le reste de l'écran
   (carte du joueur, menu, outils) ne change pas. (La mine, qui s'y affichait, n'est plus : docs/gisements.md.) */
#map-stage { position: fixed; left: 0; right: 0; top: var(--header-h); bottom: var(--dock); z-index: var(--z-stage); overflow: hidden; background: #5d5562; touch-action: none; -webkit-user-select: none; user-select: none; }
#map-stage[hidden] { display: none; }
/* Le même canvas que la ferme (un seul jeu Phaser, js/carte/jeu.js), posé ici pendant l'excursion. */
#map-stage canvas { display: block; width: 100% !important; height: 100% !important; image-rendering: pixelated; }
/* le god mode (Options) : son menu d'actions de test, à gauche sous la carte du joueur (js/ui/hote.js) */
#god-bar { position: fixed; left: 8px; top: calc(var(--player-h, 110px) + 10px); z-index: var(--z-debug); }
#god-bar label { display: flex; align-items: center; gap: 4px; padding: 3px 6px; border-radius: 10px; background: rgba(29, 19, 35, 0.82); color: #eeddf8; font-size: 13px; }
#god-bar select { max-width: 52vw; font: inherit; border-radius: 6px; border: 1px solid #88639d; background: #f5ecfb; color: #281832; padding: 2px 4px; }
#map-stage .map-retour { position: absolute; left: 50%; transform: translateX(-50%); top: calc(var(--player-h, 110px) + 16px); z-index: 6; }

body.has-stage { padding-bottom: 0; }

/* ---------- Fenêtres de la carte : au-dessus de la carte et du menu, sous les fenêtres de #modal-root ---------- */
.window-layer {
  position: fixed;
  inset: 0;
  z-index: var(--z-window);
  display: flex;
  align-items: flex-end;
  justify-content: center;
}
.window-backdrop {
  position: absolute;
  inset: 0;
  background: rgba(0, 0, 0, 0.45);
}
.stage-window {
  position: relative;
  display: flex;
  flex-direction: column;
  width: 100%;
  max-width: 720px;
  max-height: 88vh;
  max-height: 88dvh;
  background: var(--bg);
  border-radius: var(--radius) var(--radius) 0 0;
  box-shadow: 0 -4px 24px rgba(0, 0, 0, 0.3);
  overflow: hidden;
}
.window-head {
  flex: none;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  min-height: 61px;
  padding: 8px 10px 8px 16px;
  background: var(--bg-header);
  border-bottom: 1px solid var(--border);
}
.window-head h2 { margin: 0; font-size: 1.15rem; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.window-body {
  flex: 1 1 auto;
  min-height: 0;
  overflow-y: auto;
  overscroll-behavior: contain;
  -webkit-overflow-scrolling: touch;
  padding: 12px 16px calc(24px + env(safe-area-inset-bottom));
}
.window-body > :first-child { margin-top: 0; }
.window-body > .subtabs:first-child { margin-top: 0; }
@media (min-width: 640px) {
  .window-layer { align-items: center; padding: 16px; }
  .stage-window { border-radius: var(--radius); }
}
.modal a { color: var(--accent); font-weight: 600; }

/* ---------- 1.1 : navigation de la carte (étiquettes, points, objectif, fenêtres, bandeau) ---------- */

/* Étiquettes des bâtiments : en DOM, par-dessus le canvas, replacées à chaque image par
   farm-stage.js. Elles ne prennent pas les appuis : la carte glisse aussi quand le doigt part
   d'une étiquette, et c'est la scène qui reconnaît un appui dessus.
   Version 1.1.1 : le nom ne s'affiche qu'au survol du lieu (classe `show`, posée par la
   scène : souris dessus, doigt posé, ou focus clavier). Sans survol, il ne reste que la
   pastille « à faire » ; sans pastille, rien du tout. */
.stage-labels { position: absolute; inset: 0; z-index: 2; overflow: hidden; pointer-events: none; }
.stage-label {
  position: absolute;
  left: 0;
  top: 0;
  display: inline-flex;
  align-items: center;
  gap: 5px;
  min-height: 22px;
  padding: 2px 8px;
  border-radius: 999px;
  border: 1px solid rgba(35, 26, 40, 0.45);
  background: rgba(248, 241, 252, 0.94);
  color: var(--color-ink);
  font-size: 0.78rem;
  font-weight: 700;
  line-height: 1.2;
  white-space: nowrap;
  box-shadow: 0 1px 4px rgba(0, 0, 0, 0.4);
  pointer-events: none;
  will-change: transform;
}
.stage-label.todo { border-color: var(--color-tomato); }
.stage-label:not(.show) { min-height: 0; padding: 0; border-color: transparent; background: none; box-shadow: none; }
.stage-label:not(.show) .stage-label-name { display: none; }
.stage-label:not(.show):not(.todo) { opacity: 0; }
.stage-label:not(.show) .stage-label-badge { box-shadow: 0 1px 4px rgba(0, 0, 0, 0.5); border: 1px solid #ffffff; }
/* FLU-37 : la pastille seule garde son dessin, mais sa zone tactile fait 44 × 44 px */
.stage-label.todo:not(.show) { min-width: 44px; min-height: 44px; justify-content: center; }
.stage-label:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
.stage-label-badge {
  min-width: 17px;
  height: 17px;
  padding: 0 4px;
  border-radius: 999px;
  background: var(--color-tomato);
  color: #ffffff;
  font-size: 0.7rem;
  line-height: 17px;
  text-align: center;
  font-variant-numeric: tabular-nums;
}
.stage-label-badge[hidden] { display: none; }

/* Objectif du chapitre : une ligne en haut de la carte ; un appui ouvre la fenêtre Chapitres. */
.stage-hud {
  position: absolute;
  left: calc(8px + env(safe-area-inset-left));
  right: calc(64px + env(safe-area-inset-right)); /* la jauge d'énergie, à droite */
  bottom: 84px; /* en bas, au-dessus de la flèche « ⌄ » et des boutons ronds (Zzz, houe) ; la jauge d'énergie est à droite */
  z-index: 6;
  display: flex;
  flex-wrap: wrap-reverse; /* FLU-06 : la bulle de la première houe passe au-dessus de la puce */
  align-items: flex-end;
  pointer-events: none;
}
.stage-chip {
  min-width: 0;
  max-width: 100%;
  min-height: 44px;
  padding: 0;
  border: 0;
  background: none;
  color: var(--text);
  display: flex;
  align-items: center;
  cursor: pointer;
  pointer-events: auto;
}
.stage-chip-pill {
  position: relative;
  min-width: 0;
  max-width: 100%;
  min-height: 34px;
  display: flex;
  align-items: center;
  gap: 6px;
  padding: 0 10px;
  border-radius: 12px;
  border: 1px solid var(--border);
  background: var(--bg-elevated);
  font-size: 0.85rem;
  font-weight: 600;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.3);
  overflow: hidden;
}
.stage-chip:focus-visible { outline: none; }
.stage-chip:focus-visible .stage-chip-pill { outline: 3px solid var(--color-sun); outline-offset: 1px; }
.stage-chip:active .stage-chip-pill { transform: translateY(1px); }
.stage-chip-text { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.stage-chip-val { flex: none; color: var(--text-muted); white-space: nowrap; }
.stage-chip-go { flex: none; color: var(--text-muted); font-size: 1.1rem; line-height: 1; }
.stage-chip-bar { position: absolute; left: 0; right: 0; bottom: 0; height: 3px; background: var(--bg-muted); }
.stage-chip-bar > span { display: block; height: 100%; background: var(--accent); }
/* La ferme générée, le mode Construire (js/ui/chantier.js) : le menu des blocs, en haut de
   l'écran (le HUD du haut s'efface : body.construction), dans le bois de la barre d'outils (même
   cadre, mêmes cases .tool-slot). Des onglets intercalaires posés sur la barre (l'ouvert, plus
   haut, avec son nom), puis la barre : une ligne de cases qui défile (le bloc choisi encadré,
   comme l'outil en main ; un bloc qu'on n'a plus, pâli), et au bout le niveau, ✕ et les
   paillasses. La bulle des murs s'ouvre sous la case des murs. */
body.construction #player-card,
body.construction #hud,
body.construction #amis-bouton,
body.construction #side-menu,
body.construction #tool-bar,
body.construction .boussole,
body.construction .stage-bubble,
body.construction .habitant-bulle,
body.construction .stage-nav,
body.construction .stage-hud > :not(.build-dock):not(.pose-meuble):not(.build-outils) { display: none !important; }
.build-dock {
  --slot: 52px;
  position: fixed;
  top: calc(8px + env(safe-area-inset-top));
  left: calc(6px + env(safe-area-inset-left));
  right: calc(6px + env(safe-area-inset-right));
  z-index: var(--z-fab);
  display: flex;
  flex-direction: column;
  align-items: stretch;
  pointer-events: none;
}
.build-dock > * { pointer-events: auto; }
/* le texte sombre du bois, en clair comme en sombre (le menu de Construire, la pose d'un meuble) */
.build-dock, .pose-meuble { color: var(--wood-ink); }
.build-tabs {
  display: flex;
  align-items: flex-end;
  gap: 2px;
  margin: 0 0 -3px 6px;
  align-self: flex-start;
  max-width: calc(100% - 12px);
  position: relative;
  z-index: 1;
}
.build-tab {
  display: flex; align-items: center; gap: 4px;
  height: 30px; min-width: 32px; padding: 0 5px;
  border: 3px solid var(--color-earth); border-bottom: 0; border-radius: 7px 7px 0 0;
  background: #9c73b4;
  font: inherit; font-weight: 800; color: var(--color-earth);
  cursor: pointer;
}
.build-tab .px { --pxs: 20px; }
.build-tab.on { height: 36px; padding: 0 10px 0 6px; background: rgb(var(--wood-bg-rgb)); }
.build-tab-nom { white-space: nowrap; }
/* Le niveau de construction : un petit carré du même bois, au bout de la barre ; un appui long
   ouvre sous lui la liste des niveaux, le plus haut en haut (on glisse jusqu'à l'un, on lâche). */
.build-level { position: relative; }
.build-level-btn, .build-level-list {
  box-sizing: border-box;
  background: rgba(var(--wood-bg-rgb), 0.92);
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
}
.build-level-btn {
  width: 34px; height: 34px;
  padding: 0;
  font: inherit; font-size: 1.1rem; font-weight: 800; color: var(--color-earth);
  cursor: pointer;
  touch-action: none; user-select: none; -webkit-user-select: none; -webkit-touch-callout: none;
}
.build-level-list {
  position: absolute; right: 0; top: calc(100% + 4px);
  display: flex; flex-direction: column; gap: 4px;
  width: 196px;
  padding: 6px;
  z-index: 2;
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, 0.3));
}
.build-level-list[hidden] { display: none; }
.build-level-titre { font-size: 0.85rem; font-weight: 800; color: var(--color-earth); text-align: center; letter-spacing: 0.04em; }
.build-level-item {
  display: flex; align-items: center; gap: 8px;
  height: calc(var(--slot) - 6px);
  padding: 0 8px; border: 0; border-radius: 4px;
  text-align: left;
  background: #cbafdb; box-shadow: inset 0 0 0 2px var(--wood-light);
  font: inherit; font-size: 1.3rem; font-weight: 800; color: var(--color-earth);
  cursor: pointer; touch-action: none; user-select: none; -webkit-user-select: none;
}
.build-level-n { flex: none; width: 1.4em; text-align: center; font-size: 1.4rem; }
.build-level-quoi { font-size: 0.8rem; font-weight: 700; line-height: 1.1; white-space: nowrap; pointer-events: none; }
.build-level-n { pointer-events: none; }
.build-level-item.active { background: #f0d4f2; box-shadow: inset 0 0 0 2px var(--color-earth); }
.build-level-item.survol { background: #e9d2f6; box-shadow: inset 0 0 0 3px var(--color-sun); }
.build-bar {
  box-sizing: border-box;
  display: flex;
  align-items: flex-start;
  gap: 6px;
  padding: 5px;
  background: rgba(var(--wood-bg-rgb), 0.92);
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, 0.3));
}
.build-bar-cases { position: relative; flex: 1; min-width: 0; }
.build-bar-grid {
  display: grid;
  grid-auto-flow: column;
  grid-auto-columns: var(--slot);
  grid-template-rows: repeat(3, var(--slot));   /* les cases sur trois lignes (Construire, l'Atelier) */
  gap: 5px;
  overflow-x: auto;
  overscroll-behavior: contain;
  scrollbar-width: thin;
  padding-bottom: 1px;
}
.build-bar-bout { display: flex; flex-direction: column; align-items: center; gap: 2px; flex-shrink: 0; }
/* Les outils (annuler, la gomme, l'outil pièce, le niveau) : une petite fenêtre du même bois, à part,
   sur la droite ; un appui long la rend déplaçable : elle s'irise (comme ce qui attend un geste sur la
   carte) et suit le doigt (js/ui/chantier.js). */
.build-outils {
  position: fixed;
  top: calc(253px + env(safe-area-inset-top));   /* sous le menu (trois lignes de cases) */
  right: calc(8px + env(safe-area-inset-right));
  z-index: var(--z-fab);
  display: flex; flex-direction: column; align-items: center; gap: 5px;
  padding: 4px 5px 6px;
  color: var(--wood-ink);
  background: rgba(var(--wood-bg-rgb), 0.94);
  border: 3px solid var(--color-earth);
  border-radius: 8px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, 0.3));
  touch-action: none; user-select: none; -webkit-user-select: none; -webkit-touch-callout: none;
  pointer-events: auto;   /* (le HUD de la carte laisse passer les appuis : pas elle) */
}
.build-outils-prise { font-size: 0.8rem; line-height: 1; color: var(--color-earth); opacity: 0.7; cursor: grab; }
.build-outils .build-level-list { right: calc(100% + 6px); top: 0; }
.build-outils.deplace { cursor: grabbing; animation: outils-irise 1.4s linear infinite; }
.build-outils.deplace::after {
  content: ''; position: absolute; inset: -3px; border-radius: 8px; pointer-events: none;
  background: linear-gradient(115deg, transparent 20%, rgba(255, 255, 255, 0.55) 45%, transparent 70%) -200% 0 / 300% 100% no-repeat,
    linear-gradient(135deg, rgba(71, 150, 227, 0.35), rgba(145, 119, 199, 0.35), rgba(202, 102, 115, 0.35), rgba(232, 182, 90, 0.35), rgba(124, 200, 200, 0.35));
  mix-blend-mode: screen;
  animation: outils-reflet 1.4s linear infinite;
}
@keyframes outils-irise {
  0% { border-color: #4796e3; box-shadow: inset 0 0 0 2px var(--wood-glow), 0 0 12px 3px #4796e3; }
  25% { border-color: #9177c7; box-shadow: inset 0 0 0 2px var(--wood-glow), 0 0 12px 3px #9177c7; }
  50% { border-color: #ca6673; box-shadow: inset 0 0 0 2px var(--wood-glow), 0 0 12px 3px #ca6673; }
  75% { border-color: #e8b65a; box-shadow: inset 0 0 0 2px var(--wood-glow), 0 0 12px 3px #e8b65a; }
  100% { border-color: #4796e3; box-shadow: inset 0 0 0 2px var(--wood-glow), 0 0 12px 3px #4796e3; }
}
@keyframes outils-reflet { from { background-position: -200% 0, 0 0; } to { background-position: 200% 0, 0 0; } }
@media (prefers-reduced-motion: reduce) {
  .build-outils.deplace, .build-outils.deplace::after { animation: none; }
  .build-outils.deplace { border-color: #9177c7; box-shadow: inset 0 0 0 2px var(--wood-glow), 0 0 12px 3px #9177c7; }
}
.build-bar-boutons { display: flex; gap: 4px; }
.build-bar-head { font-weight: 700; font-size: 0.85rem; white-space: nowrap; }
.build-bar-close {
  width: 34px; height: 34px; padding: 0;
  border: 0; border-radius: 4px;
  background: #cbafdb; box-shadow: inset 0 0 0 2px var(--wood-light);
  font: inherit; font-size: 1rem; line-height: 1; cursor: pointer;
}
.build-slot { position: relative; height: var(--slot); font-size: 1.4rem; }
.build-slot .px { --pxs: 32px; }
.build-slot-n {
  position: absolute; right: 3px; bottom: 2px;
  font-size: 0.72rem; font-weight: 800; line-height: 1;
  color: var(--color-earth);
}
/* sur le dessin d'une machine (qui remplit la case), le nombre sur un fond clair */
.build-slot:has(.build-slot-dessin) .build-slot-n { padding: 1px 2px; border-radius: 3px; background: rgba(var(--wood-bg-rgb), 0.9); }
/* le style d'aménagement d'un bloc (js/engine/styles.js) : sa petite icône, en haut à gauche */
.build-slot-style { position: absolute; left: 2px; top: 1px; font-size: 0.62rem; line-height: 1; pointer-events: none; }
/* A-2 (js/ui/catalogue.js) : un favori, sa petite étoile en haut à droite ; l'appui long qui le met en
   favori ne sélectionne rien, n'ouvre pas le menu du navigateur */
.build-slot { -webkit-touch-callout: none; user-select: none; -webkit-user-select: none; }
.build-slot-fav { position: absolute; right: 2px; top: 1px; font-size: 0.6rem; line-height: 1; pointer-events: none; }
.build-slot .build-slot-fav .px, .build-slot .build-slot-style .px { --pxs: 12px; vertical-align: top; }
.build-filtre .px { --pxs: 16px; vertical-align: middle; }
/* les filtres, au-dessus des cases : de petites puces de bois, qui défilent si elles sont trop nombreuses */
.build-filtres {
  display: flex; gap: 4px; padding: 2px 4px 4px;
  overflow-x: auto; scrollbar-width: none;
}
.build-filtres::-webkit-scrollbar { display: none; }
.build-filtre {
  flex: none; display: flex; align-items: center; gap: 3px;
  height: 26px; min-width: 30px; padding: 0 6px;
  border: 2px solid var(--color-earth); border-radius: 13px;
  background: #b18ec6;
  font: inherit; font-size: 0.78rem; font-weight: 800; color: var(--color-earth);
  cursor: pointer;
}
.build-filtre.on { background: #f6dfa8; box-shadow: inset 0 0 0 2px var(--wood-glow); }
.build-filtre-nom { white-space: nowrap; }
.build-vide { padding: 8px 10px; font-size: 0.85rem; font-style: italic; opacity: 0.8; }
.ami-style { margin: 4px 0; }
/* le carnet de plans, sous l'Atelier (js/ui/plans.js) */
.carnet-plans .plans-pays { margin-top: 6px; }
.plans-liste { list-style: none; margin: 2px 0 0; padding: 0 0 0 4px; display: flex; flex-direction: column; gap: 2px; }
.plan.inconnu { opacity: 0.8; }
/* le projet d'un hameau (js/ui/habitants.js) */
.projet-besoin { list-style: none; margin: 4px 0; padding: 0; display: flex; flex-direction: column; gap: 4px; }
.projet-ligne { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; }
.projet-bar { flex: 1 1 80px; min-width: 80px; }
.build-slot.epuise { opacity: 0.55; }
.build-slot-img { max-width: 30px; max-height: 30px; image-rendering: pixelated; pointer-events: none; }
/* une machine des chaînes de production : son dessin de la carte (une case de 16 × 24 de blocs.png,
   --f : son rang), agrandi deux fois */
.build-slot-dessin {
  display: block; width: 32px; height: 48px; margin: auto;
  background-repeat: no-repeat; background-size: auto 48px; background-position: calc(var(--f) * -32px) 0;
  image-rendering: pixelated; pointer-events: none;
}
.build-bulle .build-slot-dessin { transform: scale(0.75); }
/* la case d'un groupe (les murs, les portes, les sols) : « ⋯ » en haut à gauche (elle ouvre sa bulle) */
.build-groupe-plus { position: absolute; left: 4px; top: -2px; font-size: 1rem; font-weight: 900; line-height: 1; color: var(--color-earth); }
/* la bulle d'un groupe : sous la ligne de sa case (--ligne), une flèche vers elle (--rang : sa
   colonne dans la barre) ; chaque bloc, son icône */
.build-bulle {
  position: absolute; left: -6px; top: calc((var(--ligne, 0) + 1) * (var(--slot) + 5px) + 7px);
  z-index: 2;
  padding: 6px;
  background: rgba(var(--wood-bg-rgb), 0.97);
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, 0.35));
}
.build-bulle::after {
  content: ''; position: absolute; left: calc(22px + var(--rang, 0) * (var(--slot) + 5px)); top: -19px;
  border: 8px solid transparent; border-bottom-color: var(--color-earth);
}
.build-bulle-titre { font-weight: 800; color: var(--color-earth); margin: 0 2px 4px; }
.build-bulle-grid { display: grid; grid-template-columns: repeat(5, 46px); grid-auto-rows: 46px; gap: 4px; }
.build-bulle .build-slot { height: 46px; }
.build-bulle .build-slot .px { --pxs: 30px; }
/* (son style et son étoile gardent leur petite taille : la règle du dessus les grossissait) */
.build-bulle .build-slot .build-slot-style .px, .build-bulle .build-slot .build-slot-fav .px { --pxs: 12px; }
.build-slot .build-slot-style .px, .build-slot .build-slot-fav .px { margin: 0; }

/* L'Atelier (js/ui/atelier.js) : dans sa fenêtre, le même menu que Construire (onglets
   intercalaires, barre de cases qui défile, bulles des murs, des portes et des sols) ; sous la
   barre, la recette choisie (son icône, ce qu'elle prend ➜ ce qu'elle donne, Fabriquer). */
.atelier-menu { --slot: 48px; display: flex; flex-direction: column; margin-bottom: 10px; }
.atelier-menu .build-bar { filter: none; }
/* ses neuf onglets, plus serrés, pour que le nom de l'ouvert tienne en entier (sur un téléphone) */
.atelier-menu .build-tabs { gap: 1px; margin-left: 3px; max-width: calc(100% - 6px); }
.atelier-menu .build-tab { min-width: 28px; padding: 0 3px; justify-content: center; }
.atelier-menu .build-tab .px { --pxs: 18px; }
.atelier-menu .build-tab.on { padding: 0 6px 0 4px; font-size: 0.88rem; }
.atelier-detail { display: flex; align-items: center; flex-wrap: wrap; gap: 10px; }
.atelier-detail-ico { font-size: 2rem; line-height: 1; }
/* le dessin d'un bloc dans une pastille (ce que donne la recette) : à sa taille, sans l'agrandir */
.atelier-mini { display: inline-flex; vertical-align: middle; margin-left: 3px; }
.atelier-mini .build-slot-dessin { width: 16px; height: 24px; background-size: auto 24px; background-position: calc(var(--f) * -16px) 0; }
.atelier-mini .build-slot-img { max-width: 20px; max-height: 20px; }
.atelier-detail-ico .px { --pxs: 40px; }
.atelier-detail-txt { display: flex; flex-direction: column; gap: 4px; flex: 1; min-width: 0; }
.atelier-detail-nom { font-weight: 800; }
.atelier-detail .chips { align-items: center; }
.atelier-fleche { font-weight: 900; color: var(--color-earth); }
.atelier-detail .btn { flex: 1 0 100%; }

/* Dans un intérieur (la Serre) : « Sortir » et « Gérer », à la place des flèches. */
.stage-room-bar {
  position: absolute;
  left: 50%;
  bottom: 8px;
  z-index: 6;
  transform: translateX(-50%);
  display: flex;
  gap: 8px;
}
/* Des boutons comme les autres (.btn, .btn.primary), en pastille. */
.stage-room-btn {
  padding: 0 16px;
  font: inherit;
  font-weight: 600;
  white-space: nowrap;
  display: flex;
  align-items: center;
  gap: 6px;
}
.stage-room-btn:active { transform: translateY(1px); }

/* Les flèches des bords de la carte. */
.stage-arrow {
  position: absolute;
  top: 27%; /* au-dessus de la zone de culture, sous la ligne de l'objectif */
  z-index: 6;
  width: 44px;
  height: 56px;
  margin-top: -28px;
  padding: 0;
  border: 0;
  background: none;
  color: #ffffff;
  display: flex;
  align-items: center;
  cursor: pointer;
}
.stage-arrow.gauche { left: 0; justify-content: flex-start; }
.stage-arrow.droite { right: 0; justify-content: flex-end; }
.stage-arrow > span {
  width: 24px;
  height: 48px;
  display: flex;
  align-items: center;
  justify-content: center;
  background: rgba(25, 22, 26, 0.5);
  font-size: 1.6rem;
  line-height: 1;
  padding-bottom: 4px;
  animation: stage-arrow 1.6s ease-in-out infinite;
}
.stage-arrow.gauche > span { border-radius: 0 12px 12px 0; --pousse: -3px; }
.stage-arrow.droite > span { border-radius: 12px 0 0 12px; --pousse: 3px; }
.stage-arrow:focus-visible { outline: 3px solid var(--color-sun); outline-offset: -4px; }
@keyframes stage-arrow {
  0%, 100% { transform: translateX(0); opacity: 0.85; }
  50% { transform: translateX(var(--pousse)); opacity: 1; }
}

/* Fenêtres de la carte : deux tailles seulement, demi-hauteur ou pleine hauteur. Le ✕ est
   toujours au même endroit dans chacune. */
.stage-window.half { height: 54vh; height: 54dvh; }
.stage-window.tall { height: 92vh; height: 92dvh; max-height: 92vh; max-height: 92dvh; }
.window-detail { font-size: 0.92rem; font-weight: 500; color: var(--text-muted); }
.window-tabs { flex: none; padding: 8px 12px; background: var(--bg); border-bottom: 1px solid var(--border); }
.window-tabs .subtabs { margin: 0; }
/* Le titre de la fenêtre dit déjà où l'on est : le premier titre du contenu, qui le répète,
   est masqué ici (la liste classique de la Ferme garde les siens). */
.window-body.sans-titre > h2:first-child,
.window-body.sans-titre > .section-head:first-child > h2,
.window-body.sans-titre > .section-head:first-child > h3 { display: none; }
.window-body.sans-titre > .section-head:first-child { justify-content: flex-end; }
.window-body .ancre { scroll-margin-top: 8px; }
main .ancre { scroll-margin-top: 150px; }

/* Sous-onglets sur un téléphone : l'icône, et le nom de l'onglet ouvert seulement. */
.subtab-icon { flex: none; }
.subtab-label { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
@media (max-width: 639px) {
  .subtabs.compact .subtab-btn { flex: 0 0 44px; padding: 0; }
  .subtabs.compact .subtab-btn:not(.active) .subtab-label {
    position: absolute;
    width: 1px;
    height: 1px;
    overflow: hidden;
    clip: rect(0 0 0 0);
    clip-path: inset(50%);
  }
  .subtabs.compact .subtab-btn.active { flex: 1 1 auto; padding: 0 10px; }
  .subtabs.compact .subtab-btn.active .subtab-label { white-space: normal; text-align: left; font-size: 0.9rem; line-height: 1.1; }
}

/* Notifications : où mène la ligne. */
.notif-where { display: block; font-size: 0.8rem; font-weight: 500; color: var(--text-muted); }

/* ---------- Version 1.5 : bonheur et Ville ---------- */

.pxgauge.joie i.on { background: #e8b030; box-shadow: inset 0 3px 0 #f8d878, inset 0 -3px 0 #b07a18; }
.portrait .pxgauge { width: 100%; }
.outing { gap: 8px; }
.outing.done { opacity: 0.7; }
.outing-facts { display: flex; flex-wrap: wrap; gap: 4px; }
.outings { grid-template-columns: repeat(auto-fill, minmax(230px, 1fr)); }

/* ---------- version 1.9 : la houe (Zone de culture et Champ) ---------- */

.hoe-bar { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; margin: 8px 0; }

.stage-chip.hoe { margin-left: auto; flex: 0 0 auto; }
/* FLU-41 : houe en main, la puce d'objectif se réduit à son icône et sa valeur */
.stage-chip.compact { flex: 0 0 auto; }

/* ---------- version 1.12 : départ d'une nouvelle partie ---------- */

.setup-graine { margin-top: 4px; }
.story-modal p { line-height: 1.5; }
/* L'accueil d'une nouvelle partie (js/ui/depart.js) : une fenêtre de dialogue, une question
   par écran ; la flèche en bas à droite passe à l'écran suivant. */
.accueil-modal { position: relative; max-width: 380px; padding-bottom: 60px; }
.modal .accueil-texte { margin: 4px 0 12px; line-height: 1.5; }
.accueil-reglage { display: flex; flex-direction: column; align-items: center; gap: 10px; }
.accueil-choix { display: flex; flex-wrap: wrap; justify-content: center; gap: 12px; }
.accueil-choix .btn { min-width: 96px; }
.accueil-champ { width: 100%; }
/* un champ et sa flèche sur une ligne (js/ui/depart.js, ligne) : le clavier d'un téléphone ne la cache pas */
.accueil-ligne { display: flex; align-items: center; gap: 8px; width: 100%; }
.accueil-ligne .accueil-champ { flex: 1; min-width: 0; }
.accueil-ligne .accueil-champ.accueil-nombre { flex: 0 0 6em; margin-left: auto; }
.accueil-ligne .accueil-nombre + .accueil-suite { margin-right: auto; }
.accueil-ligne .accueil-suite { position: static; flex: none; }
.accueil-modal:has(.accueil-ligne) { padding-bottom: 16px; }
.accueil-champ.accueil-nombre { width: 6em; text-align: center; }
.accueil-persos { width: 100%; }
/* Le choix du personnage : tous visibles d'un coup, dessinés deux fois plus gros (64 px) ; la case
   ne garde que la largeur du personnage (les marges transparentes de .perso-px la débordent). */
.perso-grid.accueil-persos {
  grid-template-columns: repeat(auto-fill, minmax(34px, 1fr)); gap: 4px;
  max-height: calc(100dvh - 230px);
}
/* Un écran de choix du personnage : la fenêtre ne défile pas (la flèche, posée en bas d'elle, défilerait avec la grille
   et finirait sur les personnages), elle tient dans l'écran ; la grille prend la place qui reste et défile seule. Un
   texte agrandi (la taille du texte d'Android, que suit le navigateur intégré de Messenger) lui prend de la place,
   sans rien cacher. */
.accueil-modal:has(.accueil-persos) {
  display: flex; flex-direction: column; overflow: hidden;
  max-height: calc(100vh - 32px); max-height: calc(100dvh - 32px);
}
.accueil-modal:has(.accueil-persos) .accueil-texte { flex: none; }
.accueil-modal:has(.accueil-persos) .accueil-reglage { flex: 1 1 auto; min-height: 0; }
.accueil-modal:has(.accueil-persos) .perso-grid.accueil-persos { flex: 0 1 auto; min-height: 80px; max-height: none; grid-auto-rows: max-content; overscroll-behavior: contain; }
.accueil-persos .perso-btn { padding: 0; overflow: hidden; }
.accueil-persos .perso-btn .perso-px { --s: 64px; }
.accueil-portrait .perso-px { --s: 128px; } /* en grand, vivant (js/ui/depart.js) */
/* L'écran « Personnaliser » (chantier « couches ») : le portrait reste en vue, les choix défilent sous lui. */
.accueil-personnaliser { width: 100%; max-height: calc(100dvh - 400px); min-height: 160px; overflow-y: auto; overscroll-behavior: contain; }
.accueil-personnaliser .apparence-groupe:first-child { margin-top: 0; }
/* La fenêtre « Modifier » d'un membre : l'aperçu reste en haut quand on descend dans « Personnaliser » (et le bouton
   « 🎨 Apparence » de la fiche y amène, sous l'aperçu). */
.member-modal .member-preview { position: sticky; top: -20px; z-index: 1; }
.member-modal #apparence-details { scroll-margin-top: 170px; }
/* Le récapitulatif, à la fin (fiche 18 ; les retours de 2026-11) : une ligne par membre, son portrait, son prénom, son
   rôle, ✏️ pour le changer (🗑️ pour un enfant ou un animal) ; ＋ en ajoute un ; puis « Valider et commencer ». */
.accueil-recap { list-style: none; margin: 0; padding: 0; width: 100%; display: flex; flex-direction: column; gap: 4px; max-height: calc(100dvh - 330px); overflow-y: auto; overscroll-behavior: contain; }
.accueil-recap li { display: flex; align-items: center; gap: 10px; padding: 2px 6px; border-radius: 6px; background: rgba(255, 255, 255, 0.35); }
.accueil-recap .perso-px { --s: 48px; flex: none; }
.accueil-recap-qui { flex: 1; min-width: 0; display: flex; flex-direction: column; line-height: 1.2; overflow-wrap: anywhere; }
.accueil-recap-qui small { opacity: 0.7; }
.accueil-recap-boutons { display: flex; gap: 4px; flex: none; }
.accueil-crayon { width: 40px; height: 40px; min-height: 0; padding: 0; font-size: 18px; }
.accueil-plus .btn { min-width: 0; }
.accueil-valider { min-width: 200px; }
.accueil-animal-icone { display: flex; align-items: center; justify-content: center; width: 48px; height: 48px; font-size: 26px; flex: none; }
.accueil-espece.active { outline: 3px solid var(--color-sun); outline-offset: 0; }
.accueil-modal .pose-meuble-ok, .accueil-modal .pose-meuble-non { width: 56px; height: 56px; }
.accueil-suite {
  position: absolute; right: 10px; bottom: 8px;
  width: 44px; height: 44px; padding: 0;
  display: flex; align-items: center; justify-content: center;
  border: 0; background: none; cursor: pointer;
}
.accueil-suite span {
  width: 0; height: 0;
  border-top: 9px solid transparent; border-bottom: 9px solid transparent;
  border-left: 14px solid var(--color-earth);
  animation: accueil-suite 0.9s ease-in-out infinite alternate;
}
.accueil-suite:disabled { cursor: default; opacity: 0.3; }
.accueil-suite:disabled span { animation: none; }
.accueil-suite:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; border-radius: 6px; }
@keyframes accueil-suite { to { transform: translateX(4px); } }
/* La flèche ◀ : l'écran d'avant, en bas à gauche (dans la ligne d'un champ, à gauche de lui). */
.accueil-retour {
  position: absolute; left: 10px; bottom: 8px;
  width: 44px; height: 44px; padding: 0;
  display: flex; align-items: center; justify-content: center;
  border: 0; background: none; cursor: pointer;
}
.accueil-retour span {
  width: 0; height: 0; opacity: 0.75;
  border-top: 9px solid transparent; border-bottom: 9px solid transparent;
  border-right: 14px solid var(--color-earth);
}
.accueil-retour:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; border-radius: 6px; }
.accueil-ligne .accueil-retour { position: static; flex: none; }
@media (prefers-reduced-motion: reduce) { .accueil-suite span { animation: none; } }
.starter-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: 8px;
  padding: 8px 0;
  border-top: 1px dashed var(--border);
}

/* FLU-01 : le bouton « Voir le chapitre » se range à côté de ✕ */
.window-head .window-chapter { margin-left: auto; margin-right: 8px; }

/* FLU-06 : bulle de la première houe en main, sous la puce Houe */
.hoe-hint {
  flex: 1 0 100%;
  align-self: flex-end;
  margin-bottom: 6px;
  margin-left: auto;
  max-width: 240px;
  padding: 8px 12px;
  border-radius: 12px;
  background: var(--accent);
  color: #fff;
  font-weight: 700;
  font-size: 0.9rem;
  text-align: center;
  box-shadow: 0 3px 8px rgba(0, 0, 0, 0.35);
  pointer-events: none;
}

/* FLU-07 : chevron « la carte continue vers le bas », en bas au milieu de la carte */
.stage-arrow.bas {
  top: auto;
  bottom: 4px;
  left: 50%;
  width: 56px;
  height: 44px;
  margin: 0 0 0 -28px;
  justify-content: center;
  align-items: flex-end;
}
.stage-arrow.bas > span { width: 48px; height: 24px; border-radius: 12px 12px 0 0; padding: 0 0 6px; font-size: 1.4rem; animation-name: stage-arrow-bas; }
@keyframes stage-arrow-bas {
  0%, 100% { transform: translateY(0); opacity: 0.85; }
  50% { transform: translateY(3px); opacity: 1; }
}
@media (prefers-reduced-motion: reduce) {
  .stage-arrow.bas > span { animation: none; }
}

/* FLU-08 : onglet Marché verrouillé (avant le panneau et la pompe) */
.nav-btn.locked { opacity: 0.55; }
.nav-btn.locked .nav-icon { position: relative; }
.nav-btn .nav-lock { position: absolute; right: -10px; bottom: -4px; font-size: 0.8rem; }

/* FLU-11 : ce qui manque pour une action groupée, écrit sous les boutons */
.group-note { flex: 1 0 100%; color: var(--danger); font-weight: 600; }

/* ---------- Carte flottante en haut à droite : la lune, le jour, l'heure ----------
   Sur tous les écrans, au-dessus de la carte de la ferme et sous les fenêtres (window-layer,
   modal-root). En pixel art (assets/hud), à la taille --hp de la carte du joueur : le hublot
   (40 × 40 : son anneau de bois, sur le ciel de l'heure, --ciel1 à --ciel3 ses trois bandes, et
   les étoiles, à --etoiles d'opacité) et la lune dedans (21 × 21, 14 cases de lunes.png, --lf sa
   case) ; dessous, le bandeau beige du jour et du mois (ruban.png : ses bouts entaillés, le
   milieu qui s'étire), à cheval sur le bas du hublot ; la plaque de l'heure en haut à gauche. */
.hud {
  --hp: var(--hud-px, 2px);
  position: fixed;
  top: calc(8px + env(safe-area-inset-top));
  right: calc(8px + env(safe-area-inset-right));
  z-index: var(--z-hud);
  pointer-events: none;
  transition: opacity 0.2s;
}
.hud-cadran {
  display: flex;
  flex-direction: column;
  align-items: center;
  padding: 0;
  border: 0;
  background: none;
  font: inherit;
  color: var(--wood-ink);
  cursor: pointer;
  pointer-events: auto;
}
.hud-cadran:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; border-radius: 6px; }
.hud-hublot {
  position: relative;
  display: block;
  width: calc(40 * var(--hp));
  height: calc(40 * var(--hp));
  image-rendering: pixelated;
}
/* l'anneau par-dessus le ciel et la lune ; le ciel déborde un peu sous l'anneau (son bord
   arrondi n'est pas en pixels) */
.hud-hublot::after,
.hud-ciel,
.hud-etoiles {
  content: '';
  position: absolute;
  inset: 0;
  pointer-events: none;
}
.hud-hublot::after { background: url('../assets/hud/hublot.png') no-repeat 0 0 / 100% 100%; }
.hud-ciel {
  clip-path: circle(calc(17 * var(--hp)) at 50% 50%);
  background: linear-gradient(var(--ciel1) calc(13 * var(--hp)), var(--ciel2) 0 calc(26 * var(--hp)), var(--ciel3) 0);
}
.hud-etoiles {
  background: url('../assets/hud/etoiles.png') no-repeat 0 0 / 100% 100%;
  opacity: var(--etoiles, 1);
  transition: opacity 1s;
}
.hud-lune {
  position: absolute;
  left: calc(10 * var(--hp));
  top: calc(10 * var(--hp));
  width: calc(21 * var(--hp));
  height: calc(21 * var(--hp));
  background: url('../assets/hud/lunes.png') no-repeat;
  background-size: calc(294 * var(--hp)) 100%;
  background-position: calc(var(--lf) * -21 * var(--hp)) 0;
  image-rendering: pixelated;
}
/* le bandeau : 12 px de haut, ses bouts de 5 px ; il ne s'étire qu'en largeur */
.hud-ruban {
  position: relative;
  display: flex;
  align-items: center;
  box-sizing: border-box;
  height: calc(12 * var(--hp));
  margin-top: calc(-5 * var(--hp));
  padding: 0 var(--hp) var(--hp);
  border-style: solid;
  border-width: 0 calc(5 * var(--hp));
  border-color: transparent;
  border-image: url('../assets/hud/ruban.png') 0 5 fill / 0 calc(5 * var(--hp)) stretch;
  image-rendering: pixelated;
  gap: 0.3em;
  white-space: nowrap;
  font-size: 0.72rem;
  font-weight: 700;
  color: #331f3f;
  font-variant-numeric: tabular-nums;
}
.hud-day { white-space: nowrap; }
.hud-month { font-weight: 600; }
/* l'heure : sa plaque à liseré de bois, en haut à gauche du hublot (un peu sur son anneau), dans la
   police de la date, à distance du bord */
.hud-heure {
  position: absolute;
  right: calc(26 * var(--hp));
  top: calc(1 * var(--hp));
  z-index: 1;
  display: flex;
  align-items: center;
  padding: 0 calc(3 * var(--hp));
  border: calc(3 * var(--hp)) solid transparent;
  border-image: url('../assets/hud/heure.png') 3 fill / calc(3 * var(--hp)) stretch;
  image-rendering: pixelated;
  font-size: 0.72rem;
  font-weight: 700;
  line-height: 1.25;
  color: #331f3f;
  font-variant-numeric: tabular-nums;
}

/* ---------- Calendrier lunaire (fenêtre) ---------- */
.cal-grid { display: grid; grid-template-columns: repeat(7, minmax(0, 1fr)); gap: 4px; margin: 4px 0; }
.cal-head { text-align: center; font-size: 0.8rem; font-weight: 700; color: #4d345c; }
.cal-day {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  padding: 4px 0;
  border-radius: 4px;
  background: #cbafdb;
  box-shadow: inset 0 0 0 2px var(--wood-light);
  font-weight: 700;
  font-variant-numeric: tabular-nums;
}
.cal-day.past { opacity: 0.55; }
.cal-day.today { background: #f0d4f2; box-shadow: inset 0 0 0 2px var(--color-earth); }
.cal-day { position: relative; }
button.cal-day { border: 0; font: inherit; color: inherit; cursor: pointer; }
button.cal-day:hover, button.cal-day:focus-visible { background: #dbc5e7; box-shadow: inset 0 0 0 2px var(--color-earth); }
.cal-evt { position: absolute; top: 1px; right: 2px; font-size: 0.7rem; line-height: 1; }
/* Les évènements du calendrier (js/ui/invitations.js) */
.evenements { display: flex; flex-direction: column; gap: 4px; margin: 6px 0; padding: 6px 0; border-top: 2px solid var(--wood-light); border-bottom: 2px solid var(--wood-light); }
.evenements > .btn { align-self: flex-start; }
.evt-liste { list-style: none; margin: 4px 0; padding: 0; display: flex; flex-direction: column; gap: 6px; }
.evt { display: flex; flex-direction: column; gap: 2px; padding: 6px 8px; border-radius: 4px; background: #d8c1e6; box-shadow: inset 0 0 0 2px var(--wood-light); }
.evt-annuler { align-self: flex-start; margin-top: 2px; }
.evt-form { display: flex; flex-direction: column; gap: 8px; }
.evt-groupe { display: flex; flex-direction: column; gap: 4px; border: 0; margin: 0; padding: 0; }
.evt-groupe legend { font-weight: 700; padding: 0; margin-bottom: 2px; }
.evt-choix { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; min-height: 32px; }
.evt-invite .muted, .repas-gouts { font-size: 0.85rem; }
.evt-boutons { display: flex; flex-wrap: wrap; gap: 8px; }
.repas-plats { display: flex; flex-direction: column; gap: 2px; max-height: 40vh; overflow-y: auto; }
.cal-phases { list-style: none; margin: 4px 0; padding: 0; display: flex; flex-direction: column; gap: 4px; }
.cal-phase { display: flex; gap: 6px; align-items: flex-start; padding: 4px 6px; border-radius: 4px; }
.cal-phase.current { background: #f0d4f2; box-shadow: inset 0 0 0 2px var(--wood-light); }
/* Un menu ouvert (fenêtre de la carte, fenêtre de dialogue) : la carte flottante reste
   visible par-dessus, à 80 % de transparence, et laisse passer les appuis. */
body:has(.window-layer) .hud,
body:has(#modal-root > *) .hud { z-index: var(--z-hud-over); opacity: 0.2; pointer-events: none; }
body:has(.window-layer) .hud button,
body:has(#modal-root > *) .hud button { pointer-events: none; }
/* Écrans sans carte : le contenu commence sous la carte flottante (sauf si l'écran est
   assez large pour qu'elle tienne à côté). */
body:not(.has-stage) main { padding-top: calc(var(--player-h, 110px) + 16px + env(safe-area-inset-top)); }
@media (min-width: 1120px) { body:not(.has-stage) main { padding-top: 16px; } }

/* Bulle de la citerne (appui long sur la carte) : combien de litres elle contient. */
.stage-tip {
  position: absolute;
  left: 0;
  top: 0;
  padding: 4px 10px;
  border-radius: 6px;
  border: 3px solid var(--color-earth);
  background: rgba(var(--wood-bg-rgb), 0.92);
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 2px 4px rgba(0, 0, 0, 0.3);
  color: var(--wood-ink);
  font-size: 0.85rem;
  font-weight: 700;
  white-space: nowrap;
  font-variant-numeric: tabular-nums;
  pointer-events: none;
  will-change: transform;
}
.stage-tip[hidden] { display: none; }

/* Version 1.18 : bulles de bande dessinée sur la carte. .stage-bubble : ce qui attend d'être
   ramassé, au-dessus de sa place (un appui y envoie le personnage) ; .stage-gain : ce qu'il
   vient de prendre, au-dessus de lui, qui s'estompe lentement. Le dessin : assets/bulle.png
   (16 × 16, pointe en bas à gauche), en neuf morceaux au double de sa taille : les coins et la
   pointe restent tels quels, le milieu s'étire à la taille du texte. La pointe (colonne 7 de
   l'image, soit 15 px du bord gauche) se pose sur le point de la carte (voir farm-stage.js). */
.stage-bubble,
.stage-gain {
  position: absolute;
  left: 0;
  top: 0;
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 0 2px;
  border-style: solid;
  border-width: 10px 12px 14px 16px;
  border-image: url('../assets/bulle.png') 5 6 7 8 fill / 10px 12px 14px 16px stretch;
  background: none;
  image-rendering: pixelated;
  color: var(--color-ink);
  font: inherit;
  font-size: 0.8rem;
  font-weight: 700;
  line-height: 1.2;
  white-space: nowrap;
  font-variant-numeric: tabular-nums;
  pointer-events: none;
  will-change: transform;
}
.stage-bubble:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
.stage-gain.fade { opacity: 0; transition: opacity 1.4s ease-in; }
/* Les bulles du dialogue du matin (stepMatin) : la phrase va à la ligne, la bulle s'estompe vite. */
.stage-bubble[hidden],
.stage-gain[hidden] { display: none; }
@media (prefers-reduced-motion: reduce) { .stage-gain.fade { transition-duration: 0.4s; } }

/* ---------- Carte du joueur, en haut à gauche (remplace le bandeau du haut) ----------
   En pixel art (assets/hud, scripts/icones/hud.py) : --hp est la taille d'un pixel des dessins,
   un nombre entier de pixels de l'écran (--hud-px, réglé par js/ui/famille.js). Le portrait dans
   son médaillon rond (l'anneau doré de l'XP : une case de portrait.png), la grande étoile du
   niveau en bas à gauche, l'anneau de l'autonomie en bas à droite ; à droite, les jauges
   horizontales et l'argent. Les tubes et la pastille sont découpés en 9 (border-image) ; les
   jauges se remplissent en CSS (.hud-fill). */
.player-card {
  --hp: var(--hud-px, 2px);
  position: fixed;
  top: calc(8px + env(safe-area-inset-top));
  left: calc(8px + env(safe-area-inset-left));
  z-index: var(--z-hud);
  display: flex;
  align-items: flex-start;
  gap: calc(9 * var(--hp));
  color: var(--wood-ink);
  font-weight: 700;
  font-size: 0.78rem;
  line-height: 1.1;
  transition: opacity 0.2s;
}
.player-card button {
  font: inherit;
  color: inherit;
  background: none;
  border: 0;
  padding: 0;
  cursor: pointer;
}
.player-card button:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 1px; border-radius: 4px; }
body:has(.window-layer) .player-card,
body:has(#modal-root > *) .player-card { z-index: var(--z-hud-over); opacity: 0.2; pointer-events: none; }
/* Le médaillon (42 × 42) ; l'étoile et l'anneau de l'autonomie débordent sous lui. */
.player-medaillon { position: relative; flex: none; width: calc(42 * var(--hp)); height: calc(42 * var(--hp)); margin-bottom: calc(5 * var(--hp)); }
/* Tous les éléments de la carte sont des boutons : « .player-card .x » l'emporte sur la
   remise à zéro ci-dessus (.player-card button), sans !important. */
.player-card .player-head { position: absolute; inset: 0; border-radius: 50%; }
.hud-portrait {
  position: absolute;
  inset: 0;
  background: url('../assets/hud/portrait.png') no-repeat;
  background-size: calc(882 * var(--hp)) 100%;
  background-position: calc(var(--f) * -42 * var(--hp)) 0;
  image-rendering: pixelated;
}
/* le personnage debout, de face (16 × 32), dans le disque crème du médaillon (rayon 16) */
.player-portrait {
  position: absolute;
  left: calc(5 * var(--hp));
  top: calc(5 * var(--hp));
  width: calc(32 * var(--hp));
  height: calc(32 * var(--hp));
  border-radius: 50%;
  overflow: hidden;
  display: flex;
  justify-content: center;
  padding-top: calc(3 * var(--hp));
  box-sizing: border-box;
}
.player-portrait .perso-px { --s: calc(32 * var(--hp)); width: calc(16 * var(--hp)); padding: 0; }
/* la grande étoile du niveau (19 × 18), en bas à gauche du médaillon, le numéro dans son cœur */
.player-card .player-level {
  position: absolute;
  left: calc(-4 * var(--hp));
  bottom: calc(-6 * var(--hp));
  width: calc(19 * var(--hp));
  height: calc(18 * var(--hp));
}
.hud-niveau {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 100%;
  height: 100%;
  padding-top: calc(2 * var(--hp));
  box-sizing: border-box;
  background: url('../assets/hud/niveau.png') no-repeat 0 0 / 100% 100%;
  image-rendering: pixelated;
}
.hud-niveau .pxt { --p: var(--hp); --row: 0; } /* chiffres sombres dans l'étoile, même en mode sombre */
/* l'anneau de l'autonomie, en bas à droite du médaillon, la pousse en haut à gauche de l'anneau */
.hud-anneau {
  position: absolute;
  right: 0;
  bottom: 0;
  width: calc(15 * var(--hp));
  height: calc(15 * var(--hp));
  background: url('../assets/hud/anneau.png') no-repeat;
  background-size: calc(315 * var(--hp)) 100%;
  background-position: calc(var(--f) * -15 * var(--hp)) 0;
  image-rendering: pixelated;
}
/* À droite du médaillon : les jauges, puis l'argent. */
.player-cote { display: flex; flex-direction: column; align-items: flex-start; gap: calc(3 * var(--hp)); padding-top: calc(2 * var(--hp)); }
/* les jauges d'énergie, d'endurance et de bonheur, horizontales, l'une sous l'autre */
.player-card .player-gauges { display: flex; }
.player-gauges-in { display: flex; flex-direction: column; gap: calc(2 * var(--hp)); }
.player-gauge { display: grid; grid-template-columns: calc(10 * var(--hp)) auto; align-items: center; justify-items: center; gap: var(--hp); }
/* Les dessins : coeur 9 × 8, éclair 8 × 10, smiley 9 × 9, étoile 11 × 10, pousse 7 × 7, pièce 10 × 10. */
.hud-ico { display: block; flex: none; background: no-repeat 0 0 / 100% 100%; image-rendering: pixelated; }
.hud-ico.coeur { width: calc(9 * var(--hp)); height: calc(8 * var(--hp)); background-image: url('../assets/hud/coeur.png'); }
.hud-ico.eclair { width: calc(8 * var(--hp)); height: calc(10 * var(--hp)); background-image: url('../assets/hud/eclair.png'); }
.hud-ico.smiley { width: calc(9 * var(--hp)); height: calc(9 * var(--hp)); background-image: url('../assets/hud/smiley.png'); }
.hud-ico.etoile { width: calc(11 * var(--hp)); height: calc(10 * var(--hp)); background-image: url('../assets/hud/etoile.png'); }
.hud-ico.piece { width: calc(10 * var(--hp)); height: calc(10 * var(--hp)); background-image: url('../assets/hud/piece.png'); }
/* Le tube d'une jauge (2 px de bord) et son remplissage, un pixel en retrait ; horizontal (.h) :
   il se remplit de gauche à droite, le reflet en haut. */
.hud-tube {
  position: relative;
  display: block;
  box-sizing: border-box;
  flex: 1 1 auto;
  width: calc(9 * var(--hp));
  min-height: calc(24 * var(--hp));
  border: calc(2 * var(--hp)) solid transparent;
  border-image: url('../assets/hud/tube.png') 2 fill / calc(2 * var(--hp)) stretch;
  image-rendering: pixelated;
}
.hud-tube.h { flex: none; width: calc(34 * var(--hp)); height: calc(8 * var(--hp)); min-height: 0; }
.hud-fill {
  position: absolute;
  left: var(--hp);
  right: var(--hp);
  bottom: var(--hp);
  max-height: calc(100% - 2 * var(--hp));
  background: #5ad23c;
  box-shadow: inset var(--hp) 0 0 #8cec6a;
  transition: height 0.3s, width 0.3s;
}
.hud-fill.mid { background: #e8b030; box-shadow: inset var(--hp) 0 0 #f8d878; }
.hud-fill.low { background: #c8503a; box-shadow: inset var(--hp) 0 0 #ec8a6e; }
.hud-fill.endu { background: #3a8ad2; box-shadow: inset var(--hp) 0 0 #7ec0f0; }
.hud-tube.h .hud-fill { top: var(--hp); right: auto; max-height: none; max-width: calc(100% - 2 * var(--hp)); box-shadow: inset 0 var(--hp) 0 #8cec6a; }
.hud-tube.h .hud-fill.mid { box-shadow: inset 0 var(--hp) 0 #f8d878; }
.hud-tube.h .hud-fill.low { box-shadow: inset 0 var(--hp) 0 #ec8a6e; }
.hud-tube.h .hud-fill.endu { box-shadow: inset 0 var(--hp) 0 #7ec0f0; }
@media (prefers-reduced-motion: reduce) { .hud-fill { transition: none; } }
/* L'argent : la pièce sur le bout gauche de sa pastille, le montant en police pixel. */
.player-card .player-money { position: relative; display: flex; align-items: center; padding-left: calc(5 * var(--hp)); }
.hud-pastille {
  display: flex;
  align-items: center;
  box-sizing: border-box;
  height: calc(13 * var(--hp));
  padding: 0 calc(2 * var(--hp)) 0 calc(5 * var(--hp));
  border: calc(3 * var(--hp)) solid transparent;
  border-image: url('../assets/hud/pastille.png') 3 fill / calc(3 * var(--hp)) stretch;
  image-rendering: pixelated;
  color: #8a2e22;
}
.hud-pastille .pxt { --p: var(--hp); --row: 0; } /* chiffres sombres sur la pastille, même en mode sombre */
.player-money .piece { position: absolute; left: 0; top: 50%; margin-top: calc(-5 * var(--hp)); }

/* ---------- Fenêtres de la carte « bois » (Famille…) : le cadre bois des cartes flottantes ----------
   Couleurs, fond et cadre : la règle commune avec .modal.bois, plus haut. */
.stage-window.bois {
  --bg: rgba(var(--wood-bg-rgb), 0.97);
  --bg-header: var(--prune);
  border-bottom: 0;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 -4px 24px rgba(0, 0, 0, 0.3);
}
.stage-window.bois .window-head { border-bottom: 3px solid var(--wood-dark); }
.stage-window.bois .window-head h2 { color: var(--wood-cream); --text-muted: #cdb8e0; }
.stage-window.bois .window-head h2 :is(.muted, small) { color: #cdb8e0; }
/* le bandeau prune : ce qui s'y pose (onglets, boutons) garde ses couleurs claires */
.stage-window.bois .window-head .inv-tab.active { border-color: var(--rose); background: rgba(208, 116, 214, 0.35); }
.stage-window.bois .card {
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 2px 4px rgba(0, 0, 0, 0.15);
}
.stage-window.bois .more > summary { color: var(--text); }
@media (min-width: 640px) { .stage-window.bois { border-bottom: 3px solid var(--color-earth); } } /* fenêtre centrée : cadre complet */

/* ---------- Essai : le Livre de recette comme un vrai livre (js/ui/livre.js) ----------
   Couverture de cuir, une page crème à la fois ; la page tournée pivote autour de la
   reliure, à gauche (rotateY), en laissant voir la suivante. */
.book-backdrop { align-items: center; padding: 16px; }
.book {
  position: relative;
  width: min(100%, 420px);
  max-height: calc(100dvh - 32px);
  display: flex;
  flex-direction: column;
  gap: 8px;
  padding: 14px 14px 10px 22px;
  background: #4a2c5b;
  background-image: linear-gradient(90deg, rgba(0, 0, 0, 0.35), rgba(0, 0, 0, 0) 14px, rgba(255, 255, 255, 0.06) 40%, rgba(0, 0, 0, 0.12));
  border: 3px solid var(--wood-dark);
  border-radius: 6px 12px 12px 6px;
  box-shadow: inset 0 0 0 2px var(--color-earth), 0 10px 30px rgba(0, 0, 0, 0.5);
  color: var(--wood-dark);
}
.book-close {
  position: absolute;
  top: -14px;
  right: -14px;
  z-index: 3;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  border: 3px solid var(--wood-dark);
  background: #e3d0ee;
  color: var(--wood-dark);
  font-weight: 800;
  cursor: pointer;
}
.book-pages {
  position: relative;
  flex: 1 1 auto;
  min-height: 0;
  height: min(540px, calc(100dvh - 120px));
  perspective: 1400px;
  touch-action: pan-y; /* le glissement horizontal tourne les pages */
}
.book-page {
  position: absolute;
  inset: 0;
  overflow-y: auto;
  padding: 18px 18px 30px 26px;
  background: #f0e5f6;
  background-image:
    linear-gradient(90deg, rgba(86, 56, 104, 0.28), rgba(86, 56, 104, 0) 18px),
    repeating-linear-gradient(180deg, rgba(0, 0, 0, 0) 0 27px, rgba(var(--color-earth-rgb), 0.12) 27px 28px);
  border-radius: 2px 8px 8px 2px;
  box-shadow: 2px 0 0 #d2bede, 4px 0 0 #bea6cc, 6px 2px 6px rgba(0, 0, 0, 0.3); /* tranche des pages */
  font-family: inherit;
}
.book-leaf {
  z-index: 2;
  overflow: hidden;
  transform-origin: left center;
  backface-visibility: hidden;
  animation: 0.45s ease-in-out forwards;
}
.book-leaf.turn-next { animation-name: book-turn-next; }
.book-leaf.turn-prev { animation-name: book-turn-prev; }
@keyframes book-turn-next {
  from { transform: rotateY(0deg); filter: brightness(1); }
  to { transform: rotateY(-180deg); filter: brightness(0.7); }
}
@keyframes book-turn-prev {
  from { transform: rotateY(-180deg); filter: brightness(0.7); }
  to { transform: rotateY(0deg); filter: brightness(1); }
}
.book-title { margin: 4px 0 2px; font-size: 1.4rem; text-align: center; color: var(--wood-ink); }
.book-sub { margin: 0 0 12px; text-align: center; font-style: italic; color: #5d426c; }
.book-h3 { margin: 14px 0 6px; font-size: 1.02rem; color: #4a2c5b; border-bottom: 1px solid rgba(var(--color-earth-rgb), 0.4); }
.book-dish { text-align: center; font-size: 3.2rem; line-height: 1.1; margin-top: 6px; }
/* fiche 14 : le dessin d'une bête (sa case de la planche du jeu, en gros pixels) */
.encyclo-betes { display: flex; justify-content: center; align-items: flex-end; flex-wrap: wrap; gap: 12px; min-height: 96px; }
.encyclo-bete { display: block; background-repeat: no-repeat; image-rendering: pixelated; }
/* (les poissons de la page de la pêche : leurs icônes, plus petites, sur deux rangées s'il le faut) */
.book-dish.encyclo-icones { font-size: 2.2rem; display: flex; flex-wrap: wrap; justify-content: center; gap: 4px 10px; }
.book-meta { margin: 0 0 6px; text-align: center; font-family: inherit; font-size: 0.85rem; color: #50375e; }
.book-ingredients { list-style: none; margin: 0 0 10px; padding: 0; display: flex; flex-direction: column; gap: 4px; }
.book-ingredients li.missing { color: #8a2e22; }
.book-note { font-size: 0.85em; color: #6f577d; }
.book-reason { margin: 6px 0 10px; font-style: italic; color: #8a2e22; }
.book-prepare { width: 100%; font-family: inherit; }
.book-toc { list-style: none; margin: 0; padding: 0; }
.book-toc-link {
  width: 100%;
  min-height: 34px;
  display: flex;
  align-items: baseline;
  gap: 6px;
  padding: 0;
  border: 0;
  background: none;
  color: inherit;
  font: inherit;
  text-align: left;
  cursor: pointer;
}
.book-toc-link:hover span:first-child { text-decoration: underline; }
.book-toc-dots { flex: 1; border-bottom: 2px dotted rgba(74, 44, 91, 0.5); transform: translateY(-4px); }
.book-folio { position: absolute; right: 14px; bottom: 8px; font-style: italic; color: #6f577d; font-size: 0.85rem; }
.book-nav { display: flex; align-items: center; justify-content: space-between; gap: 8px; color: #e3d0ee; }
.book-turn { min-width: 52px; font-size: 1.4rem; line-height: 1; background: #e3d0ee; border: 2px solid var(--wood-dark); color: var(--wood-dark); }
.book-turn:disabled { opacity: 0.4; }
.book-count { font-weight: 700; }
@media (prefers-reduced-motion: reduce) { .book-leaf { animation: none; } }

/* ---------- L'Encyclopédie (js/ui/encyclopedie.js) : le même livre, en cuir vert ----------
   Un wiki qui se remplit : les entrées découvertes sont des liens, les autres « ? ? ? ». */
.book.encyclo {
  background-color: #2f4f3a;
  border-color: #1d3324;
  box-shadow: inset 0 0 0 2px #8557a0, 0 10px 30px rgba(0, 0, 0, 0.5);
}
.book.encyclo .book-turn, .book.encyclo .book-close { border-color: #1d3324; color: #1d3324; }
.book.encyclo .book-toc-link .num { flex: none; white-space: nowrap; }
.book.encyclo .book-toc-dots { min-width: 12px; }
.encyclo-jauge { height: 10px; margin: 0 auto 4px; max-width: 260px; border: 2px solid var(--color-earth); border-radius: 6px; background: #dac7e5; overflow: hidden; }
.encyclo-jauge span { display: block; height: 100%; background: #5d9a4a; }
.encyclo-total { margin: 0 0 4px; text-align: center; font-size: 0.85rem; color: #50375e; }
.encyclo-liens { display: flex; flex-wrap: wrap; gap: 6px; }
.encyclo-lien, .encyclo-inconnue { font: inherit; font-size: 0.9rem; }
.encyclo-lien { cursor: pointer; border: 2px solid var(--color-earth); background: #f5eafb; color: var(--wood-ink); }
.encyclo-lien:hover { background: #e3d0ee; }
.encyclo-inconnue { border: 2px dashed rgba(var(--color-earth-rgb), 0.45); background: none; color: #866f94; letter-spacing: 0.1em; }
.encyclo-neuf { margin-left: 4px; padding: 0 5px; border-radius: 4px; background: #c0392b; color: #fff; font-size: 0.72rem; vertical-align: 1px; }
.encyclo-liste { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 2px; }
/* D-1 : les collections du naturaliste, au sommaire */
.encyclo-collections { list-style: none; margin: 0 0 8px; padding: 0; display: flex; flex-direction: column; gap: 4px; }
.encyclo-collection { line-height: 1.35; }
/* G-1 : le temps au cadran */
.hud-meteo { margin-left: 4px; }
.encyclo-collection.faite strong { color: var(--vert-fonce, #2f6b2f); }
.encyclo-item { display: block; width: 100%; min-height: 32px; padding: 4px 2px; border: 0; border-bottom: 1px dotted rgba(var(--color-earth-rgb), 0.45); background: none; color: var(--wood-ink); font: inherit; text-align: left; }
button.encyclo-item { cursor: pointer; }
button.encyclo-item:hover { text-decoration: underline; }
span.encyclo-item.encyclo-inconnue { color: #866f94; }
.encyclo-categorie { margin: 0; text-align: center; }
.encyclo-lien-texte { padding: 4px 0; border: 0; background: none; color: #4a2c5b; font: inherit; font-size: 0.9rem; text-decoration: underline; cursor: pointer; }
.encyclo-retour { margin: 12px 0 0; }
.encyclo-texte { margin: 8px 0 4px; line-height: 1.5; color: var(--wood-ink); }
.encyclo-astuce { margin: 14px 0 0; font-size: 0.85rem; font-style: italic; color: #5d426c; }

/* ---------- Marché en cases (comme l'Inventaire) ----------
   Le prix en haut à gauche (police pixel et pièce), la quantité en bas à droite ; une case
   grisée : on ne peut pas l'acheter (pièces, places) ou plus rien à vendre. */
.shop-slot-price {
  position: absolute;
  left: 3px;
  top: 3px;
  display: inline-flex;
  align-items: center;
  gap: 1px;
  filter: drop-shadow(1px 1px 0 #1e1424) drop-shadow(-1px 0 0 #1e1424);
}
.shop-slot-price .pxt { --p: 2px; }
.shop-coin .px { --pxs: 10px; vertical-align: top; }
.shop-slot .inv-slot-icon { margin-top: 6px; }
.shop-slot .inv-slot-qty .px { --pxs: 14px; vertical-align: top; }
.shop-slot.off { opacity: 0.5; }
.window-head .shop-help { flex: none; margin-left: auto; }
/* Fiche d'un article : un bouton par lot, le total dessous. */
.lot-btns .lot-btn { flex: 1 1 0; min-width: 64px; display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 0; padding: 4px 6px; line-height: 1.15; }
.lot-btns .lot-btn small { font-weight: 600; font-size: 0.75rem; }
/* Sous-rayons du Marché (Acheter : Ingrédients, Plats) : deux onglets côte à côte, sous l'en-tête. */
.shop-subtabs { display: flex; gap: 6px; margin: 0 0 10px; }
.shop-subtab {
  flex: 1 1 0;
  min-height: 40px;
  border: 2px solid var(--color-earth);
  border-radius: 6px;
  background: var(--wood-paper);
  color: var(--wood-ink);
  font: inherit;
  font-weight: 700;
  cursor: pointer;
}
.shop-subtab.active { background: var(--color-earth); color: var(--wood-cream); }
.shop-subtab:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 1px; }
/* Meubles au Marché : leur dessin (assets/meuble_*.png) dans la case, l'onglet et la fiche. */
.meuble-img { max-width: 44px; max-height: 38px; image-rendering: pixelated; margin-top: 6px; }
.meuble-tab { max-width: 34px; max-height: 26px; image-rendering: pixelated; }
.meuble-big { max-width: 56px; max-height: 56px; image-rendering: pixelated; }
/* En-tête des fenêtres flottantes (Inventaire, Marché) : des onglets un peu plus étroits. */
.window-head .inv-tab { width: 40px; }

/* Étable : les animaux en cartes carrées, deux par rangée (le dessin, le nom, l'état). */
.animal-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 8px; margin: 10px 0; }
.animal-card { aspect-ratio: 1; align-items: center; justify-content: center; text-align: center; gap: 4px; padding: 8px; }
.animal-card .animal-art { display: flex; justify-content: center; min-height: 48px; }
.animal-card strong { font-size: 0.95rem; }
.animal-card .animal-state { font-size: 0.82rem; color: var(--text-muted); }
.animal-card .animal-state.alert { color: var(--danger); font-weight: 700; }
.animal-card .bar { width: 100%; }
.animal-card .btn { min-height: 36px; width: 100%; }
.animal-card.ready { border-color: var(--color-sun); }
.animal-card.hungry { border-color: var(--danger); }
.help-emoji { font-size: 32px; line-height: 1; }

/* ---------- Comptes (un appui sur les pièces) : une addition, total en bas ---------- */
.compta { list-style: none; margin: 12px 0; padding: 0; max-height: 55vh; overflow-y: auto; }
.compta-ligne { display: flex; justify-content: space-between; gap: 12px; padding: 4px 2px; border-bottom: 1px dashed var(--border); }
.compta-ligne .num { white-space: nowrap; font-weight: 700; }
.compta-ligne .gain { color: #2f6b2a; }
.compta-ligne .perte { color: #a3322a; }
.compta-jour { margin-top: 10px; font-weight: 700; font-size: 0.85rem; color: var(--text-muted); }
.compta-avant { color: var(--text-muted); }
.compta-vide { padding: 8px 2px; }
.compta-total {
  position: sticky; bottom: 0;
  margin-top: 6px; padding-top: 8px;
  border-top: 3px double var(--color-earth); border-bottom: 0;
  background: var(--bg);
  font-weight: 800; font-size: 1.1rem;
}

/* ---------- Version 1.17 : les adultes ont l'apparence d'un personnage du catalogue ----------
   Le portrait est le personnage de la carte, debout, de face : la première case (16 × 32) de sa
   planche (assets/personnages/perso_XX.png, 8 cases par rangée), au milieu d'un carré de 32
   pixels de l'image, agrandi d'un nombre entier de fois : --s, réglé par js/ui/famille.js
   (--portrait-<taille>). Les marges gauche et droite cachent les cases voisines. */
.perso-px {
  --s: var(--portrait-48, 48px);
  display: block; flex: none; box-sizing: border-box;
  width: var(--s); height: var(--s); padding: 0 calc(var(--s) / 4);
  background: no-repeat 0 0 / calc(var(--s) * 4) auto content-box;
  image-rendering: pixelated;
}
.member-row .perso-px { --s: var(--portrait-40, 40px); }
/* Les portraits vivants du menu Famille (js/ui/famille.js, persoHtml) : ils respirent (les cases idle_bas_0
   et idle_bas_1 de la planche, en alternance, comme sur la carte) et clignent des yeux (.perso-cligne : la
   tuile des yeux fermés de assets/personnages/visages.png, posée sur la zone du visage, qui descend avec la
   tête). --u : un pixel du dessin. Avant les règles de .fiche-perso (qui le posent en absolu). */
.perso-px.vivant { position: relative; animation: portrait-respire 1.2s step-end infinite; }
@keyframes portrait-respire { 0% { background-position-x: 0; } 50% { background-position-x: calc(var(--s) / -2); } }
.perso-cligne {
  --u: calc(var(--s) / 32);
  position: absolute; pointer-events: none; opacity: 0;
  left: calc(var(--s) / 4 + 4 * var(--u)); top: calc(var(--visage-y0) * var(--u));
  width: calc(8 * var(--u)); height: calc(5 * var(--u));
  background-repeat: no-repeat; background-size: calc(144 * var(--u)) auto;
  background-position: calc(-8 * 2 * var(--u)) calc(var(--visage-rang) * -5 * var(--u));
  image-rendering: pixelated;
  animation: portrait-respire-visage 1.2s step-end infinite, portrait-cligne var(--cligne, 4.6s) step-end var(--cligne-decale, 0s) infinite;
}
@keyframes portrait-respire-visage { 0% { top: calc(var(--visage-y0) * var(--u)); } 50% { top: calc(var(--visage-y1) * var(--u)); } }
@keyframes portrait-cligne { 0% { opacity: 0; } 97% { opacity: 1; } }
@media (prefers-reduced-motion: reduce) { .perso-px.vivant, .perso-cligne, .fiche-calque.haut { animation: none; } }
.member-preview .perso-px { --s: 128px; } /* l'aperçu de la fenêtre « Modifier » : en grand, vivant */
.perso-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(44px, 1fr)); gap: 6px; max-height: 240px; overflow-y: auto; padding: 2px; }
.perso-btn { padding: 2px; min-height: 0; display: flex; align-items: center; justify-content: center; }
.perso-btn .perso-px { --s: 32px; }
.perso-btn.active { outline: 3px solid var(--color-sun); outline-offset: 0; }

/* ---------- Fiche 11 : la fiche d'un membre (js/ui/fiche-membre.js ; le croquis du joueur) ----------
   À gauche, la colonne des cases d'équipement (et celle du sac pour le personnage principal) ; au
   milieu, le membre en pied dans un cadre, ses pièces dessinées par-dessus (des calques de
   assets/personnages/equipement.png, la même géométrie que .perso-px : une rangée de 32 pixels par
   pièce, la colonne de l'adulte puis celle de l'enfant) ; sous lui, son prénom et son rôle ; à
   droite, ses jauges ; en bas, un onglet par membre. --fiche-px : la taille d'un pixel du dessin
   (environ 4 px CSS, un nombre entier de pixels de l'écran : js/ui/famille.js). */
.fiche-membre {
  margin: 4px 0 12px; padding: 10px 10px 0;
  background: var(--wood-cream); border: 3px solid var(--wood-dark); border-radius: 10px;
  box-shadow: inset 0 0 0 2px var(--wood-light);
}
.fiche-corps { display: grid; grid-template-columns: auto auto minmax(0, 1fr); gap: 10px; align-items: start; }
.fiche-cases { display: flex; flex-direction: column; gap: 8px; }
.fiche-case {
  position: relative; width: 52px; height: 52px; padding: 0;
  display: flex; align-items: center; justify-content: center;
  background: var(--wood-paper); border: 2px solid var(--wood-dark); border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-light); cursor: pointer; color: var(--wood-ink);
}
.fiche-case.vide { border-style: dashed; color: var(--text-muted); font-size: 1.4rem; box-shadow: none; }
.fiche-case.sac { margin-top: 6px; border-color: var(--color-leaf-dark); }
.fiche-case.sac.vide { font-size: 1.5rem; opacity: 0.8; }
.fiche-case-icone { font-size: 2rem; line-height: 1; }
.fiche-case-n {
  position: absolute; right: -6px; bottom: -8px; padding: 0 4px; border-radius: 999px;
  background: var(--wood-paper); border: 2px solid var(--wood-dark);
  font-size: 0.7rem; font-weight: 800; line-height: 1.3; color: var(--wood-ink);
}
.fiche-case:focus-visible, .fiche-onglet:focus-visible { outline: 3px solid var(--focus); outline-offset: 2px; }
.fiche-centre { display: flex; flex-direction: column; align-items: center; gap: 6px; }
.fiche-cadre {
  padding: 6px 10px; border: 3px solid var(--wood-dark); border-radius: 4px;
  background: linear-gradient(#cfe6f2, #e9f3d6 70%, #b9d38f 70%);
  box-shadow: inset 0 0 0 2px var(--wood-light);
}
.fiche-perso { position: relative; display: block; --s: calc(var(--fiche-px, 4px) * 32); width: calc(var(--s) / 2); height: var(--s); }
.fiche-perso .perso-px { --s: calc(var(--fiche-px, 4px) * 32); position: absolute; left: calc(var(--s) / -4); top: 0; }
.fiche-perso .fiche-calque { background-size: var(--s) auto; }
/* (l'équipement suit la respiration : le haut du corps, rangées 0 à 24 de la case d'un adulte, 0 à 26 d'un
   enfant, descend d'un pixel avec lui, en même temps ; le bas ne bouge pas) */
.fiche-perso { --coupe: 25; }
.fiche-perso.enfant { --coupe: 27; }
.fiche-perso .fiche-calque.haut { clip-path: inset(0 0 calc(var(--s) * (32 - var(--coupe)) / 32) 0); animation: portrait-calque 1.2s step-end infinite; }
.fiche-perso .fiche-calque.bas { clip-path: inset(calc(var(--s) * var(--coupe) / 32) 0 0 0); }
@keyframes portrait-calque { 0% { transform: none; } 50% { transform: translateY(calc(var(--s) / 32)); } }
.fiche-nom {
  margin: 0; padding: 3px 10px; max-width: 150px; text-align: center; overflow-wrap: anywhere;
  background: var(--wood-paper); border: 2px solid var(--wood-dark); border-radius: 999px; font-size: 0.9rem;
}
.fiche-apparence { min-height: 36px; padding: 3px 12px; font-size: 0.85rem; background: var(--wood-paper); border-color: var(--wood-dark); }
.fiche-jauges { display: flex; flex-direction: column; gap: 10px; min-width: 0; padding-top: 4px; }
.fiche-jauge { display: grid; grid-template-columns: minmax(0, 1fr) auto; gap: 2px 6px; align-items: center; }
.fiche-jauge-nom { grid-column: 1 / -1; font-size: 0.85rem; font-weight: 700; color: var(--wood-ink); }
.fiche-jauge .bar { height: 12px; border-color: var(--wood-dark); }
.fiche-jauge .num { font-size: 0.8rem; }
.fiche-aide { align-self: flex-end; }
.fiche-onglets {
  display: flex; gap: 4px; margin: 10px -10px 0; padding: 0 6px; overflow-x: auto;
  border-top: 3px solid var(--wood-dark); scrollbar-width: thin;
}
.fiche-onglet {
  flex: 0 0 auto; min-height: 40px; max-width: 46%; padding: 4px 10px; margin-bottom: 4px;
  background: var(--wood-paper); border: 2px solid var(--wood-dark); border-top: 0; border-radius: 0 0 8px 8px;
  color: var(--wood-ink); font: inherit; font-size: 0.9rem; cursor: pointer;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.fiche-onglet.active { background: var(--color-sun); font-weight: 800; }
.choix-pieces { list-style: none; margin: 8px 0; padding: 0; display: flex; flex-direction: column; gap: 8px; }
.choix-piece { display: flex; align-items: center; gap: 10px; }
.choix-piece .item-icon { font-size: 1.8rem; }
.choix-piece-texte { flex: 1 1 auto; min-width: 0; display: flex; flex-direction: column; }
.choix-piece.non .choix-piece-texte { opacity: 0.7; }
.sac-modal .sac-vide { margin: 4px 0; }
.sac-modal .boite-ligne > .row { flex-wrap: nowrap; }
@media (max-width: 420px) {
  .fiche-corps { gap: 6px; }
  .fiche-case { width: 46px; height: 46px; }
  .fiche-case-icone { font-size: 1.7rem; }
  .fiche-cadre { padding: 4px 6px; }
  .fiche-nom { max-width: 110px; }
}

/* La barre d'outils (js/ui/outils.js) : en bas au milieu de la carte, dans le cadre bois des
   cartes flottantes (bordure de 3 px, fond crème, filet clair) ; une case par outil, l'outil
   dessiné à 32 px. Rangée, elle glisse sous le bord de l'écran et n'en dépasse que sa languette. */
.tool-bar {
  --u: 7.5px; /* la hauteur de la barre : 9 × --u */
  position: fixed;
  left: 50%;
  bottom: calc(var(--dock) + 6px);
  z-index: var(--z-fab);
  display: flex;
  flex-direction: column;
  align-items: center;
  transform: translate(-50%, calc(9 * var(--u) + 6px));
  transition: transform 0.2s ease-out;
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, 0.3));
}
.tool-bar.open { transform: translate(-50%, 0); }
.tool-bar[hidden] { display: none; }
@media (prefers-reduced-motion: reduce) { .tool-bar { transition: none; } }
.tool-bar-body {
  box-sizing: border-box;
  display: flex;
  gap: 5px;
  height: calc(9 * var(--u));
  padding: 5px;
  background: rgba(var(--wood-bg-rgb), 0.88);
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
}
.tool-bar:not(.open) .tool-bar-body { visibility: hidden; transition: visibility 0s 0.2s; }
.tool-slot {
  box-sizing: border-box;
  height: 100%;
  aspect-ratio: 1;
  display: grid;
  place-items: center;
  padding: 0;
  border: 0;
  border-radius: 4px;
  background: #cbafdb;
  box-shadow: inset 0 0 0 2px var(--wood-light);
  font-size: 1rem;
  cursor: pointer;
}
.tool-slot.active { background: #f0d4f2; box-shadow: inset 0 0 0 2px var(--color-earth); }
/* Le galop (js/ui/galop.js) : en selle, les pommes de la sacoche au-dessus de la languette, dans des cases comme
   celles des outils. Chaque pomme est une jauge : sa chair (la case de droite de assets/galop_pommes.png) la couvre
   de gauche à droite à mesure qu'elle est mangée (--mange) ; celle du galop a un bord doré et brille. */
.galop-rangee {
  display: flex;
  gap: 5px;
  height: calc(9 * var(--u) - 16px);
  margin-bottom: 6px;
}
.galop-pomme { position: relative; height: 100%; }
.galop-pomme > span {
  grid-area: 1 / 1;
  width: 32px;
  height: 32px;
  background: url("../assets/galop_pommes.png") no-repeat;
  background-size: 128px 32px;
  background-position: calc(var(--f) * -32px) 0;
  image-rendering: pixelated;
}
.galop-pomme .galop-chair { clip-path: inset(0 calc(100% - var(--mange, 0%)) 0 0); }
.galop-pomme.vide { cursor: default; }
.galop-pomme.vide > span { filter: grayscale(1); opacity: 0.3; }
.galop-pomme.active {
  background: #f0d4f2;
  box-shadow: inset 0 0 0 3px #e8b830, 0 0 8px 3px rgba(255, 214, 90, 0.85);
  animation: galop-brille 1.1s ease-in-out infinite alternate;
}
@keyframes galop-brille { to { box-shadow: inset 0 0 0 3px #f6d060, 0 0 14px 6px rgba(255, 224, 110, 0.55); } }
@media (prefers-reduced-motion: reduce) { .galop-pomme.active { animation: none; } }
/* la fiche du cheval : ses places de la sacoche, les mêmes pommes-jauges */
.galop-titre { margin: 10px 0 6px; font-weight: 700; }
.galop-places { display: flex; gap: 8px; justify-content: center; margin: 4px 0 10px; }
.galop-place { display: grid; place-items: center; width: 52px; height: 52px; border-radius: 8px; background: #f3ead6; box-shadow: inset 0 0 0 3px var(--color-earth); }
.galop-place > span {
  grid-area: 1 / 1; width: 32px; height: 32px;
  background: url("../assets/galop_pommes.png") no-repeat; background-size: 128px 32px;
  background-position: calc(var(--f) * -32px) 0; image-rendering: pixelated;
}
.galop-place .galop-chair { clip-path: inset(0 calc(100% - var(--mange, 0%)) 0 0); }
.galop-place.vide > span { filter: grayscale(1); opacity: 0.3; }
.cheval-modal .item-head .help-btn { margin-left: auto; }
.galop-aide { margin: 6px 0; }
.tool-slot .px { --pxs: 32px; vertical-align: 0; }
/* Les outils, à des tailles accordées entre elles (leurs dessins de 32 px n'occupent pas tous leur
   case autant) : la houe et la hache × 2, la pioche × 1,75, la faux et la canne × 1,25, le marteau
   tel quel. L'icône déborde de sa boîte sans agrandir la case (la marge négative). */
.tool-slot .px { margin: calc((32px - var(--pxs)) / 2); }
.tool-slot[data-outil="houe"] .px, .tool-slot[data-outil="hache"] .px { --pxs: 64px; }
.tool-slot[data-outil="pioche"] .px { --pxs: 56px; }
.tool-slot[data-outil="faux"] .px, .tool-slot[data-outil="canne"] .px { --pxs: 40px; }
.tool-slot:active { transform: translateY(1px); }
.tool-slot:focus-visible { outline: 3px solid var(--color-sun); outline-offset: -2px; }
.tool-slot.vide { cursor: default; opacity: 0.6; }
/* La cruche (fiche 17, js/ui/cruche.js) : son icône, une jauge d'eau à sa droite (bleue, de bas
   en haut, dans un tube sombre comme les jauges du HUD) et ses litres en bas à gauche. Vide :
   le tube rougit un peu, il faut aller au puits. */
.cruche-slot { position: relative; }
.cruche-slot .cruche-icone { font-size: 1.35rem; line-height: 1; transform: translateX(-3px); }
.cruche-jauge {
  position: absolute; right: 5px; top: 7px; bottom: 7px; width: 7px;
  display: flex; flex-direction: column; justify-content: flex-end;
  background: #3a2c42; border-radius: 2px; box-shadow: inset 0 0 0 1px #231a28; overflow: hidden;
}
.cruche-jauge > span { display: block; width: 100%; background: linear-gradient(90deg, #3a86c8, #7cc4f0); transition: height 0.3s ease-out; }
.cruche-slot.vide-eau .cruche-jauge { box-shadow: inset 0 0 0 1px var(--color-tomato); }
.cruche-litres {
  position: absolute; left: 4px; bottom: 2px;
  font-size: 0.62rem; font-weight: 800; line-height: 1; color: #231a28;
}
@media (prefers-reduced-motion: reduce) { .cruche-jauge > span { transition: none; } }
/* La languette, au-dessus du milieu de la barre : le même bois, le même fond. */
.tool-bar-tab {
  position: relative;
  width: 60px;
  height: 24px;
  margin-bottom: -3px; /* posée sur le bois de la barre : un seul cadre */
  padding: 0;
  display: grid;
  place-items: center;
  background: rgba(var(--wood-bg-rgb), 0.88);
  border: 3px solid var(--color-earth);
  border-bottom: 0;
  border-radius: 8px 8px 0 0;
  box-shadow: inset 0 2px 0 var(--wood-glow);
  cursor: pointer;
}
.tool-bar-tab::after { content: ""; position: absolute; inset: -12px 0 -6px; } /* zone d'appui de 44 px environ */
.tool-bar-arrow { fill: #4a2c5b; transition: transform 0.2s; }
.tool-bar:not(.open) .tool-bar-arrow { transform: scaleY(-1); } /* rangée : le triangle montre le sens où elle ressort */
.tool-bar-tab:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
/* Avec la barre, le chevron « la carte continue vers le bas » passe au-dessus d'elle. */
body.has-toolbar .stage-arrow.bas { bottom: calc(9 * 7.5px + 46px); }
/* … et le bouton Dormir (la nuit) aussi, pour ne pas la couvrir sur un téléphone. */
body.has-toolbar .sleep-fab { bottom: calc(var(--dock) + 9 * 7.5px + 18px); }
/* La pose d'un meuble (js/ui/chantier.js) : en bas, au-dessus de la barre d'outils, une
   bande du même bois : ce qu'on fait, ✔️ (vert : le poser là où est son aperçu) et ❌ (sortir
   de ce mode). */
.pose-meuble {
  position: fixed;
  left: 50%;
  bottom: calc(150px + env(safe-area-inset-bottom));
  transform: translateX(-50%);
  z-index: var(--z-fab);
  display: flex;
  align-items: center;
  gap: 8px;
  max-width: calc(100% - 32px);
  padding: 6px 8px 6px 12px;
  background: rgba(var(--wood-bg-rgb), 0.92);
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
  filter: drop-shadow(0 2px 3px rgba(0, 0, 0, 0.3));
  font-weight: 700;
  pointer-events: auto;
}
.pose-meuble-txt { flex: 1; min-width: 0; }
.pose-meuble-ok, .pose-meuble-non, .pose-meuble-tourne, .pose-meuble-peint {
  flex: none;
  width: 48px; height: 48px; padding: 0;
  border: 0; border-radius: 6px;
  font: inherit; font-size: 1.5rem; line-height: 1;
  cursor: pointer;
}
.pose-meuble-ok { background: #6fcf6a; box-shadow: inset 0 0 0 3px #2f8a3a; }
.pose-meuble-ok:disabled { background: #c9d8c2; box-shadow: inset 0 0 0 3px #9aa894; opacity: 0.6; cursor: default; }
.pose-meuble-non { background: #cbafdb; box-shadow: inset 0 0 0 2px var(--wood-light); }
/* 🎨 : la couleur du meuble qu'on pose (A-3) */
.pose-meuble-peint { background: #f0d4f2; box-shadow: inset 0 0 0 3px var(--color-earth); }
/* ↻ : tourner l'aperçu du meuble (js/ui/chantier.js) ; la flèche dit où il regarde */
.pose-meuble-tourne { position: relative; background: #f0d4f2; box-shadow: inset 0 0 0 3px var(--color-earth); color: var(--color-earth); font-weight: 700; }
.pose-meuble-sens { position: absolute; right: 2px; bottom: 1px; font-size: 0.85rem; }

/* « Ravi de te revoir ! » (js/ui/loop.js openAbsenceModal) : une petite fenêtre du jeu, cadre
   bois, en-tête et ✕ comme les fenêtres de la carte ; la date, l'argent, les biens produits. */
.absence-modal { --bg-header: rgba(193, 158, 214, 0.6); max-width: 320px; padding: 0; overflow: hidden; display: flex; flex-direction: column; }
.absence-modal .window-head { min-height: 0; padding: 6px 8px 6px 14px; border-bottom: 3px solid var(--color-earth); }
.absence-modal .window-head h2 { font-size: 1.05rem; }
.absence-body { padding: 12px 14px 16px; overflow-y: auto; }
.absence-ligne { margin: 0 0 6px; font-size: 1.02rem; }
.absence-body h3 { margin: 12px 0 6px; font-size: 0.95rem; }
.absence-body .muted { margin: 0; }
.absence-biens { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 4px; }
.absence-biens li { display: flex; align-items: center; gap: 6px; padding: 4px 8px; border: 1px solid var(--border); border-radius: 6px; background: var(--bg-elevated); }
.absence-biens strong { margin-left: auto; }

/* ---------- Planter un arbre depuis l'Inventaire (js/ui/plantation.js) ----------
   Un bandeau en bas de l'écran (quoi faire, « Annuler ») ; la question, au milieu. */
.plantation-bandeau {
  position: fixed;
  left: 50%;
  bottom: calc(24px + env(safe-area-inset-bottom));
  transform: translateX(-50%);
  z-index: var(--z-hud);
  width: min(calc(100% - 32px), 440px);
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 10px 8px 14px;
  background: rgba(var(--wood-bg-rgb), 0.96);
  border: 3px solid var(--color-earth);
  border-radius: 8px;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 6px 18px rgba(0, 0, 0, 0.3);
  color: var(--wood-ink);
  font-size: 15px;
  line-height: 1.35;
}
.plantation-bandeau span { flex: 1; }
.plantation-bandeau .btn { flex: none; }
.modal-backdrop:has(.plantation-modal) { align-items: center; padding: 16px; }
.plantation-modal { max-width: 340px; border-radius: 8px; }
.plantation-question { margin: 6px 0 14px; font-size: 1.1rem; text-align: center; }
.plantation-choix { justify-content: center; gap: 12px; }
.plantation-choix .btn { min-width: 96px; }

/* la boîte à nourriture (js/ui/boite.js) */
.boite-liste { list-style: none; margin: 4px 0; padding: 0; display: flex; flex-direction: column; gap: 4px; }
.boite-ligne { display: flex; align-items: center; gap: 8px; }
.boite-ligne .boite-nom { flex: 1 1 auto; min-width: 0; }
.boite-ligne .btn { min-width: 44px; padding: 0 8px; }

/* les bacs à compost (js/ui/compost.js) : un bac par ligne, sa jauge jusqu'au prochain engrais ; les aliments à y jeter */
.compost-liste, .compost-aliments { list-style: none; margin: 4px 0 0; padding: 0; display: flex; flex-direction: column; }
.compost-ligne { display: flex; flex-direction: column; gap: 4px; padding: 8px 0; border-top: 1px solid rgba(86, 56, 104, 0.25); }
.compost-titre { font-weight: bold; }
.compost-etat { display: flex; align-items: center; gap: 8px; }
.compost-jauge { flex: 1 1 auto; max-width: 180px; height: 10px; border-radius: 5px; background: rgba(59, 40, 70, 0.25); overflow: hidden; }
.compost-jauge > span { display: block; height: 100%; background: linear-gradient(90deg, #4f355e, #735088); }
.compost-aliment { display: flex; align-items: center; gap: 6px; padding: 4px 0; }
.compost-aliment .compost-nom { flex: 1 1 auto; min-width: 0; }
.compost-aliment .btn { min-width: 44px; min-height: 44px; padding: 0 8px; }

/* les tonnelets (js/ui/tonnelet.js) : un tonnelet par ligne, ce qui s'y affine, ou les boutons pour le remplir */
.tonnelet-liste { list-style: none; margin: 4px 0 0; padding: 0; display: flex; flex-direction: column; }
.tonnelet-ligne { display: flex; flex-direction: column; gap: 4px; padding: 8px 0; border-top: 1px solid rgba(86, 56, 104, 0.25); }
.tonnelet-titre { font-weight: bold; }
.tonnelet-actions { display: flex; flex-wrap: wrap; gap: 6px; }
.tonnelet-actions .btn { display: inline-flex; align-items: center; gap: 6px; min-height: 44px; padding: 0 10px; }

/* La bannière d'un hameau du grand monde découvert (js/ui/stage.js, banniereHameau : fiche 7a) : son
   nom, en haut de la carte, quelques secondes ; un panneau de bois clair au liseré sombre. */
.hameau-banniere {
  position: fixed;
  top: calc(64px + env(safe-area-inset-top, 0px));
  left: 50%;
  transform: translate(-50%, -12px);
  z-index: var(--z-toast);
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  padding: 10px 28px 12px;
  max-width: calc(100vw - 32px);
  background: #cdb3dc;
  color: #2a1c32;
  border: 3px solid #412a4e;
  border-radius: 6px;
  box-shadow: 0 0 0 2px #cdb3dc, 0 6px 18px rgba(0, 0, 0, 0.35);
  text-align: center;
  pointer-events: none;
  opacity: 0;
  transition: opacity 0.6s ease, transform 0.6s ease;
}
.hameau-banniere.visible { opacity: 1; transform: translate(-50%, 0); }
.hameau-banniere strong { font-size: 1.5rem; letter-spacing: 0.02em; }
.hameau-banniere-sous { font-size: 0.85rem; opacity: 0.8; }
@media (prefers-reduced-motion: reduce) { .hameau-banniere { transition: none; } }
.encyclo-hameaux { margin: 0 0 12px; padding-left: 20px; }
/* Les habitants des hameaux (fiche 7b, js/carte/ferme/habitants.js) : la bulle d'un habitant
   qu'on touche, au-dessus de sa tête (son prénom, son métier, sa phrase), dans le calque des
   étiquettes ; la fiche du hameau (js/ui/habitants.js : ses familles, sa réserve). */
/* Le récit : la fenêtre d'une scène (js/ui/scene.js) — un portrait, un nom, une réplique, « Suite ». */
.scene-modal { max-width: 420px; }
.scene-ligne { display: flex; gap: 12px; align-items: flex-start; }
.scene-portrait { flex: none; display: block; }
.scene-parole { min-width: 0; }
.scene-nom { margin: 0 0 4px; font-size: 1.05rem; }
.scene-texte { margin: 0; font-size: 1.05rem; line-height: 1.5; min-height: 3em; }
.scene-pied { display: flex; justify-content: space-between; align-items: center; gap: 12px; margin-top: 14px; }
.scene-pied .btn { min-height: 44px; min-width: 44px; }

/* Le carnet du joueur (js/ui/carnet.js) : les pages trouvées, dans l'ordre, chacune son titre et son texte. */
.carnet-modal { max-width: 440px; }
.carnet-pages { list-style: none; margin: 0 0 14px; padding: 0; display: flex; flex-direction: column; gap: 12px; max-height: 60vh; overflow-y: auto; }
.carnet-page h3 { margin: 0 0 4px; font-size: 1.15rem; }
.carnet-page + .carnet-page { border-top: 1px dashed currentColor; padding-top: 10px; }
.carnet-page p { margin: 0; line-height: 1.5; font-style: italic; }
.carnet-modal .btn { min-height: 44px; }
/* Les promesses de Maurice (le récit, lot 6 : js/ui/caleche.js), en haut de l'onglet Vendre de la calèche. */
.promesses { list-style: none; margin: 0 0 12px; padding: 0; display: flex; flex-direction: column; gap: 10px; }
.promesse { display: flex; flex-wrap: wrap; align-items: center; gap: 6px 10px; }
.promesse-titre { flex: 1 1 100%; font-weight: 600; }
.promesse-besoins { flex: 1 1 auto; display: flex; flex-wrap: wrap; gap: 4px 10px; font-size: 0.9rem; }
.promesse-besoin.ok { opacity: 0.6; text-decoration: line-through; }
.promesse .btn { min-height: 44px; }
.promesse.tenue .promesse-titre { opacity: 0.7; }

.habitant-bulle {
  position: absolute;
  left: 0;
  top: 0;
  display: flex;
  flex-direction: column;
  gap: 1px;
  max-width: 220px;
  padding: 6px 10px 7px;
  background: #e6d7ef;
  color: #2a1c32;
  border: 2px solid #412a4e;
  border-radius: 6px;
  box-shadow: 0 3px 8px rgba(0, 0, 0, 0.3);
  font-size: 0.8rem;
  line-height: 1.25;
  pointer-events: none;
  will-change: transform;
}
.habitant-bulle::after {
  content: '';
  position: absolute;
  left: 50%;
  bottom: -8px;
  margin-left: -6px;
  border: 6px solid transparent;
  border-top: 6px solid #412a4e;
  border-bottom: 0;
}
.habitant-bulle strong { font-size: 0.9rem; }
.habitant-bulle-metier { font-size: 0.72rem; opacity: 0.75; }
/* une scène du récit sur la carte (js/carte/ferme/rencontre.js) : la bulle de qui parle ; celle du personnage du
   joueur, d'un autre ton ; le petit signe « appuie pour la suite » */
.rencontre-bulle { max-width: 240px; padding-right: 20px; }
.rencontre-bulle.joueur { background: #f2e8f8; border-color: #2f6a2a; }
.rencontre-bulle.joueur::after { border-top-color: #2f6a2a; }
.rencontre-aide { margin-top: 3px; font-size: 0.68rem; opacity: 0.65; font-style: italic; }
.rencontre-suite { position: absolute; right: 6px; bottom: 3px; font-size: 0.7rem; opacity: 0.7; animation: rencontre-suite 1.1s ease-in-out infinite; }
@keyframes rencontre-suite { 50% { transform: translateX(2px); opacity: 0.35; } }
@media (prefers-reduced-motion: reduce) { .rencontre-suite { animation: none; } }
/* l'amitié (js/ui/amitie.js) : le palier, la jauge, le bouton « Offrir » de la bulle */
.habitant-bulle-ami { display: flex; align-items: center; gap: 4px; margin-top: 3px; font-size: 0.72rem; }
.ami-jauge { display: inline-block; width: 46px; height: 6px; background: #bfa7cd; border: 1px solid #412a4e; border-radius: 3px; overflow: hidden; vertical-align: middle; }
.ami-jauge > span { display: block; height: 100%; background: #e8a33a; }
.ami-jauge.grande { width: 120px; height: 9px; }
.ami-gain { color: #2f7a2a; font-weight: 700; }
/* la bulle du compagnon (js/carte/ferme/etiquettes.js compagnonDit) : sa question et les réponses (js/ui/compagnon.js) */
.aide-bulle { max-width: 240px; }
.aide-bulle .habitant-bulle-texte { font-weight: 600; }
.aide-choix { display: flex; flex-wrap: wrap; gap: 4px; margin-top: 5px; }
.aide-bouton {
  pointer-events: auto;
  min-height: 34px;
  padding: 3px 10px;
  font: inherit;
  font-size: 0.8rem;
  color: #2a1c32;
  background: #d8c1e6;
  border: 2px solid #412a4e;
  border-radius: 6px;
  cursor: pointer;
}
.aide-bouton:hover, .aide-bouton:focus-visible { background: #ffd66b; }
.habitant-bulle-offrir {
  pointer-events: auto;
  align-self: flex-start;
  margin-top: 4px;
  padding: 2px 8px;
  font: inherit;
  font-size: 0.75rem;
  color: #2a1c32;
  background: #d8c1e6;
  border: 2px solid #412a4e;
  border-radius: 5px;
  cursor: pointer;
}
.habitant-bulle-offrir:hover, .habitant-bulle-offrir:focus-visible { background: #ffd970; }
/* l'émotion d'une réaction (js/carte/ferme/amis.js) : un emoji au-dessus de la tête */
.habitant-emo {
  position: absolute;
  left: 0;
  top: 0;
  font-size: 1rem;
  line-height: 1;
  pointer-events: none;
  will-change: transform;
  filter: drop-shadow(0 1px 1px rgba(0, 0, 0, 0.35));
}
body.construction .habitant-emo, body.construction .presents-porte { display: none !important; }
.ami-ligne { display: flex; flex-wrap: wrap; align-items: center; gap: 6px; }
.ami-palier { font-weight: 700; }
.ami-gouts { list-style: none; margin: 0 0 8px; padding: 0; display: grid; gap: 2px; font-size: 0.9rem; }
.ami-cadeaux { display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); gap: 6px; margin: 8px 0 12px; max-height: 45vh; overflow-y: auto; }
.ami-cadeau { justify-content: flex-start; text-align: left; }
.ami-marque { margin-left: 2px; }
.ami-mini { font-size: 0.78rem; white-space: nowrap; }
.ile-ami { font-size: 0.78rem; color: #562d6d; white-space: nowrap; }
.habitant-bulle-texte { margin-top: 2px; }
/* La visite de bienvenue (fiche 18, js/carte/ferme/visite.js) : le plat posé devant la porte, qui
   attend le retour du personnage. */
.visite-plat {
  position: absolute;
  left: 0;
  top: 0;
  padding: 2px 4px;
  font-size: 1.1rem;
  line-height: 1;
  background: #e6d7ef;
  border: 2px solid #412a4e;
  border-radius: 50%;
  box-shadow: 0 2px 5px rgba(0, 0, 0, 0.3);
  pointer-events: none;
  will-change: transform;
}
.hameau-familles, .hameau-reserve { list-style: none; margin: 0 0 12px; padding: 0; display: grid; gap: 6px; }
.hameau-famille { display: flex; align-items: center; gap: 10px; padding: 6px 8px; border-radius: 6px; background: rgba(255, 255, 255, 0.35); }
.hameau-portraits { display: flex; flex-shrink: 0; }
.hameau-portraits .perso-px { --s: var(--portrait-64, 64px); margin-right: -22px; }
.hameau-portraits .perso-px:last-child { margin-right: 0; }
.hameau-famille-texte { display: flex; flex-direction: column; gap: 3px; min-width: 0; }
.hameau-noms .muted { font-size: 0.85em; }
.hameau-bonheur { display: flex; align-items: center; gap: 6px; font-size: 0.8rem; flex-wrap: wrap; }
.hameau-bonheur .bar { width: 70px; }
.hameau-reserve { grid-template-columns: repeat(auto-fill, minmax(150px, 1fr)); gap: 4px 12px; }
.hameau-reserve li { display: flex; align-items: center; gap: 6px; }
/* Le récit, lot 7 : les ateliers d'un hameau garanti (js/ui/habitants.js) — une ligne par recette ou par meuble,
   le texte à gauche, les boutons à droite (ils passent dessous sur un téléphone étroit). */
.ile-atelier-titre { margin: 10px 0 4px; font-size: 1rem; }
.ile-liste { list-style: none; margin: 0 0 8px; padding: 0; display: grid; gap: 6px; }
.ile-recette, .ile-meuble { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: 4px 10px; }
.ile-recette .row { gap: 6px; margin: 0; }
.ile-liste .btn { min-height: 44px; }
.hameau-reserve .num { margin-left: auto; font-weight: 700; }
.hameau-reserve .gain { margin-left: 4px; color: #2f6b3a; font-size: 0.8rem; }
/* La calèche (fiche 7c, js/carte/ferme/caleche.js, js/ui/caleche.js) : l'icône au bord de l'écran
   quand elle est proche (sa flèche tournée vers elle ; « Héler » quand elle passe tout près), le
   bouton Héler au-dessus d'elle, la bulle de son arrivée à la ferme ; dans sa fenêtre, le bandeau
   (là, ou où elle est et quand elle passe à la ferme). */
.caleche-signe, .caleche-heler {
  position: absolute;
  left: 0;
  top: 0;
  display: flex;
  align-items: center;
  gap: 4px;
  padding: 4px 8px;
  background: #e6d7ef;
  color: #2a1c32;
  border: 2px solid #412a4e;
  border-radius: 999px;
  box-shadow: 0 3px 8px rgba(0, 0, 0, 0.3);
  font: inherit;
  font-size: 0.8rem;
  line-height: 1.1;
  pointer-events: auto;
  cursor: pointer;
  will-change: transform;
}
.caleche-signe[hidden], .caleche-heler[hidden] { display: none; }
.caleche-signe-ico { font-size: 1.15rem; }
.caleche-signe-fleche { display: inline-block; transform: rotate(var(--angle, 0rad)); color: #412a4e; }
.caleche-signe-heler { display: none; font-weight: bold; }
.caleche-signe.helable .caleche-signe-heler { display: inline; }
.caleche-signe.helable, .caleche-heler { background: #d8c1e6; animation: caleche-pouls 1.2s ease-in-out infinite; }
@keyframes caleche-pouls { 50% { box-shadow: 0 0 0 4px rgba(255, 200, 80, 0.55), 0 3px 8px rgba(0, 0, 0, 0.3); } }
@media (prefers-reduced-motion: reduce) { .caleche-signe.helable, .caleche-heler { animation: none; } }
.caleche-bulle { font-weight: bold; }
.caleche-bandeau {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
  margin: 0 0 8px;
  padding: 6px 10px;
  border: 2px solid rgba(65, 42, 78, 0.35);
  border-radius: 6px;
  background: rgba(241, 228, 249, 0.6);
  font-size: 0.85rem;
  line-height: 1.3;
}
.caleche-bandeau.ici { background: rgba(190, 226, 140, 0.55); }
.caleche-bandeau .caleche-ico { font-size: 1.5rem; flex: none; }
.caleche-bandeau .caleche-texte { flex: 1 1 180px; }
/* La malle de la calèche (js/ui/caleche.js, malleHtml) : son image (assets/malle.png, la case fermée) dans le
   bandeau ; les titres de ses sections, leur bouton à droite ; le titre des lots d'une fiche (Déposer, Commander). */
.caleche-bandeau .malle-ico {
  flex: none;
  width: 50px;
  height: 44px;
  background-repeat: no-repeat;
  background-size: 100px 44px;
  background-position: 0 0;
  image-rendering: pixelated;
}
.section-title.malle-titre { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.section-title.malle-titre .btn { margin-left: auto; }
.lot-titre { margin: 6px 0 2px; }
/* S'orienter (fiche 8). La boussole (js/carte/ferme/boussole.js) : sous l'horloge, à droite de la carte ;
   son cadran en gros pixels (un canevas de 30 px agrandi deux fois, sans lissage), dessous le but et sa
   distance sur une plaque de bois. Un appui ouvre la carte du monde. */
.boussole {
  position: absolute;
  top: calc(118px + env(safe-area-inset-top, 0px) - var(--header-h, 0px));
  right: calc(12px + env(safe-area-inset-right, 0px));
  z-index: 3;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  padding: 0;
  border: 0;
  background: none;
  font: inherit;
  cursor: pointer;
  filter: drop-shadow(0 3px 3px rgba(0, 0, 0, 0.35));
}
.boussole[hidden] { display: none; }
.boussole:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; border-radius: 8px; }
#farm-stage .boussole canvas.boussole-cadran { display: block; width: 60px !important; height: 60px !important; image-rendering: pixelated; cursor: pointer; }
.boussole-legende {
  display: flex;
  flex-direction: column;
  align-items: center;
  max-width: 132px;
  padding: 2px 8px 3px;
  background: #e6d7ef;
  color: #2a1c32;
  border: 2px solid #412a4e;
  border-radius: 6px;
  font-size: 0.72rem;
  line-height: 1.2;
}
.boussole-nom { font-weight: bold; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 116px; }
.boussole-distance { color: #4f375d; }
@media (max-width: 560px) {
  .boussole { top: calc(96px + env(safe-area-inset-top, 0px) - var(--header-h, 0px)); right: 8px; }
  #farm-stage .boussole canvas.boussole-cadran { width: 48px !important; height: 48px !important; }
  .boussole-legende { font-size: 0.66rem; max-width: 104px; }
}
/* La carte du monde (js/ui/carte-monde.js) : une grande fenêtre bois ; la carte en gros pixels, le
   brouillard par-dessus, les repères (des boutons) posés sur elle ; dessous, le lieu choisi. */
.modal.carte-monde {
  width: min(980px, calc(100vw - 16px));
  max-width: none;
  height: min(760px, calc(100dvh - 24px));
  display: flex;
  flex-direction: column;
  gap: 8px;
}
.modal-backdrop:has(.carte-monde) { align-items: center; padding: 8px; }
.carte-monde h2 { margin: 0; }
.carte-monde-cadre {
  position: relative;
  flex: 1 1 auto;
  min-height: 180px;
  overflow: hidden;
  border: 3px solid var(--color-earth);
  border-radius: 6px;
  background: #c9d0d8;
  touch-action: none;
  -webkit-user-select: none;
  user-select: none;
}
.carte-monde-canevas { position: absolute; inset: 0; width: 100%; height: 100%; cursor: grab; }
.carte-monde-canevas:active { cursor: grabbing; }
.carte-monde-reperes { position: absolute; inset: 0; pointer-events: none; }
.carte-monde-repere {
  position: absolute;
  left: 0;
  top: 0;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 1px;
  width: 0;
  margin: -14px 0 0 0;
  padding: 2px;
  border: 0;
  background: none;
  font: inherit;
  color: #2a1c32;
  pointer-events: auto;
  cursor: pointer;
}
.carte-monde-icone {
  display: grid;
  place-items: center;
  width: 24px;
  height: 24px;
  background: #e6d7ef;
  border: 2px solid #412a4e;
  border-radius: 50%;
  font-size: 0.9rem;
  box-shadow: 0 2px 3px rgba(0, 0, 0, 0.35);
}
.carte-monde-icone .px { --pxs: 16px; }
.carte-monde-repere.ferme .carte-monde-icone { width: 28px; height: 28px; }
.carte-monde-repere.caleche { pointer-events: none; margin: -2px 0 0 14px; }
.carte-monde-repere.caleche .carte-monde-icone { width: 20px; height: 20px; background: #d8c1e6; }
.carte-monde-repere.but .carte-monde-icone { border-color: #c03a24; box-shadow: 0 0 0 2px #ffd36a, 0 2px 3px rgba(0, 0, 0, 0.35); }
.carte-monde-repere.choisi .carte-monde-icone { background: #d8c1e6; transform: scale(1.15); }
.carte-monde-repere:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 1px; border-radius: 6px; }
.carte-monde-nom {
  padding: 1px 6px;
  background: rgba(230, 215, 239, 0.92);
  border: 1px solid #412a4e;
  border-radius: 4px;
  font-size: 0.72rem;
  font-weight: bold;
  white-space: nowrap;
}
.carte-monde-perso { position: absolute; left: 0; top: 0; width: 0; height: 0; pointer-events: none; }
.carte-monde-perso::before {
  content: '';
  position: absolute;
  left: -7px;
  top: -7px;
  width: 10px;
  height: 10px;
  background: #ffffff;
  border: 2px solid #c03a24;
  border-radius: 50%;
  box-shadow: 0 0 0 2px rgba(42, 28, 50, 0.6);
}
.carte-monde-fleche { position: absolute; left: 0; top: 0; width: 0; height: 0; }
.carte-monde-fleche::after {
  content: '';
  position: absolute;
  left: 8px;
  top: -6px;
  border: 6px solid transparent;
  border-left: 9px solid #c03a24;
  filter: drop-shadow(0 0 1px #2a1c32);
}
.carte-monde-zoom { position: absolute; right: 8px; top: 8px; display: flex; flex-direction: column; gap: 4px; }
.carte-monde-zoom .btn { min-width: 36px; min-height: 36px; padding: 0; font-size: 1.1rem; font-weight: bold; }
.carte-monde-attente { position: absolute; inset: 0; display: grid; place-items: center; margin: 0; color: #2a1c32; font-weight: bold; pointer-events: none; }
.carte-monde-attente[hidden] { display: none; }
.carte-monde-info { display: flex; flex-wrap: wrap; align-items: center; gap: 6px 12px; min-height: 36px; }
.carte-monde-info-nom { font-size: 1.05rem; }
.carte-monde-info-but { color: #8a2c18; font-weight: bold; }
.carte-monde-aide { margin: 0; font-size: 0.8rem; }
@media (max-width: 560px) {
  .carte-monde-aide { display: none; }
}

/* Options › Son (js/ui/son.js) : un curseur par volume */
.son-curseur { display: grid; grid-template-columns: minmax(0, 1fr) minmax(120px, 1.2fr); align-items: center; gap: 12px; min-height: 44px; }
.son-curseur input[type="range"] { width: 100%; accent-color: var(--accent); }
@media (max-width: 420px) { .son-curseur { grid-template-columns: 1fr; gap: 4px; } }

/* L'écran de chargement (jeu.html, #chargement) : par-dessus tout, sur le fond de la page, le
   temps que la carte soit dessinée. Quatre carottes du potager (assets/crops.png, la carotte : son
   sprite de data/crops.json, rangée 0, colonnes 0 à 3, une case de 24 × 44 agrandie 3 fois sans
   lissage) poussent stade par stade dans une bande de terre (assets/soil_dry.png), puis l'écran
   s'efface en fondu. Le milieu de leur butte (à 39,8 px du haut de la case, comme sur la carte :
   scripts/carte/planche_cultures.py, TACHE) est posé au milieu de la bande : -36 px (132 - 119,4,
   plus les 23 px du haut de la bande à son milieu). */
.chargement {
  position: fixed;
  inset: 0;
  z-index: 1000;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 22px;
  padding: 24px;
  background: var(--bg);
  color: var(--text);
  transition: opacity 0.4s ease-out;
}
.chargement.fini { opacity: 0; pointer-events: none; }
.chargement-titre { margin: 0; font-size: 32px; font-weight: normal; color: var(--text); }
/* l'écran de chargement : un soir prune, où les lettres du logo se lisent */
.chargement { background: radial-gradient(circle at 50% 35%, #4a3a6a, var(--prune) 70%); }
.chargement .chargement-texte { color: #f0b8f3; }
/* le logo (assets/logo.png, 90 × 45) agrandi sans lissage, sur le soir prune */
.chargement-titre img { display: block; width: 270px; max-width: 80vw; height: auto; image-rendering: pixelated; }
.chargement-rang { display: flex; flex-direction: column; align-items: stretch; }
.chargement-plants { display: flex; gap: 4px; padding: 0 10px; margin-bottom: -36px; position: relative; z-index: 1; }
.chargement-plants i {
  width: 72px;
  height: 132px;
  background: url('../assets/crops.png') no-repeat 0 0 / 360px 2376px;
  image-rendering: pixelated;
}
.chargement-plants i[data-stade="1"] { background-position: -72px 0; }
.chargement-plants i[data-stade="2"] { background-position: -144px 0; }
.chargement-plants i[data-stade="3"] { background-position: -216px 0; }
.chargement-terre {
  height: 40px;
  border: 3px solid var(--color-earth);
  border-radius: 4px;
  background: url('../assets/soil_dry.png') 0 0 / 64px 64px;
  image-rendering: pixelated;
  box-shadow: inset 0 0 0 2px var(--wood-light), 0 4px 0 rgba(42, 28, 50, 0.35);
}
.chargement-texte { font-size: 20px; color: var(--color-earth); }
@media (prefers-color-scheme: dark) { .chargement-texte { color: var(--wood-light); } }
@media (prefers-reduced-motion: reduce) { .chargement { transition: none; } }

/* L'outil pièce (js/ui/chantier.js, build-piece) : un carré du même bois que celui du niveau, à
   côté de lui ; allumé, il prend le jaune de la case choisie. */
.build-piece {
  box-sizing: border-box;
  width: 34px; height: 34px; padding: 0;
  display: grid; place-items: center;
  background: rgba(var(--wood-bg-rgb), 0.92);
  border: 3px solid var(--color-earth); border-radius: 6px;
  box-shadow: inset 0 0 0 2px var(--wood-glow);
  color: var(--color-earth);
  cursor: pointer;
}
.build-piece.on { background: #f0d4f2; box-shadow: inset 0 0 0 2px var(--color-earth); }
.build-piece:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 1px; }
.build-piece:disabled { opacity: 0.45; cursor: default; }
.build-gomme.on { background: #d8c1e6; }
.build-tourner span, .build-sens span { font-size: 1.1rem; font-weight: 700; line-height: 1; }
.build-tourner.on { background: #cfe8ff; }

/* ---------- Étape E6 du chantier « couches » : l'apparence d'un membre, attribut par attribut (js/ui/famille.js) ---------- */
.apparence-choix summary { cursor: pointer; padding: 4px 0; }
/* Les couleurs du bois (celles de la fenêtre Famille et de l'accueil), dans la fenêtre « Modifier » aussi. */
#apparence-choix {
  margin-top: 6px; padding: 8px 10px 10px; border-radius: 10px; color: var(--wood-ink);
  background: var(--wood-cream); border: 3px solid var(--wood-dark); box-shadow: inset 0 0 0 2px var(--wood-light);
}
.btn.primary.apparence-hasard {
  display: block; margin: 0 auto 4px; min-height: 40px; padding: 4px 16px; border-radius: 999px;
  background: var(--color-sun); border: 2px solid var(--wood-dark); color: #1c0f24; font-weight: 700;
}
.apparence-groupe { border: 0; border-top: 2px dashed var(--wood-light); margin: 10px 0 0; padding: 4px 0 0; min-width: 0; }
.apparence-groupe legend { padding: 0 6px 0 0; font-size: 0.75rem; text-transform: uppercase; letter-spacing: 0.08em; color: var(--wood-ink); opacity: 0.65; }
.apparence-champ { margin-top: 8px; }
.apparence-titre { margin: 0 0 4px; font-size: 0.95rem; color: var(--wood-ink); }
.apparence-valeur { font-size: 0.85rem; opacity: 0.7; }
.apparence-options { display: flex; flex-wrap: wrap; gap: 6px; padding: 4px 0 4px 6px; } /* (de quoi voir l'anneau de la pastille choisie) */
/* les couleurs : des pastilles rondes, la choisie cerclée de jaune et cochée */
.pastille-apparence {
  position: relative; width: 36px; height: 36px; padding: 0; border-radius: 50%; cursor: pointer;
  border: 2px solid var(--wood-dark);
}
.pastille-apparence.active { box-shadow: 0 0 0 3px var(--wood-cream), 0 0 0 6px var(--color-sun); }
.pastille-apparence.active::after {
  content: '✓'; position: absolute; inset: 0; display: grid; place-items: center;
  color: #fff; font-size: 16px; text-shadow: 0 0 2px #000, 0 0 2px #000;
}
/* les formes : la tête du personnage avec ce choix */
.vignette-apparence {
  min-width: 62px; padding: 3px 3px 2px; border: 2px solid var(--wood-dark); border-radius: 8px; cursor: pointer;
  background: var(--wood-paper); color: var(--wood-ink); font: inherit; font-size: 0.65rem; line-height: 1.1; text-align: center;
  display: flex; flex-direction: column; align-items: center; gap: 2px;
}
.vignette-apparence img { width: 32px; height: 32px; image-rendering: pixelated; }
.apparence-options .vignette-apparence span { font-size: 10px; letter-spacing: -0.03em; line-height: 1.15; overflow-wrap: normal; white-space: normal; }
.vignette-apparence.active { outline: 3px solid var(--color-sun); outline-offset: 1px; background: #dec7ec; }
/* le reste (le motif, les signes, les accessoires) : des puces */
.choix-apparence {
  min-height: 34px; padding: 3px 12px; font: inherit; font-size: 0.85rem; border-radius: 999px; cursor: pointer;
  background: var(--wood-paper); border: 2px solid var(--wood-dark); color: var(--wood-ink);
}
.choix-apparence.active { background: var(--color-sun); color: #1c0f24; font-weight: 700; }

/* E-2 : le bandeau du monde en ligne (js/ui/en-ligne.js), en haut, au milieu */
.en-ligne-bandeau {
  position: fixed;
  top: calc(env(safe-area-inset-top, 0px) + 4px);
  left: 50%;
  transform: translateX(-50%);
  z-index: 60;
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 4px 6px 4px 12px;
  border-radius: 999px;
  border: 2px solid var(--border);
  background: var(--bg-card, #ebdcf4);
  color: var(--text);
  font-size: 0.85rem;
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.25);
  max-width: calc(100vw - 16px);
}
.en-ligne-bandeau .btn { min-height: 32px; padding: 2px 10px; font-size: 0.8rem; white-space: nowrap; flex: none; }
.en-ligne-etat { white-space: nowrap; min-width: 0; overflow: hidden; text-overflow: ellipsis; }
/* Sur un écran étroit, la carte du joueur (en haut à gauche), la lune et la boussole (à droite) occupent
   le haut : le bandeau passe sous la carte du joueur (≈ 50 pixels du jeu, --hud-px), à gauche de la
   boussole, sur deux lignes (l'état, puis les boutons), « Ma ferme solo » dit « solo ». */
@media (max-width: 820px) {
  .en-ligne-bandeau {
    top: calc(env(safe-area-inset-top, 0px) + 12px + 50 * var(--hud-px, 2px));
    left: calc(8px + env(safe-area-inset-left, 0px));
    transform: none;
    max-width: calc(100vw - 16px - 50 * var(--hud-px, 2px));
    flex-wrap: wrap;
    gap: 4px 6px;
    padding: 4px 6px;
    border-radius: 16px;
    font-size: 0.8rem;
  }
  .en-ligne-bandeau .btn { min-height: 30px; padding: 2px 8px; }
  .en-ligne-etat { flex-basis: 100%; padding-left: 4px; }
  .en-ligne-bandeau .btn .en-ligne-mot { display: none; }
}

/* L'écran d'accueil (js/ui/ecran-titre.js) : la grande ferme vivante en plein écran (js/ui/accueil-vivant.js),
   l'enseigne de bois en haut, les deux boutons en bas. */
#ecran-titre {
  position: fixed; inset: 0; z-index: 1001;   /* au-dessus de l'écran de chargement (#chargement, 1000) */
  overflow: hidden; background: #3c6b2c; color: var(--wood-ink);
}
/* la ferme vivante : un canvas (js/ui/accueil-vivant.js), qui paraît en fondu une fois ses images chargées */
.titre-ferme { position: absolute; inset: 0; width: 100%; height: 100%; display: block; opacity: 0; transition: opacity 0.6s ease-out; }
.titre-ferme.pret { opacity: 1; }
.titre-enseigne, .titre-boutons {
  position: absolute; left: 50%; transform: translateX(-50%);
  background: rgba(var(--wood-bg-rgb), 0.96);
  border: 3px solid var(--color-earth); border-radius: 8px;
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 4px 0 rgba(42, 28, 50, 0.35);
}
.titre-enseigne { top: max(8%, calc(16px + env(safe-area-inset-top))); width: min(86%, 460px); padding: 14px 20px 12px; text-align: center; }
/* l'enseigne : la prune du logo, sur laquelle ses lettres lavande se lisent */
.titre-enseigne { background: var(--prune); border-color: var(--wood-dark); box-shadow: inset 0 0 0 2px var(--wood-light), 0 4px 0 rgba(30, 21, 48, 0.45); }
.titre-nom { margin: 0; font-size: clamp(32px, 9vw, 48px); font-weight: normal; line-height: 1; }
.titre-nom img { display: block; width: 360px; max-width: 100%; height: auto; margin: 0 auto; image-rendering: pixelated; }
.titre-slogan { margin: 8px 0 0; font-size: 1.05rem; color: #f0b8f3; }
.titre-boutons {
  bottom: max(7%, calc(16px + env(safe-area-inset-bottom))); width: min(88%, 400px);
  display: grid; gap: 12px; padding: 14px;
}
.titre-btn {
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  min-height: 56px; padding: 6px 16px; width: 100%;
  border: 3px solid var(--color-earth); border-radius: 7px;
  font: inherit; font-size: 1.25rem; line-height: 1.2; white-space: nowrap; cursor: pointer;
  background: #ecdaf7; color: var(--wood-ink);
  box-shadow: inset 0 0 0 2px var(--wood-glow), 0 3px 0 #2a1c32;
}
.titre-btn.primary { background: #444f9f; color: #fff; box-shadow: inset 0 0 0 2px #7480d6, 0 3px 0 #2a1c32; }
.titre-btn:active { transform: translateY(2px); box-shadow: none; }
.titre-btn:focus-visible { outline: 3px solid var(--color-sun); outline-offset: 2px; }
.titre-info { font-size: 0.8rem; opacity: 0.8; white-space: normal; }
.titre-question { margin: 0; text-align: center; }
/* la partie d'avant (js/ui/transfert.js) : le bouton, plus discret, et le message au retour de l'ancienne adresse */
.titre-btn.titre-pont { min-height: 44px; font-size: 1rem; }
.titre-message { margin: 0; padding: 6px 8px; border-radius: 6px; background: #f6efc8; text-align: center; font-size: 0.95rem; line-height: 1.35; }
.titre-erreur { position: absolute; left: 50%; bottom: 2%; transform: translateX(-50%); margin: 0; padding: 4px 10px; border-radius: 6px; background: rgba(0, 0, 0, 0.6); color: #fff; }

/* Les chaînes de production : le mode d'emploi illustré et le diagnostic (js/ui/chaines-aide.js). La rangée : les
   dessins des blocs de la carte, côte à côte sur un bout d'herbe ; la place d'un bloc qui manque : un « ? » rouge. */
.chaine-rangee {
  display: flex; justify-content: center; gap: 4px; margin: 8px 0; padding: 8px 4px 4px;
  border-radius: 8px; background: #cfe3a8; overflow-x: auto;
}
.chaine-case { display: flex; flex-direction: column; align-items: center; flex: 1 1 0; min-width: 0; max-width: 70px; }
.chaine-case small { font-size: 9px !important; line-height: 1.1; text-align: center; white-space: nowrap; color: var(--color-ink); }
.chaine-case.bout small { white-space: normal; }
.chaine-dessin .build-slot-dessin { width: 32px; height: 48px; }
.chaine-vide {
  display: flex; align-items: center; justify-content: center; width: 30px; height: 30px; margin: 16px 0 2px;
  border: 2px dashed var(--color-earth); border-radius: 6px; color: var(--color-earth); font-size: 18px !important;
}
.chaine-case.manque .chaine-vide { border-color: var(--danger); color: var(--danger); background: #fbe1dc; }
.chaine-regles { margin: 6px 0; padding-left: 22px; }
.chaine-regles li { margin: 2px 0; }
.chaine-astuce { margin: 8px 0; padding: 6px 8px; border-radius: 8px; background: var(--bg-header); }
.chaine-recettes { list-style: none; margin: 0 0 10px; padding: 0; }
.chaine-recette { display: flex; align-items: center; gap: 4px; padding: 4px 2px; border-bottom: 1px solid var(--border); }
.chaine-recette.verrou { opacity: 0.45; }
.chaine-outils { display: flex; flex: 0 0 auto; }
.chaine-mini .build-slot-dessin { width: 16px; height: 24px; background-size: auto 24px; background-position: calc(var(--f) * -16px) 0; }
.chaine-fleche { margin: 0 2px; }
.chaine-produit { font-size: 22px !important; }
.chaine-recette-txt { display: flex; flex-direction: column; min-width: 0; }
.chaine-recette-txt small { font-size: 13px !important; color: var(--text-muted); }
.chaine-cadenas { margin-left: auto; }
.chaine-diag { list-style: none; margin: 6px 0 10px; padding: 0; }
.chaine-diag li { margin: 4px 0; padding: 4px 8px; border-radius: 6px; }
.chaine-diag li.ok { background: #e5f0dc; }
.chaine-diag li.ko { background: #fbe1dc; }
.chaine-diag li.info { background: var(--bg-header); }
.chaine-boutons { display: flex; gap: 8px; flex-wrap: wrap; }
.chaine-aide-btn { margin-top: 8px; width: 100%; }

/* les bacs à fleurs : la fenêtre « Semer » (js/ui/bacs.js) */
.bac-graines { list-style: none; margin: 0.6em 0 1em; padding: 0; display: grid; gap: 0.4em; }
.bac-graine { width: 100%; display: flex; align-items: center; gap: 0.5em; text-align: left; }
.bac-graine .bac-graine-nom { flex: 1; }
.bac-graine small { white-space: nowrap; opacity: 0.8; }
.bac-astuce { font-style: italic; }

/* ---------- Les amis (js/ui/amis.js) : le bouton 💌, le volet, la fiche ---------- */
.amis-bouton {
  position: fixed;
  top: calc(212px + env(safe-area-inset-top, 0px) - var(--header-h, 0px));
  right: calc(12px + env(safe-area-inset-right, 0px));
  z-index: var(--z-fab);
  width: 46px; height: 46px; border-radius: 50%;
  display: grid; place-items: center;
  font-size: 1.35rem; line-height: 1;
  background: var(--wood-cream); border: 3px solid var(--prune);
  box-shadow: 0 2px 6px rgba(0, 0, 0, 0.3);
  cursor: pointer;
}
.amis-bouton:focus-visible { outline: 3px solid var(--rose); outline-offset: 2px; }
body:has(#modal-root > *) .amis-bouton { opacity: 0.2; pointer-events: none; }
.amis-pastille {
  display: inline-block; min-width: 18px; padding: 0 5px; border-radius: 9px;
  background: var(--rose); color: #fff; font-size: 0.72rem; font-weight: 700; line-height: 18px; text-align: center;
}
.amis-bouton .amis-pastille { position: absolute; top: -4px; right: -4px; box-shadow: 0 0 0 2px var(--wood-cream); }
#amis-volet { position: fixed; inset: 0; z-index: calc(var(--z-modal) - 1); }
.amis-fond { position: absolute; inset: 0; background: rgba(30, 21, 48, 0.25); }
.amis-panneau {
  position: absolute; top: 0; right: 0; bottom: 0; width: min(320px, 82vw);
  display: flex; flex-direction: column;
  background: var(--wood-cream); color: var(--wood-ink);
  border-left: 4px solid var(--prune); box-shadow: -6px 0 18px rgba(0, 0, 0, 0.35);
  animation: amis-entre 0.2s ease-out;
}
@keyframes amis-entre { from { transform: translateX(100%); } }
.amis-panneau header {
  display: flex; align-items: center; gap: 8px;
  padding: calc(10px + env(safe-area-inset-top, 0px)) 12px 10px;
  background: var(--prune); color: var(--wood-cream); font-weight: 700; font-size: 1.05rem;
}
.amis-x { margin-left: auto; min-width: 40px; min-height: 40px; background: none; border: 0; color: var(--wood-cream); font-size: 1.2rem; cursor: pointer; }
.amis-liste { flex: 1; overflow-y: auto; padding-bottom: 8px; }
.amis-liste h3 { margin: 12px 12px 4px; font-size: 0.78rem; text-transform: uppercase; letter-spacing: 1px; color: var(--text-muted); }
.amis-v { display: flex; align-items: center; gap: 6px; padding: 4px 10px; }
.amis-qui { flex: 1; min-width: 0; display: flex; align-items: center; gap: 8px; padding: 2px; background: none; border: 0; border-radius: 10px; text-align: left; color: inherit; font: inherit; cursor: pointer; }
.amis-qui:hover, .amis-qui:focus-visible { background: var(--wood-paper); }
.amis-id { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 2px; }
.amis-id > * { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.amis-niv { display: inline-block; padding: 0 6px; border-radius: 999px; background: var(--prune); color: var(--wood-cream); font-size: 0.72rem; font-weight: 700; vertical-align: 1px; }
.amis-ou { font-size: 0.78rem; color: var(--text-muted); }
.amis-ou.on { color: #3d8a47; font-weight: 700; }
.amis-v.off .amis-av { filter: grayscale(0.7) brightness(0.92); opacity: 0.85; }
.amis-rond { flex: none; width: 40px; min-width: 40px; height: 40px; min-height: 40px; padding: 0; border-radius: 50%; font-size: 1rem; }
.amis-av {
  display: inline-block; flex: none;
  width: calc(16px * var(--k)); height: calc(32px * var(--k));
  background-repeat: no-repeat; background-size: calc(128px * var(--k)) calc(448px * var(--k)); background-position: 0 0;
  image-rendering: pixelated;
}
.amis-av.marche { animation: amis-marche 0.72s steps(1) infinite; }
.amis-av.respire { animation: amis-respire 1.2s steps(1) infinite; }
@keyframes amis-marche {
  0% { background-position: calc(-32px * var(--k)) 0; } 25% { background-position: calc(-48px * var(--k)) 0; }
  50% { background-position: calc(-64px * var(--k)) 0; } 75% { background-position: calc(-80px * var(--k)) 0; }
}
@keyframes amis-respire { 0% { background-position: 0 0; } 50% { background-position: calc(-16px * var(--k)) 0; } }
@media (prefers-reduced-motion: reduce) { .amis-av.marche, .amis-av.respire, .amis-panneau { animation: none; } }
.amis-msg { display: flex; align-items: center; gap: 8px; margin: 4px 10px; padding: 8px; border-radius: 12px; background: var(--rose-pale); border: 2px solid var(--rose); font-size: 0.85rem; }
.amis-msg span { flex: 1; }
.amis-msg .btn { flex: none; min-height: 36px; padding: 2px 10px; font-size: 0.82rem; }
.amis-vide, .amis-attente { margin: 12px; color: var(--text-muted); font-size: 0.88rem; }
.amis-pied { padding: 10px 12px calc(10px + env(safe-area-inset-bottom, 0px)); border-top: 2px solid var(--border); display: flex; flex-direction: column; gap: 6px; }
.amis-pied > .btn { width: 100%; }
.amis-ajout { display: flex; flex-direction: column; gap: 6px; font-size: 0.85rem; }
.amis-ajout p { margin: 0; }
.amis-code { font-size: 1.05rem; letter-spacing: 1px; color: var(--prune); user-select: all; }
.amis-ajout .row { display: flex; gap: 6px; flex-wrap: wrap; }
.amis-ajout input { flex: 1; min-width: 0; min-height: 40px; padding: 4px 10px; font: inherit; font-size: 1rem; text-transform: uppercase; border-radius: 10px; border: 2px solid var(--wood-light); background: #fff; color: var(--wood-ink); }
.amis-fiche-fond { position: absolute; inset: 0; background: rgba(30, 21, 48, 0.35); }
.amis-fiche {
  position: absolute; left: 0; right: 0; bottom: 0; max-width: 520px; margin: 0 auto;
  padding: 10px 16px calc(16px + env(safe-area-inset-bottom, 0px));
  background: var(--wood-cream); color: var(--wood-ink);
  border-top: 4px solid var(--prune); border-radius: 18px 18px 0 0; box-shadow: 0 -8px 20px rgba(0, 0, 0, 0.35);
  animation: amis-monte 0.2s ease-out;
}
@keyframes amis-monte { from { transform: translateY(100%); } }
.amis-poignee { display: block; width: 60px; height: 18px; margin: 0 auto 6px; background: none; border: 0; cursor: pointer; position: relative; }
.amis-poignee::after { content: ''; position: absolute; left: 8px; right: 8px; top: 6px; height: 5px; border-radius: 3px; background: var(--border); }
.amis-fiche-haut { display: flex; gap: 14px; align-items: flex-end; }
.amis-socle { flex: none; width: 96px; height: 118px; border-radius: 14px; display: flex; justify-content: center; align-items: flex-end; background: linear-gradient(var(--lavande) 0 60%, #7fb069 60%); }
.amis-socle.off { background: linear-gradient(#444f9f 0 60%, #4f7a4a 60%); }
.amis-socle .amis-av { margin-bottom: 4px; }
.amis-fiche-id { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 4px; font-size: 0.9rem; }
.amis-fiche-id h2 { margin: 0; }
.amis-fiche-actions { margin-top: 12px; gap: 6px; }
.amis-fiche-actions .row { display: flex; gap: 6px; }
.amis-fiche-actions .row .btn { flex: 1; }
