AS3:访问函数外的变量
AS3: Access variable outside of function
这个问题快把我逼疯了,我不知道我错过了什么。这是我的代码:
package {
import flash.display.*;
import flash.text.*;
import flash.events.*;
import flash.net.*;
import flash.xml.*;
public class PopUp extends Sprite {
public var container:Array = new Array();
public function PopUp() {
var contentXML:XML = new XML();
var XML_URL:String = "./content/content.xml";
var contentXMLURL:URLRequest = new URLRequest(XML_URL);
var contentLoader:URLLoader = new URLLoader(contentXMLURL);
contentLoader.addEventListener("complete", FuncXML);
function FuncXML(event:Event):void {
contentXML = XML(contentLoader.data);
for each (var item in contentXML.item) {
var txtbox:Sprite = new Sprite();
txtbox.graphics.beginFill(0x444444, 0.9);
txtbox.graphics.drawRoundRect(0, 0, 100, 100, 15, 15)
txtbox.graphics.endFill();
txtbox.name = "txtbox_"+item.settings.target;
addChild(txtbox);
container.push(txtbox);
}
trace(container.length); // Returns 2
}
trace(container.length); // Returns 0
}
}
}
此代码的最终版本应根据 xml 文件的内容创建文本框,但我无法从函数 "FuncXML" 中获取内容。我用痕迹试过了。函数内的trace returns 正确的长度是"container",也就是2。函数外的trace returns 0。请问这里有什么问题吗?
正如其他答案中所解释的那样,您的第二个跟踪将在内部函数中的第一个跟踪之前执行。我碰巧是因为 URLLoader 不是即时的,加载数据需要一些时间。所以你必须等到它完成工作。您可以等待本文档中描述的特定事件:URLLoader Adobe Help。
下面我可以建议一些您可能想要做的基本示例:
public class PopUp extends Sprite {
public var container:Array = new Array();
// Class constructor
public function PopUp() {
}
public function prepareAndLoad():void {
var XML_URL:String = "./content/content.xml";
var contentXMLURL:URLRequest = new URLRequest(XML_URL);
var contentLoader:URLLoader = new URLLoader();
contentLoader.addEventListener(Event.COMPLETE, onXMLLoadComplete);
// good practice here would be to expect errors as well:
contentLoader.addEventListener(IOErrorEvent.IO_ERROR, onError);
contentLoader.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onError);
contentLoader.load(contentXMLURL);
}
private function onError(e:ErrorEvent):void {
trace("Error");
// maybe you want to handle this situation somehow.
}
private function onXMLLoadComplete(event:Event):void {
var contentXML:XML = XML(event.target.data);
for each (var item in contentXML.item) {
var txtbox:Sprite = new Sprite();
txtbox.graphics.beginFill(0x444444, 0.9);
txtbox.graphics.drawRoundRect(0, 0, 100, 100, 15, 15)
txtbox.graphics.endFill();
txtbox.name = "txtbox_"+item.settings.target;
addChild(txtbox);
container.push(txtbox);
}
trace(container.length);
// here your XML is loaded and processed. Dispatch an event to notify that job is done and container is not empty.
dispatchEvent(new Event(Event.COMPLETE));
}
}
您可以在项目的某处创建此弹出窗口的实例:
//...
var popUp:PopUp = new PopUp();
popUp.addEventListener(Event.COMPLETE, onPopUpReady);
popUp.prepareAndLoad();
//...
private function onPopUpReady(e:Event):void {
var popUp:PopUp = e.target as PopUp;
trace(popUp.container.length); // Ready and loaded.
}
//...
阅读你的代码我可以看到第二个 trace(container.length);
returns 0 只是因为它被称为 before "first" trace(container.length);
.
如果您看到函数 FuncXML
仅在第二次跟踪之前被声明并添加为侦听器回调(或处理程序),您就可以理解它,但是由于您处于 异步 上下文你永远不会知道 FuncXML
内容是否会在第二个 "trace" 调用之前执行。
特别是您有两个并行运行的函数流:PopUp
流 FuncXML
流,但您假设它们是相应的。
希望对您有所帮助
如前所述,您正在查找项目,然后才加载它们。
您应该等到它们加载并准备就绪,然后在舞台上或其他地方处理它们。
我会这样处理这种情况:
在您的主文件上:
var newTxt:PopUp = new PopUp({
onReady_func: handlePopUp //pass the function to PopUp class as a parameter
});
// this function will be called whenever PopUp is ready
function handlePopUp(){
trace(newTxt.container.length);
}
在弹出窗口中 class:
...
// the $config object contains setup parameters
public function PopUp($config) {
...
function FuncXML(event:Event):void {
...
// Everything is ready. Lets tell them.
$config.onReady_func(); // this call should be in the last line of funcXML
}
这个问题快把我逼疯了,我不知道我错过了什么。这是我的代码:
package {
import flash.display.*;
import flash.text.*;
import flash.events.*;
import flash.net.*;
import flash.xml.*;
public class PopUp extends Sprite {
public var container:Array = new Array();
public function PopUp() {
var contentXML:XML = new XML();
var XML_URL:String = "./content/content.xml";
var contentXMLURL:URLRequest = new URLRequest(XML_URL);
var contentLoader:URLLoader = new URLLoader(contentXMLURL);
contentLoader.addEventListener("complete", FuncXML);
function FuncXML(event:Event):void {
contentXML = XML(contentLoader.data);
for each (var item in contentXML.item) {
var txtbox:Sprite = new Sprite();
txtbox.graphics.beginFill(0x444444, 0.9);
txtbox.graphics.drawRoundRect(0, 0, 100, 100, 15, 15)
txtbox.graphics.endFill();
txtbox.name = "txtbox_"+item.settings.target;
addChild(txtbox);
container.push(txtbox);
}
trace(container.length); // Returns 2
}
trace(container.length); // Returns 0
}
}
}
此代码的最终版本应根据 xml 文件的内容创建文本框,但我无法从函数 "FuncXML" 中获取内容。我用痕迹试过了。函数内的trace returns 正确的长度是"container",也就是2。函数外的trace returns 0。请问这里有什么问题吗?
正如其他答案中所解释的那样,您的第二个跟踪将在内部函数中的第一个跟踪之前执行。我碰巧是因为 URLLoader 不是即时的,加载数据需要一些时间。所以你必须等到它完成工作。您可以等待本文档中描述的特定事件:URLLoader Adobe Help。 下面我可以建议一些您可能想要做的基本示例:
public class PopUp extends Sprite {
public var container:Array = new Array();
// Class constructor
public function PopUp() {
}
public function prepareAndLoad():void {
var XML_URL:String = "./content/content.xml";
var contentXMLURL:URLRequest = new URLRequest(XML_URL);
var contentLoader:URLLoader = new URLLoader();
contentLoader.addEventListener(Event.COMPLETE, onXMLLoadComplete);
// good practice here would be to expect errors as well:
contentLoader.addEventListener(IOErrorEvent.IO_ERROR, onError);
contentLoader.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onError);
contentLoader.load(contentXMLURL);
}
private function onError(e:ErrorEvent):void {
trace("Error");
// maybe you want to handle this situation somehow.
}
private function onXMLLoadComplete(event:Event):void {
var contentXML:XML = XML(event.target.data);
for each (var item in contentXML.item) {
var txtbox:Sprite = new Sprite();
txtbox.graphics.beginFill(0x444444, 0.9);
txtbox.graphics.drawRoundRect(0, 0, 100, 100, 15, 15)
txtbox.graphics.endFill();
txtbox.name = "txtbox_"+item.settings.target;
addChild(txtbox);
container.push(txtbox);
}
trace(container.length);
// here your XML is loaded and processed. Dispatch an event to notify that job is done and container is not empty.
dispatchEvent(new Event(Event.COMPLETE));
}
}
您可以在项目的某处创建此弹出窗口的实例:
//...
var popUp:PopUp = new PopUp();
popUp.addEventListener(Event.COMPLETE, onPopUpReady);
popUp.prepareAndLoad();
//...
private function onPopUpReady(e:Event):void {
var popUp:PopUp = e.target as PopUp;
trace(popUp.container.length); // Ready and loaded.
}
//...
阅读你的代码我可以看到第二个 trace(container.length);
returns 0 只是因为它被称为 before "first" trace(container.length);
.
如果您看到函数 FuncXML
仅在第二次跟踪之前被声明并添加为侦听器回调(或处理程序),您就可以理解它,但是由于您处于 异步 上下文你永远不会知道 FuncXML
内容是否会在第二个 "trace" 调用之前执行。
特别是您有两个并行运行的函数流:PopUp
流 FuncXML
流,但您假设它们是相应的。
希望对您有所帮助
如前所述,您正在查找项目,然后才加载它们。
您应该等到它们加载并准备就绪,然后在舞台上或其他地方处理它们。
我会这样处理这种情况:
在您的主文件上:
var newTxt:PopUp = new PopUp({
onReady_func: handlePopUp //pass the function to PopUp class as a parameter
});
// this function will be called whenever PopUp is ready
function handlePopUp(){
trace(newTxt.container.length);
}
在弹出窗口中 class:
...
// the $config object contains setup parameters
public function PopUp($config) {
...
function FuncXML(event:Event):void {
...
// Everything is ready. Lets tell them.
$config.onReady_func(); // this call should be in the last line of funcXML
}