6

我正在尝试同时读取和写入由 AVAssetWriter 编写的 H.264 mov 文件。我设法提取了单个 NAL 单元,将它们打包到 ffmpeg 的 AVPackets 中,并使用 ffmpeg 将它们写入另一种视频格式。它工作正常,生成的文件播放良好,但播放速度不正确。如何从原始 H.264 数据计算正确的 PTS/DTS 值?或者也许还有其他方法可以得到它们?

这是我尝试过的:

  1. 将捕获最小/最大帧速率限制为 30,并假设输出文件为 30 fps。事实上,它的 fps 总是小于我设置的值。而且,我认为 fps 在数据包之间不是恒定的。

  2. 记住每个书面样本的呈现时间戳,并假设样本一对一映射到 NALU,并将保存的时间戳应用于输出数据包。这行不通。

  3. 将 PTS 设置为 0 或 AV_NOPTS_VALUE。不工作。

通过谷歌搜索,我了解到原始 H.264 数据通常不包含任何时间信息。它有时可以在 SEI 中包含一些时间信息,但我使用的文件没有它。另一方面,有一些应用程序完全可以做我想做的事情,所以我想它是可能的。

4

1 回答 1

5

您要么必须自己生成它们,要么访问 MP4/MOV 容器中包含时序信息的 Atom 以生成 PTS/DTS 信息。FFmpeg 在 libavformat 中的 mov.c 可能会有所帮助。

您使用 AVAssetWriter 编写的每个样本/帧都将与 VCL NAL 一对一映射。如果您所做的只是转换,那么让 FFmpeg 完成所有繁重的工作。从一种容器格式转换到另一种容器格式时,它将正确维护时间信息。

AVAssetWriter 生成的比特流不包含 SEI 数据。它只包含 SPS/PPS/I/P 帧。SPS 也不包含 VUI 或 HRD 参数。

- 编辑 -

另外,请记住,如果您从 CMSampleBufferRef 保存 PTS 信息,则时基可能与目标容器的时基不同。例如 AVFoundation 时基是纳秒,而 FLV 文件是毫秒。

于 2012-06-22T21:20:47.510 回答