Question about the glow buffer in Glow Filter sample

Hey!

I’ve been studying the Glow Filter sample and I think I got the hang of the stuff going on in there, save for one thing. How does the glowbuffer get its information? I can’t see any code that renders to it, nor any code that connects it to the main scene. Obviously the Tron actor is rendered to it, but where is it setup?

BR // Astrogee

I think that it’s rendered into an additional render target (of the main framebuffer) using the shader generator, as setShaderAuto() must be enabled on the main scene and the ABOGlow AuxBitplaneAttrib must be applied.

Hm, I still don’t see how it works. This is all the code I can find concerning the Actor.

self.tron=Actor()
self.tron.loadModel("models/tron")
self.tron.loadAnims({"running":"models/tron_anim"})
self.tron.reparentTo(render)
self.interval = self.tron.hprInterval(60,Point3(360,0,0))
self.interval.loop()

setShaderAuto() is not called anywhere in the code. I’m looking in Tut-Glow-Advanced.py in 1.7.0.

I think the loader does that. In the egg file you’d have:
alpha-file { “colour_and_glow.png” }
format { rgba }
envtype { modulate_glow }
or something like that. The glow map is added to the models emission… and then magic happens.

Magic! :smiley: Don’t we love it.

Seriously though, I think the following section cleared it out for me

panda3d.org/manual/index.php … ics_Engine

So I’m guessing the glowBuffer is sharing the context with base.render. Everything that is rendered to base.render is also rendered to the glowBuffer, and then the glow shader clears out the stuff that should not glow. Correct?

No, I think you misunderstand. Sharing “context” has nothing to do with sharing the actual rendered content. Sharing context just means both buffers have access to the same set of textures, vertices, and so on.

The magic happens through the actions of a shader. In the case of the “advanced” glow filter demo, explicit custom shaders are loaded and applied. In the “basic” glow filter demo, the CommonFilters object is invoked, and this object is responsible for applying the appropriate shader.

David

Ok, thank you David for clearing that out. I don’t feel any wiser though as I still don’t know how this ‘magic’ is controlled. I’m looking in the shader code, but from my understanding the shader only operates on the buffer it is connected to, in this case the glow buffer.

So, how do I know the glow buffer is processing the intended data? Maybe I don’t want the glow buffer to operate on the Tron texture but instead on some programmatically generated polygons. What then?

I’m sorry if I come across as a overly persistent SOB, but it is really frustrating for me when I don’t understand how to control ‘magic’ 8)

There’s not a separate glow buffer. It’s a post-process that’s run over the main buffer. The alpha component of the main buffer is what controls the glow, as you can see in the comment in Tut-Glow-Basic.py:

        # Use class 'CommonFilters' to enable a bloom filter.
        # The brightness of a pixel is measured using a weighted average
        # of R,G,B,A.  We put all the weight on Alpha, meaning that for
        # us, the framebuffer's alpha channel alpha controls bloom.

Thus, the Tron guy needs to have alpha = 1 painted into the parts of the texture where he’s supposed to be glowing, and alpha = 0 where he’s not supposed to be glowing. This could have been painted into a single four-channel texture image, but in this case it’s actually loaded from a separate image and combined into a single texture by the egg loader according to the following lines in tron.egg:

<Texture> Tex1 {
  "tron-color.png"
  <Scalar> alpha-file { "tron-glow.png" }
  <Scalar> format { rgba }
  <Scalar> alpha { off }

The “alpha { off }” bit tells the egg loader not to use the alpha for transparency, which is important because otherwise the non-glowing parts of the Tron guy would be transparent.

David

In Tut-Glow-Advanced.py, there is a separate glow buffer, and it has its own camera, but it draws the same scene as seen by the main camera (because the glow camera is also parented to render). So the scene gets drawn twice in this approach, once for the main camera, and again for the glow camera.

David

Thanks, this is what I was looking for. :smiley: Just one last issue if you’ll bear with me. This is the code that creates the camera in Tut-Glow-Advanced.py.

glowCamera=base.makeCamera(glowBuffer, lens=base.cam.node().getLens())
tempnode = NodePath(PandaNode("temp node"))
tempnode.setShader(glowShader)
glowCamera.node().setInitialState(tempnode.getState())

I don’t see how this camera is parented to render. Is it because we’re using the lens from the base camera? Or because we never reparent the glow camera to something other than render?

base.makeCamera() automatically reparents the camera it creates to base.camera, which is itself parented to render.

You could also create a Camera() object directly and parent it to render yourself.

David

Ok, I was not aware of that. Thanks David! :slight_smile: