- Home /
What is better to preserve, Draw calls or Tris? [Mobile]
When it really comes down to every bit if performance juice what is more important to keep low for mobile development; draw calls or tris?
I currently develop for Android, and will port out to IOS eventually, I target higher end devices and I have been using the built in Terrain engine because it's so easy. I don't really do any LOD or tress or anything using the engine I just place that type of stuff in a prefab and allow the user to "turn on high detail".
I've been messing around with Terrain 4 Mobile and on some of my very optimized terrain scenes I haven't been able to dramatically increase the performance by switching the terrain to a mesh; in fact I've hurt performance in a few.
In a couple scenes I can either save ~13k tris by using the built in terrain engine, or I can save ~3 draw calls by switching to a mesh?
In this specific example on my high end phones I saw no difference but on some low end devices I saw a decrease in 1-2 FPS by switching to the mesh (higher tris lower draw call). (But who knows if that was a real increase. Maybe my phone started running a background process - I don't know)
These tests were done at an idle and not truly tested when the game was engaged.
With that being said what would be better overall? Lower draw calls or tris?
It seems to me that the decision is highly dependent on the shader and the material.
It depends on "many" things, including the size of the batch per draw-call.
$$anonymous$$y own suggestion would be to use the built-in terrain as the more optimized solution, especially if you don't have (aren't) a dedicated optimization expert. Why? Because its optimized to work well with many other things in the Unity eco-system including trees etc that you may not need now, but will likely need later, or may not even be aware that you are using.
Ummm, built in terrain and optimised don't usually fit in the same sentence unless accompanied by "is not for mobile" :P Though I guess it may be getting better.
I suppose big terrains without trees etc might just find some instances of improved perforamance.
$$anonymous$$y solution is to convert terrains to meshes, use low impact shaders (max 4 textures) and run Cruncher on the terrain generated by T4$$anonymous$$ to significantly reduce the number of triangles too...
I think this is more of a forum question, as this question doesn't really have a correct answer unless you're willing to accept "It depends on your target device and your game." as one...
Here is the Unity's Practical Guide to $$anonymous$$obile Optimizing.
Basically what I took from that guide was: $$anonymous$$eep both as low as possible. If your GPU is the botttleneck, it's better to add Draw Calls. If your CPU is the bottleneck, it's better to add tris.
Answer by trs9556 · Nov 01, 2013 at 11:35 PM
Thanks for all the answers. Like @Jamora stated this wasn't the best place to post this considering there isn't a "real" answer. As a result I'll just post what I found out.
In my specific case NOT using the terrain engine didn't effect CPU/GPU performance much. What I did find though is the Unity Terrain uses WAY TO MUCH memory. As a result, being on mobile devices, memory is very valuable. So I did end up converting all my terrains with Terrain 4 Mobile.
I then exported my T4M object with a script I found on the wiki (export it as an .obj) and opened that into blender and further optimized so it would have less tris. It works great!
Answer by bpears · Aug 23, 2013 at 05:50 AM
You need to have a balance. I would worry more about draw calls. On IOS/Android, these are very delicate, and get used up quickly. You'll likely want to look into draw call batching or mesh.CombineMeshes in the docs. Use batching if your game would also benifit from occlusion culling. If it wouldn't (aka you're going to see most of the scene, most of the time), then just use mesh.CombineMeshes. Look into Texture atlasing also. Using all these will keep your game mean and lean.
Answer by Imawizrd · Aug 23, 2013 at 05:59 AM
with iPhone 4 in mind, every app I do I aim for <20k tris, <40 draw calls. Don't use any transparent shaders, stay away from lighting, and real time shadows. Optomising becomes a skill I think, you will eventually learn and make habit of all of the tricks.
Of course these numbers can vary depending on what you are doing.
Answer by RaiSacdalandrs · Aug 23, 2013 at 05:30 AM
Draw calls
Uhmm...not necessarily. Technically you could put "all" of your triangles in a single draw-call but it would likely be "slower" than a multi-draw call solution...
Back in the OpenGL days, we would present our setups/tests in the OpenGL forums on what the best draw-call-to-batch-size ratio was. Low draw calls wasn't/isn't always the best way to go.
Really? Because given a choice Unity would batch everything into 1 or 2 draw calls.
Ok, I'm probably missing something, but that's talking about vertex buffer limits (which are around 64k in Unity not 2^16 BTW). No batching in Unity will ever exceed that on a single batch and dynamic batching is fairly limited on the complexity of meshes it uses.
I guess that to allow for occlusion culling or frustum culling it can be possible to reduce the load on the hardware but not batching, certainly if you end up processing a bunch of points that are just culled afterwards.
Unity will however batch anything that fits within the limits of a single mesh (given restrictions on the complexity as mentioned before) - so they definitely think that it's the most costly expense on mobile phones etc.
I think the confusion arises since I was discussing the GPU concept whereas you were discussing it in a Unity-specific context (which is likely more relevent).
Unity's 64k per mesh limitation is a result of its 16-bit indexing. A 32-bit indexing scheme would substantially raise the limits (perhaps in another version?). How big, then, should your single VBO be? Should you bunch them all into one large VBO, or break them into multiple smaller ones? You could actually make your VBO larger than available GPU memory and cause it to page, significantly degrading performance.
The answer is not very clear, and depends on the GPU and its architecture, and a bunch of other factors. Hence the link.
BTW, I keep referring to VBOs because from a GPU point-of-view, at its most fundamental level, glDrawArrays is THE "draw" call, and it draws a VBO...