I am hoping to speed up my transfers of live video to the OpenGL video card we are using. Currently I transfer with glTexSubImage2D and am thinking of using PPO’s. I have a sample, and have some questions about it:
In my sample, it constructs a “temp buffer” with this call:
glGenBuffersARB(1, &pboID);
glBindBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, pboID);
glBufferDataARB(GL_PIXEL_UNPACK_BUFFER_ARB, bytes, NULL, GL_STREAM_DRAW_ARB);
CHECK_GL();
Should this happen every frame, or only once during startup?
Also with this call:
glDeleteBuffersARB(1, &pboID);
should this happen every frame, or only once at shutdown?
You should take a look at the performance sample of PBOs at nvidias homepage. I have the same situation where i upload video in real time to textures but I have found out that its very HW dependant and VERY image format dependant. When it comes to Nvidia HW you almost get worse performance if you are using standard RGB or RGBA images. ATI hw improves in general and a lot on osx so the conclusion is that i have a performance matrix with image format, hw and operating system as a lut to see if the pbos are good or not. phew…
Thanks for the ideas guys. I have modified my code so that it is setting things up once, and then using them. It is very fast on the transfer. Unfortunately all I get is an olive green texture. Do you see anything obvious I am doing wrong?
Setup code
bytes = width * height * 3;
glGenBuffersARB(1, &m_extension_buffer_id);
glBindBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, m_extension_buffer_id);
glBufferDataARB(GL_PIXEL_UNPACK_BUFFER_ARB, bytes, NULL, GL_STREAM_DRAW_ARB);
Texture binding code:
int bytes = 0;
void * data = NULL;
if (m_extension_buffer_allocated)
{
glEnable(GL_TEXTURE_2D);
glBindTexture(GL_TEXTURE_2D, m_video_texture_index_id );
glBindBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, m_extension_buffer_id);
bytes = width * height * 3;
data = glMapBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, GL_WRITE_ONLY_ARB);
if (data != NULL)
{
memcpy(data, input_buffer, bytes);
glUnmapBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB);
glTexSubImage2D(GL_TEXTURE_2D, 0, 0, 0, width, height, GL_RGB, GL_UNSIGNED_BYTE, 0);
}
glBindBufferARB(GL_PIXEL_UNPACK_BUFFER_ARB, 0);
glBindTexture(GL_TEXTURE_2D, 0);
Cleanup code:
if (m_extension_buffer_allocated == true)
{
glDeleteBuffersARB(1, &m_extension_buffer_id);
}