5
\$\begingroup\$

I'm reading the Occlusion Culling section in Real-Time Rendering 3rd Edition and I couldn't understand how it works. Some questions:

  1. How does having a "Z-pyramid" contribute? Why do we need multiple resolutions of the Z-buffer? In the book, it's displayed as follows (left side): enter image description here

  2. Is the Octree structure the same Octree that is used for general frustum culling and rendering? Or is it a specialized Octree made just for the occlusion culling technique?

  3. A more general question: In a previous section (and also here), the Occlusion Query term is described as "rendering a simplified bounding-volume of an object and comparing it's depth results to the Z-buffer, returning the amount of pixels that are visible." What functions in OpenGL are associated with this Occlusion Query concept?

  4. Is this technique the standard for open-world games occlusion culling?

\$\endgroup\$
6
\$\begingroup\$

How does having a "Z-pyramid" contribute? Why do we need multiple resolutions of the Z-buffer? In the book, it's displayed as follows (left side):

It's part of being a tree. If you have only the full resolution image, you must query each individual sample in the depth buffer to determine the maximum depth of an area.

The lower mip levels allow you to instead query a single sample to determine the depth of a 2x2 region of the next mip level.

You start by reading from the smallest mip level. If that fails, you know that every sample in the full mip level will also fail, so you have no reason to check further. If the check succeeds, you step into the next mip level and repeat.

Note that hierarchical Z buffers are a feature of the hardware on literally all GPUs you're going to care about these days. There's nothing special you have to do to use them. Though there are some things you might do that would disable that optimization (e.g. explicitly writing depth values in your fragment shader).

Is the Octree structure the same Octree that is used for general frustum culling and rendering? Or is it a specialized Octree made just for the occlusion culling technique?

Both yes and no. It's just an octree, but there's already a ton of different approaches to building octrees. I'm not personally sure which is the best variant for this use case because of the items below.

A more general question: In a previous section (and also here), the Occlusion Query term is described as "rendering a simplified bounding-volume of an object and comparing it's depth results to the Z-buffer, returning the amount of pixels that are visible." What functions in OpenGL are associated with this Occlusion Query concept?

OpenGL Query Objects are the native OpenGL way of performing these tests.

Again, these automatically work with the hardware's hierarchical Z buffer implementation. You setup a query object, draw your bounding volumes, then check the results of the query objects to see which volumes had any visible pixels.

Is this technique the standard for open-world games occlusion culling?

It can be part of it, but it's traditionally been a bit less common than one might think for (counter-intuitively) performance reasons.

GPUs are complex beasts. Rendering does not happen instantly. Reading from a query object requires, naturally, that the rendering you're querying actually be done. If you're reading from a query object right after rendering, the CPU has to sit there and do nothing while it waits for the GPU.

Using the query objects efficiently requires a good deal more complication. You have to delay the checking of the query objects until well after you've rendering your simplified shapes in order to give the GPU time to complete its work. Furthermore, you want to queue up even more work on the GPU so the GPU isn't idle while you're processing the results of the query objects.

This ultimately works best with a multi-frame renderer (e.g., using the results of from N-1 or even N-3 while rendering frame N). Which, in turn, introduces some inaccuracy in the results of the queries, especially for objects that are moving quickly, so that also has to be accounted for.

Then there's the problem of GPU usage. As powerful as our GPUs are today, our graphics are that much better. The GPU is often taxed to the limit by actually rendering our scenes, even on beefier ultra-gamer rigs. That leaves very few spare GPU cycles for culling, physics, or other tasks. Conversely, most games are making very poor use of the multiple core that CPUs have available today and have quite a bit of spare CPU power lying around.

Thus, it is often a far better idea to keep all the culling on the CPU and focus on better parallelizing the renderer. Popular middleware like Umbra are used by virtually all games in order to provide extremely fast CPU-side culling of scenes (and sometimes also used for audio, AI, etc.).

Of course, now we're seeing a rise in a number of GPU-only rendering techniques where the CPU is hardly involved at all in any of the scene rendering. The GPU does all culling, draw call submission, and so on. I'm not personally enough of a graphics buff to really explain the trade-offs with those techniques nor go into the specifics of how the culling works. I do not believe those techniques can directly handle large open worlds without some heavy CPU-side help, however, if for no other reason than the inability of the GPU to initiate content streaming from disk.

\$\endgroup\$
  • \$\begingroup\$ Even though you covered general case with the occlusion culling, I would like to point out that it tend to be even worse for open-world games due to typical scene - open world. There not many good occluders - trees? too thin. Buildings? few and far away. Terrain(hills etc.)? Maybe, but LOD will kick in much sooner than occlusion and there is not much to be gain from culling ultra-simple models - furthest LOD models (or even billboards!). \$\endgroup\$ – wondra Nov 29 '15 at 19:10
  • \$\begingroup\$ @wondra Your general point is good, but keep in mind that open-world does not necessarily mean having buildings "few and far away". Take GTA for instance. Buildings, cars and NPCs are not necessarily few and far away and can easily lay within the frustrum so to escape frustum culling even if their visibility is completely blocked. If they are of low-poly due to LOD it's the important question. If not, occlusion culling can still be of significant performance gain \$\endgroup\$ – MAnd Nov 29 '15 at 19:31
  • \$\begingroup\$ The book explained that "multi-frame renderer" concept too. It looks like I should stick to CPU culling because having that "inaccuracy" you mentioned (caused by using N-x frames) is a real turnoff. Can you name any CPU culling techniques that are worth reading? Big thanks by the way! \$\endgroup\$ – Pilpel Nov 29 '15 at 21:37
  • \$\begingroup\$ @Pilpel: the obvious ones are almost identical to the technique for the GPU; the only difference being that you implement a trapezoid rasterizer in software (super easy since you're just writing depth values and don't have to deal with perspective correction). Stepping up from there is the Umbra library, which ain't cheap; they half-document their algorithm (voxelization) so you might be able to do something similar, but I've not personally heard of anyone writing "real" games who doesn't just use Umbra. :/ \$\endgroup\$ – Sean Middleditch Nov 29 '15 at 23:54
  • \$\begingroup\$ Note also that the inaccuries of frame-delayed query results are fairly easy to account for, too. A combination of using bounding boxes smaller than otherwise required along with "stretching" objects that are moving (or when the camera is moving) can do wonders. You'd also likely use this only for larger groups of objects rather than many individual items. False negatives should be rare with that effort, and false positives are at worst just a small perf hit. \$\endgroup\$ – Sean Middleditch Nov 29 '15 at 23:58

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.