# VSM Extended - Take 2

## Recommended Posts

lonesock    807
Hi, All. OK, this may be a bit premature, but I am excited so want to share. Remember my older thread about Extending VSM? Well, I'm taking that same framework (i.e. still using my alternate encoding and a fake PCSS), but trying a little difference. Instead of computing the shadowing term to be: float m_d = moments[0] - depth; float lit = variance / (variance + m_d * m_d); use this basic form instead: float lit = 1.0 - 1.33 * m_d / sqrt( variance ); (of course guarding for /0 and precision issues, and clamping in the 0,1 range.) The result is that the precision issues are much lighter, and more importantly, no lightening halos around stacked shadow casters! (naturally, I'm lying, or at least exagerating [8^)...I did spot it in one case, but normally I can not see any, even when looking for it!). Here's the screenshot: and here is the actual GLSL snippet:
sigma2 = 0.75 * sqrt( max( 1e-10, sigma2 ) );
float delta = max( 0.0, d1*0.995 - sd1 );
sigma2 = max( sigma2, delta );
float lit = 1.0 - delta / sigma2;


And that's it! The preview image show the RGBA16f FBO format since that is typically the worst looking (both 16i and 32f look much beter with standard VSM)! (Oh, the theory...I wanted to take variance into account for the brightness, but not allow the lightening to occur. 1-delta/sigma gives me that. The 0.75 comes about because if you plot the value of (average_x - sigma) along a step function with an arbitrary smoothing filter width, you can see it will go from 0 up to 1, but will dip below 0 to -0.207 or so. Thus, to disallow lightening below the surface of the shadow-map, I needed the term to fall to zero faster. I implemented it by scaling sigma down to 3/4 scale, thus falling off 1/3 faster than if I just used sigma verbatim.)

##### Share on other sites
This looks nice indeed. Will you release a demo like last time?

wolf    852
very nice.

##### Share on other sites
lonesock    807
Thanks, Matt and Wolf!

Yep, I will release a demo soon. Things I'm working on:

* I think I have a better alternate encoding for low precision formats.

* For cases where the shadow texture size is smaller than the screen size, I plan to perform the calculation of sigma (taking the square-root of variance) inside the blur shader, and store average depth in one channel, and sigma directly in another (instead of average depth^2).

* I'm working on an option to harden the shadow edges artificially, but not be blocky (should be straightforward to do...by cranking up the fall-off term from 1.333 to something much higher I should be able to get an effect similar to the signed distance field alpha-threshold effect)

* I now also have access to an Intel G43 chipset, which supports GLSL 1.10 with the latest version of the drivers. I'm trying to get this to work there (I can not use any of the *Lod version of the texture fetch commands, so I need to determine which mipmap level is accessed by default, so I can duplicate the *Lod calls with the mipmap bias term from the regular texture fetch versions)

* I will probably update my OBJ loader...I have some bugs in there, especially with normal vectors!

##### Share on other sites
bzztbomb    122
Looks good! It seems like you can keep larger pneumbra and still attack bleeding. It's a pretty subtle difference in my tests between this technique and normal VSM's with the light bleeding tweaked for the scene. I ended up using 1.5 instead of 1.3 to get rid of some extra light bleeding in my test scene.

I took a bunch of screenshots and notes of VSM, VSM Extended, and ESM's here: http://www.bzztbomb.com/noise/?p=32

I'm hoping to expand on it when I find more time.

Brian Richardson
http://www.bzztbomb.com/noise/

##### Share on other sites
lonesock    807
Hey, bzztbomb, nice quick screen-shot overview!

Regarding my previous goals, here's an update:

* no beter alternate encoding, other than storing 1-depth helps 16f formats

* calculating sigma in the blur pass: haven't had time yet

* hardening the shadows doesn't look good with my Mipmap-then-3x3-Gaussian-Blur method...maybe using a regular separable blur with a larger kernel would look good.

* The Intel G43 supports GLSL 1.10 pretty well (need the latest drivers), but does not allow the *Lod version of the texture fetch commands inside the fragment shader. That's OK if you don't want the fake PCSS (which depends on specifying the mip level specifically).

Thanks again for your patience everybody!