# Structura — UX.md

> Livrable étape [2] — User stories, flows, wireframes textuels, interactions et états vides.
> Desktop only. Largeur min 1280px, optimisé 1440×900. Aucun responsive mobile.

---

## 1. Personas

### Persona A — Ingénieur partenaire (utilisateur principal)

**Profil** : Ingénieur structure ou géotechnicien dans un bureau d'études. 35-50 ans. Connaît les capteurs, les mesures vibratoires et les concepts FFT. Ne sait pas écrire du Python, mais comprend les résultats.

**Objectif** : Analyser rapidement l'état structurel d'un ouvrage, identifier les anomalies, exporter un rapport pour son client final.

**Frustrations actuelles** : reçoit des fichiers Python ou Excel bruts de la part du prestataire, doit interpréter lui-même les graphes, pas d'historique centralisé.

**Ce qu'il attend de Structura** : une interface qui lui donne l'essentiel d'un coup d'œil, sans apprentissage, avec des graphes clairs et un statut capteur visible en permanence.

---

### Persona B — Décideur du cabinet partenaire

**Profil** : Directeur technique ou associé d'un bureau d'études. Signe les accès et les licences. Consulte le tableau de bord une fois par semaine pour avoir une vue d'ensemble.

**Objectif** : Savoir combien de projets sont actifs, si des alertes critiques sont remontées, vérifier que les partenaires sous licence sont à jour.

**Ce qu'il attend de Structura** : des KPI clairs en page d'accueil, une liste de projets avec statuts, un panneau partenaires propre.

---

### Persona C — Opérateur terrain / technicien de maintenance

**Profil** : Technicien qui pose ou vérifie les capteurs sur site. Accès limité à Structura (lecture seule). Consulte uniquement les alertes et le statut des capteurs d'un projet donné.

**Objectif** : Savoir si un capteur est hors ligne ou déclenche une alerte avant de se déplacer inutilement.

**Ce qu'il attend de Structura** : accès rapide au détail d'un projet, vue capteur avec statut en temps réel, sans avoir à naviguer dans les menus d'analyse.

---

## 2. User stories détaillées

### Dashboard (écran 1)

**US01 — Vue KPI globale**
En tant que décideur du cabinet, je veux voir sur la page d'accueil le nombre de projets actifs, de capteurs en ligne et d'alertes ouvertes, pour évaluer l'état de la flotte sans ouvrir un seul projet.

Critères d'acceptation :
- Trois `Stat` cards en haut de page avec valeur animée (`CounterValue`) et variation vs période précédente.
- Chaque `Stat` affiche un `StatusDot` coloré (vert/orange/rouge) selon un seuil configurable dans les données mock.
- Les valeurs s'animent au chargement initial (counter 0 → valeur finale, 600ms).

**US02 — Derniers événements**
En tant qu'ingénieur partenaire, je veux voir la liste des 5 derniers événements (alerte, mesure anormale, nouveau projet) triée par date décroissante, pour savoir immédiatement si quelque chose a changé depuis ma dernière connexion.

Critères d'acceptation :
- Liste de `Card` compacts avec `Badge` type (alerte / mesure / projet), timestamp relatif ("il y a 2h"), et lien vers le projet concerné.
- Entrée en stagger : chaque item entre avec un décalage de 60ms par rapport au précédent.
- Cliquer un événement navigue vers le projet ou l'analyse concerné.

**US03 — Mini-preview 3D hero**
En tant que décideur, je veux voir une structure 3D animée en arrière-plan de la hero section, pour que la démo soit immédiatement impressionnante visuellement.

Critères d'acceptation :
- `SceneWrapper` en lecture seule (pas d'interaction), rotation lente automatique (0.3 rpm).
- La scène se charge dans un `Loader` skeleton puis apparaît avec un fade-in 400ms.
- Aucune saccade : la scène ne bloque pas le rendu du reste de la page (dynamic ssr:false).

---

### Projets (écran 2)

**US04 — Liste des projets avec filtres**
En tant qu'ingénieur partenaire, je veux filtrer la liste des projets par type (pont / bâtiment) et par statut (actif / archivé / alerte), pour retrouver rapidement le projet qui m'intéresse.

Critères d'acceptation :
- Barre de filtres avec deux `Select` (type, statut) et un `Input` recherche texte.
- Les `Card` projets se réordonnent/masquent au changement de filtre avec une transition opacity+translateY 200ms.
- Le nombre de résultats s'affiche sous la barre de filtres ("6 projets correspondants").

**US05 — Cartes projets animées**
En tant qu'ingénieur partenaire, je veux que les cartes de projets entrent en cascade à l'ouverture de la page, pour que la navigation soit fluide et professionnelle.

Critères d'acceptation :
- Chaque `Card` projet entre avec stagger 80ms (translateY 20px → 0, opacity 0 → 1).
- Chaque carte affiche : nom du projet, type (`Badge`), statut (`StatusDot`), date de dernière mesure, `SparkLine` de la dernière semaine d'activité capteurs.
- Hover sur une carte : légère élévation (box-shadow intensifiée, 150ms).

**US06 — Stats agrégées de la liste**
En tant que décideur, je veux voir en haut de la liste des projets un résumé (X ponts, Y bâtiments, Z alertes actives), pour avoir une vue macro sans scroller.

Critères d'acceptation :
- Trois `Stat` mini placés dans un `Panel` au-dessus de la grille.
- Valeurs `CounterValue` animées à l'entrée.
- Mise à jour cohérente avec les filtres actifs.

---

### Détail projet (écran 3)

**US07 — Visualisation 3D de la structure**
En tant qu'ingénieur partenaire, je veux voir la structure de l'ouvrage en 3D dans la zone principale, pour comprendre la disposition des capteurs dans l'espace réel.

Critères d'acceptation :
- `SceneWrapper` interactif : rotation orbitale à la souris (clic maintenu + drag), zoom molette.
- La scène affiche les capteurs comme des sphères colorées (vert = OK, orange = alerte, rouge = hors ligne).
- Skeleton `Loader` pendant le chargement de la scène (minimum 800ms simulé pour effet réaliste).

**US08 — Clic sur capteur**
En tant qu'ingénieur partenaire, je veux cliquer sur un capteur dans la vue 3D pour voir ses mesures récentes dans le panneau latéral, sans quitter la vue 3D.

Critères d'acceptation :
- Clic sur une sphère capteur : `Tooltip` contextuel avec nom + dernière valeur + timestamp.
- Le panneau latéral droit se met à jour avec les données du capteur sélectionné (transition slide 250ms).
- Le capteur sélectionné s'illumine (halo pulsant, 1.5s loop).

**US09 — Panneau latéral mesures temps réel**
En tant qu'opérateur terrain, je veux voir dans le panneau latéral les mesures du capteur sélectionné actualisées toutes les 2-3 secondes (mock), pour avoir l'impression d'un flux live.

Critères d'acceptation :
- `Panel` droit 360px fixe avec : nom capteur, type de mesure, valeur actuelle en `CounterValue` (tick animé), `LineChart` mini de l'historique récent (30 points).
- Les nouvelles valeurs arrivent avec un flash de couleur (cyan 200ms → couleur normale).
- Un `StatusDot` indique l'état de connexion du capteur.

**US10 — Navigation vers analyses**
En tant qu'ingénieur partenaire, je veux accéder aux analyses détaillées du projet depuis le détail projet, pour basculer rapidement vers les graphes d'analyse.

Critères d'acceptation :
- `Button` primaire "Voir les analyses" dans le panneau latéral, navigue vers l'écran Analyses avec le projet pré-sélectionné.
- `Breadcrumbs` en haut : Projets > [Nom du projet] > Vue 3D.
- Transition de page : fade 200ms.

---

### Analyses (écran 4)

**US11 — Tabs entre types d'analyse**
En tant qu'ingénieur partenaire, je veux switcher entre les onglets Amplitude, FFT et Anomalies pour naviguer entre les types d'analyse sans rechargement de page.

Critères d'acceptation :
- Composant `Tabs` avec 3 onglets : Amplitude / Spectre FFT / Anomalies détectées.
- Transition entre onglets : fade cross 180ms, pas de jump de layout.
- L'onglet actif persiste dans l'URL (query param `?tab=fft`).

**US12 — Courbe d'amplitude**
En tant qu'ingénieur partenaire, je veux voir la courbe d'amplitude sur une période configurable (1h / 24h / 7j), pour identifier les pics et tendances de vibration.

Critères d'acceptation :
- `LineChart` plein largeur avec axe X (temps) et Y (mm/s²), grille grise subtile.
- Sélecteur de période en `Select` (1h / 24h / 7j) — les données mock changent au choix.
- La courbe se dessine avec une animation path SVG de gauche à droite (400ms) à chaque changement de période.

**US13 — Spectre FFT**
En tant qu'ingénieur partenaire, je veux voir le spectre fréquentiel (FFT) des mesures pour identifier les fréquences propres de la structure.

Critères d'acceptation :
- `BarChart` avec axe X (Hz, 0-50) et Y (amplitude normalisée), barres colorées par intensité (vert → orange → rouge).
- Les pics de fréquence propre sont annotés avec un `Tooltip` au survol (fréquence exacte + label "Mode 1", "Mode 2"...).
- Animation d'entrée : barres montent du bas (stagger 10ms par barre, 300ms total).

**US14 — Heatmap des anomalies**
En tant qu'ingénieur partenaire, je veux voir une heatmap temporelle des anomalies détectées par le système Python pour identifier les périodes et capteurs les plus problématiques.

Critères d'acceptation :
- `Heatmap` axes : X = jours (30 derniers), Y = capteurs. Couleur : bleu froid (normal) → rouge (anomalie).
- `Tooltip` au survol d'une cellule : date, capteur, score d'anomalie, type.
- Cellules entrent avec fade stagger 5ms par cellule (balayage gauche-droite, ligne par ligne).

**US15 — Timeline des événements**
En tant qu'ingénieur partenaire, je veux voir une timeline chronologique des événements détectés sur le projet, pour comprendre l'historique et rédiger mon rapport.

Critères d'acceptation :
- Liste verticale d'événements dans un `Panel` droit fixe (360px), chaque item avec : `Badge` sévérité, description courte, timestamp.
- Scroll indépendant du panneau (overflow-y auto).
- Bouton "Exporter rapport PDF" en bas (présent, non fonctionnel — `Button` secondary disabled).

---

### Partenaires (écran 5)

**US16 — Liste des partenaires**
En tant que décideur du cabinet, je veux voir la liste des partenaires avec leur statut de licence et leur dernière activité, pour savoir qui est actif et qui doit renouveler.

Critères d'acceptation :
- Grille de `Card` partenaires : logo (placeholder), nom, adresse, `Badge` statut licence (active / expirée / trial), `StatusDot` dernière connexion.
- `Select` filtre par statut de licence.
- Stagger d'entrée 70ms par carte.

**US17 — Gestion des accès partenaire**
En tant que décideur, je veux modifier le niveau d'accès d'un partenaire (lecture seule / accès complet) depuis la liste, pour contrôler les permissions sans outil externe.

Critères d'acceptation :
- `Select` inline dans chaque `Card` partenaire : "Lecture seule" / "Accès complet".
- Changement confirmé par un `Modal` de confirmation ("Modifier l'accès de [Partenaire] ?", `Button` "Confirmer" + "Annuler").
- Après confirmation : `Badge` se met à jour avec animation pulse 300ms.

**US18 — Secure Deploy**
En tant que décideur, je veux déclencher un déploiement chiffré d'une nouvelle version de Structura chez un partenaire, pour m'assurer que le code source Python ne soit jamais exposé.

Critères d'acceptation :
- `Button` primary "Secure Deploy" dans chaque carte partenaire.
- Clic → `Modal` "Déployer chez [Partenaire]" avec : version à déployer (`Select`), bouton "Lancer le déploiement".
- Après confirmation : animation de logs de déploiement en temps réel (mock, texte mono défilant dans un terminal-style `Panel`, 3-5 lignes par seconde, 8-10 secondes total), puis message "Déploiement terminé — build chiffré transmis".

**US19 — Ajout d'un partenaire**
En tant que décideur, je veux ajouter un nouveau partenaire à la liste, pour intégrer un nouveau bureau d'études sans avoir à contacter le prestataire.

Critères d'acceptation :
- `Button` secondary "Ajouter un partenaire" en haut de page → `Modal` avec `Input` (nom, email, adresse) + `Select` niveau d'accès.
- Validation côté formulaire (champs requis) avec messages d'erreur inline.
- Après soumission : la nouvelle carte s'insère en tête de liste avec animation slide-down + fade 300ms.

**US20 — Indicateur de sécurité build**
En tant que décideur, je veux voir qu'un build déployé est bien chiffré, pour être certain que le code source Python n'est jamais accessible au partenaire.

Critères d'acceptation :
- Chaque carte partenaire affiche un `Badge` "Build chiffré ✓" après un déploiement réussi.
- `Tooltip` sur ce badge : "Le code source Python est chiffré et non lisible par le partenaire."
- L'icône cadenas dans le `Badge` pulse une fois à l'affichage (animation 400ms, une seule fois).

---

### Stories transverses

**US21 — Navigation globale fluide**
En tant qu'ingénieur partenaire, je veux naviguer entre les 5 écrans via la sidebar sans rechargement visible, pour une expérience proche d'une application native.

Critères d'acceptation :
- `Sidebar` fixe 240px avec icône + label pour chaque écran.
- Item actif mis en surbrillance (fond accent + texte blanc).
- Transition entre pages : fade 200ms géré par les transitions Next.js App Router.

**US22 — Topbar contextuelle**
En tant qu'ingénieur partenaire, je veux voir en permanence le nom du projet courant et les `Breadcrumbs` dans la topbar, pour savoir où je suis dans la navigation.

Critères d'acceptation :
- `Topbar` fixe 56px avec `Breadcrumbs` à gauche, notification bell (badge count) et avatar/initiales à droite.
- `Breadcrumbs` se met à jour dynamiquement selon la route active.
- Bell notification → dropdown de 3 alertes mock au clic.

**US23 — États d'alerte visibles**
En tant qu'opérateur terrain, je veux que les alertes critiques soient immédiatement visibles quelle que soit la page où je suis, pour ne jamais manquer un problème urgent.

Critères d'acceptation :
- Si une alerte critique est active (mock), la `Topbar` affiche un bandeau rouge 32px au-dessus d'elle avec le message d'alerte et un lien vers le projet.
- `StatusDot` rouge pulsant dans la `Sidebar` sur les projets concernés.
- Le bandeau est dismiss-able via une croix (disparition slide-up 200ms).

**US24 — `RingMeter` de santé globale**
En tant que décideur, je veux voir un indicateur visuel circulaire de la santé globale de la flotte de capteurs sur le dashboard, pour avoir une lecture instantanée sans lire les chiffres.

Critères d'acceptation :
- `RingMeter` de diamètre 120px sur le dashboard : arc coloré 0-100% selon le % de capteurs OK.
- Couleur arc : vert (>80%), orange (50-80%), rouge (<50%).
- L'arc s'anime de 0 au pourcentage cible à l'entrée (600ms, easing ease-out).

**US25 — Skeleton / chargement cohérent**
En tant que tout utilisateur, je veux que tous les éléments dynamiques affichent un état de chargement visuellement cohérent, pour que l'interface ne semble jamais cassée ou vide.

Critères d'acceptation :
- Chaque `Card`, `Stat`, `LineChart`, `BarChart`, `Heatmap` a un état skeleton (shimmer animé) pendant le chargement mock (300-800ms simulé).
- Le skeleton a exactement la même taille que le contenu chargé (pas de layout shift).
- Shimmer : fond gris-800 avec un gradient lumineux qui balaye de gauche à droite, 1.2s loop.

---

## 3. Flows principaux

### Flow A — Onboarding partenaire → première mesure visible

```
[Écran 1 : Dashboard]
  └─ Topbar affiche "Structura" + 0 projet actif
  └─ Hero 3D tourne (scène de démonstration)
  └─ KPI : 0 projets, 0 capteurs, 0 alertes (CounterValue animés)
       │
       ▼
[Clic "Projets" dans Sidebar]
  └─ Écran 2 : liste vide → état vide affiché (voir §6)
  └─ Bouton "Importer un projet" (mock)
       │
       ▼
[Clic "Importer un projet" → Modal import]
  └─ Input nom projet, Select type (pont/bâtiment), Input fichier de config (mock)
  └─ Bouton "Importer"
       │
       ▼
[Simulation import 1.5s (progress bar dans Modal)]
  └─ Modal se ferme
  └─ Nouveau projet inséré en tête de liste (slide-down + fade)
  └─ KPI du Dashboard incrémentent (+1 projet, +N capteurs)
       │
       ▼
[Clic sur la carte du projet]
  └─ Écran 3 : Détail projet
  └─ SceneWrapper charge (skeleton 800ms) → scène 3D apparaît
  └─ Sphères capteurs apparaissent avec stagger (50ms par capteur)
       │
       ▼
[Clic sur un capteur dans la scène 3D]
  └─ Panneau latéral droit se met à jour
  └─ CounterValue de la mesure commence à ticker (mock toutes les 2.5s)
  └─ LineChart affiche l'historique (animation path SVG 400ms)
  → Première mesure visible. Flow terminé.
```

---

### Flow B — Diagnostic d'anomalie → switch vers analyses FFT

```
[Écran 1 : Dashboard]
  └─ Bandeau alerte rouge visible en topbar : "Anomalie détectée — Pont A75"
  └─ Badge "2 alertes" dans la Stat cards
       │
       ▼
[Clic sur l'événement dans la liste "Derniers événements"]
  └─ Navigation vers Écran 3 (Détail projet Pont A75)
  └─ Capteur problématique pré-sélectionné (panneau latéral déjà chargé)
  └─ StatusDot rouge pulsant sur le capteur concerné dans la scène 3D
       │
       ▼
[Clic "Voir les analyses" dans le panneau latéral]
  └─ Navigation vers Écran 4 (Analyses)
  └─ Onglet actif par défaut : Anomalies détectées
  └─ Heatmap affiche les jours/capteurs anormaux (cellules rouges visibles)
       │
       ▼
[Clic onglet "Spectre FFT"]
  └─ Transition fade cross 180ms
  └─ BarChart FFT s'anime (barres montent 300ms)
  └─ Pic de fréquence anormal annoté en rouge avec Tooltip
  → Ingénieur identifie le mode propre affecté. Flow terminé.
```

---

### Flow C — Déploiement sécurisé chez un partenaire

```
[Sidebar → Clic "Partenaires"]
  └─ Écran 5 : liste des partenaires (cartes avec stagger)
  └─ Partenaire "Bureau Dupont & Associés" — statut licence active
       │
       ▼
[Clic "Secure Deploy" sur la carte]
  └─ Modal "Déployer chez Bureau Dupont & Associés"
  └─ Select version (v2.1.0 / v2.0.3 / v1.9.5)
  └─ Avertissement inline : "Le build sera chiffré AES-256 avant transmission."
       │
       ▼
[Clic "Lancer le déploiement"]
  └─ Modal passe en mode "Terminal logs"
  └─ Lignes de log défilent (mono, fond noir) :
       > Packaging Python modules...
       > Encrypting build (AES-256)...
       > Signing bundle...
       > Transmitting to partner endpoint...
       > Verifying checksum...
       > Deploy successful. Build ID: BLD-20260415-0042
  └─ Animation check vert (800ms) + message "Déploiement terminé"
       │
       ▼
[Fermeture Modal]
  └─ Badge "Build chiffré ✓" apparaît sur la carte partenaire (pulse 400ms)
  └─ Colonne "Dernière mise à jour" passe à "À l'instant"
  → Déploiement sécurisé simulé. Code source jamais exposé. Flow terminé.
```

---

## 4. Wireframes textuels

### Wireframe — Shell global (commun à tous les écrans)

```
┌────────────────────────────────────────────────────────────────────────────────┐
│ TOPBAR [fixe, hauteur 56px, fond bg-900, border-bottom 1px border-800]        │
│  [Logo Structura 32px]  [Breadcrumbs: Projets > Pont A75 > Vue 3D]  [Bell 🔔] [Avatar] │
├──────────────┬─────────────────────────────────────────────────────────────────┤
│ SIDEBAR      │ MAIN CONTENT AREA                                               │
│ [fixe 240px] │ [flex-1, min-w 0, overflow-y auto]                             │
│ fond bg-950  │                                                                 │
│              │                                                                 │
│ [Dashboard]  │                                                                 │
│ [Projets]    │                                                                 │
│ [Analyses]   │                                                                 │
│ [Partenaires]│                                                                 │
│              │                                                                 │
│ [séparateur] │                                                                 │
│ [Paramètres] │                                                                 │
│              │                                                                 │
│ bg-800 (item │                                                                 │
│ actif)       │                                                                 │
└──────────────┴─────────────────────────────────────────────────────────────────┘
Total : min 1280px. Sidebar 240px fixe. Topbar 56px fixe. Main = 1280-240 = 1040px min.
```

---

### Wireframe — Écran 1 : Dashboard

```
┌─ TOPBAR ─────────────────────────────────────────────────────────────────────────────┐
│  Structura                    Dashboard                              🔔  [A]         │
├─ SIDEBAR ──┬─ MAIN (1200px à 1440) ─────────────────────────────────────────────────┤
│            │                                                                         │
│ [Dashboard]│  ┌── PageHeader ────────────────────────────────────────────────────┐  │
│ [Projets]  │  │  "Vue d'ensemble"   [badge "Live"]                               │  │
│ [Analyses] │  └──────────────────────────────────────────────────────────────────┘  │
│[Partenaires│                                                                         │
│            │  ┌── KPI ROW (3 × Stat) ────────────────────────────────────────────┐  │
│            │  │  [Stat: Projets actifs]  [Stat: Capteurs en ligne]  [Stat: Alertes]│ │
│            │  │   CounterValue animé      CounterValue animé         StatusDot rouge│ │
│            │  │   "↑2 ce mois"            "94% uptime"               "2 critiques" │  │
│            │  └──────────────────────────────────────────────────────────────────┘  │
│            │                                                                         │
│            │  ┌── ROW PRINCIPALE ──────────────────────────────────────────────────┐ │
│            │  │                                                                     │ │
│            │  │  ┌── HERO 3D (SceneWrapper) ─────────────┐  ┌── EVENTS (Panel) ─┐ │ │
│            │  │  │                                        │  │                   │ │ │
│            │  │  │  [Scène 3D pont — rotation auto]       │  │ Derniers événements│ │ │
│            │  │  │  [Loader skeleton pendant chargement]  │  │                   │ │ │
│            │  │  │  fond bg-900, accent cyan sur câbles   │  │ • [Badge] Alerte   │ │ │
│            │  │  │                                        │  │   Capteur C3 A75  │ │ │
│            │  │  │  h: 360px                              │  │   il y a 23min    │ │ │
│            │  │  │  w: ~680px (flex-1)                    │  │                   │ │ │
│            │  │  │                                        │  │ • [Badge] Mesure  │ │ │
│            │  │  │  [RingMeter 120px en bas à droite]     │  │   Bât. Centre-Sud │ │ │
│            │  │  │   arc cyan = % capteurs OK             │  │   il y a 1h05     │ │ │
│            │  │  │                                        │  │                   │ │ │
│            │  │  └────────────────────────────────────────┘  │ • [Badge] Projet  │ │ │
│            │  │                                               │   Pont B12 créé   │ │ │
│            │  │                                               │   hier            │ │ │
│            │  │                                               │                   │ │ │
│            │  │                                               │  [lien Tout voir] │ │ │
│            │  │                                               └───────────────────┘ │ │
│            │  └─────────────────────────────────────────────────────────────────────┘ │
└────────────┴──────────────────────────────────────────────────────────────────────────┘

Composants : Sidebar, Topbar, PageHeader, Stat × 3, CounterValue × 3, StatusDot × 3,
             SceneWrapper, Loader, RingMeter, Panel, Card × N, Badge × N.
Ratios : Sidebar 240px | Main 1200px | Hero 3D flex-1 | Panel events 320px fixe.
```

---

### Wireframe — Écran 2 : Projets

```
┌─ TOPBAR ─────────────────────────────────────────────────────────────────────────────┐
│  Structura                    Projets                                🔔  [A]         │
├─ SIDEBAR ──┬─ MAIN ─────────────────────────────────────────────────────────────────┤
│            │                                                                         │
│ [Dashboard]│  ┌── PageHeader ────────────────────────────────────────────────────┐  │
│ [Projets ●]│  │  "Projets"    [Button primary "Nouveau projet"]                  │  │
│ [Analyses] │  └──────────────────────────────────────────────────────────────────┘  │
│[Partenaires│                                                                         │
│            │  ┌── STATS MINI (Panel) ────────────────────────────────────────────┐  │
│            │  │  [Stat: X ponts]   [Stat: Y bâtiments]   [Stat: Z alertes actives] │ │
│            │  └──────────────────────────────────────────────────────────────────┘  │
│            │                                                                         │
│            │  ┌── FILTRES ───────────────────────────────────────────────────────┐  │
│            │  │  [Input search "Rechercher un projet..."]  [Select Type ▾]  [Select Statut ▾] │
│            │  │  "6 projets correspondants"                                       │  │
│            │  └──────────────────────────────────────────────────────────────────┘  │
│            │                                                                         │
│            │  ┌── GRILLE PROJETS (3 colonnes, gap 24px) ───────────────────────────┐ │
│            │  │                                                                     │ │
│            │  │  ┌── Card projet ──┐  ┌── Card projet ──┐  ┌── Card projet ──┐   │ │
│            │  │  │ [Badge PONT]    │  │ [Badge BÂTIMENT]│  │ [Badge PONT]    │   │ │
│            │  │  │ Pont A75        │  │ Centre-Sud      │  │ Pont B12        │   │ │
│            │  │  │ [StatusDot] OK  │  │ [StatusDot] ⚠   │  │ [StatusDot] OK  │   │ │
│            │  │  │ Dernière mesure │  │ Dernière mesure │  │ Dernière mesure │   │ │
│            │  │  │ il y a 5min     │  │ il y a 2h       │  │ il y a 1j       │   │ │
│            │  │  │ [SparkLine]     │  │ [SparkLine]     │  │ [SparkLine]     │   │ │
│            │  │  └─────────────────┘  └─────────────────┘  └─────────────────┘  │ │
│            │  │                                                                     │ │
│            │  │  (2e rangée de 3 cards...)                                          │ │
│            │  └─────────────────────────────────────────────────────────────────────┘ │
└────────────┴──────────────────────────────────────────────────────────────────────────┘

Composants : Sidebar, Topbar, PageHeader, Button, Panel, Stat × 3, Input, Select × 2,
             Card × 6, Badge × 6, StatusDot × 6, SparkLine × 6.
Ratios : Sidebar 240px | Main 1200px | Grille 3 cols auto.
```

---

### Wireframe — Écran 3 : Détail projet

```
┌─ TOPBAR ─────────────────────────────────────────────────────────────────────────────┐
│  Structura     Projets > Pont A75 > Vue 3D                           🔔  [A]         │
├─ SIDEBAR ──┬─ MAIN ──────────────────────────────────────────┬── PANEL DROIT ───────┤
│            │                                                  │  [fixe 360px]        │
│ [Dashboard]│  ┌── PageHeader ───────────────────────────┐    │                      │
│ [Projets ●]│  │  "Pont A75"  [Badge PONT] [StatusDot OK]│    │ ┌── Capteur sélect. ┐│
│ [Analyses] │  └─────────────────────────────────────────┘    │ │ Nom : Cap-C3       ││
│[Partenaires│                                                  │ │ Type : Accéléro.   ││
│            │  ┌── SceneWrapper ────────────────────────┐     │ │ [StatusDot] En ligne││
│            │  │                                         │     │ │                    ││
│            │  │  [Scène 3D pont interactif]             │     │ │ Valeur actuelle    ││
│            │  │  Tablier, piliers, câbles               │     │ │ [CounterValue]     ││
│            │  │  Sphères capteurs :                     │     │ │ 2.34 mm/s²         ││
│            │  │   ● cyan = OK                           │     │ │ (tick toutes 2.5s) ││
│            │  │   ● orange = alerte                     │     │ │                    ││
│            │  │   ● rouge = hors ligne                  │     │ │ [LineChart mini]   ││
│            │  │                                         │     │ │  30 pts historique ││
│            │  │  [Controls orbit: souris drag + zoom]   │     │ │                    ││
│            │  │  [Loader skeleton si chargement]        │     │ │ [Button primary]   ││
│            │  │                                         │     │ │ "Voir les analyses"││
│            │  │  h: 100% (calc 100vh - 56px - 80px)    │     │ └────────────────────┘│
│            │  │  flex-1                                 │     │                      │
│            │  │                                         │     │ ┌── Infos projet ───┐│
│            │  │  [Tooltip au survol capteur :           │     │ │ Localisation       ││
│            │  │   "Cap-C3 — 2.34 mm/s² — il y a 3s"]  │     │ │ Date création      ││
│            │  └─────────────────────────────────────────┘     │ │ Nb capteurs total  ││
│            │                                                   │ │ Dernier rapport    ││
│            │                                                   │ └────────────────────┘│
└────────────┴───────────────────────────────────────────────────┴──────────────────────┘

Composants : Sidebar, Topbar, Breadcrumbs, PageHeader, Badge, StatusDot, SceneWrapper,
             Loader, Tooltip, Panel × 2, CounterValue, LineChart, Button.
Ratios : Sidebar 240px | SceneWrapper flex-1 | Panel droit 360px.
Total main = 1440 - 240 = 1200px → SceneWrapper = 1200 - 360 = 840px.
```

---

### Wireframe — Écran 4 : Analyses

```
┌─ TOPBAR ─────────────────────────────────────────────────────────────────────────────┐
│  Structura     Projets > Pont A75 > Analyses                         🔔  [A]         │
├─ SIDEBAR ──┬─ MAIN ──────────────────────────────────────────┬── PANEL DROIT ───────┤
│            │                                                  │  [fixe 360px]        │
│ [Dashboard]│  ┌── PageHeader ───────────────────────────┐    │                      │
│ [Projets ●]│  │  "Analyses — Pont A75"  [Select capteur]│    │ ┌── Timeline ────────┐│
│ [Analyses ●│  └─────────────────────────────────────────┘    │ │ Événements récents ││
│[Partenaires│                                                  │ │                    ││
│            │  ┌── Tabs ──────────────────────────────────┐   │ │ [Badge rouge]      ││
│            │  │  [Amplitude]  [Spectre FFT]  [Anomalies] │   │ │ Anomalie détectée  ││
│            │  └──────────────────────────────────────────┘   │ │ Cap-C3 — 14 avr.  ││
│            │                                                  │ │                    ││
│            │  ── Onglet Amplitude ──────────────────────      │ │ [Badge orange]     ││
│            │  ┌── Panel ──────────────────────────────────┐   │ │ Pic amplitude      ││
│            │  │ [Select période: 1h / 24h / 7j]           │   │ │ Cap-B1 — 12 avr.  ││
│            │  │                                            │   │ │                    ││
│            │  │  [LineChart plein largeur]                 │   │ │ [Badge vert]       ││
│            │  │   axe X = temps, axe Y = mm/s²            │   │ │ Rapport généré     ││
│            │  │   h: 220px, courbe cyan sur fond bg-900   │   │ │ 10 avr.            ││
│            │  │   animation path gauche→droite 400ms      │   │ │                    ││
│            │  └──────────────────────────────────────────┘    │ │ [scroll indépendant││
│            │                                                   │ │  overflow-y auto]  ││
│            │  ── Onglet FFT (caché si autre onglet actif) ─    │ │                    ││
│            │  ┌── Panel ──────────────────────────────────┐   │ │ [Button secondary] ││
│            │  │  [BarChart]                                │   │ │ "Exporter PDF"     ││
│            │  │   axe X = Hz (0-50), axe Y = amplitude    │   │ │ (disabled)         ││
│            │  │   barres colorées intensité, h: 220px     │   │ └────────────────────┘│
│            │  │   Tooltip au survol : fréquence + mode    │   │                      │
│            │  └──────────────────────────────────────────┘    │                      │
│            │                                                   │                      │
│            │  ── Onglet Anomalies ──────────────────────────   │                      │
│            │  ┌── Panel ──────────────────────────────────┐   │                      │
│            │  │  [Heatmap]                                 │   │                      │
│            │  │   30 colonnes (jours) × N lignes (capteurs)│   │                      │
│            │  │   couleur : bleu froid → rouge anomalie    │   │                      │
│            │  │   Tooltip cellule : date + capteur + score │   │                      │
│            │  └──────────────────────────────────────────┘    │                      │
└────────────┴───────────────────────────────────────────────────┴──────────────────────┘

Composants : Sidebar, Topbar, Breadcrumbs, PageHeader, Select × 2, Tabs, Panel × 3,
             LineChart, BarChart, Heatmap, Tooltip, Badge × N, Button.
Ratios : Sidebar 240px | Main analyses flex-1 | Panel timeline 360px.
```

---

### Wireframe — Écran 5 : Partenaires

```
┌─ TOPBAR ─────────────────────────────────────────────────────────────────────────────┐
│  Structura                    Partenaires                            🔔  [A]         │
├─ SIDEBAR ──┬─ MAIN ─────────────────────────────────────────────────────────────────┤
│            │                                                                         │
│ [Dashboard]│  ┌── PageHeader ────────────────────────────────────────────────────┐  │
│ [Projets]  │  │  "Partenaires"   [Select filtre statut ▾]  [Button "Ajouter +"]  │  │
│ [Analyses] │  └──────────────────────────────────────────────────────────────────┘  │
│[Partenaires│                                                                         │
│          ●]│  ┌── GRILLE (2 colonnes, gap 24px) ────────────────────────────────────┐ │
│            │  │                                                                     │ │
│            │  │  ┌── Card partenaire ─────────────────────────────────────────┐   │ │
│            │  │  │ [Logo placeholder 48px]  Bureau Dupont & Associés          │   │ │
│            │  │  │ Paris, France            [Badge "Active"] [StatusDot vert]  │   │ │
│            │  │  │                                                              │   │ │
│            │  │  │ Dernière connexion : il y a 2h                               │   │ │
│            │  │  │ [Badge "Build chiffré ✓"]                                   │   │ │
│            │  │  │                                                              │   │ │
│            │  │  │ Accès : [Select "Accès complet ▾"]                          │   │ │
│            │  │  │                                                              │   │ │
│            │  │  │ [Button primary "Secure Deploy"]  [Button ghost "Détails"] │   │ │
│            │  │  └────────────────────────────────────────────────────────────┘   │ │
│            │  │                                                                     │ │
│            │  │  ┌── Card partenaire ─────────────────────────────────────────┐   │ │
│            │  │  │ [Logo placeholder 48px]  Ingérop Structures                │   │ │
│            │  │  │ Lyon, France             [Badge "Trial"]  [StatusDot orange]│   │ │
│            │  │  │ Dernière connexion : il y a 3j                              │   │ │
│            │  │  │ [pas de badge build chiffré]                                │   │ │
│            │  │  │ Accès : [Select "Lecture seule ▾"]                          │   │ │
│            │  │  │ [Button primary "Secure Deploy"]  [Button ghost "Détails"] │   │ │
│            │  │  └────────────────────────────────────────────────────────────┘   │ │
│            │  └─────────────────────────────────────────────────────────────────────┘ │
│            │                                                                         │
│            │  ┌── Modal "Secure Deploy" (overlay, centré, w: 560px) ─────────────┐  │
│            │  │  Titre : "Déployer chez Bureau Dupont & Associés"               │  │
│            │  │  [Select version ▾]                                               │  │
│            │  │  [Panel info : "Build chiffré AES-256"]                          │  │
│            │  │  [Button primary "Lancer"] [Button ghost "Annuler"]              │  │
│            │  │  --- après lancement : Terminal logs panel ---                    │  │
│            │  │  fond bg-950 mono text cyan, lignes défilantes 3/s               │  │
│            │  └──────────────────────────────────────────────────────────────────┘  │
└────────────┴──────────────────────────────────────────────────────────────────────────┘

Composants : Sidebar, Topbar, PageHeader, Select × N, Button × N (primary, ghost, secondary),
             Card × N, Badge × N, StatusDot × N, Modal, Panel, Tooltip.
Ratios : Sidebar 240px | Main 1200px | Grille 2 cols (col ~580px chacune avec gap 24px).
```

---

## 5. Interactions / micro-animations par écran

### Règle globale

Toutes les animations respectent : durée 200-400ms, easing `cubic-bezier(0.4, 0, 0.2, 1)` (ease standard Material), aucune animation en boucle sauf ce qui est explicitement noté "loop". Aucune particule, aucun parallax.

---

### Écran 1 — Dashboard

| Élément | Animation | Durée | Déclencheur |
|---|---|---|---|
| `Stat` cards (3) | fade-in + translateY(-10px → 0), stagger 100ms | 300ms | montée de page |
| `CounterValue` | counter 0 → valeur, easing ease-out | 600ms | après fade-in card |
| `RingMeter` arc | arc 0 → % cible, easing ease-out | 600ms | montée de page |
| `SceneWrapper` hero | fade-in opacity 0 → 1 après chargement | 400ms | fin de chargement |
| Rotation scène | rotation orbitale automatique 0.3 rpm | loop | permanent |
| `Card` events | stagger 60ms (translateY 12px → 0 + opacity) | 250ms par item | montée de page |
| Hover `Card` event | box-shadow 0 → 0 0 0 2px accent | 150ms | hover |

---

### Écran 2 — Projets

| Élément | Animation | Durée | Déclencheur |
|---|---|---|---|
| `Card` projets | stagger 80ms (translateY 20px → 0 + opacity) | 280ms par card | montée de page / filtre |
| Filtre change | cards : opacity 1 → 0 → 1 + reorder | 200ms | changement `Select` ou `Input` |
| Hover `Card` | box-shadow intensifiée + légère scale(1.01) | 150ms | hover |
| `SparkLine` | path draw gauche → droite | 300ms | montée de page |
| `Stat` mini | CounterValue 0 → valeur | 500ms | montée de page |

---

### Écran 3 — Détail projet

| Élément | Animation | Durée | Déclencheur |
|---|---|---|---|
| `SceneWrapper` | fade-in après skeleton | 400ms | fin chargement 3D |
| Sphères capteurs | scale 0 → 1, stagger 50ms par capteur | 200ms par sphère | après chargement scène |
| Clic capteur | halo pulsant (scale 1 → 1.4 → 1, opacity 1 → 0) | 1.5s loop | sélection capteur |
| Panneau latéral update | slide-in gauche (translateX 20px → 0 + opacity) | 250ms | sélection capteur |
| `CounterValue` tick | flash couleur accent → couleur normale | 200ms | chaque nouveau tick |
| `LineChart` mini | path draw 30 points gauche → droite | 400ms | chargement panneau |
| `Tooltip` | opacity 0 → 1 + translateY(-4px → 0) | 150ms | hover capteur |

---

### Écran 4 — Analyses

| Élément | Animation | Durée | Déclencheur |
|---|---|---|---|
| Switch `Tabs` | fade cross entre contenus (ancien → 0, nouveau → 1) | 180ms | clic onglet |
| `LineChart` courbe | path SVG draw gauche → droite | 400ms | montée onglet / changement période |
| `BarChart` barres | scaleY 0 → 1 depuis le bas, stagger 10ms par barre | 300ms total | montée onglet |
| `Heatmap` cellules | opacity 0 → 1, stagger 5ms par cellule, balayage L→R ligne par ligne | 400ms total | montée onglet |
| `Tooltip` graphes | opacity 0 → 1 | 100ms | hover point / cellule |
| `Badge` timeline | none (statique) | — | — |

---

### Écran 5 — Partenaires

| Élément | Animation | Durée | Déclencheur |
|---|---|---|---|
| `Card` partenaires | stagger 70ms (translateY 16px → 0 + opacity) | 260ms par card | montée de page |
| Hover `Card` | box-shadow 0 → 0 0 0 2px accent | 150ms | hover |
| `Modal` open | scale(0.95) → scale(1) + opacity 0 → 1, backdrop fade | 200ms | clic bouton |
| `Modal` close | inverse : scale(1) → scale(0.95) + opacity → 0 | 180ms | clic fermer |
| Terminal logs | nouveau line : translateY(10px) → 0 + opacity | 80ms par ligne | tick 300ms |
| Succès deploy | check icon : scale 0 → 1 + bounce | 800ms | fin simulation |
| `Badge` "Build chiffré" | scale 0 → 1 + pulse opacity 0.7 → 1 (1 fois) | 400ms | fermeture modal |
| `Badge` access update | pulse opacity 0.5 → 1 (1 fois) | 300ms | confirmation modal accès |

---

## 6. États vides / chargement

### Shimmer skeleton — règle commune

Tous les skeletons utilisent le même pattern :
- Fond : `bg-gray-800` (teinte proche du fond de card `bg-gray-900`)
- Animation shimmer : gradient linéaire à 90° (`transparent → rgba(255,255,255,0.06) → transparent`) qui balaye de gauche à droite, `background-size: 200% 100%`, animation `keyframes shimmer` 1.2s linear infinite.
- Taille : identique au contenu final — zéro layout shift.
- Pas de texte "Chargement..." : visuel only.

---

### Dashboard — états

| Composant | État skeleton | État vide |
|---|---|---|
| `Stat` card | Skeleton rectangulaire (titre 60px, valeur 80px, variation 40px) | CounterValue = 0, variation "--" |
| `SceneWrapper` hero | Skeleton fond bg-900 plein, shimmer | Message centré "Aucune structure configurée" |
| `Card` events | 3 skeletons (ligne titre 70%, ligne date 40%) | Panel vide : "Aucun événement récent" |
| `RingMeter` | Arc gris-800 complet + shimmer centre | Arc à 0%, label "N/D" |

---

### Projets — états

| Composant | État skeleton | État vide |
|---|---|---|
| `Card` projet | Skeleton : header (badge+nom), corps (statut+sparkline), 160px de haut | — |
| Grille projets | 6 card skeletons en grille 3 cols | Zone centrale : icône + "Aucun projet. Importez votre premier projet." + Button "Importer" |
| `Stat` mini | Skeleton 80px × 40px × 3 | CounterValue = 0 |

---

### Détail projet — états

| Composant | État skeleton | État vide (aucun capteur sélectionné) |
|---|---|---|
| `SceneWrapper` | Skeleton plein (fond bg-900 + shimmer overlay) pendant 800ms simulé | Message overlay semi-transparent : "Cliquez sur un capteur pour voir ses mesures" |
| Panneau latéral | Skeleton : titre 60%, valeur 80px, chart 120px | Texte gris : "Sélectionnez un capteur dans la vue 3D" |
| `LineChart` mini | Skeleton rectangulaire 120px de haut | — |

---

### Analyses — états

| Composant | État skeleton | État vide |
|---|---|---|
| `LineChart` | Skeleton plein + shimmer, 220px de haut | Texte centré "Aucune donnée pour cette période" |
| `BarChart` | Skeleton 220px de haut (barres grises fixes) | Idem |
| `Heatmap` | Grille de cellules bg-gray-800 shimmer | Texte centré "Aucune anomalie détectée" |
| Timeline panel | 5 lignes skeleton (badge+texte) | "Aucun événement pour ce projet" |

---

### Partenaires — états

| Composant | État skeleton | État vide |
|---|---|---|
| `Card` partenaire | Skeleton : logo 48px, titre 120px, lignes × 3, boutons 80px | — |
| Grille | 4 card skeletons | Texte centré + Button "Ajouter un partenaire" |
| Terminal logs | Lignes skeleton avant démarrage | — |

---

## 7. Contraintes de largeur — récapitulatif par écran

Toutes les mesures sont en pixels, base de calcul 1440px de largeur viewport.

| Zone | Valeur | Note |
|---|---|---|
| Viewport min | 1280px | `min-width: 1280px` sur `body` |
| Viewport cible | 1440px × 900px | Design optimisé pour cette résolution |
| `Sidebar` | 240px fixe | `position: fixed`, `left: 0`, hauteur 100vh |
| `Topbar` | 100% − 240px, hauteur 56px fixe | `position: fixed`, `top: 0`, `left: 240px` |
| Main content | `calc(100vw - 240px)`, `padding: 32px` | Commence à left: 240px |
| Contenu utile max | 1200px (à 1440) | Pas de `max-width` contraignant — full width |

### Par écran

| Écran | Layout | Colonnes |
|---|---|---|
| Dashboard | Panel events 320px fixe à droite + flex-1 pour hero | Hero ~840px, Events 320px |
| Projets | Full width, grille 3 cols auto | ~373px par col (avec gap 24px, padding 32px) |
| Détail projet | Panel droit 360px fixe + flex-1 pour SceneWrapper | SceneWrapper ~840px |
| Analyses | Panel timeline 360px fixe + flex-1 pour graphes | Graphes ~840px |
| Partenaires | Full width, grille 2 cols | ~576px par col (avec gap 24px, padding 32px) |

---

*Fin du document UX.md — Structura prototype v1.*
