Im optimizing my game for mobile. For that reason a low amount of batches is important. By using Frame Debug I found out that for some reason the Draw Mesh Node command is performed for every single node eventhough the nodes are static and have the same material as far as I understand. The frame debugger says that the objects cannot be batches because the "Objects have different materials". I dont get why and how to fix that. The nodes are all based on a prefab of them. The only thing that is different between them is their position. Please help
The Frame Debug Window:
Prefab for every node:
Example for one of the nodes in game (ONLY their position is different):
Problem solved after 2 days of being sad and watching every graphic performance tutorital on youtube.
Basically I needed to change every .material code to .sharedMaterial because for some to me unknown reason unity creates a copy of the material when using .material, after which each node got its own material. For that reason the performance was so bad. Now it works and my live quality has increased, since everything gets batched, reducing the draw calls from 300 to 10 :)
I hope future readers are helped by this!
Related
I have a 2d project that started running extremely slow. I've tried to backtrack what I did but I can't remember what exactly happened that caused this, as it was running perfectly at one point. Here's a screenshot of the profiler:
What I've tried:
Updating my GPU to the latest version
Updating Unity to the latest version
Restarting the editor multiple times
Restarting my PC multiple times
Lowered the framerate via custom interaction mode
I'm quite new to Unity, and quite frankly I'm very lost right now. I've been Googling this for hours now. Any help is greatly appreciated.
Screenshot of profile in hierarchy view:
There should be smth with your grid or tile map, try to turn off those components. If fps raises, try to recreate tilemap/grid
1119.19ms is a solid second meaning you get less than 1 FPS.
For 60 FPS, you should not use more than 16,666ms.
Use the Profiler. (Window -> Analysis -> Profiler) it will tell you what takes up time.
Enable the "Stats" in Game View. For pc, Triangles should be below 6 Million and Batches (drawCalls) should be lower than ~4000 preferably. These numbers are purely for reference on high-end CPU and GPU for a 3D Game, but if you have a BIG difference you should look into that (Like 60k Batches or 20M Triangles would be BAD). GPU Instancing can lower DrawCalls. Making all the non-moving things static in your scene will help as well. Re-Use materials as often as you can. But the most important thing: Profile. You need to know your bottleneck.
You can manually boost performance using simple script
void Start()
{
// Make the game run as fast as possible
Application.targetFrameRate = 300;
}
I have a problem on some Android devices with the particle system's rendering (weirdly enough the problem seems occur on devices with higher capabilities). The problem occurs when mesh based particles (Renderer/Renderer Mode/Mesh) are being rendered. It seems like the meshes that are being spewed out and slowly shrunk with time are being reduced ("reverse-tessellated") which results in a nasty visual effect. Does anyone know what might be the cause of this?
UPDATE: One thing that I've noticed is that with time - the longer the gameplay - this problem is getting worse.
UPDATE: What I've tried is to make one particle system bigger (around x5 times) in order to check if it will have any effect on it's rasterization. Normally particles are sized down from 1 to 0 based on their life-time. What I've noticed, after sizing them up, is that the problem does not occur anymore.
UPDATE: Visualisation of the problem:
Properly rendered:
Improperly rendered:
I was able to track the issue down. It turned out to be a problem within a toon shader I wrote while a go. All the things I've noticed are valid but unfortunately it took some time to put me on the right track.
Taken from Unity's documentation
The half and fixed types only become relevant when targeting mobile
GPUs, where these types primarily exist for power (and sometimes
performance) constraints. Keep in mind that you need to test your
shaders on mobile to see whether or not you are running into
precision/numerical issues.
Unfortunately for me, as it cost me quite some time, I've used half3/4 values with POSITION semantics which caused some numerical precision issues on some Android devices (in this case the particles were getting smaller and smaller - size 0 to be exact). As a general rule, from what I've read in Unity's documentation, float3/4 should always be preferred in conjunction with POSITION semantics.
I'm making my first game with Swift and SpriteKit and have noticed that my game quickly approaches 100% CPU use. I have been posting a lot about this recently, but here I'm now I'm now attempting to pull it apart to determine where my problems are. I originally thought my problem was with instantiating new enemies, so I removed everything but the small user-controlled spaceship and its shooting functionality. However, I'm still hitting 100% after a couple minutes of "play". I'm using the time-profiler instrument to try and figure out whats going on but I'm having trouble. I've broken up the time line:
Here is the first subgraph when the user clicks a homeScene button to enter the GameScene.
I'm not entirely sure what the red and yellow "Heaviest backtraces" with 3256x and 861x respectively mean, but from tutorials I've seen I would imagine that they are abnormally high. Here is the Call Tree as well:
I'm also not entirely sure why the controller textures would be using so much as they are simply setting two textures in the file right before the GameScene class:
let controllerBaseTexture = SKTextureAtlas(named:"Sprites").textureNamed("controllerBase")
let controllerHandleTexture = SKTextureAtlas(named:"Sprites").textureNamed("controllerHandle")
class GameScene: SKScene, SKPhysicsContactDelegate {
Then here is the Call Tree when the game starts and when the CPU reaches 100%:
I'm also confused about what "UnsaveMutableAddressors" are, as I see them very commonly when trying to debug this code.
I know this is a lot, but I'm not sure where to begin. Any suggestions would be awesome. I would also like to know if there are good resources on how to interpret this better because I've gone through a handful and I'm still very stuck.
Thanks for any help!
The profiler shows it's something in your update method for your gameScene. Keep in mind this gets ran around 60 times per second so you don't want to do anything extremely heavy there.
I am making a app which draws continuous lines like a snake using Unity and SKSpriteKit (Obj-C) in Xcode (I’m making 2 versions of the same app in both):
http://i.stack.imgur.com/qA1zk.png
http://i.stack.imgur.com/484kj.png
http:// i.stack.imgur.com/QTEkC.png (Apologies for the image posts. I can't post an image/more than 2 links)
If you’ve ever heard of a game called Curve Fever, what I’m doing here is quite similar to it. I’m controlling the direction of the end of the line with the arrowkeys, whilst the end of the line automatically moves forward every frame creating an image like the one above.
However, from the 3 screenshots above, it is quite obvious that my program isn’t very efficient - every frame, I add a circle sprite to the SKScene in the place where my moving sprite is, which is why, after a while, there are over 1000 nodes on the screen, and the energy impact/memory/cpu is very high… Not ideal.
So now I’m looking for better ways of drawing the line on the screen without drawing thousands of nodes.
A while ago, a friend talked to me about how he made a similar app in GameMaker (which I have no knowledge of how to use). When I asked him how he rendered the line, he said he created something called a “surface”, and when anything moved on that surface, the old position of the sprite would still stay there - which would create lines if a circle moved across the surface.
He was rather vague about this, and I tried to do some research later, but with no success. I couldn’t find anything relevant about continuous lines, surfaces and GameMaker, Xcode or Unity.
If someone could come up with a solution like my friend was talking about, for Xcode/Unity - preferably both (or if someone could tell me what he was talking about for GameMaker), then I’d be grateful, as this would optimise my game and reduce the severe lags I get after around 30 seconds.
Also, I’d be grateful if anyone could suggest alternative solutions to this, too.
I'm using GameMaker but I have no knowledge of Xcode or Unity. I can't help you directly but I can explain GameMaker surfaces.
Surfaces in GM are objects where you can draw on instead of directly drawing on the screen. Later you can draw the surface to the screen. The main advantage of it is that you can store a surface and for example draw it again in another tick, while the screen is redrawn in every tick, or that you can change it over time.
Surfaces are basically just bitmaps where you draw on. That means it wouldn't be hard to do the same in any other environment. Most other libraries/APIs call it canvas.
In your example you would draw one circle to the bitmap in each tick and then draw the whole bitmap to the screen.
A related topic is destructible terrain as it is discussed here: https://gamedev.stackexchange.com/questions/6721/implementing-a-2d-destructible-landscape-like-worms
Our first game is about to go live. We have found that the performance of sprite kit is reasonably good. We are moving hundreds of sprites around and have effect nodes and sounds. However you must not dare to set the score. The SKLabelNode is very slow.
after running diagnostics it was found that the following code was the culprit.
scoreLabel.text = [NSString stringWithFormat:#"Score: %d",my_score];
In the diagnostic tool the setText command was showing as the most expensive. We even made sure that it was not being called that often. It still resulted in a lag causing the sprites to jerk/jitter/hickup. Once we removed the line...we got smooth motion.
If we are not able to use the SKLabelNodes inside the game scene, what other options are there?
Be careful you aren't loading the entire font family.
If I load "Chalkboard SE" it will take 4-6 seconds, and appear to work.
But if I load ChalkboardSE-Regular , it's virtually instantaneous ~100ms or less.
Once it's added to the scene, subsequent calls are very quick. But if you transition to another scene, it might re-load, so do it early.
I did some testing with font families first, and the results are pretty catastrophic. Caching strong references doesn't help. https://gilesey.wordpress.com/2015/01/14/ios-spritekit-font-loading-times-of-sklabelnodes/