先说一下我遇到的问题,我弄了一个对象池管理多个对象,对象池绑定在一个GameObject上,每个对象在OnBecameInvisible时会进行回收(即移出屏幕就回收),但是当场景切换或停止运行程序时场景中如果还有待回收的对象,就会报错,报错显示的信息为,我的对象池GameObject已经被销毁了云云,因为回收的对象我会把他们作为绑定了对象池的GameObject的子级来方便管理。

所以唯一的可能就是脚本方法调用顺序不可控,即不同GameObject的OnBecameInvisible在其它GameObject的OnDestroy之后调用。

在Unity3D中,我们知道GameObject的Update和LateUpdate两个函数的执行顺序是:每一帧中所有GameObject的Update方法都优先LateUpdate方法执行,即所有GameObject的Update方法都执行完毕才会执行LateUpdate方法。

那么我在使用下面3个方法时也认为其执行顺序也同Update和LateUpdate一致:

  • OnBecameInvisible:当GameObject存在renderer属性时,消失(不渲染)时会调用;
  • OnDisable:SetActivite(false)时调用;
  • OnDestroy:销毁时调用;

我认为在关闭程序或场景销毁时,其调用顺序是所有GameObject的OnBecameInvisible调用完毕后才开始调用OnDisable,最后再统一调用OnDestroy方法,即和Update与LateUpdate逻辑一致。

但是实际上并不是这样,对于每个GameObject来说,实际调用顺序是OnDisable->OnBecameInvisible->OnDestroy,但是在多个GameObject直接不能保证调用顺序,可能第一个GameObject的OnDestroy已经调用了,另一个的OnDisable才开始调用,大家可以用下面的脚本在场景中多放几个GameObject测试一下看看,注意要添加一个显示的东西,比如Cube,否则OnBecameInvisible不会调用到。

 using UnityEngine;
using System.Collections; public class NewBehaviourScript : MonoBehaviour
{
public string name; void OnBecameInvisible()
{
Debug.Log(name + " : OnBecameInvisible");
} void OnDisable()
{
Debug.Log(name + " : OnDisable");
} void OnDestroy()
{
Debug.Log(name + " : OnDestroy");
}
}

结果可以印证多个GameObject之间的方法调用顺序不能保证,所以我们开发程序在遇到场景销毁时管理一些对象时要注意。

我的解决方法:

实在想不出更好的办法了,要么让对象池GameObject在切换场景时不销毁,要么只有添加判断,如果对象池GameObject已经销毁了就不要进行对象回收。

大家可以参考一下国外的这个问题:

http://answers.unity3d.com/questions/505088/

Unity3D中关于场景销毁时事件调用顺序的一点记录的更多相关文章

  1. cocos2d-x 2.x版本中,场景切换各方法调用顺序

    假设从A场景切换到B场景,调用各场景方法的顺序为: 如果没有切换效果(transition),则先调用B的init(),再调用A的onExitTransitionStart(),接着调用A的onExi ...

  2. Unity3D中C#和js方法相互调用

    通过查找资料,Unity3D中C#和js要相互调用彼此的方法,js文件必须放在"Standard Assets". "Pro Standard Assets" ...

  3. AJAX 中Sys.WebForms.PageRequestManager的事件激发顺序 《转》

    AJAX 中Sys.WebForms.PageRequestManager的事件激发顺序 测试代码: 测试代码如下: <%@ Page Language="C#" AutoE ...

  4. 三种方式创建bean对象在springIOC容器中初始化、销毁阶段要调用的自定义方法

    1. 使用@Bean注解定义initMethod和destroyMethod 所谓initMethod和destroyMethod,是指在springIOC容器中,对于bean对象执行到初始化阶段和销 ...

  5. java中构造代码块、方法调用顺序问题

    1. 继承的概念 继承在本职上是特殊——一般的关系,即常说的is-a关系.子类继承父类,表明子类是一种特殊的父类,并且具有父类所不具有的一些属性或方法. 2. 继承中的初始化顺序 从类的结构上而言,其 ...

  6. Unity3D 中鼠标按下时OnMouseDown()、Input.GetMouseButtonDown()和EventType.MouseDown的响应验证

    初学unity3D,对于其中的事件响应不是很清楚,于是写了下面的代码来验证: 1.新建.cs文件,名为testMouse.cs: using UnityEngine; using System.Col ...

  7. Unity3D中如何计算场景中的三角面和顶点数

    在做游戏开发时,场景中的三角面和顶点数影响着运行效率,尤其是在手机平台上,实时的知道场景中的各项指标,对性能优化来说至关重要,下面我们来实现一个小功能,来实时计算场景中的三角面和顶点数: 如果要知道场 ...

  8. vue中使用element组件时事件想要传递其他参数的问题

    在使用element的上传组件时在一下几个钩子中传递其他参数 图中是文件上传时的几个钩子,参数为文件或文件列表或者其他参数,但是现在我想在原有参数上传递其他参数.比如我想在on-success的钩子中 ...

  9. Unity3D中切换场景可能导致材质变暗的问题

    Unity版本:5.1.1f1 做公司项目的时候,无意间发现了一个很奇葩的现象:场景A(纯UI,故没有光源)转场到场景B的时候,B中原有的光源似乎失效了,但在Hierarchy窗口中能够看到光源存在, ...

随机推荐

  1. Qt之QTableView添加复选框(QAbstractItemDelegate)

    简述 上节分享了使用自定义模型QAbstractTableModel来实现复选框.下面我们来介绍另外一种方式: 自定义委托-QAbstractItemDelegate. 简述 效果 QAbstract ...

  2. ASP.NET MVC 学习3、Controller左手从Model获取数据,右手传递到View页面

    参考:http://www.asp.net/mvc/tutorials/mvc-4/getting-started-with-aspnet-mvc4/accessing-your-models-dat ...

  3. bzoj3555: [Ctsc2014]企鹅QQ

    将字符串hash.不难写.然而1.注意用longlong2.数组大小注意...3.似乎别人都用的unsigned long long ?. #include<cstdio> #includ ...

  4. BZOJ_1624_ [Usaco2008_Open]_Clear_And_Present_Danger_寻宝之路_(最短路_Floyd)

    描述 http://www.lydsy.com/JudgeOnline/problem.php?id=1025 给出\(n\)个点以及之间的边的长度,给出必须访问的点的顺序,求最短路线长度. 分析 用 ...

  5. C#委托的介绍(delegate、Action、Func、predicate)【转】

    转自 http://www.cnblogs.com/akwwl/p/3232679.html 委托是一个类,它定义了方法的类型,使得可以将方法当作另一个方法的参数来进行传递.事件是一种特殊的委托. 1 ...

  6. WDF模型驱动程序开发

    WDF驱动程序开发 1. 引言 设备驱动程序是硬件设备连接到计算机系统的软件接口,任何设备都必须有相应的驱动程序才能在计算机系统上正常工作.设备驱动程序的优劣直接关系到整个系统的性能和稳定性,因此,设 ...

  7. LeetCode: Single Number I && II

    I title: Given an array of integers, every element appears twice except for one. Find that single on ...

  8. 一天一个Java基础——序列化

    1.概念 Java的“对象序列化”能将一个实现了Serializable接口的对象转换成一组byte,这样日后要用这个对象的时候,能把这些byte数据恢复出来,并据此重新构建那个对象. 对象序列化能实 ...

  9. ioctl用法详解 (网络)

    本函数影响由fd参数引用的一个打开的文件. #include#include int ioctl( int fd, int request, .../* void *arg */ );返回0:成功   ...

  10. MFC字体与文本输出

    字体 成员函数 1.CFont( ); 构造一个CFont对象.此对象在使用之前应该先使用CreateFont.CreateFontIndirect.CreatePointFont或CreatePoi ...