(need advice) Best way to boost performance for mobile

So I launched my game a few times on my phone and it plays but is a little laggy. I tried lowering material quality in settings and the shader. What else could I do to make it run smoother on mobile? Would lowering the light map resolution make a difference? That was my next option to try.

Search, there are numerous threads about in on those forums.
There is also documentation made by epic about mobile performance.

some tips for performance on mobile:

  • best is if you do not use lights at all, instead use fake light material (again some threads about it on forum)

  • do not use any dynamic lights, again same topics about fake light

  • use single atlas texture for all static meshes instead of separate skin texture for each mesh, something like this is done for topdown scifi mesh set (on marketplace)

  • do not use transparent materials, instead use unlit additive

  • watch shadow map sizes if you use static light

  • low poly meshes

  • use fewer but bigger meshes (this works much better if you do not use lights)

  • do not use “event tick”, instead in some “global” blueprint (i wish we had one trully global bp class) create dispatcher (i call it pulse), which you call every 0.2 seconds (it was proven just like FPS that this is around minimal frequency that our brains do not notice). Everything that you usually do on tick do rather on that pulse.

  • if you have more than 30 actors that use tick (or pulse) you need to rethink your code,

  • create and destroy actors around player during runtime. Make some manager that at begin play stores all actors from map and spawns/despawns them in runtime. This helped me with my endless spess shooter game.

Awesome thanks. I’ll look for some of those threads. And I actually do have event tick. I’m making an endless runner as well. I will try that dispatcher “pulse” you mentioned.

Since around 4.9 - In your blueprint parent ‘self’ component in the detail panel there is some parameters: Actor Tick. Here you can specify the tick interval (secs) the the event tick should use in that blueprint :wink:

https://www.youtube.com/watch?v=dl7IGBqymb0 check out this talk that CCP did talking about gunjack performance. This one was good too https://www.youtube.com/watch?v=Rtzi4SRbDTc this whole conference had a bunch of good stuff.

Are you spawning a lot of actors? There is a cost to that, consider making a pooling system

Check out your physics actors and collisions too.
Try implement custom collisions for maximum of your actors.
Have very low physics collisions.
For a example a vehicle at the min will have 5 collisions.
One for root & rest for tires(assuming you intend to have 4 of them, :wink: ), this will soon become expensive once you have more than a single vehicle, plus it’ll cost you a lot of FPS.
Try to rethink your actors if you are using too much physics.
Again, you’ll find a lot of talk on that one.
Learning methodologies from other engines might also help in this scenario :wink:

Oh great, indeed. Then all is needed is some centralized way to tell them all their update speeds (i am lazy and do not want to edit every blueprint class manually).
Pulse still has its use, because you want your stuff to slow down when you pause game.

Stuff I found out to influence gameplay in a major way:

  • Vertices amount of actor. (From own searching I found that 50.000 vertices would be max (on screen during any given time), but in practice I found out that 2.500 (on screen during any given time) can already become challenging for a device to render without issues)
  • Texture maps. 1024² seems to be the highest tier without losing to much performance. 2048² is a big “Hmmmmm, do I need it?”
  • Music/Audio samples. From own expierence, going for High Quality sound is nice, but it’s a eater in performance. For myself I figured out sampling rates of 80kbps @ 22.050Hz is more then enough for the little speakers. Higher is nice but larger files will take more storage anyways in the APK/OBB file. 96kbps @ 44.100 Hz = CD quality (as reference).

@Amsanity
> but in practice I found out that 2.500 can already become challenging
Really? you missing a zero there right? :wink:

I am using LDR and have all post processing turned off (no bloom sniff).
using ‘stat rhi’ / ‘stat fps’ tells me I am drawing 65K triangles / 150 draw calls comfortably on low end GPU chipsets (eg. Adreno 305/Mali T720) - this is will a reasonable amount of translucent materials.
My target is only 30fps, not 60fps and so must complete the frame in around 32milliseconds rather than 16milliseconds - I am seeing 16-25milliseconds depending on the device.

The biggest hit I found was resolution/fillrate (which is device specific).
Current low end GPU chips seem designed to work at 800x480 / 960x540, but manufactures sometime peer these chip with 1280x720 screen for marketing reasons.
1280x720 is almost double the pixels of 960x540 (do the math).
For devices with low end chipsets and high res screens you really need to set r.MobileContentScaleFactor 0.8 or 0.5 to make anything playable.

Unfortunately fixing this means writing a custom AndroidDeviceProfileSelectorModule to find these devices and push them to a low resolution.

You no longer need to write code to extend the Android device profile system; it can use regular expressions to assign them. Looks at the [/Script/AndroidDeviceProfileSelector.AndroidDeviceProfileMatchingRules] section in Engine/Config/BaseDeviceProfiles.ini for examples.

The actual profiles can be edited in the editor under Window->Developer Tools->Device Profiles.

is it possible to change r.MobileContentScaleFactor at runtime? I tried doing it with console… all it did was break my UMG :S I’d like to give my users a slider or something to change performance

What I’d really like is somehow to do this - unity performance technique - low res rendering of low poly things - possible to replicate in UE? - Rendering - Unreal Engine Forums

r.MobileContentScaleFactor is applied very early in the startup and isn’t checked again. I’ll see what can be done but I’ve seen some device drivers fail to properly resize the buffer without a full teardown and restart.

> You no longer need to write code to extend the Android device profile system; it can use regular expressions
Yes and that is appreciated, however what I am describing is a slightly specialised case:
The rule needs to match two things ‘native resolution total pixels > X’ (which isn’t currently exposed) AND ‘known low end GPU chipset ID’.
Am I missing something obvious? I wrote my own Frankencode to do this, but its not well tested or particularly future proof.

Admittedly I’m not sure how many of these mutant (high resolution, low end chipset) devices are out there.
Unfortunately one of the Android devices in front of me has this problem and r.MobileContentScaleFactor makes the difference between playable and not.

More general advice:* if you have performance problems, try dropping r.MobileContentScaleFactor to see if this makes a huge difference to the frame rate.*

Wow, there’s a ton of great info in this thread… thanks everyone for sharing! I will definitely be referring to this thread as I develop my own mobile game. I’m currently optimizing my character’s morph targets, and was wondering if unused/inactive morphs present in the character’s data will slowdown gameplay performance on mobile? Only the “blink” morph would get called 90% of the time. I’m also wondering if there’s any performance benefit to having the “blink” action contained INSIDE the idle cycle / walk cycle, rather than calling it separately through Blueprint randomly. Thanks for any tips on this. That is greatly appreciated!

~Adam