/* ====================================================================
   LES CASQUETTES FILMS · Clean rebuild
   Direction : FRACTAL — brutalist éditorial
   ==================================================================== */

/* ─── RÈGLE INTANGIBLE — STACKING CONTEXTS ─────────────────────────────
   NE PAS ajouter `transform`, `filter`, `will-change: transform`,
   `perspective`, ni `contain: paint/layout` sur :
     • body, html, #root, main
     • .portfolio, .team, .news, .services, .photo (sections root)
   Ces propriétés transformeraient l'élément en containing block pour
   `position: fixed` enfants — ce qui CASSERAIT les modales et le menu.
   Si une nouvelle anim est nécessaire, scope-la au pseudo ::before ou
   à un élément enfant non-parent-d'une-modale. */

/* ---------- Tokens ---------- */
:root {
  --bg:        #0d0d0e;
  --bg-elev:   #161617;
  --bg-light:  #f2efe8;
  --ink:       #eeeae0;
  --ink-soft:  #b0aea6;
  --ink-mute:  #5b5a55;
  --line:      rgba(238, 234, 224, 0.12);
  --line-str:  rgba(238, 234, 224, 0.32);
  --accent:    #2d5bff;
  --accent-rgb: 45, 91, 255;
  --live:      #ff3b30;

  /* ─── Verre — recette translucide unifiée (inspiration obvious-art) ───
     Teinte sombre propre + liseré BLANC filiforme + flou raffiné +
     légère saturation + liseré de lumière interne. Les DÉGRADÉS des
     en-têtes de section restent gérés à part (non touchés). */
  --glass-scrim:      rgba(7, 7, 9, 0.88);      /* fonds plein écran — profond (cf. bg-black/90) */
  --glass-chip:       rgba(12, 12, 14, 0.42);   /* puces / boutons en verre */
  --glass-chip-hover: rgba(12, 12, 14, 0.70);
  --glass-line:       rgba(255, 255, 255, 0.12); /* liseré blanc filiforme (cf. white/10) */
  --glass-blur:       18px;
  --glass-sat:        140%;
  /* Verre "liquide" : reflet spéculaire en diagonale (sheen) + biseau
     lumineux haut / ombre interne bas (épaisseur du verre) + ombre portée. */
  --glass-sheen:      linear-gradient(135deg, rgba(255,255,255,0.24) 0%, rgba(255,255,255,0.07) 22%, rgba(255,255,255,0) 46%);
  --glass-highlight:  inset 0 1px 0 rgba(255,255,255,0.30), inset 0 -1px 1px rgba(0,0,0,0.22), 0 10px 30px rgba(0,0,0,0.38);
  --glass-shadow:     0 14px 44px rgba(0, 0, 0, 0.42);
  /* Texture du verre — grain fin (SVG feTurbulence, data-URI, zéro requête).
     Superposé en couche d'image sur la teinte → effet "verre dépoli"
     plutôt que flou plat. Deux intensités : fine (puces) / douce (fonds). */
  --glass-noise:      url("data:image/svg+xml,%3Csvg%20xmlns='http://www.w3.org/2000/svg'%20width='140'%20height='140'%3E%3Cfilter%20id='g'%3E%3CfeTurbulence%20type='fractalNoise'%20baseFrequency='0.9'%20numOctaves='2'%20stitchTiles='stitch'/%3E%3CfeColorMatrix%20type='saturate'%20values='0'/%3E%3C/filter%3E%3Crect%20width='100%25'%20height='100%25'%20filter='url(%23g)'%20opacity='0.22'/%3E%3C/svg%3E");
  --glass-noise-soft: url("data:image/svg+xml,%3Csvg%20xmlns='http://www.w3.org/2000/svg'%20width='160'%20height='160'%3E%3Cfilter%20id='g'%3E%3CfeTurbulence%20type='fractalNoise'%20baseFrequency='0.85'%20numOctaves='2'%20stitchTiles='stitch'/%3E%3CfeColorMatrix%20type='saturate'%20values='0'/%3E%3C/filter%3E%3Crect%20width='100%25'%20height='100%25'%20filter='url(%23g)'%20opacity='0.10'/%3E%3C/svg%3E");
  /* Texture "verre dépoli" pour la section Services : turbulence BASSE
     fréquence (grosses marbrures douces) + léger flou → aspect nuageux de
     verre dépoli (et non un grain sec). Tuile 320 × baseFreq 0.025 = 8
     cycles entiers → répétition sans couture. */
  --glass-noise-svc: url("data:image/svg+xml,%3Csvg%20xmlns='http://www.w3.org/2000/svg'%20width='600'%20height='600'%3E%3Cfilter%20id='g'%3E%3CfeTurbulence%20type='fractalNoise'%20baseFrequency='0.015'%20numOctaves='4'%20stitchTiles='stitch'/%3E%3CfeColorMatrix%20type='saturate'%20values='0'/%3E%3CfeGaussianBlur%20stdDeviation='1'/%3E%3C/filter%3E%3Crect%20width='100%25'%20height='100%25'%20filter='url(%23g)'%20opacity='0.2'/%3E%3C/svg%3E");

  --display:   "Archivo Black", Impact, sans-serif;
  --mono:      "Courier Prime", "Courier New", ui-monospace, monospace;
  --body:      "Inter", -apple-system, sans-serif;

  --pad-x:     clamp(20px, 3vw, 40px);
  --section-y: clamp(80px, 11vw, 160px);

  /* ─── ÉCHELLE D'EMPILEMENT (z-index) ────────────────────────────────
     Documentée pour éviter les "z-index magiques" comme 9999 ou 200.
     Tout nouveau composant doit utiliser ces variables, pas des nombres.

     -1   --z-section-image      → image de fond ::before des heads
      1-9 --z-content / --z-content-top → contenu courant (cards, texte)
      10-29 --z-section-overlay   → voiles gradients ::after des heads
      30-99 --z-section-interactive → hovers, focus rings, badges
        90 --z-top-fade           → dégradé d'en-tête haut de viewport
                                     (devant le contenu, sous la nav)
      100-199 NAVIGATION (toujours au-dessus du contenu)
        100 --z-nav-base          → menu latéral droite (desktop)
        110 --z-nav-brand         → logo brand fixed (anim hero)
        150 --z-nav-burger        → burger mobile (top-right)
        180 --z-nav-overlay       → drawer mobile-nav plein écran
      1000-1199 MODALES & LIGHTBOXES (trap focus utilisateur)
        1000 --z-modal            → modals projet/news/team/cookies
        1100 --z-modal-lightbox   → lightbox au-dessus d'une modale (galerie)
      9000+ TOP DE TOUT (effets globaux + a11y)
        9000 --z-grain            → grain bruit pleine fenêtre
        9100 --z-cookie-banner    → bandeau cookies (au-dessus du grain)
        9999 --z-skip             → skip-link a11y (focus clavier)
   ──────────────────────────────────────────────────────────────────── */
  --z-section-image:       -1;
  --z-content:              1;
  --z-content-top:          5;
  --z-section-overlay:     10;
  --z-section-interactive: 30;
  --z-top-fade:            90;
  --z-nav-base:           100;
  --z-nav-brand:          110;
  --z-nav-burger:         150;
  --z-nav-overlay:        180;
  --z-modal:             1000;
  --z-modal-lightbox:    1100;
  --z-grain:             9000;
  --z-cookie-banner:     9100;
  --z-skip:              9999;

  /* Ombres internes 3D des heads parallax — portée du dégradé noir en
     haut/bas des ::after (effet relief). Réduites sur mobile, où les
     heads sont bien plus petits (sinon l'ombre couvre ~2/3 de l'image). */
  --head-shadow-top:    68px;
  --head-shadow-bottom: 52px;
}
@media (max-width: 640px) {
  :root {
    --head-shadow-top:    42px;
    --head-shadow-bottom: 32px;
  }
}

/* ---------- Reset ---------- */
*, *::before, *::after {
  box-sizing: border-box;
  margin: 0;
  padding: 0;
  -webkit-tap-highlight-color: transparent;
}
html {
  -webkit-text-size-adjust: 100%;
  text-size-adjust: 100%;
  /* `clip` empêche le scroll horizontal sans créer de contexte de scroll
     secondaire (contrairement à `hidden` qui peut piéger position:sticky).
     Fallback `hidden` pour les rares navigateurs sans support. */
  overflow-x: hidden;
  overflow-x: clip;
}
html, body { background: var(--bg); color: var(--ink); font-size: 19.2px; }

/* ─── Lenis (scroll fluide) — CSS requis par la lib ─────────────────── */
html.lenis, html.lenis body { height: auto; }
.lenis.lenis-smooth { scroll-behavior: auto !important; }
.lenis.lenis-smooth [data-lenis-prevent] { overscroll-behavior: contain; }
.lenis.lenis-stopped { overflow: hidden; }
body {
  font-family: var(--body);
  font-weight: 300;
  /* --site-font-size : surchargé dynamiquement par site-content.js / admin "Apparence" */
  font-size: var(--site-font-size, 16px);
  line-height: 1.5;
  -webkit-font-smoothing: antialiased;
  overflow-x: hidden;
  min-width: 280px; /* relâché pour Z Fold fermé (280px) */
  /* Safe-area : padding latéral seulement. Top/bottom gérés par section. */
  padding-left:  env(safe-area-inset-left, 0);
  padding-right: env(safe-area-inset-right, 0);
}
img, svg, video { display: block; max-width: 100%; height: auto; }
a { color: inherit; text-decoration: none; }
button { font: inherit; color: inherit; background: none; border: none; cursor: pointer; }
input, textarea, select {
  font: inherit;
  color: inherit;
  background: none;
  border: none;
  outline: none;
  /* iOS : empêche le zoom auto quand un input prend le focus.
     16px CSS-px est le seuil en-dessous duquel Safari iOS zoome. */
  font-size: max(16px, 1em);
}

/* ---------- Grain ---------- */
.grain {
  pointer-events: none;
  position: fixed; inset: 0;
  z-index: var(--z-grain);  /* 9000 — sous skip-link et cookie-banner */
  opacity: 0.08;
  mix-blend-mode: overlay;
  background-image: url("data:image/svg+xml;utf8,<svg xmlns='http://www.w3.org/2000/svg' width='240' height='240'><filter id='n'><feTurbulence type='fractalNoise' baseFrequency='0.9' numOctaves='2' stitchTiles='stitch'/><feColorMatrix values='0 0 0 0 1  0 0 0 0 1  0 0 0 0 1  0 0 0 0.5 0'/></filter><rect width='100%' height='100%' filter='url(%23n)'/></svg>");
}

/* ---------- Type helpers ---------- */
.mono     { font-family: var(--mono); }
.mono-xs  { font-family: var(--mono); font-size: 10px; letter-spacing: 0.28em; text-transform: uppercase; }
.mono-sm  { font-family: var(--mono); font-size: 12px; letter-spacing: 0.18em; text-transform: uppercase; }
.display  { font-family: var(--display); font-weight: 900; line-height: 0.86; letter-spacing: -0.02em; text-transform: uppercase; }
.outline  { color: transparent; -webkit-text-stroke: 1px rgba(244, 237, 224, 0.55); }
.italic-serif { font-family: "Times New Roman", Georgia, serif; font-style: italic; font-weight: 400; text-transform: none; letter-spacing: -0.01em; color: var(--accent); }

/* ====================================================================
   HERO · scroll-driven brand block (centre → nav top-left, 0–400px)
   ==================================================================== */
/* No more body lock — natural scroll. */
body.hero-locked { overflow: visible; }

.hero {
  position: relative;
  min-height: 100vh;
  height: 100vh;
  overflow: hidden;
  background: #0d0d0e;
}
.hero__scene { display: none; }

/* --------------------------------------------------------------------
   BRAND BLOCK
   Single fixed element, ALWAYS horizontally centered.
   --p drives interpolation 0 → 1 on scrollY 0 → 400.
   p=0: logo (big) above, title below, vertically centered.
   p=1: same composition, smaller, pinned to the top centre (nav slot).
   Only transform + opacity animate — top/left are static.
   -------------------------------------------------------------------- */
.brand {
  --p: 0;
  /* Block is anchored top-center; we offset translateY by half the block
     height (~200px @ scale 1) so it sits visually centered at p=0. */
  --y-start: calc(50vh - 200px);
  --y-end: 20px;
  --y: calc(var(--y-start) * (1 - var(--p)) + var(--y-end) * var(--p));
  /* Linear interpolation of scale: 1 → 0.3 */
  --s: calc(1 * (1 - var(--p)) + 0.3 * var(--p));

  position: fixed;
  top: 0; left: 50%;
  /* TranslateX(-50%) keeps it centered; translateY moves it up; scale shrinks it. */
  transform: translate3d(-50%, var(--y), 0) scale(var(--s));
  transform-origin: 50% 0%;
  z-index: var(--z-nav-brand);  /* 110 — au-dessus du side-menu (100) */
  pointer-events: none;
  will-change: transform;
  /* Force own compositor layer so transform updates skip layout/paint. */
  backface-visibility: hidden;
  -webkit-backface-visibility: hidden;
}

.brand__core {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 18px;
  /* Sparks canvas — overlays the brand block, transparent, click-through */
  position: relative;
}

.brand__logo {
  width: 320px;
  height: 320px;
  position: relative;
  display: flex; align-items: center; justify-content: center;
  /* Opacity-only pulse, GPU-composited (no transform conflict with parent). */
  animation: neonPulse 1.6s ease-in-out infinite;
  will-change: opacity;
}
/* Two stacked logo layers with STATIC drop-shadows.
   Crossfade their opacity via --p — opacity is composited, so it stays
   on the GPU thread instead of triggering a filter recompute per frame. */
.brand__logo-img {
  position: absolute;
  inset: 0;
  width: 100%; height: 100%;
  object-fit: contain;
  /* Promote to its own layer; keeps the cached filter buffer alive. */
  transform: translateZ(0);
  backface-visibility: hidden;
}
.brand__logo-img--bloom {
  /* Heavy glow — visible when centered (p≈0). */
  filter:
    drop-shadow(0 0 calc(26px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.9 * var(--neon-mult, 1))))
    drop-shadow(0 0 calc(52px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.55 * var(--neon-mult, 1))));
  opacity: calc(1 - var(--p));
}
.brand__logo-img--tight {
  /* Tight glow — visible when pinned (p≈1). */
  filter:
    drop-shadow(0 0 calc(8px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.6 * var(--neon-mult, 1))))
    drop-shadow(0 0 calc(14px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.35 * var(--neon-mult, 1))));
  opacity: var(--p);
}
@keyframes neonPulse {
  /* Opacity-only — never transform here. Transform is owned by .brand. */
  0%, 100% { opacity: 1; }
  45%      { opacity: 0.78; }
  50%      { opacity: 0.98; }
  78%      { opacity: 0.88; }
}

.brand__title {
  font-family: var(--display);
  font-size: 64px;
  letter-spacing: -0.02em;
  line-height: 1;
  color: #f4ede0;
  text-align: center;
  white-space: nowrap;
  text-shadow:
    0 0 18px rgba(var(--accent-rgb), 0.32);
}
.brand__title-1 { font-family: var(--display); }
.brand__title-2 {
  font-family: "Times New Roman", Georgia, serif;
  font-style: italic;
  font-weight: 400;
  /* Same blue as the neon logo / sparks — independent of --accent. */
  color: #60A5FA;
  letter-spacing: -0.01em;
  margin-left: 8px;
  text-shadow:
    0 0 6px  rgba(96, 165, 250, 0.95),
    0 0 14px rgba(59, 130, 246, 0.8),
    0 0 28px rgba(59, 130, 246, 0.6),
    0 0 52px rgba(59, 130, 246, 0.4);
}

@media (max-width: 768px) {
  .brand__logo  { width: 220px; height: 220px; }
  .brand__title { font-size: 38px; }
  .brand        { --y-start: calc(50vh - 140px); }
}

/* legacy holders kept around but inert */
.hero__logo-stage { display: none !important; }
.hero__split { display: none !important; }
.hero__logo-stage {
  position: absolute;
  left: 50%; top: 50%;
  transform: translate(-50%, -50%);
  width: var(--logo-w, 280px);
  height: var(--logo-h, 280px);
  max-width: 95vw;
  max-height: 85vh;
  z-index: 4;
  pointer-events: none;
  transition: width .05s linear, height .05s linear;
}
.hero__logo-stage .neon-img {
  width: 100%; height: 100%;
  object-fit: contain;
  opacity: calc((1 - var(--progress, 0)) * var(--neon-mult, 1));
  filter:
    drop-shadow(0 0 calc(20px * var(--neon-mult, 1)) rgba(var(--accent-rgb), 0.55))
    drop-shadow(0 0 calc(40px * var(--neon-mult, 1)) rgba(var(--accent-rgb), 0.3));
  transition: opacity .1s linear;
}
.neon-badge img {
  width: 100%; height: 100%;
  object-fit: contain;
  filter: drop-shadow(0 0 8px rgba(var(--accent-rgb), 0.6));
}
.neon-badge { width: 76px; height: 76px; }

.hero__logo-stage svg {
  width: 100%; height: 100%;
  filter:
    drop-shadow(0 0 calc(var(--neon-i, 1) * 32px) rgba(var(--accent-rgb), calc(var(--neon-i, 1) * 0.95)))
    drop-shadow(0 0 calc(var(--neon-i, 1) * 10px) rgba(var(--accent-rgb), calc(var(--neon-i, 1) * 0.7)));
  transition: filter .15s linear;
  opacity: calc(1 - var(--progress, 0));
}
.hero__logo-stage .neon-stroke {
  stroke: var(--accent);
  opacity: var(--neon-i, 1);
  filter: drop-shadow(0 0 calc(var(--neon-i, 1) * 12px) rgba(var(--accent-rgb), calc(var(--neon-i, 1) * 0.95)));
}
.hero__logo-stage .neon-fill { fill: rgba(var(--accent-rgb), calc(var(--neon-i, 1) * 0.10)); }
.hero__logo-stage .neon-tube {
  stroke: var(--accent);
  stroke-width: 1.5;
  opacity: var(--neon-i, 1);
  filter: drop-shadow(0 0 calc(var(--neon-i, 1) * 14px) rgba(var(--accent-rgb), 0.95));
}
.hero__logo-stage .neon-ghost { stroke: rgba(238, 234, 224, 0.12); opacity: calc(1 - var(--neon-i, 1)); }

.hero__split {
  position: relative;
  z-index: 5;
  display: flex; flex-direction: column; align-items: center;
  pointer-events: none;
  mix-blend-mode: difference;
  opacity: var(--progress, 0);
  transition: opacity .1s linear, transform .6s cubic-bezier(.7,0,.2,1);
}

/* Persistent title banner — when hero is unlocked, lock title to top */
.hero--unlocked .hero__split {
  position: fixed;
  top: 70px; left: 0; right: 0;
  z-index: 92;
  opacity: 1;
  transform: scale(0.34);
  transform-origin: center top;
  mix-blend-mode: normal;
}
.hero--unlocked .hero__split-word {
  text-shadow: 0 0 18px rgba(var(--accent-rgb), 0.35);
}
.hero__split-word {
  font-family: var(--display);
  font-size: clamp(48px, 9vw, 168px);
  text-transform: none;
  line-height: 0.9;
  letter-spacing: -0.025em;
  color: #f4ede0;
  will-change: transform;
}
.hero__split-word.right span {
  font-family: "Times New Roman", serif;
  font-style: italic;
  font-weight: 400;
  color: var(--accent);
  letter-spacing: -0.01em;
  text-shadow:
    0 0 6px rgba(var(--accent-rgb), 0.95),
    0 0 14px rgba(var(--accent-rgb), 0.8),
    0 0 28px rgba(var(--accent-rgb), 0.65),
    0 0 52px rgba(var(--accent-rgb), 0.45),
    0 0 80px rgba(var(--accent-rgb), 0.3);
  animation: neonFlicker 6s ease-in-out infinite;
}
@keyframes neonFlicker {
  0%, 3%, 5%, 12%, 14%, 27%, 31%, 42%, 49%, 51%, 68%, 71%, 84%, 92%, 100% {
    opacity: 1;
    text-shadow:
      0 0 6px rgba(var(--accent-rgb), 0.95),
      0 0 14px rgba(var(--accent-rgb), 0.8),
      0 0 28px rgba(var(--accent-rgb), 0.65),
      0 0 52px rgba(var(--accent-rgb), 0.45),
      0 0 80px rgba(var(--accent-rgb), 0.3);
  }
  4%   { opacity: 0.2; text-shadow: 0 0 3px rgba(var(--accent-rgb), 0.3); }
  13%  { opacity: 0.55; text-shadow: 0 0 5px rgba(var(--accent-rgb), 0.45); }
  28%  { opacity: 0.15; text-shadow: 0 0 2px rgba(var(--accent-rgb), 0.2); }
  30%  { opacity: 0.85; }
  43%  { opacity: 0.35; text-shadow: 0 0 4px rgba(var(--accent-rgb), 0.35); }
  50%  { opacity: 0.1;  text-shadow: 0 0 1px rgba(var(--accent-rgb), 0.15); }
  69%  { opacity: 0.6; }
  85%  { opacity: 0.25; text-shadow: 0 0 3px rgba(var(--accent-rgb), 0.25); }
  87%  { opacity: 0.9; }
}
.hero__split-word.right span { animation-duration: 7.3s; }

.hero__hint {
  position: absolute;
  left: 50%; bottom: 38px;
  transform: translateX(-50%);
  z-index: 7;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.3em;
  text-transform: uppercase;
  color: rgba(238, 234, 224, 0.55);
  opacity: calc(1 - var(--progress, 0) * 1.5);
  transition: opacity .2s;
  pointer-events: none;
  display: flex; gap: 12px; align-items: center;
}
.hero__hint .bar {
  display: inline-block;
  width: 28px; height: 1px;
  background: var(--accent);
  position: relative; overflow: hidden;
}
.hero__hint .bar::after {
  content: ""; position: absolute; inset: 0;
  background: rgba(238,234,224,0.4);
  transform-origin: left;
  transform: scaleX(calc(1 - var(--progress, 0)));
  transition: transform .1s linear;
}

/* ====================================================================
   Tired neon badge — appears after hero
   ==================================================================== */
.neon-badge {
  position: fixed;
  top: 14px; left: 50%;
  transform: translateX(-50%);
  z-index: 95;
  width: 64px; height: 64px;
  opacity: 0;
  pointer-events: none;
  transition: opacity .6s ease;
}
.neon-badge.on { opacity: 1; }
.neon-badge svg {
  width: 100%; height: 100%;
  filter: drop-shadow(0 0 8px rgba(var(--accent-rgb), 0.7));
  animation: flickerTired 4.2s linear infinite;
}
@keyframes flickerTired {
  0%, 4%, 6%, 11%, 14%, 26%, 29%, 33%, 41%, 47%, 49%, 63%, 67%, 78%, 86%, 88%, 100% { opacity: 1;   filter: drop-shadow(0 0 8px rgba(var(--accent-rgb), 0.85)); }
  5%   { opacity: 0.15; filter: drop-shadow(0 0 2px rgba(var(--accent-rgb), 0.2)); }
  12%  { opacity: 0.7;  filter: drop-shadow(0 0 5px rgba(var(--accent-rgb), 0.55)); }
  13%  { opacity: 0.2;  filter: drop-shadow(0 0 1px rgba(var(--accent-rgb), 0.18)); }
  27%  { opacity: 0.8;  filter: drop-shadow(0 0 6px rgba(var(--accent-rgb), 0.6)); }
  31%  { opacity: 0.3;  filter: drop-shadow(0 0 2px rgba(var(--accent-rgb), 0.25)); }
  42%  { opacity: 0.55; filter: drop-shadow(0 0 3px rgba(var(--accent-rgb), 0.35)); }
  48%  { opacity: 0.18; filter: drop-shadow(0 0 1px rgba(var(--accent-rgb), 0.18)); }
  64%  { opacity: 0.4;  filter: drop-shadow(0 0 3px rgba(var(--accent-rgb), 0.3)); }
  77%  { opacity: 0.6;  filter: drop-shadow(0 0 4px rgba(var(--accent-rgb), 0.4)); }
  87%  { opacity: 0.25; filter: drop-shadow(0 0 2px rgba(var(--accent-rgb), 0.22)); }
}
.neon-badge svg, .neon-badge img { animation-duration: 5.7s; }

.hero--unlocked .hero__logo-stage { opacity: 0; transition: opacity .6s ease; }
.hero--unlocked .hero__split { opacity: 1 !important; transition: opacity .6s ease; }
.hero__bg {
  position: absolute; inset: -10% 0 0 0; height: 115%;
  opacity: var(--bg-fade, 1);
  /* L'image, son point focal et son zoom sont pilotés par 3 CSS vars
     modifiables depuis l'admin (--hero-bg, --hero-pos, --hero-zoom). */
  background-image:
    linear-gradient(180deg, rgba(13,13,14,0.55) 0%, rgba(13,13,14,0.45) 35%, rgba(13,13,14,0.85) 75%, rgba(13,13,14,0.95) 100%),
    var(--hero-bg, url("assets/hero-bg.webp"));
  background-size: cover;
  background-position: center, var(--hero-pos, center 35%);
  background-repeat: no-repeat;
  /* Zoom du cadrage (piloté par l'admin) — défaut 1 = aucun effet. */
  transform: scale(var(--hero-zoom, 1));
  transform-origin: var(--hero-pos, center 35%);
  will-change: transform;
}
/* Vidéo de fond du hero (iframe Vimeo/YouTube) — couvre tout le hero façon
   object-fit:cover : on dimensionne le 16:9 pour déborder puis on centre. */
.hero__video {
  position: absolute; top: 50%; left: 50%;
  transform: translate(-50%, -50%);
  width: 100vw; height: 56.25vw;          /* 16:9 basé largeur */
  min-width: 177.78vh; min-height: 100vh; /* … ou basé hauteur, le plus grand gagne */
  border: 0;
  pointer-events: none;                    /* le hero reste cliquable/scrollable */
  z-index: 0;
}
/* Voile dégradé au-dessus de la vidéo — lisibilité du logo/nav. S'efface en
   mode immersif (idle) pour dévoiler la vidéo nette. */
.hero__video-scrim {
  position: absolute; inset: 0; z-index: 1; pointer-events: none;
  background: linear-gradient(180deg, rgba(13,13,14,0.5) 0%, rgba(13,13,14,0.32) 38%, rgba(13,13,14,0.72) 78%, rgba(13,13,14,0.9) 100%);
  transition: opacity 1.2s ease;
}
body.hero-immersive .hero__video-scrim { opacity: 0.15; }
/* Surcouches du hero qui s'effacent en mode immersif (idle) */
.hero__nav, .hero__grid, .hero__hint, .hero__foot, .brand {
  transition: opacity 1.1s ease;
}
body.hero-immersive .hero__nav,
body.hero-immersive .hero__grid,
body.hero-immersive .hero__hint,
body.hero-immersive .hero__foot,
body.hero-immersive .hero__glow,
body.hero-immersive .brand {
  opacity: 0;
  pointer-events: none;
}
.hero__stripes { display: none; }
.hero__glow {
  position: absolute; left: 50%; top: 38%;
  width: 60vw; height: 50vh;
  transform: translate(-50%, -50%);
  background: radial-gradient(ellipse, rgba(var(--accent-rgb), 0.18) 0%, transparent 65%);
  filter: blur(40px);
  pointer-events: none;
  z-index: 2;
}
.hero__logo {
  position: absolute; left: 50%; top: 48%;
  transform: translate(calc(-50% + var(--mx, 0px)), calc(-50% + var(--my, 0px)));
  width: clamp(280px, 38vw, 560px);
  z-index: 3;
  pointer-events: none;
  will-change: transform, opacity;
  transition: opacity .4s;
}
.hero__logo svg, .hero__logo img { width: 100%; height: auto; }

.hero__nav {
  position: absolute; top: 0; left: 0; right: 0;
  display: grid;
  grid-template-columns: 1fr auto 1fr;
  align-items: center;
  padding: 22px var(--pad-x);
  z-index: 8;
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
}
.hero__nav-l, .hero__nav-r { display: flex; gap: 26px; }
.hero__nav-r { justify-content: flex-end; }
.hero__nav a { color: var(--ink); opacity: 0.85; transition: opacity .2s, color .2s; }
.hero__nav a:hover { opacity: 1; color: var(--accent); }
.hero__nav .live::before {
  content: ""; display: inline-block;
  width: 6px; height: 6px;
  background: var(--live);
  border-radius: 50%;
  margin-right: 8px;
  vertical-align: middle;
  box-shadow: 0 0 8px var(--live);
  animation: livePulse 1.6s ease-in-out infinite;
}
@keyframes livePulse {
  0%, 100% { opacity: 1; transform: scale(1); }
  50%      { opacity: 0.45; transform: scale(0.7); }
}
.hero__mark {
  font-family: var(--display);
  font-size: 15px;
  letter-spacing: 0.15em;
  text-align: center;
  line-height: 1.05;
}
.hero__mark small {
  display: block;
  font-family: var(--mono);
  font-size: 9px;
  font-weight: 400;
  letter-spacing: 0.32em;
  opacity: 0.55;
  margin-top: 4px;
}

.hero__grid {
  position: absolute;
  top: 80px; left: var(--pad-x); right: var(--pad-x);
  display: grid;
  grid-template-columns: 1fr 1fr 1fr;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.32em;
  text-transform: uppercase;
  color: rgba(238, 234, 224, 0.78);
  z-index: 6;
}
.hero__grid > :nth-child(2) { text-align: center; }
.hero__grid > :nth-child(3) { text-align: right; }
.hero__grid a {
  transition: color .25s ease, text-shadow .25s ease, opacity .25s ease;
  opacity: 0.85;
}
.hero__grid a:hover {
  /* Neon blue — same colour family as the logo / "Films" italic */
  color: #60A5FA;
  opacity: 1;
  text-shadow:
    0 0 6px  rgba(96, 165, 250, 0.9),
    0 0 14px rgba(59, 130, 246, 0.7),
    0 0 28px rgba(59, 130, 246, 0.45);
}

.hero__display {
  position: absolute;
  left: var(--pad-x); right: var(--pad-x);
  bottom: clamp(140px, 18vh, 200px);
  font-family: var(--display);
  font-weight: 900;
  line-height: 0.85;
  letter-spacing: -0.025em;
  text-transform: uppercase;
  font-size: clamp(56px, 13vw, 200px);
  color: #f4ede0;
  z-index: 4;
  will-change: transform;
}
.hero__display .row { display: block; }

.hero__foot {
  position: absolute;
  bottom: 30px; left: var(--pad-x); right: var(--pad-x);
  display: grid;
  grid-template-columns: 1fr 1fr 1fr 1fr;
  gap: 24px;
  align-items: end;
  z-index: 6;
}
.hero__foot .lbl {
  display: block;
  font-family: var(--mono);
  font-size: 9px;
  letter-spacing: 0.3em;
  text-transform: uppercase;
  color: rgba(238, 234, 224, 0.45);
  margin-bottom: 4px;
}
.hero__foot .val {
  font-family: var(--body);
  font-weight: 500;
  font-size: 14px;
  color: #f4ede0;
}
.hero__cta {
  font-family: var(--body);
  font-size: 14px;
  font-weight: 500;
  color: #f4ede0;
  border-bottom: 1px solid #f4ede0;
  padding-bottom: 4px;
  justify-self: end;
  transition: color .2s, border-color .2s, transform .2s;
}
.hero__cta:hover { color: var(--accent); border-color: var(--accent); transform: translateX(4px); }

/* ====================================================================
   MARQUEE
   ==================================================================== */
.marquee {
  /* Traits haut/bas supprimés — plus de filets autour des sections,
     seules les séparations services / galeries photo / journal restent. */
  overflow: hidden;
  padding: 20px 0;
  background: var(--bg);
}
.marquee__track {
  display: inline-flex;
  gap: 56px;
  white-space: nowrap;
  animation: marquee 30s linear infinite;
  font-family: var(--display);
  font-size: clamp(40px, 6.4vw, 88px);
  text-transform: uppercase;
  line-height: 1;
  letter-spacing: -0.02em;
}
.marquee__track .star { color: var(--accent); }
.marquee__track .ghost { color: transparent; -webkit-text-stroke: 1px rgba(238,234,224,0.4); }
@keyframes marquee {
  from { transform: translateX(0); }
  to   { transform: translateX(-50%); }
}

/* ====================================================================
   SECTION HELPERS
   ==================================================================== */
.section { padding: var(--section-y) var(--pad-x); position: relative; }
.section--light { background: var(--bg-light); color: #111; }

.section__head {
  display: grid;
  grid-template-columns: 100px 1fr;
  gap: 32px;
  align-items: start;
  padding-bottom: 56px;
  margin-bottom: 64px;
}
.section__head .num   { font-family: var(--mono); font-size: 12px; letter-spacing: 0.2em; color: var(--ink-mute); }
.section--light .section__head .num { color: #999; }
.section__head .title { font-family: var(--display); font-size: clamp(40px, 6vw, 88px); line-height: 0.9; text-transform: uppercase; letter-spacing: -0.025em; }
.section__head .sub   { font-family: var(--mono); font-size: 12px; letter-spacing: 0.14em; text-transform: uppercase; color: var(--ink-soft); margin-top: 18px; max-width: 480px; }
.section--light .section__head .sub { color: #666; }

/* ====================================================================
   MANIFESTE (LUX inline editorial — light)
   ==================================================================== */
.manifeste { padding: var(--section-y) var(--pad-x); background: var(--bg-light); color: #0a0a0a; }
.manifeste .label { font-family: var(--mono); font-size: 11px; letter-spacing: 0.28em; color: #777; margin-bottom: 40px; text-transform: uppercase; }
.manifeste__txt {
  font-family: var(--display);
  /* Grande taille (comme avant) MAIS pleine largeur → moins de retours à la
     ligne (le cap max-width:1480px forçait ~7 lignes). Vise ~3-4 lignes. */
  font-size: clamp(30px, 4.5vw, 82px);
  line-height: 1.0;
  text-transform: uppercase;
  letter-spacing: -0.03em;
  max-width: none;
  text-align: justify;
  text-justify: inter-word;
}
.manifeste__txt .swatch {
  display: inline-block;
  width: clamp(52px, 5.4vw, 92px);
  height: clamp(32px, 3.2vw, 56px);
  vertical-align: middle;
  margin: 0 8px;
  border-radius: 2px;
}
.manifeste__txt .accent {
  font-family: "Times New Roman", serif;
  font-style: italic;
  font-weight: 400;
  text-transform: none;
  letter-spacing: -0.01em;
  color: var(--accent);
}
.manifeste__meta {
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  gap: 32px;
  margin-top: 80px;
  padding-top: 32px;
}
.manifeste__meta .col { font-family: var(--mono); font-size: 12px; letter-spacing: 0.1em; text-transform: uppercase; line-height: 1.6; }
.manifeste__meta .col strong { display: block; font-weight: 700; color: #000; margin-bottom: 4px; }
.manifeste__meta .col span { color: #666; }

/* ====================================================================
   SERVICES
   --------------------------------------------------------------------
   UNE SEULE image BTS (caméra ARRI), continue, couvre toute la section
   en parallax : nette dans la bande du head (les calques de flou ne
   commencent qu'en dessous), puis floutée progressivement jusqu'en bas
   via des calques backdrop-filter masqués (.services__blur, technique
   "progressive blur" : flou croissant sans palier). Un voile (::after)
   garde les lignes de services lisibles et fond le bas de section dans
   var(--bg).
   ==================================================================== */
.services {
  padding: var(--section-y) var(--pad-x);
  background: var(--bg);
  position: relative;
  overflow: hidden;
  isolation: isolate;
  /* Parallax MESURÉ sur le head (même formule/ressenti que les autres
     heads pendant sa traversée) mais ÉCRIT ici : l'image plein-section
     le porte. Au-delà du head, l'offset reste saturé au clamp ±220px. */
  --parallax-y: 0px;
}
/* Image plein-section : mêmes sources/réglages admin que le head
   (--services-head-bg / focal / zoom), débordement vertical = amplitude
   parallax + marge, comme les ::before des heads. */
.services::before {
  content: "";
  position: absolute;
  top: calc(-1 * (var(--head-parallax-travel, 220px) + 24px));
  bottom: calc(-1 * (var(--head-parallax-travel, 220px) + 24px));
  left: 0;
  right: 0;
  z-index: -1;
  display: none;   /* PAS de photo de fond par défaut : section propre/sombre ; la photo n'apparaît qu'au survol d'un titre */
  background-image: var(--services-head-bg, url("assets/services-bg.webp"));
  background-repeat: no-repeat;
  background-size: cover;
  background-position: var(--services-head-focal, 50% 50%);
  transform: translate3d(0, var(--parallax-y, 0px), 0) scale(var(--services-head-zoom, 1));
  transform-origin: var(--services-head-focal, 50% 50%);
  -webkit-filter: url(#svc-smear) saturate(1.22) brightness(1.12);
  filter: url(#svc-smear) saturate(1.22) brightness(1.12);
  will-change: transform;
}
/* AUCUN voile sur la section (opacité 0 partout — la transition entre
   head et lignes ne se fait que par le flou progressif). Seul reste un
   fondu de SORTIE vers var(--bg) tout en bas, pour la jonction avec la
   section Photo. */
.services::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  background: linear-gradient(
    to bottom,
    rgba(13, 13, 14, 0) 86%,
    var(--bg) 100%
  );
}
/* Calques de flou progressif — couvrent la section, le head (z 1) les
   occulte sur sa bande : la photo y reste nette. Rampes des masques en
   chevauchement → flou perçu continu de ~0 (sous le head) à 20px (bas). */
.services__blur {
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
}
.services__blur > span { display: none; }
@supports ((backdrop-filter: blur(1px)) or (-webkit-backdrop-filter: blur(1px))) {
  .services__blur > span {
    display: block;
    position: absolute;
    inset: 0;
  }
  .services__blur > span:nth-child(1) {
    -webkit-backdrop-filter: blur(2px);
            backdrop-filter: blur(2px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 4%, #000 18%, #000 32%, transparent 46%);
            mask-image: linear-gradient(to bottom, transparent 4%, #000 18%, #000 32%, transparent 46%);
  }
  .services__blur > span:nth-child(2) {
    -webkit-backdrop-filter: blur(5px);
            backdrop-filter: blur(5px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 18%, #000 32%, #000 46%, transparent 60%);
            mask-image: linear-gradient(to bottom, transparent 18%, #000 32%, #000 46%, transparent 60%);
  }
  .services__blur > span:nth-child(3) {
    -webkit-backdrop-filter: blur(9px);
            backdrop-filter: blur(9px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 32%, #000 46%, #000 60%, transparent 74%);
            mask-image: linear-gradient(to bottom, transparent 32%, #000 46%, #000 60%, transparent 74%);
  }
  .services__blur > span:nth-child(4) {
    -webkit-backdrop-filter: blur(14px);
            backdrop-filter: blur(14px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 46%, #000 60%, #000 74%, transparent 88%);
            mask-image: linear-gradient(to bottom, transparent 46%, #000 60%, #000 74%, transparent 88%);
  }
  /* Dernier calque : tient le flou max jusqu'en bas. */
  .services__blur > span:nth-child(5) {
    -webkit-backdrop-filter: blur(20px);
            backdrop-filter: blur(20px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 60%, #000 74%, #000 100%);
            mask-image: linear-gradient(to bottom, transparent 60%, #000 74%, #000 100%);
  }
}
/* Mobile : 3 calques (2/6/12px) pour préserver les FPS. */
@media (max-width: 640px) {
  .services__blur > span:nth-child(1) {
    -webkit-mask-image: linear-gradient(to bottom, transparent 0%, #000 20%, #000 40%, transparent 60%);
            mask-image: linear-gradient(to bottom, transparent 0%, #000 20%, #000 40%, transparent 60%);
  }
  .services__blur > span:nth-child(2) {
    -webkit-backdrop-filter: blur(6px);
            backdrop-filter: blur(6px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 20%, #000 40%, #000 60%, transparent 80%);
            mask-image: linear-gradient(to bottom, transparent 20%, #000 40%, #000 60%, transparent 80%);
  }
  .services__blur > span:nth-child(3) {
    -webkit-backdrop-filter: blur(12px);
            backdrop-filter: blur(12px);
    -webkit-mask-image: linear-gradient(to bottom, transparent 40%, #000 65%, #000 100%);
            mask-image: linear-gradient(to bottom, transparent 40%, #000 65%, #000 100%);
  }
  .services__blur > span:nth-child(4),
  .services__blur > span:nth-child(5) { display: none; }
}
/* Le head (image nette) et les lignes passent AU-DESSUS du flou/voile. */
.services > .section__head { z-index: 1; }
.services__list {
  position: relative;
  z-index: 1;
  border-top: 1px solid var(--line);
}
/* Typo de la section : tout ce qui n'est pas bleu passe en blanc cassé
   charte (#F5F5F0) — les gris (num, sub, desc) manquaient de présence
   sur l'image sans voile. Les éléments bleus (italic-serif, flip hover,
   accents) ne sont pas touchés. */
.services > .section__head .num,
.services > .section__head .sub,
.services .svc-row__num,
.services .svc-row__desc,
.services .svc-row__title {
  color: #F5F5F0;
}

/* Head de la section Services — photo BTS de la caméra ARRI en fond,
   visible à droite, fade noir à gauche, parallax vertical (sens inverse).
   Pattern identique à la section "LA vidéo" (.portfolio__head). */
.services > .section__head {
  position: relative;
  /* Plein-bleed : on neutralise le padding-x de .services */
  margin-left:  calc(var(--pad-x) * -1);
  margin-right: calc(var(--pad-x) * -1);
  margin-top:   calc(var(--section-y) * -1);
  padding: clamp(90px, 14vw, 160px) var(--pad-x) clamp(48px, 6vw, 72px);
  margin-bottom: clamp(40px, 5vw, 64px);
  isolation: isolate;
  overflow: hidden;
  /* Pas de background-color : l'image plein-section transparaît dans la
     bande du head — c'est la MÊME photo que derrière le corps. */
}
/* Voile (gradients) sur ::after — opacité contrôlable depuis l'admin */
.services > .section__head::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  /* UNIQUE dégradé d'ENTRÉE de section : fondu depuis la section
     précédente vers l'image, sur ~38% du head. Aucun autre voile sur le
     head — plus aucune différence d'opacité entre sa bande et celle des
     lignes : la transition se fait uniquement par le flou progressif. */
  background-image: linear-gradient(
    to bottom,
    var(--bg) 0%,
    rgba(13, 13, 14, 0.62) 16%,
    rgba(13, 13, 14, 0) 38%
  );
  background-repeat: no-repeat;
  background-size: 100% 100%;
  background-position: 0% 0%;
  opacity: var(--services-head-overlay-opacity, 1);
}
/* L'image va dans un pseudo derrière les gradients, pour supporter transform: scale (zoom).
   Le parallax est ré-appliqué via translateY (translate non affecté par transform-origin). */
/* Pas de ::before sur le head Services : c'est l'image PLEIN-SECTION
   (.services::before) qui transparaît dans sa bande — une seule photo
   continue du head jusqu'en bas, nette ici, floutée plus bas. */

@media (prefers-reduced-motion: reduce) {
  .services { --parallax-y: 0px !important; }
}
/* Canvas WebGL "verre liquide" : porte la photo du service, déformée par le
   fluide. pointer-events:none → les titres restent survolables (le pointeur
   est écouté sur la section). Sous le voile/texte. */
.services__fluid {
  position: absolute;
  inset: 0;
  z-index: 0;
  width: 100%;
  height: 100%;
  display: block;
  pointer-events: none;
  opacity: 0;
  transition: opacity .6s ease;
}
.services.is-fluid .services__fluid { opacity: 1; }
/* Quand le fluide est actif, il porte l'image → on masque les calques CSS
   (photos crossfade + image de base) pour éviter le doublon. */
.services.is-fluid .services__photos { display: none; }
.services.is-fluid::before { opacity: 0; }
/* Photos par service — révélées en crossfade au survol du titre (Obvious
   Art). Placées au-dessus du flou (donc nettes) mais sous le contenu ;
   un voile sombre assure la lisibilité des titres. */
.services__photos {
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  /* L'image maculée FLOTTE au centre et se fond dans le noir sur les bords
     (comme obvious-art) via un masque radial elliptique. */
  -webkit-mask-image: radial-gradient(96% 86% at 50% 48%, #000 42%, rgba(0,0,0,0) 92%);
          mask-image: radial-gradient(96% 86% at 50% 48%, #000 42%, rgba(0,0,0,0) 92%);
}
.services__photo {
  position: absolute;
  inset: -80px;                 /* déborde large : le smear horizontal ne révèle pas de halo */
  background-size: cover;
  background-repeat: no-repeat;
  -webkit-filter: url(#svc-smear) saturate(1.22) brightness(1.12);
  filter: url(#svc-smear) saturate(1.22) brightness(1.12);
  opacity: 0;
  transition: opacity 1.6s ease-in-out;
  will-change: opacity;
}
.services__veil {
  position: absolute;
  inset: 0;
  /* 1er calque : FONDU DÉGRADÉ EN HAUT du module (var(--bg) → transparent)
     pour une transition douce depuis la section précédente.
     2e calque : voile sombre léger (lisibilité des titres, photo bien visible). */
  background:
    linear-gradient(to bottom, var(--bg) 0%, rgba(13, 13, 14, 0) 15%),
    linear-gradient(to bottom, rgba(6, 6, 9, 0.06) 0%, rgba(6, 6, 9, 0.30) 100%);
  opacity: 1;   /* voile constant : l'effet verre dépoli est toujours présent */
}
@media (prefers-reduced-motion: reduce) {
  .services__photo, .services__veil { transition: none; }
}

/* Vitre dépolie texturée sur TOUTE la section "Ce qu'on fait" : la photo
   (qui change au survol) est vue à travers du verre. Frost léger (photo
   reconnaissable) + teinte translucide + grain (la texture) + reflet
   spéculaire + liseré de lumière interne sur les bords du panneau. Au-dessus
   des photos, SOUS le contenu (titres/desc restent nets et lisibles). */
.services__glass {
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  /* Comme obvious-art : PAS de grain. La "texture" vient du smear de l'image
     (flou directionnel, cf. .services__photo). On ne garde qu'un très léger
     reflet + un vignettage interne pour fondre les bords dans le noir. */
  background: var(--glass-sheen);
  background-repeat: no-repeat;
  background-size: cover;
  background-position: center;
  box-shadow: inset 0 0 120px rgba(0, 0, 0, 0.35);
}
/* Le flou progressif d'origine est remplacé par la vitre uniforme. */
.services__blur { display: none; }

.svc-row {
  display: grid;
  grid-template-columns: 80px 1fr 320px;
  align-items: center;
  gap: 32px;
  padding: 40px 0;
  border-bottom: 1px solid var(--line);
  position: relative;
  transition: padding .4s;
}
/* Quand le service a une image (--svc-img défini en inline),
   on l'affiche en background à gauche avec un dégradé sombre qui masque
   progressivement la droite — garde la lisibilité du titre + description. */
.svc-row--with-image {
  /* Image visible à DROITE — dégradé sombre masque la GAUCHE (où passent num + titre) */
  background-image:
    linear-gradient(
      to left,
      rgba(13, 13, 14, 0)    0%,
      rgba(13, 13, 14, 0)    35%,
      rgba(13, 13, 14, 0.55) 65%,
      rgba(13, 13, 14, 0.92) 88%,
      var(--bg)              100%
    ),
    var(--svc-img);
  background-size: cover, cover;
  background-position: right center, var(--svc-pos, right center);
  background-repeat: no-repeat;
  padding-left: var(--pad-x);
  padding-right: var(--pad-x);
  margin-left: calc(var(--pad-x) * -1);
  margin-right: calc(var(--pad-x) * -1);
}
.svc-row__num   { font-family: var(--mono); font-size: 12px; letter-spacing: 0.2em; color: var(--ink-mute); }
.svc-row__title { font-family: var(--display); font-size: clamp(22px, 3.4vw, 50px); text-transform: uppercase; line-height: 0.95; letter-spacing: -0.02em; }
.svc-row__desc  { font-family: var(--mono); font-size: 12px; letter-spacing: 0.06em; text-transform: uppercase; color: var(--ink-soft); text-align: right; line-height: 1.5; }

/* Flip-link hover effect — the title slides up and a blue clone rises from
   below to replace it. Pure CSS, GPU-accelerated transform. */
.svc-row__title-flip {
  position: relative;
  display: inline-block;
  overflow: hidden;
  vertical-align: top;
  line-height: 1;
  /* Tiny vertical padding so descenders & glow aren't clipped */
  padding: 0.04em 0.06em;
  margin: -0.04em -0.06em;
}
.svc-row__title-text {
  display: block;
  transition: transform .55s cubic-bezier(.65, 0, .35, 1);
  will-change: transform;
}
.svc-row__title-text--hover {
  position: absolute;
  top: 0; left: 0;
  width: 100%;
  padding: inherit;
  transform: translateY(110%);
  color: var(--accent);
  text-shadow:
    0 0 12px rgba(var(--accent-rgb), 0.55),
    0 0 28px rgba(var(--accent-rgb), 0.3);
}
.svc-row:hover .svc-row__title-text                       { transform: translateY(-110%); }
.svc-row:hover .svc-row__title-text--hover                { transform: translateY(0); }
@media (prefers-reduced-motion: reduce) {
  .svc-row__title-text { transition: none; }
}

/* Scramble "tableau d'aéroport" : le ghost (texte final) fixe la largeur,
   les lettres animées occupent des cases de largeur égale par-dessus →
   nombre de lettres constant, aucun voisin qui bouge. */
/* Le mot ne se coupe jamais (nowrap) ; seul le "& ..." (em, hors scramble)
   passe à la ligne selon l'écran → nombre de lignes stable. */
.svc-scramble { display: inline-block; white-space: nowrap; vertical-align: top; }
/* Chaque case = largeur de SA lettre finale (ghost caché) ; la lettre
   animée (live) est centrée par-dessus sans changer la largeur. */
.svc-flap { position: relative; display: inline-block; }
.svc-flap__g { visibility: hidden; }
.svc-flap__l { position: absolute; inset: 0; text-align: center; }
/* Titre bleu au survol */
.svc-row.is-active .svc-row__title { color: var(--accent); }

/* ====================================================================
   SERVICES — tiroirs vidéo (projets fusionnés sous chaque thème)
   ==================================================================== */
.svc-group {
  position: relative;
  z-index: 1;
  /* Séparateur de ligne porté par le groupe → présent que le tiroir soit
     ouvert ou fermé (le tiroir n'est rendu qu'à l'ouverture). */
  border-bottom: 1px solid var(--line);
}
/* La ligne service devient un bouton dépliable */
button.svc-row {
  appearance: none;
  background: transparent;
  border: 0;
  border-bottom: 0;     /* le séparateur est porté par .svc-group */
  width: 100%;
  font: inherit;
  color: inherit;
  text-align: left;
  cursor: pointer;
}
.svc-row--toggle { grid-template-columns: 80px 1fr 320px auto; }
.svc-row--toggle:focus-visible { outline: 2px solid var(--accent); outline-offset: -2px; }
.svc-row__toggle-end {
  display: flex; align-items: center; gap: 14px;
  justify-self: end;
}
.svc-row__count {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.18em;
  text-transform: uppercase; color: var(--accent); white-space: nowrap;
}
.svc-row__chevron {
  font-size: 24px; line-height: 1; color: var(--ink-soft);
  transition: transform .4s cubic-bezier(.22,1,.36,1), color .3s;
}
.svc-row--toggle.is-open .svc-row__chevron { transform: rotate(180deg); color: var(--accent); }

/* Tiroir : rendu uniquement à l'ouverture (cf. JSX) → animation d'entrée
   simple et fiable (fondu + glissé), pas de bidouille de hauteur. */
.svc-drawer {
  overflow: hidden;
  animation: svc-drawer-in .42s cubic-bezier(.22, 1, .36, 1) both;
}
@keyframes svc-drawer-in {
  from { opacity: 0; transform: translateY(-8px); }
  to   { opacity: 1; transform: translateY(0); }
}
@media (prefers-reduced-motion: reduce) {
  .svc-drawer { animation: none; }
}
/* Carrousel horizontal type Netflix / portail VOD */
.svc-carousel { position: relative; }
.svc-drawer__row {
  display: flex;
  gap: 18px;
  /* padding vertical = marge pour le zoom au survol (sinon clippé par overflow) */
  padding: 18px 0 30px;
  overflow-x: auto;
  overflow-y: hidden;
  scroll-snap-type: x proximity;
  -webkit-overflow-scrolling: touch;        /* inertie iOS */
  /* Barre de défilement masquée (demande utilisateur) — la navigation se fait
     par les flèches (desktop) ou le swipe (tactile). */
  scrollbar-width: none;
  -ms-overflow-style: none;
}
.svc-drawer__row::-webkit-scrollbar { display: none; width: 0; height: 0; }
/* Flèches latérales — apparaissent au survol du carrousel (desktop). */
.svc-carousel__arrow {
  position: absolute;
  top: 18px;                 /* aligné avec le haut des vignettes (padding-top du row) */
  bottom: 76px;              /* s'arrête au-dessus de la zone titre/infos */
  width: 52px;
  display: flex; align-items: center; justify-content: center;
  border: 0;
  font-family: var(--body); font-size: 30px; line-height: 1; color: #fff;
  cursor: pointer;
  z-index: 4;
  opacity: 0;
  pointer-events: none;   /* n'intercepte les clics que quand visible (cf. --scrollable:hover) */
  transition: opacity .25s ease, background .25s ease;
}
.svc-carousel__arrow--prev {
  left: 0;
  background: linear-gradient(to right, rgba(8,8,10,0.92) 0%, rgba(8,8,10,0.55) 60%, rgba(8,8,10,0) 100%);
  justify-content: flex-start; padding-left: 8px;
}
.svc-carousel__arrow--next {
  right: 0;
  background: linear-gradient(to left, rgba(8,8,10,0.92) 0%, rgba(8,8,10,0.55) 60%, rgba(8,8,10,0) 100%);
  justify-content: flex-end; padding-right: 8px;
}
.svc-carousel--scrollable:hover .svc-carousel__arrow { opacity: 1; pointer-events: auto; }
.svc-carousel__arrow:hover { color: var(--accent); }
/* Sans survol (tactile) : pas de flèches, on scrolle au doigt. */
@media (hover: none) {
  .svc-carousel__arrow { display: none; }
}
.svc-tile {
  appearance: none; border: 0; background: transparent; padding: 0;
  font: inherit; color: inherit; text-align: left; cursor: pointer;
  display: flex; flex-direction: column; gap: 10px;
  flex: 0 0 auto;
  width: clamp(230px, 26vw, 320px);
  scroll-snap-align: start;
  transition: transform .35s cubic-bezier(.22,1,.36,1);
}
.svc-tile:hover, .svc-tile:focus-visible { transform: scale(1.045); z-index: 2; }
.svc-tile:focus-visible { outline: none; }
.svc-tile__media {
  position: relative;
  aspect-ratio: 16 / 9;
  background-size: cover; background-position: center; background-repeat: no-repeat;
  overflow: hidden;
  border-radius: 7px;
  border: 1px solid var(--line);
  box-shadow: 0 6px 22px rgba(0,0,0,0.40);
  transition: border-color .3s, box-shadow .35s;
}
.svc-tile:hover .svc-tile__media,
.svc-tile:focus-visible .svc-tile__media {
  border-color: rgba(var(--accent-rgb), 0.7);
  box-shadow: 0 16px 44px rgba(0,0,0,0.6), 0 0 0 1px rgba(var(--accent-rgb), 0.45);
}
.svc-tile__play {
  position: absolute; inset: 0; margin: auto;
  width: 54px; height: 54px; border-radius: 50%;
  display: flex; align-items: center; justify-content: center;
  background: rgba(0,0,0,0.42); color: #fff; font-size: 16px;
  padding-left: 3px;     /* recentre le glyphe ▶ */
  -webkit-backdrop-filter: blur(4px); backdrop-filter: blur(4px);
  border: 1px solid rgba(255,255,255,0.45);
  opacity: 0.85;
  transition: transform .3s, background .3s, border-color .3s, opacity .3s;
  z-index: 2;
}
.svc-tile:hover .svc-tile__play,
.svc-tile:focus-visible .svc-tile__play { transform: scale(1.12); background: var(--accent); border-color: var(--accent); opacity: 1; }
/* Voile + infos révélés au survol (synopsis, badges) */
.svc-tile__hover {
  position: absolute; inset: 0;
  display: flex; flex-direction: column; justify-content: flex-end;
  gap: 8px; padding: 12px;
  background: linear-gradient(180deg, rgba(0,0,0,0) 30%, rgba(0,0,0,0.86) 100%);
  opacity: 0;
  transition: opacity .3s ease;
}
.svc-tile:hover .svc-tile__hover,
.svc-tile:focus-visible .svc-tile__hover { opacity: 1; }
.svc-tile__badges { display: flex; flex-wrap: wrap; gap: 6px; }
.svc-tile__badge {
  font-family: var(--mono); font-size: 9.5px; letter-spacing: 0.12em; text-transform: uppercase;
  color: #f4ede0; padding: 3px 7px; border: 1px solid rgba(255,255,255,0.35); border-radius: 3px;
  background: rgba(0,0,0,0.35);
}
.svc-tile__badge--play { background: var(--accent); border-color: var(--accent); color: #fff; }
.svc-tile__synopsis {
  margin: 0; font-family: var(--body); font-size: 12px; line-height: 1.45; color: rgba(244,237,224,0.92);
  /* 3 lignes max */
  display: -webkit-box; -webkit-line-clamp: 3; -webkit-box-orient: vertical; overflow: hidden;
}
.svc-tile__info { display: flex; flex-direction: column; gap: 3px; }
.svc-tile__client { font-family: var(--mono); font-size: 10px; letter-spacing: 0.16em; text-transform: uppercase; color: var(--ink-mute); }
.svc-tile__title  { font-family: var(--display); font-size: 18px; text-transform: uppercase; line-height: 1; letter-spacing: -0.01em; color: var(--ink); transition: color .3s; }
.svc-tile:hover .svc-tile__title { color: var(--accent); }

/* ====================================================================
   PHOTO SECTION  (contact-sheet mosaic + lightbox)
   ==================================================================== */
.photo-section {
  padding: var(--section-y) var(--pad-x);
  background: var(--bg);
  position: relative;
}

.photo-section__head {
  position: relative;
  display: grid;
  /* Titre ancré en bas à GAUCHE (même position que le head La vidéo) :
     rangée 1 = numéro (toute la largeur), rangée 2 = titre à gauche +
     tag PORTRAIT · PLATEAU · SCÈNE en bas à droite. */
  grid-template-columns: 1fr auto;
  gap: 18px 32px;
  align-items: end;

  /* Pull to section edges so the bg image is full-bleed inside the section. */
  margin-left:  calc(var(--pad-x) * -1);
  margin-right: calc(var(--pad-x) * -1);
  margin-top:   calc(var(--section-y) * -1);
  margin-bottom: clamp(40px, 6vw, 80px);
  padding: clamp(90px, 15vw, 160px) var(--pad-x) clamp(48px, 6vw, 72px);

  /* Parallax offset (px), updated by JS on scroll. The image background's
     vertical position is computed from this value so the photo glides
     while the text and surrounding sections scroll normally. */
  --parallax-y: 0px;

  background-color: var(--bg);
  overflow: hidden;
  isolation: isolate;
}
/* Voile (gradients) sur ::after — opacité contrôlable */
.photo-section__head::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  /* Couches (du dessus vers le dessous) :
     0. Ombres internes haut/bas (noir → transparent sur ~60px) — léger
        effet 3D : l'image paraît en retrait derrière les bords.
     1. Fade vertical haut + bas vers var(--bg) — adoucit la transition de
        l'image pendant le parallax (effet de fondu doux aux bordures).
     2. Fade horizontal — bg opaque à gauche/droite, image révélée au centre.
     3. Voile vertical sombre — du léger en haut au fond bg en bas. */
  background-image:
    linear-gradient(to bottom, rgba(0,0,0,0.42) 0px, rgba(0,0,0,0) var(--head-shadow-top, 68px)),
    linear-gradient(to top, rgba(0,0,0,0.32) 0px, rgba(0,0,0,0) var(--head-shadow-bottom, 52px)),
    linear-gradient(to bottom, var(--bg) 0%, rgba(13,13,14,0) 14%, rgba(13,13,14,0) 86%, var(--bg) 100%),
    linear-gradient(to right, var(--bg) 0%, rgba(13,13,14,0) 18%, rgba(13,13,14,0) 82%, var(--bg) 100%),
    linear-gradient(to bottom, rgba(13,13,14,0.10) 0%, rgba(13,13,14,0.35) 70%, var(--bg) 100%);
  background-repeat: no-repeat, no-repeat, no-repeat, no-repeat, no-repeat;
  background-size: 100% 100%, 100% 100%, 100% 100%, 100% 100%, 100% 100%;
  background-position: 0% 0%, 0% 0%, 0% 0%, 0% 0%, 0% 0%;
  opacity: var(--photo-head-overlay-opacity, 1);
}
/* Image dans un pseudo pour pouvoir appliquer transform:scale (zoom) +
   parallax via translateY indépendant. */
.photo-section__head::before {
  content: "";
  position: absolute;
  /* Débordement vertical = amplitude parallax + marge (cf. .portfolio__head::before).
     Photo translate ±220px (MAX_TRAVEL) → fallback 220px du var suffit. */
  top: calc(-1 * (var(--head-parallax-travel, 220px) + 24px));
  bottom: calc(-1 * (var(--head-parallax-travel, 220px) + 24px));
  left: 0;
  right: 0;
  z-index: -1;
  background-image: var(--photo-head-bg, url("assets/photo-studio-bg.webp"));
  background-repeat: no-repeat;
  background-size: cover;
  background-position: var(--photo-head-focal, 50% 55%);
  transform: translate3d(0, var(--parallax-y, 0px), 0) scale(var(--photo-head-zoom, 1));
  transform-origin: var(--photo-head-focal, 50% 50%);
  will-change: transform;
}

@media (prefers-reduced-motion: reduce) {
  .photo-section__head { --parallax-y: 0px !important; }
}

/* Light-palette variant — re-tint the side fades with the light bg */
body.palette-light .photo-section__head {
  background:
    linear-gradient(
      to right,
      var(--bg) 0%,
      rgba(242, 239, 232, 0) 22%,
      rgba(242, 239, 232, 0) 78%,
      var(--bg) 100%
    ),
    linear-gradient(
      to bottom,
      rgba(242, 239, 232, 0.20) 0%,
      rgba(242, 239, 232, 0.55) 60%,
      var(--bg) 100%
    ),
    url("assets/photo-studio-bg.webp");
  background-repeat: no-repeat, no-repeat, no-repeat;
  background-size: 100% 100%, 100% 100%, cover;
  background-position:
    0% 0%,
    0% 0%,
    50% calc(55% + var(--parallax-y, 0px));
}
.photo-section__num {
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--ink-mute);
  justify-self: start;
  grid-column: 1 / -1;   /* rangée à part, au-dessus du titre */
}
.photo-section__title {
  font-family: var(--display);
  font-size: clamp(40px, 6vw, 88px);
  line-height: 0.9;
  letter-spacing: -0.025em;
  text-transform: uppercase;
  margin: 0;
  text-align: left;
}
.photo-section__title em {
  font-family: "Playfair Display", "Times New Roman", Georgia, serif;
  font-style: italic;
  font-weight: 400;
  text-transform: none;
  color: #60A5FA;
  letter-spacing: -0.01em;
  padding: 0 0.04em;
}
.photo-section__tag {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-soft);
  text-align: right;
  white-space: nowrap;
  justify-self: end;
}

.photo-section__intro {
  max-width: 720px;
  font-size: 16px;
  line-height: 1.65;
  color: var(--ink-soft);
  margin: 0 0 64px;
}

/* Grille 3 colonnes avec subgrid : les 3 .photo-cat partagent les mêmes
   lignes (head puis grille images) — du coup le sous-titre de
   PORTRAIT/PLATEAU/SCÈNE peut faire 1 ou 2 lignes sans déphaser
   verticalement les galeries. La row "auto" prend la hauteur du head
   le plus haut, ce qui aligne mécaniquement les 3 grilles. */
.photo-cats {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  grid-template-rows: auto 1fr;
  column-gap: 48px;
  row-gap: 16px;
}
.photo-cat {
  display: grid;
  grid-template-rows: subgrid;
  grid-row: span 2;
}
/* Fallback navigateurs sans subgrid : on impose une hauteur minimale au
   head pour garder un semblant d'alignement (~2 lignes de sous-titre). */
@supports not (grid-template-rows: subgrid) {
  .photo-cats { grid-template-rows: none; }
  .photo-cat { display: flex; flex-direction: column; }
  .photo-cat__head { min-height: 64px; }
}

.photo-cat__head {
  padding-bottom: 12px;
  border-bottom: 1px solid var(--line);
  /* Aligne le contenu en haut du head : si la cellule est étirée à la
     hauteur de la plus grande, le titre + sous-titre restent groupés
     en haut avec la bordure au pied de la cellule. */
  align-self: stretch;
  display: flex;
  flex-direction: column;
  justify-content: flex-start;
}
.photo-cat__title {
  font-family: var(--display);
  font-size: clamp(18px, 1.4vw, 22px);
  letter-spacing: 0.16em;
  text-transform: uppercase;
  margin: 0 0 6px;
}
.photo-cat__sub {
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: 0.12em;
  text-transform: uppercase;
  color: var(--ink-mute);
  margin: 0;
  line-height: 1.5;
}

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

/* ── Tiroir "voir plus" des galeries ─────────────────────────────────
   Seules les 2 premières photos de chaque galerie sont visibles ; le
   reste se déroule via le bouton flèche (desktop + mobile). Animation
   par grid-template-rows 0fr → 1fr (pas de max-height magique). */
.photo-cat__body {
  display: flex;
  flex-direction: column;
  min-width: 0;
}
.photo-cat__more {
  display: grid;
  grid-template-rows: 0fr;     /* fermé : hauteur 0 */
  visibility: hidden;          /* tuiles non focusables quand fermé */
  transition:
    grid-template-rows .5s cubic-bezier(.16, 1, .3, 1),
    visibility 0s .5s;
}
.photo-cat__more--open {
  grid-template-rows: 1fr;
  visibility: visible;
  transition:
    grid-template-rows .5s cubic-bezier(.16, 1, .3, 1),
    visibility 0s 0s;
}
.photo-cat__more-inner {
  overflow: hidden;
  min-height: 0;
}
.photo-cat__grid--more {
  padding-top: 4px;            /* = gap de la grille, continuité visuelle */
}
.photo-cat__toggle {
  margin-top: 10px;
  min-height: 44px;            /* cible tactile mobile */
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  width: 100%;
  background: transparent;
  border: 1px solid var(--line);
  color: var(--ink-mute);
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: 0.16em;
  text-transform: uppercase;
  cursor: pointer;
  transition: color .25s ease, border-color .25s ease;
}
.photo-cat__toggle:hover,
.photo-cat__toggle:focus-visible {
  color: var(--accent);
  border-color: rgba(var(--accent-rgb), 0.5);
}
.photo-cat__toggle:focus-visible {
  outline: 1px solid rgba(var(--accent-rgb), 0.6);
  outline-offset: 3px;
}
.photo-cat__toggle-chev {
  width: 14px;
  height: 14px;
  transition: transform .35s cubic-bezier(.16, 1, .3, 1);
}
.photo-cat__toggle[aria-expanded="true"] .photo-cat__toggle-chev {
  transform: rotate(180deg);
}
@media (prefers-reduced-motion: reduce) {
  .photo-cat__more,
  .photo-cat__more--open,
  .photo-cat__toggle-chev { transition: none; }
}

.photo-tile {
  position: relative;
  display: block;
  aspect-ratio: 4 / 5;
  overflow: hidden;
  background: #0a0a0c;
  border: 0;
  padding: 0;
  cursor: pointer;
  outline: 0;
}
.photo-tile img {
  /* Débord vertical (height 116%, top -8%) : l'image est plus haute que
     son cadre, ce qui donne la marge nécessaire pour une parallaxe BIEN
     visible sans jamais recadrer ni révéler les bords. --ptile-y est
     pilotée par parallax-media.js au scroll ; --ptile-s gère le zoom au
     survol. Les deux sont composées dans un seul transform pour ne jamais
     se marcher dessus. */
  position: absolute;
  top: -8%;
  left: 0;
  right: 0;
  width: 100%;
  height: 116%;
  object-fit: cover;
  display: block;
  --ptile-y: 0px;
  --ptile-s: 1;
  filter: contrast(1.05);
  transform: translate3d(0, var(--ptile-y), 0) scale(var(--ptile-s));
  /* Transition courte = suivi net du scroll avec juste assez de lissage
     pour gommer le micro-jitter (pas de "rubber-band" qui chasse). */
  transition:
    transform .18s linear,
    filter .45s ease;
  will-change: transform;
}
.photo-tile:hover img,
.photo-tile:focus-visible img {
  --ptile-s: 1.05;
  filter: contrast(1.06) saturate(1.06) brightness(1.04);
}
@media (prefers-reduced-motion: reduce) {
  .photo-tile img { --ptile-y: 0px !important; }
}
.photo-tile__cap {
  position: absolute;
  left: 0; right: 0; bottom: 0;
  padding: 18px 12px 10px;
  font-family: var(--mono);
  font-size: 10.5px;
  letter-spacing: 0.1em;
  text-transform: uppercase;
  color: #f4ede0;
  background: linear-gradient(180deg, transparent 0%, rgba(0,0,0,0.78) 100%);
  opacity: 0;
  transform: translateY(4px);
  transition: opacity .25s ease, transform .25s ease;
  text-align: left;
  pointer-events: none;
}
.photo-tile:hover .photo-tile__cap,
.photo-tile:focus-visible .photo-tile__cap { opacity: 1; transform: translateY(0); }

.photo-tile--placeholder {
  display: flex;
  align-items: flex-end;
  justify-content: flex-start;
  padding: 10px;
  cursor: default;
}
.photo-tile__pm {
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: rgba(238, 234, 224, 0.45);
}

.photo-section__cta {
  margin-top: 64px;
  display: flex;
  justify-content: flex-end;
}
.photo-cta {
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.22em;
  text-transform: uppercase;
  color: var(--ink);
  border: 1px solid var(--line-str);
  padding: 16px 28px;
  display: inline-flex;
  align-items: center;
  gap: 12px;
  transition: color .2s, border-color .2s, transform .2s, background .2s;
}
.photo-cta:hover {
  color: #fff;
  background: #60A5FA;
  border-color: #60A5FA;
  transform: translateX(4px);
}

/* ---------- Lightbox ---------- */
.photo-lightbox {
  position: fixed;
  inset: 0;
  z-index: var(--z-modal-lightbox);  /* 1100 — lightbox au-dessus modales */
  background: var(--glass-noise-soft) var(--glass-scrim);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  display: flex;
  align-items: center;
  justify-content: center;
  animation: pl-fade-in .2s ease both;
  cursor: zoom-out;
}
@keyframes pl-fade-in { from { opacity: 0; } to { opacity: 1; } }
.photo-lightbox__inner {
  position: relative;
  max-width: min(92vw, 1400px);
  max-height: 88vh;
  cursor: default;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 14px;
}
.photo-lightbox__inner img {
  display: block;
  max-width: 100%;
  max-height: 82vh;
  object-fit: contain;
  box-shadow: 0 0 80px rgba(96, 165, 250, 0.15);
}
.photo-lightbox__caption {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-soft);
}
.photo-lightbox__count {
  position: absolute;
  bottom: -34px;
  right: 0;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.18em;
  color: var(--ink-mute);
}
.photo-lightbox__close,
.photo-lightbox__nav {
  position: fixed;
  background: var(--glass-sheen), var(--glass-chip);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  border: 1px solid var(--glass-line);
  box-shadow: var(--glass-highlight);
  color: #f4ede0;
  font-family: var(--display);
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  transition: background .15s, border-color .15s, transform .15s;
}
.photo-lightbox__close:hover,
.photo-lightbox__nav:hover {
  background: rgba(96, 165, 250, 0.16);
  border-color: #60A5FA;
}
.photo-lightbox__close {
  top: 22px; right: 22px;
  width: 44px; height: 44px;
  font-size: 26px;
  line-height: 1;
}
.photo-lightbox__nav {
  top: 50%;
  transform: translateY(-50%);
  width: 54px; height: 54px;
  font-size: 36px;
  line-height: 1;
}
.photo-lightbox__nav--prev { left: 22px; }
.photo-lightbox__nav--next { right: 22px; }
.photo-lightbox__nav:hover { transform: translateY(-50%) scale(1.06); }

/* ---------- Responsive ---------- */
@media (max-width: 1080px) {
  .photo-cats {
    grid-template-columns: 1fr;
    /* Garde le row-gap "interne" (head ↔ grille) à 16px, et augmente
       seulement la séparation visuelle entre 2 catégories empilées. */
    row-gap: 16px;
  }
  /* Espace entre 2 .photo-cat sur la pile mobile/tablette */
  .photo-cat + .photo-cat { margin-top: 40px; }
  .photo-cat__grid { grid-template-columns: repeat(3, minmax(0, 1fr)); }
}
/* Tablette / laptop / desktop standard : la grille 3 cols (num · title · tag)
   ne tient pas en dessous de ~1500px parce que le titre "L'œil photographique"
   à 6vw pousse la colonne auto plus large que le conteneur, ce qui projette
   le tag "Portrait · Plateau · Scène" sous la zone du menu latéral (PLATEAU
   disparait). Stack en 1 colonne jusqu'au breakpoint mobile existant.
   En passant à 1 colonne, le titre passe aussi en align:left pour éviter
   qu'un texte plus large que la cellule (grid-template-columns: 1fr avec
   text-align: center par défaut) déborde visuellement sur la gauche. */
@media (max-width: 1500px) and (min-width: 641px) {
  .photo-section__head { grid-template-columns: 1fr; gap: 14px; }
  .photo-section__title { text-align: left; }
  .photo-section__tag { text-align: left; }
}

@media (max-width: 640px) {
  .photo-section__head { grid-template-columns: 1fr; gap: 18px; }
  .photo-section__title { text-align: left; }
  .photo-section__tag { text-align: left; }
  .photo-cat__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .photo-lightbox__nav { width: 44px; height: 44px; font-size: 28px; }
}

/* ====================================================================
   STUDIO PHONOGRAPHIQUE — le pôle son
   --------------------------------------------------------------------
   Section sœur de .photo-section, placée juste en dessous. Head sans
   image de fond (sobre, distinct du head photo) + petite galerie de
   tuiles qui réutilise .photo-tile / .photo-lightbox.
   ==================================================================== */
.studio-section {
  padding: var(--section-y) var(--pad-x);
  background: var(--bg-elev);
  position: relative;
}
.studio-section__head {
  position: relative;
  display: grid;
  grid-template-columns: 1fr auto;
  gap: 14px 32px;
  align-items: end;
  margin-bottom: clamp(36px, 5vw, 64px);
  padding-bottom: clamp(28px, 4vw, 44px);
  border-bottom: 1px solid var(--line);
}
.studio-section__num {
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--ink-mute);
  justify-self: start;
  grid-column: 1 / -1;
}
.studio-section__title {
  font-family: var(--display);
  font-size: clamp(40px, 6vw, 88px);
  line-height: 0.9;
  letter-spacing: -0.025em;
  text-transform: uppercase;
  margin: 0;
  text-align: left;
}
.studio-section__title em {
  font-family: "Playfair Display", "Times New Roman", Georgia, serif;
  font-style: italic;
  font-weight: 400;
  text-transform: none;
  color: #60A5FA;
  letter-spacing: -0.01em;
  padding: 0 0.04em;
}
.studio-section__tag {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-soft);
  text-align: right;
  white-space: nowrap;
  justify-self: end;
}
.studio-section__intro {
  max-width: 720px;
  font-size: 16px;
  line-height: 1.65;
  color: var(--ink-soft);
  margin: 0 0 clamp(40px, 5vw, 56px);
}
.studio-gallery {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: 4px;
}
/* Grille du tiroir "Dérouler" : même gabarit, padding-top = gap pour la
   continuité visuelle avec les 3 photos déjà visibles au-dessus. */
.studio-gallery--more { padding-top: 4px; }
.studio-toggle { margin-top: 14px; }
/* Studio Son : cadres PAYSAGE (le .photo-tile partagé est en 4:5 portrait,
   trop haut ici). object-fit:cover + focal (image_meta) gèrent le cadrage. */
.studio-gallery .photo-tile { aspect-ratio: 3 / 2; }
@media (max-width: 1500px) and (min-width: 641px) {
  .studio-section__head { grid-template-columns: 1fr; gap: 14px; }
  .studio-section__title,
  .studio-section__tag { text-align: left; justify-self: start; }
}
@media (max-width: 640px) {
  .studio-section__head { grid-template-columns: 1fr; gap: 18px; }
  .studio-section__title,
  .studio-section__tag { text-align: left; justify-self: start; }
  /* Les 3 photos restent sur UNE seule ligne, même en mobile (bandeau). */
  .studio-gallery { grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 3px; }
}

/* ====================================================================
   OUTIL D'ÉCOUTE — extraits sonores + forme d'onde (transparent)
   ==================================================================== */
.son-player { margin-top: clamp(30px, 4vw, 52px); background: transparent; }
.son-player__wave {
  display: block; width: 100%; height: 84px; margin-bottom: 6px;
}
.son-player__list { list-style: none; margin: 0; padding: 0; }
.son-track {
  display: grid;
  /* play | titre+crédits | photo (à droite) — plus de séparateurs */
  grid-template-columns: 46px 1fr 56px;
  align-items: center;
  gap: 16px;
  padding: 16px 0;
}
/* Trait qui se dessine au survol, UNIQUEMENT sous le titre survolé
   (même animation que les collaborateurs), là où étaient les séparateurs. */
.son-track__line {
  display: block; height: 1px; margin-top: 10px;
  background: var(--accent); opacity: 0.9;
  transform: scaleX(0); transform-origin: left center;
  transition: transform .5s cubic-bezier(.22,1,.36,1), opacity .35s ease;
}
.son-track:hover .son-track__line,
.son-track.is-active .son-track__line { transform: scaleX(1); opacity: 1; }
.son-track__img {
  width: 56px; height: 56px; border-radius: 8px; flex: none;
  background-size: cover; background-position: center;
  background-color: rgba(255,255,255,0.05);
  border: 1px solid rgba(255,255,255,0.12);
  display: flex; align-items: center; justify-content: center; overflow: hidden;
  transition: transform .4s cubic-bezier(.22,1,.36,1), border-color .3s;
}
.son-track:hover .son-track__img { transform: scale(1.06); border-color: rgba(var(--accent-rgb), 0.6); }
.son-track__img--btn {
  padding: 0; cursor: zoom-in;
  -webkit-appearance: none; appearance: none;  /* iOS masque sinon l'image de fond */
}
.son-track__img-ph { font-size: 22px; color: var(--accent); opacity: 0.85; }
.son-track__btn {
  width: 46px; height: 46px; border-radius: 50%;
  border: 1px solid rgba(255,255,255,0.28); background: transparent; color: var(--ink);
  display: flex; align-items: center; justify-content: center; cursor: pointer;
  transition: border-color .25s, background .25s, color .25s;
}
.son-track__btn svg { width: 20px; height: 20px; fill: currentColor; }
.son-track__spin {
  width: 18px; height: 18px; border-radius: 50%;
  border: 2px solid rgba(var(--accent-rgb), 0.25);
  border-top-color: var(--accent);
  animation: sonSpin .7s linear infinite;
}
@keyframes sonSpin { to { transform: rotate(360deg); } }
.son-track__btn:hover { border-color: var(--accent); color: var(--accent); }
.son-track.is-active .son-track__btn { border-color: var(--accent); color: var(--accent); background: rgba(var(--accent-rgb), 0.08); }
.son-track__meta { min-width: 0; }
.son-track__title { font-family: var(--display); font-size: clamp(16px, 2vw, 22px); text-transform: uppercase; letter-spacing: -0.01em; line-height: 1.1; color: var(--ink); transition: color .3s ease; white-space: nowrap; }
.son-track:hover .son-track__title,
.son-track.is-active .son-track__title { color: var(--accent); }
/* Crédits masqués par défaut, révélés au survol (l'espace est réservé → pas de saut) */
.son-track__credit {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.04em; color: var(--ink-soft);
  margin-top: 5px; line-height: 1.45;
  opacity: 0; transition: opacity .35s ease;
}
.son-track:hover .son-track__credit,
.son-track.is-active .son-track__credit { opacity: 1; }
@media (max-width: 640px) {
  .son-track { grid-template-columns: 40px 1fr 44px; gap: 12px; padding: 14px 0; }
  .son-track__img { width: 44px; height: 44px; }
  .son-track__btn { width: 40px; height: 40px; }
  .son-track__btn svg { width: 17px; height: 17px; }
  .son-track__credit { font-size: 10px; }
  .son-track__title { white-space: normal; }   /* titres longs peuvent passer à la ligne */
}
/* Tactile (pas de survol) : crédits toujours visibles. Le trait ne
   s'affiche que sous la piste active (celle qu'on écoute). */
@media (hover: none) {
  .son-track__credit { opacity: 1; }
}

/* ====================================================================
   TEAM
   ==================================================================== */
.team { padding: var(--section-y) var(--pad-x); background: var(--bg-elev); }
/* Collaborateurs suit immédiatement Team → on resserre le bas de Team
   pour rapprocher les deux blocs (demande "réduire l'espace"). */
.team { padding-bottom: clamp(28px, 4.5vw, 60px); }
/* La place du menu latéral est DÉJÀ réservée par body.menu-active
   (padding-right sur le <body>). On ne rajoute donc AUCUNE marge sur la
   grille (l'ancienne marge faisait doublon → grand vide à droite). La
   grille remplit la largeur dispo et se centre sur très grand écran. */
.team__grid {
  display: grid;
  /* Une seule ligne, tous les membres visibles, taille auto-adaptative —
     pas de scroll horizontal, les cards se resserrent à mesure que les
     membres s'ajoutent.
     minmax(0, 1fr) et PAS 1fr seul : 1fr ne descend pas sous la largeur
     min du contenu (noms longs) → colonnes inégales → portraits de
     tailles différentes. minmax(0,…) force des colonnes strictement
     égales, donc des photos toutes identiques (ratio 4:5 commun). */
  grid-auto-flow: column;
  grid-auto-columns: minmax(0, 1fr);
  gap: 2px;
  /* Grille centrée : remplit l'espace dispo et se centre sur très grand
     écran (au-delà de max-width). */
  max-width: 1200px;
  margin-inline: auto;
}
.team-card {
  background: var(--bg);
  padding: 40px 28px;
  display: flex; flex-direction: column; gap: 18px;
  position: relative;
  /* Conteneur de requête : la taille du nom suit la largeur réelle de la
     carte (cf. .team-card__name) — les colonnes étant désormais
     strictement égales, c'est la typo qui s'adapte, pas la colonne. */
  container-type: inline-size;
}
.team-card__portrait {
  aspect-ratio: 4 / 5;
  background: linear-gradient(135deg, #2a2a2c 0%, #1a1a1c 60%, #0a0a0a 100%);
  position: relative;
  overflow: hidden;
}
.team-card__portrait::after {
  content: var(--initials, "BM");
  position: absolute; inset: 0;
  display: flex; align-items: center; justify-content: center;
  font-family: var(--display);
  font-size: clamp(80px, 12vw, 160px);
  color: rgba(238, 234, 224, 0.08);
  letter-spacing: -0.04em;
}
/* Halo accent : UNIQUEMENT sur les vignettes placeholder (initiales) —
   sur une vraie photo N&B il créait une teinte bleutée parasite. */
.team-card__portrait::before {
  content: ""; position: absolute; inset: 0;
  background: radial-gradient(circle at 50% 38%, rgba(var(--accent-rgb), 0.18) 0%, transparent 60%);
}
.team-card__portrait--photo::before { content: none; }
.team-card__name {
  font-family: var(--display);
  /* cqw = % de la CONTENT-box de la carte (largeur moins padding) : un
     nom long (MARCHAND) tient toujours dans sa colonne, quel que soit
     le nombre de membres ou l'état du menu latéral. */
  font-size: clamp(15px, 11.8cqw, 40px);
  text-transform: uppercase;
  letter-spacing: -0.02em;
  overflow-wrap: break-word;
}
.team-card__role { font-family: var(--mono); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase; color: var(--accent); }
.team-card__bio  { font-size: 14px; color: var(--ink-soft); line-height: 1.6; }
.team-card__ig {
  display: inline-block; margin-top: 8px;
  font-family: var(--mono); font-size: 12px; letter-spacing: 0.08em;
  color: var(--accent);
}

/* Reset button styles pour les team-card (elles sont des <button> cliquables) */
button.team-card {
  appearance: none;
  border: 0;
  background: var(--bg);
  text-align: center;
  cursor: pointer;
  font: inherit;
  color: inherit;
  transition: background .25s ease;
  width: 100%;
}
button.team-card:hover { background: rgba(255,255,255,0.04); }
button.team-card:focus-visible { outline: 2px solid var(--accent); outline-offset: -2px; }

/* ====================================================================
   TEAM MODAL — popup détaillé au clic sur une card
   ==================================================================== */
.team-modal {
  position: fixed;
  inset: 0;
  background: var(--glass-noise-soft) var(--glass-scrim);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  z-index: var(--z-modal);  /* 1000 */
  display: flex;
  align-items: center;
  justify-content: center;
  padding: clamp(20px, 4vw, 60px);
  animation: team-modal-fade-in .2s ease-out;
}
@keyframes team-modal-fade-in {
  from { opacity: 0; }
  to   { opacity: 1; }
}
.team-modal__box {
  position: relative;
  display: grid;
  grid-template-columns: minmax(0, 1fr) minmax(0, 1.1fr);
  gap: clamp(24px, 3vw, 56px);
  align-items: stretch;
  width: 100%;
  max-width: 1100px;
  max-height: calc(100vh - clamp(40px, 8vw, 120px));
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: 4px;
  padding: clamp(24px, 3vw, 48px);
  animation: team-modal-rise .35s cubic-bezier(.16, 1, .3, 1);
}
@keyframes team-modal-rise {
  from { transform: translateY(20px); opacity: 0; }
  to   { transform: translateY(0); opacity: 1; }
}
.team-modal__close {
  position: absolute;
  top: 14px;
  right: 14px;
  appearance: none;
  border: 1px solid var(--line);
  background: transparent;
  color: var(--ink);
  width: 38px;
  height: 38px;
  border-radius: 50%;
  font-size: 22px;
  line-height: 1;
  cursor: pointer;
  transition: border-color .15s, color .15s, background .15s;
  z-index: 2;
}
.team-modal__close:hover {
  border-color: var(--accent);
  color: var(--accent);
  background: rgba(255,255,255,0.05);
}
.team-modal__portrait {
  position: relative;
  aspect-ratio: 4 / 5;
  background: linear-gradient(135deg, #2a2a2c 0%, #1a1a1c 60%, #0a0a0a 100%);
  background-repeat: no-repeat;
  overflow: hidden;
  border-radius: 2px;
  min-height: 0;
}
.team-modal__portrait::after {
  content: var(--initials, "");
  position: absolute;
  inset: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: var(--display);
  font-size: clamp(80px, 14vw, 180px);
  color: rgba(255,255,255,0.08);
  letter-spacing: -0.02em;
}
.team-modal__info {
  display: flex;
  flex-direction: column;
  gap: 18px;
  overflow-y: auto;
  padding-right: 8px;
}
.team-modal__role {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--accent);
}
.team-modal__name {
  font-family: var(--display);
  font-size: clamp(36px, 5vw, 64px);
  text-transform: uppercase;
  line-height: 0.95;
  letter-spacing: -0.02em;
  color: var(--ink);
  margin: 0;
}
.team-modal__bio {
  font-size: 16px;
  line-height: 1.65;
  color: var(--ink-soft);
  white-space: pre-line;
}
.team-modal__ig {
  display: inline-flex; align-items: center; gap: 8px;
  margin-top: 20px;
  font-family: var(--mono); font-size: 14px; letter-spacing: 0.05em;
  color: var(--accent); text-decoration: none;
  transition: opacity .2s;
}
.team-modal__ig:hover { opacity: 0.7; }
.team-modal__ig-icon { font-size: 17px; line-height: 1; }

@media (max-width: 720px) {
  .team-modal__box {
    grid-template-columns: 1fr;
    gap: 18px;
    padding: 18px;
  }
  .team-modal__portrait {
    aspect-ratio: 4 / 3;
  }
  .team-modal__name { font-size: clamp(28px, 8vw, 44px); }
}

/* ====================================================================
   PROJECT MODAL — popup détaillé au clic sur une card du portfolio
   ==================================================================== */
.project-modal {
  position: fixed;
  inset: 0;
  background: var(--glass-noise-soft) var(--glass-scrim);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  z-index: var(--z-modal);  /* 1000 */
  display: flex;
  align-items: flex-start;
  justify-content: center;
  padding: clamp(20px, 4vw, 60px);
  overflow-y: auto;
  animation: project-modal-fade .25s ease-out;
}
@keyframes project-modal-fade {
  from { opacity: 0; }
  to   { opacity: 1; }
}
.project-modal__box {
  position: relative;
  width: 100%;
  max-width: 1100px;
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: 4px;
  overflow: hidden;
  animation: project-modal-rise .35s cubic-bezier(.16, 1, .3, 1);
  margin: auto;
}
@keyframes project-modal-rise {
  from { transform: translateY(24px); opacity: 0; }
  to   { transform: translateY(0); opacity: 1; }
}
.project-modal__close {
  position: absolute;
  top: 16px;
  right: 16px;
  appearance: none;
  border: 1px solid var(--glass-line);
  background: var(--glass-sheen), var(--glass-chip);
  box-shadow: var(--glass-highlight);
  color: var(--ink);
  width: 40px;
  height: 40px;
  border-radius: 50%;
  font-size: 24px;
  line-height: 1;
  cursor: pointer;
  z-index: 5;
  transition: all .15s;
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
}
.project-modal__close:hover {
  border-color: var(--accent);
  color: var(--accent);
}
.project-modal__media {
  position: relative;
  width: 100%;
  aspect-ratio: 16 / 9;
  background: #000;
  border-bottom: 1px solid var(--line);
  overflow: hidden;  /* clippe la couche image zoomée (cadrage) */
}
.project-modal__info {
  padding: clamp(24px, 4vw, 48px) clamp(20px, 4vw, 48px);
}
.project-modal__meta {
  display: flex;
  flex-wrap: wrap;
  gap: 14px;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--ink-mute);
  margin-bottom: 16px;
}
.project-modal__meta > span:not(:last-child)::after {
  content: " ·";
  margin-left: 6px;
  color: var(--ink-mute);
}
.project-modal__title {
  font-family: var(--display);
  font-size: clamp(36px, 5vw, 64px);
  text-transform: uppercase;
  line-height: 0.95;
  letter-spacing: -0.02em;
  margin: 0 0 22px;
  color: var(--ink);
}
.project-modal__desc {
  font-size: 16px;
  line-height: 1.7;
  color: var(--ink-soft);
  max-width: 720px;
  white-space: pre-line;
}
.project-modal__vimeo-link {
  display: inline-block;
  margin-top: 18px;
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--accent);
  text-decoration: none;
  border-bottom: 1px solid currentColor;
  padding-bottom: 2px;
}
.project-modal__vimeo-link:hover { opacity: 0.7; }
.project-modal__gallery {
  padding: 0 clamp(20px, 4vw, 48px) clamp(24px, 4vw, 48px);
  border-top: 1px solid var(--line);
  padding-top: clamp(24px, 4vw, 48px);
}
.project-modal__gallery-label {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--ink-mute);
  margin-bottom: 14px;
}
.project-modal__gallery-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(180px, 1fr));
  gap: 8px;
}
.project-modal__gallery-item {
  display: block;
  aspect-ratio: 4 / 3;
  background-color: #0a0a0a;
  border: 1px solid var(--line);
  border-radius: 2px;
  transition: transform .2s ease, border-color .15s;
  cursor: zoom-in;
  /* Reset des styles button */
  appearance: none;
  padding: 0;
  font: inherit;
  color: inherit;
  width: 100%;
}
.project-modal__gallery-item:hover {
  border-color: var(--accent);
  transform: scale(1.015);
}
.project-modal__gallery-item:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 2px;
}

@media (max-width: 720px) {
  .project-modal { padding: 0; align-items: stretch; }
  .project-modal__box { border-radius: 0; min-height: 100vh; }
  .project-modal__title { font-size: clamp(28px, 8vw, 44px); }
}

/* ====================================================================
   PROJECT LIGHTBOX — plein écran pour les images de la galerie
   ==================================================================== */
.project-lightbox {
  position: fixed;
  inset: 0;
  background: var(--glass-noise-soft) var(--glass-scrim);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  z-index: var(--z-modal-lightbox);  /* 1100 — au-dessus de la modale projet (1000) */
  display: flex;
  align-items: center;
  justify-content: center;
  padding: clamp(40px, 6vw, 80px) clamp(60px, 8vw, 120px);
  animation: project-modal-fade .2s ease-out;
  cursor: zoom-out;
}
.project-lightbox__img {
  max-width: 100%;
  max-height: 100%;
  width: auto;
  height: auto;
  display: block;
  object-fit: contain;
  border-radius: 2px;
  box-shadow: 0 8px 40px rgba(0, 0, 0, 0.5);
  cursor: default;
}
.project-lightbox__close {
  position: absolute;
  top: 20px;
  right: 20px;
  appearance: none;
  border: 1px solid var(--glass-line);
  background: var(--glass-sheen), var(--glass-chip);
  box-shadow: var(--glass-highlight);
  color: #fff;
  width: 44px;
  height: 44px;
  border-radius: 50%;
  font-size: 26px;
  line-height: 1;
  cursor: pointer;
  z-index: 2;
  transition: all .15s;
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
}
.project-lightbox__close:hover {
  border-color: var(--accent);
  color: var(--accent);
}
.project-lightbox__nav {
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
  appearance: none;
  border: 1px solid var(--glass-line);
  background: var(--glass-sheen), var(--glass-chip);
  box-shadow: var(--glass-highlight);
  color: #fff;
  width: 52px;
  height: 52px;
  border-radius: 50%;
  font-size: 32px;
  line-height: 1;
  cursor: pointer;
  z-index: 2;
  transition: all .15s;
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  display: flex;
  align-items: center;
  justify-content: center;
  padding: 0;
}
.project-lightbox__nav:hover {
  border-color: var(--accent);
  color: var(--accent);
}
.project-lightbox__nav--prev { left: 20px; }
.project-lightbox__nav--next { right: 20px; }
.project-lightbox__counter {
  position: absolute;
  bottom: 24px;
  left: 50%;
  transform: translateX(-50%);
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.2em;
  color: rgba(255,255,255,0.7);
  background: var(--glass-sheen), var(--glass-chip);
  border: 1px solid var(--glass-line);
  box-shadow: var(--glass-highlight);
  padding: 6px 14px;
  border-radius: 999px;
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
}

@media (max-width: 720px) {
  .project-lightbox { padding: 60px 12px; }
  .project-lightbox__nav {
    width: 42px;
    height: 42px;
    font-size: 26px;
  }
  .project-lightbox__nav--prev { left: 10px; }
  .project-lightbox__nav--next { right: 10px; }
}

/* ====================================================================
   COLLABORATORS — petite liste compacte sous Team
   ==================================================================== */
.collabs {
  /* Espace réduit avec la section Team juste au-dessus (padding-top minimal) */
  padding: clamp(8px, 1.6vw, 22px) var(--pad-x) clamp(52px, 8vw, 104px);
  background: var(--bg-elev);
}
.collabs__head {
  margin-bottom: 28px;
  display: flex;
  align-items: flex-end;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 18px;
}
.collabs__label {
  font-family: var(--mono);
  font-size: 14px;
  letter-spacing: 0.2em;
  text-transform: uppercase;
  color: var(--ink-mute);
}
/* "collaborateurs" en italique bleu — encore +70% (24 → 41px) */
.collabs__label .italic-serif {
  font-size: 41px;
  line-height: 1;
  letter-spacing: 0;
  text-transform: none;
  color: var(--accent);
  vertical-align: middle;
  margin-left: 8px;
}
.collabs__list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(364px, 1fr));
  gap: 13px 36px;
}
.collabs__item {
  display: grid;
  /* avatar | infos | trait extensible | handle */
  grid-template-columns: auto minmax(0, auto) 1fr auto;
  align-items: center;
  gap: 18px;
  padding: 10px 0;
}
/* Trait qui se dessine entre le nom et l'Instagram au survol (style Obvious) */
.collabs__line {
  height: 1px;
  align-self: center;
  background: var(--line);
  opacity: 0.45;
  transform: scaleX(0);
  transform-origin: left center;
  transition: transform .5s cubic-bezier(.22,1,.36,1),
              background-color .35s ease,
              opacity .35s ease;
}
.collabs__item:hover .collabs__line,
.collabs__item:focus-within .collabs__line {
  transform: scaleX(1);
  background: var(--accent);
  opacity: 1;
}
.collabs__avatar {
  width: 47px; height: 47px;
  border-radius: 50%;
  object-fit: cover;
  border: 1px solid var(--line);
  background: rgba(255,255,255,0.04);
}
/* Variant wrapper rond pour permettre transform:scale (zoom focal picker)
   sans laisser l'image déborder du cercle. */
.collabs__avatar--wrap {
  display: block;
  overflow: hidden;
  position: relative;
  padding: 0;
  flex: none;
}
.collabs__avatar--wrap > img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}
.collabs__avatar--initials {
  display: flex; align-items: center; justify-content: center;
  font-family: var(--mono);
  font-size: 14px;
  letter-spacing: 0.05em;
  color: var(--ink-soft);
}
.collabs__info { min-width: 0; }
.collabs__name {
  font-family: var(--body);
  font-weight: 500;
  font-size: 18px;
  color: var(--ink);
  line-height: 1.2;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  transition: color .3s ease;
}
.collabs__item:hover .collabs__name,
.collabs__item:focus-within .collabs__name { color: var(--accent); }
.collabs__role {
  font-family: var(--mono);
  font-size: 13px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-mute);
  margin-top: 4px;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
}
.collabs__handle {
  font-family: var(--mono);
  font-size: 16px;
  color: var(--accent);
  white-space: nowrap;
  opacity: 0.78;
  transition: opacity .3s ease, transform .5s cubic-bezier(.22,1,.36,1);
}
.collabs__item:hover .collabs__handle,
.collabs__item:focus-within .collabs__handle {
  opacity: 1;
  transform: translateX(2px);
}
.collabs__handle:hover { opacity: 0.7; }
.collabs__handle--muted { color: var(--ink-mute); }

/* ── Filtre par métier ──────────────────────────────────────────── */
.collabs__filter { display: flex; align-items: center; gap: 10px; }
.collabs__filter-label {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.18em;
  text-transform: uppercase; color: var(--ink-mute);
}
.collabs__select-wrap { position: relative; display: inline-flex; align-items: center; }
.collabs__select {
  appearance: none; -webkit-appearance: none;
  font-family: var(--mono); font-size: 13px; letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--ink);
  background: rgba(255,255,255,0.04);
  border: 1px solid var(--line);
  border-radius: 4px;
  padding: 9px 34px 9px 14px;
  cursor: pointer;
  min-width: 220px;
  transition: border-color .25s, background .25s;
}
.collabs__select:hover { border-color: rgba(var(--accent-rgb), 0.6); }
.collabs__select:focus-visible { outline: none; border-color: var(--accent); }
.collabs__select option { background: var(--bg-elev); color: var(--ink); text-transform: none; }
.collabs__select-chevron {
  position: absolute; right: 12px; pointer-events: none;
  font-size: 14px; color: var(--accent);
}
/* Bandeau du filtre actif */
.collabs__active-filter {
  display: flex; align-items: center; gap: 12px; flex-wrap: wrap;
  margin: -8px 0 20px;
  font-family: var(--mono); font-size: 12px; letter-spacing: 0.06em;
  text-transform: uppercase; color: var(--ink-soft);
}
.collabs__active-filter strong { color: var(--accent); font-weight: 500; }
.collabs__clear {
  appearance: none; border: 1px solid var(--line); background: transparent;
  color: var(--ink-mute); font-family: var(--mono); font-size: 11px;
  letter-spacing: 0.1em; text-transform: uppercase;
  padding: 5px 10px; border-radius: 3px; cursor: pointer;
  transition: color .2s, border-color .2s;
}
.collabs__clear:hover { color: var(--accent); border-color: var(--accent); }
.collabs__empty {
  font-family: var(--mono); font-size: 13px; color: var(--ink-mute);
  padding: 8px 0 4px;
}

/* ── Repli à 2 lignes + tiroir ───────────────────────────────────── */
.collabs__list--collapsed {
  max-height: 150px;   /* ~2 lignes (desktop) */
  overflow: hidden;
  -webkit-mask-image: linear-gradient(to bottom, #000 78%, transparent 100%);
          mask-image: linear-gradient(to bottom, #000 78%, transparent 100%);
}
.collabs__toggle {
  appearance: none; background: transparent;
  border: 1px solid var(--line); border-radius: 4px;
  color: var(--ink); font-family: var(--mono); font-size: 12px;
  letter-spacing: 0.14em; text-transform: uppercase;
  padding: 11px 20px; margin-top: 22px; cursor: pointer;
  display: inline-flex; align-items: center; gap: 10px;
  transition: color .25s, border-color .25s, background .25s;
}
.collabs__toggle:hover { color: var(--accent); border-color: var(--accent); background: rgba(var(--accent-rgb), 0.06); }
.collabs__toggle-chevron { font-size: 15px; color: var(--accent); transition: transform .3s; display: inline-block; }
.collabs__toggle-chevron--up { transform: rotate(180deg); }

/* ====================================================================
   CLIENTS strip
   ==================================================================== */
.clients {
  padding: 48px var(--pad-x);
  display: flex;
  flex-direction: column;
  align-items: stretch;
  gap: 28px;
  overflow: hidden;
  /* Bandeau GRIS sur TOUTE la section (titre + marquee), fondu haut/bas pour
     se raccorder aux sections sombres voisines. Gris moyen → logos noirs ET
     blancs ressortent. */
  background: linear-gradient(180deg,
    rgba(150,152,158,0)    0%,
    rgba(150,152,158,0.6)  8%,
    rgba(150,152,158,0.6)  92%,
    rgba(150,152,158,0)    100%);
}
.clients__label {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase;
  color: rgba(0,0,0,0.55); line-height: 1.5;   /* lisible sur le gris */
  /* Centré pour mettre en valeur le titre au-dessus de la marquee */
  text-align: center;
}
/* Wrapper non-animé qui masque les bords de la marquee. Le mask reste fixe
   en viewport pendant que le strip translate à l'intérieur — les logos
   apparaissent en fondu à gauche et disparaissent à droite. */
.clients__viewport {
  position: relative;
  overflow: hidden;
  -webkit-mask-image: linear-gradient(
    to right,
    transparent 0%,
    #000 10%,
    #000 90%,
    transparent 100%
  );
          mask-image: linear-gradient(
    to right,
    transparent 0%,
    #000 10%,
    #000 90%,
    transparent 100%
  );
  /* Le fond gris est désormais porté par TOUTE la section .clients (voir plus
     haut) — le viewport ne garde que le fondu gauche/droite des logos. */
}
.clients__strip {
  display: flex; align-items: center;
  padding: 26px 0;   /* hauteur du bandeau gris autour des logos */
  /* width: max-content → le strip se dimensionne sur son CONTENU (les 8 copies),
     pas sur le viewport. Sinon `100%` = largeur viewport et translate(-100%/8)
     ne tombe PAS sur une copie entière → saut visible au reset. */
  width: max-content;
  /* PAS de gap : padding-right sur chaque item pour spacing parfaitement
     constant (sinon dernier item sans gap → saccade au loop). */
  animation: clients-carousel 40s linear infinite;
  white-space: nowrap;
  /* NB : pas de will-change/backface-visibility ici. Sur un layer très large
     (8 copies), iOS/Safari leur alloue une texture géante puis abandonne les
     tuiles éloignées du viewport → logos qui « disparaissent » en plein vol.
     L'animation translate3d compose déjà sur GPU sans ces hints. */
}
.clients__logo { padding-right: 56px; }
@keyframes clients-carousel {
  /* On translate d'exactement UNE série (1 / --clients-copies de la largeur du
     strip) → contenu pixel-identique à la position de départ = loop parfait.
     --clients-copies est posé en inline depuis components.jsx. */
  from { transform: translate3d(0, 0, 0); }
  to   { transform: translate3d(calc(-100% / var(--clients-copies, 6)), 0, 0); }
}
.clients__logo {
  font-family: var(--display); font-size: 26px;
  text-transform: uppercase; letter-spacing: -0.02em;
  color: var(--ink-soft); opacity: 0.55;
  transition: opacity .2s, color .2s, filter .25s;
  flex-shrink: 0;
}
.clients__logo:hover { opacity: 1; color: var(--ink); }
.clients__logo--italic {
  font-family: "Times New Roman", serif; font-style: italic; font-weight: 700; letter-spacing: -0.04em;
}
/* Logo image — hauteur fixe pour homogénéité. Le fond "verre" est porté par
   TOUTE la section (cf. .clients__viewport), pas par chaque logo. */
.clients__logo--img {
  display: inline-flex;
  align-items: center; justify-content: center;
  height: 56px;
  min-width: 120px;      /* réserve la place → pas d'effondrement du strip avant
                            chargement des images (logos qui "sautent"/disparaissent) */
  opacity: 0.95;
}
.clients__logo--img img {
  height: 100%;
  width: auto;
  max-width: 170px;
  object-fit: contain;
  display: block;
}
.clients__logo--img:hover { opacity: 1; }

/* Filtre monochrome blanc — activé via toggle admin "clients_monochrome".
   Marche bien pour les logos avec fond transparent. Pour les logos avec fond
   blanc, le filtre conserve le fond visible (à éviter dans ce cas). */
.clients--monochrome .clients__logo--img img {
  filter: brightness(0) invert(1) opacity(0.85);
}
.clients--monochrome .clients__logo--img:hover img {
  filter: brightness(0) invert(1) opacity(1);
}

/* ====================================================================
   AWARDS
   ==================================================================== */
.awards {
  padding: var(--section-y) var(--pad-x);
  /* Scène sombre : le néon des lauriers doit ressortir (comme le logo hero). */
  background:
    radial-gradient(120% 80% at 50% 42%, rgba(var(--accent-rgb), 0.08) 0%, rgba(var(--accent-rgb), 0) 60%),
    #0d0d0e;
}
.awards .section__head .title .italic-serif { color: var(--accent); }
/* ── Prix : sélecteur « façon jeu vidéo » (roulette de lauriers néon) ── */
.award-rig {
  position: relative;
  margin-top: clamp(24px, 4vw, 44px);
  padding-bottom: 72px;     /* place pour la fiche technique + le compteur */
  display: flex; align-items: center; justify-content: center;
  gap: clamp(4px, 2vw, 24px);
  outline: none;
  cursor: grab;
  user-select: none;
  touch-action: pan-y;      /* le scroll vertical de page reste possible */
}
.award-rig:active { cursor: grabbing; }
.award-rig__arrow {
  flex: none;
  width: clamp(44px, 5vw, 58px); height: clamp(44px, 5vw, 58px);
  border-radius: 50%;
  border: 1px solid rgba(var(--accent-rgb), 0.4);
  background: rgba(var(--accent-rgb), 0.04);
  color: var(--accent);
  font-size: 26px; line-height: 1;
  display: flex; align-items: center; justify-content: center;
  cursor: pointer; z-index: 6;
  transition: border-color .25s, background .25s, box-shadow .25s, transform .2s;
}
.award-rig__arrow:hover {
  border-color: var(--accent);
  background: rgba(var(--accent-rgb), 0.12);
  box-shadow: 0 0 18px rgba(var(--accent-rgb), 0.45);
  transform: scale(1.06);
}
.award-rig__track {
  position: relative;
  flex: 1 1 auto;
  min-width: 0;
  height: clamp(300px, 42vw, 460px);
}
/* Rail « sélection de véhicule ». Le RAIL entier se translate d'un cran
   (mouvement d'ensemble : tous les lauriers bougent ensemble) ; chaque laurier
   (slot) se met à l'échelle selon sa distance au centre → le voisin grandit en
   arrivant au centre, l'extrémité rétrécit et disparaît sur le bord.
   Positions/échelles calculées en JS (style inline). */
.award-rail {
  position: absolute; left: 50%; top: 50%;
  transition: transform .6s cubic-bezier(.3,.9,.25,1);
  will-change: transform;
}
.award-slot {
  position: absolute;
  width: min(560px, 82vw);
  transition: transform .6s cubic-bezier(.3,.9,.25,1), opacity .6s ease;
  will-change: transform, opacity;
}
.award-slot--side { cursor: pointer; }
.award-rig__arrow:disabled { opacity: 0.22; cursor: default; box-shadow: none; }
.award-rig__arrow:disabled:hover { transform: none; background: rgba(var(--accent-rgb), 0.04); border-color: rgba(var(--accent-rgb), 0.4); }
.award-card__frame { position: relative; width: 100%; }
.award-card__laurel { position: relative; width: 100%; }
.award-card__laurel .laurel-svg,
.award-card__img { display: block; width: 100%; height: auto; }

/* Néon des lauriers — mêmes réglages que le logo hero (drop-shadow empilés).
   Plein néon + scintillement réservés au laurier CENTRAL ; les voisins sont
   atténués (aperçu). */
.laurel-leaf { fill: var(--accent); }
.laurel-stem { fill: none; stroke: var(--accent); stroke-width: 3; stroke-linecap: round; }
.award-slot--center .award-card__laurel .laurel-svg,
.award-slot--center .award-card__laurel .award-card__img {
  filter:
    drop-shadow(0 0 calc(10px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.95 * var(--neon-mult, 1))))
    drop-shadow(0 0 calc(26px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.6 * var(--neon-mult, 1))))
    drop-shadow(0 0 calc(52px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(0.32 * var(--neon-mult, 1))));
  animation: flickerTired 13s linear infinite;   /* scintillement lent / posé */
}
/* Voisins (aperçu) : lauriers atténués, sans scintillement */
.award-slot--side .laurel-leaf { fill: rgba(var(--accent-rgb), 0.5); }
.award-slot--side .laurel-stem { stroke: rgba(var(--accent-rgb), 0.5); }
.award-slot--side .award-card__laurel .laurel-svg { filter: drop-shadow(0 0 7px rgba(var(--accent-rgb), 0.3)); }
.award-slot--side .award-card__fest { display: none; }   /* trop petit pour être lisible */
.award-card__frame:hover .award-card__laurel .laurel-svg,
.award-card__frame:hover .award-card__laurel .award-card__img { animation-play-state: paused; opacity: 1; }
/* Au survol du laurier CENTRAL, TOUS les voisins (gauche ET droite) s'effacent
   pour dégager la fiche « Tron » (sinon le texte chevauche un aperçu). */
.award-rail:has(.award-slot--center .award-card__frame:hover) .award-slot--side {
  opacity: 0 !important; pointer-events: none;
}
/* « Faux contact » : coupure nette du tube (piloté en JS, toggle .is-out) */
.award-card__frame.is-out .laurel-svg,
.award-card__frame.is-out .award-card__img {
  opacity: 0.05 !important;
  filter: drop-shadow(0 0 2px rgba(var(--accent-rgb), 0.2)) !important;
  transition: none !important;
}
.award-card__frame.is-out .award-card__fest,
.award-card__frame.is-out .award-card__year { opacity: 0.15; transition: none; }

/* Texte d'identité au CENTRE du laurier — cantonné à la zone vide centrale
   pour ne jamais chevaucher les feuilles (haut / bas / côtés). */
.award-card__inner {
  position: absolute; inset: 31% 26% 24%;
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  text-align: center; gap: 7px;
  pointer-events: none; overflow: hidden;
}
.award-card__fest {
  font-family: var(--mono); font-size: clamp(9px, 1vw, 12px);
  letter-spacing: 0.14em; text-transform: uppercase; color: var(--accent);
  text-shadow: 0 0 10px rgba(var(--accent-rgb), 0.6);
  max-width: 100%;
}
.award-card__title {
  font-family: var(--mono); font-weight: 700; text-transform: uppercase;
  font-size: clamp(15px, 2.5vw, 30px); line-height: 1.02; letter-spacing: -0.01em;
  color: #f4ede0; overflow-wrap: anywhere; max-width: 100%;
  text-shadow: 0 0 10px rgba(var(--accent-rgb), 0.35), 0 0 26px rgba(var(--accent-rgb), 0.25);
}
.award-card__year {
  font-family: var(--mono); font-size: clamp(12px, 1.4vw, 17px);
  letter-spacing: 0.14em; color: var(--accent);
  text-shadow: 0 0 12px rgba(var(--accent-rgb), 0.7);
  margin-top: 2px;
}

/* Flanc = zone à gauche/droite du laurier. Contient l'APERÇU du prix voisin
   (au repos) ET la fiche technique « Tron » (au survol du laurier). */
.award-flank {
  position: absolute; top: 50%; transform: translateY(-50%);
  width: clamp(180px, 22vw, 280px);
  z-index: 5;
}
.award-flank--left  { right: calc(100% + clamp(6px, 2vw, 26px)); }
.award-flank--right { left:  calc(100% + clamp(6px, 2vw, 26px)); }

/* Aperçu du prix précédent / suivant (petit laurier + titre), cliquable */
.award-peek {
  display: flex; flex-direction: column; align-items: center; gap: 9px;
  width: 100%; background: none; border: none; cursor: pointer;
  opacity: 0.5; transition: opacity .4s ease, transform .4s cubic-bezier(.2,1,.3,1);
}
.award-peek:hover { opacity: 1; transform: scale(1.05); }
.award-peek__laurel { width: clamp(94px, 12vw, 148px); }
.award-peek__laurel .laurel-svg { width: 100%; height: auto; display: block;
  filter: drop-shadow(0 0 7px rgba(var(--accent-rgb), 0.35)); }
.award-peek .laurel-leaf { fill: rgba(var(--accent-rgb), 0.5); }
.award-peek .laurel-stem { stroke: rgba(var(--accent-rgb), 0.5); stroke-width: 3; }
.award-peek__label {
  display: flex; flex-direction: column; gap: 2px; max-width: 100%;
  font-family: var(--mono); font-size: 10px; line-height: 1.3; letter-spacing: 0.05em;
  text-transform: uppercase; color: rgba(238,234,224,0.6); text-align: center;
  overflow-wrap: anywhere;
}
.award-peek__yr { color: var(--accent); }

/* Fiche technique « terminal Tron » — superposée au flanc, cachée au repos */
.award-card__side {
  position: absolute; top: 50%; transform: translateY(-50%);
  width: 100%;
  display: flex; flex-direction: column; gap: 12px;
  pointer-events: none;
}
.award-card__side--left  { right: 0; align-items: flex-end;   text-align: right; }
.award-card__side--right { left:  0; align-items: flex-start; text-align: left; }
.award-line {
  display: flex; flex-direction: column; gap: 2px; max-width: 100%;
  opacity: 0; transform: translateX(var(--dir, -12px));
  transition: opacity .2s linear, transform .28s cubic-bezier(.2,1,.3,1);
}
.award-card__side--left  .award-line { --dir: -12px; }
.award-card__side--right .award-line { --dir:  12px; }
.award-line__k {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.18em; text-transform: uppercase;
  color: rgba(var(--accent-rgb), 0.85);
}
.award-line__v {
  font-family: var(--mono); font-size: 16px; line-height: 1.3; color: #eaf0ff;
  letter-spacing: 0.02em;
  text-shadow: 0 0 8px rgba(var(--accent-rgb), 0.55);
}
.award-card__side--right .award-line__v::before { content: "◂ "; color: var(--accent); }
.award-card__side--left  .award-line__v::after  { content: " ▸"; color: var(--accent); }

/* Survol du laurier central → l'aperçu s'efface, la fiche s'allume ligne à
   ligne (séquence rapide, alternée gauche/droite, façon terminal). */
.award-card__frame:hover ~ .award-flank .award-peek { opacity: 0; pointer-events: none; }
.award-card__frame:hover ~ .award-flank .award-line { opacity: 1; transform: none; }
.award-card__frame:hover ~ .award-flank--left  .award-line:nth-child(1) { transition-delay: .05s; }
.award-card__frame:hover ~ .award-flank--right .award-line:nth-child(1) { transition-delay: .11s; }
.award-card__frame:hover ~ .award-flank--left  .award-line:nth-child(2) { transition-delay: .17s; }
.award-card__frame:hover ~ .award-flank--right .award-line:nth-child(2) { transition-delay: .23s; }
.award-card__frame:hover ~ .award-flank--left  .award-line:nth-child(3) { transition-delay: .29s; }
.award-card__frame:hover ~ .award-flank--right .award-line:nth-child(3) { transition-delay: .35s; }

.award-rig__counter {
  position: absolute; bottom: 16px; left: 50%; transform: translateX(-50%);
  font-family: var(--mono); font-size: 12px; letter-spacing: 0.18em; color: rgba(238,234,224,0.55);
  transition: opacity .3s ease;
}
.award-rig__index { color: var(--accent); }
.award-rig__sep { margin: 0 6px; opacity: 0.5; }

@media (prefers-reduced-motion: reduce) {
  .award-card__laurel .laurel-svg,
  .award-card__laurel .award-card__img { animation: none; }
  .award-slot, .award-rail { transition: none; }
}
/* Pas assez de place pour le rail : on masque les lauriers voisins et on
   empile la fiche sous le laurier central. Fenêtres étroites ET tactile. */
@media (max-width: 1180px), (hover: none) {
  .award-rig { display: block; position: relative; padding-bottom: 8px; }
  .award-rig__track { height: auto; padding: 6px 0 4px; }
  .award-rig__arrow {
    position: absolute; top: min(240px, calc(6px + 35vw));
    transform: translateY(-50%); z-index: 6;
  }
  .award-rig__arrow--prev { left: 0; }
  .award-rig__arrow--next { right: 0; }
  .award-rail { position: static !important; transform: none !important; left: auto; top: auto; }
  .award-slot--side { display: none; }        /* pas de place pour les aperçus */
  .award-slot--center {
    position: static !important; transform: none !important; opacity: 1 !important;
    width: min(560px, 90vw); margin: 0 auto;
  }
  /* La fiche latérale fait doublon avec le texte du laurier en version
     mobile → on la masque (les infos essentielles sont déjà au centre). */
  .award-flank { display: none; }
  .award-rig__counter { position: static; transform: none; margin: 18px auto 0; text-align: center; }
}

/* ====================================================================
   NEWS / BLOG
   ==================================================================== */
.news { padding: var(--section-y) var(--pad-x); }
.news__grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 2px;
  background: var(--line);
  border-top: 1px solid var(--line);
  border-bottom: 1px solid var(--line);
}
.news-card {
  background: var(--bg);
  display: flex; flex-direction: column;
  min-height: 320px;
  transition: background .2s;
  cursor: pointer;
  /* Reset button styles */
  appearance: none;
  border: 0;
  font: inherit;
  color: inherit;
  text-align: left;
  padding: 0;
  width: 100%;
  overflow: hidden;
}
.news-card:hover { background: var(--bg-elev); }
.news-card:focus-visible { outline: 2px solid var(--accent); outline-offset: -2px; }
.news-card__cover {
  width: 100%;
  aspect-ratio: 16 / 10;
  background-size: cover;
  background-repeat: no-repeat;
  background-color: #0a0a0a;
  border-bottom: 1px solid var(--line);
}
.news-card__body {
  padding: 24px 28px 28px;
  display: flex; flex-direction: column; gap: 14px; flex: 1;
}
.news-card__meta {
  display: flex; flex-wrap: wrap; gap: 12px;
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase;
  color: var(--accent);
}
.news-card__cat { color: var(--ink-mute); }
.news-card__date { font-family: var(--mono); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase; color: var(--accent); }
.news-card__title { font-family: var(--display); font-size: 22px; text-transform: uppercase; line-height: 1.05; letter-spacing: -0.015em; margin: 0; }
.news-card__excerpt { font-size: 14px; line-height: 1.6; color: var(--ink-soft); flex: 1; white-space: pre-line; }
.news-card__link { font-family: var(--mono); font-size: 11px; letter-spacing: 0.18em; text-transform: uppercase; color: var(--ink); border-bottom: 1px solid var(--ink); align-self: flex-start; padding-bottom: 2px; }
.news-card:hover .news-card__link { color: var(--accent); border-color: var(--accent); }

/* ====================================================================
   NEWS MODAL — popup riche article au clic
   ==================================================================== */
.news-modal {
  position: fixed; inset: 0;
  background: var(--glass-noise-soft) var(--glass-scrim);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  z-index: var(--z-modal);  /* 1000 */
  display: flex;
  align-items: flex-start;
  justify-content: center;
  padding: clamp(20px, 4vw, 60px);
  overflow-y: auto;
  animation: project-modal-fade .25s ease-out;
}
.news-modal__box {
  position: relative;
  width: 100%;
  max-width: 920px;
  background: var(--bg-elev);
  border: 1px solid var(--line);
  border-radius: 4px;
  overflow: hidden;
  animation: project-modal-rise .35s cubic-bezier(.16, 1, .3, 1);
  margin: auto;
}
.news-modal__close {
  position: absolute; top: 16px; right: 16px;
  appearance: none;
  border: 1px solid var(--glass-line);
  background: var(--glass-sheen), var(--glass-chip);
  box-shadow: var(--glass-highlight);
  color: var(--ink);
  width: 40px; height: 40px;
  border-radius: 50%;
  font-size: 24px; line-height: 1;
  cursor: pointer; z-index: 5;
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  transition: all .15s;
}
.news-modal__close:hover { border-color: var(--accent); color: var(--accent); }
.news-modal__hero {
  width: 100%;
  aspect-ratio: 16 / 9;
  background-size: cover;
  background-repeat: no-repeat;
  background-color: #0a0a0a;
  border-bottom: 1px solid var(--line);
}
.news-modal__head {
  padding: clamp(28px, 4vw, 48px) clamp(24px, 4vw, 56px) 16px;
}
.news-modal__meta {
  display: flex; flex-wrap: wrap; gap: 14px;
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.18em; text-transform: uppercase;
  color: var(--ink-mute); margin-bottom: 16px;
}
.news-modal__cat { color: var(--accent); }
.news-modal__title {
  font-family: var(--display);
  font-size: clamp(32px, 4.5vw, 56px);
  text-transform: uppercase;
  line-height: 1;
  letter-spacing: -0.025em;
  color: var(--ink);
  margin: 0 0 18px;
}
.news-modal__lead {
  font-size: 18px; line-height: 1.6; color: var(--ink-soft);
  max-width: 720px; margin: 0; font-style: italic;
}
.news-modal__body {
  padding: 4px clamp(24px, 4vw, 56px) clamp(24px, 4vw, 40px);
  max-width: 720px;
}
.news-modal__para {
  font-size: 16px; line-height: 1.75; color: var(--ink-soft);
  margin: 0 0 18px;
}
.news-modal__para:last-child { margin-bottom: 0; }
.news-modal__para strong { color: var(--ink); font-weight: 700; }
.news-modal__para em { font-style: italic; }
.news-modal__video {
  padding: 0 clamp(24px, 4vw, 56px) clamp(24px, 4vw, 40px);
}
.news-modal__gallery {
  padding: clamp(20px, 4vw, 40px) clamp(24px, 4vw, 56px);
  border-top: 1px solid var(--line);
}
.news-modal__gallery-label {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase;
  color: var(--ink-mute); margin-bottom: 14px;
}
.news-modal__gallery-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(160px, 1fr));
  gap: 8px;
}
.news-modal__gallery-item {
  display: block;
  aspect-ratio: 4 / 3;
  background-color: #0a0a0a;
  background-size: cover;
  background-position: center;
  background-repeat: no-repeat;
  border: 1px solid var(--line);
  border-radius: 2px;
  appearance: none;
  padding: 0;
  font: inherit;
  color: inherit;
  width: 100%;
  cursor: zoom-in;
  transition: transform .2s ease, border-color .15s;
}
.news-modal__gallery-item:hover { border-color: var(--accent); transform: scale(1.015); }
.news-modal__gallery-item:focus-visible { outline: 2px solid var(--accent); outline-offset: 2px; }
.news-modal__tags {
  padding: 0 clamp(24px, 4vw, 56px) clamp(20px, 4vw, 32px);
  display: flex; flex-wrap: wrap; gap: 8px;
}
.news-modal__tag {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.1em;
  color: var(--ink-soft);
  padding: 4px 10px;
  border: 1px solid var(--line);
  border-radius: 999px;
}
.news-modal__cta {
  padding: 0 clamp(24px, 4vw, 56px) clamp(28px, 4vw, 48px);
}
.news-modal__cta-btn {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 14px 22px;
  background: var(--accent);
  color: #fff;
  font-family: var(--mono);
  font-size: 12px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  text-decoration: none;
  border-radius: 3px;
  transition: opacity .2s;
}
.news-modal__cta-btn:hover { opacity: 0.85; }

@media (max-width: 720px) {
  .news-modal { padding: 0; align-items: stretch; }
  .news-modal__box { border-radius: 0; min-height: 100vh; }
}

/* ====================================================================
   TESTIMONIALS
   ==================================================================== */
.tests { padding: var(--section-y) var(--pad-x); background: var(--bg-light); color: #0a0a0a; }
.tests__grid {
  display: grid;
  grid-template-columns: 1fr 1fr 1fr;
  gap: 32px;
  margin-top: 64px;
}
.test-card { padding: 28px; background: #fff; border: 1px solid rgba(0,0,0,0.08); display: flex; flex-direction: column; gap: 16px; }
.test-card__head { display: flex; align-items: center; gap: 12px; }
.test-card__avatar {
  width: 42px; height: 42px;
  border-radius: 50%;
  object-fit: cover;
  border: 1px solid rgba(0,0,0,0.10);
  background: rgba(0,0,0,0.04);
  flex: none;
}
.test-card__avatar--initials {
  display: flex; align-items: center; justify-content: center;
  font-family: var(--mono);
  font-size: 14px;
  font-weight: 700;
  color: #555;
}
.test-card__head-info { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.test-card__head-info strong {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.14em;
  text-transform: uppercase;
  color: #000;
}
.test-card__date {
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: 0.08em;
  color: #999;
}
.test-card__stars { color: var(--accent); letter-spacing: 3px; font-size: 14px; }
.test-card__stars-empty { color: rgba(0,0,0,0.15); }
.test-card__quote { font-family: "Times New Roman", serif; font-style: italic; font-size: 18px; line-height: 1.5; color: #1a1a1a; flex: 1; }
.test-card__author { display: flex; flex-wrap: wrap; gap: 8px; align-items: baseline; justify-content: space-between; margin-top: 4px; }
.test-card__author span {
  font-family: var(--mono); font-size: 10px;
  letter-spacing: 0.14em; text-transform: uppercase;
  color: #777;
}
.test-card__source {
  font-family: var(--mono); font-size: 10px;
  letter-spacing: 0.1em; text-transform: uppercase;
  padding: 3px 8px;
  border: 1px solid rgba(0,0,0,0.15);
  border-radius: 999px;
  color: #555;
  background: rgba(0,0,0,0.03);
}

/* ====================================================================
   CONTACT
   ==================================================================== */
.contact {
  padding: var(--section-y) var(--pad-x);
  background: var(--bg);
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 64px;
}
.contact__lead {
  font-family: var(--display);
  font-size: clamp(40px, 5.6vw, 88px);
  text-transform: uppercase;
  line-height: 0.9;
  letter-spacing: -0.025em;
}
.contact__lead .blink { color: var(--accent); animation: blink 1.2s steps(2) infinite; }
@keyframes blink { 50% { opacity: 0; } }

.contact__details { margin-top: 64px; display: grid; gap: 22px; font-family: var(--mono); font-size: 13px; letter-spacing: 0.08em; text-transform: uppercase; }
.contact__details .col strong { display: block; color: var(--ink-soft); font-weight: 400; margin-bottom: 6px; font-size: 11px; letter-spacing: 0.18em; }
.contact__details .col a, .contact__details .col p { font-size: 17px; letter-spacing: 0.04em; }
.contact__details .col a:hover { color: var(--accent); }

.contact__form {
  background: var(--bg-elev);
  border: 1px solid var(--line);
  padding: 36px;
  display: grid;
  gap: 18px;
}
.field { display: grid; gap: 6px; }
.field label { font-family: var(--mono); font-size: 10px; letter-spacing: 0.22em; text-transform: uppercase; color: var(--ink-mute); }
.field input, .field textarea, .field select {
  background: transparent;
  border-bottom: 1px solid var(--line-str);
  padding: 10px 0;
  font-family: var(--mono); font-size: 14px;
  color: var(--ink);
  width: 100%;
  transition: border-color .2s;
}
.field input:focus, .field textarea:focus, .field select:focus { border-color: var(--accent); }
.field textarea { min-height: 80px; resize: vertical; }
.field-row { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; }
.chips { display: flex; flex-wrap: wrap; gap: 6px; }
.chip {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.14em; text-transform: uppercase;
  padding: 8px 12px;
  border: 1px solid var(--line);
  color: var(--ink-soft);
  transition: all .2s;
}
.chip:hover { color: var(--ink); }
.chip.active { background: var(--accent); color: #fff; border-color: var(--accent); }
.submit-btn {
  margin-top: 8px;
  padding: 18px;
  background: var(--accent);
  color: #fff;
  font-family: var(--mono); font-size: 12px; letter-spacing: 0.22em; text-transform: uppercase; font-weight: 700;
  display: flex; justify-content: space-between; align-items: center;
  transition: background .2s, box-shadow .3s;
}
.submit-btn:hover { background: #1d48e0; box-shadow: 0 0 28px rgba(var(--accent-rgb), 0.55); }
.submit-btn:disabled { opacity: 0.55; cursor: not-allowed; box-shadow: none; }

/* ----- Brief form: honeypot, validation messages, hint, consent ----- */
/* Honeypot — visually & semantically removed from real users, but kept in
   the DOM so bots that fill all fields will tick it. */
.hp-field {
  position: absolute !important;
  left: -10000px !important;
  top: auto !important;
  width: 1px !important;
  height: 1px !important;
  overflow: hidden !important;
  opacity: 0 !important;
  pointer-events: none !important;
}

.field-hint {
  font-family: var(--mono);
  font-size: 10px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-mute);
  margin-top: 2px;
}

.form-msg {
  font-family: var(--mono);
  font-size: 12px;
  line-height: 1.55;
  letter-spacing: 0.02em;
  padding: 12px 14px;
  border-radius: 4px;
  border: 1px solid transparent;
}
.form-msg--ok {
  background: rgba(74, 222, 128, 0.08);
  border-color: rgba(74, 222, 128, 0.45);
  color: #86efac;
}
.form-msg--err {
  background: rgba(255, 77, 77, 0.08);
  border-color: rgba(255, 77, 77, 0.45);
  color: #ff8a8a;
}

.form-consent {
  font-family: var(--mono);
  font-size: 10px;
  line-height: 1.6;
  letter-spacing: 0.06em;
  color: var(--ink-mute);
  margin: 4px 0 0;
}
.form-consent a {
  color: var(--accent);
  text-decoration: underline;
  text-underline-offset: 3px;
}
.form-consent a:hover { color: var(--ink); }

/* ====================================================================
   FOOTER
   ==================================================================== */
.footer { padding: 56px var(--pad-x) 32px; }
/* Brand sur sa propre ligne — sinon "CASQUETTES" en 8vw (~740px) pousse
   les 4 autres colonnes vers la droite et la dernière (Légal) sort de l'écran.
   Cette mise en page tient à toutes les largeurs réalistes (1024 → 2560+). */
.footer__top {
  display: grid;
  grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: 40px 32px;
  padding-bottom: 48px;
}
.footer__brand {
  grid-column: 1 / -1;
  margin-bottom: 4px;
  font-family: var(--display);
  font-size: clamp(48px, 7.5vw, 120px);
  line-height: 0.85;
  text-transform: uppercase;
  letter-spacing: -0.03em;
}
.footer__col h4 { font-family: var(--mono); font-size: 11px; letter-spacing: 0.2em; text-transform: uppercase; color: var(--ink-mute); margin-bottom: 16px; }
.footer__col a, .footer__col p { display: block; font-family: var(--mono); font-size: 13px; padding: 4px 0; transition: color .2s; }
.footer__col a:hover { color: var(--accent); }
.footer__bottom { display: flex; justify-content: space-between; padding-top: 24px; font-family: var(--mono); font-size: 11px; letter-spacing: 0.14em; text-transform: uppercase; color: var(--ink-mute); gap: 14px; flex-wrap: wrap; }
/* Raccourci back-office discret : un point cliquable en bas de page. */
.footer__admin-dot {
  color: inherit; text-decoration: none; cursor: pointer;
  padding: 0 8px; margin-left: 2px; opacity: 0.6;
  transition: color .2s, opacity .2s;
}
.footer__admin-dot:hover { color: var(--accent); opacity: 1; }

/* ====================================================================
   PALETTE: LIGHT MODE
   ==================================================================== */
body.palette-light { color: var(--ink); }
body.palette-light .hero, body.palette-light .hero__bg { background: var(--bg); }
body.palette-light .marquee__track .ghost { -webkit-text-stroke: 1px rgba(0,0,0,0.4); }
body.palette-light .hero__nav a, body.palette-light .hero__grid, body.palette-light .hero__foot .val, body.palette-light .hero__cta { color: var(--ink); }
body.palette-light .hero__cta { border-color: var(--ink); }
body.palette-light .hero__bg {
  background:
    linear-gradient(180deg, rgba(245,243,236,0.2) 0%, rgba(245,243,236,0.4) 50%, rgba(245,243,236,0.95) 100%),
    radial-gradient(ellipse at 50% 30%, #d9d3c2 0%, #ede8de 55%, #f5f3ec 100%);
}
body.palette-light .hero__stripes {
  background: repeating-linear-gradient(90deg,
    rgba(0,0,0,0.5) 0px, rgba(0,0,0,0.5) 4px,
    rgba(0,0,0,0.08) 4px, rgba(0,0,0,0.08) 8px);
}
body.palette-light .marquee { background: var(--bg); }
body.palette-light .section, body.palette-light .services, body.palette-light .team, body.palette-light .news, body.palette-light .awards, body.palette-light .clients, body.palette-light .contact, body.palette-light .footer { background: var(--bg); color: var(--ink); }
body.palette-light .section--light, body.palette-light .manifeste, body.palette-light .tests { background: #fff; color: #0a0a0a; }
body.palette-light .card { background: var(--bg-elev); }
body.palette-light .contact__form { background: var(--bg-elev); border-color: rgba(0,0,0,0.1); }
body.palette-light .field input, body.palette-light .field textarea { color: var(--ink); border-color: rgba(0,0,0,0.2); }
body.palette-light .news-card, body.palette-light .team-card { background: var(--bg-elev); }
body.palette-light .news-card:hover { background: #fff; }
body.palette-light .news-card__link, body.palette-light .team-card__name, body.palette-light .footer__brand { color: var(--ink); }
body.palette-light .news-card__excerpt, body.palette-light .team-card__bio { color: rgba(0,0,0,0.65); }
body.palette-light .clients__logo { color: rgba(0,0,0,0.4); }
body.palette-light .clients__logo:hover { color: var(--ink); }
body.palette-light .award__title { color: var(--ink); }
body.palette-light .award__fest { color: rgba(0,0,0,0.55); }
body.palette-light .award__cat  { color: rgba(0,0,0,0.35); }
body.palette-light :root, body.palette-light { --line: rgba(0,0,0,0.12); --line-str: rgba(0,0,0,0.32); --ink-soft: rgba(0,0,0,0.55); --ink-mute: rgba(0,0,0,0.35); }
   ==================================================================== */
body.no-grain .grain { display: none; }
body.no-stripes .hero__stripes { display: none; }
body.no-badge .neon-badge { display: none; }
body.no-numbers .section__head .num,
body.no-numbers .label,
body.no-numbers .mono-xs:first-child { display: none; }

[data-radius="soft"]  .card,
[data-radius="soft"]  .test-card,
[data-radius="soft"]  .news-card,
[data-radius="soft"]  .contact__form,
[data-radius="soft"]  .filter-btn,
[data-radius="soft"]  .chip,
[data-radius="soft"]  .submit-btn   { border-radius: 8px; }
[data-radius="round"] .card,
[data-radius="round"] .test-card,
[data-radius="round"] .news-card,
[data-radius="round"] .contact__form,
[data-radius="round"] .filter-btn,
[data-radius="round"] .chip,
[data-radius="round"] .submit-btn  { border-radius: 18px; }

[data-casing="title"] .display,
[data-casing="title"] h1, [data-casing="title"] h2, [data-casing="title"] h3,
[data-casing="title"] .hero__display, [data-casing="title"] .hero__split-word,
[data-casing="title"] .card__title, [data-casing="title"] .svc-row__title,
[data-casing="title"] .section__head .title,
[data-casing="title"] .footer__brand { text-transform: none; }
[data-casing="lower"] .display,
[data-casing="lower"] h1, [data-casing="lower"] h2, [data-casing="lower"] h3,
[data-casing="lower"] .hero__display, [data-casing="lower"] .hero__split-word,
[data-casing="lower"] .card__title, [data-casing="lower"] .svc-row__title,
[data-casing="lower"] .section__head .title,
[data-casing="lower"] .footer__brand { text-transform: lowercase; }

[data-italic="sans"] .italic-serif, [data-italic="sans"] .accent { font-family: var(--body); font-style: italic; }
[data-italic="mono"] .italic-serif, [data-italic="mono"] .accent { font-family: var(--mono); font-style: normal; }

.marquee__track { animation-duration: var(--marquee-speed, 30s); }
.clients__strip { animation-duration: var(--marquee-speed, 30s); }

[data-ratio="4x5"] .card { aspect-ratio: 4 / 5; }
[data-ratio="1x1"] .card { aspect-ratio: 1 / 1; }
[data-ratio="4x5"] .portfolio__grid--list .card,
[data-ratio="1x1"] .portfolio__grid--list .card { aspect-ratio: 21 / 6; }

[data-hover="tilt"] .card { transition: transform .35s ease; }
[data-hover="tilt"] .card:hover { transform: perspective(900px) rotateX(2deg) rotateY(-3deg) scale(1.01); }
[data-hover="lift"] .card { transition: transform .35s ease, box-shadow .35s ease; }
[data-hover="lift"] .card:hover { transform: translateY(-6px); box-shadow: 0 24px 60px rgba(0,0,0,0.5), 0 0 0 1px rgba(var(--accent-rgb), 0.3); }
[data-hover="invert"] .card:hover .card__media { filter: invert(1) hue-rotate(180deg); }
[data-hover="none"]   .card:hover .card__media { transform: none; }

.hero__logo-stage svg { filter:
  drop-shadow(0 0 calc(var(--neon-i, 1) * 32px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(var(--neon-i, 1) * 0.95 * var(--neon-mult, 1))))
  drop-shadow(0 0 calc(var(--neon-i, 1) * 10px * var(--neon-mult, 1)) rgba(var(--accent-rgb), calc(var(--neon-i, 1) * 0.7 * var(--neon-mult, 1))));
}

/* ====================================================================
   DENSITY TWEAK
   ==================================================================== */
[data-density="compact"] { --section-y: clamp(56px, 7vw, 100px); }
[data-density="loose"]   { --section-y: clamp(120px, 14vw, 240px); }

/* ====================================================================
   SCROLL ANIMATIONS
   ==================================================================== */
.anim-pending { will-change: transform, opacity, filter; }
.anim-fade.anim-pending { opacity: 0; transform: translate3d(0, 40px, 0); }
.anim-fade { transition: opacity .9s cubic-bezier(.16,.84,.34,1), transform .9s cubic-bezier(.16,.84,.34,1); }
.anim-slide.anim-pending { opacity: 0; transform: translate3d(-50px, 0, 0); }
.anim-slide { transition: opacity .9s cubic-bezier(.16,.84,.34,1), transform .9s cubic-bezier(.16,.84,.34,1); }
.anim-reveal.anim-pending { clip-path: inset(0 100% 0 0); }
.anim-reveal { transition: clip-path 1.1s cubic-bezier(.7,0,.2,1); clip-path: inset(0 0 0 0); }
.anim-blur.anim-pending { opacity: 0; filter: blur(18px); transform: scale(1.03); }
.anim-blur { transition: opacity 1.1s ease, filter 1.1s ease, transform 1.1s ease; filter: blur(0); transform: scale(1); }

/* ====================================================================
   RESPONSIVE
   ==================================================================== */
@media (max-width: 900px) {
  .hero { min-height: 92vh; height: 92vh; }
  .hero__nav { padding: 14px 18px; font-size: 10px; }
  .hero__nav-l, .hero__nav-r { gap: 14px; }
  .hero__nav-l a:nth-child(2), .hero__nav-r a:nth-child(2) { display: none; }
  .hero__grid { display: none; }
  .hero__display { font-size: clamp(48px, 16vw, 96px); bottom: 160px; }
  .hero__foot { grid-template-columns: 1fr 1fr; gap: 14px; bottom: 20px; }
  .hero__foot .col:nth-child(3) { display: none; }
  .hero__cta { justify-self: start; grid-column: 1 / -1; }

  .marquee__track { font-size: clamp(34px, 11vw, 60px); gap: 36px; }

  .manifeste__meta { grid-template-columns: 1fr 1fr; }

  .portfolio__grid,
  .portfolio__grid--3col,
  .portfolio__grid--editorial { grid-template-columns: 1fr; }
  .portfolio__grid--editorial .card { grid-column: auto !important; }

  .svc-row { grid-template-columns: 40px 1fr; gap: 16px; }
  .svc-row--toggle { grid-template-columns: 40px 1fr auto; }
  .svc-row__desc { display: none; }
  .svc-row__count { display: none; }   /* on garde juste le chevron sur mobile */
  .svc-drawer__row { gap: 12px; padding: 14px 0 22px; }
  .svc-tile { width: clamp(180px, 64vw, 240px); }   /* ~1 vignette et demie visible → invite au swipe */
  .svc-tile__title { font-size: 15px; }
  .svc-tile__synopsis { -webkit-line-clamp: 2; }

  /* News et tests passent en colonne unique sur mobile.
     Team garde tous ses membres sur une ligne (auto-adaptatif). */
  .news__grid, .tests__grid { grid-template-columns: 1fr; }

  .clients { grid-template-columns: 1fr; gap: 14px; }
  .clients__label { max-width: 100%; }

  .award { grid-template-columns: 60px 1fr 30px; gap: 12px; font-size: 11px; }
  .award__fest, .award__cat { display: none; }

  .contact { grid-template-columns: 1fr; }

  .footer__top { grid-template-columns: 1fr 1fr; }
}

/* ====================================================================
   SIDE MENU — fixed right rail, magnet hover, neon-blue active state
   ==================================================================== */
/* Reserve right-side space when the side menu is active.
   --menu-shift is the LEFT offset applied to centered fixed elements
   (.brand, .neon-badge) so they stay centered in the visible content.
   Padding scales per breakpoint to keep ≥40px between content and menu. */
body {
  --menu-shift: 0px;
  padding-right: 0;
  transition: padding-right .6s cubic-bezier(.16, 1, .3, 1);
}
body.menu-active {
  --menu-shift: 70px;
  padding-right: 140px;
}
@media (max-width: 1280px) {
  body.menu-active { --menu-shift: 55px; padding-right: 110px; }
}
@media (max-width: 1024px) {
  /* padding-right doit être ≥ menu (right:15 + ~75px largeur = ~90) sinon
     les sections (team, photo, etc.) débordent visuellement sous les items
     du menu latéral. 100px laisse une marge de respiration. */
  body.menu-active { --menu-shift: 35px; padding-right: 100px; }
}
@media (max-width: 768px) {
  body.menu-active { --menu-shift: 0px; padding-right: 0; }
}

/* Manifeste — large editorial title needs its own breathing room beyond
   the global padding, otherwise the 6vw type touches the menu zone. */
body.menu-active .manifeste__txt { padding-right: 24px; }

/* Centered fixed elements need an extra `left` shift to remain visually
   centered in the reduced content area. Plain CSS transitions on `left`
   interpolate the calc() result smoothly when the class toggles. */
.brand,
.neon-badge {
  transition: left .6s cubic-bezier(.16, 1, .3, 1);
}
body.menu-active .brand,
body.menu-active .neon-badge {
  left: calc(50% - var(--menu-shift));
}
@media (prefers-reduced-motion: reduce) {
  body, .brand, .neon-badge { transition: none; }
}

/* ─── Dégradé d'en-tête haut de viewport ─────────────────────────────
   Quand le logo se docke en en-tête (scroll > 400px → body.menu-active,
   même déclencheur que le side-menu), un dégradé transparent fixe
   apparaît en haut de l'écran : DERRIÈRE le logo (z 90 < brand 110)
   mais DEVANT le reste du site (z 90 > contenu ≤ 30). Il assoit le
   logo docké sur le contenu qui défile dessous. */
body::before {
  content: "";
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  /* Opaque à 100% du haut de l'écran jusqu'au NIVEAU DE LA VISIÈRE de
     la casquette du logo docké (dernier pixel encré du PNG mesuré à
     y ≈ 103px desktop, ≈ 77px mobile — le fichier a ~13% de marge
     transparente sous le dessin), puis fondu continu adouci jusqu'à 0%
     en bas de la zone. */
  --top-fade-visor: 103px;
  height: clamp(200px, 26vh, 264px);
  background: linear-gradient(
    to bottom,
    rgba(13, 13, 14, 1) 0px,
    rgba(13, 13, 14, 1) var(--top-fade-visor),
    rgba(13, 13, 14, 0.58) 55%,
    rgba(13, 13, 14, 0.28) 75%,
    rgba(13, 13, 14, 0.10) 89%,
    rgba(13, 13, 14, 0) 100%
  );
  pointer-events: none;
  opacity: 0;
  transition: opacity .6s cubic-bezier(.16, 1, .3, 1);
  z-index: var(--z-top-fade);  /* 90 — sous side-menu (100) et brand (110) */
}
body.menu-active::before { opacity: 1; }
/* Palette claire : même fondu, dans la couleur de fond claire */
body.palette-light::before {
  background: linear-gradient(
    to bottom,
    rgba(242, 239, 232, 1) 0px,
    rgba(242, 239, 232, 1) var(--top-fade-visor),
    rgba(242, 239, 232, 0.58) 55%,
    rgba(242, 239, 232, 0.28) 75%,
    rgba(242, 239, 232, 0.10) 89%,
    rgba(242, 239, 232, 0) 100%
  );
}
/* Mobile : logo docké plus petit → visière plus haute (mesurée à 64px
   au scale docké, dernier pixel encré du PNG) */
@media (max-width: 640px) {
  body::before { --top-fade-visor: 64px; }
}
@media (prefers-reduced-motion: reduce) {
  body::before { transition: opacity .01s linear; }
}

/* --------------------------------------------------------------------
   Bandeau opaque de la « safe-area » haute (encoche / barre d'état iOS).
   Avec viewport-fit=cover le contenu passe SOUS l'horloge / batterie et
   on voyait le site derrière. Ce bandeau, toujours présent, couvre cette
   bande à hauteur de env(safe-area-inset-top) (0 sur les écrans sans
   encoche → aucun effet). z au-dessus du grain, sous skip-link/cookie. */
body::after {
  content: "";
  position: fixed;
  top: 0; left: 0; right: 0;
  height: env(safe-area-inset-top, 0px);
  background: #0d0d0e;              /* fond sombre du site */
  z-index: 9500;
  pointer-events: none;
}
body.palette-light::after { background: #f2efe8; }

.side-menu {
  position: fixed;
  top: 50%;
  right: 30px;
  /* Keep the centering translateY in both states; only translateX animates. */
  transform: translateY(-50%) translateX(20px);
  opacity: 0;
  pointer-events: none;
  z-index: var(--z-nav-base);  /* 100 — sous brand (110), burger (150), mobile-nav (180) */
  transition:
    opacity .6s cubic-bezier(.16, 1, .3, 1),
    transform .6s cubic-bezier(.16, 1, .3, 1);
}
.side-menu--visible {
  opacity: 1;
  transform: translateY(-50%) translateX(0);
  pointer-events: auto;
}
.side-menu__list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 20px;
  text-align: right;
}
.side-menu__li {
  /* Each LI is the visual slot; magnet transforms apply to the ITEM, not
     the LI, so the slot positions stay fixed (avoids layout shift of
     unhovered neighbours past the affected radius). */
  overflow: visible;
}
.side-menu__item {
  display: inline-block;
  font-family: "Courier Prime", "Courier New", monospace;
  font-size: 12px;
  letter-spacing: 2px;
  text-transform: uppercase;
  color: #F5F5F0;
  opacity: 0.5;
  text-decoration: none;
  cursor: pointer;
  transform-origin: 100% 50%;
  /* Halo subtil pour rester lisible quand le menu passe au-dessus d'une
     image de head claire (Portfolio, Services, Photo). Pas une ombre marquée :
     juste assez de contraste pour le texte clair sur fond clair. */
  text-shadow: 0 1px 4px rgba(0, 0, 0, 0.55), 0 0 1px rgba(0, 0, 0, 0.4);
  transition:
    transform .4s cubic-bezier(.34, 1.56, .64, 1),
    color .3s ease,
    text-shadow .3s ease,
    opacity .3s ease;
  will-change: transform;
}
.side-menu__item:hover,
.side-menu__item:focus-visible {
  color: #60A5FA;
  opacity: 1;
  text-shadow:
    0 0 4px  #60A5FA,
    0 0 10px #3B82F6,
    0 0 20px #3B82F6;
}
.side-menu__item:focus-visible {
  outline: 1px solid rgba(96, 165, 250, 0.6);
  outline-offset: 6px;
}
.side-menu__item.active {
  color: #3B82F6;
  opacity: 1;
  text-shadow:
    0 0 4px  #60A5FA,
    0 0 10px #3B82F6,
    0 0 20px #3B82F6;
  animation: sideMenuPulse 2s ease-in-out infinite;
}
@keyframes sideMenuPulse {
  0%, 100% {
    text-shadow:
      0 0 4px  #60A5FA,
      0 0 10px #3B82F6,
      0 0 20px #3B82F6;
  }
  50% {
    text-shadow:
      0 0 6px  #60A5FA,
      0 0 14px #3B82F6,
      0 0 28px #3B82F6;
  }
}

/* Réseaux sociaux sous la nav — mêmes codes visuels que les items
   (blanc cassé à 50%, hover bleu néon + glow). URLs éditables dans
   l'admin (contact_info) ; les liens non renseignés retombent sur "#". */
.side-menu__socials {
  margin-top: 28px;
  display: flex;
  justify-content: flex-end;
  gap: 16px;
}
.side-menu__social {
  display: inline-flex;
  color: #F5F5F0;
  opacity: 0.5;
  /* Pendant du text-shadow des items : lisibilité sur images claires */
  filter: drop-shadow(0 1px 3px rgba(0, 0, 0, 0.55));
  transition: color .3s ease, opacity .3s ease, filter .3s ease;
}
.side-menu__social svg {
  width: 16px;
  height: 16px;
  display: block;
}
.side-menu__social:hover,
.side-menu__social:focus-visible {
  color: #60A5FA;
  opacity: 1;
  filter:
    drop-shadow(0 0 4px #60A5FA)
    drop-shadow(0 0 10px #3B82F6);
}
.side-menu__social:focus-visible {
  outline: 1px solid rgba(96, 165, 250, 0.6);
  outline-offset: 4px;
}

/* Tablet — tighter rail */
@media (max-width: 1024px) {
  .side-menu { right: 15px; }
  .side-menu__item { font-size: 10px; letter-spacing: 1.5px; }
  .side-menu__list { gap: 16px; }
  .side-menu__socials { gap: 13px; margin-top: 22px; }
  .side-menu__social svg { width: 14px; height: 14px; }
}

/* Mobile — hidden; burger nav covers it */
@media (max-width: 768px) {
  .side-menu { display: none; }
}

/* Reduced motion — kill the spring & pulse, keep only color/opacity */
@media (prefers-reduced-motion: reduce) {
  .side-menu {
    transition: opacity .01s linear, transform .01s linear;
  }
  .side-menu__item {
    transition: color .2s ease, opacity .2s ease;
  }
  .side-menu__item.active {
    animation: none;
  }
}

/* =====================================================================
   ACCESSIBILITY — global helpers
   =====================================================================*/

/* Visually-hidden helper for SR-only labels */
.sr-only,
.visually-hidden {
  position: absolute !important;
  width: 1px !important;
  height: 1px !important;
  padding: 0 !important;
  margin: -1px !important;
  overflow: hidden !important;
  clip: rect(0, 0, 0, 0) !important;
  white-space: nowrap !important;
  border: 0 !important;
}

/* Skip link — first focusable element, jumps to #main. Hidden until focused. */
.skip-link {
  position: fixed;
  top: -50px;
  left: 12px;
  z-index: var(--z-skip);  /* 9999 — a11y top du top */
  padding: 10px 16px;
  background: var(--accent, #3B82F6);
  color: #fff;
  font-family: var(--mono, monospace);
  font-size: 12px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  text-decoration: none;
  border-radius: 4px;
  box-shadow: 0 8px 24px rgba(0, 0, 0, 0.5);
  transition: top .18s ease;
}
.skip-link:focus,
.skip-link:focus-visible {
  top: 12px;
  outline: 2px solid #fff;
  outline-offset: 2px;
}

/* Global focus ring — applies to all keyboard-focused interactive elements
   that don't already define their own focus style. Bright blue, 2px,
   2px offset — readable on both dark and light palettes. */
a:focus-visible,
button:focus-visible,
input:focus-visible,
textarea:focus-visible,
select:focus-visible,
[tabindex]:focus-visible,
[role="button"]:focus-visible {
  outline: 2px solid #60A5FA;
  outline-offset: 2px;
  border-radius: 2px;
}
/* On light palettes, use the accent's strong variant for contrast */
.palette-light a:focus-visible,
.palette-light button:focus-visible,
.palette-light input:focus-visible,
.palette-light textarea:focus-visible,
.palette-light select:focus-visible,
.palette-light [tabindex]:focus-visible {
  outline-color: #1d4ed8;
}

/* =====================================================================
   MOBILE BURGER NAV  (visible < 768px, replaces .side-menu)
   --------------------------------------------------------------------- */

/* Bouton burger en haut à droite — hors flux, fixed.
   Caché par défaut, montré uniquement < 768px par la cascade plus bas. */
.burger {
  position: fixed;
  top: max(14px, env(safe-area-inset-top, 0));
  right: max(14px, env(safe-area-inset-right, 0));
  z-index: var(--z-nav-burger);  /* 150 — navigation, sous modales (1000) pour pas bloquer */
  width: 48px;
  height: 48px;
  display: none;             /* affiché en mobile via la cascade */
  align-items: center;
  justify-content: center;
  background: var(--glass-sheen), var(--glass-chip);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
          backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  border: 1px solid var(--glass-line);
  box-shadow: var(--glass-highlight);
  border-radius: 50%;
  cursor: pointer;
  transition: background .2s, border-color .2s;
}
.burger:hover { background: var(--glass-sheen), var(--glass-chip-hover); border-color: var(--accent); }
.burger__lines {
  position: relative;
  width: 20px;
  height: 14px;
}
.burger__lines span {
  position: absolute;
  left: 0;
  width: 100%;
  height: 2px;
  background: var(--ink);
  border-radius: 1px;
  transition: transform .25s cubic-bezier(.7, 0, .3, 1), opacity .15s;
}
.burger__lines span:nth-child(1) { top: 0; }
.burger__lines span:nth-child(2) { top: 6px; }
.burger__lines span:nth-child(3) { top: 12px; }
.burger.is-open .burger__lines span:nth-child(1) { transform: translateY(6px) rotate(45deg); }
.burger.is-open .burger__lines span:nth-child(2) { opacity: 0; }
.burger.is-open .burger__lines span:nth-child(3) { transform: translateY(-6px) rotate(-45deg); }

/* Overlay plein écran */
.mobile-nav {
  position: fixed;
  inset: 0;
  z-index: var(--z-nav-overlay);  /* 180 — drawer mobile, sous modales */
  display: flex;
  flex-direction: column;
  background: var(--glass-noise-soft) rgba(10, 10, 12, 0.90);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
          backdrop-filter: blur(var(--glass-blur)) saturate(var(--glass-sat));
  padding:
    max(96px, calc(env(safe-area-inset-top, 0) + 80px))
    max(24px, env(safe-area-inset-right, 0))
    max(40px, env(safe-area-inset-bottom, 0))
    max(24px, env(safe-area-inset-left, 0));
  opacity: 0;
  visibility: hidden;
  transform: translateY(-12px);
  transition: opacity .35s ease, transform .35s ease, visibility 0s linear .35s;
  overflow-y: auto;
  -webkit-overflow-scrolling: touch;
}
.mobile-nav.is-open {
  opacity: 1;
  visibility: visible;
  transform: translateY(0);
  transition: opacity .35s ease, transform .35s ease, visibility 0s linear 0s;
}
.mobile-nav__list {
  list-style: none;
  display: flex;
  flex-direction: column;
  gap: 4px;
}
.mobile-nav__item {
  display: flex;
  align-items: baseline;
  gap: 18px;
  padding: 16px 8px;
  min-height: 56px;
  font-family: var(--display);
  font-size: clamp(22px, 6vw, 32px);
  letter-spacing: -0.01em;
  text-transform: uppercase;
  color: var(--ink);
  border-bottom: 1px solid rgba(238, 234, 224, 0.08);
  cursor: pointer;
  transition: color .2s, padding-left .25s;
}
.mobile-nav__item:hover,
.mobile-nav__item.is-active {
  color: var(--accent);
  padding-left: 18px;
}
.mobile-nav__item .num {
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.2em;
  color: var(--ink-mute);
  text-transform: uppercase;
  min-width: 30px;
}
.mobile-nav__item.is-active .num { color: var(--accent); }
.mobile-nav__foot {
  margin-top: auto;
  padding-top: 32px;
  font-family: var(--mono);
  font-size: 11px;
  letter-spacing: 0.18em;
  text-transform: uppercase;
  color: var(--ink-mute);
  line-height: 1.7;
}
.mobile-nav__foot a {
  color: var(--accent);
  text-decoration: none;
  display: inline-block;
  padding: 6px 0;
  min-height: 44px;
}

/* Lock body scroll when mobile nav is open (JS toggles .nav-open on body) */
body.nav-open { overflow: hidden; }

/* =====================================================================
   RESPONSIVE CASCADE — tablette → mobile → micro-mobile → paysage
   --------------------------------------------------------------------- */

/* ---- Tablette portrait (1024px) ---- */
@media (max-width: 1024px) {
  :root {
    --pad-x: clamp(20px, 4vw, 32px);
    --section-y: clamp(64px, 9vw, 110px);
  }
  .photo-cat__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

/* ---- Tablette portrait étroite & gros téléphone (768px) ----
   Bascule majeure : burger menu, layout 1-col, nav simplifiée. */
@media (max-width: 768px) {
  :root {
    --pad-x: 20px;
    --section-y: clamp(56px, 14vw, 90px);
  }

  /* Burger active */
  .burger { display: flex; }

  /* Nav hero : on cache TOUT sauf le badge live (déplacé en haut à gauche).
     Le burger remplace la nav. Le logo central reste géré par .brand. */
  .hero__nav { padding: 14px 16px; font-size: 11px; }
  .hero__nav-l a:not(.live) { display: none; }
  .hero__nav-r { display: none; }
  .hero__nav .live { font-size: 12px !important; }

  /* Hauteur fiable iOS (svh exclut barre du navigateur) */
  .hero {
    min-height: 100svh;
    height: 100svh;
  }
  .hero__grid { display: none; }
  .hero__display { font-size: clamp(40px, 12vw, 80px); bottom: 140px; }
  .hero__foot {
    grid-template-columns: 1fr;
    gap: 8px;
    bottom: max(20px, env(safe-area-inset-bottom, 0));
    padding-right: 60px;       /* place pour le burger */
  }
  .hero__foot .col:nth-child(n+2) { display: none; }
  .hero__cta { justify-self: start; grid-column: 1 / -1; }

  /* "Scroll pour révéler" — sur mobile, à droite ET au-dessus du foot
     (Direction / Franck Marchand) pour éviter que la barre du hint ne
     morde sur le nom à gauche. Le décalage vertical = hauteur du foot
     (~56px label+valeur) + petit gap. */
  .hero__hint {
    left: auto;
    right: 20px;
    bottom: calc(max(20px, env(safe-area-inset-bottom, 0)) + 70px);
    transform: none;
    text-align: right;
  }

  /* Brand block — recentré dans la zone sans burger */
  .brand__logo { width: 200px; height: 200px; }
  .brand__title { font-size: 34px; }
  .brand { --y-start: calc(50svh - 130px); }

  /* Marquee : un peu plus rapide visuellement, gap réduit */
  .marquee__track { font-size: clamp(30px, 10vw, 54px); gap: 28px; }

  /* Manifeste */
  .manifeste { padding: 60px 20px; }
  .manifeste__txt { font-size: clamp(20px, 5.4vw, 32px); line-height: 1.25; }
  .manifeste__meta { grid-template-columns: 1fr 1fr; gap: 20px; }
  .manifeste__meta .col { font-size: 13px; }

  /* Portfolio */
  .portfolio { --portfolio-pad-x: 20px; padding: 60px var(--portfolio-pad-x); }
  .portfolio__head {
    grid-template-columns: 1fr;
    gap: 18px;
    /* Full-bleed : compense le padding horizontal de .portfolio ci-dessus
       (+ notch éventuel). La règle de base ne compense que les safe-areas
       car la section n'a AUCUN padding-x en desktop — en dessous de 768px
       le padding 20px (16px ≤480) laissait des bandes noires de part et
       d'autre du head. La var est redéfinie à 16px dans la media 480. */
    margin-left:  calc(-1 * var(--portfolio-pad-x) - env(safe-area-inset-left, 0px));
    margin-right: calc(-1 * var(--portfolio-pad-x) - env(safe-area-inset-right, 0px));
  }
  /* Gap 12px : les 5 filtres texte tiennent sur une ligne à 375px
     (263px de boutons + 4×12px = 311px ≤ 343px utiles). Retour à la
     ligne seulement sous ~330px. */
  .portfolio__filters { flex-wrap: wrap; gap: 4px 12px; }
  .portfolio__filters .filter-btn { min-height: 44px; padding: 8px 6px; }
  .portfolio__grid,
  .portfolio__grid--3col,
  .portfolio__grid--editorial { grid-template-columns: 1fr; gap: 18px; }
  .portfolio__grid--editorial .card { grid-column: auto !important; }

  /* Services */
  .services { padding: 60px 20px; }
  .section__head { grid-template-columns: 1fr; gap: 14px; }
  .svc-row { grid-template-columns: 40px 1fr; gap: 14px; padding: 20px 0; }
  .svc-row--toggle { grid-template-columns: 40px 1fr auto; }
  .svc-row__desc { font-size: 13px; opacity: 0.85; }

  /* Team — sur mobile on NE garde PAS tout sur une seule ligne (4 colonnes
     ultra-étroites → noms qui se cassent lettre par lettre). On bascule en
     grille à 2 colonnes qui passe à la ligne. */
  .team { padding: 60px 20px; }
  .team__grid {
    grid-auto-flow: row;
    grid-template-columns: repeat(2, minmax(0, 1fr));
    grid-auto-columns: auto;
    gap: 4px;
  }
  .team-card { padding: 26px 20px; gap: 12px; }
  .team-card__role { letter-spacing: 0.12em; overflow-wrap: break-word; }
  .team-card__name { font-size: clamp(17px, 8.5cqw, 34px); }

  /* Clients */
  .clients { grid-template-columns: 1fr; gap: 18px; padding: 40px 20px; }
  .clients__label { max-width: 100%; }
  .clients__strip { font-size: 22px; gap: 36px; }

  /* Awards */
  .awards { padding: 60px 20px; }
  .award { grid-template-columns: 50px 1fr 30px; gap: 10px; font-size: 13px; padding: 14px 0; }
  .award__fest, .award__cat { display: none; }
  .award__title { font-size: 14px; }

  /* News + Tests */
  .news, .tests { padding: 60px 20px; }
  .news__grid, .tests__grid { grid-template-columns: 1fr; gap: 20px; }

  /* Contact */
  .contact { grid-template-columns: 1fr; gap: 32px; padding: 60px 20px; }
  .contact__lead { font-size: clamp(36px, 9vw, 56px); }
  .contact__details { grid-template-columns: 1fr 1fr; gap: 20px; }
  .contact__form { padding: 28px 20px; }

  /* Brief form : champs full-width, touch-friendly, anti-zoom */
  .field input, .field textarea, .field select {
    min-height: 48px;
    padding: 12px 4px;
    font-size: 16px;        /* anti-zoom iOS */
  }
  .field textarea { min-height: 120px; padding: 12px 4px; }
  .field-row { grid-template-columns: 1fr; gap: 16px; }
  .chips { gap: 8px; }
  .chip { min-height: 44px; padding: 10px 14px; font-size: 14px; }
  .submit-btn { width: 100%; min-height: 56px; font-size: 16px; }

  /* Footer */
  .footer { padding: 50px 20px 30px; }
  .footer__top { grid-template-columns: 1fr; gap: 28px; }
  .footer__brand { font-size: 34px; }
  .footer__col h4 { margin-bottom: 10px; }
  .footer__col a {
    display: block;
    padding: 8px 0;
    min-height: 44px;
    line-height: 1.5;
  }
  .footer__bottom {
    flex-direction: column;
    gap: 8px;
    text-align: center;
    font-size: 11px;
    padding-bottom: max(20px, env(safe-area-inset-bottom, 0));
  }

  /* Side menu : déjà caché par sa propre règle, mais on désactive le shift.
     `0px` (pas `0`) — sinon `calc(50% - 0)` mélange % et number, devient
     invalide et le navigateur calcule `left` à 0 → logo collé à gauche. */
  body.menu-active { --menu-shift: 0px; padding-right: 0; }
}

/* ---- Petit smartphone (480px) ---- */
@media (max-width: 480px) {
  :root {
    --pad-x: 16px;
    --section-y: clamp(48px, 14vw, 80px);
  }

  /* Hero */
  .hero__nav { padding: 12px 14px; }
  .hero__display { font-size: clamp(34px, 11vw, 60px); bottom: 120px; }
  .brand__logo { width: 170px; height: 170px; }
  .brand__title { font-size: 28px; }
  .brand { --y-start: calc(50svh - 110px); }

  /* Marquee : trop bruyant, on la masque pour libérer du flux vertical */
  .marquee { display: none; }

  /* Manifeste */
  .manifeste { padding: 44px 16px; }
  .manifeste__txt { font-size: clamp(18px, 5.4vw, 26px); }
  .manifeste__meta .col strong { font-size: 16px !important; }

  /* Portfolio — la marge négative full-bleed du head (media 768) suit via
     --portfolio-pad-x, donc padding et compensation restent synchronisés. */
  .portfolio { --portfolio-pad-x: 16px; padding: 44px var(--portfolio-pad-x); }
  .card__body { padding: 14px 16px; }
  .card__title { font-size: clamp(16px, 4.4vw, 20px); }

  /* Photo — le titre "PHOTOGRAPHIQUE" (14 lettres uppercase) débordait à 40px
     sous ~440px de viewport. On réduit pour qu'il rentre proprement. */
  .photo-section__title { font-size: clamp(24px, 7vw, 36px); }

  /* Services / News / Tests / Team / Awards / Contact / Footer */
  .services, .team, .awards, .news, .tests { padding: 44px 16px; }
  .contact { padding: 44px 16px; }
  .footer { padding: 40px 16px 28px; }
  .footer__brand { font-size: 28px; }

  /* Photo */
  .photo-cat__grid { grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 6px; }

  /* Awards */
  .award { grid-template-columns: 44px 1fr 26px; font-size: 12px; }

  /* Contact details : 1 col */
  .contact__details { grid-template-columns: 1fr; }

  /* Section heads */
  .section__head .title { font-size: clamp(34px, 10vw, 56px); }
  .section__head .num { font-size: 12px; }
  .section__head .sub { font-size: 13px; }
}

/* ---- Micro-mobile (360px et moins) ---- */
@media (max-width: 360px) {
  :root {
    --pad-x: 14px;
    --section-y: 44px;
  }

  .hero__display { font-size: clamp(30px, 11vw, 48px); bottom: 110px; }
  .brand__logo { width: 150px; height: 150px; }
  .brand__title { font-size: 24px; }
  .brand { --y-start: calc(50svh - 100px); }

  .manifeste__txt { font-size: clamp(17px, 5.8vw, 22px); }
  .manifeste__meta { grid-template-columns: 1fr; gap: 14px; }

  .footer__brand { font-size: 24px; }

  .portfolio__filters .filter-btn { padding: 8px 10px; font-size: 11px; }
  .chip { padding: 10px 12px; font-size: 13px; }
  .contact__lead { font-size: clamp(30px, 9vw, 44px); }
}

/* ---- Paysage smartphone (hauteur très réduite) ---- */
@media (orientation: landscape) and (max-height: 500px) and (max-width: 1024px) {
  .hero { min-height: 100svh; height: 100svh; }
  .hero__display { font-size: clamp(28px, 7vw, 44px); bottom: 80px; }
  .hero__foot { bottom: 12px; }
  .brand__logo { width: 130px; height: 130px; }
  .brand__title { font-size: 22px; }
  .brand { --y-start: calc(50svh - 90px); }

  .manifeste, .portfolio, .services, .team, .awards, .news, .tests, .contact,
  .footer { padding-top: 36px; padding-bottom: 36px; }
}

/* =====================================================================
   COOKIE BANNER — mobile
   --------------------------------------------------------------------- */
@media (max-width: 640px) {
  .lcf-cb__inner {
    flex-direction: column;
    align-items: stretch !important;
    gap: 14px !important;
    padding: 16px !important;
    padding-bottom: max(16px, env(safe-area-inset-bottom, 0)) !important;
  }
  .lcf-cb__actions {
    flex-direction: column-reverse !important;  /* "Tout refuser" en premier */
    gap: 8px !important;
  }
  .lcf-cb-btn {
    width: 100%;
    min-height: 48px !important;
    font-size: 14px !important;
  }
  .lcf-cb__title { font-size: 13px !important; }
  .lcf-cb__text  { font-size: 12.5px !important; line-height: 1.5; }

  /* Modal de personnalisation : plein écran sur mobile */
  .lcf-cm__panel {
    width: 100% !important;
    max-width: 100% !important;
    height: 100svh !important;
    max-height: 100svh !important;
    border-radius: 0 !important;
    padding-top: max(24px, env(safe-area-inset-top, 0)) !important;
    padding-bottom: max(24px, env(safe-area-inset-bottom, 0)) !important;
    overflow-y: auto;
    -webkit-overflow-scrolling: touch;
  }
  .lcf-cm__foot {
    flex-direction: column !important;
    gap: 8px !important;
  }
  .lcf-cm__foot-r {
    flex-direction: column !important;
    width: 100%;
    gap: 8px !important;
  }
  .lcf-cm__foot-r .lcf-cb-btn { width: 100%; }
}

/* =====================================================================
   TWEAKS PANEL — désactivé sur mobile (le panel est trop large pour
   l'écran et n'apporte rien aux visiteurs réels).
   --------------------------------------------------------------------- */
@media (max-width: 768px) {
  .twk-panel { display: none !important; }
}

/* ====================================================================
   APPARENCE — densité + palette claire (admin "Apparence")
   ==================================================================== */

/* Densité — multiplie les paddings verticaux des sections.
   Aucune classe = densité par défaut (équivalente à "regular"). */
body.density-compact      { --section-y: clamp(56px, 8vw, 112px); }
body.density-regular      { --section-y: clamp(80px, 11vw, 160px); } /* défaut */
body.density-comfortable  { --section-y: clamp(110px, 15vw, 220px); }

/* Palette claire — bascule les couleurs principales en mode jour.
   On garde le contraste lisible et on ne touche pas aux accents média. */
body.palette-light {
  --bg:        #f6f4ef;
  --bg-elev:   #ffffff;
  --ink:       #1a1a1a;
  --ink-soft:  #444;
  --ink-mute:  #888;
  --line:      rgba(0, 0, 0, 0.10);
  --line-str:  rgba(0, 0, 0, 0.28);
}
body.palette-light .grain { opacity: 0.04; }


/* ====================================================================
   IMAGES D'EN-TÊTE — Team / Awards / News
   ---------------------------------------------------------------------
   Apparence par défaut : pas de bg image (comportement actuel inchangé).
   Quand l'utilisateur uploade une image depuis l'admin, site-content.js
   ajoute `body.has-team-head` / `has-awards-head` / `has-news-head`,
   ce qui active le full-bleed + l'image avec focal point + gradients.
   ==================================================================== */
body.has-team-head .team > .section__head,
body.has-awards-head .awards > .section__head,
body.has-news-head .news > .section__head {
  position: relative;
  margin-left:  calc(var(--pad-x) * -1);
  margin-right: calc(var(--pad-x) * -1);
  margin-top:   calc(var(--section-y) * -1);
  padding: clamp(90px, 14vw, 160px) var(--pad-x) clamp(48px, 6vw, 72px);
  margin-bottom: clamp(40px, 5vw, 64px);
  isolation: isolate;
  overflow: hidden;
  background-color: var(--bg);
}
/* Voile gradients sur ::after — opacité contrôlable */
body.has-team-head .team > .section__head::after,
body.has-awards-head .awards > .section__head::after,
body.has-news-head .news > .section__head::after {
  content: "";
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
  /* Couches (du dessus vers le dessous) :
     0. Ombres internes haut/bas (noir → transparent sur ~60px) — léger
        effet 3D : l'image paraît en retrait derrière les bords.
     1. Fade vertical haut + bas vers var(--bg) — adoucit le parallax.
     2. Fade horizontal — sombre à gauche pour lisibilité texte.
     3. Voile vertical sombre — vignette en bas. */
  background-image:
    linear-gradient(to bottom, rgba(0,0,0,0.42) 0px, rgba(0,0,0,0) var(--head-shadow-top, 68px)),
    linear-gradient(to top, rgba(0,0,0,0.32) 0px, rgba(0,0,0,0) var(--head-shadow-bottom, 52px)),
    linear-gradient(to bottom, var(--bg) 0%, rgba(13,13,14,0) 14%, rgba(13,13,14,0) 86%, var(--bg) 100%),
    linear-gradient(to right, var(--bg) 0%, rgba(13,13,14,0.85) 30%, rgba(13,13,14,0.25) 70%, rgba(13,13,14,0) 100%),
    linear-gradient(to bottom, rgba(13,13,14,0.15) 0%, rgba(13,13,14,0.10) 50%, rgba(13,13,14,0.55) 100%);
  background-repeat: no-repeat, no-repeat, no-repeat, no-repeat, no-repeat;
  background-size: 100% 100%, 100% 100%, 100% 100%, 100% 100%, 100% 100%;
  background-position: 0% 0%, 0% 0%, 0% 0%, 0% 0%, 0% 0%;
}
body.has-team-head .team > .section__head::after   { opacity: var(--team-head-overlay-opacity, 1); }
body.has-awards-head .awards > .section__head::after { opacity: var(--awards-head-overlay-opacity, 1); }
body.has-news-head .news > .section__head::after   { opacity: var(--news-head-overlay-opacity, 1); }
/* Prix : le BAS de la photo d'en-tête se fond dans le fond SOMBRE de la
   scène néon (raccord invisible avec la roulette de lauriers). */
body.has-awards-head .awards > .section__head::after {
  background-image:
    linear-gradient(to bottom, rgba(0,0,0,0.42) 0px, rgba(0,0,0,0) 68px),
    linear-gradient(to right, var(--bg) 0%, rgba(13,13,14,0.85) 30%, rgba(13,13,14,0.25) 70%, rgba(13,13,14,0) 100%),
    linear-gradient(to bottom, var(--bg) 0%, rgba(13,13,14,0) 16%, rgba(13,13,14,0) 50%, rgba(13,13,14,0.85) 84%, #0d0d0e 100%);
}
/* Image dans pseudo ::before pour permettre transform:scale (zoom) */
body.has-team-head .team > .section__head::before,
body.has-awards-head .awards > .section__head::before,
body.has-news-head .news > .section__head::before {
  content: "";
  position: absolute;
  /* Débordement vertical = amplitude parallax + marge (cf. .portfolio__head::before).
     Team/Awards/News utilisent useHeadParallax → translate ±220px (MAX_TRAVEL),
     donc le fallback 220px du var couvre les trois. */
  top: calc(-1 * (var(--head-parallax-travel, 220px) + 24px));
  bottom: calc(-1 * (var(--head-parallax-travel, 220px) + 24px));
  left: 0;
  right: 0;
  z-index: -1;
  background-repeat: no-repeat;
  background-size: cover;
}
/* translate3d + scale combinés : --parallax-y est posée par le useEffect
   de chaque composant ; safe à 0px si pas de JS. */
body.has-team-head .team > .section__head::before {
  background-image: var(--team-head-bg, none);
  background-position: var(--team-head-focal, 50% 50%);
  transform: translate3d(0, var(--parallax-y, 0px), 0) scale(var(--team-head-zoom, 1));
  transform-origin: var(--team-head-focal, 50% 50%);
  will-change: transform;
}
body.has-awards-head .awards > .section__head::before {
  background-image: var(--awards-head-bg, none);
  background-position: var(--awards-head-focal, 50% 50%);
  transform: translate3d(0, var(--parallax-y, 0px), 0) scale(var(--awards-head-zoom, 1));
  transform-origin: var(--awards-head-focal, 50% 50%);
  will-change: transform;
}
body.has-news-head .news > .section__head::before {
  background-image: var(--news-head-bg, none);
  background-position: var(--news-head-focal, 50% 50%);
  transform: translate3d(0, var(--parallax-y, 0px), 0) scale(var(--news-head-zoom, 1));
  transform-origin: var(--news-head-focal, 50% 50%);
  will-change: transform;
}

/* ====================================================================
   TITRES DES HEADS À IMAGE — ancrés en bas à GAUCHE
   --------------------------------------------------------------------
   Même position que le head La vidéo : numéro en petit au-dessus du
   titre, pile en colonne alignée à gauche, posée au bas du bandeau.
   Remplace la grille 100px + 1fr du .section__head générique (qui
   mettait le numéro à gauche du titre, plus haut dans le bandeau). */
.services > .section__head,
body.has-team-head .team > .section__head,
body.has-awards-head .awards > .section__head,
body.has-news-head .news > .section__head {
  display: flex;
  flex-direction: column;
  justify-content: flex-end;
  align-items: flex-start;
  gap: 18px;
}

/* ====================================================================
   FIX z-index : texte des heads doit rester AU-DESSUS du voile (::after)
   ==================================================================== */
.services > .section__head > *,
.portfolio__head > *,
.photo-section__head > *,
body.has-team-head .team > .section__head > *,
body.has-awards-head .awards > .section__head > *,
body.has-news-head .news > .section__head > * {
  position: relative;
  z-index: 1;
}
/* Filtres portfolio (situés sous le head visuellement, mais aussi dans .portfolio
   au même niveau que __head) — ils doivent passer au-dessus de l'image pour rester
   cliquables. */
.portfolio__filters,
.portfolio__grid {
  position: relative;
  z-index: 1;
}

/* ====================================================================
   AUDIT RESPONSIVE — corrections mobile pour features récentes
   ==================================================================== */

/* ── Collaborateurs (public) : -40% sur mobile (taille texte/avatars/spacing) ── */
@media (max-width: 640px) {
  .collabs { padding: clamp(28px, 7vw, 48px) var(--pad-x); }
  .collabs__head { margin-bottom: 16px; }
  .collabs__label { font-size: 10px; letter-spacing: 0.15em; }
  .collabs__label .italic-serif { font-size: 22px; line-height: 1; margin-left: 4px; }
  .collabs__list {
    grid-template-columns: 1fr;  /* une seule colonne */
    gap: 6px;
  }
  .collabs__item {
    gap: 10px;
    padding: 6px 0;
  }
  .collabs__avatar { width: 32px; height: 32px; }
  .collabs__avatar--initials { font-size: 10px; }
  .collabs__name { font-size: 13px; }
  .collabs__role { font-size: 9px; letter-spacing: 0.12em; margin-top: 2px; }
  .collabs__handle { font-size: 12px; }
  /* Filtre : passe pleine largeur sous le label */
  .collabs__head { align-items: stretch; }
  .collabs__filter { width: 100%; flex-direction: column; align-items: flex-start; gap: 6px; }
  .collabs__select-wrap { width: 100%; }
  .collabs__select { width: 100%; min-width: 0; }
  /* Repli : ~2 lignes en 1 colonne (avatars 32px) */
  .collabs__list--collapsed { max-height: 96px; }
  .collabs__toggle { width: 100%; justify-content: center; margin-top: 16px; }
}

/* ── Clients carrousel : padding/logo réduits sur mobile ── */
@media (max-width: 640px) {
  .clients { padding: clamp(32px, 7vw, 52px) 0; }
  .clients__label { padding: 0 var(--pad-x); margin-bottom: 18px; }
  .clients__logo { padding-right: 32px; }
  .clients__logo--img { height: 40px; }
  .clients__logo--img img { max-width: 110px; }
  .clients__strip { padding: 18px 0; }
}

/* ── Project modal : galerie plus serrée sur mobile, padding hero réduit ── */
@media (max-width: 640px) {
  .project-modal__gallery-grid {
    grid-template-columns: repeat(auto-fill, minmax(120px, 1fr));
    gap: 6px;
  }
  .project-modal__media { aspect-ratio: 16 / 10; }
}

/* ── News modal : pareil + body padding réduit ── */
@media (max-width: 640px) {
  .news-modal__gallery-grid {
    grid-template-columns: repeat(auto-fill, minmax(120px, 1fr));
    gap: 6px;
  }
  .news-modal__lead { font-size: 16px; }
  .news-modal__para { font-size: 15px; line-height: 1.65; }
}

/* ── News card mobile : cover plus compacte, body plus tassé ── */
@media (max-width: 640px) {
  .news-card { min-height: 0; }
  .news-card__cover { aspect-ratio: 16 / 9; }
  .news-card__body { padding: 18px 20px 22px; gap: 10px; }
  .news-card__title { font-size: 18px; }
  .news-card__excerpt { font-size: 13px; }
}

/* ── Section heads images : sur mobile, parallax + zoom restent OK mais
       on s'assure que les paddings ne mangent pas tout l'écran ── */
@media (max-width: 640px) {
  .services > .section__head,
  .portfolio__head,
  .photo-section__head,
  body.has-team-head .team > .section__head,
  body.has-awards-head .awards > .section__head,
  body.has-news-head .news > .section__head {
    padding-top: clamp(60px, 22vw, 110px);
    padding-bottom: clamp(28px, 6vw, 48px);
  }
}

/* ── Section heads texte : .num peut déborder sur 320px ── */
@media (max-width: 360px) {
  .section__head .title,
  .photo-section__title { font-size: clamp(30px, 11vw, 50px); }
}

/* ── Project lightbox : flèches latérales plus petites pour 320px ── */
@media (max-width: 480px) {
  .project-lightbox { padding: 50px 8px; }
  .project-lightbox__nav { width: 38px; height: 38px; font-size: 22px; }
  .project-lightbox__nav--prev { left: 8px; }
  .project-lightbox__nav--next { right: 8px; }
  .project-lightbox__close { top: 12px; right: 12px; width: 38px; height: 38px; }
  .project-lightbox__counter { bottom: 14px; font-size: 11px; padding: 4px 10px; }
}

/* ── Manifeste : sur très petits écrans, les swatches sont déjà clamp(80px, 9vw, 140px),
       on les réduit encore un poil pour 320px pour éviter qu'ils dominent le texte ── */
@media (max-width: 360px) {
  .manifeste__txt .swatch {
    width: clamp(60px, 14vw, 90px);
    height: clamp(36px, 8vw, 54px);
    margin: 0 4px;
  }
}

/* ====================================================================
   OPTIMISATIONS TACTILE (iPad / smartphone)
   --------------------------------------------------------------------
   Allège le compositing GPU pour un scroll fluide. Les parallaxes et le
   smooth-scroll Lenis sont DÉJÀ désactivés en JS sur (pointer: coarse).
   Ici on réduit les effets de rendu les plus coûteux sur GPU mobile.
   ==================================================================== */
@media (hover: none) {
  /* Flou de verre réduit (18px -> 10px) sur toutes les surfaces "glass". */
  :root { --glass-blur: 10px; }

  /* Plus de backdrop-filter sur les overlays PLEIN ÉCRAN (pire cas GPU
     mobile). Le fond semi-opaque suffit : on l'opacifie un peu pour
     compenser l'absence de flou. */
  .photo-lightbox,
  .project-lightbox,
  .mobile-nav {
    -webkit-backdrop-filter: none !important;
            backdrop-filter: none !important;
  }
  .photo-lightbox,
  .project-lightbox { background: rgba(7, 7, 9, 0.96); }
  .mobile-nav { background: rgba(10, 10, 12, 0.97); }

  /* Grain décoratif : overlay fixed + mix-blend-mode = recomposition plein
     écran permanente. Inutile sur mobile → coupé. */
  .grain { display: none; }

  /* Ombre interne large de la vitre Services : repaint moins large. */
  .services__glass { box-shadow: inset 0 0 60px rgba(0, 0, 0, 0.2); }

  /* Halo flou du hero allégé (40px -> 22px). */
  .hero__glow { -webkit-filter: blur(22px); filter: blur(22px); }

  /* Section "Ce qu'on fait" : le filtre SVG #svc-smear sur une grande image
     est LENT à rendre sur GPU mobile (rendu logiciel) → la photo mettait du
     temps à apparaître. On le remplace par un flou natif (composité GPU,
     quasi instantané). Rendu quasi identique : le smear actuel (10/8) est
     déjà presque isotrope. */
  .services__photo {
    -webkit-filter: blur(7px) saturate(1.22) brightness(1.12);
            filter: blur(7px) saturate(1.22) brightness(1.12);
  }
}

/* ---------- Bascule de langue FR / EN ---------- */
.lang-toggle {
  font-family: var(--mono); font-size: 11px; letter-spacing: 0.14em;
  background: none; border: 1px solid var(--line); border-radius: 999px;
  color: var(--ink-soft); padding: 6px 12px; cursor: pointer;
  display: inline-flex; align-items: center; gap: 5px;
  transition: border-color .2s, color .2s, background .2s;
}
.lang-toggle:hover { border-color: var(--accent); color: var(--ink); }
.lang-toggle .is-on { color: var(--accent); font-weight: 700; }
.lang-toggle__sep { opacity: 0.4; }
