Question about alpha test performance

Hello world.

I am developing on iphone using PowerVR MBX. I know alpha test can kill performance, but I encountered one weird result when running demo. I had test case 1 & 2, test case 2 is submitting fewer triangles than test case 1, all other states and number of draw calls and texture size are the same, but test case 2 is SLOWER than test case 1. Test case 2 is drawing more pixels on screen but that doesn’t differ TOO many pixels, about the screen size. Test case 2 is like 10 times slower. Is the extra pixels making case 2 so slow? When using alpha test, does the triangle order makes performance different? Any particular trick to use alpha test on PowerVR? Thanks a lot.Smile

Hi Shawn,





Your correct that alpha test can kill performance. The reason for it is that it negates a number of performance advantages the hardware provides, most notably it removes the benefit of deferring the render (fragment visibility cannot be determined during Hidden Surface Removal). Reordering triangle submission order can affect performance, but only if depth writes are enabled (e.g. if you draw objects close to the camera first, obscured fragments in renders further away will be ignored by the hardware anyway).





Your best approach is to use alpha testing sparingly, or avoid it completely. In many cases, setting the alpha value to zero and blending gives the same result. Because the hardware does not have to re-determine fragment visibility when alpha blending (just blends with the previous contents of the colour buffer), its a much faster solution.





You can also vastly improve performance by breaking objects (particularly for sprites) into opaque sections to be rendered and alpha blended/tested sections, as this increases the number of opaque fragments that can take advantage of the hardware’s TBDR performance advantages.





What is the particular effect your trying to achieve?Joe2011-01-10 12:11:29

Thanks for the answerSmile

Basically I was doing a lot of sprite rendering,  I will first try if I can completely using alpha blending, if not I will try to experiment spliting sprite into opaqe parts and alpha test parts.

Thanks.



No worries :slight_smile:





Btw, you may find using more complex geometry that’s optimised for the shape of the texture in the sprite to be a good performance boost, i.e. if drawing a tree sprite with a triangular body, texturing a (simple, 3/4 triangle) tree shaped polygon instead of a square one will mean there are less fragments to blend (a tighter fitting polygon would have less empty areas that need to be blended out).

A related question to this thread: if you have to use glEnable( GL_BLEND ) for all renderable geometry (no, or hard to determine opaque areas), is alpha testing (more) expensive then too, or do you pay once?

Alpha testing is more expensive than alpha blend on any hardware that performs depth tests early in the render. You should always favour alpha blend if you can achieve as good as, or close to, the same graphic fidelity as the performance will be better. Please see the “How can I render sprites efficiently on POWERVR hardware?” section of our FAQ page for more information

Thanks Joe, that’s helpful information.





Reading the FAQ item you mention, I’m wondering: is depth-testing actually speeding up rendering? In my particular case, I depth-sort my 2D sprites manually and therefore have switched off the OpenGL depth buffer altogether. All my sprites are drawn with alpha blending on (unfortunately, there are just hardly any opaque areas, or they are very hard to determine). zmippie2011-02-21 10:28:07

If you have depth-sorted and switch off the depth buffer then no depth-test is being carried out so depth-testing will not be making any difference at all. Make sure that you aren’t initialising a depth buffer.

If you really have to render all sprites with alpha blend then ensure that you’re clearing and discarding buffers between frames and render any of your opaque backgrounds with blending disabled.

In the situation described in the FAQ item, depth testing is necessary for hidden surface removal to take place on obscured fragments and for sprites to still overlay coherently.

Quote:
Make sure that you aren't initialising a depth buffer.

No, I'm not initialising it, not clearing it, etc.

Quote:
ensure that you're clearing and discarding buffers between frames and render any of your opaque backgrounds with blending disabled

Yup, I'm doing that. In fact, I've thrown out the (512x512) background tiles entirely because even without blending turned on, I noticed that they were still eating up a lot of fillrate.



Thanks for the info.

Going back to your initial question: there really is no reason to prefer alpha test if you’re not using a depth buffer. In fact, alpha blending will look nicer since you can utilise a full range of alpha values instead of the punch-through effect available with alpha-test.

In your two examples, it seems that you’re fragment/pixel limited (as would be expected in a 2D app like this) so submitting more triangles makes no difference - drawing more pixels does (10x difference still sounds extreme though). Remember all tested/blended pixels count towards the processing cost, not just the pixels you see.

Thanks for your clarifications Gordon.