yield return for Photon RPC Coroutine

Hi,

I am calling a photon RPC Coroutine from within another unity Coroutine.

I need the execution of the unity Coroutine to pause “i.e. Yield Return” until the Photon Coroutine has finished execution, but yield return does not work when calling a Photon RPC

In the code example below you can see how unity would ordinarily pause execution in the 2nd statement by using yield return StartCoroutine().

But how do I achieve the same for the 1st Statement where I call Photon RPC Coroutine?

    private IEnumerator GameLoop ()
    {
        // Start off by running the 'RoundStarting' coroutine but don't return until fin
        view.RPC("RoundStarting", RpcTarget.AllBufferedViaServer);

        // Once the 'RoundStarting' fin run 'RoundPlaying' but don't return until fin
        yield return StartCoroutine (RoundPlaying());

        // Once execution has returned here, run the 'RoundEnding' 
        yield return StartCoroutine (RoundEnding());

        // This code is not run until 'RoundEnding' has finished. 
        if (m_GameWinner != null)
        {
            // If there is a game winner, restart the level.
            SceneManager.LoadScene (1);
        }
        else
        {
            // If there isn't a winner yet, restart this coroutine so the loop continues.
            StartCoroutine (GameLoop ());
        }
    }

Well then, given the additional information:

What you are trying to do here does not work. There is no way to have a RPC “return” in a way that you can directly yield for it.

So what can we do instead?

What you need to implement here is some kind of “acknowledgement” which is sent from all players to the master. So you can still send the start command for your “GameStart” state but the state ends once the master player has received the “ack” call for “GameStarting” from all players in the room. Then you can send the next RPC out.

This for example could be done in a simple manner with a counter which is incremented by one for each “ack” message for the current game state:

 private int acksRecievedForCurrentState = 0;

 [RPC]
 public void acknowledgeState()
 {
       //increment acksRecievedForCurrentState 
 }

Given this you can then change your yield statement for:

 view.RPC("RoundStarting", RpcTarget.AllBufferedViaServer);
 yield return new WaitUntil(acksRecievedForCurrentState >= playernumberInRoom);
 acksRecievedForCurrentState = 0; // don't forget to reset once you enter the next stage
 view.RPC("RoundPlaying", RpcTarget.AllBufferedViaServer);

Let me know if that helped or something was unclear.

This works perfectly thank you!