Skip to main content
gamedev.net
🔒 Locked

pbuffer binding

Started by Coluna Nov 17, 2004 at 10:26 AM 7 replies 1.3k views
Original Post
Coluna
Coluna
Hello; Im using 2 pbuffers in my app: one for reflecting and one for refracting (an water demo), and a GLSL program to do the shading...in my ATI 9600, it works fine (although the time consumed by enabling/ disabling them is about 20 milliseconds!), but when i run it in a fx 5200, one of the pbuffers ( the previous one witch was binded) didnt work...im first binding the reflect-buffer, and then the refract-buffer,so the reflect-buffer is not showed, its like if a bleck texture was used...but if i comment out the refract-buffer binding, the reflect-buffer is showed correctly ...what can i do? i tried calling share lists for them , changing the creation order, but nothing happened...and why is the switching spending so much time?
mrrolf810p
mrrolf810p
I had a similar problem, I was using a 5800U though. I kept fiddling with how I rendered things, and I finally got it to work. I didn't have to change out I initialized the pbuffers, but maybe I got lucky on the first try.

Here is a snippet of the working version:

wglReleaseTexImageARB(My_GL::pbuffer.hpbuffer, WGL_FRONT_LEFT_ARB);wglReleaseTexImageARB(My_GL::pbuffer.hpbuffer, WGL_BACK_LEFT_ARB);My_GL::SwitchToPbufferContext();glDrawBuffer(GL_BACK);glReadBuffer(GL_FRONT);My_GL::start_Frame();My_GL::set_ortho(0,0,w,h);RenderSpace();	    glDrawBuffer(GL_FRONT);glReadBuffer(GL_BACK);My_GL::start_Frame();My_GL::set_ortho(0,0,w,h);CExplosion_Cache::RenderShockWaveDisplacement();	    My_GL::SwitchToNormalContext();glEnable(GL_TEXTURE_2D);glBindTexture(GL_TEXTURE_2D, My_GL::pbuffer.texID[0]);wglBindTexImageARB(My_GL::pbuffer.hpbuffer, WGL_BACK_LEFT_ARB);glEnable(GL_TEXTURE_2D);glBindTexture(GL_TEXTURE_2D, My_GL::pbuffer.texID[1]);wglBindTexImageARB(My_GL::pbuffer.hpbuffer, WGL_FRONT_LEFT_ARB);...Then I go on to use My_GL::pbuffer.texID[0] and My_GL::pbuffer.texID[1] as input textures to a fragment program.
_the_phantom_
_the_phantom_
Quote:
Original post by Coluna
and why is the switching spending so much time?


Switching takes a long time because you are switching from one context to another, which is a slow operation and has to perform a glFlush() to ensure that all operations are finished on that context before it can move to the next one, which introduces delays, overheads and all maner of issues.

There is a new extension being worked on to improve this and give proper render to texture support to OpenGL, however atm there is only what appears to be prototype functions in the NV drivers and ATI have 'something' relating to it by the looks of things (and also related to the Uberbuffers extension).

Hopefully within a couple of months something will come along and we can wave goodbye to pbuffers and their annoying limitations....
Coluna
Coluna
Thanx mrrolf810p, im trying to correct it now...and _the_phantom_ , one strange thing i've noticed is that when i run in debug (visual c++ 6.0, usnig F5), the time drops to 2-3 milliseconds, and whrn i run without debugging (ctrl+F5), it raises to 20milliseconds again...and in fx 5200, the time is about 1-2 milliseconds..may it be an ATI lazy implementation?
_the_phantom_
_the_phantom_
Ah, but when you run in debug mode there could be more instructions being executed on the CPU between the final draw call and the change in context, these extra instructions would ofcourse cause the apprent time to be less as the gpu wont have to complete as many instructions before the switch, thus it appears faster.

As for the ATI issue, it could be a hardware or driver issue, however hopefully with the removeal of having to use a pbuffer in the future this shouldnt be an issue.
silvermace
silvermace
^^^^^ That was me

here is how i use the class:
// COPYRIGHT (C) 2004 DANUSHKA ABEYSURIYA// RE-USE OF THIS CODE IS PERMITTED AS LONG AS THIS HEADER// IS KEPT WITH THIS CODE AND DERIVATIVES, ALSO THE AUTHOR// SHOULD BE CREDITED SOMEWHERE.#include <windows.h>#include <gl\glu.h>#include "pbuffer.h"#include "vector.h"#include "texture.h"#include "shader.h"#include ".\MD3\md3model.h"#include <string>using namespace std;CVector3 cam[3] = { CVector3(0,  25, -10),                     CVector3(0,  23,  0),                    CVector3(0,  1,  0) };/*CVector3 cam[3] = { CVector3(0,  10, -20),                     CVector3(0,  5,  0),                    CVector3(0,  1,  0) };*/int windowHeight = 512;int windowWidth  = 512;const int PBUFFER_WIDTH = 512;const int PBUFFER_HEIGHT = 512;/*** OUTPUT AFFECTING VARIABLES ***/int extraBlurPasses = 4;float supress_scaleFactor = 1;bool pulse = false;/**********************************/PBuffer *buf;PBuffer *blurPass1;PBuffer *blurPass2;PBuffer *sceneTex;float theta = 0;CTexture decal;CTexture envMap;ShaderContext context;Shader suppress;Shader blur;Shader tonemap;CModelMD3 *model;void RenderScreenQuad() {	glColor3f(1,1,1);	glBegin( GL_QUADS );		glTexCoord2f( 0, 0 );		glVertex3f( 0, 0, 0.9f );		glTexCoord2f( 1, 0 );		glVertex3f( (float)windowWidth, 0, 0.9f );		glTexCoord2f( 1, 1 );		glVertex3f( (float)windowWidth, (float)windowHeight, 0.9f );		glTexCoord2f( 0, 1 );		glVertex3f( 0, (float)windowHeight, 0.9f );	glEnd();}void PerspectiveMatrix( float fov, int w, int h ) {	glEnable( GL_DEPTH_TEST );	glDepthFunc( GL_LEQUAL );		glMatrixMode( GL_PROJECTION );		gluPerspective( fov, (float)w/(float)h, 0.1f, 200.0f );	glMatrixMode( GL_MODELVIEW );		glViewport( 0, 0, w, h );	}void OrthogonalMatrix( int w, int h ) {	glMatrixMode( GL_PROJECTION );		glLoadIdentity();			glOrtho( 0, w, 0, h, -1, 1);	glMatrixMode( GL_MODELVIEW );	glViewport( 0, 0, w, h );}void Initialize(){	// Initialize GL extensions	SetupGL1_4();	SetupWGLExtensions();	SetupARBExtensions();	SetupEXTExtensions();	SetupATIExtensions();	buf		  = new PBuffer( PBUFFER_WIDTH, PBUFFER_HEIGHT, 32, false, false, true, false, true, true);	blurPass1 = new PBuffer( windowWidth, windowHeight, 32, false, false, true, false, true, true);	blurPass2 = new PBuffer( windowWidth, windowHeight, 32, false, false, true, false, true, true);	sceneTex  = new PBuffer( windowWidth, windowHeight, 32, false, false, true, false, true, true);	if( !buf || !buf->IsValid() || 		!blurPass1 || !blurPass1->IsValid() ||		!blurPass2 || !blurPass2->IsValid() ||		!sceneTex || !sceneTex->IsValid() ) 	{		MessageBox( NULL, "Error Creating Render Targets.", "Error", MB_ICONERROR|MB_OK );		if( buf ) delete buf;		if( blurPass1 ) delete blurPass1;		if( blurPass2 )	delete blurPass1;		if( sceneTex ) delete sceneTex;		blurPass1 = blurPass2 = buf = sceneTex = NULL;	} 	else {		//setup the projection matricies		sceneTex->Bind();			PerspectiveMatrix(90, windowWidth, windowHeight );		sceneTex->Unbind();				buf->Bind();			PerspectiveMatrix(90, PBUFFER_WIDTH, PBUFFER_HEIGHT );		buf->Unbind();		blurPass1->Bind();			OrthogonalMatrix( windowWidth, windowHeight );		blurPass1->Unbind();		blurPass2->Bind();			OrthogonalMatrix( windowWidth, windowHeight );		blurPass2->Unbind();	}	// Create the shader context etc.	if( !context.init() )		return;	// VP LOADING	blur.createShader( context, "data/blur_vp.txt", "data/blur_fp.txt" );	blur.bindVariable( "blurX", Shader::FRAGMENT_SHADER );	blur.bindVariable( "blurY", Shader::FRAGMENT_SHADER );	suppress.createShader( context, "data/default_vp.txt", "data/suppress_fp.txt" );	suppress.bindVariable( "scaleFactor", Shader::FRAGMENT_SHADER );	tonemap.createShader ( context, "data/default_vp.txt", "data/tonemap_fp.txt" );	// Load the Test Model	model = new CModelMD3( "data/model/model.md3", "" );	decal.LoadTGA( "data/model/decal.tga" );	envMap.LoadTGA( "data/model/env.tga" );}void RenderScene( Shader *shader ){	// render the quad    glMatrixMode( GL_MODELVIEW );    glClear (GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);    glLoadIdentity();    gluLookAt( cam[0].x, cam[0].y, cam[0].z,               cam[1].x, cam[1].y, cam[1].z,               cam[2].x, cam[2].y, cam[2].z );		glEnable( GL_BLEND );		glBlendFunc( GL_ONE, GL_ONE_MINUS_SRC_ALPHA );				glPushMatrix();			glRotatef( -90, 1.0f, 0.0f, 0.0f);			glRotatef( theta, 0.0f, 0.0f, 1.0f);			float s = 0.33f;			glScalef( s,s,s );						glEnable( GL_TEXTURE_2D );			decal.Bind();			if( shader )				shader->bindShader( context, Shader::FRAGMENT_SHADER | Shader::VERTEX_SHADER );						model->Render( 0.0f );		glPopMatrix();		glDisable( GL_BLEND );}// render to the pbuffervoid RenderLDRSuppress() {		buf->Bind();		// render the HDR composistion		glClearColor (0.0f, 0.0f, 0.0f, 1.0f);		suppress.setParam1f( "scaleFactor", supress_scaleFactor );		RenderScene( &suppress );		context.unbind();	buf->Unbind();}void BlurPass(PBuffer *renderTarget, PBuffer *previous, float bx, float by){	renderTarget->Bind();	glMatrixMode( GL_MODELVIEW );	glLoadIdentity();		glPushMatrix();					//glEnable( GL_BLEND );			//glBlendFunc( GL_ONE, GL_ONE );			glActiveTexture( GL_TEXTURE0_ARB );			glEnable( GL_TEXTURE_2D );			previous->BindAsTexture();			blur.bindShader( context, Shader::FRAGMENT_SHADER | Shader::VERTEX_SHADER );						// blur in the X direction			blur.setParam1f( "blurX", bx );			blur.setParam1f( "blurY", by );			// Render the Screen quad			RenderScreenQuad();			// Unbind CG			context.unbind();			// Free PBuffer for rendering			previous->UnBindAsTexture();		glPopMatrix();	renderTarget->Unbind();}void BlendScene( PBuffer *scene, PBuffer *blur ){	glMatrixMode( GL_PROJECTION );		glPushMatrix();		glLoadIdentity();			glOrtho( 0, windowWidth, 0, windowHeight, -1, 1);	glMatrixMode( GL_MODELVIEW );	glLoadIdentity();	glPushMatrix();		glActiveTexture( GL_TEXTURE0_ARB );		glEnable( GL_TEXTURE_2D );		scene->BindAsTexture();		glActiveTexture( GL_TEXTURE1_ARB );		glEnable( GL_TEXTURE_2D );		blur->BindAsTexture();		tonemap.bindShader( context, Shader::FRAGMENT_SHADER | Shader::VERTEX_SHADER );		// Render the Screen quad		RenderScreenQuad();		// Unbind CG		context.unbind();		// Free PBuffer for rendering		glActiveTexture( GL_TEXTURE1_ARB );		blur->UnBindAsTexture();		glDisable( GL_TEXTURE_2D );		glActiveTexture( GL_TEXTURE0_ARB );		scene->UnBindAsTexture();	glPopMatrix();	glMatrixMode( GL_PROJECTION );		glPopMatrix();	glMatrixMode( GL_MODELVIEW );}// do the renderingvoid Render(){    theta += 0.33f;    	float max = 2.75f;	static float step = 0.1f;	static float limit = max;	if( pulse ) {		if( supress_scaleFactor < 1.0f || supress_scaleFactor > max )			step = step * -1;		supress_scaleFactor += step;	}	else {		if( supress_scaleFactor < max / 2.0f )			supress_scaleFactor += step/3.0f;	}	// render something	RenderLDRSuppress();	sceneTex->Bind();		glClearColor (0.0f, 0.0f, 0.0f, 0.0f);		RenderScene( NULL );	sceneTex->Unbind();	// do some pixel magicy stuff (blur)	float offs = 1.0f / (float)PBUFFER_WIDTH;	// 3x 2-stage blur pass	BlurPass(blurPass1, buf,	   offs, 0 );	BlurPass(blurPass2, blurPass1, 0, offs );	for(int i=0; i < extraBlurPasses; i++) {		BlurPass(blurPass1, blurPass2, offs, 0 );		BlurPass(blurPass2, blurPass1, 0, offs );	}	// do some more pixel magic-ery	BlendScene( sceneTex, blurPass2 );}    
Coluna
Coluna
Thanks all replies...and sorry for my delay...the problem i told only happenned in fx 5x00 cards, but its gone...now the problem is the time spent by the contest switching...the_phantom, i know in debug mode may has more instructions before the flush (or anywhere...), but the FPS goes from 60 (in debug) to 35...this in my 9600 card...does anybody has some little demo using pbuffers, for me to test if its my app or my card the problem? thanks all!
Coluna
Coluna
Here is a link to my app...
http://s15.yousendit.com/d.aspx?id=D289DA9082EF1146640EC10543E42114

i've tested it only in my ati 9600, and it may work where GLSL is present ...please tell me how much time is the CONTEXT SWITCHING consuming ...u can walk with arrow keys and shift is a boost...there is reflection/refraction in the scene, thats why im using 2 pbuffers...see ya!

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.