android - 在 Android 上使用 glEGLImageTargetTexture2DOES 替换 glReadPixels
问题描述
给定一个textureId,我需要从纹理中提取像素数据。
glReadPixels 可以工作,但在某些设备上非常慢,即使是 FBO/PBO。(在小米 5 上为 65 毫秒,使用 PBO 甚至更慢)。所以我决定使用Hardwarebuffer
and eglImageKHR
,它应该更快。但是,我无法让它工作。屏幕变黑,没有任何内容被读入数据。
//attach inputTexture to FBO
glBindFrameBuffer(GL_FRAMEBUFFER, fbo)
glFrameBufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, textureId, 0)
//allocate hardware buffer
AHardwareBuffer* buffer = nullptr;
AHardwareBuffer_Desc desc = {};
desc.width = width;
desc.height = height;
desc.layers = 1;
desc.usage = AHARDWAREBUFFER_USAGE_CPU_READ_OFTEN | AHARDWAREBUFFER_USAGE_CPU_WRITE_NEVER
| AHARDWAREBUFFER_USAGE_GPU_COLOR_OUTPUT ;
desc.format = AHARDWAREBUFFER_FORMAT_R8G8B8A8_UNORM;
//create eglImageKHR
EGLint eglAttributes[] = {EGL_IMAGE_PRESERVED_KHR, EGL_TRUE, EGL_NONE};
EGLClientBuffer clientBuffer = eglGetNativeClientBufferANDROID(buffer);
EGLImageKHR eglImageKhr = eglCreateImageKHR(eglDisplay, eglContext,
EGL_NATIVE_BUFFER_ANDROID, clientBuffer, eglAttributes);
//read pixels to hardware buffer ????
glBindTexture(GL_TEXTURE_2D, textureId);
glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, eglImageKhr);
//copy pixels into memory
void *readPtr;
AHardwareBuffer_lock(buffer, AHARDWAREBUFFER_USAGE_CPU_READ_OFTEN, -1, nullptr, (void**)&readPtr);
memcpy(writePtr, readPtr, width * 4);
AHardwareBuffer_unlock(buffer, nullptr);
这是我的代码glReadPixels
,它可以在将纹理附加到帧缓冲区后获取像素。
GLES30.glBindFramebuffer(GLES30.GL_FRAMEBUFFER, fboBuffer!![0])
GLES30.glFramebufferTexture2D(GLES30.GL_FRAMEBUFFER,
GLES30.GL_COLOR_ATTACHMENT0,
GLES30.GL_TEXTURE_2D,
inputTextureId,
0)
GLES30.glReadPixels(0, 0, width, height, GLES30.GL_RGBA, GLES30.GL_UNSIGNED_BYTE, byteBuffer)
请告诉我哪里做错了:(
解决方案
//read pixels to hardware buffer ????
glBindTexture(GL_TEXTURE_2D, textureId);
glEGLImageTargetTexture2DOES(GL_TEXTURE_2D, eglImageKhr);
这不会读取任何数据。这只是设置纹理以引用 EGLImage。如果您希望将数据复制到其中,您需要执行glCopyTexImage2D()
或将其绑定到帧缓冲区并渲染到其中。
推荐阅读
- spring - 方法名称的 Spring AOP 执行不匹配
- python - Beautiful Soup 不能多次在 for 循环中工作
- dart - 如何在 Dart 中打印二叉树图?
- python - 如何引用嵌套的 Python 数据类?
- python - 为什么这不在我的列表中打印负值?
- plsql - PLS-00382:表达式在填充关联数组表时类型错误
- javascript - 当直接赋值适用于 Javascript 数字数据类型时,为什么加法会丢失精度?
- bash - 如何将多个参数作为变量传递给应用程序?
- node.js - Bot Framework:选择卡重试提示不起作用
- python-3.x - FileNotFoundError 但文件在那里:密码学版