When do you use D3DPT_TRIANGLEFAN?

It seems to me that a naive use of triangle fan would lead to a prohibitive amount of drawprimitives, essentially per polygon. Is triangle fan just a relic of the old days when low bus bandwith and memory were constraints? Here's part of an article I found off of MSDN:

Watch Out for DrawPrimitive Optimizations
In addition to state change optimizations, the runtime will attempt to optimize the number of draw calls that the driver has to process. For example, consider these back to back draw calls:

DrawPrimitive(D3DPT_TRIANGLELIST, 0, 3); // Draw 3 primitives, vertices 0 - 8
DrawPrimitive(D3DPT_TRIANGLELIST, 9, 4); // Draw 4 primitives, vertices 9 - 20

Example 5a: Two Draw Calls

This sequence contains two draw calls, which the runtime will consolidate into a single call equivalent to:

DrawPrimitive(D3DPT_TRIANGLELIST, 0, 7); // Draw 7 primitives, vertices 0 - 20

Example 5b: A Single Concatenated Draw Call

The runtime will concatenate both of these particular draw calls into a single call, which reduces the driver work by 50 percent because the driver will now only need to process one draw call.

In general, the runtime will concatenate two or more back-to-back IDirect3DDevice9::DrawPrimitive calls when:

The primitive type is a triangle list (D3DPT_TRIANGLELIST).
Each successive IDirect3DDevice9::DrawPrimitive call must reference consecutive vertices within the vertex buffer.
Similarly, the right conditions for concatenating two or more back-to-back IDirect3DDevice9::DrawIndexedPrimitive calls are:

The primitive type is a triangle list (D3DPT_TRIANGLELIST).
Each successive IDirect3DDevice9::DrawIndexedPrimitive call must sequential reference consecutive indices within the index buffer.
Each successive IDirect3DDevice9::DrawIndexedPrimitive call must use the same value for BaseVertexIndex.
To prevent concatenation during profiling, modify the render sequence so that the primitive type is not a triangle list, or modify the render sequence so that there are no back-to-back draw calls that use consecutive vertices (or indices). More specifically, the runtime will also concatenate draw calls that meet both of the following conditions:

Notice it won't even consolidate 2 DP's with no state changes if a fan is used.
 
I believe the primary reason to use things like triangle strips and fans is to make it easier for the hardware to maintain its transformed vertex cache. In reality, optimized triangle lists are typically faster (where the vertex cache has been taken into account), since you can have more triangles per vertex (strips/fans both limit to one triangle per vertex: an optimized triangle list can go as high as two triangles per vertex).
 
The fact is I'm not going to be using fans if I have to waste my DP budget calling DP for every polygon. This is what I'm getting at.
 
Its all about triangle LISTS optimized for the post-transform vertex cache. Its so simple to do this that it pretty much negates the point of the other primitive types now.

A couple of years ago it was all about using strips and there were loads of tools out to "strip-ify" meshes, but that seems to have been replaced now.

Avoiding triangle fans has been a long held "rule of thumb" - they have few redeeming qualities in comparison to others. They aren't very cache/fetch friendly and they can't represent arbitrary meshes anywhere near as well (lots of restarts are required which means lots of expensive draw calls for relatively little work)...

Just use optimized lists and forget about it ;)

hth
Jack
 
IIRC all the bsp surfaces in Quake2 were drawn using triangle fans. This is an odd case, as the data structures in their bsp file format were actually setup with fans in mind. (Every surface was a 'polygon' not a soup of triangles).
Q3 still uses the same data format, but I'd expect uses triangle lists instead.
 
Numerator said:
You don't need triangle fans. Use triangle strips in triangle fan order for best perf.
Really? Here is a list of triangles

...ABC ACD AEF AFG AHI AJK...

Pray tell me what the strip order is that gives the same performance as a fan?:rolleyes:
 
To be clear, none of this means that you should use trifans. They're obsolete. You're better off avoiding the kinds of topology that "needs" fans, or simply use indexed triangle lists, which usually provide better perf these days anyway.
 
To be clear, none of this means that you should use trifans. They're obsolete. You're better off avoiding the kinds of topology that "needs" fans, or simply use indexed triangle lists, which usually provide better perf these days anyway.
That assumes that hardware X has an indexed triangle vertex cache. If it doesn't then you are shooting yourself in the foot.:???:
 
Last edited by a moderator:
Last time I did anysort of real performance test, strips (optimised for the cache) were still faster in the case of simple vertex shaders, because tri-lists ended up setup bound.
 
Back
Top