3
\$\begingroup\$

I have tried to reduce shadow shimmering/flickering using technique described here: http://msdn.microsoft.com/en-us/library/windows/desktop/ee416324%28v=vs.85%29.aspx

I works as I want and shimmering is reduced but sometimes I have artifacts. It looks like my code try to index space outside the shadow map. Article above wrotes about it but I didn't find any solution.

Screen

When I played with code I get also black strips on the corners.

Code:

// reduce shadow shimmering/flickering
Vector2 vecWorldUnitsPerTexel = Vector2(D.x() / (float)D.shadowMapSize(), D.y() / (float)D.shadowMapSize());

// get only x and y dimensions
Vector2 min2D = min.vector2(),
                max2D = max.vector2();

min2D /= vecWorldUnitsPerTexel;
min2D = Round(min2D);
min2D *= vecWorldUnitsPerTexel;

max2D /= vecWorldUnitsPerTexel;
max2D = Round(max2D);
max2D *= vecWorldUnitsPerTexel;

min.set(min2D, min.z);
max.set(max2D, max.z);

// crop matrix based on this article http://http.developer.nvidia.com/GPUGems3/gpugems3_ch10.html
Vector scale;
Vector offset;
scale.x  = 2.0f / (max.x - min.x);
scale.y  = 2.0f / (max.y - min.y);
scale.z =  1.0f / (max.z - min.z);

offset.x = -0.5f * (max.x + min.x) * scale.x;
offset.y = -0.5f * (max.y + min.y) * scale.y;
offset.z = -min.z * scale.z;

Matrix4 m;
m.x = Vector4(scale.x, 0, 0, 0);
m.y = Vector4(0, scale.y, 0, 0);
m.z = Vector4(0, 0, scale.z, 0);
m.w = Vector4(offset.x, offset.y, offset.z, 1.0f);

I think that I should store in depth map slightly larger area but I'm not sure how to do this. I tried to change scale of scrop matrix but it doesn't help.

EDIT: It seems I've found a solution. When I'm rounding (or flooring) min and max values I subtract one to min value and add one to max value. This makes the shadow map contains slightly larger area and I don't see any artifacts.

\$\endgroup\$

Your Answer

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

Browse other questions tagged or ask your own question.