Bootstrap

【Unity实战】yield return null还是WaitForEndOfFrame

当在Unity中编写协程(尤其是协程套无限循环)时,常常会用到yield关键字来控制协程的执行流程避免程序假死。以下是常见做法:

yield return null

当使用yield return null时,协程会在下一帧继续执行。这意味着协程将暂停一帧,然后在下一帧继续执行。使用yield return null可以在每一帧之间进行操作,比如更新游戏对象的位置、旋转或者其他计算。

IEnumerator MyCoroutine()
{
    while (true)
    {
        // Do something
        yield return null;
    }
}

yield return new WaitForEndOfFrame()

与yield return null不同,yield return new WaitForEndOfFrame()会等待当前帧的渲染完成后再继续执行。这意味着协程会在当前帧的末尾执行,通常用于在所有渲染操作完成后再执行一些操作。

IEnumerator MyCoroutine()
{
    while (true)
    {
        // Do something
        yield return new WaitForEndOfFrame();
    }
}

区别总结

  • yield return null会在下一帧继续执行,用于在每一帧之间进行操作。
  • yield return new WaitForEndOfFrame()会等待当前帧渲染完成后再执行,用于在渲染操作完成后执行特定操作。

有趣现象

正如上文总结,一个在下一帧继续执行,一个是等渲染结束然后继续执行。如果读者还是没什么感受的话,可以尝试写两个协程分别使用上文所提到的两种等待方式(最好留一个log输出),然后在编辑器执行。

运行过程中,尝试来回切换Scene和Game视图,看看log输出有什么变化。注意不要把这两个窗口独立出来,否则俩视图永远都是活动状态。

在这里插入图片描述

理论上你应该会发现当你切换到Scene视图时,你的WaitForEndOfFrame会卡住,永远不会启动新一轮循环;而使用null的部分却正常进行新一轮循环。

所以如果你遇到切后台或者编辑器切视图后协程暂停的表现,多半是WaitForEndOfFrame卡住了。如果代码和渲染有很强关联性,那么请继续用WaitForEndOfFrame,否则使用null。

;