/* ==========================================================================
   DigitCraft — Design System v5 "Atelier Démo"
   Palette : Beige #f1f2eb · Bleu nuit #114b5f · Vert d'eau #1ea896 · Blanc
   Typo : Space Grotesk (titres) + Inter (texte) + JetBrains Mono (repères)

   Objectif : le site ne décrit plus seulement les prestations, il en fait la
   démonstration — un chatbot avec lequel on peut vraiment discuter, une carte
   de fidélité Fidzy cliquable et animée, un schéma d'automatisation vivant,
   une étude de cas mise en avant en grand format. Navigation repensée en
   dock flottant façon application, plus de menu plein écran, plus de listes
   numérotées façon dossier — nouvelle structure de page à chaque section.
   ========================================================================== */

:root {
  --color-cream: #f1f2eb;
  --color-cream-dark: #e3e5d6;
  --color-navy: #114b5f;
  --color-navy-deep: #0a2e3a;
  --color-navy-soft: #1c6478;
  --color-teal: #1ea896;
  --color-teal-light: #3fd1bd;
  --color-teal-deep: #157567;
  --color-white: #ffffff;

  --text-strong: var(--color-navy-deep);
  --text-body: #3c5561;
  --text-muted: #5c747d;
  --text-on-dark: rgba(255, 255, 255, 0.92);
  --text-on-dark-muted: rgba(255, 255, 255, 0.64);

  --surface-page: var(--color-cream);
  --surface-card: var(--color-white);
  --surface-dark: var(--color-navy-deep);
  --border-soft: rgba(10, 46, 58, 0.22);
  --border-strong: var(--color-navy-deep);

  --shadow-hard-sm: 5px 5px 0 rgba(10, 46, 58, 0.14);
  --shadow-float: 0 16px 40px rgba(10, 46, 58, 0.22);

  --font-heading: 'Space Grotesk', 'Segoe UI', sans-serif;
  --font-body: 'Inter', 'Segoe UI', sans-serif;
  --font-mono: 'JetBrains Mono', ui-monospace, 'SFMono-Regular', Menlo, monospace;

  --radius-xs: 3px;
  --radius-sm: 5px;
  --radius-md: 8px;
  --section-pad: clamp(64px, 9vw, 128px);
  --container-w: 1180px;

  --ease-out: cubic-bezier(0.16, 1, 0.3, 1);
  --ease-inout: cubic-bezier(0.65, 0, 0.35, 1);
  --dur-fast: 0.18s;
  --dur-medium: 0.3s;
  --dur-slow: 0.6s;
}

/* ==========================================================================
   Reset
   ========================================================================== */

*, *::before, *::after { box-sizing: border-box; }
html { scroll-behavior: smooth; -webkit-text-size-adjust: 100%; }

@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after {
    animation-duration: 0.001ms !important;
    animation-iteration-count: 1 !important;
    transition-duration: 0.001ms !important;
    scroll-behavior: auto !important;
  }
}

body {
  margin: 0;
  font-family: var(--font-body);
  /* Grain très subtil (bruit SVG en fond, sous le contenu) : casse le côté trop
     lisse/générique d'un aplat de couleur pur, sans que ce soit perceptible
     consciemment — juste un peu plus "matière", plus artisanal. */
  background-color: var(--surface-page);
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 180 180'%3E%3Cfilter id='n'%3E%3CfeTurbulence type='fractalNoise' baseFrequency='0.85' numOctaves='2' stitchTiles='stitch' result='t'/%3E%3CfeColorMatrix in='t' type='matrix' values='0 0 0 0 0.043  0 0 0 0 0.184  0 0 0 0 0.231  0 0 0 0.05 0'/%3E%3C/filter%3E%3Crect width='100%25' height='100%25' filter='url(%23n)'/%3E%3C/svg%3E");
  background-repeat: repeat;
  color: var(--text-body);
  line-height: 1.65;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
}

img, svg, video { max-width: 100%; display: block; }
a { color: inherit; text-decoration: none; }
ul, ol { list-style: none; margin: 0; padding: 0; }
button { font: inherit; cursor: pointer; }

h1, h2, h3, h4, h5, h6 {
  font-family: var(--font-heading);
  color: var(--text-strong);
  line-height: 1.1;
  margin: 0 0 0.5em;
  letter-spacing: -0.015em;
}
h1 { font-size: clamp(2.4rem, 4.8vw, 4.2rem); font-weight: 700; }
h2 { font-size: clamp(1.9rem, 3.2vw, 2.75rem); font-weight: 700; }
h3 { font-size: clamp(1.35rem, 2vw, 1.65rem); font-weight: 600; }
h4 { font-size: 1.15rem; font-weight: 600; }
p { margin: 0 0 1em; }

.container {
  width: 100%;
  max-width: var(--container-w);
  margin-inline: auto;
  padding-inline: clamp(20px, 5vw, 32px);
}

section { padding-block: var(--section-pad); }

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

.skip-link {
  position: absolute; left: 12px; top: -60px;
  background: var(--color-navy-deep); color: #fff;
  padding: 12px 18px; border-radius: var(--radius-xs);
  z-index: 1000; transition: top var(--dur-fast) var(--ease-out);
}
.skip-link:focus { top: 12px; }

a:focus-visible, button:focus-visible, input:focus-visible,
textarea:focus-visible, select:focus-visible {
  outline: 3px solid var(--color-teal); outline-offset: 3px; border-radius: 2px;
}

/* ==========================================================================
   Eyebrow / tag
   ========================================================================== */

.eyebrow {
  display: inline-flex; align-items: center; gap: 10px;
  font-family: var(--font-mono); font-size: 0.78rem; font-weight: 500;
  letter-spacing: 0.09em; text-transform: uppercase;
  color: var(--color-teal-deep); margin-bottom: 16px;
}
.eyebrow::before { content: ''; width: 22px; height: 2px; background: var(--color-teal); }
.on-dark .eyebrow { color: var(--color-teal-light); }

.section-head { max-width: 640px; margin-bottom: 44px; }
.section-head.center { margin-inline: auto; text-align: center; }
.section-head.center .eyebrow { justify-content: center; }
.section-head p { color: var(--text-muted); font-size: 1.05rem; }

/* ==========================================================================
   Boutons — rectangulaires
   ========================================================================== */

.btn {
  position: relative;
  display: inline-flex; align-items: center; justify-content: center; gap: 10px;
  padding: 15px 28px; border-radius: var(--radius-sm);
  font-family: var(--font-heading); font-weight: 600; font-size: 0.98rem;
  border: 2px solid transparent;
  transition: transform var(--dur-fast) var(--ease-out), box-shadow var(--dur-fast) var(--ease-out),
              background var(--dur-fast) var(--ease-out), color var(--dur-fast) var(--ease-out),
              border-color var(--dur-fast) var(--ease-out);
  white-space: nowrap;
}
.btn:active { transform: translate(0, 0) !important; box-shadow: none !important; }
/* Sur mobile, certains libellés de bouton sont trop longs pour tenir sur une ligne
   (ex. "Choisir un créneau sur Google Calendar") : autoriser le retour à la ligne
   plutôt que de laisser le texte déborder de son conteneur. */
@media (max-width: 640px) {
  .btn { white-space: normal; text-align: center; }
}

.btn-primary { background: var(--color-navy-deep); border-color: var(--color-navy-deep); color: #fff; }
.btn-primary:hover { background: var(--color-teal); border-color: var(--color-teal); transform: translate(-3px, -3px); box-shadow: var(--shadow-hard-sm); }

.btn-secondary { background: transparent; color: var(--color-navy-deep); border-color: var(--color-navy-deep); }
.btn-secondary:hover { background: var(--color-navy-deep); color: #fff; transform: translate(-3px, -3px); box-shadow: var(--shadow-hard-sm); }

.on-dark .btn-secondary, .cta-band .btn-secondary { color: #fff; border-color: rgba(255,255,255,0.5); }
.on-dark .btn-secondary:hover, .cta-band .btn-secondary:hover { background: #fff; color: var(--color-navy-deep); border-color: #fff; }
/* Bug corrigé : les cartes de démo (fond clair) posées dans une section .on-dark
   héritaient quand même du style "bouton secondaire blanc" pensé pour un fond
   sombre direct — texte blanc sur carte blanche, donc invisible (repéré ici sur
   "Réinitialiser" et sur les nouveaux boutons de la Roue Avis). Ces cartes gardent
   leur propre style clair quel que soit le fond de la section qui les entoure. */
.on-dark .demo-loyalty .btn-secondary, .on-dark .demo-roue .btn-secondary {
  color: var(--color-navy-deep); border-color: var(--color-navy-deep);
}
.on-dark .demo-loyalty .btn-secondary:hover, .on-dark .demo-roue .btn-secondary:hover {
  background: var(--color-navy-deep); color: #fff; border-color: var(--color-navy-deep);
}
.cta-band .btn-primary { background: #fff; color: var(--color-navy-deep); border-color: #fff; }
.cta-band .btn-primary:hover { background: var(--color-teal-light); border-color: var(--color-teal-light); }

.btn svg { width: 18px; height: 18px; transition: transform var(--dur-fast) var(--ease-out); }
.btn:hover svg { transform: translateX(3px); }
.btn-sm { padding: 10px 18px; font-size: 0.88rem; }

/* ==========================================================================
   Barre supérieure — fine, logo + un seul CTA (la navigation vit dans le dock)
   ========================================================================== */

.site-header {
  position: sticky; top: 0; z-index: 500;
  background: var(--surface-page);
  border-bottom: 2px solid var(--border-strong);
}
.nav-bar { display: flex; align-items: center; justify-content: space-between; padding-block: 16px; }
.brand { display: inline-flex; align-items: center; }
.brand-logo { height: 46px; width: auto; display: block; transition: transform var(--dur-medium) var(--ease-out); }
.brand:hover .brand-logo { transform: scale(1.05); }
.footer-brand .brand-logo { height: 54px; }
@media (max-width: 560px) { .brand-logo { height: 38px; } }
.nav-cta { display: flex; align-items: center; gap: 10px; }
@media (max-width: 560px) { .nav-cta .btn-secondary { display: none; } }

/* ==========================================================================
   Dock — navigation flottante façon application (remplace tout menu classique)
   ========================================================================== */

.app-dock {
  position: fixed; left: 50%; bottom: 18px; transform: translateX(-50%);
  z-index: 700; display: flex; align-items: stretch; gap: 2px;
  background: var(--color-navy-deep); border: 2px solid var(--color-navy-deep);
  border-radius: var(--radius-md); box-shadow: var(--shadow-float); padding: 6px;
}
.dock-item { position: relative; }
.dock-link, .dock-btn {
  display: flex; flex-direction: column; align-items: center; justify-content: center; gap: 4px;
  padding: 9px 15px; border-radius: var(--radius-sm);
  color: rgba(255,255,255,0.72); border: none; background: transparent;
  font-family: var(--font-mono); font-size: 0.64rem; text-transform: uppercase; letter-spacing: 0.03em;
  transition: background var(--dur-fast) var(--ease-out), color var(--dur-fast) var(--ease-out);
}
.dock-link svg, .dock-btn svg { width: 19px; height: 19px; transition: transform var(--dur-fast) var(--ease-out); }
.dock-link:hover, .dock-btn:hover { color: #fff; background: rgba(255,255,255,0.1); }
.dock-link:hover svg, .dock-btn:hover svg { transform: translateY(-2px); }
.dock-link.is-current { color: var(--color-teal-light); }
.dock-item.is-open .dock-btn { color: #fff; background: rgba(255,255,255,0.14); }

.dock-popover {
  position: absolute; bottom: calc(100% + 14px); left: 50%; transform: translateX(-50%);
  background: var(--surface-card); border: 2px solid var(--color-navy-deep); border-radius: var(--radius-sm);
  box-shadow: var(--shadow-float); padding: 10px; min-width: 230px;
  display: none; flex-direction: column; gap: 2px;
}
.dock-item.is-open .dock-popover { display: flex; }
.dock-popover a { padding: 10px 12px; border-radius: var(--radius-xs); font-size: 0.92rem; font-weight: 500; color: var(--text-body); }
.dock-popover a:hover, .dock-popover a.is-current { background: var(--color-cream); color: var(--text-strong); }
.dock-popover .dock-popover-label { font-family: var(--font-mono); font-size: 0.68rem; text-transform: uppercase; letter-spacing: 0.04em; color: var(--text-muted); padding: 6px 12px 2px; }

@media (max-width: 640px) {
  .app-dock { left: 10px; right: 10px; bottom: 10px; transform: none; justify-content: space-between; }
  .dock-link, .dock-btn { flex: 1; padding: 8px 4px; }
  /* Le popover s'ancre à toute la barre du dock (plutôt qu'au bouton cliqué) pour
     ne jamais déborder de l'écran, que ce soit "Services" (à gauche) ou "Plus" (à droite). */
  .dock-item { position: static; }
  .dock-popover { left: 0; right: 0; transform: none; min-width: 0; width: auto; max-height: 60vh; overflow-y: auto; }
}

.site-footer { padding-bottom: 118px; }

/* ==========================================================================
   Hero
   ========================================================================== */

.hero { position: relative; padding-top: clamp(44px, 6vw, 80px); padding-bottom: clamp(40px, 5vw, 56px); }
.hero-inner { max-width: 780px; }
.hero h1 { margin-bottom: 16px; }
.hero .lede { font-size: 1.15rem; color: var(--text-muted); max-width: 60ch; margin-bottom: 22px; }
.hero-cta-row { display: flex; flex-wrap: wrap; gap: 14px; margin-bottom: 22px; }
.hero-trust {
  display: flex; flex-wrap: wrap; gap: 22px;
  font-family: var(--font-mono); font-size: 0.8rem; color: var(--text-muted);
}
.hero-trust li { display: flex; align-items: center; gap: 8px; }
.hero-trust svg { width: 15px; height: 15px; color: var(--color-teal); flex-shrink: 0; }
@media (max-width: 640px) { .hero-trust { display: none; } }
@media (max-width: 480px) {
  .hero { padding-top: 32px; padding-bottom: 28px; }
  .page-hero { padding-block: 28px 24px; }
  .breadcrumb { margin-bottom: 14px; }
  .eyebrow { margin-bottom: 10px; }
  .hero-cta-row { gap: 10px; margin-bottom: 14px; }
}

/* ==========================================================================
   Démo — chatbot fonctionnel
   ========================================================================== */

.demo-panel-grid { display: grid; grid-template-columns: 1fr 1fr; gap: clamp(32px, 5vw, 64px); align-items: center; }
.demo-panel-grid > * { min-width: 0; }
@media (max-width: 900px) { .demo-panel-grid { grid-template-columns: 1fr; } }
.demo-panel-grid.reverse { direction: rtl; }
.demo-panel-grid.reverse > * { direction: ltr; }

.demo-tag {
  display: inline-flex; align-items: center; gap: 6px; font-family: var(--font-mono);
  font-size: 0.7rem; text-transform: uppercase; letter-spacing: 0.05em; color: var(--color-teal-deep);
  border: 1.5px solid var(--color-teal-deep); border-radius: var(--radius-xs); padding: 4px 10px; margin-bottom: 16px;
}
.on-dark .demo-tag { color: var(--color-teal-light); border-color: var(--color-teal-light); }

.demo-chat {
  border: 2px solid var(--color-navy-deep); border-radius: var(--radius-md);
  background: var(--color-navy-deep); color: #fff; overflow: hidden;
  box-shadow: var(--shadow-float); max-width: 460px; margin-inline: auto;
}
.demo-chat-head {
  display: flex; align-items: center; gap: 10px; padding: 14px 18px;
  border-bottom: 2px solid rgba(255,255,255,0.15);
  font-family: var(--font-mono); font-size: 0.76rem; text-transform: uppercase; letter-spacing: 0.04em;
  color: rgba(255,255,255,0.68);
}
.demo-chat-dot { width: 8px; height: 8px; border-radius: 50%; background: var(--color-teal-light); flex-shrink: 0; }
.demo-chat-body { padding: 18px; display: flex; flex-direction: column; gap: 12px; min-height: 210px; max-height: 320px; overflow-y: auto; }
.demo-msg { max-width: 82%; padding: 10px 14px; border-radius: var(--radius-sm); font-size: 0.92rem; line-height: 1.4; }
.demo-msg.bot { background: rgba(255,255,255,0.08); border: 1px solid rgba(255,255,255,0.2); align-self: flex-start; }
.demo-msg.user { background: var(--color-teal); color: var(--color-navy-deep); align-self: flex-end; font-weight: 600; }
.demo-chat-suggestions { display: flex; flex-wrap: wrap; gap: 8px; padding: 0 18px 14px; }
.demo-chat-suggestions button {
  font-family: var(--font-mono); font-size: 0.7rem; text-transform: uppercase; letter-spacing: 0.02em;
  background: transparent; border: 1.5px solid rgba(255,255,255,0.3); color: rgba(255,255,255,0.75);
  border-radius: var(--radius-xs); padding: 6px 10px;
}
.demo-chat-suggestions button:hover { border-color: var(--color-teal-light); color: #fff; }
.demo-chat-form { display: flex; gap: 8px; padding: 14px 18px; border-top: 2px solid rgba(255,255,255,0.15); }
.demo-chat-form input {
  flex: 1; background: rgba(255,255,255,0.08); border: 1.5px solid rgba(255,255,255,0.28);
  border-radius: var(--radius-sm); padding: 10px 12px; color: #fff; font-family: var(--font-body); font-size: 0.92rem;
}
.demo-chat-form input::placeholder { color: rgba(255,255,255,0.4); }
.demo-chat-form button {
  background: var(--color-teal); border: 1.5px solid var(--color-teal); color: var(--color-navy-deep);
  border-radius: var(--radius-sm); padding: 10px 18px; font-weight: 700;
}
.demo-chat-form button:hover { background: var(--color-teal-light); border-color: var(--color-teal-light); }

/* ==========================================================================
   Démo — mini-terminal "code tapé en direct" (preuve concrète du "codé à la
   main, pas de template" : un vrai extrait du CSS de ce site s'écrit tout seul)
   ========================================================================== */
.demo-terminal {
  border: 2px solid var(--color-navy-deep); border-radius: var(--radius-md);
  background: var(--color-navy-deep); overflow: hidden;
  box-shadow: var(--shadow-float); max-width: 460px; margin-inline: auto;
}
.demo-terminal-head {
  display: flex; align-items: center; gap: 8px; padding: 12px 16px;
  border-bottom: 2px solid rgba(255,255,255,0.15);
}
.demo-terminal-dot { width: 11px; height: 11px; border-radius: 50%; }
.demo-terminal-dot.red { background: #ff6159; }
.demo-terminal-dot.yellow { background: #ffbd2e; }
.demo-terminal-dot.green { background: #27c93f; }
.demo-terminal-file {
  margin-left: 8px; font-family: var(--font-mono); font-size: 0.74rem; color: rgba(255,255,255,0.5);
}
.demo-terminal-body {
  padding: 20px 22px; font-family: var(--font-mono); font-size: 0.86rem; line-height: 1.65;
  min-height: 200px; white-space: pre-wrap; word-break: break-word;
}
.tok-kw { color: var(--color-teal-light); font-weight: 600; }
.tok-prop { color: #7fd8ff; }
.tok-val { color: #ffd479; }
.tok-punct { color: rgba(255,255,255,0.55); }
.tok-comment { color: rgba(255,255,255,0.4); font-style: italic; }
.typed-cursor {
  display: inline-block; width: 7px; height: 1.1em; background: var(--color-teal-light);
  margin-left: 1px; vertical-align: text-bottom; animation: blinkCursor 1s step-end infinite;
}
@keyframes blinkCursor { 0%, 100% { opacity: 1; } 50% { opacity: 0; } }
@media (prefers-reduced-motion: reduce) { .typed-cursor { animation: none; } }

/* ==========================================================================
   Démo — carte de fidélité Fidzy interactive
   ========================================================================== */

.demo-loyalty {
  border: 2px solid var(--color-navy-deep); border-radius: var(--radius-md);
  background: var(--surface-card); padding: 28px; max-width: 420px; margin-inline: auto;
  box-shadow: var(--shadow-float);
}
.demo-loyalty-head { display: flex; justify-content: space-between; align-items: center; margin-bottom: 22px; }
.demo-loyalty-head strong { font-family: var(--font-heading); font-size: 1.1rem; color: var(--text-strong); }
.demo-loyalty-stamps { display: grid; grid-template-columns: repeat(4, 1fr); gap: 12px; margin-bottom: 22px; }
.demo-stamp {
  aspect-ratio: 1; border: 2px dashed var(--border-soft); border-radius: 50%;
  display: flex; align-items: center; justify-content: center; color: var(--color-teal);
  transition: border-color var(--dur-medium) var(--ease-out), background var(--dur-medium) var(--ease-out), transform var(--dur-medium) var(--ease-out);
}
.demo-stamp.is-filled { border-style: solid; border-color: var(--color-teal); background: rgba(30,168,150,0.12); transform: scale(1.05); }
.demo-stamp svg { width: 20px; height: 20px; opacity: 0; transform: scale(0.4); transition: all var(--dur-medium) var(--ease-out); }
.demo-stamp.is-filled svg { opacity: 1; transform: scale(1); }
.demo-loyalty-reward {
  text-align: center; padding: 14px; border: 2px solid var(--color-teal); border-radius: var(--radius-sm);
  background: rgba(30,168,150,0.08); font-weight: 700; color: var(--color-teal-deep);
  margin-bottom: 16px; display: none;
}
.demo-loyalty.is-complete .demo-loyalty-reward { display: block; }
.on-dark .demo-loyalty-reward { color: var(--color-teal-deep); }
.demo-loyalty-actions { display: flex; gap: 10px; }
.demo-loyalty-actions .btn { flex: 1; padding: 12px 16px; font-size: 0.88rem; }

/* Bascule Mode tampons / Mode points à l'intérieur de la carte de démo */
.demo-loyalty .tab-switch { margin-bottom: 18px; gap: 8px; }
.demo-loyalty .tab-switch button { padding: 7px 14px; font-size: 0.72rem; }
.demo-points { margin-bottom: 22px; }
.demo-points-bar {
  height: 16px; border-radius: 999px; background: var(--border-soft); overflow: hidden; margin-bottom: 10px;
}
.demo-points-fill {
  height: 100%; width: 0%; border-radius: 999px; background: var(--color-teal);
  transition: width var(--dur-medium) var(--ease-out);
}
.demo-points-label { text-align: center; font-family: var(--font-mono); font-size: 0.85rem; color: var(--text-muted); }
.demo-points-label strong { color: var(--text-strong); font-size: 1rem; }
.on-dark .demo-points-label { color: var(--text-muted); }
.on-dark .demo-points-label strong { color: var(--text-strong); }

/* ==========================================================================
   Démo — Roue Avis interactive
   ========================================================================== */

.demo-roue {
  border: 2px solid var(--color-navy-deep); border-radius: var(--radius-md);
  background: var(--surface-card); padding: 28px; max-width: 420px; margin-inline: auto;
  box-shadow: var(--shadow-float); text-align: center;
}
.demo-roue-wheel-wrap { position: relative; width: 200px; height: 200px; margin: 6px auto 20px; }
.demo-roue-pointer {
  position: absolute; top: -7px; left: 50%; transform: translateX(-50%);
  width: 0; height: 0; border-left: 9px solid transparent; border-right: 9px solid transparent;
  border-top: 15px solid var(--color-navy-deep); z-index: 2;
}
.demo-roue-wheel {
  position: relative; width: 100%; height: 100%; border-radius: 50%;
  border: 4px solid var(--color-navy-deep);
  background: conic-gradient(
    var(--color-teal) 0deg 60deg, var(--color-cream-dark) 60deg 120deg,
    var(--color-teal-light) 120deg 180deg, var(--color-cream-dark) 180deg 240deg,
    var(--color-teal) 240deg 300deg, var(--color-cream-dark) 300deg 360deg
  );
  transition: transform 3.2s cubic-bezier(0.17, 0.67, 0.16, 1);
}
.demo-roue-hub {
  position: absolute; top: 50%; left: 50%; width: 28px; height: 28px; margin: -14px 0 0 -14px;
  border-radius: 50%; background: var(--color-navy-deep); border: 3px solid var(--surface-card); z-index: 1;
}
.demo-roue-slice {
  position: absolute; top: 50%; left: 50%; width: 68px; margin-left: -34px;
  transform-origin: 50% 0; text-align: center; line-height: 1.15;
  font-family: var(--font-mono); font-size: 0.6rem; font-weight: 700; color: var(--color-navy-deep);
}
.demo-roue-slice:nth-child(1) { transform: rotate(30deg) translateY(54px); }
.demo-roue-slice:nth-child(2) { transform: rotate(90deg) translateY(54px); }
.demo-roue-slice:nth-child(3) { transform: rotate(150deg) translateY(54px); }
.demo-roue-slice:nth-child(4) { transform: rotate(210deg) translateY(54px); }
.demo-roue-slice:nth-child(5) { transform: rotate(270deg) translateY(54px); }
.demo-roue-slice:nth-child(6) { transform: rotate(330deg) translateY(54px); }
.demo-roue-result {
  text-align: center; padding: 12px; border: 2px solid var(--color-teal); border-radius: var(--radius-sm);
  background: rgba(30,168,150,0.08); font-weight: 700; color: var(--color-teal-deep);
  margin-bottom: 14px; opacity: 0; transition: opacity var(--dur-medium) var(--ease-out);
}
.demo-roue-result.is-visible { opacity: 1; }
.demo-roue-actions {
  display: flex; flex-wrap: wrap; gap: 8px; margin-top: 12px;
  opacity: 0; transform: translateY(6px); pointer-events: none;
  transition: opacity var(--dur-medium) var(--ease-out), transform var(--dur-medium) var(--ease-out);
}
.demo-roue-actions.is-visible { opacity: 1; transform: none; pointer-events: auto; }
.demo-roue-actions .btn { flex: 1; min-width: 150px; padding: 10px 14px; font-size: 0.82rem; }
[data-roue-spin]{ width: 100%; }

/* ==========================================================================
   Démo — schéma d'automatisation animé
   ========================================================================== */

.demo-flow { display: flex; align-items: flex-start; justify-content: space-between; padding-block: 20px 8px; }
.demo-flow-node { display: flex; flex-direction: column; align-items: center; gap: 10px; position: relative; flex: 1; }
.demo-flow-icon {
  width: 54px; height: 54px; border-radius: var(--radius-sm); border: 2px solid var(--color-navy-deep);
  background: var(--surface-page); display: flex; align-items: center; justify-content: center; color: var(--color-navy-deep);
  z-index: 1;
}
.on-dark .demo-flow-icon { background: var(--color-navy-deep); border-color: var(--color-teal-light); color: var(--color-teal-light); }
.demo-flow-icon svg { width: 24px; height: 24px; }
.demo-flow-label { font-family: var(--font-mono); font-size: 0.7rem; text-transform: uppercase; letter-spacing: 0.03em; color: var(--text-muted); text-align: center; }
.on-dark .demo-flow-label { color: var(--text-on-dark-muted); }
.demo-flow-line { position: absolute; top: 27px; left: 50%; width: 100%; height: 2px; background: var(--border-soft); overflow: hidden; }
.on-dark .demo-flow-line { background: rgba(255,255,255,0.2); }
.demo-flow-node:last-child .demo-flow-line { display: none; }
.demo-flow-line::after {
  content: ''; position: absolute; top: -3px; left: -10%; width: 10px; height: 8px; border-radius: 50%;
  background: var(--color-teal); animation: flowPulse 2.4s linear infinite;
}
.demo-flow-node:nth-child(2) .demo-flow-line::after { animation-delay: 0.6s; }
.demo-flow-node:nth-child(3) .demo-flow-line::after { animation-delay: 1.2s; }
.demo-flow-node:nth-child(4) .demo-flow-line::after { animation-delay: 1.8s; }
@keyframes flowPulse { 0% { left: -10%; opacity: 0; } 12% { opacity: 1; } 88% { opacity: 1; } 100% { left: 100%; opacity: 0; } }
@media (prefers-reduced-motion: reduce) { .demo-flow-line::after { animation: none; left: 45%; opacity: 1; } }
@media (max-width: 700px) {
  .demo-flow { flex-wrap: wrap; gap: 28px 0; }
  .demo-flow-node { flex: 1 1 40%; }
  .demo-flow-line { display: none; }
}

/* ==========================================================================
   Étude de cas — mise en avant grand format (portfolio réel)
   ========================================================================== */

.case-study {
  border: 2px solid var(--color-navy-deep); border-radius: var(--radius-md); overflow: hidden;
  background: var(--surface-card); box-shadow: var(--shadow-float);
}
.case-study-head {
  background: var(--color-navy-deep); color: #fff; padding: clamp(24px, 4vw, 36px);
  display: flex; justify-content: space-between; align-items: flex-start; flex-wrap: wrap; gap: 16px;
}
.case-study-head h3 { color: #fff; margin-bottom: 6px; }
.case-study-head p { color: var(--text-on-dark-muted); margin-bottom: 0; }
.case-study-tags { display: flex; flex-wrap: wrap; gap: 8px; }
.case-study-preview {
  display: block; width: 100%; aspect-ratio: 16 / 9;
  object-fit: cover; object-position: top center;
  background: var(--color-cream);
  border-bottom: 2px solid var(--border-soft);
}
.case-study-preview-grid {
  display: grid; grid-template-columns: 1fr 1fr; gap: 2px;
  border-bottom: 2px solid var(--border-soft); background: var(--border-soft);
}
.case-study-preview-grid .case-study-preview { aspect-ratio: 4 / 3; border-bottom: none; }
@media (max-width: 560px) { .case-study-preview-grid { grid-template-columns: 1fr; } }
.case-study-body { padding: clamp(24px, 4vw, 36px); }
.case-study-stats { display: flex; flex-wrap: wrap; gap: clamp(24px, 5vw, 48px); margin-top: 24px; padding-top: 24px; border-top: 2px solid var(--border-soft); }
.case-study-stat .num { font-family: var(--font-heading); font-weight: 700; font-size: clamp(1.8rem, 3vw, 2.3rem); color: var(--color-teal-deep); line-height: 1; }
.case-study-stat .label { font-family: var(--font-mono); font-size: 0.72rem; text-transform: uppercase; letter-spacing: 0.03em; color: var(--text-muted); margin-top: 6px; }

/* ==========================================================================
   Onglets services (interrupteur, remplace la grille de cartes)
   ========================================================================== */

.tab-switch { display: flex; flex-wrap: wrap; gap: 8px; margin-bottom: 32px; }
.tab-switch button {
  font-family: var(--font-mono); font-size: 0.8rem; text-transform: uppercase; letter-spacing: 0.02em;
  background: transparent; border: 2px solid var(--border-soft); color: var(--text-body);
  border-radius: var(--radius-sm); padding: 10px 18px;
}
.tab-switch button:hover { border-color: var(--color-navy-deep); }
.tab-switch button.is-active { background: var(--color-navy-deep); border-color: var(--color-navy-deep); color: #fff; }
.tab-switch-panel { display: none; }
.tab-switch-panel.is-active { display: block; }
.tab-switch-body { display: grid; grid-template-columns: 1.1fr 0.9fr; gap: clamp(32px, 5vw, 56px); align-items: center; }
.tab-switch-body > * { min-width: 0; }
@media (max-width: 900px) { .tab-switch-body { grid-template-columns: 1fr; } }
.tab-switch-visual {
  border: 2px solid var(--color-navy-deep); border-radius: var(--radius-md); background: var(--color-navy-deep);
  color: #fff; padding: clamp(28px, 4vw, 40px); min-height: 220px; display: flex; flex-direction: column; justify-content: center;
}

/* ==========================================================================
   Liste de définition — remplace les grilles de cartes pour les listes de
   fonctionnalités (plus légère qu'une liste indexée : puce ronde, pas de
   règle épaisse ni de numéro)
   ========================================================================== */

.deflist { display: flex; flex-direction: column; }
.deflist-item { display: flex; gap: 18px; padding-block: 22px; }
.deflist-item + .deflist-item { border-top: 1px solid var(--border-soft); }
.on-dark .deflist-item + .deflist-item { border-top-color: rgba(255,255,255,0.18); }
.deflist-check {
  flex-shrink: 0; width: 28px; height: 28px; border-radius: 50%; border: 2px solid var(--color-teal);
  color: var(--color-teal-deep); display: flex; align-items: center; justify-content: center; margin-top: 3px;
}
.on-dark .deflist-check { border-color: var(--color-teal-light); color: var(--color-teal-light); }
.deflist-check svg { width: 14px; height: 14px; }
.deflist-body h3 { margin-bottom: 6px; font-size: 1.08rem; }
.deflist-body p { margin-bottom: 0; color: var(--text-muted); }
.on-dark .deflist-body p { color: var(--text-on-dark-muted); }

/* ==========================================================================
   Cartes (comparatifs tarifaires) — règle épaisse en haut plutôt que boîte
   ========================================================================== */

.grid { display: grid; gap: 24px; }
.grid-2 { grid-template-columns: repeat(2, 1fr); }
.grid-3 { grid-template-columns: repeat(3, 1fr); }
.grid-4 { grid-template-columns: repeat(4, 1fr); }
@media (max-width: 980px) { .grid-3, .grid-4 { grid-template-columns: repeat(2, 1fr); } }
@media (max-width: 620px) { .grid-2, .grid-3, .grid-4 { grid-template-columns: 1fr; } }

.card {
  background: var(--surface-card); padding: 30px 28px;
  border-top: 3px solid var(--color-navy-deep);
  border-left: 1px solid var(--border-soft); border-right: 1px solid var(--border-soft); border-bottom: 1px solid var(--border-soft);
  transition: border-top-color var(--dur-medium) var(--ease-out), transform var(--dur-medium) var(--ease-out), box-shadow var(--dur-medium) var(--ease-out);
}
.card:hover { border-top-color: var(--color-teal); transform: translateY(-6px); box-shadow: var(--shadow-hard-sm); }
.on-dark .card { background: rgba(255,255,255,0.04); border-top-color: var(--color-teal-light); border-left-color: rgba(255,255,255,0.18); border-right-color: rgba(255,255,255,0.18); border-bottom-color: rgba(255,255,255,0.18); }
.card .card-link { display: inline-flex; align-items: center; gap: 6px; margin-top: 14px; font-weight: 600; color: var(--color-teal-deep); font-size: 0.92rem; }
.card .card-link svg { width: 16px; height: 16px; transition: transform var(--dur-fast) var(--ease-out); }
.card:hover .card-link svg { transform: translateX(4px); }

.on-dark { background: var(--color-navy-deep); color: var(--text-on-dark); border-top: 3px solid var(--color-teal); }
.on-dark h1, .on-dark h2, .on-dark h3, .on-dark h4 { color: #fff; }
.on-dark p { color: var(--text-on-dark-muted); }

/* ==========================================================================
   Process (steps)
   ========================================================================== */

.steps { display: grid; grid-template-columns: repeat(4, 1fr); gap: 24px; counter-reset: step; }
@media (max-width: 900px) { .steps { grid-template-columns: repeat(2, 1fr); } }
@media (max-width: 560px) { .steps { grid-template-columns: 1fr; } }
.step { position: relative; padding-top: 16px; border-top: 2px solid var(--border-soft); }
.step::before {
  counter-increment: step; content: counter(step, decimal-leading-zero);
  font-family: var(--font-mono); font-size: 1.9rem; font-weight: 600; color: var(--color-teal-deep);
  display: block; margin-bottom: 10px;
}
.on-dark .step { border-top-color: rgba(255,255,255,0.25); }
.on-dark .step::before { color: var(--color-teal-light); }

/* ==========================================================================
   Bandeau CTA — plein-bleed
   ========================================================================== */

.cta-band {
  background: var(--color-navy-deep); color: #fff;
  border-top: 3px solid var(--color-teal); border-bottom: 3px solid var(--color-teal);
  text-align: center;
}
.cta-band h2 { color: #fff; }
.cta-band p { color: rgba(255,255,255,0.8); max-width: 56ch; margin-inline: auto; }
.cta-band .hero-cta-row { justify-content: center; margin-bottom: 0; }

/* ==========================================================================
   Footer
   ========================================================================== */

.site-footer { background: var(--color-navy-deep); color: var(--text-on-dark-muted); border-top: 4px solid var(--color-teal); padding-top: 72px; }
.footer-grid { display: grid; grid-template-columns: 1.4fr 1fr 1fr 1fr; gap: 40px; padding-bottom: 48px; border-bottom: 1px solid rgba(255,255,255,0.14); }
@media (max-width: 900px) { .footer-grid { grid-template-columns: 1fr 1fr; } }
@media (max-width: 560px) { .footer-grid { grid-template-columns: 1fr; } }
.footer-grid h4 { font-family: var(--font-mono); color: #fff; font-size: 0.82rem; text-transform: uppercase; letter-spacing: 0.08em; margin-bottom: 18px; font-weight: 500; }
.footer-grid ul { display: flex; flex-direction: column; gap: 11px; }
.footer-grid a { display: inline-block; transition: color var(--dur-fast) var(--ease-out), transform var(--dur-fast) var(--ease-out); }
.footer-grid a:hover { color: #fff; transform: translateX(4px); }
.footer-brand p { max-width: 32ch; }
.footer-bottom { display: flex; justify-content: space-between; align-items: center; flex-wrap: wrap; gap: 12px; padding-block: 24px; font-size: 0.85rem; }
.footer-legal { display: flex; gap: 18px; flex-wrap: wrap; }

/* ==========================================================================
   Reveal on scroll
   ========================================================================== */

[data-reveal] { transition: opacity 0.6s var(--ease-out), transform 0.6s var(--ease-out); }
body.reveal-ready [data-reveal] { opacity: 0; transform: translateY(20px); }
body.reveal-ready [data-reveal].is-visible { opacity: 1; transform: translateY(0); }
[data-reveal-delay="1"] { transition-delay: 0.08s; }
[data-reveal-delay="2"] { transition-delay: 0.16s; }
[data-reveal-delay="3"] { transition-delay: 0.24s; }
[data-reveal-delay="4"] { transition-delay: 0.32s; }
[data-reveal-delay="5"] { transition-delay: 0.40s; }
[data-reveal-delay="6"] { transition-delay: 0.48s; }

/* ==========================================================================
   Breadcrumb / page header
   ========================================================================== */

.page-hero { padding-block: clamp(40px, 6vw, 72px) clamp(32px, 5vw, 56px); }
.breadcrumb {
  display: flex; align-items: center; gap: 8px;
  font-family: var(--font-mono); font-size: 0.78rem; text-transform: uppercase; letter-spacing: 0.03em;
  color: var(--text-muted); margin-bottom: 22px;
}
.breadcrumb a:hover { color: var(--color-teal-deep); }

/* ==========================================================================
   Utilities
   ========================================================================== */

.text-center { text-align: center; }
.mt-0 { margin-top: 0; }
.mb-0 { margin-bottom: 0; }
.badge {
  display: inline-flex; align-items: center; gap: 6px; padding: 5px 12px;
  border-radius: var(--radius-xs); background: transparent; border: 1.5px solid var(--color-teal-deep);
  color: var(--color-teal-deep); font-family: var(--font-mono); text-transform: uppercase;
  letter-spacing: 0.04em; font-size: 0.76rem; font-weight: 500;
}
.on-dark .badge { background: transparent; border-color: rgba(255,255,255,0.5); color: #fff; }

/* Soulignement "tracé main" (plutôt qu'un simple aplat rectangulaire) : une
   petite vague irrégulière façon coup de feutre, clin d'œil au côté artisanal
   de DigitCraft. Le SVG s'étire sur toute la largeur du texte (viewBox non
   proportionnel) donc s'adapte à n'importe quelle longueur de mot. */
.text-accent {
  position: relative; font-style: normal; font-weight: 700; color: var(--color-navy-deep);
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 300 20' preserveAspectRatio='none'%3E%3Cpath d='M2,12 Q20,3 38,12 T74,12 T110,12 T146,12 T182,12 T218,12 T254,12 T290,12' fill='none' stroke='%233fd1bd' stroke-width='7' stroke-linecap='round'/%3E%3C/svg%3E");
  background-repeat: no-repeat; background-size: 100% 0.5em; background-position: 0 96%;
  padding: 0 0.1em;
}
.on-dark .text-accent {
  color: #fff;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 300 20' preserveAspectRatio='none'%3E%3Cpath d='M2,12 Q20,3 38,12 T74,12 T110,12 T146,12 T182,12 T218,12 T254,12 T290,12' fill='none' stroke='%233fd1bd' stroke-opacity='0.65' stroke-width='7' stroke-linecap='round'/%3E%3C/svg%3E");
  background-size: 100% 0.5em; background-position: 0 96%;
}

/* ==========================================================================
   Bandeau de consentement cookies
   ========================================================================== */

.cookie-banner {
  position: fixed; top: 0; left: 0; right: 0; z-index: 500;
  background: var(--color-navy-deep); color: #fff;
  padding: 16px 20px; box-shadow: 0 4px 18px rgba(0,0,0,0.18);
  transform: translateY(-110%); transition: transform 0.35s ease;
}
.cookie-banner.is-visible { transform: translateY(0); }
.cookie-banner-inner {
  max-width: 1100px; margin: 0 auto; display: flex; align-items: center; justify-content: space-between;
  gap: 20px; flex-wrap: wrap;
}
.cookie-banner p { margin: 0; font-size: 0.9rem; color: rgba(255,255,255,0.9); max-width: 62ch; }
.cookie-banner a { color: var(--color-teal-light); text-decoration: underline; }
.cookie-banner-actions { display: flex; gap: 10px; flex-wrap: wrap; flex-shrink: 0; }
.cookie-banner-actions button {
  font-family: var(--font-mono); font-size: 0.8rem; font-weight: 600; text-transform: uppercase;
  letter-spacing: 0.03em; padding: 9px 18px; border-radius: var(--radius-sm); cursor: pointer; border: 1.5px solid transparent;
}
.cookie-accept { background: var(--color-teal); color: var(--color-navy-deep); }
.cookie-decline { background: transparent; border-color: rgba(255,255,255,0.5); color: #fff; }
.cookie-manage-link { background: none; border: none; color: var(--color-teal-light); text-decoration: underline; font-size: 0.82rem; cursor: pointer; padding: 0; font-family: var(--font-body); }
@media (max-width: 640px) {
  .cookie-banner-inner { flex-direction: column; align-items: flex-start; }
  .cookie-banner-actions { width: 100%; }
  .cookie-banner-actions button { flex: 1; }
}

/* ==========================================================================
   Accordéon FAQ (composant réutilisable sur plusieurs pages)
   ========================================================================== */
.faq-item { border-bottom: 1px solid var(--border-soft); padding: 22px 0; }
.faq-question {
  width: 100%; display: flex; justify-content: space-between; align-items: center; gap: 16px;
  background: none; border: none; text-align: left; font-family: var(--font-heading);
  font-weight: 600; font-size: 1.05rem; color: var(--text-strong); cursor: pointer;
}
.faq-question .icon {
  flex-shrink: 0; width: 24px; height: 24px; border-radius: var(--radius-xs);
  border: 1.5px solid var(--color-teal-deep); color: var(--color-teal-deep); background: transparent;
  display: flex; align-items: center; justify-content: center; transition: transform 0.3s var(--ease-out);
}
.faq-item.is-open .faq-question .icon { transform: rotate(45deg); }
.faq-answer { max-height: 0; overflow: hidden; transition: max-height 0.4s var(--ease-out); color: var(--text-muted); }
.faq-item.is-open .faq-answer { max-height: 400px; }
.faq-answer p { padding-top: 14px; margin: 0; }

/* ==========================================================================
   Mascotte "Digi" — un personnage qui vit sur le site plutôt qu'un widget
   figé dans un coin : il marche le long du bas de l'écran au fil du scroll
   (la vitesse et le sens de la marche suivent l'avancement dans la section
   regardée), s'arrête pour pointer du doigt ou inspecter quelque chose, et
   ne parle que sur de rares sections clés — ailleurs, aucune bulle : le
   mouvement et les gestes suffisent à animer le site.
   Le coin BAS-DROIT reste volontairement toujours libre (réservé à un futur
   widget de chatbot) : Digi marche sur une ligne de "sol" (bottom) toujours
   nettement au-dessus du dock de navigation, et le moteur JS (main.js)
   recalcule à chaque redimensionnement la plage horizontale sûre pour ne
   jamais s'approcher du bord droit. Voir main.js pour le détail du calcul.
   ========================================================================== */
.mascot { display: flex; flex-direction: column; align-items: center; gap: 10px; }
.mascot-figure { width: 130px; height: auto; overflow: visible; }

.mascot-body { animation: mascotBob 3.2s ease-in-out infinite; transform-box: fill-box; transform-origin: center; }
.mascot-shadow { fill: var(--color-navy-deep); opacity: 0.15; animation: mascotShadow 3.2s ease-in-out infinite; transform-box: fill-box; transform-origin: center; }
@keyframes mascotBob { 0%, 100% { transform: translateY(0); } 50% { transform: translateY(-10px); } }
@keyframes mascotShadow { 0%, 100% { transform: scale(1); opacity: 0.15; } 50% { transform: scale(0.82); opacity: 0.09; } }

.mascot-head { fill: var(--color-navy-deep); }
.mascot-torso { fill: var(--color-teal); stroke: var(--color-navy-deep); stroke-width: 3; }
.mascot-arm-left, .mascot-arm-right, .mascot-leg-left, .mascot-leg-right { fill: var(--color-navy-deep); }
.mascot-eye-white { fill: #fff; }
.mascot-pupil { fill: var(--color-navy-deep); }
.mascot-cheek { fill: var(--color-teal-light); opacity: 0.55; }
.mascot-smile { fill: none; stroke: var(--color-teal-light); stroke-width: 5; stroke-linecap: round; }
.mascot-antenna-stem { stroke: var(--color-navy-deep); stroke-width: 4; stroke-linecap: round; }
.mascot-antenna-light {
  fill: var(--color-teal); filter: drop-shadow(0 0 3px var(--color-teal));
  animation: mascotPulse 1.8s ease-in-out infinite; transform-box: fill-box; transform-origin: center;
}
@keyframes mascotPulse { 0%, 100% { transform: scale(1); opacity: 1; } 50% { transform: scale(1.25); opacity: 0.75; } }
.mascot-screen { fill: var(--color-navy-deep); }
.mascot-screen-text { fill: var(--color-teal-light); font-family: var(--font-mono); font-size: 15px; font-weight: 600; }

/* Sur un fond bleu nuit (bandeaux "on-dark"/CTA final, pied de page), la
   tête/les bras/les jambes/l'écran de Digi sont dessinés dans le même bleu
   nuit que le fond : il devient quasi invisible. Variante claire, activée
   par JS via .on-dark-bg selon la zone regardée, + léger halo pour le
   détacher nettement du fond. */
.mascot-figure.on-dark-bg .mascot-head,
.mascot-figure.on-dark-bg .mascot-arm-left,
.mascot-figure.on-dark-bg .mascot-arm-right,
.mascot-figure.on-dark-bg .mascot-leg-left,
.mascot-figure.on-dark-bg .mascot-leg-right,
.mascot-figure.on-dark-bg .mascot-screen { fill: #fff; }
.mascot-figure.on-dark-bg .mascot-pupil { fill: var(--color-navy-deep); }
.mascot-figure.on-dark-bg .mascot-screen-text { fill: var(--color-navy-deep); }
.mascot-figure.on-dark-bg .mascot-antenna-stem { stroke: #fff; }
.mascot-figure.on-dark-bg .mascot-torso { fill: var(--color-teal-light); stroke: #fff; }
.mascot-figure.on-dark-bg .mascot-shadow { fill: #000; opacity: 0.22; }
.mascot-figure.on-dark-bg { filter: drop-shadow(0 0 8px rgba(63, 209, 189, 0.5)); }

.mascot-eyes { animation: mascotBlink 4.5s ease-in-out infinite; transform-box: fill-box; transform-origin: center; }
@keyframes mascotBlink { 0%, 92%, 100% { transform: scaleY(1); } 95% { transform: scaleY(0.12); } }

/* Bras droit : petit salut ambiant par défaut (tic sympathique, pas un
   "message"), remplacé par une posture explicite (pose-point / pose-inspect)
   quand le JS l'attribue selon la section regardée. */
.mascot-arm-right { animation: mascotWave 5s ease-in-out infinite; transform-box: fill-box; transform-origin: 50% 100%; }
@keyframes mascotWave {
  0%, 82%, 100% { transform: rotate(0deg); }
  86% { transform: rotate(-20deg); }
  90% { transform: rotate(10deg); }
  94% { transform: rotate(-14deg); }
  98% { transform: rotate(4deg); }
}
@keyframes mascotPoint {
  0%, 100% { transform: rotate(-58deg); }
  50% { transform: rotate(-66deg); }
}
.mascot-figure.pose-point .mascot-arm-right { animation: mascotPoint 1.7s ease-in-out infinite; }

/* Posture "inspecteur" : Digi s'arrête de saluer, se penche légèrement et
   porte la main près du visage, comme s'il regardait quelque chose de près. */
.mascot-figure.pose-inspect .mascot-arm-right { animation: none; transform: rotate(0deg); }
.mascot-figure.pose-inspect .mascot-arm-left {
  animation: mascotInspect 2.4s ease-in-out infinite;
  transform-box: fill-box; transform-origin: 50% 100%;
}
.mascot-figure.pose-inspect .mascot-body {
  animation: mascotBobInspect 3.2s ease-in-out infinite;
  transform-box: fill-box; transform-origin: 50% 100%;
}
@keyframes mascotBobInspect {
  0%, 100% { transform: translateY(0) rotate(-4deg); }
  50% { transform: translateY(-10px) rotate(-4deg); }
}
@keyframes mascotInspect {
  0%, 100% { transform: rotate(0deg); }
  50% { transform: rotate(38deg) translate(3px, -4px); }
}

/* Posture "loupe" : Digi brandit une petite loupe pour mettre en avant un
   prix ou un chiffre clé de la section regardée (voir data-mascot-spotlight
   dans le HTML et la classe .is-spotlighted plus bas). La loupe est un
   élément à part dans le SVG (pas un enfant du bras) : elle pivote autour du
   même point que le bras (l'épaule, en coordonnées absolues du SVG) grâce à
   transform-box:view-box, pour paraître attachée à la main. */
.mascot-figure.pose-loupe .mascot-arm-right { animation: none; transform: rotate(-38deg); }
.mascot-loupe {
  opacity: 0; transition: opacity 0.25s ease;
  transform-box: view-box; transform-origin: 146.5px 139px;
}
.mascot-loupe-ring { fill: rgba(255, 255, 255, 0.3); stroke: var(--color-navy-deep); stroke-width: 5; }
.mascot-loupe-handle { stroke: var(--color-navy-deep); stroke-width: 6; stroke-linecap: round; }
.mascot-figure.on-dark-bg .mascot-loupe-ring, .mascot-figure.on-dark-bg .mascot-loupe-handle { stroke: #fff; }
.mascot-figure.pose-loupe .mascot-loupe {
  opacity: 1; animation: mascotLoupeHold 2.4s ease-in-out infinite;
}
@keyframes mascotLoupeHold {
  0%, 100% { transform: rotate(-38deg); }
  50% { transform: rotate(-32deg) translate(2px, -3px); }
}

/* Le chiffre/prix mis en avant pendant la posture "loupe" : léger halo qui
   pulse doucement, synchronisé par JS (classe ajoutée seulement pendant que
   la section correspondante est active). */
.is-spotlighted {
  display: inline-block; border-radius: 4px; padding: 0 4px; margin: 0 -4px;
  animation: mascotSpotlightPulse 1.8s ease-in-out infinite;
}
@keyframes mascotSpotlightPulse {
  0%, 100% { box-shadow: 0 0 0 0 rgba(30, 168, 150, 0.35); }
  50% { box-shadow: 0 0 0 6px rgba(30, 168, 150, 0.12); }
}

/* Jambes : n'animent (cycle de marche) que pendant un déplacement réel,
   quand JS ajoute "is-walking" sur .mascot-figure parce que sa position
   horizontale change au fil du scroll. À l'arrêt, elles restent immobiles :
   Digi a l'air de s'être arrêté pour regarder ou pointer quelque chose. */
.mascot-leg-left, .mascot-leg-right { transform-box: fill-box; transform-origin: 50% 0%; }
.mascot-figure.is-walking .mascot-leg-left { animation: mascotWalkLegL 0.6s linear infinite; }
.mascot-figure.is-walking .mascot-leg-right { animation: mascotWalkLegR 0.6s linear infinite; }
@keyframes mascotWalkLegL { 0%, 100% { transform: rotate(-24deg); } 50% { transform: rotate(24deg); } }
@keyframes mascotWalkLegR { 0%, 100% { transform: rotate(24deg); } 50% { transform: rotate(-24deg); } }

.mascot-bubble {
  position: relative; background: var(--surface-card); border: 2px solid var(--color-navy-deep);
  border-radius: var(--radius-sm); padding: 16px 28px; max-width: 320px; text-align: center;
  font-size: 0.86rem; line-height: 1.5; color: var(--text-body); box-shadow: var(--shadow-hard-sm);
  transition: opacity var(--dur-fast) var(--ease-out);
}
/* La bulle est toujours affichée au-dessus de Digi (voir bottom: calc(100%
   + 10px) plus bas) : le petit triangle doit donc pointer vers le bas, vers
   sa tête, pour qu'on comprenne que c'est bien lui qui parle — pas vers le
   haut, à l'opposé de lui. */
.mascot-bubble::after {
  content: ''; position: absolute; bottom: -9px; left: 50%; transform: translateX(-50%) rotate(45deg);
  width: 15px; height: 15px; background: var(--surface-card);
  border-right: 2px solid var(--color-navy-deep); border-bottom: 2px solid var(--color-navy-deep);
}
/* white-space: pre-line -- chaque texte de Digi est écrit avec un retour
   à la ligne par phrase/mini-phrase (voir data-mascot-text dans le HTML) ;
   pre-line rend ces retours à la ligne tout en laissant le texte
   continuer à s'adapter en largeur si besoin (pas de saut à un endroit
   arbitraire). */
.mascot-bubble p { margin: 0; transition: opacity 0.18s ease; white-space: pre-line; }
.mascot-bubble strong { color: var(--color-teal-deep); }
.mascot-bubble.is-updating p { opacity: 0; }

.mascot-dismiss {
  display: none; position: absolute; top: -10px; right: -10px; width: 22px; height: 22px;
  align-items: center; justify-content: center; padding: 0; border-radius: 50%;
  background: var(--color-navy-deep); color: #fff; border: 2px solid var(--surface-card);
  box-shadow: var(--shadow-hard-sm); cursor: pointer; z-index: 2;
  transition: transform var(--dur-fast) var(--ease-out);
}
.mascot-dismiss:hover { transform: scale(1.12); background: var(--color-teal-deep); }

/* ==========================================================================
   Mode "en scène" — actif dès le chargement sur les 16 pages. Digi est
   ancré à une hauteur fixe près du bas de l'écran (bottom), toujours
   nettement au-dessus du dock de navigation (fixe, centré, ~75px de haut :
   voir plus haut ".app-dock") quelle que soit la largeur d'écran, pour ne
   jamais le traverser visuellement même quand il marche sur toute la
   largeur. Sa position horizontale (left) est fixée en pixels par le JS à
   chaque scroll, dans une plage qui exclut toujours le coin bas-droit
   (réservé au futur chatbot) et les bords de l'écran.
   ========================================================================== */
.mascot.mascot--floating {
  position: fixed; left: 14px; right: auto; top: auto; bottom: 112px;
  z-index: 640; max-width: calc(100vw - 28px);
  animation: mascotFloatIn 0.4s var(--ease-out);
  /* Digi ne doit jamais bloquer un clic sur ce qu'il y a en dessous (bouton,
     lien...) : lui seul est "traversable" à la souris/au doigt. Seules la
     bulle et sa croix de fermeture (quand elles sont visibles) redeviennent
     cliquables, via pointer-events:auto plus bas. */
  pointer-events: none;
}
.mascot--floating .mascot-figure {
  width: 76px; flex-shrink: 0; animation: mascotSway 4.5s ease-in-out infinite;
}
.mascot-figure.is-walking { animation: none; }
.mascot--floating .mascot-figure.is-reacting { animation: mascotHop 0.55s var(--ease-out); }

/* Digi devient saisissable : on peut l'attraper (souris ou doigt) et le
   lancer. Pendant qu'on le tient ou qu'il vole après un lancer, ses
   animations habituelles (balancement, marche) s'effacent au profit du
   mouvement piloté par JS (position + rotation en ligne). */
.mascot-figure { cursor: grab; touch-action: none; pointer-events: auto; }
.mascot-figure.is-grabbed, .mascot-figure.is-thrown { animation: none; cursor: grabbing; }
.mascot-figure.is-grabbed { transform: scale(1.08); }
.mascot-figure.is-bouncing { animation: mascotBounceSquash 0.28s var(--ease-out); }
@keyframes mascotBounceSquash {
  0% { transform: scaleX(1) scaleY(1); }
  30% { transform: scaleX(1.28) scaleY(0.72); }
  100% { transform: scaleX(1) scaleY(1); }
}

/* Chute et escalade : déclenchées une seule fois par section marquée
   data-mascot-fall, la première fois qu'on y arrive en scrollant — Digi
   trébuche, tombe au bas de l'écran, puis remonte en escaladant avant de
   reprendre sa marche normale. Un clin d'œil ponctuel, pas systématique. */
.mascot-figure.is-falling { animation: mascotFall 0.65s cubic-bezier(.55,0,1,.45) forwards; }
.mascot-figure.is-climbing { animation: mascotClimb 1.1s cubic-bezier(.34,1.56,.64,1) forwards; }
@keyframes mascotFall {
  0% { transform: translateY(0) rotate(0deg); }
  100% { transform: translateY(130px) rotate(220deg); }
}
@keyframes mascotClimb {
  0% { transform: translateY(130px) rotate(220deg); }
  55% { transform: translateY(-16px) rotate(-10deg); }
  80% { transform: translateY(4px) rotate(4deg); }
  100% { transform: translateY(0) rotate(0deg); }
}

/* Petite pause d'ambiance : quand on ne scrolle plus depuis un moment, Digi
   s'étire, saute sur place, ou se jette sur le côté de temps en temps,
   comme s'il patientait — un détail de plus pour qu'il ait l'air vivant,
   pas juste "en pause". Le JS choisit une variante au hasard à chaque
   déclenchement pour varier les plaisirs. */
.mascot-figure.is-idling-stretch { animation: mascotIdleStretch 2.4s ease-in-out; }
@keyframes mascotIdleStretch {
  0%, 100% { transform: translateY(0) rotate(0deg) scaleY(1); }
  20% { transform: translateY(-3px) rotate(-6deg) scaleY(1.02); }
  40% { transform: translateY(-9px) rotate(5deg) scaleY(1.05); }
  60% { transform: translateY(-3px) rotate(-4deg) scaleY(1.02); }
  80% { transform: translateY(0) rotate(3deg) scaleY(1); }
}
.mascot-figure.is-idling-jump { animation: mascotIdleJump 0.9s cubic-bezier(.34, 1.56, .64, 1); }
@keyframes mascotIdleJump {
  0% { transform: translateY(0) scaleY(1); }
  15% { transform: translateY(6px) scaleY(0.85); }
  45% { transform: translateY(-36px) scaleY(1.08); }
  72% { transform: translateY(0) scaleY(0.88); }
  86% { transform: translateY(-5px) scaleY(1.04); }
  100% { transform: translateY(0) scaleY(1); }
}
.mascot-figure.is-idling-dive-left { animation: mascotIdleDiveLeft 1.1s cubic-bezier(.36, .07, .19, .97); }
@keyframes mascotIdleDiveLeft {
  0%, 100% { transform: translateX(0) rotate(0deg); }
  30% { transform: translateX(-22px) rotate(-24deg); }
  55% { transform: translateX(-26px) rotate(-16deg); }
  80% { transform: translateX(-4px) rotate(5deg); }
}
.mascot-figure.is-idling-dive-right { animation: mascotIdleDiveRight 1.1s cubic-bezier(.36, .07, .19, .97); }
@keyframes mascotIdleDiveRight {
  0%, 100% { transform: translateX(0) rotate(0deg); }
  30% { transform: translateX(22px) rotate(24deg); }
  55% { transform: translateX(26px) rotate(16deg); }
  80% { transform: translateX(4px) rotate(-5deg); }
}
/* Deux variantes de pause supplémentaires : un petit tour sur lui-même
   façon "figure de style", et un clin d'œil complice (un seul œil, tête
   qui se penche, antenne qui clignote deux fois plus vite le temps du
   clin d'œil) — encore plus de variété à chaque pause d'ambiance. */
.mascot-figure.is-idling-spin { animation: mascotIdleSpin 0.9s cubic-bezier(.45, 0, .55, 1); transform-box: fill-box; transform-origin: 50% 78%; }
@keyframes mascotIdleSpin {
  0% { transform: rotate(0deg) translateY(0); }
  30% { transform: rotate(130deg) translateY(-13px); }
  60% { transform: rotate(270deg) translateY(-9px); }
  100% { transform: rotate(360deg) translateY(0); }
}
.mascot-figure.is-idling-wink .mascot-eyes .mascot-eye-white:nth-of-type(2),
.mascot-figure.is-idling-wink .mascot-eyes .mascot-pupil:nth-of-type(2) {
  animation: mascotWinkEye 0.7s ease-in-out; transform-box: fill-box; transform-origin: center;
}
@keyframes mascotWinkEye {
  0%, 100% { transform: scaleY(1); }
  35%, 55% { transform: scaleY(0.08); }
}
.mascot-figure.is-idling-wink .mascot-head {
  animation: mascotWinkHead 0.7s ease-in-out; transform-box: fill-box; transform-origin: 50% 100%;
}
@keyframes mascotWinkHead {
  0%, 100% { transform: rotate(0deg); }
  40% { transform: rotate(-6deg); }
  70% { transform: rotate(2deg); }
}
.mascot-figure.is-idling-wink .mascot-antenna-light { animation: mascotPulse 0.35s ease-in-out 2; }

/* Suivi du regard : les pupilles se décalent très légèrement vers le
   curseur (JS calcule --pupil-dx/--pupil-dy sur .mascot-figure), pour un
   effet "vivant" continu — pas seulement pendant les pauses d'ambiance.
   Valeurs par défaut à 0 tant qu'aucune souris n'a bougé (ou sur tactile
   pur, où l'événement mousemove ne se déclenche jamais). */
.mascot-pupil {
  transform: translate(var(--pupil-dx, 0px), var(--pupil-dy, 0px));
  transition: transform 0.15s ease-out;
  transform-box: fill-box; transform-origin: center;
}
/* Petit écran de poitrine qui change de temps en temps (voir JS) : une
   transition douce plutôt qu'un changement brutal de texte. */
.mascot-screen-text { transition: opacity 0.26s ease; }

/* ==========================================================================
   Trois nouvelles animations "spectacle", pour renforcer l'effet
   "attraction du site" (demande explicite de Julien) : un saut par-dessus
   un titre, un petit sprint entre deux sections qui se termine par une
   glissade, et — une fois qu'on arrive tout en bas du site — une chute
   suivie d'une remontée en ballons. Toutes réservées à quelques sections
   choisies (voir data-mascot-jump/data-mascot-dash dans le HTML), jamais
   sur toutes les pages, pour rester une surprise plutôt qu'un tic répété.
   ========================================================================== */

/* Saut par-dessus un titre : posé sur .mascot-figure comme les autres
   animations "ponctuelles" (chute, pause d'ambiance...). Le titre visé
   (trouvé dynamiquement en JS via querySelector('h1,h2,h3') dans la zone
   tirée au sort) reçoit en même temps un petit "wiggle" façon "ouf, pile
   évité" via la classe .is-hurdled posée directement dessus — voir JS. */
.mascot-figure.is-jumping-obstacle { animation: mascotObstacleJump 1s cubic-bezier(.34, 1.56, .64, 1); }
@keyframes mascotObstacleJump {
  0% { transform: translateY(0) rotate(0deg); }
  22% { transform: translateY(-6px) rotate(-5deg); }
  50% { transform: translateY(-58px) rotate(8deg); }
  78% { transform: translateY(-8px) rotate(-4deg); }
  100% { transform: translateY(0) rotate(0deg); }
}
.is-hurdled {
  animation: mascotHurdleWiggle 0.6s ease-in-out;
}
@keyframes mascotHurdleWiggle {
  0%, 100% { transform: rotate(0deg) translateY(0); }
  25% { transform: rotate(-1.4deg) translateY(-2px); }
  55% { transform: rotate(1.1deg) translateY(1px); }
  80% { transform: rotate(-0.5deg) translateY(0); }
}

/* Sprint entre deux sections : jambes accélérées pendant la traversée
   d'une section marquée data-mascot-dash (même cycle de marche, juste plus
   rapide), puis petite glissade/rattrapage une fois arrivé de l'autre
   côté — "il court en ligne droite [...] et tombe à la fin". Volontairement
   plus léger qu'une vraie chute-escalade (section (12)) : Digi ne quitte
   pas l'écran, il trébuche juste et se rattrape aussitôt. */
.mascot-figure.is-walking.is-dashing .mascot-leg-left,
.mascot-figure.is-walking.is-dashing .mascot-leg-right { animation-duration: 0.26s; }
.mascot-figure.is-stumbling { animation: mascotStumble 0.55s ease-in-out; }
@keyframes mascotStumble {
  0% { transform: translateY(0) rotate(0deg); }
  25% { transform: translateY(5px) rotate(-9deg); }
  55% { transform: translateY(9px) rotate(7deg); }
  80% { transform: translateY(2px) rotate(-3deg); }
  100% { transform: translateY(0) rotate(0deg); }
}

/* Chute jusqu'en bas du site + remontée en ballons : jouée une seule fois
   par page, quand on arrive tout en bas du scroll (pas juste d'une
   section, du site entier) — un vrai petit moment de mise en scène pour
   récompenser celles et ceux qui vont au bout de la page. */
.mascot-figure.is-mega-falling { animation: mascotMegaFall 0.9s cubic-bezier(.55, 0, 1, .45); }
@keyframes mascotMegaFall {
  0% { transform: translateY(0) rotate(0deg); }
  100% { transform: translateY(230px) rotate(300deg); }
}
.mascot-figure.is-rising-balloons { animation: mascotBalloonRise 3s cubic-bezier(.22, 1, .36, 1); }
@keyframes mascotBalloonRise {
  0% { transform: translateY(230px) rotate(300deg); }
  10% { transform: translateY(224px) rotate(340deg); }
  100% { transform: translateY(0) rotate(360deg); }
}
.mascot-balloons {
  opacity: 0; transition: opacity 0.4s ease; pointer-events: none;
  transform-box: fill-box; transform-origin: center;
}
.mascot-figure.is-rising-balloons .mascot-balloons {
  opacity: 1; animation: mascotBalloonSway 2.2s ease-in-out infinite;
}
@keyframes mascotBalloonSway {
  0%, 100% { transform: translateX(0) rotate(0deg); }
  50% { transform: translateX(3px) rotate(2deg); }
}
.mascot-balloon-string { stroke: var(--color-navy-deep); stroke-width: 2; opacity: 0.55; }
.mascot-balloon { stroke: var(--color-navy-deep); stroke-width: 3; }
.mascot-balloon-a { fill: #ff8a65; }
.mascot-balloon-b { fill: var(--color-teal); }
.mascot-balloon-c { fill: #ffd166; }
.mascot-figure.on-dark-bg .mascot-balloon-string { stroke: #fff; }

@keyframes mascotSway {
  0%, 100% { transform: translateX(0) rotate(0deg); }
  25% { transform: translateX(4px) rotate(2deg); }
  75% { transform: translateX(-4px) rotate(-2deg); }
}
@keyframes mascotHop {
  0% { transform: translateY(0) scale(1); }
  35% { transform: translateY(-13px) scale(1.07); }
  65% { transform: translateY(2px) scale(0.97); }
  100% { transform: translateY(0) scale(1); }
}
@keyframes mascotFloatIn { from { opacity: 0; transform: translateY(10px); } to { opacity: 1; transform: translateY(0); } }

/* La bulle ne s'affiche que sur les rares sections qui fournissent un
   texte (classe "has-text" ajoutée par JS) : le reste du temps, Digi anime
   le site par le déplacement et les gestes seuls, sans parler. Position
   absolue (et non un enfant flex) : quand elle est masquée, elle ne réserve
   aucun espace et n'agrandit donc jamais la zone "solide" de Digi — ce qui
   évite qu'il ne recouvre du contenu (boutons, texte) situé plus haut. */
.mascot--floating .mascot-bubble {
  position: absolute; bottom: calc(100% + 10px); left: 50%;
  width: max-content; max-width: min(320px, calc(100vw - 40px));
  font-size: 0.86rem; line-height: 1.5; padding: 16px 26px;
  opacity: 0; pointer-events: none;
  /* --bubble-shift : ajusté par JS à chaque scroll pour que la bulle reste
     toujours entièrement dans la fenêtre même quand Digi marche près d'un
     bord (marche pleine largeur oblige) — sans ça, une bulle large peut
     déborder de l'écran quand il est tout à gauche ou tout à droite. */
  transform: translateX(calc(-50% + var(--bubble-shift, 0px))) translateY(6px) scale(0.94);
  transition: opacity 0.3s var(--ease-out), transform 0.3s var(--ease-out);
}
.mascot--floating .mascot-bubble.has-text {
  opacity: 1; transform: translateX(calc(-50% + var(--bubble-shift, 0px))) translateY(0) scale(1);
  pointer-events: auto;
}
.mascot--floating .mascot-dismiss { display: flex; pointer-events: auto; }

/* Une fois passé la dernière section "présentée" (pied de page), Digi
   s'efface en douceur plutôt que de rester figé sur du contenu qu'il ne
   commente plus. Il revient si on remonte dans la page. */
.mascot--floating.mascot--offstage { opacity: 0; transform: translateY(12px); transition: opacity 0.15s var(--ease-out), transform 0.15s var(--ease-out); }

@media (max-width: 640px) {
  .mascot.mascot--floating { bottom: 96px; left: 8px; }
  .mascot--floating .mascot-figure { width: 60px; }
  .mascot--floating .mascot-bubble { max-width: min(260px, calc(100vw - 32px)); font-size: 0.78rem; line-height: 1.48; padding: 13px 20px; }
}

