Mobile physics optimizations and Mesh Colliders

I’ve been reading a fairly large amount how to utilize Unity’s implementation of PhysX, and I’m getting to the point of frustration on how to get my very simple game to run buttery smooth. Basically, the premise is object’s that are spawned randomly from an object pool and you simply dodge them by moving a platform. It’s an infinite scroller, nothing very complicated, with some additional physics based powerups.

I’m fairly new to coding, so I’ve been running with higher application level functions that really shouldn’t be utilized, which was one of the first sources of optimization for my code.

I was previously using LINQ for my object recycler, but I’ve digressed to using simple random number queries to search through my List(T) instead of reducing the size of my code by using LINQ. So far, from the profiler, it seems physics.Simulate is causing slight frame rate stutters occasionally, nothing to make the game come to a screeching halt or even effect gameplay significantly, but it bothers me that such a lightweight game is taking a nasty hit from Physics.

My game is using MESH COLLIDERS, and I read somewhere in the documentation that utilizing gameObject.SetActiveRecursively() or gameObject.active causes re-computation of the mesh vertex collision information every time it’s activated. So this is fairly large cause for concern, since objects are being spawned progressively faster and faster and I’m utilizing these calls every 0.33 seconds at the hardest difficulty. Once again the game doesn’t come to a screeching halt, but stutters are noticeable to an observant eye. As a note, I’ve tried using compound primitive colliders and this didn’t have any appreciable effect on performance, if anything performance was almost exactly the same. The most complicated Mesh Collider has only 28 faces ( using mesh colliders for more accurate collisions since object’s have fairly random shapes ). I realize that performance optimization has it’s cap with much higher poly numbers so having 28 faces doesn’t matter compared to something that has a much higher count.

Does anyone have extensive physics experience with Unity3D and Android / iOS to recommend some performance tips to further optimize this scenario? I have taken a deep look into profiling my game over the past week and when the Physics.Simulate spikes, my frame rate on my MBPro drops from 1500+ fps to 500 fps, and I’m having a hard time pinpointing the direct transgressors. I am making extensive use of OnCollisionStay / Enter / Exit calls, but when profiling these don’t seem to be the source of computation time under this group hierarchy, just generally under Physics.Simulate. Some direction or recommendations woud be greatly appreciated.

Firstly make 100% sure that it is the physics that is slow. The profiler can sometimes be misleading. Use the iOS Unity internal profiler on your device and see if it says the physics is taking all the time, you may find that on the device it might be waiting on the GPU or something else.

If it is the physics then try:
Do all your objects have Rigidbody components? If not try adding them as the physics system will assume these objects are going to change over time. If they don’t it’ll assume they are static objects and pre-calculate a buch of stuff to make them run ‘faster’ this pre-calculation itself is slow though and is intended to only be done at the start of the level once.

Another thing to try is activating and deactivating objects using layers instead of gameObject.active = false/true. To do this create a layer called Deactivate. Make sure no cameras render that layer and also in the Physics settings make sure no other physics layers collide with that layer. Then set that object and all its children to that layer instead of using gameObject.active. This will not remove and add the objects from the simulation every time they change layer instead the camera and physics simulation will just ignore them. The downside is that they will take up more overhead and other scripts on those objects will still be running when they are in the disabled layer unless you disable all of them manually as well, so if you have a lot of objects doing this then it my be slow because of all the overhead.

Hope this helps.