Framebuffer setup question...

I am attempting to create 2 offscreen render surfaces that share a depth buffer in Panda. I used graphicsengine.MakeOutput to create the buffers, and used addRenderTexture to add textures to the 2 buffers, using the same texture for the depth buffer attachment of each buffer.

This does not appear to give the desired results. One of the points to this exercise is to “burn” the depth information in an early pass, then be able to use this depth to eliminate overdraw in a subsequent pass. Should save significant fill rate as the later pass is fragment shader heavy.

Currently if I disable the depth clear on the second render buffer, I get nothing drawn. Is the default depth test not less than or equal?

I am using the OpenGL renderer, and I’ve mocked up an app that does exactly this in OpenGL using GL_EXT_framebuffer_object and GL_ARB_texture_rectangle. So it’s certainly possible in the GL, and I must be missing something with the Panda API.

Anyone have any hints?? Thanks in advance.

it’s certainly possible with gl as you proved. but panda usualy is used for high-level programming which makes lots of things easyer, therefore restrict some things,too.
i’m not familliar with all the low level rendering process of panda so i can only give vague hints.
so my first guess:
read the very bottom of:
http://panda3d.org/manual/index.php/Render_to_Texture
if you are sure you are not trying something listed there… well then i guess you have to read the manual about the rendering process very carefully. i cant really help you since i’m pretty much non-programmer. just to make sure you’r not trying to do something impossible with panda :wink:
and keep in mind that panda has to fully work with both d3d/gl. so it might be that some gl features are not useable because d3d doesnt support it (or the other way round)
well for debugging i recomment debugging mode for buffers like in the manual.
from the manual
“There is a debugging mode in which makeTextureBuffer will create a visible window (class GraphicsWindow) instead of a hidden one (class GraphicsBuffer). To enable this debugging mode, set the boolean variable “show-buffers #t” in your panda configuration file.”

nevermind if my post doesnt contain anything usefull :slight_smile:
greetings
thomas e

Ah, in NodePath.cxx lines 4779-4782

DepthTestAttrib::PandaCompareFunc mode =
depth_test ?
DepthTestAttrib::M_less :
DepthTestAttrib::M_none;

This could well be the problem. With a Z test of M_less, you shouldn’t be able to multi-pass over the same geometry without a Z clear. This doesn’t make sense to me, shouldn’t this be M_less_equal? That would be more typical, as it works for every day depth comparison and allows for multi-pass over the same geometry in a given frame without a Z clear.

Any thoughts??
Thanks,

I believe the default of M_less was chosen to more easily support nested coplaner subpolygons, e.g. decalling. It is, of course, a matter of some debate whether decalling is a more common operation than multipass rendering. It would probably be better to replace this method with one that accepted an explicit DepthTest mode, rather than a simple boolean, but this method exists as it is for historical reasons.

Of course, you can always set the explicit DepthTest mode you want, with a call like this:

nodePath.setAttrib(DepthTestAttrib.make(DepthTestAttrib.MLessEqual))

David

Thanks David, does my setup sound as though it should work? I am attaching the same depth texture to 2 different output buffers. And using 2 different color textures. Should Panda react as the FBO extension does and allow me to do that? Such that the 2 outputs share a depth buffer?

Sorry I didn’t answer this sooner, I was in California.

When rendering to a texture, there are two basic ways to do it: binding the framebuffer to the texture, or copying from the framebuffer to the texture. If you want two buffers to share a depth-buffer, then you need to bind the same texture to both depth buffers. First, though, you need buffers that can bind every bitplane (ie, the depth buffer). To do that, you need to specify the BF_can_bind_every property at buffer creation time. Of course, the buffer creation may fail if the video card doesn’t support that.

I believe that this should work.

Thanks for the response Josh, This is what I’m doing, see anything wrong with it??

self.glowBuffer = base.graphicsEngine.makeOutput(
   base.pipe, "glow buffer", -3, fbProps, winProps,
   GraphicsPipe.BFCanBindEvery | GraphicsPipe.BFRefuseWindow,
   base.win.getGsg(), base.win)
self.renderBuffer = base.graphicsEngine.makeOutput(
   base.pipe, "render buffer", -1, fbProps, winProps, 
   GraphicsPipe.BFCanBindEvery | GraphicsPipe.BFRefuseWindow,
   base.win.getGsg(),base.win)

self.zBufferTexture = Texture()
self.glowBufferTexture = Texture()
self.renderBufferTexture = Texture()
self.glowBuffer.addRenderTexture(self.zBufferTexture, 
   GraphicsOutput.RTMNone, GraphicsOutput.RTPDepth)

self.glowBuffer.addRenderTexture(self.glowBufferTexture, 
   GraphicsOutput.RTMBindOrCopy, GraphicsOutput.RTPColor)
self.renderBuffer.addRenderTexture(self.zBufferTexture,  
   GraphicsOutput.RTMNone, GraphicsOutput.RTPDepth)
self.renderBuffer.addRenderTexture(self.renderBufferTexture,
   GraphicsOutput.RTMBindOrCopy, GraphicsOutput.RTPColor)

Thanks,

I think that “RTMNone” is the wrong value. It should be RTMBindOrCopy. Actually, I really should have a value RTMBind, because you don’t want copy.

I don’t know what RTMNone does.