pixel buffer problem

Started by
4 comments, last by Morpheus011 18 years ago
Hi, I have used codesampler's example of pixel buffers to make my own program to render to a texture but I have a problem. What my program does at the moment is select the pBuffer RC, draw a piece of geometry to it, select the windows RC, bind the pBuffer as a texture then texture a quad with the pBuffer. What appears on the screen is a blank background (my windows RC clear colour), and a black square (the quad with the pBuffer texture). The clear colour of the pBuffer is white. What I was expecting was my geometry in the quad. I have called wglShareLists() with the 1st argument as the windows RC and the second as the pBuffer RC. Am I doing something wrong (well, I obviuously am)? Can anyone help me please? Thanks in advance!
Advertisement
Your logic sounds correct, but you'll have to post some code in order for me to help you debug it. You said you've used the CodeSampler's example, though, so you must have set something up wrong somewhere.
Well this is my initialisation code.
void initPixBuffer(int width){	// Texture to render to	glGenTextures(1, &renderTex);	glBindTexture(GL_TEXTURE_2D, renderTex);	glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, width, width, 0, GL_RGB, GL_FLOAT, 0);	glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_LINEAR);	glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_LINEAR);	// Check for extensions	if (WGLEW_ARB_pbuffer && WGLEW_ARB_pixel_format && WGLEW_ARB_render_texture)		printf("Ready touse pixel buffers\n");	else	{		printf("No pixel buffer support\n");		exit(1);	}	// Setup pixel buffer	pixBuff.hPBuffer = NULL;	pixBuff.nWidth = width;	pixBuff.nHeight = width;	// Set pixel format for pixel buffer	int pf_attr[] =	{		WGL_SUPPORT_OPENGL_ARB, TRUE,       // P-buffer will be used with OpenGL		WGL_DRAW_TO_PBUFFER_ARB, TRUE,      // Enable render to p-buffer		WGL_BIND_TO_TEXTURE_RGBA_ARB, TRUE, // P-buffer will be used as a texture		WGL_RED_BITS_ARB, 8,                // At least 8 bits for RED channel		WGL_GREEN_BITS_ARB, 8,              // At least 8 bits for GREEN channel		WGL_BLUE_BITS_ARB, 8,               // At least 8 bits for BLUE channel		WGL_ALPHA_BITS_ARB, 8,              // At least 8 bits for ALPHA channel		WGL_DEPTH_BITS_ARB, 16,             // At least 16 bits for depth buffer		WGL_DOUBLE_BUFFER_ARB, TRUE,       // We don't require double buffering		0                                   // Zero terminates the list	};	unsigned int count = 0;	int pixelFormat;	wglChoosePixelFormatARB( hDC,(const int*)pf_attr, NULL, 1, &pixelFormat, &count);	if( count == 0 )	{		MessageBox(NULL,"Could not find an acceptable pixel format!",			"ERROR",MB_OK|MB_ICONEXCLAMATION);		exit(-1);	}	// Set to use RGBA	int pb_attr[] =	{		WGL_TEXTURE_FORMAT_ARB, WGL_TEXTURE_RGBA_ARB, // Our p-buffer will have a texture format of RGBA		WGL_TEXTURE_TARGET_ARB, WGL_TEXTURE_2D_ARB,   // Of texture target will be GL_TEXTURE_2D		0                                             // Zero terminates the list	};	pixBuff.hPBuffer = wglCreatePbufferARB( hDC, pixelFormat, pixBuff.nWidth, pixBuff.nHeight, pb_attr );	pixBuff.hDC      = wglGetPbufferDCARB( pixBuff.hPBuffer );	pixBuff.hRC      = wglCreateContext( pixBuff.hDC );	if( !pixBuff.hPBuffer )	{		MessageBox(NULL,"Could not create the p-buffer",			"ERROR",MB_OK|MB_ICONEXCLAMATION);		exit(-1);	}	int h;	int w;	wglQueryPbufferARB( pixBuff.hPBuffer, WGL_PBUFFER_WIDTH_ARB, &h );	wglQueryPbufferARB( pixBuff.hPBuffer, WGL_PBUFFER_WIDTH_ARB, &w );	if( h != pixBuff.nHeight || w != pixBuff.nWidth )	{		MessageBox(NULL,"The width and height of the created p-buffer don't match the requirements!",			"ERROR",MB_OK|MB_ICONEXCLAMATION);		exit(-1);	}	if( !wglMakeCurrent( pixBuff.hDC, pixBuff.hRC ) ) 	{		MessageBox(NULL,"Could not make the p-buffer's context current!",			"ERROR",MB_OK|MB_ICONEXCLAMATION);		exit(-1);	}	// Success in creating a pbuffer!	glClearColor( 1.0f, 1.0f, 1.0f, 1.0f );	glEnable(GL_TEXTURE_2D);	glEnable(GL_DEPTH_TEST);	//glViewport(0, 0, width, width);	// Reset current Viewport	glMatrixMode(GL_PROJECTION);	// Select the projection matrix	glLoadIdentity();				// Reset projection matrix	// Calculate The Aspect Ratio Of The Window	gluPerspective(75.0f,pixBuff.nWidth/pixBuff.nHeight,1.0f,1000.0f);	glMatrixMode(GL_MODELVIEW);		// Select Model View matrix	glLoadIdentity();				// Reset Model View matrix	wglShareLists(hRC, pixBuff.hRC);} // end initPixBuffer()

It's a bit long but I think most of it is the same as codesampler's but I made a few tiny changes. Main change is that I use glew to get to the extensions. The render to texture is also made a lot bigger (1440x1440, for my screen resolution). Finally I have a global for the render texture width instead of a #define.

At the start of my render function I have:
int flag = 0;    wglQueryPbufferARB( pixBuff.hPBuffer, WGL_PBUFFER_LOST_ARB, &flag );    if( flag != 0 )    {        MessageBox(NULL,"The p-buffer was lost!",            "ERROR",MB_OK|MB_ICONEXCLAMATION);        exit(-1);    }	if( !wglMakeCurrent( pixBuff.hDC, pixBuff.hRC ) )	{		MessageBox(NULL,"Could not make the p-buffer's context current!",			"ERROR",MB_OK|MB_ICONEXCLAMATION);        exit(-1);	}	glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );	glMatrixMode( GL_MODELVIEW );	glLoadIdentity();		// Reset The Current Modelview Matrix


I then render an object. I then switch to my windows RC like this:
if( !wglMakeCurrent( hDC, hRC ) )	{		MessageBox(NULL,"Could not make the window's context current!",			"ERROR",MB_OK|MB_ICONEXCLAMATION);        exit(-1);    }	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);	// Clear The Screen And The Depth Buffer	// Store projection matrix	glMatrixMode(GL_PROJECTION);	glPushMatrix();	// Set ortho mode	glLoadIdentity();	// Reset projection matrix	glOrtho(0, xRes, 0, yRes, -1, 1);		// Set ortho mode	// Store and setup modelview matrix	glMatrixMode(GL_MODELVIEW);	glPushMatrix();	glLoadIdentity();		//glUseProgramObjectARB(0);	glActiveTexture(GL_TEXTURE0);	// Set active texture unit	glBindTexture( GL_TEXTURE_2D, renderTex );	//glBindTexture(GL_TEXTURE_2D, g_texID[TESTCHAR_TEX]);	if( !wglBindTexImageARB( pixBuff.hPBuffer, WGL_FRONT_LEFT_ARB ) )	{		MessageBox(NULL,"Could not bind p-buffer to render texture!",			"ERROR",MB_OK|MB_ICONEXCLAMATION);		exit(-1);	}	// TEST DRAW	glBegin(GL_TRIANGLE_STRIP);	glColor4f(1.0f, 1.0f, 1.0f, 1.0f);	glNormal3f(0, 0, 1);	glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 0,1);	glVertex3f(200, 500, 0.0f);	glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 0,0);	glVertex3f(200, 200, 0.0f);	glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 1,1);	glVertex3f(500, 500, 0.0f);	glMultiTexCoord2fARB(GL_TEXTURE0_ARB, 1,0);	glVertex3f(500, 200, 0.0f);	glEnd();    //    // Before we forget, we need to make sure that the p-buffer has been     // released from the dynamic "render-to" texture.    //    if( !wglReleaseTexImageARB( pixBuff.hPBuffer, WGL_FRONT_LEFT_ARB ) )    {        MessageBox(NULL,"Could not release p-buffer from render texture!",            "ERROR",MB_OK|MB_ICONEXCLAMATION);        exit(-1);    }
From a quick glance at the code, two things look wrong.

First, you set WGL_DOUBLE_BUFFER_ARB to TRUE even though your comment says "We don't require double buffering". If you use double buffering, you will need to call SwapBuffers to bring the back buffer to the front.

Second, does your hardware support the ARB_texture_non_power_of_two extention? If not, a size of 1440x1440 will not work -- you will need to make the texture a power of two size.
Aha! You have a good eye! I did set double buffering to TRUE. I wanted to have double buffering since my main window was double buffered. I turned it off and it worked!! Thanks a lot!! All is fine and dandy now!
just as a note, you should probably make your textures power of 2 anyways. Not doing so can cause performance issues

This topic is closed to new replies.

Advertisement