File size: 8,696 Bytes
aedd96f
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
# 🎥 Guide de Détection Vidéo

## ✅ Fonctionnalité Ajoutée

Une **page dédiée** pour traiter les vidéos a été créée avec :
- Upload drag & drop de vidéos (MP4, AVI, MOV)
- Traitement frame par frame avec YOLO
- Vidéo annotée téléchargeable
- Statistiques complètes (FPS, durée, nombre de détections)
- Historique des vidéos traitées

---

## 🚀 Comment utiliser

### 1. **Accéder à la page Vidéo**

Dans l'application web (http://localhost:3000), cliquez sur **"Vidéos"** dans le menu de navigation.

### 2. **Uploader une vidéo**

**Option 1 - Drag & Drop:**
- Glissez-déposez votre vidéo dans la zone de dépôt

**Option 2 - Sélection:**
- Cliquez sur la zone de dépôt
- Sélectionnez votre fichier vidéo

**Formats acceptés:** MP4, AVI, MOV  
**Taille maximale:** 100 MB

### 3. **Lancer la détection**

1. Une fois la vidéo uploadée, une prévisualisation s'affiche
2. Cliquez sur **"Détecter sur Vidéo"**
3. **Attendez le traitement** (peut prendre quelques minutes selon la durée)
4. Une barre de progression s'affiche

### 4. **Voir les résultats**

Une fois le traitement terminé, vous obtenez :

#### 📹 **Vidéo Annotée**
- Chaque frame annotée avec les bounding boxes
- Compteur de frames
- Player vidéo intégré

#### 📊 **Statistiques**
- **Total frames**: Nombre de frames traitées
- **FPS**: Frames par seconde de la vidéo
- **Durée**: Durée totale en secondes
- **Temps de traitement**: Temps pris pour traiter la vidéo

#### 🎯 **Résumé des détections**
- Nombre total de détections
- Répartition par classe (poubelle_pleine / poubelle_vide)
- Nombre de frames où chaque classe apparaît

### 5. **Télécharger la vidéo annotée**

Cliquez sur **"Télécharger Vidéo Annotée"** pour enregistrer la vidéo avec les annotations.

---

## 🔧 Architecture Technique

### Backend (API)

**Endpoint:** `POST /api/predict/video`

**Traitement:**
1. Reçoit la vidéo uploadée
2. Ouvre avec OpenCV (`cv2.VideoCapture`)
3. Pour chaque frame :
   - Exécute YOLO inference
   - Annote le frame avec bounding boxes
   - Ajoute compteur de frames
   - Collecte les détections
4. Écrit vidéo annotée avec `cv2.VideoWriter`
5. Encode en base64
6. Retourne JSON avec vidéo + statistiques

**Code API (api.py):**
```python
@app.post("/api/predict/video")
async def predict_video(file: UploadFile = File(...)):
    # Traitement frame par frame
    while cap.isOpened():
        ret, frame = cap.read()
        if not ret:
            break
        
        # Inférence YOLO sur frame
        results = model.predict(source=frame, conf=0.25, device='cpu')
        annotated_frame = results[0].plot()
        
        # Écrire frame annoté
        out.write(annotated_frame)
    
    # Retourner vidéo encodée + stats
    return {
        "video_base64": video_base64,
        "stats": {...},
        "detections": [...]
    }
```

### Frontend (React)

**Composant:** `VideoPage.jsx`

**Fonctionnalités:**
- React Dropzone pour upload
- Axios pour requête API (timeout 5 minutes)
- Barre de progression simulée
- Décodage base64 → Blob → URL pour lecture
- LocalStorage pour historique

**Flow:**
1. User drop vidéo → `onDrop()`
2. Prévisualisation avec `<video>`
3. Click "Détecter" → `handleDetect()`
4. POST `/api/predict/video` avec FormData
5. Affichage résultats + vidéo annotée
6. Download via blob URL

---

## ⚡ Optimisations Possibles

### 1. **Traitement par lots de frames**
Au lieu de traiter frame par frame, traiter par batch de 10-30 frames :
```python
batch_frames = []
for i in range(batch_size):
    ret, frame = cap.read()
    if ret:
        batch_frames.append(frame)

# Inférence sur batch
results = model.predict(source=batch_frames, batch=True)
```

### 2. **Réduire la résolution**
Redimensionner les frames avant inférence :
```python
frame_resized = cv2.resize(frame, (640, 480))
results = model.predict(source=frame_resized)
```

### 3. **Sauter des frames (frame skipping)**
Ne traiter que 1 frame sur N :
```python
skip_frames = 2  # Traiter 1 frame sur 3
if frame_count % skip_frames == 0:
    results = model.predict(source=frame)
```

### 4. **GPU Acceleration**
Si disponible, utiliser GPU :
```python
model.to('cuda')  # Au lieu de 'cpu'
results = model.predict(source=frame, device='cuda')
```

### 5. **Codec H.264 (plus efficace)**
Utiliser codec H.264 au lieu de mp4v :
```python
fourcc = cv2.VideoWriter_fourcc(*'H264')  # ou 'avc1', 'x264'
```

### 6. **WebSocket pour progression en temps réel**
Au lieu de simuler, envoyer vraie progression :
```python
# Backend
from fastapi import WebSocket

@app.websocket("/ws/video_progress")
async def websocket_endpoint(websocket: WebSocket):
    await websocket.accept()
    # Envoyer progression pendant traitement
    await websocket.send_json({"progress": frame_count / total_frames})
```

### 7. **Celery pour tâches asynchrones**
Pour vidéos longues, utiliser Celery :
```python
from celery import Celery

celery = Celery('tasks', broker='redis://localhost:6379')

@celery.task
def process_video(video_path):
    # Traitement long
    pass

# API retourne task_id
# Frontend poll status avec GET /task/{task_id}
```

---

## 📊 Performances Attendues

### Exemple avec vidéo 30s @ 30 FPS

**Spécifications:**
- Durée: 30 secondes
- FPS: 30
- Total frames: 900
- Résolution: 1920x1080

**Sans optimisation (CPU):**
- Temps par frame: ~50-100ms
- Temps total: 45-90 secondes
- Ratio: 1.5-3x temps réel

**Avec GPU (CUDA):**
- Temps par frame: ~10-20ms
- Temps total: 9-18 secondes
- Ratio: 0.3-0.6x temps réel

**Avec optimisations (skip 2 frames, résolution 640x480):**
- Frames traitées: 300
- Temps par frame: ~30ms
- Temps total: 9 secondes
- Ratio: 0.3x temps réel

---

## 🐛 Dépannage

### Erreur: "connect ECONNREFUSED 127.0.0.1:8000"

**Cause:** API backend non démarrée

**Solution:**
```bash
cd /home/mouhammad/Bureau/nourrou/projet-poubelle/trash_full_detection
source .venv/bin/activate
python api.py
```

### Erreur: "Request Timeout"

**Cause:** Vidéo trop longue, timeout atteint (5 min)

**Solutions:**
1. Augmenter timeout dans `VideoPage.jsx` :
```jsx
timeout: 600000 // 10 minutes
```

2. Réduire durée/résolution vidéo

3. Utiliser frame skipping

### Erreur: "File too large"

**Cause:** Vidéo > 100 MB

**Solutions:**
1. Augmenter limite dans `VideoPage.jsx` :
```jsx
maxSize: 200 * 1024 * 1024 // 200 MB
```

2. Compresser vidéo avec ffmpeg :
```bash
ffmpeg -i input.mp4 -vcodec h264 -crf 28 output.mp4
```

### Vidéo annotée ne se télécharge pas

**Cause:** Erreur décodage base64

**Solution:** Vérifier que le backend retourne bien `video_base64`

**Test API direct:**
```bash
curl -X POST "http://localhost:8000/api/predict/video" \
  -F "file=@test.mp4" \
  -o result.json

# Extraire vidéo
jq -r '.video_base64' result.json | base64 -d > output.mp4
```

### Vidéo noire/corrompue

**Cause:** Codec incompatible

**Solutions:**
1. Changer codec dans API :
```python
fourcc = cv2.VideoWriter_fourcc(*'XVID')  # Tester différents codecs
```

2. Convertir vidéo source :
```bash
ffmpeg -i input.mp4 -c:v libx264 -preset fast output.mp4
```

---

## 📝 Exemple d'utilisation avec le notebook

Si vous voulez tester en dehors de l'app web, utilisez le notebook **2_yolo_inference_app.ipynb** :

```python
# Cellule : Traitement vidéo
video_path = "chemin/vers/votre/video.mp4"
output_path = "outputs/video/annotated_video.mp4"

cap = cv2.VideoCapture(video_path)
fourcc = cv2.VideoWriter_fourcc(*'mp4v')
out = cv2.VideoWriter(output_path, fourcc, 30, (width, height))

while cap.isOpened():
    ret, frame = cap.read()
    if not ret:
        break
    
    results = model_detect.predict(source=frame, conf=0.25, device='cpu')
    annotated = results[0].plot()
    out.write(annotated)

cap.release()
out.release()
print(f"Vidéo sauvegardée: {output_path}")
```

---

## 🎯 Résumé

**Vous pouvez maintenant :**
✅ Uploader des vidéos (MP4, AVI, MOV)  
✅ Traiter frame par frame avec YOLO  
✅ Voir vidéo annotée avec détections  
✅ Télécharger la vidéo annotée  
✅ Consulter statistiques détaillées  
✅ Historique des vidéos traitées  

**Endpoints API disponibles :**
- `POST /api/predict/image` → Images
- `POST /api/predict/video` → Vidéos ✨ NOUVEAU
- `GET /api/health` → Status
- `GET /api/stats` → Métriques modèle

**Navigation app :**
- `/` → Accueil
- `/upload` → Images
- `/video` → Vidéos ✨ NOUVEAU
- `/history` → Historique
- `/stats` → Statistiques
- `/about` → À propos

---

**Votre application est maintenant complète avec support Images ET Vidéos ! 🎥🎉**