Question about implementing Hierarchical Z-Buffering in DirectX

Started by
9 comments, last by grill8 16 years, 5 months ago
Hello, I recently read the article: http://www.gamasutra.com/features/19991109/moller_haines_02.htm on Hierarchical Z-Buffering and am going to implement it in my game engine. I read the article several times before fully understanding it but before I begin work on designing the code for it I already see one thing in DirectX that I simply do not know how to implement. From the article: "To maintain a Z-pyramid, whenever a z-value is overwritten in the Z-buffer it is propagated through the coarser levels of the Z-pyramid." If you haven't read the article, in a nutshell what is needed is that whenever a new z value is written to the DirectX z buffer, it's new z value needs to be noted and possible written to smaller and smaller versions of the z buffer. My problem is this ... I know how to maintain and control a DirectX z buffer but only when rendering entire meshes and allowing directX to write to the z buffer for you, but in order to properly implement the Hierarchical Z-Buffering I need to be able to (like the algorithm) says perform operations whenever a new z value PIXEL is written. I simply do not know how to do this on a per pixel level. Again, I only know how to use the z buffer when an entire mesh is rendered and DirectX handles the z buffer for you and do not know how to manipulate the z buffer on a per pixel write instance. Thank you for your help. Jeremy
Advertisement
There is no way to implement this in DX nor OpenGL and you also don't have to.

Hierarchical Z-Buffering is something the graphics cards implement themselfs in hardware and current (if not also previous) generation gfx cards already do implement this internally.

All you have to do to take advantage of it is draw the scene front to back and not modify the depth value in the pixel shader. This way Early-Z and also Hierarchical-Z optimizations will take place.
I believe alpha testing can (will?) also disable the hierarchical z optimizations.
Exactly how alpha testing and depth modification affects early-z or hi-z implementations seems to be an unknown quantity. Some people say that you should never do it, others say you can get away with it in certain situations etc...

You need to dig through the published whitepapers from AMD/Nvidia or be on their devrel programs to find out.

hth
Jack

<hr align="left" width="25%" />
Jack Hoxley <small>[</small><small> Forum FAQ | Revised FAQ | MVP Profile | Developer Journal ]</small>

AFAIK alpha testing does not interfere neither with early-z nor with hierarchical-z optimizations since alpha does not have anything to do with depth at all. This is only valid as long as you do not modify the per pixel depth value. Also using the discard keyword/instruction in a fragment shader should not interfere with this. I'm pretty sure I'm right with this.

And you should always use GL_LESS or GL_LEQUAL as the depth test function and be consistent with it. Changing it mid frame could potentially disable hirarchical-z optimizations.
Quote:Original post by Trenki
AFAIK alpha testing does not interfere neither with early-z nor with hierarchical-z optimizations since alpha does not have anything to do with depth at all. This is only valid as long as you do not modify the per pixel depth value. Also using the discard keyword/instruction in a fragment shader should not interfere with this. I'm pretty sure I'm right with this.

This ATI paper and this NVidia paper (page 30) disagree.
Sirob Yes.» - status: Work-O-Rama.
Okay, that article is from 1999.

Here's a hint: Don't rely on articles from 1999 to tell you what to implement.

Now, as far as HZB goes. All graphics cards made in the last several years have implemented HZB in hardware. You don't need to do it yourself.
SlimDX | Ventspace Blog | Twitter | Diverse teams make better games. I am currently hiring capable C++ engine developers in Baltimore, MD.
Quote:Original post by sirob
Quote:Original post by Trenki
AFAIK alpha testing does not interfere neither with early-z nor with hierarchical-z optimizations since alpha does not have anything to do with depth at all. This is only valid as long as you do not modify the per pixel depth value. Also using the discard keyword/instruction in a fragment shader should not interfere with this. I'm pretty sure I'm right with this.

This ATI paper and this NVidia paper (page 30) disagree.


Ok, thanks. I read those two documents now and as it seems early-z optimizations are disabled when discard or alpha test is used even though I don't understand why this should be the case. Still, hierarchical-z optimizations remain functional even when alpha test is used as the ATI document confirms.

Edit: My brother had an idea on why early-z won't work with alpha test. He thinks it may be because of occlusion querries as the hardware always has to count how many pixels pass the depth test also when no occlusion queriers are currently made. And since the depth test comes after the alpha test in the pipeline it cannot be optimized.

[Edited by - Trenki on November 2, 2007 4:14:46 PM]
All good to know ... thanks guys.

I am still trying to figure all of this out exactly. I am still a newbie compared to most of you so I have a lot of questions which may seem silly.

Quote:
All you have to do to take advantage of it is draw the scene front to back and not modify the depth value in the pixel shader. This way Early-Z and also Hierarchical-Z optimizations will take place.


Questions:
1) Can approximate front to back order be used or does it have to be exact? I currently use an octree/frustum cull technique but it only handles approximate front to back rendering.

2) I do have many objects with alpha translucent portions to them and would like to use them in the game. I obviously want to take advantage of any hardware features as well and do not want to disable any z optimizations or anything if at all possible. Can someone lead me to the proper way to handle this?

3) Just as a verification, to use hardware hierarchical z buffering on modern hardware one only needs to render the application object meshes (and no occluder meshes etc.) in front to back order (approximate?) and not alter the z buffer? Seems like cake.

Thanks, Jeremy
1) Yes, approximate front to back rendering is fine. Perfect front to back ordering would be too expensive.

2) The ATI or Nvidia doc suggests to first render all opaque objects followed by the alpha tested objects and then the alpha blended objects.

3) You don't have to render any occluder meshes. You simply render the objects with depth test and depth writes. Alpha blended objects should be rendered back to front with no depth writes.

This topic is closed to new replies.

Advertisement