为小视频渲染像素完美的字幕

Posted

技术标签:

【中文标题】为小视频渲染像素完美的字幕【英文标题】:Rendering pixel perfect subtitles for small videos 【发布时间】:2017-08-27 10:45:18 【问题描述】:

我想在小尺寸视频上刻录字体尽可能小(但可读)的字幕,如第一张图片所示。 FFmpeg 使尝试的任何字体大小的字体都变得模糊(第二张图片)。

ffmpeg -i in.jpg -vf "scale=160x128,subtitles=in.srt:force_style='OutlineColour=&H80000000,BorderStyle=3,Fontsize=15,Fontname=Silkscreen'" out.png

有没有什么方法可以使用 FFmpeg 或其他现成的命令行工具来实现像素完美的小字体字幕? (我找到的最小字体是Silkscreen,虽然它只是ASCII!)

【问题讨论】:

the official subtitles video filter documentation 有帮助吗? 光栅化是libass完成的,不是ffmpeg和AFAICT,抗锯齿不能跳过。 另请注意,除非做错了,否则抗锯齿应该降低可读性(这不是它正在做的,理论上的信号) @MarcusMüller:非常小的字体上的抗锯齿会破坏它。我可以说没有绕过这个的选项。 值得try,尽管我不关注该库的开发。一种解决方法可能是在大型透明画布上渲染字幕,然后将其缩小并覆盖在小视频上。 【参考方案1】:

您可以通过在 libass 中启用字体提示来获得更好的结果,但是 appears FFmpeg 目前不支持设置此选项。用mpv试试这个:

mpv in.jpg --vf=scale=160:128 --sub-file=in.srt --sub-ass-hinting=light --sub-font=Silkscreen --sub-font-size=54 --sub-back-color=0/0/0/0.5 --sub-color=1/1/1 --o=out.png

(还有--sub-ass-force-style=FontName=Silkscreen,etc.,如果您需要它或者只是更喜欢直接使用 ASS 语法。)

--sub-ass-hinting=normal--sub-ass-hinting=native 可能会更好,但值 light 为我提供了问题中图像的最佳结果。

这是我得到的:

(我在网上找到的源图像的宽高比是 3:2,但您的示例是 4:3。在左侧,我必须使用 --vf=scale=160:120,dsize=160:120 来匹配您的尺寸和宽高比。在右侧,我用--vf=scale=180:120来匹配你的图像高度但保持原来的纵横比。)

为了获得更好的结果,您可能需要调整字体大小,因为据我所知,相关字体已针对特定大小进行了优化。 ASS“字体大小”不是以磅为单位的传统字体大小(而是以像素为单位的上升高度和下降高度之和),所以这并非完全无关紧要,但一些实验可能会让你到达那里。

与您的旧方法相比,这也为您在字幕周围/后面提供了一个更干净的框。当您像现在这样使用带有半透明 OutlineColourBorderStyle=3 时,每行文本都有一个单独的框,并且这些框略有重叠;因此,您可以在每两行文本之间看到一个颜色较深/颜色较深的薄区域。这在你的尺寸下可能不是很明显,但如果你足够努力的话,你会看到它。作为 ASS 格式的扩展,libass 支持自定义 BorderStyle=4,它会在整个文本周围生成一个框。在 mpv 中设置--sub-back-color 时,它会自动选择它。 (如果多个文本同时出现,每个文本仍然有自己的框,并且框可能重叠。但根据我非常简短的搜索,似乎这种情况在 SRT 文件中很少见。)你想恢复到BorderStyle=3 ,我认为您需要添加--sub-ass-force-style=BorderStyle=3 并将--sub-back-color 替换为--sub-border-color

【讨论】:

以上是关于为小视频渲染像素完美的字幕的主要内容,如果未能解决你的问题,请参考以下文章

uniapp小视频项目:滑动播放视频

怎么把视频里的一小段视频做成动态图片?

OC录制小视频

vue怎么加滚动字幕

小视频-上传视频

iOS拍个小视频