使用Python实现照片生成数字人口播视频

核心思路是:将文本转为语音 → 用照片+音频生成说话人视频。推荐两个主流方案:SadTalker(开源本地运行)和LivePortrait(云服务API)。

方案一:SadTalker(推荐,纯Python实现)

SadTalker仅需一张照片 + 一段音频即可生成逼真的说话人视频,支持本地部署。

  1. 环境准备
#克隆SadTalker项目
git clone https://github.com/OpenTalker/SadTalker.git
cd SadTalker

# 安装依赖(需Python 3.8+,6GB以上显存)
pip install torch torchvision
pip install -r requirements.txt

# 下载预训练模型权重
bash scripts/download_models.sh
  1. 完整Python实现代码
import os
import asyncio
import edge_tts  # 文本转语音
import sys
from pathlib import Path

class DigitalHumanGenerator:
    def __init__(self, sadtalker_path="SadTalker"):
        """初始化数字人生成器"""
        self.sadtalker_path = Path(sadtalker_path)
        self.output_path = Path("output")
        self.output_path.mkdir(exist_ok=True)
        
        # 检查环境
        if not self.sadtalker_path.exists():
            raise Exception("SadTalker目录不存在,请先克隆项目")
    
    async def text_to_speech(self, text, audio_path="temp_audio.wav"):
        """步骤1:文本转语音(使用edge-tts,免费)"""
        print(f"🎙️ 正在生成语音: {text[:30]}...")
        
        # 选择中文语音
        communicate = edge_tts.Communicate(text, "zh-CN-XiaoxiaoNeural")
        await communicate.save(audio_path)
        
        print(f"✅ 语音文件已保存: {audio_path}")
        return audio_path
    
    def generate_video(self, photo_path, audio_path, result_dir=None):
        """步骤2:调用SadTalker生成视频"""
        if result_dir is None:
            result_dir = self.output_path
        
        print(f"🎬 正在生成数字人视频...")
        print(f"   照片: {photo_path}")
        print(f"   音频: {audio_path}")
        
        # 构建SadTalker命令
        cmd = [
            sys.executable,  # Python解释器路径
            str(self.sadtalker_path / "inference.py"),
            "--driven_audio", audio_path,
            "--source_image", photo_path,
            "--result_dir", str(result_dir),
            "--still",  # 保持头部稳定
            "--preprocess", "full",  # 全图预处理
            "--batch_size", "1"
        ]
        
        # 执行生成
        try:
            import subprocess
            result = subprocess.run(cmd, capture_output=True, text=True, cwd=self.sadtalker_path)
            
            if result.returncode == 0:
                # 查找生成的视频
                video_files = list(Path(result_dir).glob("*.mp4"))
                if video_files:
                    video_path = video_files[-1]  # 取最新生成的
                    print(f"✅ 视频生成成功: {video_path}")
                    return str(video_path)
                else:
                    raise Exception("未找到生成的视频文件")
            else:
                print(f"❌ 生成失败: {result.stderr}")
                raise Exception(f"SadTalker执行出错: {result.stderr}")
                
        except Exception as e:
            print(f"❌ 错误: {e}")
            raise
    
    async def generate(self, photo_path, text, cleanup=True):
        """主流程:文本→语音→视频"""
        try:
            # 生成语音
            audio_path = await self.text_to_speech(text)
            
            # 生成视频
            video_path = self.generate_video(photo_path, audio_path)
            
            # 清理临时文件
            if cleanup and os.path.exists(audio_path):
                os.remove(audio_path)
            
            print(f"🎉 数字人口播视频生成完成!")
            print(f"📁 文件路径: {video_path}")
            
            return video_path
            
        except Exception as e:
            print(f"❌ 生成失败: {e}")
            return None

# ==================== 使用示例 ====================
if __name__ == "__main__":
    # 初始化生成器
    generator = DigitalHumanGenerator(sadtalker_path="./SadTalker")
    
    # 输入配置
    YOUR_PHOTO = "your_photo.jpg"  # 替换为你的照片路径
    SPEECH_TEXT = "大家好,我是你的数字人分身。今天很高兴能和大家见面,希望我的介绍能帮助你更好地了解数字人技术。"
    
    # 检查文件
    if not os.path.exists(YOUR_PHOTO):
        print(f"❌ 照片文件不存在: {YOUR_PHOTO}")
        exit(1)
    
    # 运行生成
    print("="*50)
    print("数字人口播视频生成工具")
    print("="*50)
    
    # 异步执行
    video_result = asyncio.run(generator.generate(YOUR_PHOTO, SPEECH_TEXT))
    
    if video_result:
        print(f"\n✨ 成功!视频已保存至: {video_result}")
    else:
        print("\n💔 生成失败,请检查错误信息")
  1. 运行方式
# 安装edge-tts
pip install edge-tts

# 运行脚本
python digital_human_generator.py

参数说明:

• YOUR_PHOTO: 清晰的正面人像照片,512x512像素以上,JPG/PNG格式
• SPEECH_TEXT: 不超过200字的中文文本(太长可能导致显存不足)
• 生成时间:约10-20分钟(取决于GPU性能)


方案二:LivePortrait API(更快捷)

如果不想本地部署,可使用阿里云/百度云的LivePortrait API,仅需调用Python SDK。

  1. 安装SDK
pip install speedpix  # 阿里云智作工坊SDK
  1. 调用代码(阿里云版)
from speedpix import Client
import asyncio

async def generate_digital_human_api(photo_path, text):
    """调用阿里云LivePortrait API生成视频"""
    
    # 步骤1:文本转语音
    import edge_tts
    audio_path = "temp_audio.wav"
    communicate = edge_tts.Communicate(text, "zh-CN-XiaoxiaoNeural")
    await communicate.save(audio_path)
    
    # 步骤2:音频转驱动视频(简单示例可用音频波形可视化)
    # 实际需准备驱动视频或使用API的音频驱动功能
    
    # 步骤3:调用API
    client = Client(api_key="your_api_key")  # 替换为你的API密钥
    
    result = client.run(
        workflow_id="01jz1yvm3f7n9xc8kgbhmcf031",  # 你的工作流ID
        input={
            "portrait_image": photo_path,
            "driving_video": audio_path,  # 某些版本支持音频直接驱动
            "frame_rate": 30
        }
    )
    
    # 保存结果
    if 'videos' in result:
        result['videos']['url'].save("output_digital_human.mp4")
        return "output_digital_human.mp4"
    
    return None

# 使用示例
# asyncio.run(generate_digital_human_api("photo.jpg", "你的口播文本"))

注意:LivePortrait API通常需要驱动视频而非直接音频,需先将音频转为面部表情视频,或使用支持音频驱动的版本。


关键技术点
照片要求
• 清晰度:正面、光线均匀、无遮挡
• 尺寸:512x512像素以上
• 格式:JPG或PNG
• 背景:纯色背景效果更佳
文本优化
• 长度控制在150字以内(避免显存溢出)
• 添加标点符号,让语音更自然
• 避免特殊符号和英文混排
性能优化

# SadTalker参数调优
--batch_size 1       # 批量大小,显存小设为1
--still              # 减少头部晃动
--preprocess full    # 完整预处理,效果更好
--enhancer gfpgan    # 使用GFPGAN增强面部(可选)

总结
方案 优点 缺点 适合场景
SadTalker 开源免费、本地运行、隐私性好 需要GPU、生成较慢 个人创作、隐私数据
LivePortrait API 速度快、效果精细、无需硬件 付费、需网络、配置复杂 企业应用、快速开发
推荐:个人用户优先选择SadTalker,有GPU可直接运行;无GPU可使用Coze等在线平台(见相关教程)。

完整SadTalker项目地址:https://github.com/OpenTalker/SadTalker


用 Python 将你的照片和文本变成数字人口播视频,在技术上已经非常成熟。目前主流的方案是使用像 Linly-Talker 这样集成了多种先进模型的开源框架,它能高质量地完成这项任务。

下面的表格梳理了实现这一目标的核心模块和当前推荐的技术选项,你可以对整体架构有个快速的了解。

核心模块 功能 推荐技术/工具
形象加载 导入并处理你的照片 OpenCV, Pillow
语音合成 将文本转换为语音 GPT-SoVITS, Edge-TTS, Coqui TTS
视频生成 驱动照片口型、表情与语音同步 SadTalker, Wav2Lip

🛠️ 如何开始:Linly-Talker 实战指南

  1. 环境准备
    首先,你需要一个具备Python 3.10、PyTorch和CUDA 11.8的环境。推荐使用NVIDIA显卡,显存最好不低于12GB。

  2. 安装与部署
    按照以下步骤安装 Linly-Talker:

# 1. 从代码仓库克隆项目
git clone https://github.com/Kedreamix/Linly-Talker.git
cd Linly-Talker

# 2. 创建并激活一个独立的Python环境
conda create -n linly python=3.10 -y
conda activate linly

# 3. 安装PyTorch等核心依赖
pip install torch==2.1.2+cu118 torchvision==0.16.2+cu118 torchaudio==2.1.2+cu118 --index-url https://download.pytorch.org/whl/cu118

# 4. 安装项目所需的其他库
pip install -r requirements.txt

# 5. 下载必要的预训练模型(注意:模型较大)
bash scripts/download_models.sh
  1. 一键运行
    完成安装后,你可以通过以下命令启动一个交互式的Web界面来体验功能:
python app.py --port 7860

在浏览器中打开 http://localhost:7860,通常你只需要上传照片、输入文本,系统就会自动完成后续所有步骤。

💡 进阶使用:代码集成与个性化

如果想把数字人功能集成到你自己的Python项目中,可以参考下面的代码示例,它清晰地展示了整个工作流程:

# one_shot.py
import os
from linly_talker.asr import WhisperASR  # 语音识别(可选)
from linly_talker.llm import LinlyLLM    # 大型语言模型(如需优化文本)
from linly_talker.tts import GPTSoVITSTTS # 语音合成
from linly_talker.thg import SadTalker    # 生成数字人视频

# 初始化各模块 (首次使用需要下载模型)
asr = WhisperASR("large-v3")
llm = LinlyLLM(model_path="checkpoints/Linly-Chinese-LLaMA-2-7B-hf")
tts = GPTSoVITSTTS(sovits_path="checkpoints/gsv-v2finetune.pth")
thg = SadTalker(checkpoint_path="checkpoints/SadTalker_V0.0.2_512.safetensors")

def create_talking_head(user_image_path, input_text, output_video_path):
    """核心函数:生成数字人口播视频"""

    # 1. 语音合成 (TTS):将文本转为语音文件
    audio_path = tts.synthesize(input_text)

    # 2. 生成视频 (Talking Head Generation):让图片按语音动起来
    video_path = thg.generate(image=user_image_path, audio=audio_path)

    return video_path

# 使用示例
if __name__ == "__main__":
    photo = "demo/user_portrait.jpg"  # 替换为你的照片路径
    text = "大家好,这是我用Python生成的第一个数字人口播视频。"  # 替换为你的口播文本

    output_video = create_talking_head(photo, text, "my_first_ai_video.mp4")
    print(f"口播视频已生成:{output_video}")

🚀 效果优化与问题排查

· 提升音质:如果对默认语音不满意,可以使用 GPT-SoVITS 等工具,用你自己的一段简短录音来克隆音色,让数字人使用你的声音。
· 改善画面:如果生成的口型不同步,可以尝试换用 Wav2Lip 或 MuseTalk 等专门优化口型的模型。
· 处理报错:
· ModuleNotFoundError: 通常通过 pip install 安装缺失的包即可解决。
· CUDA Out of Memory: 这表示显存不够了。可以尝试在代码中降低视频生成的分辨率或使用半精度(FP16)模式。

希望这份指南能帮助你顺利创造出自己的数字人视频。如果在实际操作中遇到困难,可以多查阅 Linly-Talker 项目的官方文档和社区讨论。祝你玩得开心!

Logo

有“AI”的1024 = 2048,欢迎大家加入2048 AI社区

更多推荐