Monday, June 29, 2009

Ambient Occlusion in Screen-Space

Screen-Space Ambient Occlusion (SSAO) is quite popular in the moment. ShaderX7 had several articles and there are lots of approaches to gradually improve the effect.
A good way to look at SSAO or any similar approach is to consider it part of a whole pipeline of effects that can share resources and extend the idea to include one diffuse (and specular) indirect bounce of light by re-using resources.
The overall issues with SSAO are:
1. quite expensive for the image quality improvement. Using the astonishing high amount of frame-time for other effects is an intriguing idea. In other words the performance / quality-improvement ratio is not very good compared to e.g. PostFX where a bunch of effects consumes a similar amount of time.
2. a typical problem is that lighting is ignored by SSAO. Using the classical SSAO implementation under varying illumination introduces objectionable artifacts because the ambient term is darkened equally (obviously you can apply SSAO to the diffuse and specular term like a shadow term ... but then it isn't ambient anymore). If you have a "global ambient" light term like skylights, SSAO will diminish the effect. It also leads to problems with dynamic shadows.

Overall I believe a fundamental shift to more generic method is necessary to solve those issues. This is one of the things I am looking into ... so expect an update at some point in the future.

21 comments:

KB said...

SSAO's wastefulness is in some ways a strength -- game makers who want to make a game that plays well on crappy computers (e.g., "Dad's 5-year-old hand-me-down laptop") can just glom-on SSAO without changing the low-spec game logic and assets, thus providing a more sophisticated-looking appearance for players with newer computers (players who often spend more on games anyway, so you want to court them too)

Andy Firth said...

our SSAO implementation costs 0.7ms (x360). This is not that expensive at all tho it does use buffers that were prepared for other passes such as z feathering of particles and SS Shadows.

Robert Cupisz said...

Are you familiar with Tobias Ritschel's SSDO technique? http://www.uni-koblenz.de/~ritschel/ Approximating Dynamic Global Illumination in Image Space

It's a tad more expensive than plain SSAO, but tries to take into account the lighting of the scene.

Wolfgang Engel said...

<<<
Are you familiar with Tobias Ritschel's SSDO technique?
<<<
Yes I am. Cool stuff :-)

Sl@yEr said...

Speaking about real-time global illumination, there is also a method proposed by Crytek which requires no pre-computation. It will be presented this year at Siggraph.
(http://www.crytek.com/fileadmin/user_upload/inside/presentations/2009/A_bit_more_deferred_-_CryEngine3.ppt , sildes 21-23). It looks very interesting.

Wolfgang Engel said...

yes I know. I will talk on the same event about the Light Pre-Pass.
My target is to figure out something on my own and then see what they implemented.

christer said...

I don't understand what you mean by "lighting is ignored by SSAO" (point 2). Ambient occlusion is a shadowing term of ambient light. You could argue that the shadowing term is only approximated in screen-space, but resulting artifacts beyond the approximation error of the shadow value would suggest not correctly modulating the ambient light by this term.

I also don't understand what it means for the ambient term to be "darkened equally" as we modulate the ambient light with different values at every screen pixel.

Andy Firth said...

I agree with Christer, SSAO done properly attenuates the ambient contribution in standard lighting.

Sl@yEr said...

My though about SSAO is that it is a wonderfull effect but it is only a special case of global illumination. It is only a grey modulation. "lighting is ignored by SSAO" could mean that SSAO is only a percentage of non-occluded rays over a surfel hemisphere (or sphere). However, the color of these non-occluded incoming rays should be taken into account.


"yes I know. I will talk on the same event about the Light Pre-Pass."
I have already read your article in ShaderX7. Very nice article!! I'm waiting for your presentation now ;) Will you share it online?

"My target is to figure out something on my own and then see what they implemented."
yes, it's always better to have it's own ideas and Crytek's algorithm is not Previous Work right now :)

Wolfgang Engel said...

christer: let me start with a short description how SSAO works: in essence we inspect for some neighboring pixels their depth values by placing sampling points on a sphere with a user-defined radius around the pixel we are interested in. For each of those spheres we calculate an occlusion value that depends on the solid angle of the sphere with regard to the receiver point == our pixel we are interested in. In other words the occlusion values from the sphere are all accumulated into a single ambient occlusion value.
SSAO displays darkening of cavities and contact
shadows, but all directional information of the incoming light is ignored.
This happens because only the geometry is used to compute Ambient Occlusion while the actual illumination is ignored.
This doesn't happen in the real-world (TM) :-) ... everything is influenced by Light: otherwise we wouldn't see it.
If you have "real" ambient lights than you use as fill lights and therefore consider ambient, you need to establish a relationship between visibility/illumination and occlusion/shadow that is probably more complicated than just multiplying those terms. Multiplying would work with your regular shadow maps because they consider the effect of light.

christer said...

SSAO is not one method as you imply by your example, but a family of (different) methods. What is common to all methods is that we compute, using a full screen pass-like process, a screen space buffer of ambient occlusion values. These are the k_A values, as defined in 9.14 of p. 375 of RTR3. Note that computing the k_A term does not involve lighting in any way; this is as it should, because k_A is a visibility/shadowing term.

Going back, your statement was "lighting is ignored by SSAO". That is not correct because SSAO computes the ambient irradiance as k_A*pi*L_A, where L_A is the incoming radiance (i.e. the not-ignored light). Perhaps you meant to say "_directional_ lighting is ignored by SSAO" but surely that's tautological; we already know -- a priori -- that AO does not depend on light directionality, so it cannot be an "issue" with SSAO!

All in all I still don't understand what you meant with your point 2 above. Your clarification seems to be talking about something entirely different, perhaps stating that SSAO != GI (which of course is true), but I'm not really sure what the clarification says either.

Wolfgang Engel said...

christer: I hope you are fine!

<<<
Note that computing the k_A term does not involve lighting in any way; this is as it should, because k_A is a visibility/shadowing term.
<<<
<<<
we already know -- a priori -- that AO does not depend on light directionality, so it cannot be an "issue" with SSAO!
<<<
This is the problem and the shortcoming of the technique.
Therefore we should look into finding something that is better :-)
In other words we know a priori that it is an issue and decide not to use the technique in this case. This is similar to many other hacks we use to fake certain real-life interactions.

The reason why it looks wrong is that it does not account for -as you say- directional lighting -both global and local-. The illusion breaks down in certain scenarios, so there might be a better solution.

I hope that clarifies what I mean.

Wolfgang Engel said...

<<<
The reason why it looks wrong is that it does not account for -as you say- directional lighting -both global and local-. The illusion breaks down in certain scenarios, so there might be a better solution.
<<<
That should be

The reason why it looks wrong is that it does not account for -as you say- directional lighting -.

Kevin Francis said...

Sorry if a solution for this has been covered in recent lit, and this question is therefore moot, but..

Isn't one of the main shortcomings of SSAO that it tends to exhibit haloing artifacts, especially on screen edges? (This due to performing the AO on a reconstruction of the scene from screen space.)

In my recent experiments, it was a feature killer.

Wolfgang Engel said...

<<<
Isn't one of the main shortcomings of SSAO that it tends to exhibit haloing artifacts, especially on screen edges? (This due to performing the AO on a reconstruction of the scene from screen space.)
<<<
This is an issue that I believe comes from the quarter size or smaller buffer that you use while blurring the occlusion value. You can use a full-size buffer to make up for it but then it is really expensive. I don't know if there is a better solution for this resolution problem. Maybe the HD technique that AMD/ATI proprosed last GDC. It looked like as if it would run in original resolution.
I think SSAO is hard to judge as long as you haven't played around with it in a real-world game scene under changing lighting conditions. Screenshots always look cool.
The issue I describe in 2 mainly shows up in changing lighting conditions. So you have a 24 hour cycle in your game. It is quite hard to get it right over the whole time cycle.

Kevin Francis said...

Haloing artifacts are related to not having the entire scene data, not the resolution of the buffer.

For example, consider an object (A) that is in front of two other objects in the distance (B & C), the nearer of which (B) is close enough to the most distant one (C) to cast an AO shadow, but is completely occluded by the near object (A).

At that point, SSAO will result in the distant object (C) not having a shadow in the best case scenario, and casting an AO shadow from the near object (A) in the worst case scenario. (In which case the shadow would have the wrong shape.)

In my experience, this sort of artifact causes all manner of distracting popping artifacts as objects in the mid-ground (B) come into visibility and cast AO shadows around them.

Granted, the results might be good enough that people who don't look at this stuff all day won't notice, but it's worth mentioning as an unavoidable artifact. (Or at least, it's unavoidable without multiple depth samples per pixel...)

As you said, screenshots FTW. (Or FTL, depending on perspective...)

KB said...

"I think SSAO is hard to judge as long as you haven't played around with it in a real-world game scene under changing lighting conditions."

Truer words rarely posted.

I'd nuance it to say "in your specific real-world game" - for example, if a lot of objects on-screen are supposed to be light *emitters*, that can have a significant impact on the usefulness of various aspects of different SSAO techniques. Similarly, say, objects with motion blur. Or clouds. I'm a firm believer in the idea that technical choices should be driven by content -- or as the phrase goes, "form follows function."

A further nuance might be "in your specific real-world game, with the art director and producer" so that you can properly balance the forces of "looks fantastic" and "must ship on time" :)

Pat Wilson said...

I could be proven wrong, but from the shots I have seen of the Crytek method, it is not screen-space. I am putting my money on some kind of round-robin updated probe system. (Basically some kind of simplified Imperfect Shadow Map method)

I really feel like a lot of attention has been given to the Screen-Space Occlusion family of effects, and while it is very cool, I place it in the "Parallax Mapping" category of effects. Sometimes they work really well for your scene/game, and if so, more power to you. I just don't understand why so much focus has been devoted to this area, when...really, the data that we want for the effect is frequently not available in screen space.

It's like we're trying to implement screen-space water reflections for an ocean-game. Everyone works very hard on methods which come really close to reflecting the skybox back without artifacts...but we just can't quite make it right.

I really, really like the Imperfect Shadow Map approach to the Global Illumination problem, and I hope that becomes more real-time feasible in the future.

Just my opinion though.

Wolfgang Engel said...

Well said! :-)

MannyK said...

Wolfgang and Pat, glad to see I am not the only one that is less than a fan of SSAOs. Kevin outlined one of is key weakness - insufficient occlusion information from 1 depth layer. My friend Louis is developing a dual-layer alg. However that involves depth peeling. There are issues at the edfes of the screen too. I demonstrated the issues from the lack of directionality in my ShaderX6 PRT demo. I want real GI.

ArKano said...

Dome time ago a developed a simple algorithm that reduces quite a bit the halos, without using edxtra depth information:

depth extrapolation:
http://www.gamedev.net/community/forums/topic.asp?topic_id=550699

works well for some scenes, not so well for others. In sponza for example halos disappear completely.