- Home /
Using a pool of objects that will be spawned ONCAMERA and removed OFFCAMERA instead of INSTANTIATE & DESTROY (iOS)
I want to use a pool of prefabs that will be randomly spawned on (random) squares of my board every 4 and collected (and removed from the board) by my character.
The board has 48 tiles, one of which is constantly occupied by my character that moves on it. This leaves 47 tiles available for the spawned tokens to occupy.
My initial approach was instantiating and destroying these prefabs, which resulted in extremely low fps. This way I learned that this practice (frequent instantiating & destroying) is to be avoided in iOS games.
After asking lots of questions and posting here and in the Forum, what Im trying to do now, is use a pool of deactivated prefabs that will be activated when needed, instantly moved to a random tile on board (as If I instantiated them) and deactivated and removed from the board (as If I destroyed them), when my character collects them.
I use the following script, attached to an empty game object:
var popSoundAtSpawn: GameObject; //the sound that plays when a token is spawned var spawnObjects : GameObject[];// this is the Array comprised of tokens that will be randomly spawned var tilesArray : GameObject[];// this is the Array comprised of all squares of the board var tokensPool : GameObject[];//this is the Array comprised of 47 tokens that at maximum will be on board at the same time var spawningRate: float= 3.3; // every spawningRate seconds, one token will be moved on board var delayBeforeSpawningBegins: float =2;// when the level begins, it will wait 2" before it starts spawning tokens var emptySquares: int; var spawnSuccessful: boolean; var tokensSpawned: int=0;
function Awake(){ InvokeRepeating("Spawn", delayBeforeSpawningBegins, spawningRate); // make spawn a token every "spawningRate" seconds }
function Spawn(){ randomTileNumber = Random.Range(0,tilesArray.length); //this will choose a random tile of the board
randomTokenNumber = Random.Range(0,tokensPool.length); // this will choose a random token from the tokens Pool
var spawnSuccessful = false;
while (spawnSuccessful == false && (tokensSpawned-characterScript.tokensSwallowed)<47)) {// this makes sure that the tokens spawned minus the ones swallowed by my character are less or equal to my available board tiles, which are 48 (in total) minus 1 that my character occupies = 47. So the while's escape condition, will be met when the board is full of tokens
var placeToSpawn: GameObject = tilesArray[randomTileNumber]; //the position of one of the randomly selected board tiles. In that position will the token be spawned
var spawnedToken: GameObject = tokensPool[randomTokenNumber]; // this will pick randomly, one of the tokensPool Array's contents
if (placeToSpawn.tag == "EmptyTile" && spawnedToken.active == false){ // this checks if the selected tile is empty and if the selected token is one of the deactivated tokens that are still off-board and have not been moved on it.
iTween.MoveTo(spawnedToken,{"x":placeToSpawn.transform.position.x, "y": 0, "z":placeToSpawn.transform.position.z,"time":0}); //this will move the token instantly, on the randomly selected empty tile's position
spawnedToken.active = true; //the token will be activated
tokensSpawned ++; // the number of instantiated tokens will be increased
Instantiate(popSoundAtSpawn); // the spawning "pop" sound will be played
spawnSuccessful = true; // the while's escape condition will be met
}
}
}
What happens, is when I hit play, sometimes 5, sometimes 10 (at best) collectibles are activated and spawned in random positions (as expected) and Unity freezes. Am I getting into an infinite loop? Isnt this script a good way to have the token prefbs spawned and removed from the board?
Even if i simplify the "while" line like this:
while (spawnSuccessful == false ) {
I get the same freezing after 5-10 spawns problem. It seems like Unity freezes when it tries to randomly pick a token from the tokensPool, that has already been picked-spawned and is already on the board. I would expect it not to try to pick an already spawned token though, as I use:
spawnedToken.active == false
in the "if" statement.
Answer by · Jan 23, 2011 at 02:59 PM
I haven't tested this locally to confirm, but at a glance it seems that it would break as soon as it randomly selected an occupied tile, or a token that was already spawned.
This bit here:
var placeToSpawn: GameObject = tilesArray[randomTileNumber];
var spawnedToken: GameObject = tokensPool[randomTokenNumber];
is occurring inside the while
loop. If either randomTileNumber
or randomTokenNumber
are inappropriate (according to the following ifcheck), then it will hang infinitely. You can fix this by putting the Random.Range inside the while
loop.
There might be better approaches to this scenario, but this should fix your immediate problem - it's 2am here and my creative thinking is a bit zapped for the day.
Let me know if you have any troubles or questions. Cheers.
Goodmornig $$anonymous$$arowi (I guess it's next day in Australia by the time you're reading this). That was it, thanks a bunch for dedicating time to read this really long question!!!
Your answer
Follow this Question
Related Questions
Activating & Deactivating prefabs from a prefab pool VS simply moving them on and off-camera (iOS) 1 Answer
How To Disable A Prefab? 2 Answers
Activate/De-Activate? 1 Answer
Activate/deactivate all GameObjects with same tag c# 1 Answer
How do I re-link an object that has unintentionally become detached from prefab? 0 Answers