【问题标题】:copying texture from GPU to CPU using pixel buffer objects使用像素缓冲区对象将纹理从 GPU 复制到 CPU
【发布时间】:2017-04-10 07:32:15
【问题描述】:

我是 OpenGL 新手,目前正在将 2D 纹理的内容复制回 CPU 内存,如下所示:

std::vector<unsigned char> frame-data(width * height * 4);
glBindTexture(GL_TEXTURE_2D, tid);
glGetTexImage(GL_TEXTURE_2D, 0, GL_RGBA, GL_UNSIGNED_BYTE, &frame_data[0]);                 

我注意到这非常缓慢,我开始阅读有关 PBO 的信息,并想尝试看看这是否能让事情变得更顺利。所以我按如下方式创建 PBO:

GLuint  pbo;
glGenBuffers(1, &pbo);
glBindBuffer(GL_PIXEL_PACK_BUFFER, pbo);
glBufferData(GL_PIXEL_PACK_BUFFER, width*height* 4, NULL, GL_STREAM_READ); 

我认为以上几行只需执行一次即可初始化 PBO。

我现在的问题是如何将数据从纹理映射到这个 PBO 对象?我知道在那之后我需要致电glMapBuffer,但我不确定如何将此纹理附加到我的 PBO。

【问题讨论】:

    标签: opengl textures pbo


    【解决方案1】:

    当缓冲区绑定到GL_PIXEL_PACK_BUFFER 时,纹理下载函数会将其最后一个data 参数解释为客户端内存中的指针,而不是从开头的字节偏移当前绑定的像素包缓冲区。

    换句话说,假设一个已经创建的纹理和一个适当大小的缓冲区已经创建:

    // bind PBO
    glBindBuffer(GL_PIXEL_PACK_BUFFER, buffer); 
    
    // bind texture
    glBindTexture(GL_TEXTURE_2D, texture);
    
    // transfer texture into PBO
    glGetTexImage(GL_TEXTURE_2D,                 
                  level,
                  pixelformat,
                  pixeltype,
                  (GLvoid*)0 // offset in bytes into "buffer",
                             // not pointer to client memory!
                 ); 
    

    传输完成后,您可以读取缓冲区中包含的纹理数据,例如通过映射它。

    请注意,如果您立即映射缓冲区,您将不会从 PBO 中获得任何好处。这种方法的重点是让传输异步发生,同时通过提交其他命令让 GPU 保持忙碌。

    您可以通过同步调用知道传输何时完成,例如在传输调用之后插入sync objects

    【讨论】:

      猜你喜欢
      • 2012-07-29
      • 2012-01-13
      • 2014-12-05
      • 2011-09-14
      • 1970-01-01
      • 2017-09-17
      • 1970-01-01
      • 2014-07-13
      • 1970-01-01
      相关资源
      最近更新 更多