【发布时间】:2020-04-15 13:27:49
【问题描述】:
我正在实施一项技术,该技术使用 ARCore(当前为 1.16.0)以及 OpenGL ES 3.2 计算着色器中的自定义图像处理。
有两种方法可以从计算着色器访问视频帧,但都有缺点:
-
使用
Session.setCameraTextureName()。 这似乎是一个自然的选择,因为我让 ARCore 为我将数据放入 OpenGL 纹理中。但是它在 RGBA 中,这可能意味着在我获取数据之前发生了不需要的有损转换。此外,由于它是 GL_TEXTURE_EXTERNAL_OES 纹理,我无法直接访问像素(使用imageLoad()),必须通过采样器。此外,在我测试过的设备上,每个 CameraConfig 的纹理分辨率都是 1080,这对于我的计算算法来说太大了,需要缩减。 -
使用
Frame.acquireCameraImage()。 这里的优点是我在 YCbCr 中获得图像,大概跳过了有损转换步骤,并且我可以选择合适的分辨率。缺点是我需要拨打两个glTexSubImage2D()电话。
(有趣的是,在三星 S8 和 A3 上,所有配置的纹理分辨率为 1920x1080,图像分辨率为 640x480、1280x720 和 1920x1080。)
ARCore + 计算似乎有点灰色地带。欢迎任何关于哪个是更好选择的建议,但请引用来源。 :)
编辑:根据反馈添加一些具体问题:
- 从主存中的 YCbCr 图像到 RGBA OpenGL ES 纹理一般在后台使用什么路径?
- 这条路径比
glTexSubImage2D()快吗? - 无论我是否设置会话的纹理名称,我都要为此支付计算成本吗?
- 主内存 YCbCr 图像是否总是在转换链中出现在 RGBA 纹理之前?
【问题讨论】:
-
没有“正确答案”。正如您自己所说,这两种方法都有缺点。目前尚不清楚您对“更好”的定义是什么——色彩准确度、性能、内存带宽、开发时间?
-
只有真正的答案 - 两者都尝试,并为您的用例衡量“更好”。
-
@solidpixel,好点,我需要澄清我所说的“更好”是什么意思。但是我不同意测量是找出答案的唯一真正选择。以近乎最优的方式实现这两条路径并在我所针对的数千台 Android 设备中的一个重要子集上进行测量是一项艰巨的任务。从一些关于如何设计视频捕获系统的基本事实开始是很有意义的,例如。 ARCore 的视频纹理是否通常通过比 glTexSubImage2D 更快的路径上传,以及主存 YCbCr 图像是否总是在转换链中的 RGBA 纹理之前。
标签: android opengl-es gpgpu arcore