Skip to main content
GameDev.net gamedev.net
🔒 Locked

multiple shadow maps in the same texture?

Started by lonesock Oct 9, 2010 at 12:51 PM 7 replies 4k views
Original Post
lonesock
lonesock
Hi, All.

(EDIT: sorry, brain's asleep...I'm using FBOs under OpenGL, but it would be nice to know if this is doable under DX as well)

I'm working on a new (very fast) soft-shadowing technique, and it uses a VSM-style blur on the shadow map as an intermediate step. I was wondering if there is an efficient way to combine multiple shadow maps into one texture, so the blurring pass could be shared, saving time. Ideally my code would go something like this:

* Set up texture-1 as a RGBA16f.
* Render scene from spotlight-A into texture-1.rg
* Render scene from spotlight-B into texture-1.ba
* Blur texture-1 (probably 5-tap separable Gaussian)
* Render final scene, computing soft shadows from both spotlight-A & -B using only a single fetch from texture-1

Is this possible? I know that I could render spotlight-A's depthmap into texture-1, and spotlight-B's depthmap into texture-2, then combine both texture-1 & -2 into texture-3 before blurring, but that seems a bit of a waste.

If there was an efficient way to do this, you could even set up 4 simple depthmaps in one RGBA16f texture for distant spotlights, and render 4 shadowmaps at once (assuming they were far enough away that the non-softness wouldn't be an issue.

I really appreciate any help / pointers / advice.

thanks,
Jonathan

(btw, a tiny video showing the current state of the technique is
">here on YouTube
, though I will probably have to change the name before going public [8^)
Erik Rufelt
Erik Rufelt
Would it work with additive blending, where the first pass sets .ba to 0 and the second pass sets .rg to 0?
Video looks nice ^^
osmanb
osmanb
If I understand this correctly, you're still going to need to do multiple reads from the texture during the lighting pass, assuming that these are normal (light-space) shadow maps. If they're the screen-space results of shadowing, then yes, you can get multiple shadows in the channels of a single texture. But otherwise, the UVs (computed using the world -> light -> projection matrices) aren't going to match up.

Incidentally, even with that caveat, we still did something like this on Marvel Ultimate Alliance 2. We had several shadow maps, with VSM for filtering. The RSX (PS3) doesn't have a two-channel 16-bit format, so we overlaid two shadow maps into a four-channel 16-bit format, and then did the VSM blurring for two shadows at once. Although, our technique was closer to the 2nd thing you described: We rendered each shadow map to a separate Z buffer first, then combined them together during the first pass of VSM.
lonesock
lonesock
Quote:
Original post by osmanb
If I understand this correctly, you're still going to need to do multiple reads from the texture during the lighting pass, assuming that these are normal (light-space) shadow maps. If they're the screen-space results of shadowing, then yes, you can get multiple shadows in the channels of a single texture. But otherwise, the UVs (computed using the world -> light -> projection matrices) aren't going to match up.

Incidentally, even with that caveat, we still did something like this on Marvel Ultimate Alliance 2. We had several shadow maps, with VSM for filtering. The RSX (PS3) doesn't have a two-channel 16-bit format, so we overlaid two shadow maps into a four-channel 16-bit format, and then did the VSM blurring for two shadows at once. Although, our technique was closer to the 2nd thing you described: We rendered each shadow map to a separate Z buffer first, then combined them together during the first pass of VSM.

You are correct, the shadow maps are in light-space. What I'm doing right now is storing the projection matrix for each spotlight in a texture matrix. That way, in my vertex shader I compute the varying shadow_map projection vec4 once per shadowmap (using gl_TextureMatrix). In the fragment shader I would have to do a separate fetch for each shadow map sampled, but at least I wouldn't have to bind more textures, and as you say, the blur pass amortizes the cost. There's probably a beter way to do this, however. [8^)

BTW, it _looks_ like I'll be able to get basically the same soft-shadow effect with a single texture channel, meaning that I could potentially store 4 shadow maps per texture, thus rendering 4 spotlights' soft-shadows per pass!

thanks for the feedback,
Jonathan
MJP
MJP
You shouldn't need to use blending. Use color write channels to mask off the channels you don't want to write to.
Geometrian
Geometrian
Consider that your blur kernel will have to handle edge cases, because the clamp/repeat functionality won't work. That's a whole lot of conditional tests for each fragment . . .
[size="1"]And a Unix user said rm -rf *.* and all was null and void...|There's no place like 127.0.0.1|The Application "Programmer" has unexpectedly quit. An error of type A.M. has occurred.
[size="2"]
lonesock
lonesock
Quote:
Original post by Geometrian
Consider that your blur kernel will have to handle edge cases, because the clamp/repeat functionality won't work. That's a whole lot of conditional tests for each fragment . . .

Hmm, I'm not sure I understand. As long as the filtering keeps each component (r,g,b,a) separate, I shouldn't face any more issues than I normally would with a single shadow map, right? For cone spotlights, I would probably just mask off a circle around the outside of the depth-mask at 0.0, so the light would not be cast outside its cone. The final shader would have to sample the shadow-map 4 times, retrieving uv[0].r, uv[1].g, etc., but each one should be properly clamped.

I'm sorry, I'm sure I missed your meaning.

Jonathan

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.