z-fighting (again?)

  1. I’ve read archive about z-fighting
  2. I can’t use 32 depth buffer (or is it possible in Voodoo3? how?)
  3. I want 7000 view distance
  4. With gluPerspective(angle,aspect,1,7000) I see z-fighting on my trees (two crossed QUADS)
  5. With gluPerspective(angle,aspect,10,7000) z-fighting is almost invisible, however I am loosing visibility <10
  6. I’ve tried glDepthFunc: GL_LESS and GL_LEQUAL
  7. I don’t understand what glDepthRange is exactly doing, isn’t called by gluPerspective?

What should I do? I am writting flight simulator and I need to know what is close (less than 10m) to me. Should I translate scene by (0,0,10) ?

If you MUST see objects far away, and you MUST see objects near the view point, then you have just got yourself some problems.

Without going into some wierd tricks, you will have to alter the near and/or far clip plane values. You have two options here. You can push the near clip plane away from the view point, of you can pull the far clip plane towards the view point. Since pushing the near clip plane out slightly helps FAR more than pulling the far clip plane, I suggest you push the near clip plane out. Just to give you an idea of how much more it helps. When you reduces the Z-fighting by pushing the near clip plane out from 1 to 10, you would have had to pull the far plane in from 7000 to 700 to get the same effect.

If you’re writing a flight simulator, it seems very unlikely to me that any terrain will be within the nearest 10 meters. Therefore you push the near plane out as far as you can while rendering the terrain/environment. When drawin the objects that can possibly be within 10 meter, you set the near plane to something very close and also changes the far clip plane to something closer, and then render these objects.

Most 16 bit Z buffer engines that need far view distances draws the scene twice:

  • draw sky box (clears color buffer)
  • clear Z buffer; set znear/far to 100/7000
  • draw all entities in the scene that intersect
    the frustum from 100m to 7000m from the camera
  • clear Z buffer, set znear/far to 1/200
  • draw all entities in the scene that intersect
    the frustum from 1m to 100m from the camera

Note the zfar of 200 in the second pass; this is to that you don’t get ugly clipping in the middle of objects at the 100m line.

Note that anything that intersects the strip at 100 meters will then be drawn twice. That’s OK; it’s the price you pay for getting less Z fighting on 16 bit Z buffers.

You can also, alternately, instead of clearing the Z buffer the second time, use glDepthRange( 0.5, 1 ) for the first time, and just do DepthRange( 0, 0.5 ) for the second time (no second Z buffer clear). This means you’ll get 15 bits precision far, and 15 bits precision near, but that might be OK with 100/7000 and 1/200.