Coroutine wait until a condition?

I’m making a Cutscene in a Coroutine, so I want to do something and then make the game wait until a continueCutscene bool is true, so it goes on with the cutscene, something like this

IEnumerator Cutscene()
    {
        //Cutscene Stuff
        continueCutscene = false;
        yield return new WaitUntil(continueCutscene == true);
        //More Cutscene Stuff and End the cutscene
    }

However, I don’t know how to do the syntax yield return new WaitUntil(continueCutscene == true); so the program actually waits for a condition to become true, how do I do that?

You need to pass in a delegate function into WaitUntil; the condition to wait for needs to be outside of the coroutine.
For example:

public class Example : MonoBehaviour {
   IEnumerator StartTask() {
      Debug.Log("Start");

      yield return new WaitUntil(SomeLongAsyncTaskOrWhatever);

      Debug.Log("Finish");
   }

   //Returns false while the task is still running, and true when it's finished.
   bool SomeLongAsyncTaskOrWhatever() {
      //etc..
   }
}

With the way you’re trying to structure your setup though, you can probably do something like this instead…

public class Example : MonoBehaviour {
   bool isCutscenePlaying;

   void StartCutscene() {
      isCutscenePlaying = true;
      StartCoroutine(Cutscene());
   }

   IEnumerator Cutscene() {
      while(isCutscenePlaying) {
         //Cutscene stuff.
      }
   }
}

…And then just set isCutscenePlaying back to false whenever the cutscene finishes.

I tried bringing my bool out of the Coroutine, but it doesn’t work. It tells me that I can’t convert from ‘bool’ to a System.Func. This is the code

//Start Cutscene
continueCutscene = false;
                    StartCoroutine(Cutscene());

IEnumerator Cutscene()
    {
        //Cutscene
        yield return new WaitUntil(continueCutscene);
        //Cutscene
    }

easier to do it like this

    IEnumerator Cutscene()
        {
            //Cutscene Stuff
            continueCutscene = false;

while(continueCutscene == false)  {
            yield return null;
}
            //More Cutscene Stuff and End the cutscene
        }

Yes, that code worked! I just changed the if to summarize it as if (!continueCutscene), thank you very much!!

//Useful when we want to hold a IEnumerator method which is using for/while loop until the passed "checkMethod" returns true
//It is needed coz in IEnumerator method we cant pass boolean variable by reference


using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using kFramework;
public class CoroutineLoopTest : MonoBehaviour
{
    // Start is called before the first frame update
    void Start()
    {
        StartCoroutine(WrongWayToPauseLoop());
        StartCoroutine(CorrectWayToPauseLoop());
    }
    // Update is called once per frame
    IEnumerator WrongWayToPauseLoop()
    {
        print("Start");
        int index = 0;
        while (index <= 20)
        {
            //This will not stop while loop or for loop
            yield return null;
            print("WrongWay Index= " + index);
            index++;
        }
        print("End");
    }
    IEnumerator CorrectWayToPauseLoop()
    {
        print("Start");
        int index = 0;
        while (index <= 20)
        {
            //Hold the coroutine loop until space button is clicked
            yield return WaitUntilTrue(IsSpaceKeyPressed);
            print("CorrectWay Index= " + index);
            index++;
        }
        print("End");
    }
    bool IsSpaceKeyPressed()
    {
        return Input.GetKeyDown(KeyCode.Space);
    }

       public IEnumerator WaitUntilTrue(Func<bool> checkMethod)
        {
            while (checkMethod() == false)
            {
                yield return null;
            }
        }


}

You are passing just a bool variable as a parameter to WaitUntil. That doesn’t work like that.
I had the same error and I solved it like the following.

  1. You may leave your code as is. Your continueCutscene variable it’s okay.
  2. Add the following line.
private bool CanContinueCutScene() => continueCutscene;
  1. Or alternativelly, add the following function, which it’s equivalent.
private bool CanContinueCutScene(){
    return continueCutscene;
}
  1. Change your line yield return new WaitUntil(continueCutscene); to the following:
yield return new WaitUntil(CanContinueCutscene);

That way, you are using your function as a way to “check” whether or not some condition has met.

The variable thing doesn’t work because is just something that stores a value.WaitUntil requieres something that can check the value of something, thus a function.

Very solid explaination, fitted to my brain. Thank you

Yes you need a delegate, a Func, not a bool.

I’m surprised no one has mentioned lambda functions. It’s much more concise.

// Change this
yield return new WaitUntil(continueCutscene == true);

// to this
yield return new WaitUntil(() => continueCutscene);

There’s no point in ever putting someBool == true. They always evaluate to the same thing.