遍历显示列表

Flash Player 9 和更高版本,Adobe AIR 1.0 和更高版本

如您所见,显示列表是一个树结构。树的顶部是舞台,它可以包含多个显示对象。那些本身就是显示对象容器的显示对象可以包含其他显示对象或显示对象容器。

DisplayObjectContainer 类包括通过显示对象容器的子级列表遍历显示列表的属性和方法。例如,考虑下面的代码,其中在 container 对象(该对象为 Sprite,Sprite 类用于扩展 DisplayObjectContainer 类)中添加了两个显示对象 titlepict

var container:Sprite = new Sprite(); 
var title:TextField = new TextField(); 
title.text = "Hello"; 
var pict:Loader = new Loader(); 
var url:URLRequest = new URLRequest("banana.jpg"); 
pict.load(url); 
pict.name = "banana loader"; 
container.addChild(title); 
container.addChild(pict);

getChildAt() 方法返回显示列表中特定索引位置的子级:

trace(container.getChildAt(0) is TextField); // true

您也可以按名称访问子对象。每个显示对象都有一个名称属性;如果没有指定该属性,Flash Player 或 AIR 会指定一个默认值,如 "instance1"。例如,下面的代码说明了如何使用 getChildByName() 方法来访问名为 "banana loader" 的子显示对象:

trace(container.getChildByName("banana loader") is Loader); // true

与使用 getChildAt() 方法相比,使用 getChildByName() 方法会导致性能降低。

由于显示对象容器可以包含其他显示对象容器作为其显示列表中的子对象,因此您可将应用程序的完整显示列表作为树来遍历。例如,在前面说明的代码摘录中,完成 pict Loader 对象的加载操作后,pict 对象将加载一个子显示对象,即位图。要访问此位图显示对象,可以编写 pict.getChildAt(0)。还可以编写 container.getChildAt(0).getChildAt(0)(由于 container.getChildAt(0) == pict)。

下面的函数提供了显示对象容器中显示列表的缩进式 trace() 输出:

function traceDisplayList(container:DisplayObjectContainer,                                                indentString:String = ""):void 
{ 
    var child:DisplayObject; 
    for (var i:uint=0; i < container.numChildren; i++) 
    { 
        child = container.getChildAt(i); 
        trace(indentString, child, child.name);  
        if (container.getChildAt(i) is DisplayObjectContainer) 
        { 
            traceDisplayList(DisplayObjectContainer(child), indentString + "    ") 
        } 
    } 
}

Adobe Flex

如果使用 Flex,您应了解 Flex 定义了许多组件显示对象类,这些类会覆盖 DisplayObjectContainer 类的显示列表访问方法。例如,mx.core 包的 Container 类会覆盖 DisplayObjectContainer 类(Container 类所扩展的类)的 addChild() 方法和其他方法。就 addChild() 方法而言,该类覆盖该方法的结果是,在 Flex 中,所有类型的显示对象都不能添加到 Container 实例。在本例中,被覆盖的方法要求所添加的子对象为 mx.core.UIComponent 对象类型。