# Genesis Starter — guide d’intégration (référence agent)

Ce document est **la référence unique** pour écrire du SCSS/HTML/Twig/JS sur ce thème, et pour **convertir** un composant Osmo / une image / un bloc fourni par le designer.

Lis d’abord **§0 (comment travailler ici)** et **§8 (convertir Osmo / images)**. Le reste = tokens & conventions.

---

## 0. Comment utiliser le thème en place

### 0.1 Stack

| Couche | Où | Rôle |
| --- | --- | --- |
| WordPress + Timber | `templates/*.twig`, `functions.php`, `inc/` | Pages Twig, contexte ACF |
| ACF Flexible | `acf-json/`, `templates/flexibles.twig` | Blocs de page (`block-*`) |
| Vite | `vite/` | SCSS + JS (dev HMR / build `dist`) |
| Lenis + GSAP + Barba | `vite/js/` | Smooth scroll, anims, transitions page |
| Design tokens | `vite/scss/` + `USAGE.md` | Couleurs, spaces, typo, grille |

- Dev : `cd vite && npm run dev` + `define('ENV_DEV', true);` dans `wp-config.php`
- Prod : `npm run build` → assets dans `vite/dist`

### 0.2 Anatomie d’un bloc (le modèle à copier)

Pour **chaque** nouveau bloc `block-foo` :

1. **Twig** — `templates/blocks/block-foo.twig`  
   - Racine BEM `.block-foo`  
   - Padding section via ACF `setting_section` + `macros.section_classes()`  
   - Typo **uniquement** via classes `.text-*` + `.font-*` dans le Twig  
   - Médias via `parts/media.twig` (jamais une `<img>` brute si le composant Media ACF existe)

2. **SCSS** — `vite/scss/blocks/_block-foo.scss`  
   - Commence par `@use '../utils' as *;`  
   - Importé dans `vite/scss/style.scss`  
   - **Aucun** `font-size` ici — jamais

3. **ACF** — groupe `group_block_foo.json` qui clone `setting_section`, + layout dans `group_flexibles.json`

4. **JS** (si besoin) — module dans `vite/js/utils/`, branché dans `pageModules.js`  
   - Si le bloc n’est pas sur toutes les pages → gate `has('[data-…]', scope)` + `import()` dynamique  
   - Attributs Osmo `data-*` : **ne jamais renommer**

### 0.3 Espacements section vs gutters

- **Padding haut/bas de section** → utilities Twig / ACF (`p-t__xxl`, `p-b__xxl`, etc.)
- **Gutter horizontal / gaps internes** → SCSS `padding-inline: var(--space-gap)` ou `gap: var(--space-xs)`  
  Ne pas inventer des `p-x__*` pour coller à la grille 12 cols.

### 0.4 Animations déjà câblées (réutiliser, ne pas recréer)

| Effet | Markup | Module |
| --- | --- | --- |
| Reveal texte ligne/mots | `js-reveal="line"` (ou `words` / `chars` / `fade`) | `textReveal.js` |
| Reveal image clip-path | `data-media-reveal` sur le cadre media | `mediaReveal.js` |
| Parallax Osmo | `parts/media.twig` avec `parallax: true` → `data-parallax="trigger|target"` | `globalParallax.js` |
| Play/pause vidéo scroll | `macros.video_mp4_playpause` → `data-video="playpause"` | `playPauseVideo.js` |
| Mask section (banner) | `data-section-mask` + `data-section-mask-el` | `bannerMask.js` |
| Accordion Osmo | `data-accordion-css-init`, `data-accordion-toggle`, … | `accordionCss.js` |
| Filter Osmo | `data-filter-group`, `data-filter-target`, `data-filter-name` | `filterBasic.js` |
| Toggle switch Osmo | `data-toggle-init`, `data-toggle-btn`, `data-toggle-active` | `toggleSwitch.js` |
| Marquee draggable | `data-draggable-marquee-*` | `draggableMarquee.js` |
| Orbit tiles | `data-orbit-tiles-*` | `orbitTiles.js` |
| Tabs pin/scrub | `data-tabs="wrapper"` … | `tabsScroll.js` |
| Bunny HLS player | `parts/bunny-player.twig` + `data-bunny-player-init` | `bunnyPlayer.js` |
| Mini showreel | `data-mini-showreel-*` | `miniShowreel.js` |
| Modal découverte | `data-modal-*` + `data-discovery-*` | `modalBasic.js` |

**Replays scroll** (texte / media) : `toggleActions: play none none reset` — rejoue en descendant, reset en remontant au-dessus, **pas** en remontant depuis le bas.

### 0.5 Ce que l’agent doit faire quand on lui donne un fichier

| On te donne… | Tu fais… |
| --- | --- |
| Un **bloc Osmo** (HTML/CSS/JS) | §8 — convertir dans le kit, garder `data-*`, brancher le JS |
| Une **image** / media ACF | `parts/media.twig` (+ parallax / reveal si demandé) |
| Un **nouveau bloc page** | §0.2 + §7 — Twig + SCSS + ACF |
| Un **ajustement visuel** | Tokens (`--c-*`, `--space-*`) ; pas de hex/px en dur si un token existe |

---

## 1. Règles fermes (à respecter dans cet ordre)

1. **Aucun `font-size` hors de `_typo.scss`.** Interdit dans `blocks/`, `layout/`, `base/`, `librairie/`. Toute taille de texte passe **uniquement** par une classe `.text-*` dans le HTML/Twig (`.text-xxs` → `.text-xxxl`). Si une taille manque → l’ajouter dans `_typo.scss`.
2. **Aucune valeur en dur.** Couleur, espacement, breakpoint, ease, durée → variable / utility du kit. Sinon → ajouter le token au bon endroit.
3. **Une seule source de vérité par token.**
   - Couleurs : `_variables.scss` (`--c-*`)
   - Espacements : `_space.scss` → `--space-*` + `.p-*__*` / `.m-*__*`
   - Typographie : `_typo.scss` (`.text-*`)
   - Easings : `_ceaser.scss` (`$g-*`, `$c-*`, `$o-*`)
   - Breakpoints : `_media-queries.scss` (`@include sm` / `md` / `md-up` / `up()` / `down()`)
4. **BEM-lite** : `.block`, `.block__element`, `.block--modifier`. Un `_<block>.scss` par bloc.
5. **Utilities padding / margin en priorité** pour les sections. En SCSS seulement si contexte (hover, MQ).
6. **`fluid()`** pour dimensions non-texte uniquement — **jamais** pour du `font-size`.
7. **Media queries en `em`** via mixins — jamais `@media (max-width: 1200px)`.
8. **Grille** : `col-width($n)` / `.col-N` / `.u-w-N` — pas de `%` / `px` en dur pour les colonnes.
9. **Ne jamais casser `--space-gap`.**
10. **Ordre du barrel** `utils/_index.scss` intouchable.
11. **Un bloc = un fichier SCSS** + un `@use` dans `style.scss`.
12. **Osmo `data-*` : ne jamais renommer** (le JS cible ces attributs).

---

## 2. Installation SCSS

```scss
// style.scss
@use 'modern-normalize/modern-normalize.css';
@use 'utils';
@use 'base/rte';
@use 'layout/header';
@use 'blocks/block-foo';
```

Chaque partial projet :

```scss
@use '../utils' as *;
```

Personnalisation sans renommer les tokens : couleurs → `_variables.scss` ; fontes → `_font.scss` (garder `.font-title` / `.font-text` / `.font-text-bold`).

---

## 3. Ordre d’import (barrel)

`utils/_index.scss` : `mixin` → `media-queries` → `space` → `variables` → `ceaser` → `font` → `typo` → `grid` → `layout` → `layout-utils` → `space-utils` → `buttons` → `reset` → `librairie/index`

Ne rien réordonner.

---

## 4. Design tokens (référence)

### 4.1 Couleurs (`_variables.scss`)

| Token | Rôle |
| --- | --- |
| `--c-white`, `--c-black` | Fixes |
| `--c-gray-100` → `--c-gray-500` | Neutres |
| `--c-primary` | Accent |
| `--c-text`, `--c-bg` | Contextuels (inversés en `.is-dark`) |

Ajouter `.is-dark` / `data-theme-section="dark"` plutôt que `color: white` en dur.

### 4.2 Espacements (`_space.scss`)

| Token | Usage |
| --- | --- |
| `--space-xxxl` … `--space-xxs` | Échelle |
| `--space-md` | Gutter desktop (`--space-gap`) |

Utilities : `.<p|m>-<t|b|l|r|y|x>__<taille>` → ex. `p-t__xxl`, `m-b__sm`.

### 4.3 Typographie (`_typo.scss`)

| Classe | Usage |
| --- | --- |
| `.text-xxs` → `.text-xxxl` | Tailles |
| `.font-title` / `.font-text` / `.font-mono` | Familles |

```html
<h1 class="text-xxxl font-title">Titre</h1>
<p class="text-sm font-text">Lead</p>
```

### 4.4 Breakpoints

`@include sm` · `md` · `md-up` · `down(xl)` · `up(md)` — jamais de px bruts.

### 4.5 Easings

`$g-*` (GSAP) · `$c-*` (Ceaser) · `$o-*` (Osmo) · alias `$ease-smooth` / `$ease-out`.

### 4.6 Boutons

`.btn` · `.btn--ghost` · `.btn--dark` · `.btn--sm` / `.btn--lg`

---

## 5. Grille 12 colonnes

- `col-width($n)` en SCSS
- `.u-w-1` → `.u-w-12` + `.u-x-center` / `left` / `right`
- `.col-N` + `@md` / `@xl`…

Debug overlay : taper `grid` (dev) — `vite/js/utils/grid-overlay.js`.

---

## 6. Convention de classes

- Blocs : BEM-lite `.block-foo__media`
- Pas de Tailwind (`.mt-4`) ni classes orphelines (`.title`, `.wrapper`)
- Combiner librement : `class="block-foo__cta btn btn--ghost m-t__md text-xxs font-mono"`

---

## 7. Recette : créer un nouveau bloc

1. Nom kebab-case : `block-cards`
2. Twig `templates/blocks/block-cards.twig` (copier un bloc proche)
3. SCSS `vite/scss/blocks/_block-cards.scss` + `@use` dans `style.scss`
4. ACF group + layout flexible
5. Si anim Osmo → module JS + gate dans `pageModules.js`

Checklist Twig :

- [ ] `macros.section_classes(block.setting_section)`
- [ ] `data-theme-section` si le header doit changer de thème
- [ ] Textes en `.text-*` + `.font-*`
- [ ] Médias via `parts/media.twig`
- [ ] Reveals : `js-reveal="line"` / `data-media-reveal` si besoin

---

## 8. Convertir un composant Osmo / une image / un snippet

### 8.1 Workflow Osmo (ordre strict)

1. **Coller le HTML** dans le Twig du bloc (ou `parts/` si réutilisable).
2. **Garder tous les `data-*` Osmo tels quels** — le JS du thème les cible. Ne pas renommer `data-tabs`, `data-orbit-tiles-*`, `data-draggable-marquee-*`, etc.
3. **Renommer les classes CSS** en BEM projet (`.block-foo__…`) **sauf** si une librairie SCSS Osmo existe déjà dans `vite/scss/librairie/` (ex. `_orbit-tiles.scss`, `_bunny-player.scss`, `_mini-showreel.scss`) — dans ce cas on **réutilise** ces classes + on wrappe dans le bloc.
4. **Traduire le CSS** vers le kit :

| Origine | Remplacer par |
| --- | --- |
| `#hex` / `rgb()` | `var(--c-*)` |
| `padding` / `margin` fixes | `.p-*__*` / `.m-*__*` ou `var(--space-*)` |
| `font-size` | classe `.text-*` dans le Twig (**jamais** dans le SCSS du bloc) |
| `font-family` | `.font-title` / `.font-text` / `.font-mono` |
| `@media (max-width: …px)` | `@include sm` / `md` / `down()` |
| `cubic-bezier(...)` | `$g-*` / `$o-*` |
| largeurs `%` / `px` grille | `col-width(n)` / `.u-w-n` |

5. **JS** :
   - Si le comportement existe déjà → **réutiliser** le module (`pageModules.js`) — ne pas dupliquer.
   - Si nouveau script Osmo → `vite/js/utils/<nom>.js`, init scopée au container Barba, cleanup à la leave si besoin, gate `has('[data-…]')` + import dynamique si lourd.
6. **Tester** : desktop / `sm`, `.is-dark`, ouverture menu underlay (pas de replay d’anims), navigation Barba (ré-init OK).

### 8.2 Convertir / brancher une image (ou video)

Toujours passer par **`templates/parts/media.twig`** :

```twig
{% include 'parts/media.twig' with {
  media: block.media,          {# champs ACF group media #}
  variant: 'cover',            {# fit | viewport | cover #}
  eager: true,                 {# LCP / above the fold #}
  parallax: true,              {# data-parallax trigger/target #}
  parallax_start: 0,           {# cover banner : souvent 0 → 40 #}
  parallax_end: 40,
  parallax_scroll_start: 'top top'
} %}
```

| Besoin | Paramètre |
| --- | --- |
| Image dans une carte / ratio | `variant: 'fit'` + `media_ratio` ACF |
| Fond plein cadre | `variant: 'cover'` |
| Parallax scroll | `parallax: true` (+ start/end) |
| Reveal clip carré → plein | wrapper `data-media-reveal` autour |
| Picture responsive | `macros.picture(image, …)` (déjà dans `media.twig`) |

**Ne pas** :

- Mettre une `<img src="…">` hardcodée si le media vient d’ACF
- Désactiver le parallax (`parallax: false`) sur un hero cover sauf demande explicite
- Animer le wrapper pin / transform parent du parallax sans `pinType: 'transform'` (menu underlay translate `data-main`)

### 8.3 Exemple — Osmo brut → kit

Avant :

```html
<div class="feature">
  <h2 class="feature__heading">Titre</h2>
  <img src="photo.jpg" alt="">
</div>
```

```css
.feature { padding: 80px 40px; background: #0a0a0a; color: #fff; }
.feature__heading { font-size: 48px; margin-bottom: 16px; }
```

Après :

```twig
<section class="block-feature is-dark {{ macros.section_classes(block.setting_section) }}" data-theme-section="dark">
  <h2 class="block-feature__title text-xxl font-title m-b__xs" js-reveal="line">{{ block.title }}</h2>
  <div class="block-feature__media" data-media-reveal>
    {% include 'parts/media.twig' with { media: block.media, variant: 'cover', parallax: true } %}
  </div>
</section>
```

```scss
@use '../utils' as *;

.block-feature {
  // padding = utilities / ACF ; typo = .text-* ; fond = .is-dark
  &__media {
    position: relative;
    overflow: hidden;
    aspect-ratio: 16 / 9;
  }
}
```

### 8.4 Checklist agent (à cocher avant de dire « done »)

- [ ] Aucun `font-size` dans le SCSS du bloc
- [ ] Aucun hex/px « inventé » si un token existe
- [ ] `data-*` Osmo intacts
- [ ] Médias via `parts/media.twig`
- [ ] Reveals / parallax branchés si le design le montre
- [ ] Module JS listé dans `pageModules.js` (gate + destroy si besoin)
- [ ] OK mobile (`@include sm`) + thème dark/light header
- [ ] Pas de régression menu underlay / Barba

---

## 9. Librairies SCSS (`vite/scss/librairie/`)

Styles des deps JS / ressources Osmo déjà portées : Lenis, bunny-player, mini-showreel, orbit-tiles, accordion, modal, boutons, etc.

Nouveau partial → `@forward` dans `librairie/_index.scss`. Prefer **adapter** une lib existante plutôt que recopier le CSS Osmo dans le bloc.

---

## 10. Résumé « à ne pas casser »

- `--space-gap` et l’ordre du barrel
- Classes `.font-title` / `.font-text` / `.font-text-bold` / `.font-mono`
- Attributs `data-*` Osmo
- Un seul système de classes (pas de mélange Tailwind)
- Un bloc = un `_block-*.scss`
- Transitions page / menu : ne pas animer `data-main` ailleurs sans tenir compte du underlay nav
