gpt4 book ai didi

android - 使用不带 MediaExtractor 的 MediaCodec 解码 mp4/h.264,预期访问单元格式

转载 作者:塔克拉玛干 更新时间:2023-11-02 20:54:44 24 4
gpt4 key购买 nike

我试图在不使用 MediaExtractor API 的情况下使用 MediaCodec API 进行解码。相反,我使用 mp4parser 从 mp4 文件中获取样本。目前,我只使用 h.264/avc 编码的视频内容。

MediaCodec API的官方文档状态:

buffers do not start and end on arbitrary byte boundaries, this is not a stream of bytes, it's a stream of access units.

意思是,我必须将访问单元提供给解码器。但是,我错过了此信息中的一些细节:

对于 h.264,在一个 mp4 样本中,可以有多个 NAL 单元,每个单元前面有 4 个(默认)字节指定 NAL 单元长度。

现在我的问题:

  1. 可以有 mp4 样本,其中编解码器配置 NAL 单元(sps、pps)与包含编码(部分)帧的 NAL 单元混合。在这种情况下,我是否应该在调用 queueInputBuffers() 时传递标志 BUFFER_FLAG_CODEC_CONFIG

  2. mp4 样本中还可以有其他(附加的)NAL 单元,例如 SEI 或访问单元定界符 NAL 单元。那些呢?没问题?

我尝试了各种可能性,但我从 Android 得到的所有反馈是 dequeueOutputBuffer() 的调用超时(或者不返回,如果我通过 -1 作为超时参数)。因此,我似乎没有办法解决这个问题。

当然也非常欢迎任何建议做什么或去哪里看。

最佳答案

指定 NAL 单元长度的 NAL 长度前缀在传递给 MediaCodec 进行解码之前需要转换为 Annex-B 起始码(字节 0x00、0x00、0x00、0x01)。 (有些解码器实际上可能会直接接受 MP4 格式,但这并不常见。)

存储在文件中avcC原子中的SPS/PPS也需要转换为使用Annex-B startcodes。请注意,avcC 原子包含一些您不需要传递给解码器的其他字段。您可以在发送任何实际帧之前通过设置 BUFFER_FLAG_CODEC_CONFIG 标志来传递打包在一个缓冲区中的 SPS 和 PPS(在每个缓冲区之前都有启动代码),或者在您用于配置解码器的 MediaFormat 中传递它们(使用 Annex-B 启动代码) (在一个带有键“csd-0”的 ByteBuffer 中,或者在两个单独的键“csd-0”和“csd-1”中)。

如果你的文件在每个帧中有更多的 SPS/PPS,你应该能够将它们作为帧的一部分传递,并且大多数解码器应该能够处理它(特别是如果它与相同的 SPS/PPS之前而不是配置更改)。

因此:将属于一个样本的所有 NAL 单元传递到一个缓冲区中,但将所有 NAL 单元长度 header 重写为起始码。并处理流本身内部没有 SPS/PPS 的 MP4 文件,解析 avcC 原子(我不知道 mp4parser 以哪种格式返回它)并将带有起始码的 SPS 和 PPS 传递给解码器(通过 MediaFormat 作为“csd-0”或作为第一个缓冲区,设置 BUFFER_FLAG_CODEC_CONFIG)。

关于android - 使用不带 MediaExtractor 的 MediaCodec 解码 mp4/h.264,预期访问单元格式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25160710/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com