舞台上的对象未在构造函数之外初始化
Posted
技术标签:
【中文标题】舞台上的对象未在构造函数之外初始化【英文标题】:Objects on stage are not initialized outside constructor 【发布时间】:2012-11-25 13:54:18 【问题描述】:在我的文档类中,我已将一些放置在舞台上的对象分配给一个数组,以便稍后调用它们。
当我在构造函数之外声明数组时,对象尚未创建并且赋值为空,这与我在构造函数中声明它们时不同。 为什么会发生这种情况?
如何我可以避免这种情况?可以使用监听器来跟踪对象的加载时间吗?
第一个案例
package
public class Document extends MovieClip
var obj:Array = [object1,object2];
public function Document()
trace(obj[0]); // <-- null
第二种情况
package
public class Document extends MovieClip
public function Document()
var obj:Array = [object1,object2];
trace(obj[0]); // <-- reference value
【问题讨论】:
【参考方案1】:在外面声明数组,在构造函数里面填充值。
public class Document extends MovieClip
var obj:Array;
public function Document()
obj = [object1,object2];
trace(obj[0]); // <-- reference value
无论你写什么作为初始化值都会被首先处理,任何嵌入在编辑器中的东西都是第二个,构造函数代码是第三个。因此,当您在初始化代码中按名称引用资产时,它们尚未初始化,因此您会收到空值。
您使用的任何侦听器都只会在对象可用后应用。 init()
和 ADDED_TO_STAGE
侦听器非常有用,如果您需要舞台参考以将您的代码控制资产与给定的舞台尺寸对齐。在此之前,阶段引用为空。
【讨论】:
我知道我的问题是为什么会这样? 因为您在声明中使用代码初始化的所有内容都会先处理,阶段元素会先处理,构造函数代码会先处理。因此,当处理构造函数外初始化代码时,object1
和 object2
尚未初始化,因此您会得到空值。
@Vesper 如果需要,您可以使用评论更改当前答案,正确答案是您的。另一件事,我可以使用Event Listener onLoad
,一些init()
函数,ADDED_ON_STAGE
还是没有必要?
在这种情况下不需要使用那些监听器【参考方案2】:
全局变量(即任何方法之外的变量)在任何事情之前加载,之后构造函数被调用,之前它被执行.
改用此代码:
package
public class Document extends MovieClip
var obj:Array;
public function Document()
obj = [object1,object2];
trace(obj[0]);
附录:
Stage 对象在构造函数代码的顶部被初始化,例如 .net 中的设计器对象。
因此,由于全局变量在构造函数代码执行之前被初始化,object1
和object2
仍然是null
。
附录 2:
你有以下序列:
-
类的构造函数被调用
全局变量已初始化(您的
obj
数组,还有 object1
/object2
变量,但不是它们的值)
Designer(你在舞台上的图形)对象被初始化(即object1 = new Object1()
被调用)
构造器代码被执行
舞台对象总是自动声明和初始化,除非您在高级 AS 设置中取消选中自动声明舞台实例。
【讨论】:
你能解释一下为什么在放置舞台对象之前调用 Document 构造函数吗? 对象是 Document 的子对象,因此 Document 必须在它们之前创建。 我发现最容易把它想象成舞台(就像在 IDE 文档中放置对象的地方)是从文档类继承。这意味着在子类(IDE 阶段)被实例化之前,文档类对舞台上声明的对象没有任何概念。 @DaveHart 很好的解释,有没有办法证明对象是在舞台上创建的,或者在我们调用构造函数时是隐含的?【参考方案3】:嗯,这有点模糊。这些对象在哪里实例化? 我建议确保它们在您的课程中被实例化:
package
public class Document extends Sprite //I don't think you really need MovieClip
//alternatively to the method bellow you could use something like:
//
// private var object1 : Object = new Object();
// private var object2 : Object = new Object();
// public var obj : Array = [object1, object2];
//
// just make sure they are instantiated before they are used in the obj contructor
public var obj : Array = [new Object(),new Object()]; //again here I would suggest using a vector if they are the same type
public function Document()
trace(obj[0]);
如果这些对象在类外部,我建议将它们传递给构造函数,如下所示:
package
public class Document extends Sprite //I don't think you really need MovieClip
public var obj : Array = [null,null]; //again here I would suggest using a vector if they are the same type
public function Document(o1:Object=null,o2:Object=null)
if (o1 != null)
obj[0] = o1;
if (o2 != null)
obj[1] = o2;
//
if (obj[0] != null)
trace(obj[0]);
else
trace("Obj[0] is null");
[稍后编辑] 至于发生这种情况的原因是因为在数组初始化时这两个是空的(它们还没有被初始化)
[稍后编辑2] OK - Document 是 flash 的根类 - 很高兴知道 就像我在我的 cmets 中所说的那样,即使在舞台上这两个对象在添加到舞台之前不会被实例化。为此,我建议收听 ADDED_TO_STAGE 事件。 如果您将它们传递到构造函数之外,则在创建数组时它们将为空,因为它们尚未添加到阶段/创建(与流行的看法相反,即使在 Flash 中,对象也不会简单地存在)
【讨论】:
不,他们在舞台上。请阅读问题! 在投 -1 票之前,请务必阅读答案。话虽如此,请解释一下您希望您的班级如何真正知道这些对象是谁?你在哪里传递对这些对象的引用?就像我之前在你的问题中说的更具体,你会得到更准确的答案。只要你没有正当理由,投-1票来诋毁别人只会让你被禁止。 不想诋毁你,但你的回答并没有为帖子添加有用的东西。你写了“嗯,这有点模糊。那些对象在哪里实例化?”,所以这意味着你实际上没有读过这个问题,因为@yannis hristofakis 指定对象在舞台上。在 Flash 中,舞台上的对象会自动声明和初始化(除非您标记了特定选项)。 我不知道你从哪里学过 Flash 但显然你的老师很差。在舞台上声明的 Flash 对象并非在该 swf 中的所有类中都可用。为了使对象在类中可用,它们必须被具体实例化// 传递给类。即使在舞台上,它们也不会在舞台实际显示之前被实例化 - 因为有 Event.INITIALIZE 和 Event.ADDED_TO_STAGE - 我知道你认为这些是无用的事件,但它们确实不是。哦,@teejay 请不要炫耀你的 Flash 知识有多低。 Document类是主舞台类的总称,自Flash CS3起,无需假设。 active.tutsplus.com/tutorials/actionscript/…以上是关于舞台上的对象未在构造函数之外初始化的主要内容,如果未能解决你的问题,请参考以下文章
角度错误 TS2564:属性“用户”没有初始化程序,并且未在构造函数中明确分配
文件导入未在构造函数 ionic native 中初始化。 cordova 文件插件和 javascript 文件接口冲突。?