Depth sorting

Hey there,

I have many flat geometries. Lines, Quads with partially transparent textures, and such. And they are all in one plane at a certain distance from the camera.

They can be devided into three categories: A, B and C.

A geoms have to be drawn in front of B geoms.

B geoms have to be drawn in front of C geoms.

C geoms have to be drawn in front of A geoms.

See the problem?

Can I solve this with ZBufferState alone? how? any other ideas?

Andy

If you're using the ortho render queue you can use the method Spatial.setZOrder() to set the ordering.

dhdd said:

A geoms have to be drawn in front of B geoms.
B geoms have to be drawn in front of C geoms.
C geoms have to be drawn in front of A geoms.

I am a little tired now, but is this even possible?

Now that I think of it there's a way to do it with the opaque queue as well. Have 3 render passes, 1 for each type of geometry, then use polygon offset on the pass that will decrease Z in order of the pass. It's definitely possible, Haladaria, as long as you know your depth buffer stuff.

It confused me too - unless all three can never overlap.

If an A is in front of a B, then where do you put a C? It can't be both in front of the A and behind the B?

Hevee or hamster would be good to consult - they have ccolusion tests - of course only really good when the scenegraph is threaded

Momoko_Fan said:

Now that I think of it there's a way to do it with the opaque queue as well. Have 3 render passes, 1 for each type of geometry, then use polygon offset on the pass that will decrease Z in order of the pass. It's definitely possible, Haladaria, as long as you know your depth buffer stuff.

If they all can overlap, then we have the following depths:
a < b
b < c
c < a
But the last will be a contradiction because we already know from the first two that a < b < c which forces a < c!

thanks guys.

i went with the renderpasses (and their order of drawing) plus zbufferstates and a little hack … complicated but seems to work

I'd love to see some details of your solution, any maybe even a little demo class to see what it looks like - do you think either would be possible?

well i have to disappoint you because the solution is much simpler than expected:

i changed the requirement ( i know i shouldn't  ;)) that said all three classes have to be in one plane so i just set the ZBufferStates appropriately.

A, B and C quads are all in seperate RenderPasses and rendered in that order:

• B is rendered normally with standard zbufferstate
• then A is rendered with TestFunction.Always but its actually slightly further away than B (0.0001f) (A is rendered in front of B)
• C is rendered normally with standard zbufferstate and its z value is between B and A (C is rendered in front of A but behind B)

i cannot give you code examples because of the variable names everyone would know what i am working on and thats not allowed to happen in the company i work.

i hope i described it well enough for you to know what i am doing.

Can't get it to work have I misunderstood something?

```    protected void simpleInitGame() {         lightState.setEnabled(false);                 Pass aPass = new RenderPass();         Quad a = new Quad("A", 5, 5);         a.setDefaultColor(ColorRGBA.red);         aPass.add(a);         Pass bPass = new RenderPass();         Quad b = new Quad("B", 5, 5);         b.setLocalTranslation(2f, 3f, 0);         b.setDefaultColor(ColorRGBA.green);         b.setLocalRotation(new Quaternion(new float[]{0, 0, FastMath.PI/3f}));         bPass.add(b);         Pass cPass = new RenderPass();         Quad c = new Quad("C", 5, 5);         c.setLocalTranslation(-3f, 2.5f, 0);         c.setLocalRotation(new Quaternion(new float[]{0, 0, -FastMath.PI/3f}));         c.setDefaultColor(ColorRGBA.blue);         cPass.add(c);                 ZBufferState standardZBuf = display.getRenderer().createZBufferState();         standardZBuf.setEnabled(true);         ZBufferState specialZBuf = display.getRenderer().createZBufferState();         specialZBuf.setEnabled(true);         specialZBuf.setFunction(ZBufferState.TestFunction.Always); //- B is rendered normally with standard zbufferstate         pManager.add(bPass);         b.setRenderState(standardZBuf); //- then A is rendered with TestFunction.Always but its actually slightly further away than B (0.0001f) (A is rendered in front of B)         pManager.add(aPass);         a.setRenderState(specialZBuf);         a.getLocalTranslation().add(0, 0, 0.0001f); //- C is rendered normally with standard zbufferstate and its z value is between B and A (C is rendered in front of A but behind B)         pManager.add(cPass);         c.setRenderState(standardZBuf);         c.getLocalTranslation().add(0, 0, 0.00005f);     }```

i cant try it myself right now but let this have a go:

``` //- B is rendered normally with standard zbufferstate         pManager.add(bPass);         b.setRenderState(standardZBuf); //- then A is rendered with TestFunction.Always but its actually slightly further away than B (0.0001f) (A is rendered in front of B)         pManager.add(aPass);         a.setRenderState(specialZBuf);         a.getLocalTranslation().add(0, 0, -0.0006f); //- C is rendered normally with standard zbufferstate and its z value is between B and A (C is rendered in front of A but behind B)         pManager.add(cPass);         c.setRenderState(standardZBuf);         c.getLocalTranslation().add(0, 0, -0.0003f); ```

of course it also matters from which side (z-wise) you look at it. i'll try to make that test work tomorrow myself  ;)