Sign in to follow this  
Tispe

Reducing draw and SetTexture calls

Recommended Posts

Tispe    1468

Hello

 

In some recent threads i've played with the thought about how I can reduce my draw and SetTexture calls such that I can output more triangles.

 

In my project each character has a face-, weapon-, shield-, helm-, armor-, gloves-, leggings- and boots -mesh. Each mesh has its own texture. That is 8 texture changes, one SetFloat(), and 8 drawcalls just to draw one character. With this system I can swap any mesh on the fly to create a mix of wearable equipment.

 

I am storing the skeletons in a dynamic texture which I sample to extract the bones during skinning. The primary reason I went with this solution was to avoid the use of the low number of constant registers for skinning. A bonus was that I could with a simple texture lock and memcpy, transfer as many as 30000 animated skeletons to the GPU memory.

 

What I do now is to loop over all characters, SetFloat(...,index,..) for the skeleton, and call all 8 draw calls, and setting a texture for each one.

 

 

Since many characters can use the same equipment, creating a texture atlas would IMO devour memory. If 30k characters each needed a 4096x4096 texture atlas with duplicate entries then that would surely break the memory limit.

 

Now, I know about setting the texture once, and then draw all meshes that uses it, BUT if 1000 characters would use different unique equipment then this method would not help at all, since each texture only has one mesh that uses it.

 

So I need a something in between a texture atlas and a batching routine.

 

 

Since SM3.0 support 16 simultanious textures I though about using the first 8 textures, like texture blending. I would first expand the vertex struct to include an index to which sampler to use, then merge all meshes into one mesh(editing every vertex with the sampler index to use), then in the render routine; SetTexture 8 times in a row each in its own sampler, then I would only have a SINGLE DrawCall.

 

Now, with this method I reduced the number of DrawCalls from 8 to 1, but I still have 8 SetTexture. The SetTextures are called one after the other with no DrawCalls inbetween, but I don't really know if this is a good improvement.

 

 

Is making a texture atlas the only way to reduce 8 SetTextures into only 1 SetTexture? Are there any other options I could take a look at?

 

Cheers!

Edited by Tispe

Share this post


Link to post
Share on other sites
Apoxol    153
One solution could be to generate dynamic atlases. Assuming that the gear on your character does not change that often you could iterate over the images used by all the gear for the current character and dump them into an atlas then upload and use that atlas. When the characters gear changes you can rebuild the atlas or since likely there will be some wasted space in the atlas you could just add new gear pieces to it until it fills up and then rebuild.

You could take this approach even further and generate a larger atlas for the cumulative needs of characters on screen for a particular level. Though that assumes that the gear would be fairly static within the scope of the level.

Hope that helps or maybe gives you some other ideas.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

Sign in to follow this