Corotine Not Working After Reloading the Scene

Hi guys,
I am working on Tower Defense game. When i run the game, only first time coroutine works. when i reload the Scene (main scene to main menu then main menu to main scene) the coroutine just stop working. First i thought the whole script isn’t working then adding some more stuff in same script i realize that script is working fine but only coroutine just stop i don’t know why.

I already check these solutions:

  • Adding Time.timeScale = 1f in Game Manager and in this Script in Start Method.
  • Checking Project Setting/Time (Time Scale is still 1).

Wave Spawner Script:

using System;
using System.Collections;
using System.Collections.Generic;
using System.Security.Cryptography;
using UnityEngine;
using UnityEngine.UI;

public class WaveSpawner : MonoBehaviour
{
    public static int enemiesAlive = 0;
    public Wave[] waves;
    public float timeBetweenWaves;
    public Transform spawnpoint;
    public Text waveIndexText;
    public Text countdownText;
    public GameObject countdownPanel;
    public GameManager gameManager;

    private float countdown = 3.5f;
    private int waveIndex = 0;

    private void Start()
    {
        Time.timeScale = 1f;
    }
    private void Awake()
    {
        StartCoroutine(CountDown());
        this.enabled = true;
    }
    // Update is called once per frame
    void Update()
    {
        if (enemiesAlive > 0)
        {
            return;
        }
        if (waveIndex == waves.Length)
        {
            gameManager.WinLevel();
            this.enabled = false;
        }
        if (countdown <= 0f)
        {
            StartCoroutine(SpawnWave());
            countdown = timeBetweenWaves;
            return;
        }
        //countdown = Mathf.Clamp(countdown, 0f, Mathf.Infinity);
        waveIndexText.text = "WAVE - " + Mathf.Round(PlayerStats.waves).ToString("00");
    }
    IEnumerator CountDown()
    {
        Debug.Log("CountDown Start");
        while (countdown > 0)
        {
            countdownPanel.SetActive(true);
            countdown -= Time.deltaTime;
            countdownText.text = countdown.ToString("0");
            yield return 0;
        }
        countdownPanel.SetActive(false);
    }


    //This coroutine is stop working after reloading the scene
    IEnumerator SpawnWave()
    {
        Debug.Log("Spawn Wave");
        Time.timeScale = 1f;
        PlayerStats.waves++;
        Wave wave = waves[waveIndex];
     
        //enemiesAlive = wave.enemyCount;
        for (int i = 0; i < wave.enemy1Count; i++)
        {
            SpawnEnemy1(wave.enemy1);
            yield return new WaitForSeconds(1f / wave.enemy1SpawnTime);
        }
        for (int i = 0; i < wave.enemy2Count; i++)
        {
            SpawnEnemy2(wave.enemy2);
            yield return new WaitForSeconds(1f / wave.enemy2SpawnTime);
        }
        waveIndex++;
    }



    void SpawnEnemy1(GameObject enemy1)
    {
        Debug.Log("Spawn Enemy 1");
        Instantiate(enemy1, spawnpoint.position, spawnpoint.rotation);
        enemiesAlive++;
    }
    void SpawnEnemy2(GameObject enemy2)
    {
        Debug.Log("Spawn Enemy 2");
        Instantiate(enemy2, spawnpoint.position, spawnpoint.rotation);
        enemiesAlive++;
    }
}

Game Manager Script:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class GameManager : MonoBehaviour
{
    public static bool gameIsOver;

    public GameObject gameOverUI;
    public GameObject completeLevelUI;

    private void Start()
    {
        gameIsOver = false;
        Time.timeScale = 1f;
    }
    // Update is called once per frame
    void Update()
    {
        if (gameIsOver)
        {
            return;
        }

        if(PlayerStats.health <= 0)
        {
            EndGame();
        }
    }
    public void EndGame()
    {
        Time.timeScale = 0f;
        gameOverUI.SetActive(true);
        gameIsOver = true;
 
    }
    public void WinLevel()
    {
        gameIsOver = true;
        completeLevelUI.SetActive(true);
    }
}

Post scripts using code tags.

Otherwise, did you try adding a bunch of debug.log calls and see what does and doesn’t run? Did you notice any console errors?

Coroutines live and die along with monobehaviours that started them.

When you ‘reload’ a scene, effectively everything gets destroyed and re-instantiated. Any coroutines that were started by these objects will be killed.

So most likely you will need to restarted the coroutine.

yes i add some Debug.log and Every functions works fine except one Coroutine (Spawn Wave) in Wave Spawner Script

i have more then one coroutine in Wave Spawner Script and after reloading the scene every corounine works fine excepts one (SpawnWave)

Why do you do this.enabled = true; immediately after? Awake doesn’t run unless the object is enabled, so it doesn’t make any sense to call that. If your object is disabled, it’s not going to start your coroutine either since it’s in Awake.

so i have to move this line of code in start method?
i have to disable this script after completing the level / winning the game and enable it when restart the level or next level

or what is the best solution to not spawn enemies when you won or loss the game/level

The thing is, Awake doesn’t run if the object were disabled at the start of the scene. So, calling enable in Awake from a disabled GameObject doesn’t make sense. There is no reason to call enable at all since you left the scene and reload it.

Hearing you say you need to enable it makes me wonder, if this script on a DontDestroyOnLoad gameObject?

public static int enemiesAlive = 0;

Probably your issue. Did you debug this value? Since it’s static, if you reload the scene, this value may still be whatever it was when you lost. Which is why I said insert a bunch of debug calls.

1 Like

i remove these 2 lines
this.enabled = true;
this.enabled = false;

from the script and still enemies didn’t spawn after reloading the scene

yes enemies still alive after reloading the scene :frowning: but games object(enemies) didn’t showing in the scene after reloading the scene

Thank You i found the issue and exactly this is the issue after reloading the scene enemies still alive.

so i put this code in Awake Method and Boom:
enemiesAlive = 0;

Thank You again

1 Like