Nick Darnell

Is there a way using the sprite batch object that you can render several rectangles, but when alpha blended, it looks like the entire object was rendered first as a single opaque image, and then that image was alpha blended, such that you would never have known it was several smaller pieces assembling the final object

Instead of normally seeing each rectangle blended as it overlays another rectangle.


Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

You could draw all your sprites to a RenderTarget2D, resolve it, and then alpha blend the resulting surface into your main scene.





Re: XNA Framework Alpha Blending (deferred)?

Nick Darnell

Is there no other option I would think that would be really slow.




Re: XNA Framework Alpha Blending (deferred)?

Nick Darnell

Here is an example of what I want to pull off.  Note that the green box absorbs the color from the red frame, but not from the blue frame that contains the green box.  It's a parent/child relationship.  Where the green box is a child of the blue frame, so it ignores the blended color of its parent since they should be rendered as a single entity.

http://img235.imageshack.us/img235/5136/alphaexamplemc5.png





Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

Rendertargets are the way to do this.





Re: XNA Framework Alpha Blending (deferred)?

Nick Darnell

Do you think this is fast enough to be usable for GUIs where each frame would be its own render target This is a situation where you're talking about a new texture every new frame rendered. (at least if something on the GUI changed). Do you think they would be fast enough Or are they are fairly costly thing to use.




Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

That totally depends on how many such targets you are likely to have, and also how fast your graphics card is.

For what it's worth, the composited translucency effects in Windows Vista seem to keep up quite nicely as long as you have a decent graphics card, but generally need to be turned off on older/slower hardware.





Re: XNA Framework Alpha Blending (deferred)?

Nick Darnell

Well the effect exists in the GUI engine of world of warcraft. I was really hoping to have that in mine in XNA. And it's a very nice effect to have. And their game runs on lots of older machines, which kind of makes me wonder what they could be doing.




Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

They're either using rendertargets, or they're just blending everything to the screen and putting up with the fact that that isn't really accurate.

There is no other way to do this than using a rendertarget.





Re: XNA Framework Alpha Blending (deferred)?

Nick Darnell

When writing or blending is there a way to trick the depth buffer into thinking the X number of sprites I am rendering all exist at the same depth, therefore whoever writes last. wins





Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

You could draw many sprites at the same depth (it's up to you to specify the depth value for anything you draw, so you can make that be whatever you like).

If you set the depth compare renderstates appropriately, you could make it reject subsequent writes to the same depth value. But that would accept the first write at any given depth, not the last!

If you think about what you're trying to do, there is fundamentally no way to compose multiple independently blended layers of alpha without some kind of temporary storage. The alpha blending hardware supports a single framebuffer blend operation for everything you draw, so it can do:

result = blend(source, existingValue);

But it sounds like you want to do something more like:

window1 = blend(background1, foreground2);
window2 = blend(background,1 foreground2);
result = blend(window1, window2);

That needs a temporary place to store the result of the intermediate blends, since there's no way to do the entire thing in a single pass.

The way to store temporary results is by using a rendertarget. I don't understand why you're so adverse to doing that





Re: XNA Framework Alpha Blending (deferred)?

Nick Darnell

Don't get me wrong man, it's not that I object to using rendertargets. It's that I've never been content hearing *this is the only way it can be done*, I like to explore any and all possibilities. Though there are a lot of issues I have with render targets. Since everything is rendered to a texture you have to know the size. Which means that your controls total size must be known ahead of time. So having texture borders or controls or anything that extends past this size you've set will not be possible.

Anyway, no I want window1 and window2 to blend normally. But, when i do my write to a depth, is there no way to do a "write last wins" It isn't like I'm doing anything different than a normal first draw to a certain depth.

Here's an example:

Background cleared to white.
Draw 3x3 pixel blue square at depth 1, at .5 alpha.
Draw 1x1 pixel yellow square at depth 1, at .5 alpha.

--- Then when the yellow square is drawn, because it is written last, there is no longer a blue pixel at that depth, just the new yellow pixel then everything below our current depth is taken into account. So only the background is blended with yellow to form the color at that pixel. Then suppose I did this:

Draw 3x3 pixel red square at depth 2, at .5 alpha.

--- Then because nothing is at that depth currently, and because the yellow and blue pixels are below it, it should take both of those colors into it's final color calculations.

Am I thinking of this wrong




Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

You can't do that without some kind of external memory store, which in graphics is known as a rendertarget.

The framebuffer can only hold a single color value per pixel. So it starts out white. Now you blend blue with 0.5 alpha, giving a pale blue. There is no memory that this was originally white: the framebuffer now contains a pale blue value. So when you come to write your yellow at 0.5 alpha, you are blending yellow with pale blue. There's absolutely no way you can ever make this blend with white, because the white data is no longer there.

What you are describing fundamentally needs more than a single color value per pixel. If you only have a single value per pixel, your only options are to apply each blend cumulatively over the top of that single existing value. In order to roll back blending computations, or to apply them in a different order, you need to store more than one value. Since a single rendertarget only stores a single value, that means you need more than one rendertarget.

There is no way around this.

Do not fear rendertargets. They are a good thing. Most of the interesting techniques in graphics rendering depend heavily on them.





Re: XNA Framework Alpha Blending (deferred)?

Jon Watte

You can do it without the rendertarget, using either the stencil buffer, or using "equals" depth testing.

For stencil, render each object to the buffer using a separate stencil value, but without writing to the color buffer. Then render again, using stencil test, each object using the appropriate value as key.

For depth, render each object to the buffer using a separate depth value, but do not write to the color buffer. Then turn on color writes, and render again, using equal depth test instead of less-equal.

However, a render target is a lot simpler. Just remember to render all your render targets first, before you start rendering the final scene (as on the Xbox, render targets don't remember their contents after a new render target is set, only the texture attached to it does).






Re: XNA Framework Alpha Blending (deferred)?

Shawn Hargreaves - MSFT

Depth or stencil can be used for "first write wins", but not for "last write wins" or "all the writes on a layer are blended together, then that layer is blended with the one below it".