解码器的输出表面如何传递到编码器的输入表面?

How does an output surface of a Decoder is passed to an input surface of an Encoder?

我正在尝试了解表面对表面方法如何与 MediaCodec 配合使用。在仅使用 ByteBuffer 的方法中,解码后的数据放在 OutputBuffers 中。可以手动处理此非编码数据,然后将其传递给编码器的 InputBuffers。

如果我们看一下来自 Android MediaCodec CTS 的示例,使用表面到表面的方法在解码器和编码器之间传递数据,我们将解码器配置为将解码数据输出到一个名为 outputSurface 的 Surface,我们配置 Encoder 以接收名为 inputSurface 的 Surface 上的数据。

在文档中,createInputSurface 和这个表面在编码器配置中的用法是这样描述的:

createInputSurface(): Requests a Surface to use as the input to an encoder, in place of input buffers.

换句话说,这在 ByteBuffers 声明的 CTS 示例中可见:编码器没有 InputBuffers。你有:

您没有在编码器输入缓冲区中排队数据,而是使用了以下代码行:

outputSurface.awaitNewImage();
outputSurface.drawImage();
inputSurface.setPresentationTime(videoDecoderOutputBufferInfo.presentationTimeUs * 1000);
inputSurface.swapBuffers();

Decoder的ouputSurface内容是如何传递给Encoder的inputSurface的?幕后具体发生了什么?

解码器's/encoder的output/inputSurface分别是特殊配置(要么物理连续reserved 等)专用硬件(例如,GPUs、硬件(加速)编解码器)或软件模块可以以最适合的方式使用的内存满足性能需求(通过使用硬件加速、DMA 等功能)。

更具体地说,例如,在当前上下文中,解码器的输出 Surface 由 SurfaceTexture 支持,因此它可以在 OpenGL environment 中用作 ]external 纹理在表面上渲染之前进行任何类型的处理,编码器可以从表面读取和编码以创建最终视频帧。

并非巧合,OpenGL 只能渲染到 Surface

因此解码器充当原始视频帧的提供者表面(纹理) carrier, OpenGL medium 将其渲染到编码器的 输入 Surface 是(要编码的)视频帧的 目的地

为了进一步满足您的好奇心,请查看 了解更多详情。

[编辑]

您可以查看 grafika Continuous Camera or Show + capture camera 中的子项目,该子项目当前将相机帧(馈送到 SurfaceTexture)渲染到视频(并显示)。所以本质上,唯一的变化是 MediaCodec 将帧馈送到 SurfaceTexture 而不是 Camera。

Google CTS DecodeEditEncodeTest 完全一样,可以作为参考,让学习曲线更平滑

从最基础的开始,正如 fadden 指出的那样,使用 Android graphics tutorials