关于 framevideo-voiceover-ssml
framevideo-voiceover-ssml 是用于从字幕、转录文本或项目分析生成旁白脚本的技能,面向视频创作者和配音制作流程。它添加发音、停顿和数字读法标记,并保留适用于不支持 SSML 的 TTS 的纯文本版本。
主要功能
- 01从字幕和转录生成旁白
- 02扩展简短字幕为自然口播
- 03标注发音、停顿和数字读法
- 04保存标记版与纯文本版脚本
- 05核对生成音频的转录与时间
适用场景
- 01为视频字幕编写配音稿
- 02校正品牌名和技术词的读音
- 03调整数字、日期及价格的口播方式
- 04让旁白节奏贴合画面文字
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ chanjing-ai/ framevideo --skill framevideo-voiceover-ssml安装后在 Claude Code 中输入/framevideo-voiceover-ssml确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
agents/openai.yamlreferences/ssml.mdworkflow.md详细介绍
FrameVideo 配音 SSML
根据现有项目内容(字幕、转录文本、AI 分析)生成旁白脚本,并使用 SSML 风格标记增强脚本,以修正发音、插入停顿和控制数字读法。
适用场景
- 用户希望根据项目字幕或转录文本生成旁白
- 需要修正品牌名称、技术术语或外语词汇的发音
- 需要控制停顿时长,以营造戏剧效果或调整节奏
- 需要规范数字、日期或价格的读法
- 将简短的字幕扩写为自然的旁白
- 制作与屏幕可见文字保持同步的配音
不适用场景
- 仅需不带标记的简单文本转语音 → 直接使用
framevideo-media(tts) - 合成数字人视频 → 使用
chanjing-digital-human - 选择 TTS 语音或服务提供商 → 使用
framevideo-media - 用户已提供可直接用于 TTS 的完整旁白脚本
快速入门
最简工作流:
# 1. Find source text (subtitle file, transcript, or analysis)
cat subtitles.txt
# Output: "Visit chanjing.ai for more info"
# 2. Add SSML markup for pronunciation
echo '<phoneme alphabet="ipa" ph="tʃæn.dʒɪŋ">Chanjing</phoneme> <break time="0.3s"/> Visit chanjing dot AI for more info.' > script-marked.txt
# 3. Generate TTS with markup (if provider supports)
npx framevideo tts script-marked.txt --voice af_heart --output narration.wav
# 4. Transcribe back to get timestamps
npx framevideo transcribe narration.wav --output transcript.json
# 5. Reference in composition
# <audio src="narration.wav" data-start="0" data-duration="5.2"></audio>
核心概念
源文本优先级
按以下顺序查找源文本:
- 项目字幕/转录文本 — 主要来源,已与可见内容同步
- AI 分析文本 — 分镜脚本制作过程中提取的场景描述或产品文案
- 现有旁白草稿 — 用户已提供时使用
- 手动撰写 — 无其他来源时的最后选择
为什么优先使用字幕? 字幕已与画面节拍同步,并且与观众在屏幕上看到的内容一致。
SSML 风格标记
以下三个标签可用于控制表达方式:
| 标签 | 用途 | 示例 |
|---|---|---|
<phoneme> | 修正发音 | <phoneme alphabet="ipa" ph="tʃæn.dʒɪŋ">Chanjing</phoneme> |
<break> | 插入停顿 | <break time="0.5s"/> |
<ttnumber> | 控制数字读法 | <ttnumber pronounce="twenty twenty-six">2026</ttnumber> |
标记仅用于编写脚本。 将其保留在脚本文件中,但在发送给不支持 SSML 的 TTS 服务提供商之前,应先移除这些标记。
回退策略
并非所有 TTS 服务提供商都支持 SSML 标签:
- Kokoro(本地): 不支持 SSML — 生成前移除标签
- Chanjing TTS: 支持
phoneme、break、ttnumber— 原样传递 - ElevenLabs: 支持部分 SSML — 请查阅其文档
始终保存两个版本:
script-marked.txt— 带 SSML 标签的原始版本script-fallback.txt— 适用于不支持 SSML 的服务提供商的纯文本版本
工作流
步骤 1:查找源文本
# Check for existing subtitles
ls subtitles.txt captions.json transcript.json
# Check AI analysis output (if using website-to-framevideo)
cat STORYBOARD.md SCRIPT.md
# Check existing narration drafts
ls narration-draft.txt script.txt
步骤 2:规范化为适合朗读的脚本
扩写简短的字幕:
Source: "New feature: AI search"
Narration: "Introducing our new feature: AI-powered search that understands your intent."
与屏幕可见文字保持同步:
- 如果字幕写着“50% faster”,旁白应在相同时间点说出“fifty percent faster”
- 如果产品名称在屏幕上显示为“FrameVideo”,旁白也应说“FrameVideo”,而不是“frame video”
文本规范化规则:
- 将
&转换为“and” - 首次出现时拼出首字母缩略词:“TTS, or text to speech”
- 转换 URL:将“chanjing.ai”读作“chanjing dot AI”
- 转换符号:将“$99”转换为“ninety-nine dollars”
步骤 3:添加 SSML 标记
谨慎使用。 仅在 TTS 误读或节奏至关重要时添加标记。
音素标签 — 修正发音
中文姓名和品牌:
<phoneme alphabet="py" ph="chan1 jing4">蝉镜</phoneme>
<phoneme alphabet="py" ph="xi1">茜</phoneme> (name: "Xi", not "qi")
英语技术术语:
<phoneme alphabet="ipa" ph="dʒiː.sæp">GSAP</phoneme> (not "guh-sap")
<phoneme alphabet="ipa" ph="weɪ.ˈeɪ.ˈeɪ.ˈpiː">WAAPI</phoneme> (spell it out)
产品名称:
<phoneme alphabet="ipa" ph="freɪm.ˈvɪd.i.oʊ">FrameVideo</phoneme>
适用场景:
- TTS 误读品牌名称
- 发音不规范的技术术语
- 英语旁白中的外语词汇
- 需要拼读而非按单词发音的首字母缩略词
音标体系:
ipa— 国际音标(通用)py— 普通话拼音x-sampa— 扩展 SAMPA(ASCII 安全的 IPA)
Break 标记 — 暂停控制
戏剧性停顿:
Introducing our new product. <break time="0.8s"/> Built for creators.
列表分隔:
Three reasons: speed<break time="0.4s"/>, quality<break time="0.4s"/>, and ease of use.
转场标记:
In the past<break time="0.3s"/>, this took hours. Now? Seconds.
时长指南:
0.2s— 自然的逗号停顿0.3-0.5s— 句子边界,换气0.6-0.8s— 戏剧性停顿,强调1.0s+— 场景转场,重大变化
适用场景:
- 默认的 TTS 语速显得仓促
- 需要在关键信息前加强调
- 旁白必须与屏幕上的时间同步
不适用场景:
- 每个逗号处(让 TTS 自然处理停顿)
- 替代正确的句子结构
Ttnumber 标记 — 数字读法
年份:
<ttnumber pronounce="twenty twenty-six">2026</ttnumber>
<ttnumber pronounce="nineteen fifty-five">1955</ttnumber>
产品代码:
Model <ttnumber pronounce="A X dash three hundred">AX-300</ttnumber>
价格:
Only <ttnumber pronounce="ninety-nine dollars">$99</ttnumber>
日期:
Launch date: <ttnumber pronounce="July seventeenth">7/17</ttnumber>
适用场景:
- 默认 TTS 对数字的读法不自然(“two thousand twenty-six” 与 “twenty twenty-six”)
- 产品代码应逐个读出字符(“A-X-three-hundred”,而不是 “ax three hundred”)
- 货币需要自然的表述方式
- 日期需要符合当地文化习惯的读法
第 4 步:选择 TTS 提供商
决策树:
Does user require Chanjing platform voices?
├─ YES → Use chanjing-digital-human skill (supports SSML)
└─ NO
├─ Need offline/free → Kokoro via framevideo-media (strip SSML)
└─ Need high quality → ElevenLabs (check SSML support)
提供商对 SSML 的支持:
| 提供商 | Phoneme | Break | Ttnumber | 调用方式 |
|---|---|---|---|---|
| Kokoro | ❌ | ❌ | ❌ | framevideo-media |
| Chanjing TTS | ✅ | ✅ | ✅ | chanjing-digital-human |
| ElevenLabs | ✅ | ✅ | ⚠️ | 外部 API |
第 5 步:生成音频
支持 SSML(Chanjing):
# Pass marked script directly
npx framevideo chanjing tts script-marked.txt \
--voice-id <voice-id> \
--output narration.wav
不支持 SSML(Kokoro):
# Strip tags first
sed 's/<[^>]*>//g' script-marked.txt > script-fallback.txt
# Generate clean
npx framevideo tts script-fallback.txt \
--voice af_heart \
--output narration.wav
移除 SSML 标记:
# Simple regex (removes all XML-like tags)
sed 's/<[^>]*>//g' input.txt > output.txt
# Or Python for precise control
python3 << 'EOF'
import re
with open('script-marked.txt') as f:
text = f.read()
# Remove SSML tags but keep inner text
text = re.sub(r'<phoneme[^>]*>(.*?)</phoneme>', r'\1', text)
text = re.sub(r'<break[^>]*/?>', ' ', text)
text = re.sub(r'<ttnumber[^>]*>(.*?)</ttnumber>', r'\1', text)
with open('script-fallback.txt', 'w') as f:
f.write(text)
EOF
第 6 步:保存两个版本
文件结构:
project/
├── script-marked.txt # Original with SSML
├── script-fallback.txt # Stripped for non-SSML TTS
├── narration.wav # Generated audio
└── transcript.json # Re-transcribed with timestamps
为什么要保存两个版本?
- 带标记的版本保留了创作意图
- 备用版本可用于通过其他 TTS 重新生成
- 未来的 TTS 提供商可能会添加 SSML 支持
第 7 步:回写到项目
根据音频生成转录文本:
npx framevideo transcribe narration.wav --output transcript.json
在合成中使用:
<audio
src="narration.wav"
data-start="0"
data-duration="12.4"
data-track-index="10"
data-volume="1.0">
</audio>
同步字幕(字幕模式请参见 framevideo 技能):
// transcript.json → caption timing
const WORDS = [
{ text: "Introducing", start: 0.2, end: 0.8 },
{ text: "FrameVideo", start: 0.9, end: 1.4 },
// ...
];
模式
模式 1:扩展字幕
输入 subtitles.txt:
🚀 New: AI Search
50% faster
Try it now
输出 script-marked.txt:
Introducing our newest feature:<break time="0.4s"/> AI-powered search.
<break time="0.3s"/>
It's fifty percent faster than traditional search.
<break time="0.5s"/>
Try it now at <phoneme alphabet="ipa" ph="tʃæn.dʒɪŋ">chanjing</phoneme> dot AI.
模式 2:保持品牌名称一致
DESIGN.md 片段:
## Brand Voice
- Company: "Chanjing" (IPA: tʃæn.dʒɪŋ, NOT "chan-jing")
- Product: "FrameVideo" (one word, capital F, capital V)
应用到脚本中:
Welcome to <phoneme alphabet="ipa" ph="tʃæn.dʒɪŋ">Chanjing</phoneme>.
<phoneme alphabet="ipa" ph="freɪm.ˈvɪd.i.oʊ">FrameVideo</phoneme> makes video simple.
模式 3:技术演示旁白
适用于产品演示:
First, click the Timeline button.<break time="0.6s"/>
Then drag the <phoneme alphabet="ipa" ph="dʒiː.sæp">GSAP</phoneme> animation track.<break time="0.5s"/>
Notice the seek time updates in real-time.
模式 4:多语言产品名称
使用中文品牌名的英文旁白:
This is <phoneme alphabet="py" ph="chan1 jing4">蝉镜</phoneme><break time="0.3s"/>, the AI video platform from China.
模式 5:包含大量数字的内容
定价和指标:
Available in three tiers:<break time="0.4s"/>
Starter at <ttnumber pronounce="forty-nine dollars">$49</ttnumber>,<break time="0.3s"/>
Pro at <ttnumber pronounce="ninety-nine dollars">$99</ttnumber>,<break time="0.3s"/>
and Enterprise at <ttnumber pronounce="four ninety-nine">$499</ttnumber>.
规则(不可妥协)
- 始终保存带标记的脚本 — 即使 TTS 目前不支持 SSML
- 备用文本必须自然 — 移除标记后,语法不应受到影响
- 转录生成的音频 — 不要假设时间与脚本一致
- 优先使用源文本 — 扩展字幕,而不是替换字幕
- 标记应适量 — 仅在 TTS 无法正确处理或时间安排至关重要时使用
避免
- ❌ 为每句话添加 SSML — 只解决实际问题
- ❌ 用
<break>替代对别扭措辞的改写 - ❌ 假设 Kokoro 支持 SSML — 它不支持,先移除标记
- ❌ 未经测试就硬编码音素 — 请确认这样确实有帮助
- ❌ 忽视提供商的限制 — 检查支持哪些标记
- ❌ 生成后丢弃带标记的脚本 — 保留以便迭代
集成
与 framevideo-media 集成
# This skill: create marked script
echo '<phoneme>...</phoneme> text' > script-marked.txt
# framevideo-media: generate TTS
npx framevideo tts script-fallback.txt --voice af_heart --output narration.wav
# framevideo-media: transcribe
npx framevideo transcribe narration.wav --output transcript.json
# framevideo skill: use in composition
与 chanjing-digital-human 集成
# This skill: create marked script with SSML
cat script-marked.txt
# chanjing-digital-human: generate with SSML support
npx framevideo chanjing tts script-marked.txt --voice-id <id> --output narration.wav
与 website-to-framevideo 集成
Step 3 (Storyboard) → produces SCRIPT.md
↓
This skill → adds SSML markup to SCRIPT.md content
↓
Step 4 (VO) → generates audio via framevideo-media or chanjing-digital-human
↓
Step 5 (Build) → uses transcript.json for caption timing
验证
1. 检查 SSML 语法:
# No unclosed tags
grep -o '<[^/>]*>' script-marked.txt | sort | uniq -c
# Phoneme has alphabet attribute
grep '<phoneme' script-marked.txt | grep -v 'alphabet='
# (should return nothing)
2. 测试备用版本的标记移除:
sed 's/<[^>]*>//g' script-marked.txt > test-fallback.txt
cat test-fallback.txt
# Verify: readable, no XML artifacts, natural grammar
3. 对 TTS 输出进行 A/B 测试:
# Generate without markup
npx framevideo tts script-fallback.txt --voice af_heart -o no-markup.wav
# Generate with markup (if supported)
npx framevideo chanjing tts script-marked.txt --voice-id <id> -o with-markup.wav
# Compare audio quality and pronunciation
4. 验证转录文本与音频的对齐:
npx framevideo transcribe narration.wav --output transcript.json
# Check: word timing matches intended beats
参考资料
- references/workflow.md — 工作流分步详情
- references/ssml.md — SSML 标记规范
framevideo-media技能 — TTS 生成和转录chanjing-digital-human技能 — 通过 Chanjing 平台使用支持 SSML 的 TTSframevideo技能 — 音频元素约定和字幕时间安排- SSML W3C 规范:https://www.w3.org/TR/speech-synthesis/
- IPA 音标表:https://www.internationalphoneticalphabet.org/ipa-charts/