舞台上的对象未在构造函数之外初始化

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 侦听器非常有用,如果您需要舞台参考以将您的代码控制资产与给定的舞台尺寸对齐。在此之前,阶段引用为空。

【讨论】:

我知道我的问题是为什么会这样? 因为您在声明中使用代码初始化的所有内容都会先处理,阶段元素会先处理,构造函数代码会先处理。因此,当处理构造函数外初始化代码时,object1object2 尚未初始化,因此您会得到空值。 @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 中的设计器对象。

因此,由于全局变量在构造函数代码执行之前被初始化,object1object2 仍然是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/…

以上是关于舞台上的对象未在构造函数之外初始化的主要内容,如果未能解决你的问题,请参考以下文章

Firebase导入未在构造函数离子原生中初始化

角度错误 TS2564:属性“用户”没有初始化程序,并且未在构造函数中明确分配

文件导入未在构造函数 ionic native 中初始化。 cordova 文件插件和 javascript 文件接口冲突。?

没有默认构造函数的成员对象的初始化列表

cppcheck警告:变量未在带有初始化初始化的构造函数中实例化

构造函数作用是啥