[英]Uploading texture to GPU by PBO not working (OpenGL version 4.1)
I have read the famous tutorial OpenGL Pixel Buffer Object (PBO) . 我已经阅读了著名的OpenGL像素缓冲区对象(PBO)教程。 I tested the sample code on my computer and it works (although with PBO on, its performance didn't improve but at least it's rendering correctly).
我在计算机上测试了示例代码,并且该代码可以正常工作(尽管启用了PBO,其性能并没有提高,但至少可以正确呈现)。
The problem is in the sample code the OpenGL context version is quite old ( Version: 2.1 INTEL-10.22.29
), and the OpenGL context version for my project is version: 4.1 INTEL-10.22.29
which doesn't support extension GL_ARB_pixel_buffer_object
any more. 问题在于示例代码中的OpenGL上下文版本很旧(
Version: 2.1 INTEL-10.22.29
),而我项目的OpenGL上下文版本是version: 4.1 INTEL-10.22.29
,它不支持扩展名GL_ARB_pixel_buffer_object
any更多。
I have read this Map and fill texture using PBO (OpenGL 3.3) , so I change my code to: 我已经阅读了此Map并使用PBO(OpenGL 3.3)填充纹理 ,因此我将代码更改为:
// generating buffers and textures
glGenVertexArrays(1, &_vertex_array);
glBindVertexArray(_vertex_array);
glGenBuffers(1, &_vertex_buffer);
glBindBuffer(GL_ARRAY_BUFFER, _vertex_buffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(vertexs_data), vertexs_data, GL_STATIC_DRAW);
glEnableVertexAttribArray(0);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 0, (void*)0);
glGenBuffers(1, &_uv_buffer);
glBindBuffer(GL_ARRAY_BUFFER, _uv_buffer);
glBufferData(GL_ARRAY_BUFFER, sizeof(uvs_data), uvs_data, GL_STATIC_DRAW);
glEnableVertexAttribArray(1);
glVertexAttribPointer(1, 2, GL_FLOAT, GL_FALSE, 0, (void*)0);
glGenBuffers(1, &_pixel_buffer);
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, _pixel_buffer);
glBufferData(GL_PIXEL_UNPACK_BUFFER, DATA_SIZE, 0, GL_STREAM_DRAW);
glGenTextures(1, &_texture);
glBindTexture(GL_TEXTURE_2D, _texture);
and render loop: 并渲染循环:
glBindTexture(GL_TEXTURE_2D, _texture);
// ======== start process PBO =========
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, _pixel_buffer);
glBufferData(GL_PIXEL_UNPACK_BUFFER, DATA_SIZE, 0, GL_STREAM_DRAW);
GLubyte *ptr = (GLubyte*) glMapBuffer(GL_PIXEL_UNPACK_BUFFER, GL_READ_WRITE);
if( ptr != nullptr )
{
cout<<"map pixel buffer success"<<endl;
memcpy(ptr, DATA_SIZE, data );
glUnmapBuffer(GL_PIXEL_UNPACK_BUFFER);
}
// ========= end process PBO ==========
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB,
_window_width, _window_height,
0, GL_RGB,
GL_UNSIGNED_BYTE, data
);
glGenerateMipmap(GL_TEXTURE_2D);
glBindBuffer(GL_PIXEL_UNPACK_BUFFER, 0);
// draw commands goes here
My code is simply rendering a single color texture, if I comment the block from ======== start process PBO =========
to ========= end process PBO ==========
then everything goes well, but with this block, it just failed and all I get is a black screen. 如果我从
======== start process PBO =========
注释该块,则我的代码只是呈现单一的颜色纹理======== start process PBO =========
到========= end process PBO ==========
然后一切都会顺利进行,但是有了这个方块,它只是失败了,我得到的只是一个黑屏。 I already checked that the glMapBuffer
works correctly and I successfully write the texture data to memory pointed by ptr
( checking by print out its value ), but I can't figure out why I didn't get my expected result. 我已经检查了
glMapBuffer
是否可以正常工作,并且成功将纹理数据写入了ptr
指向的内存中(通过打印出其值进行检查),但是我不知道为什么我没有得到预期的结果。
Thanks in advance. 提前致谢。
My Environment: 我的环境:
OS: macOS sierra 10.12.3 (16D32)
Graphics: Intel Iris Graphics 6100 1536 MB
This answer has been accepted, but it requires modifications. 该答案已被接受,但需要进行修改。 Here they are:
他们来了:
First my eye pointed out a cast from (void*)
. 首先,我的眼睛指出了
(void*)
的演员表。 No, this can't be, memcpy() will cast it again. 不,这不可能,memcpy()将再次对其进行转换。
Then I arrived to glTextImage2D
. 然后我到达了
glTextImage2D
。 And erroneously thought it can not be used with PBO (dam, I make too mistakes due to rush. I must relax...). 并错误地认为它不能与PBO一起使用(大坝,由于匆忙我犯了太多错误。我必须放松一下...)。 Thanks Nico Bolas corrected me.
谢谢尼科·波拉斯纠正了我。
Then, slowly reading again, it was just a matter of not using a pointer to client data in glTextImage2D, change data
to 0
然后,再次慢慢读取,这只是不使用glTextImage2D中的指向客户端数据的指针,而是将
data
更改为0
Docs say clearly about this last parameter: 文档清楚地说明了最后一个参数:
If a non-zero named buffer object is bound to the GL_PIXEL_UNPACK_BUFFER target (see glBindBuffer) while a texture image is specified, data is treated as a byte offset into the buffer object's data store.
如果在指定纹理图像时将非零命名的缓冲区对象绑定到GL_PIXEL_UNPACK_BUFFER目标(请参阅glBindBuffer),则将数据视为缓冲区对象的数据存储区中的字节偏移。
GLubyte *ptr = (GLubyte*) glMapBuffer(GL_PIXEL_UNPACK_BUFFER, GL_READ_WRITE);
You are degenerating the returned pointer. 您正在退化返回的指针。 Let it be
(void*)
if you only use it in a memcpy() command: 如果仅在memcpy()命令中使用它,则将其设为
(void*)
:
void* ptr = glMapBuffer(GL_PIXEL_UNPACK_BUFFER, GL_READ_WRITE);
EDIT: (after I read again that you want to copy from PBO to a texture) 编辑:(在我再次阅读您要从PBO复制到纹理后)
glTextImage2D()
reads from a pointer data while glTexSubImage2D()
can be used to read from a bound PBO. glTextImage2D()
从指针数据中读取,而glTexSubImage2D()
可用于从绑定的PBO中读取。 In this last case the last parameter to glTexSubImage2D()
is an offset to that PBO (0 if no offset is needed). 在后一种情况下,
glTexSubImage2D()
的最后一个参数是该PBO的偏移量(如果不需要偏移量,则为0)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.