はじめに
今回はStopCoroutineメソッドを使うにあたって注意しなければならないことについての記事になります!
コルーチンを止める方法として用意されているStopCoroutine
メソッドですが、実はこのメソッドには3つの呼び出し方(オーバーロード)があることをご存じでしょうか。
ただこのオーバーロードを正しく使わなければ、うまく動かないことがあるのです。
まずはその3つの使い方を紹介した後、注意しなければならないことについて詳しくみていきたいと思います。
また早く結論が見たいかたは、目次からオーバーロードの説明を飛ばしていただいても全然OKです。
Stringを使ったStopCoroutine
まずはstring
型の変数を引数にとるオーバーロードについてです。
using System.Collections; using UnityEngine; public class CoroutineTest : MonoBehaviour { private IEnumerator Start() { StartCoroutine("SomeCoroutine"); yield return new WaitForSeconds(1f); StopCoroutine("SomeCoroutine"); } private IEnumerator SomeCoroutine() { int i = 0; while (true) { i++; Debug.Log(i); yield return new WaitForSeconds(.1f); } } }
IEnumratorを使ったStopCoroutine
今度はIEnumratorインターフェイスを用いたオーバーロードについてです。
using System.Collections; using UnityEngine; public class CoroutineTest : MonoBehaviour { IEnumerator _someCoroutine; private IEnumerator Start() { _someCoroutine = SomeCoroutine(); StartCoroutine(_someCoroutine); yield return new WaitForSeconds(1f); StopCoroutine(_someCoroutine); } private IEnumerator SomeCoroutine() { int i = 0; while (true) { i++; Debug.Log(i); yield return new WaitForSeconds(.1f); } } }
Coroutineを使ったStopCoroutine
名前がややこしいですが、MonoBehavior.Coroutine
というクラスのインスタンスの参照を引数にとるオーバーロードがあります。
using System.Collections; using UnityEngine; public class CoroutineTest : MonoBehaviour { Coroutine _someCoroutine; private IEnumerator Start() { _someCoroutine = StartCoroutine(SomeCoroutine()); yield return new WaitForSeconds(1f); StopCoroutine(_someCoroutine); } private IEnumerator SomeCoroutine() { int i = 0; while (true) { i++; Debug.Log(i); yield return new WaitForSeconds(.1f); } } }
注意しなければならないこと
先程の3つのオーバーロードの使用例ですが、なにか違和感を感じた方がもしかしたらいるのではないでしょうか。
その違和感は、StopCoroutine
メソッドの種類によってStartCoroutine
メソッドの使い方を変化させていたところです。
実はこれは公式にも表記されているのですが、StartCoroutine
メソッドでstring型の引数を用いたら、StopCoroutine
メソッドの引数は必ずstring型の引数を用いなければならないのです。
これはIEnumrator
でもCoroutine
でも同様になります。
ダメな例
using System.Collections; using UnityEngine; public class CoroutineTest : MonoBehaviour { private IEnumerator Start() { StartCoroutine(SomeCoroutine()); yield return new WaitForSeconds(1f); StopCoroutine("SomeCoroutine"); } private IEnumerator SomeCoroutine() { int i = 0; while (true) { i++; Debug.Log(i); yield return new WaitForSeconds(.1f); } } }
これをやると永遠にコルーチンが止まりません…
さいごに
割と最初はこれは引っ掛かりやすい罠なような気がします。
もしうまく停止してなさそうな時は是非ここらへんをチェックしてみてください!