c#实现的协程样例代码: https://gist.github.com/liyonghelpme/87754c95e4a2d4e1f4c9git
c# 自己支持迭代器IEnumerator,能够封装函数的执行上下文,可是迭代器不支持嵌套迭代,而为了实现带堆栈支持的协程,须要对c#作扩展。github
Unity 中协程的嵌套形式以下: yield return StartCoroutine(IEnumerator);c#
为了嵌套协程须要保存协程调用的堆栈信息,而且在IEnumerator结束的时候,继续执行上一层的IEnumerator.函数
所以Unity 封装了一个类Coroutine, 该类中保存有当前IEnumerator 等待的下一级IEnumerator(waitingFor) 以及当当前IEnumerator 执行结束的时候所要调用的上一级IEnumerator(ContinueWhenFinished).协程
调用Unity StartCoroutine 接口对象
Unity 建立一个 Coroutine 协程对象, 并初始化协程中的迭代器接口
Unity 合适时机调用 协程中迭代器的 moveNext 方法生命周期
这时候 Unity获取迭代器的Current 返回值;若是返回值为NULL 则Unity将对迭代器的执行加入到下一帧的循环中,不然根据返回值不一样作不一样的处理。队列
若是返回值是一个new WaitForSeconds() 对象则将将协程加入到延迟回调队列里面;事件
若是返回值是另一个协程对象,则设置当前协程的waitFor 为这个新协程对象,而且设置新协程对象的ContinueWhenFinish 为当前协程。
Unity 提供 StartCoroutine 接口用于建立一个协程, 建立完协程以后,将会调用协程Run接口,执行一下协程,若返回NULL,则将协程加入到下一帧执行队列中,不然根据状况来作不一样的调度。
在初始化StartCoroutine 的时候会执行一次协程;以后根据协程执行的返回结果,来作不一样的调度; 返回NULL 调度下一帧继续执行;
返回另一个协程对象,则配置两个协程的关系,同时中止调度当前协程,将子协程加入到调度队列里面;
返回Wait 则将当前协程加入到等待调度队列里面。
协程生命周期和Monobehavior 相绑定,当GameObject SetActive False的时候,全部协程都会中止。
在建立协程的时候,若协程将会加入到 Monobehavior的ActiveCoroutine 活跃协程列表中,接着执行一次协程;若协程本次执行完以后没有yield调用,则表示协程生命周期结束,以后调用的协程清理函数会清理掉协程。
不然协程会加入到延迟调用队列中。
当协程须要等待其它事件,或者其它协程的时候,协程引用计数+1,这样协程会在其它事件执行完以后,才检测是否执行清理工做。