I cast shadows in either opened or closed environment for a directional light whose lookat position follows the player position. So the shadowmap is refreshed regularly so that I cannot store a fixed preblurred map. As blurring consumes useless cycles when there's no shadow or when the scene if almost fully shadowed I would like to know if there is a method to detect if blur should be required or not. I've seen these ddx/ddy functions used sometimes to calculate the bias. Can they be used for my question? Or other methods. There is of course the alternative variance shadow technique where you can preblur but this is not my question.
1 Answer
A naive idea is to use gathercmpred to sample two corners away from the central pixel your working with like this:
float 4 S = txDepthMap.GatherCmpRed(samCmpLess, ShadowProj.xy, Bias, int2(-1,-1)); S += txDepthMap.GatherCmpRed(samCmpLess, ShadowProj.xy, Bias, int2(1,1)); S.x = dot(S,(1.0f).xxxx); Shadow = (S.x==8);//8 all texel are shadowed, 0 none if ((S.x>0) && (S.x<8)) do some blur In a rather fully shadowed area (3 level cascaded shadow) using a 3x3 optimized fixed pcf for the final blur give a small impact. The idea starts to be interesting at 5x5 or 7x7 samples. A drawback I saw is a degradation of the blur with some loss of the gradient effect. Maybe some improvement could be done. Enlarging the corner distance (e.g. int2(+/-2,+/-2) does not improve the result for 5x5 sampling. In general I see better results with a direct texcoord modification (e.g like texcoord+1.0f/texsize).
- \$\begingroup\$ Would it be better to use the version of GatherCmpRed() that takes four offsets to sample all four corners at the same time? \$\endgroup\$Adam– Adam2025-04-03 20:24:49 +00:00Commented Apr 3 at 20:24
- \$\begingroup\$ Yep, I just did not think of it. Thanks a lot for this remark. \$\endgroup\$philB– philB2025-04-07 07:01:52 +00:00Commented Apr 7 at 7:01