跳到主要内容

生命周期与帧循环:代码什么时候执行

后端代码常由请求或消息触发。Unity 还会不断推进帧循环。理解“代码什么时候执行”,比先背很多 API 更重要,因为许多偶现错误本质上是时间顺序和对象寿命不匹配。

游戏逻辑与渲染帧持续推进,固定物理步可能在一帧中执行零次或多次
观察一帧里的处理顺序。固定步长的物理模拟与渲染帧不是一一对应关系。

先认识这些回调​

回调先这样使用常见误解
Awake准备自身组件和内部状态假定其他对象已准备好
OnEnable注册需要随启用生效的事件重复注册却不注销
Start在首次帧更新前完成启动逻辑当作每次启用都会调用
Update处理逐帧逻辑把不变的查找和配置每帧重做
FixedUpdate按固定游戏时间步执行物理相关逻辑认为每渲染帧恰好一次
LateUpdate在 Update 之后处理跟随等逻辑当成通用顺序依赖补丁
OnDisable / OnDestroy对应停止、注销和释放假定所有退出场景都可可靠做最终存档

同一个对象上,初始化有规定的顺序;跨对象不应随意假定谁的 Awake 或 OnEnable 先发生。依赖复杂时,用明确的启动入口协调,而不是反复调整脚本执行顺序掩盖问题。

时间应该怎样计算​

让非物理物体移动,可以用每秒速度乘以帧间隔。下面是独立组件,挂到不受动态刚体控制的对象上:

using UnityEngine;
public sealed class MoveRight : MonoBehaviour
{
[SerializeField] private float unitsPerSecond = 2f;
private void Update()
{
transform.position += Vector3.right * unitsPerSecond * Time.deltaTime;
}
}

不用 deltaTime 而每帧固定移动一段距离,会让高帧率设备移动更快。动态刚体移动则需要遵循物理系统规则,见2D 物理。

协程是跨帧等待,不是自动多线程​

private System.Collections.IEnumerator ShowThenHide(GameObject tip)
{
tip.SetActive(true);
yield return new WaitForSeconds(1f);
tip.SetActive(false);
}

这是协程方法片段,由有效的 MonoBehaviour 使用 StartCoroutine 启动,调用方保证 tip 的寿命。WaitForSeconds 使用缩放后的游戏时间;暂停时若要继续计时,可考虑不受 timeScale 影响的等待方式。

协程执行到等待之前的工作仍会占用主线程。把一个耗时循环放进协程不会自动变快。GameObject 失活会停止它的协程;仅将组件 enabled 改为 false 不会产生同样效果。

异步返回时,对象可能已经不在​

网络、广告或资源加载发起后,玩家可能切换界面、退出场景或重复点击。回调需要确认请求仍有效、对象仍存在、当前状态仍允许接收结果。适合取消的操作要在生命周期结束时取消。

微信的线程能力依赖具体工具链和平台模式。无论是否存在可用后台线程,Unity 对象操作通常仍要求在正确的主线程上下文中进行。不要用 .Wait() 或 .Result 把异步流程重新堵死。

验收与 AI 提问​

让 AI 为每项行为标明触发时机、重复进入时的处理和退出时的清理。验证启用两次、暂停恢复、等待中切场景、网络慢返回等路径,而不只验证第一次正常启动。

参考:执行顺序、协程。