- Home /
Delaying in for loop, Spawning enemies
Hello, I have code that spawns enemies in for loop. Problem is it spawns them all in one place, one solution is to offset spawning position.I did that at some extent, but script that would delay spawning in for random number of milliseconds would do a better job.
I couldn't make yield work, it did increase number of second for loop ran, but enemies still spawned for every
for ( counter=0; counter<currentWaveCount; counter++){ spawnOffset = transform.position;//reset variable to spawnpoint location spawnOffset.x += Random.Range(spawnOffsetMin, spawnOffsetMax);//randomize position of spawning
Instantiate(enemy, spawnOffset, transform.rotation);//spawn enemy
}
this is for loop I want to introduce time delay between spawns in.
this is whole code.
var waves : String[]; //Array of enemy waves, must be assigned through inspector view. each element of wave array must contain 3 numbers denoted by "," (comma). exm: 7,4,2. first number is time in seconds wave will spawn at, second is number of enemies to spawn in wave, third is randomizator to second number. var wavesDone : int = 0; //counter for how many waves were already spawned. var currentWaveTime : int;//extracting current wave spawn time from waves string array for easy of use. var currentWaveCount : int;//extracting current wave enemy count from waves string array for easy of use. var enemy: GameObject;//what enemy to spawn. var noMoreWaves: boolean; //boolean to disable spawnpoint after all waves were spawned var currentwave:Array ;//ID of current wave var counter: int; var spawnOffset: Vector3;//variable used to offset enemy position on X axis when Instantiate-ing it., var spawnOffsetMin: float=1.0; var spawnOffsetMax: float=2.0;
//this code adds icon to spawn point game object, to easily select in scene view function OnDrawGizmos() { Gizmos.DrawIcon(transform.position, "TG_EnemySpawner.tif"); }
//we prepare for next wave, extracting and reseting variables function NextWave() { if (wavesDone<waves.length){ //if waves already done are less then lenght of wave array currentwave = waves[wavesDone].Split(","[0]);//extracting variables from waves string for current wave currentWaveTime = int.Parse(currentwave[0]);//assigning current wave spawn time currentWaveCount = int.Parse(currentwave[1])+Mathf.Round(Random.Range(-int.Parse(currentwave[2]),int.Parse(currentwave[2])));//we assign number of enemies to spawn + random number between(-randomizator,+randomizator) (third number from waves string array) } else{ noMoreWaves=true;//if all waves were spawned disable spawner } } //funtion that spawns current wave of enemies function SpawnWave() {
for ( counter=0; counter<currentWaveCount; counter++){
spawnOffset = transform.position;//reset variable to spawnpoint location
spawnOffset.x += Random.Range(spawnOffsetMin, spawnOffsetMax);//randomize position of spawning
Instantiate(enemy, spawnOffset, transform.rotation);//spawn enemy
}
wavesDone++; // Get next wave information NextWave(); }
function Start() { NextWave();//get info for first wave }
function Update() { if (noMoreWaves == false){//not all waves were spawned if (Level_Attributes.gameTime >= currentWaveTime){//Timer is run from the start of the game, if time has come to spawn current wave SpawnWave();//spawn wave } } print(Level_Attributes.gameTime);//print timer for debug purphoses. }
Answer by Tuck · Feb 09, 2011 at 06:12 PM
There are a couple ways to do this, but I would actually shy away from using a for loop in this situation. One way would be to use Invoke to call a function that Instantiates an enemy, and that function Invokes itself until all enemies have been created. For example:
int iMaxEnemies = 5; int iTotalEnemies = 0; float fSpawnDelay = 5.0f;
void Start() { Invoke("spawnEnemies", fSpawnDelay); }
void spawnEnemies() { //Do your spawn offset stuff here Instantiate(enemy, transform.position /plus spawn offset/, Quaternion.identity); iTotalEnemies++;
if(iTotalEnemies < iMaxEnemies) { Invoke("spawnEnemies", fSpawnDelay); } }
Another way, which I would actually use instead, would be to create a timer to check if it is time to spawn a new enemy. The logic is very similar.
float fNextSpawn = 0.0f; float fSpawnInterval = 5.0f
int iMaxEnemies = 5; int iTotalEnemies = 0;
void Start() { fNextSpawn = Time.time + fSpawnInterval; }
void Update() { if(Time.time > fNextSpawn && iTotalEnemies < iMaxEnemies) { fNextSpawn = Time.time + fSpawnInterval; spawnEnemy(); } }
void spawnEnemy() { Instantiate(enemy, transform.position + offset, Quaternion.identity); iTotalEnemies++; }
Your answer
Follow this Question
Related Questions
trying to delay a loop using yield - not working 1 Answer
How do I put a delay in this script ? 1 Answer
delay first spawn 2 Answers
Classic Fireball Shooting Up Obstacle 1 Answer
Adding Delay to a for loop in C# 1 Answer