# Mode d'édition inline Nimbus - Documentation technique
## 📋 Vue d'ensemble
Le mode d'édition Nimbus suit le concept WYSIWYG par blocs, inspiré de Notion, avec une **toolbar inline intégrée dans chaque bloc** plutôt qu'une barre fixe.
## 🎯 Concepts clés
### 1. Toolbar inline par bloc
Chaque bloc affiche sa propre toolbar au survol ou au focus:
- **Position**: Intégrée directement dans la ligne du bloc
- **Visibilité**: Apparaît au hover ou focus
- **Drag handle**: `⋮⋮` à gauche pour déplacer/ouvrir menu contextuel
### 2. Déclenchement du menu contextuel
Le menu "Add Block" s'ouvre de **3 façons**:
1. **Caractère "/"** - Frappe au début ou après espace
2. **Icône "⬇️"** - Clic sur bouton "More items"
3. **Drag handle** - Clic sur `⋮⋮` à gauche du bloc
### 3. États visuels
```
┌─────────────────────────────────────────────────────────┐
│ État par défaut (non focus, non hover) │
│ - Placeholder gris visible │
│ - Icônes cachées (opacity: 0) │
│ - Drag handle caché │
└─────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────┐
│ État hover (souris au dessus) │
│ - Background subtil (bg-neutral-800/30) │
│ - Icônes semi-visibles (opacity: 70%) │
│ - Drag handle visible │
└─────────────────────────────────────────────────────────┘
┌─────────────────────────────────────────────────────────┐
│ État focus (édition active) │
│ - Placeholder masqué │
│ - Icônes complètement visibles (opacity: 100%) │
│ - Drag handle visible │
│ - Curseur visible │
└─────────────────────────────────────────────────────────┘
```
## 🏗️ Architecture des composants
### BlockInlineToolbarComponent
**Fichier**: `src/app/editor/components/block/block-inline-toolbar.component.ts`
**Responsabilités**:
- Afficher le drag handle (⋮⋮) avec tooltip
- Afficher les icônes rapides (AI, checkbox, lists, table, etc.)
- Gérer les états hover/focus
- Émettre les actions vers le bloc parent
**Structure**:
```html
```
**Inputs**:
- `isFocused: Signal` - État focus du bloc
- `isHovered: Signal` - État hover du bloc
- `placeholder: string` - Texte du placeholder
**Outputs**:
- `action: EventEmitter` - Action déclenchée (use-ai, table, more, etc.)
### ParagraphBlockComponent (mis à jour)
**Fichier**: `src/app/editor/components/block/blocks/paragraph-block.component.ts`
**Nouvelles fonctionnalités**:
1. Intégration de `BlockInlineToolbarComponent`
2. Gestion des états `isFocused` et `isHovered` via signals
3. Détection du "/" pour ouvrir le menu
4. Gestion des actions de toolbar
**Template structure**:
```html
```
### BlockMenuComponent (optimisé)
**Fichier**: `src/app/editor/components/palette/block-menu.component.ts`
**Changements**:
- **Taille réduite**: 420px × 500px (vs 680px × 600px)
- **Position contextuelle**: S'ouvre près du bloc actif/curseur
- **Design compact**: Spacing réduit, textes plus petits
- **Sticky headers**: Restent visibles au scroll
**Positionnement**:
```typescript
menuPosition = computed(() => {
const activeBlock = document.querySelector('[contenteditable]:focus');
if (activeBlock) {
const rect = activeBlock.getBoundingClientRect();
return {
top: rect.top + 30, // 30px sous le curseur
left: rect.left // Aligné à gauche
};
}
return { top: 100, left: 50 }; // Fallback
});
```
## 🎨 Design tokens
### Toolbar inline
```css
/* Drag handle */
-left-8 /* Position absolue gauche */
opacity-0 /* Caché par défaut */
group-hover/block:opacity-100 /* Visible au hover */
/* Container */
px-3 py-2 /* Padding interne */
hover:bg-neutral-800/30 /* Background au hover */
rounded-lg /* Coins arrondis */
/* Icônes */
w-4 h-4 /* Taille icônes */
text-gray-400 /* Couleur par défaut */
hover:text-gray-200 /* Couleur au hover */
```
### Menu contextuel
```css
/* Panel */
bg-neutral-800/98 /* Background semi-transparent */
backdrop-blur-md /* Effet flou */
w-[420px] /* Largeur fixe */
max-h-[500px] /* Hauteur max */
rounded-lg /* Coins arrondis */
border-neutral-700 /* Bordure */
/* Section header (sticky) */
sticky top-0 /* Reste en haut au scroll */
bg-neutral-800/95 /* Background avec transparence */
backdrop-blur-md /* Flou de fond */
text-[10px] /* Texte très petit */
uppercase tracking-wider /* Majuscules espacées */
/* Item */
px-2 py-1.5 /* Padding compact */
hover:bg-neutral-700/80 /* Background hover */
text-sm /* Texte petit */
```
## 🔧 Intégration dans d'autres blocs
Pour ajouter la toolbar inline à un autre type de bloc:
### 1. Importer le composant
```typescript
import { BlockInlineToolbarComponent } from '../block-inline-toolbar.component';
import { signal } from '@angular/core';
@Component({
imports: [BlockInlineToolbarComponent],
// ...
})
```
### 2. Ajouter les signals
```typescript
isFocused = signal(false);
isHovered = signal(false);
```
### 3. Wrapper le contenu
```html
```
### 4. Gérer les événements
```typescript
onToolbarAction(action: string): void {
if (action === 'more' || action === 'menu') {
this.paletteService.open();
} else {
// Logique spécifique
}
}
```
## 📱 Responsive
### Desktop
- Drag handle à `-left-8` (32px à gauche)
- Toutes les icônes visibles
- Menu 420px de large
### Tablet
- Drag handle visible au tap
- Menu 90% de la largeur viewport
- Icônes réduites
### Mobile
- Drag handle toujours visible
- Menu plein écran
- Toolbar simplifiée (icônes essentielles seulement)
## ⌨️ Raccourcis clavier
### Dans un bloc
| Touche | Action |
|--------|--------|
| `/` | Ouvrir le menu contextuel |
| `@` | Mention (futur) |
| `Enter` | Nouveau bloc paragraphe |
| `Backspace` (bloc vide) | Supprimer le bloc |
| `↑` / `↓` | Naviguer entre blocs |
### Dans le menu
| Touche | Action |
|--------|--------|
| `↑` / `↓` | Naviguer dans les items |
| `Enter` | Sélectionner l'item |
| `Esc` | Fermer le menu |
| Lettres | Rechercher |
## 🚀 Améliorations futures
1. **Drag & drop** - Utiliser le drag handle pour réordonner
2. **Menu bloc contextuel** - Options spécifiques (dupliquer, supprimer, transformer)
3. **Formatage texte** - Bold, italic, couleur via toolbar flottante sur sélection
4. **Slash commands avancés** - `/table 3x3`, `/heading 2`, etc.
5. **Templates inline** - Insertion rapide de structures prédéfinies
6. **Collaboration** - Curseurs multiples et édition temps réel
## 📐 Schéma de flux
```
Utilisateur clique dans un bloc
↓
isFocused.set(true)
↓
Toolbar inline devient visible (opacity: 100%)
↓
Utilisateur tape "/"
↓
PaletteService.open()
↓
BlockMenuComponent s'affiche près du curseur
↓
Utilisateur sélectionne un item
↓
Nouveau bloc inséré après le bloc actuel
↓
Focus sur le nouveau bloc
```
---
**Version**: 2.0
**Date**: 7 novembre 2025
**Auteur**: Nimbus Team