如何使用 FFMPEG 从一系列 1000 个 PNG 图像创建未压缩的 AVI

39 video linux png ffmpeg

如何使用 FFMPEG 从一系列 1000 个 PNG 图像创建未压缩的 AVI?

我使用此命令将input.avi文件转换为一系列 PNG 帧:

ffmpeg -y -i input.avi  -an -vcodec png  -s 1024x768 pic%d.png`
Run Code Online (Sandbox Code Playgroud)

现在我需要知道如何从所有这些 PNG 帧制作未压缩的 AVI 视频。我试过这个:

ffmpeg -i pic%d.png -y -f avi -b 1150 -s 1024x768 -r 29.97 -g 12 -qmin 3 -qmax 13 -ab 224 -ar 44100 -ac 2 test.avi
Run Code Online (Sandbox Code Playgroud)

但与原始 AVI 相比,生成的视频质量下降了很多。

War*_*ung 91

有几种方法可以从 .avi 中获取“未压缩”的 AVI ffmpeg,但我怀疑您实际上是指“无损”。正如您将看到的,这两个术语的定义都有相当大的回旋余地。

我将用 720p 高清版Big Buck Bunny来锚定这个讨论,因为它是一个免费提供的视频,我们都可以用它来测试并获得我们可以比较的结果。24 fps 的 1280×720p 视频的原始数据速率非常接近于您声明的 29.97 fps 目标下的 1024×768 视频的原始数据速率,因此我的结果应该是一个很好的指南,可以指导您对素材的预期数据速率。

自动列出可用选项

以下 POSIX 命令¹ 为您提供了一个列表,其中大部分² 与我们在下面讨论的内容相匹配:

$ ffmpeg -codecs 2> /dev/null | grep '^..EV..S ' | grep -vE 'bitmap|image'
Run Code Online (Sandbox Code Playgroud)

您可能希望在自己的机器上运行该命令,以查看您的 FFmpeg 版本将支持什么。FFmpeg 很少在启用所有可能的编码器的情况下构建。

现在让我们讨论这些选项。

完全未压缩

如果你的“无压缩”的定义是格式的视频被设置于右侧前它是由数字显示转向光子,我在看到最近的ffmpeg -codecs列表是-c:v r210r10kv410v308ayuvv408。这些都是基本相同的东西,仅在颜色深度颜色空间alpha 通道支持方面有所不同。

  • R210R10K是 4:4:4 RGB,每个组件 (bpc) 为 10 位,因此在我的测试中,它们都需要大约708 Mbit/s才能实现 720p。(这大约是每小时 ⅓ TB,朋友们!)

    这些编解码器都将每个像素的 3×10 位颜色分量打包成 32 位值,以便于计算机操作,就像 2 的幂一样。这些编解码器之间的唯一区别是两个未使用的位位于 32 位字的哪一端。这种微不足道的差异无疑是因为它们分别来自竞争公司Blackmagic DesignAJA Video Systems

    尽管这些是简单的编解码器,但您可能需要下载 Blackmagic 和/或 AJA 编解码器才能在计算机上使用它们播放文件。这两家公司都将让您下载自己的编解码器,而不必先买他们的硬件,因为他们知道你可能会处理由客户谁生产的文件有他们的一些硬件。

  • V410本质上只是R210/R10K的YUV版本;它们的数据速率相同。不过,此编解码器可能会编码得更快,因为ffmpeg更有可能在输入帧的色彩空间和此色彩空间之间具有加速的色彩空间转换路径。

    但是,我不能推荐这种编解码器,因为即使安装了 AJA 和 Blackmagic 编解码器,我也无法在我尝试过的任何软件中播放生成的文件。

  • V308V410的 8 bpc 变体,因此在我的测试中达到518 Mbit/s。与 V410 一样,我无法在普通视频播放器软件中播放这些文件。

  • AYUVV408V308本质上是一样的,除了它们包括一个 alpha 通道,无论是否需要!如果您的视频不使用透明度,这意味着您要支付上述 10 bpc R210/R10K 编解码器的尺寸损失,而没有获得更深色彩空间的好处。

    AYUV 确实有一个优点:它是 Windows Media 中的“本机”编解码器,因此不需要特殊软件即可播放。

    V408 应该以相同的方式原生于 QuickTime,但 V408 文件不会在我的 Mac 上的 QuickTime 7 或 10 中播放。

所以,把所有这些放在一起,如果你的 PNG 被命名frame0001.png等等:

$ ffmpeg -i frame%04d.png -c:v r10k output.mov
  ...or...                -c:v r210 output.mov
  ...or...                -c:v v410 output.mov
  ...or...                -c:v v408 output.mov
  ...or...                -c:v v308 output.mov
  ...or...                -c:v ayuv output.avi
Run Code Online (Sandbox Code Playgroud)

请注意,我在 AYUV 的情况下指定了 AVI,因为它几乎是仅适用于 Windows 的编解码器。其他的可能在 QuickTime 或 AVI 中工作,具体取决于您的机器上的编解码器。如果一种容器格式不起作用,请尝试另一种。

上面的命令 - 以及下面的命令 - 假设您的输入帧已经与您想要的输出视频大小相同。如果没有,请-s 1280x720在命令中添加类似的内容,在输出文件名之前。

压缩的 RGB,但也是无损的

如果,正如我怀疑的那样,您实际上是指“无损”而不是“未压缩”,那么比上述任何一个都更好的选择是Apple QuickTime Animation,通过-c:v qtrle

我知道你说你想要一个 AVI,但事实是你可能必须在 Windows 机器上安装一个编解码器来读取这里提到的任何基于 AVI 的文件格式,而使用 QuickTime 有可能是视频您选择的应用程序已经知道如何打开 QuickTime 动画文件。(上面的 AYUV 编解码器是我所知道的唯一例外,但它的数据速率非常高,只是为了获得 AVI 的好处。)

ffmpeg将为您填充qtrle到 AVI 容器中,但结果可能不是非常广泛兼容。在我的测试中,QuickTime Player 会对这样的文件有点不满,但它会播放它。奇怪的是,即使VLC部分基于ffmpeg. 对于这个编解码器,我会坚持使用 QT 容器。

QuickTime 动画编解码器使用一个简单的RLE方案,因此对于简单的动画,它应该和下面的 Huffyuv 一样好。每帧中的颜色越多,它就越接近上述完全未压缩选项的比特率。在我与大巴克兔子测试中,我能得到ffmpeg给我一个165 Mbit / s的在RGB 4文件:4:4模式下通过-pix_fmt rgb24

尽管此格式已压缩,但它会为您的 PNG 输入文件提供相同的输出像素值,原因与PNG 的无损压缩不会影响像素值的原因相同。

ffmpeg通道的QuickTime动画的实现也支持-pix_fmt argb,它可以让你4:4:4:4 RGB,这意味着它有一个alpha通道。以一种非常粗略的方式,它相当于-c:v ayuv上面提到的 QuickTime 。然而,由于无损压缩,它只有214 Mbit/s,低于 AYUV 数据速率的 1/3,质量或特征损失为零。

QuickTime Animation 有一些每像素少于24 位的变体,但它们最适合用于逐渐简化的动画样式。ffmpeg似乎仅支持规范定义的其他格式之一-pix_fmt rgb555be,即 15 bpp big-endian RGB。对于某些视频来说这是可以接受的,并且对于大多数截屏视频捕获和简单的动画来说都可以。如果您可以接受色彩空间抽取,您可能会发现它的122 Mbit/s数据速率很有吸引力。

将所有这些放在一起:

$ ffmpeg -i frame%04d.png -c:v qtrle -pix_fmt rgb24    output.mov
  ...or...                           -pix_fmt argb     output.mov
  ...or...                           -pix_fmt rgb555be output.mov
Run Code Online (Sandbox Code Playgroud)

有效无损:YUV 技巧

现在,关于RGB和4:4:4 YUV的事情是这些编码对于计算机来说很容易处理,但是它们忽略了一个关于人类视觉的事实,即我们的眼睛对黑白差异比对颜色差异更敏感.

因此,视频存储和传输系统几乎总是使用比亮度信息更少的每像素位来处理颜色信息。这称为色度子采样。最常见的方案是 4:2:0 和 4:2:2。

4:2:0 YUV 的数据速率仅比黑白(仅 Y)未压缩视频高 50%,是 4:4:4 RGB 或 YUV 数据速率的 1/2。

4:2:2 是一种介于 4:2:0 和 4:4:4 之间的中间点。它是 Y-only 视频数据速率的两倍和 4:4:4 数据速率的 ⅔。

您有时还会看到 4:1:1,就像在旧的DV 摄像机标准中一样。4:1:1 与 4:2:0 具有相同的未压缩数据速率,但颜色信息的排列方式不同。

所有这一切的重点是,如果您从 4:2:0 H.264 文件开始,将其重新编码为 4:4:4 未压缩 RGB 绝对不会超过 4:2:0 无损压缩的 YUV。即使您知道您的工作流程是 4:4:4 RGB,也是如此,因为这是一个微不足道的转换;视频硬件和软件会定期进行此类转换。

当您进行像素窥视或对视频进行像素级颜色更改时,您实际上只需要 4:4:4,并且您需要保留精确的像素值。例如,使用 4:4:4 像素格式更容易完成视觉效果(VFX) 工作,因此高端 VFX 公司通常愿意容忍其所需的更高数据速率。

有效无损:编解码器选择

一旦您开始使用带有颜色抽取的 YUV 编解码器,您的选择也会随之打开。ffmpeg有许多有效的无损编解码器。

胡菲夫

最广泛兼容的选项是Huffyuv。你通过-c:v huffyuv.

最初的 Windows Huffyuv 编解码器仅支持两种像素格式:RGB24 和 YUV 4:2:2。(实际上,它支持两种 YUV 4:2:2 风格,仅在磁盘上的字节顺序上有所不同。)

旧版本的 FFmpeg Huffyuv 编解码器不包括 RGB24 支持,因此如果您尝试它并且 FFmpeg 告诉您它将使用yuv422p像素格式,您需要升级。

FFmpeg 还有一个名为 FFVHuff 的 Huffyuv 变体编解码器,它支持 YUV 4:2:0。此变体与 Windows DirectShow Huffyuv 编解码器不兼容,但它应该可以在任何基于 的软件中打开libavcodec,例如 VLC。

  • RGB24 — RGB 4:4:4 本质上与 QuickTime Animation 的 RGB24 色彩空间选项相同。对于给定的文件,这两种编解码器在压缩方面会有所不同,但它们通常很接近。

    它也与上面 V308 选项使用的 YUV 4:4:4 模式基本相同。颜色空间差异没有实际区别,因为颜色空间转换很容易实时进行。

    由于 Huffyuv 的无损压缩,我能够在 RGB24 模式下将测试视频压缩到大约251 Mbit/s,其视觉质量与从 V308 或 AYUV 获得的视觉质量相同。如果 AVI对您来说绝对是必须的,那么安装Huffyuv 编解码器可能比支付 AYUV 的 3 倍数据速率成本更痛苦。

  • YUV 4:2:2——这种模式对于视频来说比RGB24更实用,这无疑是ffmpeg开发者选择首先实现它的原因。正如您对上面讨论的理论 ⅔ 减少所期望的那样,我的测试文件编码为173 Mbit/s。如果您考虑到这两个测试之间的音轨没有变化这一事实,那几乎就是 ⅔。

  • YUV 4:2:0 — 此选项比 4:2:2 更能减少颜色信息,在我的测试中将数据速率降至133 Mbit/s

将所有这些放在一起:

$ ffmpeg -i frame%04d.png -c:v huffyuv -pix_fmt rgb24   output.avi
  ...or...                             -pix_fmt yuv422p output.avi
  ...or...                -c:v ffvhuff -pix_fmt yuv420p output.avi
Run Code Online (Sandbox Code Playgroud)

尽管ffvhuff编解码器在我编写本文时默认为 4:2:0,并且确实在我使用的发行版中支持该像素格式,但这正在发生变化,因此您应该包含该标志,以防此默认值发生变化。

视频

与 Huffyuv 和 FFVHuff 具有相同精神的更新选项是Ut Video。像 Huffyuv 一样,有一个 Windows 视频编解码器,这意味着任何可以播放电影的 Windows 程序都可以在安装了编解码器的情况下使用此编解码器播放视频。与 Huffyuv 不同的是,还有一个 Mac 视频编解码器,因此您不受基于 FFmpeg 的软件或libavcodec在 Mac 上读取这些文件的限制。

这个编解码器在色彩空间方面非常灵活,所以我只举几个常见色彩空间的例子:

  • 4:4:4 RGB via-f avi -c:v utvideo -pix_fmt rgb24提供178 Mbit/sec输出

  • 4:4:4 YUV via-f avi -c:v utvideo -pix_fmt yuv444p提供153 Mbit/sec输出

  • 4:2:2 YUV via-f avi -c:v utvideo -pix_fmt yuv422p提供123 Mbit/sec输出

  • 4:2:0 YUV via-f avi -c:v utvideo -pix_fmt yuv420p提供100 Mbit/sec输出

我怀疑 4:4:4 YUV 在这个测试中比 4:4:4 RGB 更好,尽管这两个在技术上是等效的,因为源视频是 4:2:0 YUV,所以以 YUV 格式排列数据可以实现更好的无损压缩通过在文件中将部分冗余的 U 和 V 通道组合在一起。

FFV1

这个领域的另一个有趣的选择是 FFmpeg 自己的FFV1编解码器。这主要用作档案编解码器,而不是播放或编辑编解码器,但由于很多软件要么基于libavcodec支持 FFmpeg的库,要么可以libavcodec通过诸如 之类的工具进行绑定ffdshow,因此无论如何它可能对您有用。

默认情况下,ffmpeg在使用像 FFV1 这样灵活的编解码器时将保留输入文件的色彩空间,因此如果您向它提供官方 Big Buck Bunny MP4 文件之一(使用 4:2:0 YUV),您将得到除非你给 一个-pix_fmt标志ffmpeg。这会产生一个63 Mbit/s 的输出文件。

如果你强制 FFV1 使用 4:4:4 YUV 色彩空间-pix_fmt yuv444p,文件大小只会上升到86 Mbit/sec,但在这种情况下它不会给我们带来任何好处,因为我们是从 4:2:0 原始编码. 但是,如果您输入一组 PNG,就像在原始问题中一样,输出文件可能会使用bgrabgr0颜色空间,这只是上面提到的argbrgb24颜色空间的重新排列。

无损 H.264

另一个有趣的选择是Lossless H.264。在撰写本文时,这几乎是仅适用x264 的东西,但那些在编码端使用 FFmpeg 的人很可能也在使用包含libx264解码端的其他软件,例如 VLC。

获取此类文件的最简单方法是:

$ ffmpeg -i frame%04d.png -c:v libx264 -qp 0 -f mp4 output.mp4
Run Code Online (Sandbox Code Playgroud)

-qp 0标志是关键:较高的值给有损压缩。(您也可以给予-crf 0以获得相同的效果。)

与 FFV1 一样,ffmpeg将尝试猜测给定输入色彩空间的最佳输出色彩空间,因此为了与上述结果进行比较,我对具有不同色彩空间的 Big Buck Bunny 源文件进行了多次编码:

  • yuv444p:这是ffmpeg当你给它一个 RGB PNG 流时的选择,就像在原始问题中一样,结果是一个44 Mbit/sec 的文件和我们的测试文件

  • yuv422p:这类似于Huffyuv的默认色彩空间,但在这种情况下我们得到了一个34 Mbit/sec 的文件,相当节省!

  • yuv420p:这是我正在测试的 Big Buck Bunny 官方 MP4 的默认设置,并生成29 Mbit/sec 的文件。

请注意,为了获得如此小的文件大小,您需要牺牲大量兼容性。这就是为什么我什至没有费心把它塞进一个 AVI 或 MOV 容器中。它与 x264 紧密相关,您不妨改用其标准容器类型 (MP4)。您也可以为此使用Matroska 之类的东西。

您可以通过添加-preset ultrafast. 在 YUV 4:2:2 模式下,这将我的测试文件的比特率提高到44 Mbit/s,但正如承诺的那样,编码速度要快得多。文档声称这-preset veryslow也是值得的,但它导致更长的编码时间,同时只节省了一点点空间;我不能推荐它。

其他

ffmpeg还支持Lagarith的仅解码模式和无损 JPEG的仅编码模式。这两个编解码器实际上有些相似,并且应该提供比 Huffyuv 小一点的相同质量的文件。如果ffmpeg开发人员添加 Lagarith 编码,它将成为 Huffyuv 的强大替代品。不过,我不能推荐无损 JPEG,因为它不享受广泛的解码支持。

感知上无损:或者,您可能可以摆脱一些损失

然后是感知无损的编解码器。除非您在进行像素窥视,否则您几乎肯定无法分辨出这些提供的视觉效果与前两组不同。通过放弃视频捕获传感器和显示设备之间绝对零变化的想法,您可以节省大量成本:

  • Apple ProRes :-c:v prores或者-c:v prores_ks— ProRes 是一种基于配置文件的编解码器,这意味着有多种变体,每个变体都具有不同的质量与空间权衡:

    • ProRes 4444仅使用114 Mbit/s对我们的测试视频进行编码,但具有VFX 质量。目前prores*在 FFmpeg 中有三种不同的编解码器,但仅prores_ks支持 ProRes 4444,正如我写的那样,通过-profile:v 4444选项。

      如果您想知道为什么要使用 ProRes 4444 而不是 Lossless H.264,这归结为兼容性、解码速度、可预测性和 Alpha 通道。

    • ProRes 422节省了更多空间,仅需要84 Mbit/s 的速度即可提供您仅通过像素窥视就能从 ProRes 4444 中辨别出来的结果。除非您需要 ProRes 4444 提供的 Alpha 通道,否则可能没有理由坚持使用 ProRes 4444。

      ProRes 422 是上述 Lossless H.264 选项的更接近的竞争对手,因为它们都不支持 alpha 通道。如果您需要与 Apple 专业视频应用程序的兼容性、编码和解码的较低 CPU 开销或可预测的比特率,您将需要容忍 ProRes 的更高比特率。例如,后者对于硬件编码器很重要。另一方面,如果您可以解决 Lossless H.264 的兼容性问题,您可以选择使用 4:2:0 色彩空间,这不是任何 ProRes 配置文件中的选项。

      FFmpeg 中的所有三个 ProRes 编码器都支持 ProRes 422 配置文件,因此最简单的选择是使用-c:v prores,而不是-c:v prores_ks -profile hq,或依赖于 的自动配置文件功能prores_ks来做正确的事情。

    还有更简洁的 ProRes 配置文件,但它们适用于标清视频或作为全分辨率文件的代理

    ProRes 的主要问题是它在 Apple 和专业视频世界之外还没有得到广泛的支持。

  • Avid 的 DNxHD是与 ProRes 类似的编解码器,但与 Apple 专业视频世界无关。Avid 为Windows 和 Macintosh提供可免费下载的编解码器,FFmpeg 现在通过-c:v dnxhd.

    因为 DNxHD 是一种类似于 ProRes 的基于配置文件的编解码器,您可以从预定义的集合中选择配置文件,这会告诉编解码器要使用的帧大小、帧速率和比特率。对于 Big Buck Bunny 测试文件,-b:v 60M配置文件最合适。不出所料,生成的文件大约为59 Mbit/s

  • 低损耗 MJPEG-vcodec mjpeg -qscale:v 1——这比无损 JPEG 更常见。事实上,这曾经是一个非常常见的视频编辑编解码器,它仍然经常被网络流媒体摄像机等使用。所有这些历史意味着很容易找到支持它的软件。

    预计此编解码器的数据速率变化很大。我刚刚在此处进行的测试为 720p 视频提供了25 Mbit/s 的速度。这足够高的压缩率让我对损失感到紧张,但对我来说看起来很不错。仅基于数据速率,我认为它的质量可能与12 Mbit/s MPEG-2 或6 Mbit/s H.264相当。

将所有这些放在一起:

$ ffmpeg -i frame%04d.png -c:v prores_ks -profile:v 4444 output.mov
  ...or...                -c:v prores_ks -profile:v hq   output.mov
  ...or...                -c:v prores                    output.mov
  ...or...                -c:v dnxhd -b:v 60M            output.mov
  ...or...                -c:v mjpeg -qscale:v 1         output.avi
Run Code Online (Sandbox Code Playgroud)

这些方法的底线是,除非你做一些非常苛刻的事情,否则“足够好”真的足够好。


脚注和题外话

  1. 该命令应该在 Linux、macOS、BSD 和 Unix 上按原样运行。如果您使用的是 Windows,则可以通过CygwinWSL获得 POSIX 命令行。

  2. 该命令生成的列表与我在上面讨论的编解码器集不完全匹配的原因有几个:

    • 第二个grep是为了过滤掉不合适的编码器,比如bmp不是“视频”编解码器,尽管V在这个列表中被标记了。虽然从技术上讲,您可能会将其中的许多内容放入 AVI、MP4 或 MKV 等容器中以获取单文件视频,但除了基于ffmpeglibavcodec.

      有一些例外,例如它-f avi -c:v ljpeg提供了可以称为“无损 MJPEG”的东西,但作为一项规则,我们对将许多静止图像文件塞入此处的 A/V 容器来制作电影不感兴趣。我们在这里需要广泛认可的视频编解码器,而不是语义欺骗。

    • 该命令当前无法过滤掉一些不合适的编码器,例如 GIF,因为它们当前未在ffmpeg -codecs输出中描述为bitmapimage文件格式。

      GIF 是一个有趣的案例:它支持单个 GIF 文件中的多个图像帧以及用于运动播放的时序信息,但出于多种原因,它完全不适合我们在这里的讨论。

    • 几个正在显示的选项是过时或从来没有真正得到多大吸引力,比如flashsvdiracsnow,因此它不值得讨论他们以上。

    • 该列表中的一些选项仅用于ffmpeg实例之间或ffmpeg与另一个程序之间的管道,例如rawvideoand wrapped_avframe,因此不适合我们这里的目的。

    • 在上面的讨论接近尾声时,我明智地扩大了问题的范围,以包含一些精心选择的有损选项,因此它们不会通过grep上述命令中的第一个过滤器。


Pet*_*des 10

所以我最终让我自己的答案太长了。
TL; DR概要:无损存储的图像,使用的序列libx264libx264rgb-preset ultrafast -qp 0。它几乎和 ffvhuff 一样快,比特率低得多,解码速度也更快。 huffyuv在 ffmpeg 之外得到更广泛的支持,但不支持ffvhuff. 所以这是使用 h.264 的另一个原因,假设您的其他工具可以处理High 4:4:4 Predictivex264 在无损模式下使用的 h.264配置文件。x264 只能在需要对任意帧进行快速随机访问的情况下进行内部处理。

从图像目录中读取时,请注意影响 libx264rgb的ffmpeg 错误。(谁知道其他情况。)在使用之前测试您的设置中的无损。(易于使用ffmpeg -i in -pix_fmt rgb24 -f framemd5源和无损压缩))

编辑:utvideo编码和解码相当快,并且是比 h.264 更简单的编解码器。它基本上是一个现代的huffyuv,支持更有用的色彩空间。如果您在使用 h.264 时遇到问题,请尝试使用 utvideo 接下来获取临时文件。

编辑 2:PNG 作为 RGB 编解码器似乎表现不错,至少在 Sintel 预告片上是这样。

另请参阅我对类似问题的类似回答:https : //superuser.com/a/860335/20798

Warren Young 的回答中有很多关于各种原始格式和编解码器的信息。我认为如果它更短,答案会更有用,所以我正在做一个新的答案。如果您正在使用不支持无损 x264 或 ffvhuff 的软件,那么其中一些信息可能仍然有用。

在这种情况下,“无损”最有用的定义是您可以逐位恢复输入。无论您做什么,都无需担心视频编码的质量下降。

http://en.wikipedia.org/wiki/Chroma_subsampling

理想情况下,避免多次色彩空间转换。舍入误差可能会累积。如果您打算使用在 RGB 色彩空间中工作的过滤器处理视频,那么保持 RGB 是有意义的,只要更高的比特率不是问题。您可能最终会制作一个yuv 4:2:0视频,但保持额外的色度分辨率可能很有用,具体取决于您要应用的过滤器。

无论哪种方式,无损X264和ffvhuff都支持RGB和YUV 4:4:44:2:24:2:0。我建议使用 x264,因为它解码速度很快。如果您尝试实时播放 RGB 高清视频,请尝试使用 opengl 而不是 xv,因为我系统上的 xv 仅接受 yuv 输入。mplayer 需要额外的 CPU 时间来进行色彩空间转换。

以下编码器测试的来源:https : //media.xiph.org/https://media.xiph.org/sintel/sintel_trailer-1080-png.tar.gz 他们忘记为 sintel 拖车 gzip y4m 文件,所以 png tarball 实际上要小得多。

ffmpeg -i 1080/sintel_trailer_2k_%4d.png -i sintel_trailer-audio.flac \
-c:a copy -c:v libx264rgb -preset ultrafast -qp 0 \
frompng.sintel.264rgb.mkv
Run Code Online (Sandbox Code Playgroud)

例如

peter@tesla:/mnt/GP1TB/p/encoder-sample/sintel$ time ffmpeg -i 1080/sintel_trailer_2k_%4d.png -i sintel_trailer-audio.flac -c:a copy -c:v libx264rgb -preset ultrafast -qp 0 frompng.sintel.264rgb.mkv
ffmpeg version N-67983-g2b358b4 Copyright (c) 2000-2015 the FFmpeg developers
  built on Jan 10 2015 05:32:37 with gcc 4.8 (Ubuntu 4.8.2-19ubuntu1)
  configuration: --enable-gpl --enable-version3 --enable-nonfree --disable-doc --disable-ffserver --enable-libx264 --enable-libx265 --enable-libmp3lame --enable-libopus --enable-libwebp --enable-libvpx --disable-outdev=oss --disable-indev=oss --disable-encoder=vorbis --enable-libvorbis --enable-libfdk-aac --disable-encoder=aac --disable-decoder=jpeg2000
  libavutil      54. 16.100 / 54. 16.100
  libavcodec     56. 20.100 / 56. 20.100
  libavformat    56. 18.100 / 56. 18.100
  libavdevice    56.  3.100 / 56.  3.100
  libavfilter     5.  7.100 /  5.  7.100
  libswscale      3.  1.101 /  3.  1.101
  libswresample   1.  1.100 /  1.  1.100
  libpostproc    53.  3.100 / 53.  3.100
Input #0, image2, from '1080/sintel_trailer_2k_%4d.png':
  Duration: 00:00:50.12, start: 0.000000, bitrate: N/A
    Stream #0:0: Video: png, rgb24, 1920x1080 [SAR 72:72 DAR 16:9], 25 fps, 25 tbr, 25 tbn, 25 tbc
Input #1, flac, from 'sintel_trailer-audio.flac':
  Duration: 00:00:52.00, start: 0.000000, bitrate: 721 kb/s
    Stream #1:0: Audio: flac, 48000 Hz, stereo, s16
File 'frompng.sintel.264rgb.mkv' already exists. Overwrite ? [y/N] y
No pixel format specified, rgb24 for H.264 encoding chosen.
Use -pix_fmt yuv420p for compatibility with outdated media players.
[libx264rgb @ 0x2770760] using SAR=1/1
[libx264rgb @ 0x2770760] using cpu capabilities: MMX2 SSE2Fast SSSE3 Cache64 SlowShuffle
[libx264rgb @ 0x2770760] profile High 4:4:4 Predictive, level 4.0, 4:4:4 8-bit
[libx264rgb @ 0x2770760] 264 - core 144 r2525+2 6a4fca8 - H.264/MPEG-4 AVC codec - Copyleft 2003-2014 - http://www.videolan.org/x264.html - options: cabac=0 ref=1 deblock=0:0:0 analyse=0:0 me=dia subme=0 psy=0 mixed_ref=0 me_range=16 chroma_me=1 trellis=0 8x8dct=0 cqm=0 deadzone=21,11 fast_pskip=0 chroma_qp_offset=0 threads=3 lookahead_threads=1 sliced_threads=0 nr=0 decimate=1 interlaced=0 bluray_compat=0 constrained_intra=0 bframes=0 weightp=0 keyint=250 keyint_min=25 scenecut=0 intra_refresh=0 rc=cqp mbtree=0 qp=0
Output #0, matroska, to 'frompng.sintel.264rgb.mkv':
  Metadata:
    encoder         : Lavf56.18.100
    Stream #0:0: Video: h264 (libx264rgb) (H264 / 0x34363248), rgb24, 1920x1080 [SAR 72:72 DAR 16:9], q=-1--1, 25 fps, 1k tbn, 25 tbc
    Metadata:
      encoder         : Lavc56.20.100 libx264rgb
    Stream #0:1: Audio: flac ([172][241][0][0] / 0xF1AC), 48000 Hz, stereo (16 bit)
Stream mapping:
  Stream #0:0 -> #0:0 (png (native) -> h264 (libx264rgb))
  Stream #1:0 -> #0:1 (copy)
Press [q] to stop, [?] for help
frame= 1253 fps= 18 q=-1.0 Lsize=  834790kB time=00:00:51.96 bitrate=131592.5kbits/s
video:830198kB audio:4575kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: 0.002025%
[libx264rgb @ 0x2770760] frame I:6     Avg QP: 0.00  size:612470
[libx264rgb @ 0x2770760] frame P:1247  Avg QP: 0.00  size:678787
[libx264rgb @ 0x2770760] mb I  I16..4: 100.0%  0.0%  0.0%
[libx264rgb @ 0x2770760] mb P  I16..4: 50.3%  0.0%  0.0%  P16..4: 12.0%  0.0%  0.0%  0.0%  0.0%    skip:37.6%
[libx264rgb @ 0x2770760] coded y,u,v intra: 71.1% 68.2% 70.0% inter: 22.8% 22.8% 23.2%
[libx264rgb @ 0x2770760] i16 v,h,dc,p: 50% 48%  1%  1%
[libx264rgb @ 0x2770760] kb/s:135693.94
Run Code Online (Sandbox Code Playgroud)

请注意,我忘记指定-r 24fps,因此它不会与音频保持 av 同步。(并且比特率(但不是文件大小)数字也会关闭。ffmpeg 默认为 25fps)。这台机器的 CPU 是第一代 (conroe) core2duo 2.4GHz (E6600)。

结果:

4.5M    sintel_trailer-audio.flac  # this is muxed in to every mkv
948M    1080  # the directory of PNGs
940M    /var/tmp/dl/sintel_trailer-1080-png.tar.gz
7434M   sintel.y4m  # yuv444, uncompressed.  mplayer gets the colors wrong?
2342M   qtrle.mkv   # encode went at 16fps, so qtrle is slower and worse filesize
2105M   sintel.huff.mkv  # ffvhuff with default options, rgb pix fmt
1228M    sintel.utvideo.mkv  # muxed without audio, I should update the others this way
946M    png-copy.mkv  # -codec copy makes a MPNG stream.  Use -codec png for non-png sources, but it won't make PNGs as small.  Decodes very fast
824M    lossy.prores_ks.mov # yuv444p10le extremely slow to encode (2.3fps), and worse bitrate.
816M    frompng.sintel.264rgb.mkv
735M    sintel.x264rgb.medium.nocabac.mkv  # encode went at 3.3 fps instead of 18.  Better gain than for live-action, though
626M    sintel_trailer.rgb.lossless.veryslow.mkv # 1.1fps.  With CABAC, 16 ref frames, etc. etc.
512M    lossy.prores.mov # yuv422p10le, 12fps
341M    sintel.yuv420.x264.lossless.mkv
21M     lossy.rgb.crf26.preset=medium.mkv
13M     lossy.yuv420.crf26.preset=medium.mkv  # remember this is WITH 4.5MB audio
Run Code Online (Sandbox Code Playgroud)

请注意,mediainfo不知道 RGB h.264,它仍然说文件是 YUV。

检查它是否真的是无损的:

ffmpeg -i 1080/sintel_trailer_2k_%4d.png -f framemd5 png.framemd5
ffmpeg -i fromhuff.sintel.264rgb.mkv -an -sn -pix_fmt rgb24  -f framemd5 x264rgb.framemd5
diff -s *.framemd5
Files png.framemd5 and x264rgb.framemd5 are identical
Run Code Online (Sandbox Code Playgroud)

因此,您可以通过这种方式恢复原始 PNG 输入,即您可以制作具有相同图像数据的 PNG。

请注意-pix_fmt rgb24x264 测试的 。ffmpeg 的 h.264 解码器输出 gbrp(平面,未打包)输出,因此位相同,但顺序不同。framemd5“容器”不会强加任何格式限制,但如果位的排列方式相同,您只会得到相同的 md5。我只是看了看 ffmpeg 在我给它提供 PNG 时说它用于 pix fmt 的内容,然后将其用作-pix_fmt解码的 arg 。顺便说一句,这就是 vlc 不会播放 RGB h.264 文件的原因(直到下一个版本,或当前每晚构建):它不支持 gbrp 像素格式。

对于 yuv 使用libx264,不是libx264rgb. 您不需要安装 x264 的 RGB 版本,实际库支持两者。只是 ffmpeg 将它实现为两个不同命名的编码器。我认为如果他们没有这样做,默认行为是将 rgb 输入保留为 rgb,并在以相同质量产生更高比特率输出的同时运行非常缓慢。(-pix_fmt yuv420p如果需要420,您有时仍然必须使用而不是444h.264 输出。

除非您制作文件用于长期存储,否则请始终使用-preset ultrafast无损 x264。更多的参考帧和运动搜索对于无损,对于带有任何噪音的非动画材料几乎没有任何区别。CABAC 以无损比特率占用大量 CPU,甚至解码也是如此。仅用于存档目的,而不是临时文件。(超快禁用 CABAC)。CABAC 可节省 10% 到 15% 的比特率。

如果您需要每一帧都成为关键帧,请设置-keyint 1. 那么只想在关键帧上或w/e上剪切的视频编辑软件将不会限制您。

回答最初的问题:这是在分阶段尝试时抛出临时文件应该做的事情(例如,缓慢的去隔行扫描,在尝试其他事情之前保存无损输出):

ffmpeg -i dv-video-source.ts -vf yadif=2:1,mcdeint=3:1:10 -c:a copy -c:v libx264 -preset ultrafast -qp 0 deinterlaced.mkv

如果您确实需要可以使用静止图像工具修改的图像文件中的输出,那么当然可以解码为 png。除了每个像素的 Y、Cb 和 Cr 值的 8 位中的最低有效位之外,您不会丢失任何东西。

x264 在这方面表现得非常好,因为有很多黑色帧和一些文本、淡入和淡出,以及许多帧的大区域之间的完美相似性,即使使用-preset ultrafast. 在真人版中,我仍然看到 x264 的文件大小是 ffvhuff (yuv420) 的一半。

对于任何好奇的人:高 CPU 时间无损 rgb 编码具有(x264 核心 144 r2525):

[libx264rgb @ 0x35b97a0] frame I:27    Avg QP: 0.00  size:604367
[libx264rgb @ 0x35b97a0] frame P:1226  Avg QP: 0.00  size:517512
[libx264rgb @ 0x35b97a0] mb I  I16..4..PCM: 46.3% 38.1% 15.7%  0.0%
[libx264rgb @ 0x35b97a0] mb P  I16..4..PCM: 24.3%  5.4%  4.5%  0.0%  P16..4: 10.5%  3.3%  5.7%  0.0%  0.0%    skip:46.3%
[libx264rgb @ 0x35b97a0] 8x8 transform intra:17.3% inter:46.1%
[libx264rgb @ 0x35b97a0] coded y,u,v intra: 81.6% 77.5% 80.0% inter: 28.0% 27.7% 28.1%
[libx264rgb @ 0x35b97a0] i16 v,h,dc,p: 35% 64%  1%  0%
[libx264rgb @ 0x35b97a0] i8 v,h,dc,ddl,ddr,vr,hd,vl,hu: 31% 49% 13%  2%  1%  1%  1%  1%  1%
[libx264rgb @ 0x35b97a0] i4 v,h,dc,ddl,ddr,vr,hd,vl,hu: 31% 37%  5%  5%  6%  5%  5%  4%  3%
[libx264rgb @ 0x35b97a0] Weighted P-Frames: Y:41.1% UV:40.7%
[libx264rgb @ 0x35b97a0] ref P L0: 74.5%  4.2%  9.1%  4.1%  2.1%  1.7%  1.2%  0.8%  0.6%  0.5%  0.3%  0.2%  0.2%  0.2%  0.2%  0.1%
[libx264rgb @ 0x35b97a0] kb/s:99721.66
Run Code Online (Sandbox Code Playgroud)

注意加权 p 帧的真正高比例,以及跳过宏块的真正高比例。每个场景转换都是淡入淡出,而不是剪切,如果您给它 CPU 时间来弄清楚如何做,x264 就会发挥优势。

进一步说明(用于编辑的有损编解码器):

对于通过剪辑向前/向后擦洗,通常只支持内部编解码器(utvideo、ffvhuff、mjpeg、jpeg2000、pro-res、AVC-Intra)。我认为具有短 GOP(1/2 到 1 秒)的常规 AVC 也可以很好地擦洗,只要软件知道它在做什么(快速擦洗时解码最近的 I 帧,在 GOP 内解码以获得如果您在时间轴上放大到需要的足够多的帧)。

我已经在这个和https://video.stackexchange.com/上发布了一些关于 pro-res 的负面信息,比如“如果它比无损编解码器更慢、更糟糕的压缩有什么意义”,但它确实有一些有趣的功能。 Apple 表示,它可以以半分辨率解码,而 CPU 时间仅为解码 full rez 的 1/3。

ffmpeg 的 prores 实现可能也没有像 Apple 那样针对速度进行优化,这就是为什么我对 ffmpeg 的测试使它看起来很慢。如果您有基于 ffmpeg 的工具的免费软件工作流程,则可能不值得使用,但如果您使用的是商业软件,则可能值得尝试。

我不做很多视频编辑,主要只是编码,所以我不太清楚什么样的测试适合像 prores 这样的编解码器。我猜想 mjpeg 可能是一个很好的快速替代方案,如果短 GOP x264 不能很好地工作。在 Linux 发行版中有 jpeg 的 asm 加速实现,它是一个非常简单的编解码器。您可以根据需要调高或调低质量,以在质量与文件大小 + 编码/解码速度之间进行权衡。它很古老,但如果你想要一个非常快的内部编解码器,它可能会击败 x264。

对于 x264,我会尝试类似x264 --crf 10 --keyint=1 --preset superfast --tune fastdecode (Intra-only,没有任何其他--avcintra-class设置的东西。) Note superfast(没有 CABAC) 或faster, notultrafast可能是有损操作的最佳选择。我认为超快在没有那么快的情况下损失了很多质量。您使用的质量越低(crf 越高),花费更多的 CPU 时间来寻找更好的编码就越值得。不过,其中很多可能与 GOP size = 1 无关。

当 GOP 大小 > 1 时,如果您在编码中投入了如此多的位,以至于在对残差进行编码时更好的帧间预测将不会节省很多位(因为帧之间的噪声/颗粒/细微变化得到了非常准确的保留),然后只是超快可能没问题。否则,与--keyint=30或什么,可能--preset veryfast --crf 12会很有趣。

理论上,给定 CRF 设置的质量在预设中应该是恒定的。如果您正在寻找较小的文件(更快的解码),权衡一些质量和一些编码时间是有意义的。