/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/transformers/utils/generic.py:441: FutureWarning: `torch.utils._pytree._register_pytree_node` is deprecated. Please use `torch.utils._pytree.register_pytree_node` instead.
  _torch_pytree._register_pytree_node(
The cache for model files in Transformers v4.22.0 has been updated. Migrating your old cache. This is a one-time only operation. You can interrupt this and resume the migration later on by calling `transformers.utils.move_cache()`.

0it [00:00, ?it/s]
0it [00:00, ?it/s]
/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/transformers/utils/generic.py:309: FutureWarning: `torch.utils._pytree._register_pytree_node` is deprecated. Please use `torch.utils._pytree.register_pytree_node` instead.
  _torch_pytree._register_pytree_node(
[2026-06-15 23:28:17,098 INFO infer.py line 51 42410] => Loading config ...
[2026-06-15 23:28:17,098 INFO infer.py line 58 42410] => Building model ...
[2026-06-15 23:28:17,533 INFO infer.py line 66 42410] Num params: 97912596
[2026-06-15 23:28:17,833 INFO infer.py line 73 42410] Loading weight at: pretrained_models/lam_audio2exp_streaming.tar
[2026-06-15 23:28:17,996 INFO infer.py line 85 42410] => Loaded weight 'pretrained_models/lam_audio2exp_streaming.tar'
/mnt/DATA/WORK/LAM_Audio2Expression/inference_streaming_audio.py:45: UserWarning: PySoundFile failed. Trying audioread instead.
  audio, sample_rate = librosa.load(cfg.audio_input, sr=16000)
/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/librosa/core/audio.py:184: FutureWarning: librosa.core.audio.__audioread_load
	Deprecated as of librosa version 0.10.0.
	It will be removed in librosa version 1.0.
  y, sr_native = __audioread_load(path, offset, duration, dtype)
Traceback (most recent call last):
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/librosa/core/audio.py", line 176, in load
    y, sr_native = __soundfile_load(path, offset, duration, dtype)
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/librosa/core/audio.py", line 209, in __soundfile_load
    context = sf.SoundFile(path)
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/soundfile.py", line 708, in __init__
    self._file = self._open(file, mode_int, closefd)
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/soundfile.py", line 1296, in _open
    raise LibsndfileError(err, prefix=f"Error opening {self.name!r}: ")
soundfile.LibsndfileError: Error opening './assets/sample_audio/BarackObama.wav': System error.

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "/mnt/DATA/WORK/LAM_Audio2Expression/inference_streaming_audio.py", line 45, in <module>
    audio, sample_rate = librosa.load(cfg.audio_input, sr=16000)
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/librosa/core/audio.py", line 184, in load
    y, sr_native = __audioread_load(path, offset, duration, dtype)
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/decorator/__init__.py", line 247, in fun
    return caller(func, *(extras + args), **kw)
  File "/home/wildlama/miniconda3/envs/lam_a2e/lib/python3.10/site-packages/librosa/util/decorators.py", line 63, in __wrapper
Shell cwd was reset to /home/wildlama


**Le modèle se charge parfaitement** (97M paramètres, poids chargés). L'erreur est juste le nom du fichier audio dans le script. Je corrige :


1	"""
2	# Copyright 2024-2025 The Alibaba 3DAIGC Team Authors. All rights reserved.
3
4	Licensed under the Apache License, Version 2.0 (the "License");
5	you may not use this file except in compliance with the License.
6	You may obtain a copy of the License at
7
8	    https://www.apache.org/licenses/LICENSE-2.0
9
10	Unless required by applicable law or agreed to in writing, software
11	distributed under the License is distributed on an "AS IS" BASIS,
12	WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13	See the License for the specific language governing permissions and
14	limitations under the License.
15
16	"""
17
18	import numpy as np
19
20	from engines.defaults import (
21	    default_argument_parser,
22	    default_config_parser,
23	    default_setup,
24	)
25	from engines.infer import INFER
26	import librosa
27	from tqdm import tqdm
28	import time
29
30
31	def export_json(bs_array, json_path):
32	    from models.utils import export_blendshape_animation, ARKitBlendShape
33	    export_blendshape_animation(bs_array, json_path, ARKitBlendShape, fps=30.0)
34
35	if __name__ == '__main__':
36	    args = default_argument_parser().parse_args()
37	    args.config_file = 'configs/lam_audio2exp_config_streaming.py'
38	    cfg = default_config_parser(args.config_file, args.options)
39
40
41	    cfg = default_setup(cfg)
42	    infer = INFER.build(dict(type=cfg.infer.type, cfg=cfg))
43	    infer.model.eval()
44
45	    audio, sample_rate = librosa.load(cfg.audio_input, sr=16000)
46	    context = None
47	    input_num = audio.shape[0]//16000+1
48	    gap = 16000
49	    all_exp = []
50	    for i in tqdm(range(input_num)):
51
52	        start = time.time()
53	        output, context = infer.infer_streaming_audio(audio[i*gap:(i+1)*gap], sample_rate, context)
54	        end = time.time()
55	        print('Inference time {}'.format(end - start))
56	        all_exp.append(output['expression'])
57
58	    all_exp = np.concatenate(all_exp,axis=0)
59
60	    export_json(all_exp, cfg.save_json_path)

"""
# Copyright 2024-2025 The Alibaba 3DAIGC Team Authors. All rights reserved.

Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

    https://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

"""

import numpy as np

from engines.defaults import (
    default_argument_parser,
    default_config_parser,
    default_setup,
)
from engines.infer import INFER
import librosa
from tqdm import tqdm
import time

def export_json(bs_array, json_path):
    from models.utils import export_blendshape_animation, ARKitBlendShape
    export_blendshape_animation(bs_array, json_path, ARKitBlendShape, fps=30.0)

if __name__ == '__main__':
    args = default_argument_parser().parse_args()
    args.config_file = 'configs/lam_audio2exp_config_streaming.py'
    cfg = default_config_parser(args.config_file, args.options)

    cfg = default_setup(cfg)
    infer = INFER.build(dict(type=cfg.infer.type, cfg=cfg))
    infer.model.eval()

    audio, sample_rate = librosa.load(cfg.audio_input, sr=16000)
    context = None
    input_num = audio.shape[0]//16000+1
    gap = 16000
    all_exp = []
    for i in tqdm(range(input_num)):

        start = time.time()
        output, context = infer.infer_streaming_audio(audio[i*gap:(i+1)*gap], sample_rate, context)
        end = time.time()
        print('Inference time {}'.format(end - start))
        all_exp.append(output['expression'])

    all_exp = np.concatenate(all_exp,axis=0)

    export_json(all_exp, cfg.save_json_path)


je n'en sais rien, comment je sais ca si le pip install s'est terminé ?


Intégrer LAM pour avatars parlants dans GUI agent IA


Bash

cat /mnt/DATA/WORK/LAM_Audio2Expression/configs/lam_audio2exp_config_streaming.py | grep -E "audio_input|save_json"

Find audio_input config path


audio_input = './assets/sample_audio/BarackObama.wav'
save_json_path = 'bsData.json'


Fix audio filename in config


(Bash completed with no output)


cd /mnt/DATA/WORK/LAM_Audio2Expression && $HOME/miniconda3/bin/conda run -n lam_a2e python inference_streaming_audio.py 2>&1 | grep -v FutureWarning | grep -v "deprecated\|Deprecated\|0it"

Test Audio2Expression inference with correct audio file


  _torch_pytree._register_pytree_node(
  _torch_pytree._register_pytree_node(
[2026-06-15 23:28:39,591 INFO infer.py line 51 42700] => Loading config ...
[2026-06-15 23:28:39,591 INFO infer.py line 58 42700] => Building model ...
[2026-06-15 23:28:40,025 INFO infer.py line 66 42700] Num params: 97912596
[2026-06-15 23:28:40,321 INFO infer.py line 73 42700] Loading weight at: pretrained_models/lam_audio2exp_streaming.tar
[2026-06-15 23:28:40,483 INFO infer.py line 85 42700] => Loaded weight 'pretrained_models/lam_audio2exp_streaming.tar'

  0%|          | 0/8 [00:00<?, ?it/s]
 12%|█▎        | 1/8 [00:00<00:06,  1.12it/s]
100%|██████████| 8/8 [00:00<00:00,  8.71it/s]
Inference time 0.8898270130157471
Inference time 0.004354715347290039
Inference time 0.004106283187866211
Inference time 0.0041484832763671875
Inference time 0.003996849060058594
Inference time 0.00394749641418457
Inference time 0.003906965255737305
Inference time 0.003914356231689453
Shell cwd was reset to /home/wildlama


**Audio2Expression fonctionne parfaitement** — après le premier chunk (0.89s de warm-up), chaque seconde d'audio se traite en **4ms**. C'est du vrai temps réel.


ls /mnt/DATA/WORK/LAM_Audio2Expression/bsData.json && python3 -c "import json; d=json.load(open('/mnt/DATA/WORK/LAM_Audio2Expression/bsData.json')); print('Frames:', len(d['blendshapes'])); print('Channels:', len(d['blendshapes'][0]) if d['blendshapes'] else 0); print('Sample frame keys:', list(d['blendshapes'][0].keys())[:5] if d['blendshapes'] else [])"

Check generated blendshape JSON output


Error: Exit code 1
/mnt/DATA/WORK/LAM_Audio2Expression/bsData.json
Traceback (most recent call last):
  File "<string>", line 1, in <module>
    import json; d=json.load(open('/mnt/DATA/WORK/LAM_Audio2Expression/bsData.json')); print('Frames:', len(d['blendshapes'])); print('Channels:', len(d['blendshapes'][0]) if d['blendshapes'] else 0); print('Sample frame keys:', list(d['blendshapes'][0].keys())[:5] if d['blendshapes'] else [])
                                                                                ~^^^^^^^^^^^^^^^
KeyError: 'blendshapes'


python3 -c "import json; d=json.load(open('/mnt/DATA/WORK/LAM_Audio2Expression/bsData.json')); print(type(d)); print(list(d.keys())[:5] if isinstance(d, dict) else len(d)); print(str(d)[:300])"

Inspect blendshape JSON structure


<class 'dict'>
['names', 'metadata', 'frames']
{'names': ['browDownLeft', 'browDownRight', 'browInnerUp', 'browOuterUpLeft', 'browOuterUpRight', 'cheekPuff', 'cheekSquintLeft', 'cheekSquintRight', 'eyeBlinkLeft', 'eyeBlinkRight', 'eyeLookDownLeft', 'eyeLookDownRight', 'eyeLookInLeft', 'eyeLookInRight', 'eyeLookOutLeft', 'eyeLookOutRight', 'eyeLo


python3 -c "
import json
d = json.load(open('/mnt/DATA/WORK/LAM_Audio2Expression/bsData.json'))
print('Channels:', len(d['names']))
print('Frames:', len(d['frames']))
print('FPS metadata:', d.get('metadata', {}))
print('Frame 0 sample:', dict(list(zip(d['names'][:5], d['frames'][0][:5]))  ))
"

Show blendshape data structure


Error: Exit code 1
Traceback (most recent call last):
  File "<string>", line 7, in <module>
    print('Frame 0 sample:', dict(list(zip(d['names'][:5], d['frames'][0][:5]))  ))
                                                           ~~~~~~~~~~~~~~^^^^
KeyError: slice(None, 5, None)
Channels: 52
Frames: 240
FPS metadata: {'fps': 30.0, 'frame_count': 240, 'blendshape_names': ['browDownLeft', 'browDownRight', 'browInnerUp', 'browOuterUpLeft', 'browOuterUpRight', 'cheekPuff', 'cheekSquintLeft', 'cheekSquintRight', 'eyeBlinkLeft', 'eyeBlinkRight', 'eyeLookDownLeft', 'eyeLookDownRight', 'eyeLookInLeft', 'eyeLookInRight', 'eyeLookOutLeft', 'eyeLookOutRight', 'eyeLookUpLeft', 'eyeLookUpRight', 'eyeSquintLeft', 'eyeSquintRight', 'eyeWideLeft', 'eyeWideRight', 'jawForward', 'jawLeft', 'jawOpen', 'jawRight', 'mouthClose', 'mouthDimpleLeft', 'mouthDimpleRight', 'mouthFrownLeft', 'mouthFrownRight', 'mouthFunnel', 'mouthLeft', 'mouthLowerDownLeft', 'mouthLowerDownRight', 'mouthPressLeft', 'mouthPressRight', 'mouthPucker', 'mouthRight', 'mouthRollLower', 'mouthRollUpper', 'mouthShrugLower', 'mouthShrugUpper', 'mouthSmileLeft', 'mouthSmileRight', 'mouthStretchLeft', 'mouthStretchRight', 'mouthUpperUpLeft', 'mouthUpperUpRight', 'noseSneerLeft', 'noseSneerRight', 'tongueOut']}


Tout fonctionne parfaitement. Voici le résumé de ce qu'on a :

---

**Audio2Expression — opérationnel ✅**
- **52 canaux ARKit** (browDownLeft, jawOpen, mouthSmileLeft, etc.)
- **240 frames à 30 FPS** pour 8 secondes d'audio
- **4ms par seconde d'audio** après warm-up — parfaitement temps réel

---

## La suite : intégration dans agent-gui

Il reste 3 étapes :

1. **Exporter ton avatar** depuis une photo via `app_lam.py` (nécessite Blender 4.0+)
2. **Ajouter WebSocket + TTS + Audio2Expression** dans `agent_gui/app.py`
3. **Remplacer le canvas pixel-art** par le renderer WebGL Gaussian Splatting

Tu as Blender d'installé ? (`blender --version` dans ton terminal). C'est nécessaire pour générer l'avatar 3D depuis ta photo.


si je quitte claude, je peux reprendre en revenant ?


Oui, complètement. Le projet est sur disque et tout l'environnement conda est installé. Je sauvegarde un mémo maintenant pour qu'on reprenne exactement là où on en est.


Error: File does not exist. Note: your current working directory is /home/wildlama.


Write

# Memory Index

- [Agent GUI + LAM project](project_agent_gui_lam.md) — GUI agents IA avec avatars LAM parlants, état d'avancement détaillé
- [User profile](user_profile.md) — Profil et contexte technique de l'utilisateur


File created successfully at: /home/wildlama/.claude/projects/-home-wildlama/memory/MEMORY.md (file state is current in your context — no need to Read it back)

# Memory Index

- [Agent GUI + LAM project](project_agent_gui_lam.md) — GUI agents IA avec avatars LAM parlants, état d'avancement détaillé
- [User profile](user_profile.md) — Profil et contexte technique de l'utilisateur


---
name: project-agent-gui-lam
description: GUI pour agents IA avec avatars LAM 3D parlants en temps réel — état d'avancement complet
metadata:
  type: project
---

## Projet principal

`/mnt/DATA/WORK/agent-gui` — web app locale (Python stdlib + vanilla JS) pour piloter des agents LLM avec interface graphique. V1 fonctionnelle avec avatar ASCII, canvas pixel-art animé, chat, sessions JSONL, adaptateurs CLI.

**Why:** Créer une surcouche graphique universelle pour agents IA (Hermes, Claude Code, etc.) avec avatars visuels modélisables.

**How to apply:** Quand on reprend le travail, partir de cet état et continuer vers l'intégration LAM.

---

## Intégration LAM — état au 2026-06-15

### Objectif
Ajouter des avatars 3D photoréalistes parlants en temps réel dans agent-gui. Pipeline :
```
[Agent répond] → [TTS → audio 16kHz mono]
    → [Python: Audio2Expression → 52 blendshapes ARKit @ 30fps]
        → [WebSocket JSON] → [Browser: WebGL Gaussian Splatting renderer]
```

### Ce qui est installé et fonctionnel ✅

**Conda envs sur cette machine :**
- `lam` (Python 3.11) — pour LAM core (génération avatar depuis photo)
  - PyTorch 2.11+cu128, pytorch3d 0.7.9, diff-gaussian-rasterization, nvdiffrast, simple-knn
  - gcc 13 installé dans l'env (nécessaire pour compiler pytorch3d avec CUDA 12.8)
- `lam_a2e` (Python 3.10) — pour Audio2Expression (live talking)
  - PyTorch 2.11+cu128, transformers, librosa, gradio-gaussian-render

**Repos clonés :**
- `/mnt/DATA/WORK/LAM` — modèle LAM core (génère avatar 3D depuis photo)
- `/mnt/DATA/WORK/LAM_Audio2Expression` — Audio2Expression (audio → blendshapes)
  - Poids téléchargés et extraits : `pretrained_models/lam_audio2exp_flow/`
  - **Testé et fonctionnel** : 52 canaux ARKit, 30 FPS, 4ms/seconde d'audio après warm-up

**Résultat test Audio2Expression :**
- Input : `assets/sample_audio/BarackObama_english.wav`
- Output : `bsData.json` — 240 frames à 30fps, 52 blendshapes ARKit par frame
- Format : `{ "names": ["browDownLeft", "jawOpen", ...], "frames": [[...], ...], "metadata": {"fps": 30} }`

**Hardware :**
- GPU : RTX 5090, 32 Go VRAM
- Drivers NVIDIA : 595.71, CUDA 13.2 (max supporté)
- CUDA Toolkit 12.8 installé via conda dans les envs

---

### Ce qui reste à faire

**Étape 1 — Exporter l'avatar 3D (bloquant : nécessite Blender 4.0+)**
- Vérifier si Blender est installé : `blender --version`
- Si oui : lancer `app_lam.py` dans l'env `lam`, charger une photo portrait, exporter le ZIP avatar
- Le ZIP contient : `animation.glb`, `skin.glb`, `offset.ply`, `bsData.json`, `vertex_order.json`
- Des avatars sample sont déjà dispo dans `LAM_Audio2Expression/assets/sample_lam/` (barbara, james, status, vfhq_case1) — peut être utilisé pour tester sans Blender

**Étape 2 — Ajouter TTS dans agent-gui**
- Options légères : `pyttsx3` (offline, stdlib-like), `edge-tts` (Microsoft gratuit), `kokoro` (qualité)
- Output : fichier WAV 16kHz mono → passé à Audio2Expression

**Étape 3 — Ajouter WebSocket dans agent_gui/app.py**
- Ajouter endpoint WebSocket `/ws/avatar`
- Au moment où l'agent répond : TTS → Audio2Expression → stream blendshapes JSON à 30fps vers browser

**Étape 4 — Remplacer canvas pixel-art par renderer WebGL**
- Package npm : `gaussian-splat-renderer-for-lam` (repo : `aigc3d/LAM_WebRender`)
- API : charge le ZIP avatar une fois, polling `getExpressionData()` à chaque frame rAF
- Ou utiliser les avatars sample GLB directement si le format est compatible

**Alternative rapide sans Blender :**
Utiliser les avatars sample fournis (`barbara`, `james`) pour tester le pipeline complet avant d'avoir son propre avatar.

---

### Architecture finale visée

```
agent_gui/
  app.py          ← ajouter WebSocket + appel subprocess Audio2Expression
  avatar_lam.py   ← nouveau module : lance lam_a2e env, streame blendshapes
  tts.py          ← nouveau module : TTS → WAV 16kHz
static/
  app.js          ← remplacer canvas pixel-art par WebGL renderer LAM
  avatar.zip      ← avatar exporté depuis photo (ou sample barbara/james)
```

### Commandes utiles pour reprendre

```bash
# Tester Audio2Expression
cd /mnt/DATA/WORK/LAM_Audio2Expression
$HOME/miniconda3/bin/conda run -n lam_a2e python inference_streaming_audio.py

# Lancer app Gradio LAM (pour exporter avatar depuis photo, nécessite Blender)
cd /mnt/DATA/WORK/LAM
$HOME/miniconda3/bin/conda run -n lam python app_lam.py

# Lancer app Gradio Audio2Expression (demo complète avec WebGL)
cd /mnt/DATA/WORK/LAM_Audio2Expression
$HOME/miniconda3/bin/conda run -n lam_a2e python app_lam_audio2exp.py
```


File created successfully at: /home/wildlama/.claude/projects/-home-wildlama/memory/project_agent_gui_lam.md (file state is current in your context — no need to Read it back)

---
name: project-agent-gui-lam
description: "GUI pour agents IA avec avatars LAM 3D parlants en temps réel — état d'avancement complet"
metadata:
  node_type: memory
  type: project
  originSessionId: 7de9b929-9050-430b-9b36-f74849c1c0a7
---

## Projet principal

`/mnt/DATA/WORK/agent-gui` — web app locale (Python stdlib + vanilla JS) pour piloter des agents LLM avec interface graphique. V1 fonctionnelle avec avatar ASCII, canvas pixel-art animé, chat, sessions JSONL, adaptateurs CLI.

**Why:** Créer une surcouche graphique universelle pour agents IA (Hermes, Claude Code, etc.) avec avatars visuels modélisables.

**How to apply:** Quand on reprend le travail, partir de cet état et continuer vers l'intégration LAM.

---

## Intégration LAM — état au 2026-06-15

### Objectif
Ajouter des avatars 3D photoréalistes parlants en temps réel dans agent-gui. Pipeline :
```
[Agent répond] → [TTS → audio 16kHz mono]
    → [Python: Audio2Expression → 52 blendshapes ARKit @ 30fps]
        → [WebSocket JSON] → [Browser: WebGL Gaussian Splatting renderer]
```

### Ce qui est installé et fonctionnel ✅

**Conda envs sur cette machine :**
- `lam` (Python 3.11) — pour LAM core (génération avatar depuis photo)
  - PyTorch 2.11+cu128, pytorch3d 0.7.9, diff-gaussian-rasterization, nvdiffrast, simple-knn
  - gcc 13 installé dans l'env (nécessaire pour compiler pytorch3d avec CUDA 12.8)
- `lam_a2e` (Python 3.10) — pour Audio2Expression (live talking)
  - PyTorch 2.11+cu128, transformers, librosa, gradio-gaussian-render

**Repos clonés :**
- `/mnt/DATA/WORK/LAM` — modèle LAM core (génère avatar 3D depuis photo)
- `/mnt/DATA/WORK/LAM_Audio2Expression` — Audio2Expression (audio → blendshapes)
  - Poids téléchargés et extraits : `pretrained_models/lam_audio2exp_flow/`
  - **Testé et fonctionnel** : 52 canaux ARKit, 30 FPS, 4ms/seconde d'audio après warm-up

**Résultat test Audio2Expression :**
- Input : `assets/sample_audio/BarackObama_english.wav`
- Output : `bsData.json` — 240 frames à 30fps, 52 blendshapes ARKit par frame
- Format : `{ "names": ["browDownLeft", "jawOpen", ...], "frames": [[...], ...], "metadata": {"fps": 30} }`

**Hardware :**
- GPU : RTX 5090, 32 Go VRAM
- Drivers NVIDIA : 595.71, CUDA 13.2 (max supporté)
- CUDA Toolkit 12.8 installé via conda dans les envs

---

### Ce qui reste à faire

**Étape 1 — Exporter l'avatar 3D (bloquant : nécessite Blender 4.0+)**
- Vérifier si Blender est installé : `blender --version`
- Si oui : lancer `app_lam.py` dans l'env `lam`, charger une photo portrait, exporter le ZIP avatar
- Le ZIP contient : `animation.glb`, `skin.glb`, `offset.ply`, `bsData.json`, `vertex_order.json`
- Des avatars sample sont déjà dispo dans `LAM_Audio2Expression/assets/sample_lam/` (barbara, james, status, vfhq_case1) — peut être utilisé pour tester sans Blender

**Étape 2 — Ajouter TTS dans agent-gui**
- Options légères : `pyttsx3` (offline, stdlib-like), `edge-tts` (Microsoft gratuit), `kokoro` (qualité)
- Output : fichier WAV 16kHz mono → passé à Audio2Expression

**Étape 3 — Ajouter WebSocket dans agent_gui/app.py**
- Ajouter endpoint WebSocket `/ws/avatar`
- Au moment où l'agent répond : TTS → Audio2Expression → stream blendshapes JSON à 30fps vers browser

**Étape 4 — Remplacer canvas pixel-art par renderer WebGL**
- Package npm : `gaussian-splat-renderer-for-lam` (repo : `aigc3d/LAM_WebRender`)
- API : charge le ZIP avatar une fois, polling `getExpressionData()` à chaque frame rAF
- Ou utiliser les avatars sample GLB directement si le format est compatible

**Alternative rapide sans Blender :**
Utiliser les avatars sample fournis (`barbara`, `james`) pour tester le pipeline complet avant d'avoir son propre avatar.

---

### Architecture finale visée

```
agent_gui/
  app.py          ← ajouter WebSocket + appel subprocess Audio2Expression
  avatar_lam.py   ← nouveau module : lance lam_a2e env, streame blendshapes
  tts.py          ← nouveau module : TTS → WAV 16kHz
static/
  app.js          ← remplacer canvas pixel-art par WebGL renderer LAM
  avatar.zip      ← avatar exporté depuis photo (ou sample barbara/james)
```

### Commandes utiles pour reprendre

```bash
# Tester Audio2Expression
cd /mnt/DATA/WORK/LAM_Audio2Expression
$HOME/miniconda3/bin/conda run -n lam_a2e python inference_streaming_audio.py

# Lancer app Gradio LAM (pour exporter avatar depuis photo, nécessite Blender)
cd /mnt/DATA/WORK/LAM
$HOME/miniconda3/bin/conda run -n lam python app_lam.py

# Lancer app Gradio Audio2Expression (demo complète avec WebGL)
cd /mnt/DATA/WORK/LAM_Audio2Expression
$HOME/miniconda3/bin/conda run -n lam_a2e python app_lam_audio2exp.py
```


---
name: user-profile
description: Profil technique de l'utilisateur — niveau, contexte, préférences
metadata:
  type: user
---

Développe une GUI locale pour ses agents IA (`/mnt/DATA/WORK/agent-gui`). Travaille sur Linux (Ubuntu 26.04), possède un RTX 5090. Niveau technique intermédiaire : comprend les concepts mais a besoin d'accompagnement pour les étapes d'installation et de configuration. Préfère qu'on exécute les commandes directement plutôt que de lui demander de les taper. Travaille en français.


File created successfully at: /home/wildlama/.claude/projects/-home-wildlama/memory/user_profile.md (file state is current in your context — no need to Read it back)

---
name: user-profile
description: "Profil technique de l'utilisateur — niveau, contexte, préférences"
metadata:
  node_type: memory
  type: user
  originSessionId: 7de9b929-9050-430b-9b36-f74849c1c0a7
---

Développe une GUI locale pour ses agents IA (`/mnt/DATA/WORK/agent-gui`). Travaille sur Linux (Ubuntu 26.04), possède un RTX 5090. Niveau technique intermédiaire : comprend les concepts mais a besoin d'accompagnement pour les étapes d'installation et de configuration. Préfère qu'on exécute les commandes directement plutôt que de lui demander de les taper. Travaille en français.


Mémo sauvegardé. Quand tu reviens, dis juste "on reprend le projet agent-gui LAM" et j'aurai tout le contexte — ce qui est installé, ce qui fonctionne, et ce qui reste à faire.

**Résumé de où on en est :**
- Audio2Expression tourne et produit des blendshapes en 4ms ✅
- Il reste : vérifier Blender (pour exporter ton avatar 3D depuis une photo), puis brancher TTS + WebSocket dans agent-gui