Spawn radom waves

Hi, I’m going trough the course, arrived to the balance and build lecture and I’m trying to polished the game. I would like to implement a random spawn of the waves I’ve created, but I’m not sure how to do this within the foreach loop we created in the course. Is there a way to do this implementation without rewriting the way in which the waves are spawning? Thanks for the replies.

Hi,

Welcome to our community! :slight_smile:

Without knowing how you wrote the random spawn, it is impossible to tell whether your solution is compatible with Gary’s.

The loop iterates over a list of objects. The order of those objects is predefined, which contradicts the idea of randomness. The only way to add randomness to the current solution without any modification of the SpawnEnemyWaves method is to randomise the list on start.

Is there any reason why you don’t want to replace Gary’s solution with your own?

Hi Nina, thanks for the reply! I haven’t implemented random spawn yet, I was just looking for a way to do it. I simply implemented wave generation as Gary showed. It’s not that I don’t want to replace Gary’s solution, I just don’t have a solution to replace it with :sweat_smile:
If the idea is to make it an “infinite scroller” arcade, if the waves were “predictable” by the player, after a short period of time the game would become too easy, unless you create hundreds of waves manually. Maybe, randomly generating waves out of 5 or 10 waves would make prediction more difficult and adds some complexity to the gameplay.
Do you think randomizing the waveConfigs list in the Start method is a good solution? I know there is no “good” or “bad” solution, I mean, is it optimized? I’m looking online for how to randomize a list in Unity but I can’t find an easy way to do it. Is there perhaps a method built into Unity?

No, I don’t think that. The reason is that I don’t like to manipulate the original data. However, you could simply create a second List or array variable. The type should be int because you could simply generate a list with indices instead of references to the objects.

Here is the idea in code:

List<int> waveIndices = new List<int>() { 5, 1, 4, 2, 2, 0 };

Well, the values are obviously hard-coded. How to populate that list at runtime?

  • Define how many waves you need.
  • Use that value in a for-loop.
  • Call Random.Range in each iteration step.
  • Use Random.Range to get an integer between 0 and the number of elements in the original list minus 1.
  • Assign the returned integer to the waveIndices list.

In Gary’s for-loop, you iterate over that list and get an object from the WaveConfigSO list with the current index.

Let’s say you successfully populated the list at runtime, and you have this now:

index 0 1 2 3 4 5
int 0 2 3 2 1 7

Let’s say the order of waves is this:

index 0 1 2 3 4 5 6 7
Object Wave1 Wave99 MyWave Wave4 Wave5 Wave6 Wave7 Wave100

You generate a list of indices to define a new order. Then you iterate over the indices list with a for-loop (see the i). And if you noted the data down in each iteration step, you would get a list like this:

i waveIndices[i] Wave
0 0 Wave1
1 2 MyWave
2 3 Wave4
4 1 Wave99
5 7 ??? (guess it)

This concept is better than manipulating the original data because you keep the original data. Also, if you want to modify the waves generator, you won’t have to rewrite the SpawnWaves method or anything else. All you would have to do is to rewrite the algorithm for populating the waveIndices list.

I hope that made sense. :slight_smile:


If you don’t need a list but just want to spawn waves forever, use a while-loop instead of foreach in the SpawnWaves method. In that while-loop, you call the Random.Range method as described above. You would not populate any list but spawn the current wave directly with a random index.

Thank you Nina, it’s all more than clear! I manage to have a random wave spawner :grin:.

Like you have said at the end of the message, I wanted to spawn the x waves I created, forever, in a random order. So to do this I was following your advice but didn’t quite get how to change the foreach loop with the while loop, but I came with the solution of delete the foreach loop and, since we are already in a do-while loop, just call the Random.Range and assign to an int variable, then assign the currentWave variable to a random item in the waveConfig list using that random int variable as index, the run the fr loop as it was before. Here’s the code that came out.

    IEnumerator SpawnEnemyWaves()
    {
        do
        {
            int randomIndex = Random.Range(0, waveConfigs.Count);

            currentWave = waveConfigs[randomIndex];
            Debug.Log(currentWave);

            for (int i = 0; i < currentWave.GetEnemyCount(); i++)
            {
                Instantiate(currentWave.GetEnemyPrefab(i),
                            currentWave.GetStartingWaypoint().position,
                            Quaternion.Euler(0, 0, 180),
                            transform);

                yield return new WaitForSeconds(currentWave.GetRandomSpawnTime());
            }

            yield return new WaitForSeconds(timeBetweenWaves);  
        }
        while (isLooping);
    }

I change the range with (0, waveConfig.Count) and not vaweConfig.Count-1 like you said because in that way this code was spawning all the waves but the last in the list, but maybe that line of code you provided was for the “fixed number of waves” implementation (?).

Anyway this seems to work fine but I would be glad if you could tell me any error o more optimized way to do this implementation in the coroutine.

Thank you very very much to follow me doing this thing! I really apprecciate! :smiley:

Good job! Your solution looks great. I’ve also noticed that you use a do-while-loop, which is fine if the loop is supposed to get executed at least once. :slight_smile:

(0, waveConfig.Count) is correct in this case because of Random.Range. The max value is exclusive but that’s true only for Random.Range. Other things might have a different definition. The last index in a list/array is count or length minus 1 because indices start at 0. My previous answer was a misleading in this respect but I’m glad you figured the solution out yourself.

1 Like

This topic was automatically closed 24 hours after the last reply. New replies are no longer allowed.

Privacy & Terms