Author Topic: BloomGLProcessor - how to specify what element/object should glow  (Read 4049 times)

Offline Wojtek

  • int
  • **
  • Posts: 62
    • View Profile
Hello,

I am newbie in 3d rendering and jpct engine, so excuse me for naive questions, but I am wondering how to specify what part of object (or which objects) should glow/shine.
I have created a simple gray space ship with blue cockpit window and light-blue engine. The ship does not have any texture - I have just specified colors for it's parts in blender.

I wanted to make the ship's engine glowing, so I have added the BloomGLProcessor to FrameBuffer as a post processor. When I ran the application I have noticed that the cockpit window is also glowing (in fact, it is glowing more than the engine).

Can you please give me some hints what should I do to avoid the situations where unwanted parts of objects are glowing?

Here I added the link to my test application: http://www.megaupload.com/?d=1FO7A72O

Thanks,
Wojtek

Offline EgonOlsen

  • Administrator
  • quad
  • *****
  • Posts: 11748
    • View Profile
    • http://www.jpct.net
Re: BloomGLProcessor - how to specify what element/object should glow
« Reply #1 on: May 28, 2009, 11:48:28 pm »
You can't really specify this with the BloomProcessor because it's a post processing effect in screen space. Every information about depth or objects is gone at that stage. Basically, bright parts of the scene tend to glow more than darker ones. How much depends on the settings of the processor.
For an engine glow, a billboarded quad positioned slightly behind the exhaust port rendered with additive blending may be the better solution. Similar to the lights of this car: http://www.jpct.net/pix/high_poly_car.jpg

Offline paulscode

  • double
  • *****
  • Posts: 863
    • View Profile
    • PaulsCode.Com
Re: BloomGLProcessor - how to specify what element/object should glow
« Reply #2 on: May 29, 2009, 12:35:52 am »
I also made an example applet with a billboarded-quad glow effect on this thread, and I posted the source code there for reference.  The basic idea works like this:

For the billboard itself, make it the same diameter as the longest diagonal length of whatever object is supposed to be glowing (such as the car headlight in Egon's example).  Then, offset the two polys of the billboard to half that distance in the -z direction in object-space.  Finally, place the center of the billboard at the center-of-mass of the headlight.

Here is a diagram in case my description above doesn't make any sense:


One additional thing that I added besides the glow quad is an actual light source so the glowing thing also lights up surrounding objects.  I commented the code pretty well, but if you need help understanding anything, let me know.

I have also been playing around with other special effects for a target-shooter game I'm working on, including motion blur, gun-flashes, energy shields, smoke, and explosions.  If you have any trouble with effects like these, I'll be happy to help.

Offline Wojtek

  • int
  • **
  • Posts: 62
    • View Profile
Re: BloomGLProcessor - how to specify what element/object should glow
« Reply #3 on: May 29, 2009, 09:24:19 pm »
Thank you for reply and explanation :)

The firefly is great. The code example of firefly also helped me a lot. I will try to use that pattern for mine ship engine and will share the results :)

There is one thing in the code that I do not understand well. The visible polys create glowing effect which is ok, but what is the purpose of the invisible polys with black texture? I have played a little bit with the firefly and temporarly commented out those invisible polys - for me there was no visible difference after that...

Offline Wojtek

  • int
  • **
  • Posts: 62
    • View Profile
Re: BloomGLProcessor - how to specify what element/object should glow
« Reply #4 on: May 29, 2009, 10:11:09 pm »
And there are the screenshots:

and



Offline paulscode

  • double
  • *****
  • Posts: 863
    • View Profile
    • PaulsCode.Com
Re: BloomGLProcessor - how to specify what element/object should glow
« Reply #5 on: May 30, 2009, 12:33:32 am »
There is one thing in the code that I do not understand well. The visible polys create glowing effect which is ok, but what is the purpose of the invisible polys with black texture? I have played a little bit with the firefly and temporarly commented out those invisible polys - for me there was no visible difference after that...
This is to correct a problem caused by the fact that calling build() places the "glow ball's" pivot in the wrong place.  If you think of the "glow ball" as an imaginary cube (see my previous diagram), jpct was placing the pivot at the end on top of the two polys, rather than at the COM of the imaginary cube (regardless of the value of "zoffset").  This results in the "glow ball" being positioned slightly incorrectly, allowing the firefly to poke through at certain angles (feel free to check how this behaviour looks by commenting out the invisible polys, and orbiting the camera and rotating the firefly).  I corrected this anoying behavior by "tricking" jpct into placing the pivot in the correct place by adding two more polys on the other side of the imaginary cube:



Egon has mentioned another method using the translateMesh method.  You would first find the following code in the loadFirefly method:
Code: [Select]
        // Create the actual polys:
        // Note: I am creating 4 polys here, so there are two on each side
        // of an imaginary box.  That way the center of the glow effect will
        // stay in the center of the firefly's butt, and the glowing polys
        // will orbit around the outside of the firefly.  This prevents the
        // firefly's butt from "sticking through" the glowing polys when rotated
        // at certain angles.  This can be tweaked by changing the above
        // 'zoffset' value, which affects how far from the firefly the glowing
        // effect will orbit.
        buttShine.addTriangle( new SimpleVector( -offset, -offset, -zoffset ),
                           0, 0,
                           new SimpleVector( -offset, offset, -zoffset ), 0, 1,
                           new SimpleVector( offset, offset, -zoffset ), 1, 1,
                           TextureManager.getInstance().getTextureID(
                                                             "Firefly Glow" ) );
        buttShine.addTriangle( new SimpleVector( offset, offset, -zoffset ),
                           1, 1,
                           new SimpleVector( offset, -offset, -zoffset ), 1, 0,
                           new SimpleVector( -offset, -offset, -zoffset ), 0, 0,
                           TextureManager.getInstance().getTextureID(
                                                             "Firefly Glow" ) );
        // These two polys will always be invisible:
        buttShine.addTriangle( new SimpleVector( offset, offset, zoffset ),
                           1, 1,
                           new SimpleVector( -offset, offset, zoffset ), 0, 1,
                           new SimpleVector( -offset, -offset, zoffset ), 0, 0,
                           TextureManager.getInstance().getTextureID(
                                                            "Clear Texture" ) );
        buttShine.addTriangle( new SimpleVector( -offset, -offset, zoffset ),
                           0, 0,
                           new SimpleVector( offset, -offset, zoffset ), 1, 0,
                           new SimpleVector( offset, offset, zoffset ), 1, 1,
                           TextureManager.getInstance().getTextureID(
                                                            "Clear Texture" ) );
And change it to:
Code: [Select]
        // Create two polys for the billboarded quad:
        buttShine.addTriangle( new SimpleVector( -offset, -offset, 0 ),
                           0, 0,
                           new SimpleVector( -offset, offset, 0 ), 0, 1,
                           new SimpleVector( offset, offset, 0 ), 1, 1,
                           TextureManager.getInstance().getTextureID(
                                                             "Firefly Glow" ) );
        buttShine.addTriangle( new SimpleVector( offset, offset, 0 ),
                           1, 1,
                           new SimpleVector( offset, -offset, 0 ), 1, 0,
                           new SimpleVector( -offset, -offset, 0 ), 0, 0,
                           TextureManager.getInstance().getTextureID(
                                                             "Firefly Glow" ) );
Then somewhere after:
Code: [Select]
        buttShine.build();  // set up bounding box and normalsAdd the following:
Code: [Select]
        // Move the polys back so the billboarded quad's pivot is in the
        // center of an imaginary box.  That way the center of the glow
        // effect will stay in the center of the firefly's butt, and the glowing
        // polys will orbit around the outside of the firefly.  This prevents the
        // firefly's butt from "sticking through" the glowing polys when rotated
        // at certain angles.  This can be tweaked by changing the above
        // 'zoffset' value, which affects how far from the firefly the glowing
        // effect will orbit.
        Matrix mb = buttShine.getTranslationMatrix();
        buttShine.setTranslationMatrix( new Matrix() );
        buttShine.translate( new SimpleVector( 0, 0, -zoffset ) );
        buttShine.translateMesh();
        buttShine.setTranslationMatrix( mb );

** IMPORTANT NOTE: If you use Egon's method, you would need to comment out the call to world.buildAllObjects() (or move the translateMesh stuff to somewhere after it is called), otherwise the pivot gets changed back to where it was before!!  Personally I prefer to use the two invisible poly method, unless the extra polys could add up and become a memory concern (such as using glow effects for bullets).

Looks good, BTW.  I would suggest playing around with a larger zoffset for your billboarded quad ("D/2" in the diagram from my previous post).  That way it won't appear to be a flat plane passing "inside" the engine when viewing it from the side (like in your first screenshot), and engine polygons won't "poke through" when viewed from certain angles (like in your second screenshot).  Of course just from the screenshots I can't see how it looks when rotating in 3D - it might look fine the way it is.
« Last Edit: May 30, 2009, 01:50:14 am by paulscode »