返回 ppt-master
audio-narration.md
根目录 / docs / zh / audio-narration.md
1 # 音频旁白与视频导出
2
3 [English](../audio-narration.md) | [Chinese](./audio-narration.md)
4
5 ---
6
7 PPT Master 可以把演讲者备注转成逐页音频旁白(默认基于 [`edge-tts`](https://github.com/rany2/edge-tts) —— 微软 Edge 的在线神经网络语音;也可配置 ElevenLabs、MiniMax、Qwen TTS、CosyVoice 使用高质量或复刻音色)。Edge、ElevenLabs、MiniMax,以及支持时间戳的 CosyVoice 音色,都会从同一次合成返回的 provider 计时生成逐页 SRT。Qwen 当前 TTS API 不返回时间戳,因此仍只生成音频。音频可继续嵌入 PPTX,供 PowerPoint 使用原生视频导出。
8
9 ## 你会得到什么
10
11 - 每页一个音频文件,存放于 `<project_path>/audio/`,文件名与 SVG 对齐(`01_cover.mp3`、`02_market_landscape.mp3` …)。
12 - 使用 provider 原生计时字幕时,每页还有一个同名字幕文件,与音频一起存放于 `<project_path>/audio/`(`01_cover.srt`、`02_market_landscape.srt` …)。每个文件使用以 `00:00:00,000` 为原点的页内时间轴;provider 的词级或字符级时间戳都会重组为同一套紧凑 cue。
13 - 完整生成成功后写出精简的 `<project_path>/audio/manifest.json`,只记录 provider、模型、音频/字幕格式、相关音色参数,以及代替云端 voice ID 原文的 SHA-256 指纹;不包含逐页清单、产物哈希或 API Key,正常生成过程也不会读取它。
14 - 选择旁白 cue 同步时,规范的 `animations.json` 与逐页 SRT 会派生 `narration_animations.json`,让无点击对象动画等待相关字幕 cue;与旁白无关的自定义动画则保留规范配置中的原始计时。两个动画 sidecar 都不存在时,旁白导出不会创建 sidecar,而是继承基础导出的已解析 motion。存在逐页 SRT 时,这些路径都可以生成与最终 PPTX 时间轴一致的 `<project_path>/audio/total.srt`;PowerPoint 导出视频后,`video_subtitles.py` 可把冻结的旁白文本与实际视频音轨对齐,生成交付用外挂字幕。
15 - 可选重新导出:在 `exports/` 生成新版 PPTX,每页对应的 `m4a` / `mp3` / `wav` 音频已嵌入到该页,且页面推进时间根据可配置的页前起始下限、音频长度和页尾停留自动设置——无人值守自动播放和视频导出都不用再手动调时间。旁白不会早于页面转场结束时启动。
16 - Windows 下可选原生视频导出:`powerpoint_video.py` 把最终带旁白 PPTX 交给 PowerPoint 2016+,并等待其原生 MP4 编码成功或失败。该 raw MP4 保留视觉动画与旁白路径,但 PowerPoint 不保证把原生转场音效或对象动画音效写入视频音轨。
17 - 原生导出路径直接交付 MP4 且存在已解析动画音效时,`video_sound_mix.py` 会生成独立的 float SFX WAV、最终混音 MP4 和 JSON 回执,证明 stem 已进入实际成片音轨,同时视频流保持不变。
18 - 也可以显式选择人工实时录制:用桌面版 Windows PowerPoint 全屏播放最终带旁白 deck,再由录屏器捕获放映画面和唯一一路应用 / 系统音频。它会录下 PowerPoint 实际播放的旁白与原生 cue,因此不能再运行 `video_sound_mix.py`。
19 - 演讲者备注原样保留。
20
21 ## 它是怎么做到的
22
23 1. **备注本身就是为 TTS 写的口播稿**。PPT Master 的 notes 规范刻意产出适合朗读的散文——没有 `[过渡]` / `[停顿]` 这种舞台标记,也没有 `要点:` / `时长:` 这种 meta 行——念出来的内容就是页面上的内容。
24 2. **AI 替你选音色**。当你提出生成旁白时,AI 根据 deck 的主语言(`zh-CN` / `en-US` / `ja-JP` / `ko-KR` / …)和所选 provider 拉取或解释可用音色,挑出 3–6 个候选,并用当前聊天语言为每个写一句调性说明(如“稳重男声·适合财报”)。语速/风格也会基于 notes 信息密度给出推荐值。
25 3. **配置一次确定**。Default Generate 和 Enhance Native 会一次确认 provider、音色、语速、是否嵌入 PPTX,以及是否继续导出视频。Quick 直接采用明确值,并自动补齐未指定的 provider、音色、语速和嵌入方式;只有明确要求直接交付视频时才开启视频导出。
26 4. **执行**。Edge、ElevenLabs、MiniMax,以及支持时间戳的 CosyVoice 音色,会依据同一次合成返回的 provider 计时,把每页音频和 SRT 一起写入 `audio/`;Qwen 和显式 CosyVoice 纯音频模式只写音频。完整生成成功后会原子写入 `audio/manifest.json` 记录来源。对于选择旁白 cue 同步的 Generate PPTX,逐页 SRT 与规范自定义动画会让 AI 将当前 SVG 内容组映射到编号后的 SRT cue,并派生无点击的 `narration_animations.json`;与旁白无关的自定义动画保留规范计时,没有动画 sidecar 时则继承基础导出的已解析 motion。随后再导出带音频的 PPTX;存在逐页 SRT 时,才从该 PPTX 读回实际计时并合并。自动视频交付继续调用 PowerPoint 原生编码器,存在 cue 时再完成验收后的混音;显式选择实时放映录制时,则捕获 PowerPoint 实际全屏画面与系统音频、跳过混音,并将交付字幕对齐到验收后的录屏。不支持长音频导入或自动拆分。
27
28 字幕保持为外部 SRT 文件:PPT Master 不把字幕嵌入 PPTX,也不烧录进 MP4。自动视频导出委托给本机 Windows PowerPoint,并不是另一套渲染器。
29
30 共享阶段见 [`workflows/stages/generate-audio.md`](../../skills/ppt-master/workflows/stages/generate-audio.md)。
31
32 ## 两条嵌入路径
33
34 | 命令 | 用途 |
35 |---|---|
36 | `--recorded-narration audio` | 准备 PowerPoint 的"录制的计时和旁白"。要求每页都有音频,并写入页面自动推进时间。用于旁白视频导出。重导出文件保存为 `exports/<name>_<timestamp>_narrated.pptx`。 |
37 | `--narration-audio-dir audio` | 底层音频嵌入能力。只嵌入匹配到的文件,允许部分页面有音频。用于测试或后续手工整理。导出文件同样带 `_narrated` 后缀。 |
38 | `--narration-start-floor 0.8` | 可选的页前参数:从目标页转场开始计,到旁白启动的最短秒数。默认 `0.8`;设为 `0` 表示转场结束后立即开始。 |
39 | `--narration-padding 0.5` | 可选的页尾参数:旁白结束后、页面推进前的静默停留秒数。默认 `0.5`。 |
40
41 两个计时参数都可以省略,也可以独立覆盖。转场结束后的实际静默时间为 `max(0, narration_start_floor - transition_duration)`;调整起始下限不会拉长转场本身。
42
43 ## 怎么触发
44
45 deck 导出后,在聊天里直接说就行:
46
47 ```
48 你: 给这个 PPT 生成音频
49 你: 帮我用日语给这个 deck 配一个温柔女声的旁白
50 你: Generate narration for this deck and re-export with audio embedded.
51 ```
52
53 Generate 路线在最终 Stage 2 把 Narration Audio 的有效结果解析为开启时,
54 也会主动运行该阶段;后续明确指令仍优先于主动默认值。剩下的 AI 全包。
55
56 ## 支持的语言
57
58 凡是 `edge-tts` 支持的 locale 都行——大约 90 个,覆盖中文全部主要变体(`zh-CN` 普通话 / `zh-TW` 台湾普通话 / `zh-HK` 粤语)、英文(美/英/澳/印)、日语、韩语、法语、德语、西班牙语、葡萄牙语、俄语、阿拉伯语等。任何 locale 的全量音色清单都可以这样查:
59
60 ```bash
61 python3 skills/ppt-master/scripts/notes_to_audio.py --list-voices --locale ja-JP
62 ```
63
64 ## 进阶:手动调用脚本
65
66 如果你想跳过 AI 流程直接跑命令:
67
68 ```bash
69 # 1. 确保备注已切分(后处理 Step 7.1)
70 python3 skills/ppt-master/scripts/total_md_split.py <project_path>
71
72 # 2A. 用 edge-tts 生成 MP3/SRT 对(默认,无需 API Key)
73 python3 skills/ppt-master/scripts/notes_to_audio.py <project_path> \
74 --voice zh-CN-YunjianNeural --rate +0%
75
76 # 2B. 用 ElevenLabs 生成 MP3/SRT 对(需要 ELEVENLABS_API_KEY)
77 export ELEVENLABS_API_KEY="your-elevenlabs-api-key"
78 python3 skills/ppt-master/scripts/notes_to_audio.py <project_path> \
79 --provider elevenlabs \
80 --voice-id <elevenlabs-voice-id> \
81 --elevenlabs-model eleven_multilingual_v2
82
83 # 2C. 用 MiniMax 生成 MP3/SRT 对(支持系统音色或复刻 voice_id)
84 export MINIMAX_API_KEY="your-minimax-api-key"
85 # 默认使用国内地址;海外访问可设置 MINIMAX_TTS_BASE_URL=https://api.minimax.io/v1/t2a_v2
86 python3 skills/ppt-master/scripts/notes_to_audio.py <project_path> \
87 --provider minimax \
88 --voice-id <minimax-voice-id> \
89 --minimax-model speech-2.8-hd
90
91 # 2D. 用 Qwen TTS 仅生成音频(系统音色或复刻音色)
92 export DASHSCOPE_API_KEY="your-dashscope-api-key"
93 python3 skills/ppt-master/scripts/notes_to_audio.py <project_path> \
94 --provider qwen \
95 --voice-id <qwen-voice> \
96 --qwen-model qwen3-tts-flash \
97 --qwen-language-type Chinese
98
99 # 2E. 用支持时间戳的 CosyVoice 音色生成 MP3/SRT 对
100 export COSYVOICE_API_KEY="your-dashscope-api-key"
101 python3 skills/ppt-master/scripts/notes_to_audio.py <project_path> \
102 --provider cosyvoice \
103 --voice-id <cosyvoice-voice> \
104 --cosyvoice-model cosyvoice-v3-flash
105
106 # 3-4. 仅当选择旁白 cue 同步,且逐页 SRT 与规范 animations.json 都存在时,
107 # 输出整套 SRT 的指纹,
108 # 再对照每页当前 SVG 内容组与 SRT cue,编写
109 # <project_path>/narration_timing.json;没有对应口播的组不写 cue,
110 # 后续按正常动画顺序出现。旁白无关的自定义动画或无 sidecar 时直接跳到第 5 步。
111 python3 skills/ppt-master/scripts/narration_sync.py fingerprint <project_path>
112
113 # 4. 从规范 animations.json 派生无点击的 narration_animations.json
114 python3 skills/ppt-master/scripts/narration_sync.py animations <project_path> \
115 --narration-start-floor 0.8 --narration-padding 0.5 --force
116
117 # 5A. 与旁白 cue 同步的自定义动画:使用派生 sidecar
118 python3 skills/ppt-master/scripts/svg_to_pptx.py <project_path> \
119 -o <final_narrated_pptx> --recorded-narration audio \
120 --narration-start-floor 0.8 --narration-padding 0.5 \
121 --animation-config narration_animations.json \
122 --inherit-motion-from "<base_postflight_report>"
123
124 # 5B. 与旁白无关的自定义动画:使用规范计时
125 python3 skills/ppt-master/scripts/svg_to_pptx.py <project_path> \
126 -o <final_narrated_pptx> --recorded-narration audio \
127 --narration-start-floor 0.8 --narration-padding 0.5 \
128 --animation-config animations.json \
129 --inherit-motion-from "<base_postflight_report>"
130
131 # 5C. 没有动画 sidecar:继承基础导出的 motion,包括 -a auto
132 python3 skills/ppt-master/scripts/svg_to_pptx.py <project_path> \
133 -o <final_narrated_pptx> --recorded-narration audio \
134 --narration-start-floor 0.8 --narration-padding 0.5 \
135 --inherit-motion-from "<base_postflight_report>"
136
137 # Quick Generate 在所选命令后追加 --quick-generate --with-notes。
138 # 原生导出混音分支存在已解析音效 cue 时,还需在所选导出命令中追加
139 # --conversion-trace <final_narrated_trace>;实时放映录制不依赖该 trace 交付声音。
140
141 # 6. 存在逐页 SRT 时,按最终 PowerPoint 计时合并
142 python3 skills/ppt-master/scripts/narration_sync.py subtitles <project_path> \
143 --pptx <final_narrated_pptx> --force
144
145 # 7. Windows 可选:通过 PowerPoint 导出 raw 视频并等待完成
146 python3 skills/ppt-master/scripts/powerpoint_video.py --check
147 python3 skills/ppt-master/scripts/powerpoint_video.py \
148 <final_narrated_pptx> -o exports/<raw_powerpoint_video>.mp4
149
150 # 8. 原生导出分支的最终 motion 存在音效 cue 时,生成独立 SFX stem 与
151 # 验收后的混音成片。默认:转场音约 35%,对象音约 25%,最终限幅 -1 dBFS。
152 python3 skills/ppt-master/scripts/video_sound_mix.py <project_path> \
153 --pptx <final_narrated_pptx> \
154 --trace <final_narrated_trace> \
155 --video exports/<raw_powerpoint_video>.mp4 \
156 -o exports/<final_mixed_video>.mp4 --force
157
158 # 9. 存在逐页 SRT 时,把冻结的旁白文本与最终视频音轨对齐;
159 # 第 8 步执行过就使用 mixed,选择录屏则使用验收后的 capture,否则使用 raw。
160 python3 skills/ppt-master/scripts/video_subtitles.py <project_path> \
161 --video "<final_delivery_video>" --language <language> --force
162 ```
163
164 发送任何 TTS 请求前,`notes_to_audio.py` 会确认每个 Generate SVG 页面或
165 Native Enhance 页面都有可读且非空的逐页备注。缺失或空备注会返回退出码
166 `2`;必须先生成这些备注,再重新运行音频生成。
167
168 edge 模式下 `--voice` 是必填项,可用 `--list-voices --locale <locale>` 查看音色。
169 Edge 默认同时生成最多 3 页音频/SRT。可用 `--concurrency <N>` 调整;
170 排查连接问题时可设为 `--concurrency 1`。云端 provider 仍保持串行。
171
172 Edge 命令会从同一次流式请求中生成 `audio/<stem>.mp3` 与 `audio/<stem>.srt`。句末标点必定结束一条字幕;单条超过默认 20 个可见字符时,优先在逗号、分号或冒号处拆分,仍然过长才在最近的词边界拆分。可用 `--subtitle-max-chars` 调整上限。相邻字幕最多允许 100 毫秒的计时重叠:后一句起点会移到前一句终点;超过该范围则报错。每页 SRT 使用从零计时的页内时间基准,并保留 Edge `WordBoundary` 的实际时间(包括首条字幕前的静音)。
173
174 MiniMax 会在同一次非流式 T2A 请求中获取词级字幕并下载返回的 JSON 时间戳。ElevenLabs 使用 `/with-timestamps` 接口,从同一 JSON 响应读取音频和原文字符级对齐。CosyVoice 开启 HTTP 流式响应与 `word_timestamp_enabled`,再使用同次合成返回的完整音频 URL 和词级时间戳。四条 provider 原生计时路径统一使用标点优先、受 `--subtitle-max-chars` 约束的重组逻辑,并原子发布通过校验的音频/SRT 对;整理后的紧凑 cue 用于语义动画映射。
175
176 CosyVoice 的时间戳能力取决于模型和音色组合:`cosyvoice-v3.5-plus`、`cosyvoice-v3.5-flash`、`cosyvoice-v3-plus`、`cosyvoice-v3-flash`、`cosyvoice-v2` 的复刻音色支持,[CosyVoice 音色清单](https://help.aliyun.com/zh/model-studio/cosyvoice-voice-list)里明确标记支持时间戳的系统音色也支持。模型与音色家族必须匹配。如果所选音色不能返回计时,而且明确只需要音频,可传入 `--cosyvoice-audio-only`。
177
178 Qwen 当前 TTS 的 HTTP 与实时响应都只返回音频,不含词级或字符级对齐。PPT Master 因此保留 Qwen 纯音频路径,不用理论时长估算 SRT。需要逐页字幕时,请选择 Edge、ElevenLabs、MiniMax 或支持时间戳的 CosyVoice 音色。
179
180 ### 服务商能力与参数选择
181
182 | 服务商 | 逐页 SRT | 原始计时 | 当前默认裁决 |
183 |---|---|---|---|
184 | Edge | 支持 | 词级 | 保留所选神经网络音色与 `+0%`;只有 notes 密度确实需要时才小幅调速。 |
185 | ElevenLabs | 支持 | 原文字符级对齐 | 保留 `eleven_multilingual_v2` 与 `mp3_44100_128`,适合稳定长文旁白。显式调速使用 `--elevenlabs-speed 0.7-1.2`;`eleven_v3` 表现力更强但波动更大,Flash v2.5 更偏延迟与成本。 |
186 | MiniMax | 支持 | 词级 | 保留现有 `speech-2.8-hd`、32 kHz 单声道 MP3 默认值,除非所选音色或交付目标另有要求。 |
187 | Qwen | 不支持 | 当前 TTS 响应无计时 | 保留稳定版 `qwen3-tts-flash`;单语 deck 明确指定 `--qwen-language-type`。当前接口固定返回 WAV,不提供格式、采样率或数值语速控制;Instruct 模型仍可通过指令控制表达。不为了不存在的时间戳盲目换模型。 |
188 | CosyVoice | 有条件支持 | 词级 | 保留兼容系统音色的 `cosyvoice-v3-flash` 与 24 kHz MP3 默认值。复刻/设计音色使用其所属模型;v3.5 音色必须显式选择匹配的 v3.5 模型。 |
189
190 CLI 会在发送请求前拒绝超出范围的 ElevenLabs stability/similarity/style、`0.7-1.2` 以外的 ElevenLabs 语速,以及不符合 provider 官方范围的 CosyVoice 音量、语速、音高或采样率。
191
192 以上裁决依据当前 [ElevenLabs 带时间戳语音接口](https://elevenlabs.io/docs/api-reference/text-to-speech/convert-with-timestamps)、[ElevenLabs 模型指南](https://elevenlabs.io/docs/overview/capabilities/text-to-speech)、[Qwen TTS API](https://www.alibabacloud.com/help/en/model-studio/qwen-tts-api) 与 [Qwen-Audio-TTS/CosyVoice HTTP API](https://help.aliyun.com/en/model-studio/cosyvoice-tts-http-api)。阿里云目前建议 CosyVoice HTTP 使用北京地域的 workspace 专属域名;有该域名时通过 `--cosyvoice-base-url` 传入,旧域名仍可用。
193
194 阿里云当前的 [TTS 模型选型指南](https://www.alibabacloud.com/help/en/model-studio/tts-model/)建议新建的预置/复刻音色工作流优先考虑 Qwen-Audio 3.0。但这些模型使用 Qwen-Audio-TTS/CosyVoice API 和另一套音色契约,仍不返回时间戳。因此 PPT Master 不会静默替换兼容的 `qwen3-tts-flash` 默认值;只有确实为了音质迁移时,才显式更换模型及其匹配音色,而不是为了字幕能力盲目迁移。
195
196 `audio/` 是唯一的当前旁白集,来源由 manifest 记录,因此默认不创建 provider 子目录。重新生成前,脚本会移除过期的 `manifest.json` 与 `total.srt`;仅生成音频的 provider 还会移除同名旧逐页 SRT。只有明确需要保留另一套 provider 结果时,才使用单独的显式输出目录。
197
198 选择旁白 cue 同步且存在规范自定义动画时,`narration_timing.json` 与只读的 `animations.json` 刻意分离:前者记录整套有序 SRT 的 SHA-256、可选的旁白起始下限、页尾 padding、有序 SVG 组 ID 和可选的 1-based cue 编号。`narration_sync.py animations` 会拒绝过期的 SRT 指纹,用当前 SVG 校验组 ID,并把 PowerPoint 支持的字段写入派生的 `narration_animations.json`。与 cue 绑定的动画使用和嵌入音频相同的页前起始下限;未绑定 cue 的标题或装饰动画保留规范相对时间。包含 `effects[]` 的分组仍只映射一条 cue:第一条有效动画行锚定该 cue,后续动画行保留相对延迟。与旁白无关的自定义动画直接使用规范 `animations.json`;没有 sidecar 时继承基础报告的已解析 motion。`narration_sync.py subtitles` 从最终 PPTX 读取真实页面关系顺序、毫秒级转场、旁白延迟与页面推进时间,因此 `total.srt` 使用原生 PPTX 时间轴。相对 `--pptx` 路径按 `<project_path>` 解析。
199
200 PowerPoint 的视频编码器可能把每个页面 / 媒体段落量化到输出帧时钟;即使 PPTX 计时值正确,这些很小的分页误差仍可能逐页累积。`video_sound_mix.py` 复用逐页旁白相关性,把每个转场 / 对象音效从理论 PPTX 时钟映射到 raw MP4 时钟,而不是直接叠加两套独立时间轴。`video_subtitles.py` 再使用 `stable-ts`,把冻结的旁白原文与最终 `.mp4` / `.wmv` / `.mov` 音轨强制对齐;交付时可为显示效果拆分过长 cue,并生成与视频同名的 SRT,不会改写视频、备注或逐页字幕。
201
202 最终带旁白的 SVG 导出使用默认文本流模式即可:在一个禁用自动换行的可编辑文本框中保留作者断行;旁白不要求每一行拆成独立文本框。
203
204 ```json
205 {
206 "version": 1,
207 "srt_sha256": "<sha256 of the ordered page-local SRT set>",
208 "narration_start_floor": 0.8,
209 "narration_padding": 0.5,
210 "slides": {
211 "01_title": {
212 "groups": [
213 { "id": "page-title", "cue": 1 },
214 { "id": "supporting-visual" }
215 ]
216 }
217 }
218 }
219 ```
220
221 ElevenLabs 模式下 `--voice-id` 是必填项,可从账户中列出音色:
222
223 ```bash
224 export ELEVENLABS_API_KEY="your-elevenlabs-api-key"
225 python3 skills/ppt-master/scripts/notes_to_audio.py --provider elevenlabs --list-voices
226 ```
227
228 MiniMax、Qwen 与 CosyVoice 使用 `--voice-id` 传入对应平台的系统音色或复刻音色 ID。声音复刻本身先在对应平台控制台 / API 中完成,`notes_to_audio.py` 使用得到的 voice ID 生成逐页旁白。
229
230 进入 PPTX 的旁白音频必须是 PowerPoint 可靠格式:`m4a`(AAC)、`mp3` 或 `wav`。内置生成路径默认使用 `mp3`;如果 provider 产出 `pcm`、`opus` 或 `flac`,需要先转码再嵌入。
231
232 ## 使用复刻音色
233
234 四个云端 provider —— **ElevenLabs**、**MiniMax**、**Qwen**、**CosyVoice** —— 都支持用一段较短的音频样本复刻一个新音色,再用这个音色合成新语音。只要你能拿到 `voice_id`,PPT Master 就能用这个音色把整份 deck 念出来。(`edge` 不支持复刻。)
235
236 **职责切分**:声音复刻本身在 provider 的控制台或 API 完成——你上传一段样本(一般 10 秒到几分钟的干净录音),平台给你返回一个 `voice_id`。PPT Master 在*消费*侧:拿到 `voice_id` 后用这个音色逐页朗读备注。PPT Master 不会把你的样本上传到任何地方。
237
238 | 服务商 | 复刻入口 | 样本时长 |
239 |---|---|---|
240 | ElevenLabs | [elevenlabs.io](https://elevenlabs.io) → Voices → Add Voice → Instant / Professional Voice Cloning | 1 分钟(Instant)/ 30 分钟以上(Professional) |
241 | MiniMax | [platform.minimaxi.com](https://platform.minimaxi.com) → 语音克隆 | 10 秒 – 5 分钟 |
242 | Qwen TTS | [DashScope 控制台](https://dashscope.console.aliyun.com) → 语音合成 → 声音复刻 | 10 秒 – 5 分钟 |
243 | CosyVoice | [DashScope 控制台](https://dashscope.console.aliyun.com) → 语音合成 → 音色复刻 | 10 秒 – 5 分钟 |
244
245 **复刻完之后怎么用** —— 在聊天里告诉 AI 即可,AI 会跳过音色推荐环节直接用你的 `voice_id`:
246
247 ```
248 你: 用 MiniMax 我克隆的音色生成旁白,voice_id 是 xxxxxxx
249 你: 用我在 ElevenLabs 复刻的 voice id abc123 生成
250 ```
251
252 也可以直接跑脚本:
253
254 ```bash
255 python3 skills/ppt-master/scripts/notes_to_audio.py <project_path> \
256 --provider minimax --voice-id <你的复刻 voice id> \
257 --minimax-model speech-2.8-hd
258 ```
259
260 把 `--provider minimax` 换成 `elevenlabs` / `qwen` / `cosyvoice` 就能切到对应平台;`--voice-id` 接收复刻音色和接收系统音色的方式完全一样。
261
262 **注意**:
263
264 - **授权** —— 只复刻你自己拥有的、或拿到了明确授权的声音。每个 provider 的服务条款都禁止冒用他人声音。
265 - **语言覆盖** —— 复刻出来的音色会继承说话人的口音。对中英混合等多语 deck,建议挑一个对你样本语言组合处理较好的 provider;ElevenLabs `eleven_multilingual_v2` 和 CosyVoice 通常最宽容。
266 - **字幕能力** —— ElevenLabs 复刻音色和受支持的 CosyVoice 复刻音色可以生成 provider 原生计时 SRT;Qwen 复刻音色在当前 API 下仍只生成音频。
267 - **服务商保留策略** —— 只要该音色仍存在于你的 provider 账户中,就可以继续复用对应 `voice_id`;保留、删除与过期规则以各平台政策为准。
268
269 ## 依赖
270
271 ```bash
272 python3 -m pip install edge-tts
273 ```
274
275 已写入 `skills/ppt-master/requirements.txt`。`edge-tts` 调用微软的在线 TTS 服务,**生成时**需要联网;生成后的音频是本地文件,PowerPoint 播放和视频导出都不依赖网络。云端 TTS provider 不需要额外 Python 包,直接通过 HTTPS 调用;API Key 可以设在当前 shell 环境中,也可以按 `.env.example` 写入 `.env`。
276
277 自动 MP4 导出不增加 Python 依赖,但要求 Windows PowerPoint 2016+ 与 Windows PowerShell;macOS 或没有兼容 PowerPoint 的机器保留带旁白 PPTX,改用手动导出。
278
279 实时放映录制不增加 PPT Master 依赖,但需要桌面版 Windows PowerPoint 和能
280 捕获放映画面及应用 / 系统音频的录屏器。[OBS Studio](https://obsproject.com/kb/quick-start-guide)
281 和 [Windows Game Bar](https://support.microsoft.com/en-us/accessibility/windows/use-a-screen-reader-to-record-your-screen-with-xbox-game-bar)
282 只是可选工具示例,不是项目依赖。
283
284 导出后混入动画音效需要系统 `PATH` 中可用的 `ffmpeg` / `ffprobe` 以及
285 `numpy`;最终视频字幕对齐另需 `stable-ts`:
286
287 ```bash
288 python3 -m pip install numpy stable-ts
289 ```
290
291 ## 经验值
292
293 - **语速**:在 Generate PPTX 路线上,PPT Master 会根据最终 SVG 中的独立信息组调整讲稿长度;每页 2–5 句只是常见节奏,并非上限。可先使用 `+0%`,较密且刻意保留细节的讲稿可尝试 `-5%`。
294 - **改某一页**:改对应的 `notes/<page>.md`,再跑一次 `notes_to_audio.py`(脚本会重新生成全量 MP3,整套 deck 跑一遍成本很低)。
295 - **混合语言 deck**(中文里夹英文术语等):主流 locale 的神经语音对嵌入的外语词处理得不错——按主语言挑音色,先用一页试听再批量。
296
297 ---
298
299 ## 导出为视频
300
301 只选择一条交付路径:
302
303 | 路径 | 适用情况 | 声音结果 |
304 |---|---|---|
305 | 原生 `CreateVideo` | 需要自动、可重复的流程 | 原生包含旁白;存在已解析转场 / 对象 cue 时必须运行 `video_sound_mix.py`。 |
306 | PowerPoint 实时放映录制 | 明确希望成片包含 PowerPoint 实际播放的全部声音 | 录屏已经包含旁白和原生 cue,不能再运行 `video_sound_mix.py`。 |
307 | 手工执行“创建视频” | 自动化不可用,但可以接受 PowerPoint 编码器 | 声音边界与原生 `CreateVideo` 相同;这不是录屏。 |
308
309 带旁白的 PPTX 在 `exports/` 里就绪后,Windows PowerPoint 2016+ 可通过下面的接口自动导出:
310
311 ```bash
312 python3 skills/ppt-master/scripts/powerpoint_video.py \
313 <final_narrated_pptx> -o <raw_powerpoint_video.mp4>
314 ```
315
316 命令使用录制的计时和旁白,默认输出 1080p/30fps,并在 PowerPoint 明确成功或失败后才返回。嵌入音频作为逐页旁白播放,页面自动推进时间控制视频节奏。`--recorded-narration` 会拒绝 `on-click` 对象动画,因为 PPT Master 不生成对象级点击计时。
317
318 即使 `animations.json` 和 PPTX package 校验通过,PowerPoint 的 raw MP4
319 也不保证包含附着在转场或 Animation Pane 行上的声音。Generate 项目的最终
320 narrated trace 含这些 cue 时,按上面的命令运行 `video_sound_mix.py`:原生声音
321 仍保留在可编辑 PPTX 中,视觉视频流原样复制,旁白保持 unity,提示音先降增益再
322 与旁白混合,最终经过峰值限幅,并输出独立 SFX stem 与机器可读验收回执。字幕应
323 基于 mixed MP4 对齐,而不是 raw 中间产物。
324
325 ### 录制 PowerPoint 实时放映
326
327 这是显式选择的实时采集路径。PowerPoint 仍是渲染器和音频播放器,录屏器只负责
328 捕获其输出。
329
330 1. 用桌面版 Windows PowerPoint 打开最终带旁白 PPTX,从第一页开始全屏放映。使用 deck 已有的自动翻页和无点击对象计时,不录编辑界面或演讲者视图。
331 2. 只捕获与 deck 宽高比一致的全屏放映画面,关闭通知,并让鼠标指针离开画面。常规目标为 1920×1080、稳定 30fps。
332 3. 只开启一路应用 / 系统音频捕获;除非明确需要现场讲话,否则关闭麦克风。不能同时捕获桌面音频和应用音频,否则会产生回声。48kHz 是推荐录制设置,不是硬要求。
333 4. 第一页开始前提前录制,最终声音拖尾结束后再停止。保留原始录屏,然后只裁去首尾缓冲。
334 5. 验收最终文件确实包含视频流和音频流,旁白清楚,所有已配置 cue 各出现一次,动画与转场完整,并且没有掉帧、通知或桌面 UI。
335 6. 存在逐页 SRT 时,对最终裁切后的录屏运行 `video_subtitles.py`,把冻结旁白文本对齐到真实录制音轨。
336
337 当前录屏验收依赖人工检查,PPT Master 不会声称它具有机器化 cue 回执。如果 cue
338 盖住旁白或发生削波,应调整 PPTX / cue 素材后重新录制,或改用带确定性增益和限幅
339 的原生导出加混音路径。Linux 可以准备完整的带旁白 PPTX、音频、计时和字幕,但
340 这一步仍需要真实的桌面版 Windows PowerPoint 播放端。
341
342 ### 手工“创建视频”回退(Windows / Mac,Office 2016+)
343
344 1. 打开 `exports/` 里那份带旁白的 `.pptx`。
345 2. **文件 → 导出 → 创建视频**。
346 3. 选清晰度以及"使用录制的计时和旁白"。
347 4. **创建视频** → 保存为 `.mp4`(Windows 也支持 `.wmv`)。
348 5. 若已配置原生转场 / 对象动画音效,先运行上面的声音混合命令;否则 PowerPoint 导出即为最终视频。
349 6. 再对最终视频运行可选的 `video_subtitles.py` 对齐命令;它会把同名 SRT 写在视频旁边。
350
351 PowerPoint for Mac 可以手动导出 MP4/MOV,但微软明确说明其影片导出不会播放动画效果。需要动画保真时,应使用 Windows 自动导出路径。
352
353 **Keynote(Mac)**:打开 deck → **文件 → 导出到 → 影片…** ——Keynote 可以读取嵌入的旁白和分页计时,输出 `.m4v` / `.mov`;这不构成 PowerPoint 动画音效已进入成片的保证。
354
355 **经验值**:
356
357 - **生成旁白不需要麦克风**:原生导出也不需要录制环节;实时放映录制捕获应用 / 系统音频,并关闭麦克风。重跑会复用同一份 notes 与参数,但云端模型仍可能出现轻微的非确定性差异。
358 - **Windows 动画保真**:PowerPoint 的 Windows 视频导出会保留 PPT Master 的原生视觉页间转场和无点击对象动画;动画音效采用验收后的导出后混音,或与其互斥的实时放映录制。Mac 影片导出存在上面的限制。详见 [转场与动画](./animations.md)。
359 - **单页改音频**:改对应 `notes/<page>.md`,再跑一遍 `notes_to_audio.py` + 嵌入步骤,再重新导出视频——单页迭代通常不到一分钟。
360 - **文件大小**:20 页全高清 deck 通常是 30–80 MB,取决于图片量。需要小文件分享时降到高清就行。
361
361 lines MARKDOWN