给电脑里的声音配字幕
mimi 是我做的实时字幕工具。电脑里放着视频、游戏或直播,它就把听到的对白写出来,再按选中的语言翻译。原来的应用照常用,屏幕上多一个可以挪动的字幕浮窗。
没有字幕时,表情和语气能帮人猜到一点意思,具体说了什么还是得有文字。日剧有时能另找字幕,游戏和直播就没那么方便。mimi 的名字取自日语的「耳朵」,みみ。
它采集系统输出的声音,交给配置好的云端服务识别和翻译,不用拿麦克风对着扬声器,也不用为每个播放器单独适配。字幕显示在独立浮窗里,不会写进视频文件。沉浸模式会收起外框,只留下字幕。
下面用《Sintel》的英文对白演示中文字幕和沉浸模式。录制使用 mimi 的真实前端,按原来的接收时间回放一次云端服务返回的字幕;原生采音和快捷键由录制环境代替。它能展示字幕怎么显示,不能拿来衡量装好应用后的采音效果或实时延迟。
Sintel © Blender Foundation (opens in a new tab), CC BY 3.0 (opens in a new tab).
字已经出来了,为什么还会改
实时字幕最烦的一件事,就是字已经出来了,读到一半它又改了。可要是等人说了一大堆才开始出字幕,话都说完了,画面也过去了。字幕和画面对不上,真的很折磨人。mimi 现在还在改这个问题。
播放器有现成字幕文件时,可以提前知道整句话,再按视频时间显示。mimi 只能听到声音以后再生成文字。识别服务先给的 partial,是“目前听起来像这样”的临时结果,后面的声音可能让它改词、补标点,甚至重划一句话的边界。final 表示这一段的识别已经结束,不再按草稿继续改;它不表示内容一定正确,也不保证意思已经说完整。Google 的流式识别文档 (opens in a new tab)就把“还会不会改”单独作为稳定程度来描述,和“认得对不对”是两件事。
翻译又多一层。即使前面的原文没认错,后半句也可能改变意思。比如“我觉得这件事……”后面接“挺好”,或者接“不太行”,前半句一样,态度完全不同。两种语言的语序也不总一样,译文不能总靠在末尾追加几个字完成,有时得把已经显示的表达重新组织。流式翻译研究 (opens in a new tab)里也有这种原文只增加上下文、译文却要改写前面的例子。论文讨论的办法包括先藏住容易变化的尾部,或者让新译文尽量沿用上一次的表达。前者要多等,后者也可能留下不合适的译法。
mimi 把这些临时内容放在当前的一块字幕里替换,不把每次修订都追加成新句子。确认后的原文和译文再进入上面的字幕记录。这样能避免前半句反复刷出来,读到的临时译文仍然可能被后来的版本改掉。
什么时候开始翻译
不同服务的结果不能都按同一种办法接。mimi 的低延迟模式接收服务直接返回的原文和译文;两边可能先后到达,需要按服务给的句子标识配对,不能把刚到的旧译文接在下一句原文下面。
另一种方案是先用 Audio 3.0 识别,再把文字交给 Qwen-MT 翻译。mimi 会等草稿短暂不变,取句号、问号等标点前已经成句的部分,先试着翻译。一直不停地说时,也有最长等待的触发条件:草稿足够长,就拿当前内容做预览,不必一直等句号。这里的标点和等待时间只决定何时试译,不会把草稿直接变成确认结果。
识别服务正式确认一段以后,mimi 再按顺序翻译确认内容。预览只保留最新的一份,旧请求会取消,迟到的旧结果也不能覆盖新的预览;确认翻译则优先处理,不能被下一句预览挤掉。这个选择保住了句子顺序,也可能让下一句的预览多等一会儿。翻译积压过多时,这条路径会报错并重新连接,不会一直攒着越来越晚的台词。
OpenAI 的路径又不同:原文和译文分别一点点追加。mimi 参考返回的时间信息和两边的句末标点,把能对应上的部分组成已确认字幕。原文的一句可能被翻译成两句,不能只按“第一句对第一句”来切;没有足够的对应信息,就还得留在当前字幕里等。
分得短,字幕有机会早点出现,但一句话的意思还没齐,翻译更容易回头改。等得长,留给翻译的上下文多了,字幕却可能等到人物已经做完动作才出来。
等译文终于出来,场景都变了,可能连人都换了。我还在回忆上一个片段到底在说什么,笑死(
收到的文字怎么显示
译文返回以后,还得让人读得下去。服务每改一次字,界面就跟着改一次,我已经读到一半,又得回去看前面。一下回来很多字,或者刚看清就被下一行挤走,也一样难受。这项实时字幕研究 (opens in a new tab)比较了逐词、整块和滚动显示:模型生成文字的节奏,和人阅读的节奏,要分开考虑。
mimi 现在会把接连几次修改稍微合在一起,等文字短暂不变,再更新当前字幕。如果一直有新字,也会隔一小会儿取最新的内容,不会等它彻底停下来才显示。这样能少打断几次阅读,但每多等一点,字幕也就更晚一点。这段等待还在调。
当前显示等待的实现细节
更新中的原文约 180 毫秒没变化后显示,译文约 400 毫秒。持续更新时,分别最多等约 750 毫秒和 1.5 秒就取最新内容。确认结果和清空会立即更新。这些计时从界面收到文字开始;声音采集、网络、识别和翻译花的时间还在前面。
当前句子很长时,浮窗只保留末尾几行可见,让旧文字从上面滚走。新文字来了,或者草稿变成已确认字幕时,也尽量不让整个区域忽然变高、重播出现动画。最近还在改连续更新中的滚动:后一次更新要从文字当前的位置接着走,不能把上一次还没完成的移动打断,让它又跳一下。
滚得顺一点,已经显示的译文还是可能改。我想早点看到字幕,又不想读着读着被打断,这部分还没有处理完。
原文和译文还可能分开到达。选了只看译文,mimi 就等译文返回,不会因为原文先到了,临时拿一行日文顶上去。想看已经识别到了什么,可以切到原文或双语模式。
为什么现在用云服务
我没有让 mimi 在电脑上跑本地大模型,当时主要担心的还是准确率。对白听错了,后面的翻译再顺也没用;同时又要尽快给反馈,不能只看最后一整段文字的效果。
安装也得算进去。用户不一定是程序员,就算是程序员,下载模型、配好运行环境、处理版本和设备兼容,也有门槛。大家的电脑不一定很好,不能按我自己的设备去安排所有人的使用方式。选多大的模型、要占多少内存、识别和翻译能不能一边跑一边跟上,都影响别人能不能用起来。
但这些只是我的考虑。“本地模型不准”这话说得太满了,我还有很多模型没测试过,就先下了这个判断,有点爆论了。
也有人愿意接受准确率差一点,换取不用付 API 费用的本地部署。音频和文字确实全部在本机处理时,隐私也更容易自己掌握;合适的模型配上合适的设备,还可能更快。这里不能默认所有本地方案都慢,也不能把免 API 费算成不占内存、不耗电、不用维护。不同人愿意付的代价不一样,我之前想得有点狭隘。
现在 mimi 仍把模型运行交给云端服务,自己处理声音、字幕和显示。云端也要等网络和服务返回,还得配置凭证、付服务费用。
它听得到声音,看不到画面
系统声音里可能混着音乐、音效和另一个网页的对白。把无关的播放关掉,比指望识别器自动知道我想听谁更直接。人物指着画面说“这个”,mimi 也不知道指的是哪一个。
画面指代的解释例子,不是应用录屏或识别结果。
有现成、校对好的字幕,可以直接用。找不到时,mimi 能先提供对白;遇到奇怪的句子,还得结合原声和画面判断。
用之前要配置服务凭证,语言、模式和费用取决于选中的服务商。系统音频会发给它处理。mimi 不使用麦克风,也不录制屏幕;保存字幕和录制系统音频默认关闭,需要时可以在设置里主动打开,记录会保存在本机,并可导出 TXT 或 WAV。这里的字幕时间是确认时间,不是视频播放位置,不能把导出文件直接当成对齐原片的字幕轨道。
现在提供 Apple 芯片和 Intel Mac(macOS 13+)安装包,以及 Windows x64、Linux x86_64 预览版。Intel 的实机采音仍待验证,Linux 的窗口行为也受桌面环境影响。下载和平台说明见 mimi 仓库 (opens in a new tab)。
评论