Search Unity

Discussion Coroutine only once

Discussion in 'Scripting' started by zedz, Feb 2, 2023.

  1. zedz

    zedz

    Joined:
    Aug 31, 2013
    Posts:
    254
    I'm literally using the Unity example and it only runs once

    https://docs.unity3d.com/ScriptReference/MonoBehaviour.StopCoroutine.html

    No Idea why this is not working as it should, note UPDATE is always getting called thus the object is always active.
    I see others on the internet often have this problem, but thats due to not having a loop, which you can see I have

    output
    Starting 1.004869
    a
    b
    Done 1.004869
    UPATE
    UPATE
    UPATE(and so on only UPDATE)

    Code (CSharp):
    1. {
    2. private IEnumerator                   coroutine;
    3.  
    4. void Start() {
    5.         print("Starting " + Time.time);
    6.         coroutine = WaitAndPrint(3.0f);
    7.         StartCoroutine(coroutine);
    8.         print("Done " + Time.time);
    9.     }
    10.  
    11.     // print to the console every 3 seconds.
    12.     // yield is causing WaitAndPrint to pause every 3 seconds
    13.     public IEnumerator WaitAndPrint(float waitTime)
    14.     {
    15.         print( "a" );
    16.         while (true)
    17.         {
    18.             print("b");
    19.             yield return new WaitForSeconds(waitTime);
    20.             print("WaitAndPrint " + Time.time);
    21.         }
    22.     }
    23.  
    24.     void Update()
    25.     {
    26.         print( "UPATE");
    27.         if (Input.GetKeyDown("space"))
    28.         {
    29.             StopCoroutine(coroutine);
    30.             print("Stopped " + Time.time);
    31.         }
    32.     }
    Actually I'm stumped, its not that difficult (its something obvious that I'm overlooking, it must be)
    Cheers zed
     
  2. halley

    halley

    Joined:
    Aug 26, 2013
    Posts:
    2,445
    Usually:

    Code (CSharp):
    1. Coroutine job = StartCoroutine(MyEnumeratorFunction(args));
    2. ...
    3. StopCoroutine(job);
    Edit: As you say, your code is almost identical to the example code. I just tried it on 2021.3 (LTS) and it worked as expected. I added your "a" and "b" printouts.

    Code (CSharp):
    1. Starting 0
    2. a
    3. b
    4. Done 0
    5. WaitAndPrint 3.000875
    6. b
    7. WaitAndPrint 6.03508
    8. b
    9. WaitAndPrint 9.036133
    10. b
    11. [spacebar pressed]
    12. Stopped 9.831909
     
    Last edited: Feb 2, 2023
    zedz and Bunny83 like this.
  3. PraetorBlue

    PraetorBlue

    Joined:
    Dec 13, 2012
    Posts:
    7,911
    Possibilities here as far as I can see are:
    - Time.timeScale is set to 0 (or something very small)
    - You haven't saved your most recent script changes
    - Your GameObject is being destroyed or deactivated
     
    zedz and Bunny83 like this.
  4. zedz

    zedz

    Joined:
    Aug 31, 2013
    Posts:
    254
    Thanks guys. I gave up trying to get it to work last night after the PC crashed
    https://forum.unity.com/threads/scr...failed-check-last-reply.1177181/#post-8777008

    @PraetorBlue none of these are what causing it.

    This morning I try it again, still not working, I try it on a completely different object in the same program, no doesnt work.
    I try it in another of my games (much simpler) it works!, so I'm assuming perhaps something in my settings or I'm doing something weird somewhere (this program is huge > 100k LOC)

    If I use InvokeRepeating("Test",3,3); then it does get called every 3 seconds
    so
    InvokeRepeating WORKS
    StartCoroutine NOT WORKING

    Compiler settings IL2CPP, faster runtime, Release using MSVC2019 for compiler (I do also have 2022 installed)

    I will use InvokeRepeating() for now even though from AFAIKS its not as good/performant but at least it works
     
  5. Bunny83

    Bunny83

    Joined:
    Oct 18, 2010
    Posts:
    4,005
    That's a red herring. You may disable / deactivate the object and immediately enable / reactivate it again. However the moment the script is disabled, a running coroutine would be stopped.

    So are you sure about that? Have you added the OnDisable callback to see if the object ever gets disabled? It it does, you can see the stacktrace to figure out from where it gets disabled.

    Your symptoms clearly show that the coroutine does get stopped at the first yield. So you should systematically rule out the causes that @PraetorBlue mentioned. To test for the other things, you could simply replace the yield return new WaitForSeconds with a simple
    yield return null;
    it's not affected by time / timescale. If it runs, you probably have a timescale issue. Try printing the timescale in the coroutine.

    Uhm, Unity compiles the script itself with its own compiler, usually Mono that ships with Unity. VS has absolutely nothing to do with it. It's just used as a code editor. Any settings inside VS has no effect on the project. The "csproj" file is ignored by Unity. Unity generates these so VS can properly work and show the files properly.
     
    PraetorBlue and zedz like this.
  6. zedz

    zedz

    Joined:
    Aug 31, 2013
    Posts:
    254
    Yes Bunny83 thanks, good thinking. I stuck a OnDisable() in there and yes it was getting called, so was able to trace back where this was occurring. So I should be able to fix this, cheers again.

    WRT the compiler (I have not looked into this, as I have 101 more important things to do on my list, i.e. stuff thats broken :))
    but when I do a build unity has been saying (ever since I installed 2022 maybe ~6 months ago) so I assumed ms visual studio was doing the compiling. But you're saying unity comes with its own c# compiler built in. OK cool.

    from unity console
    Note - C++ and not C#/mono

    I haven't looked into this, (like I said I have 101 more important things that need fixing and it works as is), need to run the environment vcbat maybe
     
  7. SF_FrankvHoof

    SF_FrankvHoof

    Joined:
    Apr 1, 2022
    Posts:
    780
    Check Edit -> Preferences -> External tools. It might still be set to 2019.
     
    zedz likes this.
  8. zedz

    zedz

    Joined:
    Aug 31, 2013
    Posts:
    254
    Yeah cheers I checked that, its been set to 2022 since about 6 months.

    I did upgrade last week from 2022.1.3 -> 2022.2.3 and it also still complained about 2019 when I done a build.
    I only upgraded cause I was hoping that d3d12 was gonna be functional, but performance was half compared to d3d11 plus there were graphical errors. (Also graphical errors were present in 2022.2.3 with d3d11) so I downgraded again to 2022.1.3.
    But no matter I'm not worried about this error 'warning: You are currently using Visual Studio 2019 to compile and link C++ code.'