Occlusion Query Test

Hi .
Why not have a occlusion_query_test command in the OpenGL, a command that can jump a block of
commands in the list, if the number of samples in a occlusion query is not what we want.
This way we don´t need to use GetQueryObject and stall the pipeline.

Using the ARB_occlusion_query example as base:

GLuint queries[N];
GLuint sampleCount;

glGenQueriesARB(N, queries);

// First rendering pass
glDisable(GL_BLEND);
glDepthFunc(GL_LESS);
glDepthMask(GL_TRUE);
// configure shader 0
for(i=0; i<N; i++)
{
glBeginQueryARB( GL_SAMPLES_PASSED_ARB, queries[i] );

// render object i

glEndQueryARB(GL_SAMPLES_PASSED_ARB);
}

// Second pass only on objects that were visible
glEnable(GL_BLEND);
glBlendFunc(…);
glDepthFunc(GL_EQUAL);
glDepthMask(GL_FALSE);

// configure shader 1
for(i=0; i<N; i++)
{
// Only render if sample count > 0
glBeginQueryTestARB( GL_QUERY_RESULT_ARB, queries[i], GL_GREATER, 0 );

// render object i

glEndQueryTestARB();

}

I hope someone understand what I´m trying to say, since my English is not good.

It is possible that, as the last pixels of the occlusing querry are rendering, the first vertices of the new object (the one in the glBeginQueryTest) are in the T&L pipeline. In order to prevent this, the pipeline must stall on glBeginQueryTest.

Granted, this will allow the minimum possible stall time.

Also, what does the graphics chip do if glEndQueryTest hasn’t happened yet?

It is possible that, as the last pixels of the occlusing querry are rendering, the first vertices of the new object (the one in the glBeginQueryTest) are in the T&L pipeline. In order to prevent this, the
pipeline must stall on glBeginQueryTest.

This can happen, but I believe the stall time will be very small, and the stall only occurs on the GPU, the CPU can continue executing GLcommands or another process.

Also, what does the graphics chip do if glEndQueryTest hasn’t happened yet?

When the glBeginQueryTest happen, the driver alredy have the result of the occlusion query, and if the test is false, all gl commands after the BeginQueryTest are not executed until the driver or chip reach the EndQueryTest.

That’s brilliant. Good syntax, too.
I see one issue with that, and it’s glBegin/glEnd not matching because of the query test.

//issue type 1
BeginQueryTest(<...> );
glBegin(GL_TRIANGLES);
EndQueryTest();
glEnd();

//issue type 2
glBegin(GL_TRIANGLES);
BeginQueryTest(<...> );
glEnd();
EndQueryTest();

What happens if the query test fails?
glNewList/glEndList is similar in this respect, so the resolution should be similar, too.

That’s brilliant. Good syntax, too.

Thanks.

What happens if the query test fails?
glNewList/glEndList is similar in this respect, so the resolution should be similar, too.

Yes, something similar to glEndList could work.
The EndQueryTest throw a GL_INVALID_OPERATION, if a glEnd or glBegin are found inside the BeginQueryTest/EndQueryTest block and the Occlusion Query Test are false.

[This message has been edited by EdJr (edited 01-22-2004).]

Originally posted by Korval:
It is possible that, as the last pixels of the occlusing querry are rendering, the first vertices of the new object (the one in the glBeginQueryTest) are in the T&L pipeline. In order to prevent this, the pipeline must stall on glBeginQueryTest.

Or add a DONT_BLOCK mode that assumes the object has passed if the query isn’t completed in time (or, even simpler, add an int to the BeginTest call that sets the default test result–this value gets overwritten by the actual query result if/when it completes).

As for not receiving an EndTest command, I suppose you could say the same thing about “what if swapbuffers never gets called.” Certain well-documented commands, like glFinish and glSwapbuffers should probably close the test branch and set an error state.

Where it gets really complicated is when you allow nested tests… not that I’m advocating tackling that can of worms.

Aside: I was hoping for something like this when I asked about putting conditionals in the pipeline, but the syntax here is more fiexible than what I had in mind.

[This message has been edited by Cyranose (edited 01-23-2004).]

This would indeed be a good idea. If I’ve understood things correctly, PCI-express will help with these kind of issues somewhat. It uses a separate upstream and downstream bus, so the card doesn’t have to stall from reading in commands the driver has batched up when it’s sending the result of the occlusion query back.

Of course the driver might perform some work when you issue the actual call, like juggling VBOs so some work would be done needlessly anyway, but it would make it much easier to handle the latency of the query.

GL_NVX_conditional_render: http://www.opengl.org/discussion_boards/cgi_directory/ultimatebb.cgi?ubb=get_topic;f=3;t=011740