- Home /
Polygon Collider 2D causing FPS drop on android build
Edit:
After some "investigating" following @sacredgeometry and @TimBur responds I looked into profiler and found out that the problem is actually in Polygon Collider 2D that is on the sprite of my cave so the Object Pooling is not really the problem, Polygon Collider 2D is.
This is my sprite for the cave map:
And this is that sprite with Polygon Collider 2D:
So, does anyone know if there is any solution to this or Polygon Collider 2D is just to much for something like this? Anything else I can use to put collider 2D on something like this sprite?
Old question: Hello, I made a simple 2d game where I have a Player character made out of few sprites and the terrain made of out two sprites that are making a map through Object Pooling.
When I disable Object Pooling script the game runs flawlessly but with the Object Pooling script enabled the game runs poorly because of the FPS drop. Before I start the game the FPS is fine, when I hit Play and Object Pooling starts FPS drops and when the game is over (Object Pooling gets disabled on game over) the FPS is fine again.
I only made Object Pooling because people told me not to use Destroy because that will slow my game and now Object Pooling is slowing my game.
The sprites that are in the Pool I made in Photoshop and simply put them in the project, I didn't lower the quality of those sprites so I don't know if that may be the problem?
Anyone know what am I doing wrong?
This is my script:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class CavePool : MonoBehaviour
{
public int cavePoolSize = 5;
public GameObject CavePrefab;
public float spawnRate = 3f;
public float caveMin = 2f;
public float caveMax = -2f;
private GameObject[] caves;
private Vector2 objectPoolPosition = new Vector2(-20f, -20f);
private float timeSinceLastSpawned;
private float spawnXPosition = 12f;
private int currentCave = 0;
void Start ()
{
caves = new GameObject[cavePoolSize];
for (int i = 0; i < cavePoolSize; i++)
{
caves[i] = (GameObject)Instantiate(CavePrefab, objectPoolPosition, Quaternion.identity);
}
}
void Update ()
{
timeSinceLastSpawned += Time.deltaTime;
if (GameManager.instance.gameOver == false && timeSinceLastSpawned >= spawnRate)
{
timeSinceLastSpawned = 0;
float spawnYPosition = Random.Range(caveMin, caveMax);
caves[currentCave].transform.position = new Vector2(spawnXPosition, spawnYPosition);
currentCave++;
if (currentCave >= cavePoolSize)
{
currentCave = 0;
}
}
}
}
Have you looked at the profiler to see what is causing the performance to drop because pooling done properly should only cause performance decreases if your objects are massive i.e. you are loading some sort of large binary data like videos into memory for each of them (or you have done something really wrong) either way in nearly all cases that has less to do with pooling and more to do with badly thought out/ written code.
Hey mate, I figured it out through profiler. I updated the question so you can see what I found out above.
Answer by Llama_w_2Ls · Jan 02, 2021 at 08:27 AM
You could use an edge collider 2D, and __draw__the collider yourself, making it less detailed and less accurate, but a lot less, and therefore better, performance-wise. @Brijac
I wanted my collider to be perfect, if I made it less accurate the player would sometimes touch the sprite of the cave and avoid death or he would die without touching the sprite if I put collider outside of the sprite area.
So I made exactly the same shape of collider with Edge Collider 2D to test it and it runs smoothly. Didn't even know I can make the same thing like Polygon Collider 2D with Edge Collider 2D.
I guess Polygon Collider in a shape like $$anonymous$$e is too much for mobile phones.
Thanks man
Answer by TimBur · Dec 31, 2020 at 02:21 AM
With object pooling, there are tradeoffs, so it isn't always the right choice. When you create a pool, it saves you CPU cycles, because the Unity engine doesn't have to spend time creating and destroying objects. The cost is that object pooling requires more memory. Instead of having only exactly as many objects as you need, you will have a full pool of objects. So if your objects are big, and your pool is big, you may get some slowdown because of memory management issues, because the system memory is over-full.
That said, a pool of 5 small cave-sprite-objects doesn't seem like it should be causing you problems. There may be something else going on. Some alternate thoughts:
How many instances of your CavePool script are in your game? Do you have just one CavePool with just 5 caves, or do you have many CavePools of many caves?
Your CavePool script looks like it's doing the right things, but there may be some subtle error that we're both missing. Adding some Debug.Log statements to CavePool may help you understand your script better, and either prove that it's working right, or discover where it's going wrong.
Object pooling is most helpful when you are creating and destroying bunches of objects each second (e.g. bullets, particle systems, etc.). In that situation, the pooling lets you avoid 100's or 1000's of calls to Instantiate and Destroy. You don't seem to be in that situation. In your situation, the CavePool script creates just one cave every 3 seconds. So switching to object pooling doesn't save you much in Instantiate / Destroy calls. If this CavePool script is really causing problems, and you can't figure it out, and you don't have many more caves that this script suggests - you could go back to not-pooling, and be totally fine.
The memory overhead of most objects is negligible though. So there is actually rarely a case for not pooling objects. That and there are ways to reduce memory overhead if necessary. I dont think I have ever got to a point in any of my games where ram was a limiting factor though.
Its not just saving on CPU cycles its about having more control over your applications performance as there is an inherent cost to running GC and you dont really have any control when it happens and for any sort of application that has a contract to supply something in a specific and every decreasingly short window, that isnt ideal.
Pooling shouldnt be causing performance problems unless it has been implemented incorrectly and that isnt a pooling problem, thats an implementation problem.
Yeah you're right. It's just a prefab that is in the Pool that has Polygon Collider 2D but I don't know what else I could use to make collider on such sprite like $$anonymous$$e.
Hey mate.
Only one instance of my CavePool script is in the game. There is just one CavePool with just 5 caves.
Yeah I used Object Pooling because sprites of Cave Top and Cave Bot would appear and destroy a lot if the player gets too far in the game so I didn't want GC to get too big.
The problem is in the Polygon Collider 2D I used to make colliders on my cave sprites. I updated the question above if you wanna check it out.
Thanks
That's a pixel-perfect Polygon Collider, with lots of triangles, and it will take some significant CPU cycles to handle. Even so, if you only have five caves, I wouldn't have expected a performance issue. But yes, you can simplify that collider to improve performance.
Open the inspector panel for your prefab, and look at the Polygon Collider component. Click the 'edit' button. Use ctrl-click on lines to delete most of your polygons. Then use left-click and drag to re-build the collider in a simpler form. Probably a house shape would be fine - a box at the bottom with a roof on top.
I'll be curious to know if that helps. Good luck!
Your answer
Follow this Question
Related Questions
Grass + lighting? 0 Answers
FPS drops with unity pro water 0 Answers
SphereCast againt Terrain collider 0 Answers
Collider Movement Script and Physics.Simulate FPS Drop 1 Answer
FPS drop when moving against objects 0 Answers