在 FFmpeg ASS 字幕中使用后备字体时字体大小不匹配

问题描述 投票:0回答:1

English 文本与 ArabicPersian 字符组合时,我遇到了 FFmpeg 渲染的 ASS 字幕中字体大小不匹配的问题。

重现步骤:

1.字幕文件: 这是 ASS 字幕文件的示例:

[Script Info]
Title: Generated ASS
ScriptType: v4.00+
WrapStyle: 2
ScaledBorderAndShadow: yes
YCbCr Matrix: none
PlayResX: 1920
PlayResY: 1080

[V4+ Styles]
Format: Name, Fontname, Fontsize, PrimaryColour, SecondaryColour, OutlineColour, BackColour, Bold, Italic, Underline, StrikeOut, ScaleX, ScaleY, Spacing, Angle, BorderStyle, Outline, Shadow, Alignment, MarginL, MarginR, MarginV, Encoding
Style: Default, ABeeZee, 40, &H00FFFFFF, &H000000FF, &H00000000, &H00000000, -1, 0, 0, 0, 100, 100, 0, 0, 1, 1, 0, 2, 10, 10, 10, 1

[Events]
Format: Layer, Start, End, Style, Name, MarginL, MarginR, MarginV, Effect, Text
Dialogue: 0,0:00:01.00,0:00:05.00,Default,,0,0,0,,Hello! This is English text.
Dialogue: 0,0:00:05.00,0:00:10.00,Default,,0,0,0,,سلام! This is mixed Arabic/English text.
  1. 使用的命令:
ffmpeg -i input.mp4 -vf "ass=subtitle.ass" output.mp4
  1. 截图: 以下是该问题的两张截图:

• 使用主字体 (ABeeZee) 渲染的文本是正确的。

• 使用后备字体 (Cinema) 渲染的文本尺寸显得更大/更小。

  1. 调试日志:
[Parsed_ass_0 @ 0xb4000079f04f8210] libass API version: 0x1701000
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] libass source: commit: 0.17.1-0-ge8ad72accd3a84268275a9385beb701c9284e5b3
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] Shaper: FriBidi 1.0.13 (SIMPLE) HarfBuzz-ng 8.0.1 (COMPLEX)
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] Using font provider fontconfig
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] Added subtitle file: '/data/***/ass_file.ass' (4 styles, 29 events)
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] fontselect: (ABeeZee, 400, 0) -> /data/***/ABeeZee_regular.ttf, 0, ABeeZee-Regular
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] Glyph 0x633 not found, selecting one more font for (ABeeZee, 400, 0)
[Parsed_ass_0 @ 0xb4000079f04f8210] 
[Parsed_ass_0 @ 0xb4000079f04f8210] fontselect: (ABeeZee, 400, 0) -> /data/***/Cinema.ttf, 0, Cinema

问题

如何确保使用后备字体呈现的文本与主要字体具有相同的大小? FFmpeg 或 ASS 字幕格式中是否有可以解决此问题的特定设置?或者,有没有办法手动调整 FFmpeg 中后备字体的缩放比例?

ffmpeg subtitle android-ffmpeg video-subtitles
1个回答
0
投票

此问题部分是由于字体造成的,部分是由于 ASS 渲染器中文本渲染的工作方式造成的。您的后备字体 Cinema(由 MaryamSoft 提供)有一个异常大的 win-descender,这很奇怪。

看这张图: Line height box and baseline

红线是字母“坐”的基线。低于基线的是胜利下降,高于基线是胜利上升。 Ascender space 用于上升(字母中延伸 x 高度的部分),而 win-ascender 是确定渲染字体上限的实际行。胜利下降具有相同的目的,但低于基线。

而且由于在 Cinema 字体中,win-descender 过大,因此会产生不必要的边距/填充,导致字体看起来比预期小。

这些指标对于 ASS 如何显示字体至关重要,假设文本在 ASS 中的字体大小为 40px(如您的示例中所示),那么它的使用方式如下:

  • 文本由字体的
    OS/2
    表中的
    usWinAscent
    usWinDescent 值定义的线条进行渲染和约束。
  • 然后缩放渲染,使总行高(从 win-ascender 到 win-descender)等于 40px。在上图中,蓝色矩形说明了这一点,它们的高度均为 40 像素。

从技术上讲,单独使用 ASS 可以缓解这种情况(通过应用更大的

\fs
覆盖标签内联,人为调整行间距,使用大的 x 旋转原点
\org
,并使用
\frz
稍微旋转文本) )。然而,我不鼓励这样的黑客行为(除了它会导致更糟糕的渲染性能并导致文本微小失真这一事实之外,但说实话,如果没有并排比较,它是无法区分的)。

更好的方法是修改字体,使

usWinAscent
usWinDescent
值更加合理。如果字体缺少 OS/2 表,您需要调整
sTypoAscender
sTypoDescender
值。请小心不要过度,如果您将值设置得太低,可能会导致部分字形被剪切。

但是,最好的解决方案是简单地选择设计更好的不同后备字体。

© www.soinside.com 2019 - 2024. All rights reserved.