数字人JoyVASA 实战记录

一、项目背景

最近在看数字人相关内容,找到这个项目,JoyVASA 是京东健康(JD Health International Inc.)与浙江大学联合开源的扩散模型驱动的音频→肖像动画框架,论文:

JoyVASA: Portrait and Animal Image Animation with Diffusion-Based Audio-Driven Facial Dynamics and Head Motion Generation

它解决的是单张静态图 + 一段音频 → 一段会说话、有表情、会点头的视频,论文侧重点是长视频的稳定性与多类主体(人/动物)的统一建模。

  • 音频驱动 ------ 仅需一张参考图 + 一段音频,自动生成唇形同步
  • 真人肖像动画 ------ 写实人像说话视频
  • 动物肖像动画 ------ 猫、狗等动物面部说话动画
  • 多语种适配 ------ 训练数据为私有中文 + 公开英文混合,中英文都可用
  • 长视频稳定 ------ 滑动窗口推理,避免长序列崩坏

二、技术原理

JoyVASA 不是端到端直接出视频,而是两阶段解耦的:

复制代码
┌─────────────────────────────────────────────────────────────┐
│  Stage 1: 离线/一次性 - 训练解耦的人脸表征                    │
│  (LivePortrait 提供 appearance encoder + motion encoder)    │
└─────────────────────────────────────────────────────────────┘
                            ↓
┌─────────────────────────────────────────────────────────────┐
│  Stage 2: 推理时 - 扩散 Transformer 采样运动序列                │
│  audio features (HuBERT/wav2vec2) → motion sequences          │
└─────────────────────────────────────────────────────────────┘
                            ↓
┌─────────────────────────────────────────────────────────────┐
│  Warping + Generator - 用采样到的关键点 warp 表征,渲染出视频     │
└─────────────────────────────────────────────────────────────┘

2.1 解耦面部表征(Decoupled Facial Representation)

参考图 → appearance encoder(LivePortrait)提取静态 3D 面部外观特征

参考图 → motion encoder 提取 3D 关键点

这一拆分的好处:外观与运动解耦,任意静态 3D 表征都能和任意运动序列组合,所以长视频可以分段生成运动、复用同一张外观,天然解决帧间连续性问题。

2.2 扩散 Transformer 生成运动

音频 → 音频编码器(chinese-hubert-base 适配中文) → 音频特征

音频特征 → DiT(Diffusion Transformer) 滑动窗口采样 → 目标运动序列

identity-independent:运动生成不依赖人物身份,所以同一段运动可以驱动不同的人/动物。

2.3 渲染

源关键点 + 采样到的目标关键点 → 计算变形场 → warp appearance feature → generator → 视频帧。


三、环境准备

3.1 硬件与系统(官方已测试)

平台 系统 CUDA 显卡
Linux Ubuntu 20.04 12.1 A100
Windows Windows 11 12.1 RTX 4060 Laptop 8GB

实际社区反馈:RTX 3090 / 4090 / 4090D 都能跑,显存建议 ≥ 8GB。

3.2 软件依赖

bash 复制代码
# 1. 基础环境
conda create -n joyvasa python=3.10 -y
conda activate joyvasa

# 2. Python 依赖
pip install -r requirements.txt

# 3. 系统依赖 ffmpeg
sudo apt-get update
sudo apt-get install ffmpeg -y

# 4. 可选:仅当你需要跑 animal 模式时
cd src/utils/dependencies/XPose/models/UniPose/ops
python setup.py build install
cd -

MultiScaleDeformableAttention 不是 pip install,而是要进子目录 setup.py 源码编译。这是新手最常踩的坑之一。

3.3 源码克隆

bash 复制代码
git clone https://github.com/jdh-algo/JoyVASA.git
cd JoyVASA

四、权重下载

这是全网最容易出错的地方。原仓库默认目录名是 pretrained_weights/,不是 checkpoints/。整套项目需要 5 套权重:

4.1 JoyVASA 主模型

bash 复制代码
mkdir -p pretrained_weights
cd pretrained_weights
git lfs install
git clone https://huggingface.co/jdh-algo/JoyVASA
cd ..

4.2 音频编码器

bash 复制代码
cd pretrained_weights

# 中文 HuBERT
git clone https://huggingface.co/TencentGameMate/chinese-hubert-base

# 可选:wav2vec2-base
# git clone https://huggingface.co/facebook/wav2vec2-base-960h
cd ..

4.3 LivePortrait 权重

bash 复制代码
cd pretrained_weights
# 方法 A:huggingface_hub CLI
pip install -U "huggingface_hub[cli]"
huggingface-cli download KwaiVGI/LivePortrait \
  --local-dir . \
  --exclude "*.git*" "README.md" "docs"
cd ..

4.4 InsightFace buffalo_l 模型

bash 复制代码
# 一般随 huggingface-cli 下载 LivePortrait 时会自动包含
# 若缺失,自行:
mkdir -p pretrained_weights/insightface/models/buffalo_l
# 从 insightface 官方源或 LivePortrait 仓库的对应位置取
# 2d106det.onnx、det_10g.onnx 是关键文件

4.5 最终目录结构(官方要求)

复制代码
JoyVASA/
./pretrained_weights/
├── insightface                                                                
│   └── models                                                              
│       └── buffalo                            
│           ├── 2d106det.onnx                                                        
│           └── det_10g.onnx   
├── JoyVASA
│   ├── motion_generator
│   │   └── iter_0020000.pt
│   └── motion_template
│       └── motion_template.pkl
├── liveportrait
│   ├── base_models
│   │   ├── appearance_feature_extractor.pth
│   │   ├── motion_extractor.pth
│   │   ├── spade_generator.pth
│   │   └── warping_module.pth
│   ├── landmark.onnx
│   └── retargeting_models
│       └── stitching_retargeting_module.pth
├── liveportrait_animals
│   ├── base_models
│   │   ├── appearance_feature_extractor.pth
│   │   ├── motion_extractor.pth
│   │   ├── spade_generator.pth
│   │   └── warping_module.pth
│   ├── retargeting_models
│   │   └── stitching_retargeting_module.pth
│   └── xpose.pth
├── TencentGameMate:chinese-hubert-base
│   ├── chinese-hubert-base-fairseq-ckpt.pt
│   ├── config.json
│   ├── gitattributes
│   ├── preprocessor_config.json
│   ├── pytorch_model.bin
│   └── README.md
└── wav2vec2-base-960h               
│   ├── config.json                  
│   ├── feature_extractor_config.json
│   ├── model.safetensors
│   ├── preprocessor_config.json
│   ├── pytorch_model.bin
│   ├── README.md
│   ├── special_tokens_map.json
│   ├── tf_model.h5
│   ├── tokenizer_config.json
│   └── vocab.json
├── src/
├── inference.py
├── app.py
├── requirements.txt
└── train.py

五、三种运行方式

5.1 命令行推理(inference.py)

5.1.1 真人模式
bash 复制代码
python inference.py \
  -r assets/examples/imgs/joyvasa_003.png \
  -a assets/examples/audios/joyvasa_003.wav \
  --animation_mode human \
  --cfg_scale 2.0

joyvasa_003_joyvasa_003

5.1.2 动物模式
bash 复制代码
python inference.py \
  -r assets/examples/imgs/joyvasa_001.png \
  -a assets/examples/audios/joyvasa_001.wav \
  --animation_mode animal \
  --cfg_scale 2.0
5.1.3 短命令 vs 全命令
说明
-r --reference 参考图
-a --audio 驱动音频
--animation_mode human / animal
--cfg_scale 表情强度
--driving_option expression-friendly / pose-friendly
--driving_multiplier 运动幅度倍率
--flag_normalize_lip 是否归一化唇形
--flag_relative_motion 是否相对运动
--do_crop / --scale / --vx_ratio / --vy_ratio 裁剪控制

5.2 WebUI(app.py)

bash 复制代码
python app.py

启动后浏览器打开:

http://127.0.0.1:7862 ← 注意是 7862,不是 7860

WebUI 包含三大区:

  • Input Section:上传参考图 + 音频
  • Configuration Section:动画模式、CFG、裁剪、归一化
  • Generate Button + 输出视频

Gradio 默认端口是 7860,但官方 app.py 写的是 7862,这是为了避免和 LivePortrait 等同生态项目冲突。


六、参数详解

6.1 关键参数

参数 官方说明 默认 范围
animation_mode 动画模式 human human / animal
cfg_scale 表情强度 4.0 0.0 ~ 10.0
driving_option 驱动风格 expression-friendly expression-friendly / pose-friendly
driving_multiplier 运动强度倍率 1.0 0.0 ~ 2.0
flag_normalize_lip 唇形归一化 True True/False
flag_relative_motion 相对运动 True True/False
flag_remap_input 贴回原图 True True/False
flag_stitching_input 拼接模块 True True/False
do_crop 是否裁剪 True True/False
scale 裁剪缩放 2.3 1.8 ~ 4.0
vx_ratio 横向裁剪偏移 0.0 -0.5 ~ 0.5
vy_ratio 纵向裁剪偏移 -0.125 -0.5 ~ 0.5

cfg_scale 推荐 1.5~2.5,官方源码默认值是 4.0,实测 2.0~4.0 出自然结果,>5 表情夸张、<1.5 表情平淡。

6.2 参数作用图谱

复制代码
                   ┌──────────────────┐
                   │  cfg_scale        │
                   │  ↑ 更夸张         │
                   │  ↓ 更含蓄         │
                   └──────────────────┘
                            ↕
   animation_mode ──► human / animal pipeline 选择
                            ↕
   ┌────────────────────┐   ┌────────────────────┐
   │ driving_option     │   │ driving_multiplier │
   │ expression-friendly│   │  ↑ 运动更明显       │
   │ pose-friendly      │   │  ↓ 运动更轻微       │
   └────────────────────┘   └────────────────────┘

   裁剪三件套(scale / vx_ratio / vy_ratio) ──► 控制人脸在画面中的取景位置

6.3 调参经验值

目标 推荐参数组合
自然口播 cfg_scale=2.0 driving_option=expression-friendly driving_multiplier=1.0
头部动作多 driving_option=pose-friendly driving_multiplier=1.3
夸张表情(主播风格) cfg_scale=4.0~5.0 driving_multiplier=1.5
几乎不动(配静态BGM) cfg_scale=1.0 driving_multiplier=0.5

七、输入素材规范

7.1 图片

建议
主体 单一人物或单一动物面部
角度 正面 / 轻微侧脸最佳,大侧脸容易崩
清晰度 面部无遮挡、无重度美颜、无糊脸
分辨率 ≥ 512×512,过低影响关键点提取
动物 眼睛、嘴部必须清晰可见

7.2 音频

建议
格式 WAV PCM 16-bit
采样率 16 kHz 单声道(官方最优)
时长 任意,内部用滑动窗口
质量 人声清晰、低背景噪音、无明显混响

格式转换示例:

bash 复制代码
ffmpeg -i input.mp3 -vn -ar 16000 -ac 1 -c:a pcm_s16le output.wav

八、能力边界

官方明确擅长

  • 真人 / 猫狗等动物面部说话动画
  • 中英文双语文本驱动
  • 唇形同步质量高、表情自然
  • 长视频通过滑动窗口稳定推理
  • 轻量级、依赖干净、MIT 可商用

官方不擅长 / 文档未声明

  • 大幅转头、大幅肢体动作
  • 复杂背景动态、镜头运镜
  • 多人 / 多动物同时动画
  • 二次元 / 插画肖像(虽然 human 模式勉强能跑,但官方未声明)
  • 实时推理(论文自述:real-time 是 future work)
  • 水印、溯源、防深伪(没有任何机制)

⚠️ 商用合规提醒

  • MIT 协议本身允许商用,但 依赖项(LivePortrait、wav2vec2、HuBERT)各自的协议需要单独核查
  • 训练数据含京东私有中文数据 + 公开英文数据,商业化前建议法务审一遍数据来源

九、常见问题与排查

现象 原因 解决
ModuleNotFoundError: MultiScaleDeformableAttention animal 模式必装,源码编译 src/utils/dependencies/XPose/models/UniPose/opssetup.py build install
ffmpeg: command not found 缺系统依赖 apt-get install ffmpeg
WebUI 打开 7860 端口空白 端口错了 实际是 7862
cfg_scale=2 表情仍夸张 误用全音轨 wav,采样率不是 16k 用 ffmpeg 转 16k mono wav
动物图跑 human 模式脸崩 mode 不匹配 --animation_mode animal
推理非常慢 缺 CUDA / 用 CPU 跑 必须有 NVIDIA GPU + CUDA 12.x
生成的视频没声音 这是正常的 inference.py 只输出画面,声音需自己用 ffmpeg 合回

把声音合回的官方习惯做法:

bash 复制代码
ffmpeg -i generated_video.mp4 -i input.wav -c:v copy -c:a aac final.mp4

十、总结

JoyVASA 把音频驱动肖像动画这件事,做到了一个比较舒服的折中点:

  1. 架构上用LivePortrait 解耦表征 + DiT 扩散生成运动的两阶段设计,绕开了端到端扩散模型长视频崩坏的硬伤。
  2. 生态上原生支持动物、中文友好、MIT 协议、依赖干净,部署门槛低。
  3. 能力上对自然表情 + 唇形同步 + 轻点头这一档需求,目前是开源里做得比较像样的。
  4. 取舍上明确不追求大幅动作、镜头运镜、实时性,这些是显式不擅长。
相关推荐
PhotonixBay2 小时前
从粗糙度到三维形貌:激光共聚焦显微镜实现微米级表面分析
图像处理·人工智能·测试工具·算法
格林威3 小时前
C#图像处理:使用imagemagick实现像素放大水印转换等多种功能
android·开发语言·图像处理·人工智能·计算机视觉·c#·视觉检测
W_326001 天前
Python-OpenCV 轮廓进阶:旋转最小外接矩形、图像矩求质心、嵌套层级 hierarchy、轮廓形状匹配
图像处理·python·opencv·机器学习·计算机视觉
牧羊人.3331 天前
计算机视觉基础 第 9 章|实战:银行卡号识别
图像处理·人工智能·opencv·计算机视觉·图搜索算法
AndrewHZ1 天前
图像处理入门010 | Pillow 与 OpenCV 对比:双库图像读写实战
图像处理·opencv·计算机视觉·pillow
W_326002 天前
Python-OpenCV边缘检测与阈值分割:Sobel、Scharr、Laplacian、Canny、全局与自适应阈值
开发语言·图像处理·python·opencv·机器学习
这张生成的图像能检测吗2 天前
图像处理 / 底层视觉论文解析汇总目录
图像处理·人工智能
AndrewHZ2 天前
图像处理入门009 | OpenCV 图像读取与显示:imread/imshow 全解析
图像处理·python·opencv·算法·计算机视觉·图像显示
W_326003 天前
Python-OpenCV图像像素与通道:通道拆分合并、深浅拷贝
图像处理·人工智能·python·opencv·机器学习