MonoBehaviour Lifecycle(生命周期/脚本执行顺序)
脚本执行顺序
前言
搭建一个示例来验证Unity脚本的执行顺序,大概测试以下部分:
- 物理方面(Physics)
- 渲染(Scene rendering)
- 输入事件(InputEvent)
流程图
Unity文档:https://docs.unity3d.com/Manual/ExecutionOrder.html
原图地址:https://docs.unity3d.com/uploads/Main/monobehaviour_flowchart.svg

测试场景
搭建场景
根据上图中的脚本生命周期,我编写三个脚本来测试部分阶段的生命周期:
- Logs.cs 输出日志(可选)
- TestInputEvent.cs(Input输入事件)
- TestPhysicOrder.cs(物理事件执行顺序)
- TestSceneRender.cs(Render顺序)
创建一个空的场景,创建三个Gameobject,每个gameobject上分别绑上要测试的脚本。每次测试不同的功能,分别激活不同的gameobject

打印调用堆栈脚本
可以打印调用方法的堆栈,包括方法名,文件名
using System;
using System.Diagnostics;
public class Logs  {
    /// <summary>
    /// 打印调用者的方法名
    /// </summary>
    public static void DoLog()
    {
        StackTrace st = new StackTrace(true);
        //获取当前调用的方法名
        StackFrame stackFrame = st.GetFrame(1);
        //var callInfo = string.Format("{0}:{1}.{2}",stackFrame.GetFileName(),stackFrame.GetFileLineNumber(),stackFrame.GetMethod().Name);
        var callInfo = stackFrame.GetMethod().Name.ToString();
        DoLog(callInfo);
    }
    public static void DoLog(string szMsg, params object[] args)
    {
        string log = string.Format("[{0}]{1}", DateTime.Now.ToString("HH:mm:ss.ffff"), string.Format(szMsg, args));
        UnityEngine.Debug.Log(log);
    }
}
物理测试
测试脚本
测试脚本中写了Unity的各个脚本函数,大致内容如下:
using System;
using UnityEngine;
using System.Collections;
public class TestPhysicOrder : MonoBehaviour
{
    // Reset to default values
    public void Reset()
    {
        Logs.DoLog();
    }
    // Awake is called when the script instance is being loaded
    public void Awake()
    {
        StartCoroutine(YieldOneFrame());
        StartCoroutine(YieldEndOfFrame());
        StartCoroutine(YieldWaitForFixedUpdate());
        Logs.DoLog();
    }
    // This function is called when the object becomes enabled and active
    public void OnEnable()
    {
        Logs.DoLog();
    }
    // Use this for initialization
    void Start()
    {
        Logs.DoLog();
    }
    // This function is called every fixed framerate frame, if the MonoBehaviour is enabled
    public void FixedUpdate()
    {
        Logs.DoLog();
    }
    // Update is called once per frame
    void Update()
    {
        Logs.DoLog();
    }
    IEnumerator YieldWaitForFixedUpdate()
    {
        yield return new WaitForFixedUpdate();
        Logs.DoLog("WaitForFixedUpdate");
    }
    IEnumerator YieldOneFrame()
    {
        yield return 1;
        Logs.DoLog("YieldOneFrame");
    }
    IEnumerator YieldEndOfFrame()
    {
        yield return new WaitForEndOfFrame();
        Logs.DoLog("YieldEndOfFrame");
    }
    // LateUpdate is called every frame, if the Behaviour is enabled
    public void LateUpdate()
    {
        Logs.DoLog();
    }
    // This function is called when the behaviour becomes disabled or inactive
    public void OnDisable()
    {
        Logs.DoLog();
    }
    // This function is called when the MonoBehaviour will be destroyed
    public void OnDestroy()
    {
        Logs.DoLog();
    }
    // Sent to all game objects when the player gets or looses focus
    public void OnApplicationFocus(bool focus)
    {
        Logs.DoLog();
    }
    // Sent to all game objects when the player pauses
    public void OnApplicationPause(bool pause)
    {
        Logs.DoLog();
    }
    // Sent to all game objects before the application is quit
    public void OnApplicationQuit()
    {
        Logs.DoLog();
    }
}
测试结果
开始部分截图

结束部分截图

Render测试
测试脚本
using System;
using UnityEngine;
public class TestSceneRender : MonoBehaviour
{
    // OnPreCull is called before a camera culls the scene
    public void OnPreCull()
    {
        Logs.DoLog();
    }
    // OnPreRender is called before a camera starts rendering the scene
    public void OnPreRender()
    {
        Logs.DoLog();
    }
    // Callback that is sent if an associated RectTransform has it's dimensions changed
    public void OnRectTransformDimensionsChange()
    {
        Logs.DoLog();
    }
    // Callback that is sent if an associated RectTransform is removed
    public void OnRectTransformRemoved()
    {
        Logs.DoLog();
    }
    // OnRenderImage is called after all rendering is complete to render image
    public void OnRenderImage(RenderTexture source, RenderTexture destination)
    {
        Logs.DoLog();
    }
    // OnRenderObject is called after camera has rendered the scene
    public void OnRenderObject()
    {
        Logs.DoLog();
    }
    // OnWillRenderObject is called once for each camera if the object is visible
    public void OnWillRenderObject()
    {
        Logs.DoLog();
    }
    // Implement this OnDrawGizmosSelected if you want to draw gizmos only if the object is selected
    public void OnDrawGizmos()
    {
        Logs.DoLog();
    }
    // OnGUI is called for rendering and handling GUI events
    public void OnGUI()
    {
        Logs.DoLog();
    }
}
测试结果
当把测试脚挂在Cube或者Camera上,会执行的函数是不相同的。
绑在Camera上

绑在Cube上

MonoBehaviour Lifecycle(生命周期/脚本执行顺序)的更多相关文章
- Unity脚本生命周期与执行顺序
		文章目录 脚本生命周期 MonoBehavior生命周期图 脚本执行顺序 自定义执行顺序 在Unity中,脚本可以理解为附加在游戏对象上的用于定义游戏对象行为的指令代码.必须绑定在游戏对象上才能开始它 ... 
- 附实例!图解React的生命周期及执行顺序
		本文由云+社区发表 作者:前端林子 1.七个可选的生命周期 可以结合下图来看: (1) componentWillMount() 仅在render()方法前被调用一次,如果在该方法中调用了setSta ... 
- Spring的Bean的生命周期方法执行顺序测试
		通过一个简单的Maven工程来演示Spring的Bean生命周期函数的执行顺序. 下面是工程的目录结构: 直接贴代码: pom.xml文件内容: <?xml version="1.0& ... 
- Unity3D脚本的生命周期(执行顺序)
		Unity脚本中有许多固定的函数 例如Start();Update(); 而这些函数都有固定的执行顺序 搞清楚这些函数的执行顺序 对于我们理清代码的逻辑就显得尤为重要 举个简单的例子 //脚本A pu ... 
- vue中的父组件及子组件生命周期的执行顺序
		一.没有任何任何显示与隐藏限制条件的情况下: 1.运行的顺序依次是: 父组件created→父组件beforeMounted→子组件created→子组件beforeMounted→子组件mounte ... 
- 简单记录一下vue生命周期及 父组件和子组件生命周期钩子执行顺序
		首先,vue生命周期可以用下图来简单理解 当然这也是官方文档的图片,详细的vue周期详解请参考这里 然而当同时存在父子组件的时候生命周期钩子是如何执行的呢? 请看下文: 加载渲染过程父beforeCr ... 
- react教程 — 组件的生命周期 和 执行顺序
		一.组件执行的生命周期: 参考 https://www.cnblogs.com/soyxiaobi/p/9559117.html 或 https://www.c ... 
- Vue 的父组件和子组件生命周期钩子执行顺序是什么
		加载渲染过程父beforeCreate->父created->父beforeMount->子beforeCreate->子created->子beforeMount-&g ... 
- Unity3D_02_基类MonoBehaviour/自带函数以及脚本执行的生命周期
		导引: 其中Time,Input,Physics都是Unity中的全局变量.GameObject是游戏中的基本物件.GameObject是由Component组合而成的,GameObject本身必须有 ... 
随机推荐
- c 小工具的使用
			1. 这是一个gps 数据过滤的小工具,目的是过滤到gps数据中不符合要求的数据,然后转为json 数据 需要两个小工具 bermuda.c ------> 过滤一定范围的数据 geo2j ... 
- Python(六)面向对象、异常处理、反射、单例模式
			本章内容: 创建类和对象 面向对象三大特性(封装.继承.多态) 类的成员(字段.方法.属性) 类成员的修饰符(公有.私有) 类的特殊成员 isinstance(obj, cls) & issu ... 
- 使用 Windows Phone Toolkit 的 Tilt 效果
			上一篇文章分享了如何使控件具有摁下的效果(在WindowsPhone中使控件具有Tilt效果),实现方式是在项目中添加新的类文件,其实,如果项目引用了Windows Phone Toolkit,那么就 ... 
- ASP.NET MVC5 ModelBinder
			什么是ModelBinding ASP.NET MVC中,所有的请求最终都会到达某个Controller中的某个Action并由该Action负责具体的处理和响应.为了能够正确处理请求,Action的 ... 
- JAVA/GUI程序之记事本
			自上半年JAVA课程结束后,再也没有看过JAVA了,最近不是很忙,又简单的看了看,本博客纯属记录学习过程,请大神们别笑,其中错误是难免的,毕竟是新手写的博客.下面就进入我们的正题吧,复习GUI时,就想 ... 
- 表格与ckeckbox的全选与单选
			先看看下面的效果: 用户点击头的checkbox时,所有表格数据行的checkbox全选或反选. 当数据行某一行没有选中时,头checkbox去选.当所有数据行的checkbox全选时,头的check ... 
- DataGridView绑定源码下载
			效果图: 源码下载:http://hovertree.com/h/bjaf/bbot18bj.htm 上面源码不包含数据库的查询,需要获取数据库数据的话,请看这个的源码: http://hovertr ... 
- 如何实现一个php框架系列文章【2】实现类的自动加载
			根据前一篇文章的设计原则,我们暂时把php文件分为3类,类名和文件名都遵守如下约定. 类名 文件名 路径 模型类m {$app}Mod {$app}.mod.php {$app}/model ... 
- [dedecms]后台不显示验证码
			原因:某个加载文件的开始处有一个标点,去掉就可显示 // 文件地址 /include/vdimgck.php @session_start(); $_SESSION['securimage_code_ ... 
- spider RPC框架的需求来源与特性介绍(一)
			spider RPC 特性介绍 spider RPC 性能测试 spider RPC 入门指南 spider RPC 配置文件参考 spider RPC 开发指南 spider RPC 安全性 spi ... 
