Optimizing Unity UI

This video has some excellent tips and it helped me make some simple optimizations to my UI in Space Engineers Calculator.

The short story:
I added sub-canvases and replaced Unity’s vertical layout group with my own implementation.

The long story:My application consists of mostly Unity UI. Most of the application runs reasonably well except for the item list.

The item list

The item list includes approximately 300 items which the user can filter by the category drop down or a text search box. When one of the larger categories like “Large Blocks” is selected, the list can be choppy/slow when the user is scrolling. I’ve tried a few times to increase the performance but it never felt as smooth as I would like.

Problem 1: My application was built with one canvas.Why is this a problem?: Whenever a UI component is set to dirty it’ll sometimes tell its canvas to update everything.Solution: Group related UI components together. If you have several UI components that update together, keep them on the same canvas. If you have a lot of static UI content (e.g., static background) keep it in another canvas. This way you don’t waste resources by updating your static background just because your dynamic content is part of the same canvas.

My application is split up between several main panels so logically I created a sub-canvas for each of these panels and I created one specifically for my item list.

Problem 2: I use Unity’s (Horizontal|Vertical) layout groups everywhere.Why is this a problem?: In the video it is recommended not to use them. Watch the video for the full reason.Solution: I removed the vertical layout group on my 300 item list, replaced it with my own version and immediately saw an improvement. I still have other UI elements using Unity’s layout groups but they don’t suffer the same performance issues as the item list did so I’m less inclined to update them.

My vertical layout code has two methods.

Get the children of this game object.

Layout the children whenever it needs to be updated. I’m utilizing Unity’s method: SetInsetAndSizeFromParentEdge to add the children starting from the top of the parent. It’s simple but it works.