【问题标题】:as3 #1009 error code provided. "Null Object reference"as3 #1009 提供错误代码。 “空对象引用”
【发布时间】:2015-04-14 14:49:54
【问题描述】:

嗨,我对 as3 比较陌生(今年),我收到了这个错误

typer error #1009 无法访问空对象的属性或方法 参考。在 FoodObject/collisionTest()

我希望有人能帮忙

package {
import flash.events.MouseEvent;
import flash.events.KeyboardEvent;
import flash.events.*
    import flash.utils.*
    import flash.display.Stage;

public class GameScene1 extends Scene {

    //public variables
    //character & scenery
    public var mainChar: Character;
    public var testFood: FoodObject;




    //constructor is used to create all necessary objects for this scene and display them
    public function GameScene1(gm_: Manager) {

        //constructor

        super(gm_);
        trace("GameScene 1 constructor");


        //character
        mainChar = new Character;
        addChild(mainChar);
        mainChar.x = 200;
        mainChar.y = 200;


        testFood = new FoodObject;
        addChild(testFood)
        testFood.x = 50
        testFood.y = 200

食物对象类在这里。

package  {
import GameScene1
import flash.display.MovieClip;
import flash.events.Event;
import flash.events.MouseEvent;
import flash.events.TimerEvent;


public class FoodObject extends MovieClip {
    public var Game1:GameScene1;

    public function FoodObject() {
         //constructor code
        this.addEventListener(Event.ENTER_FRAME, collisionTest)
    }

    public function collisionTest(e:Event)
    {
        if (this.hitTestObject(Game1.mainChar))
        {
            trace("it works")
        }
    }

}

}

游戏经理在这里: 包{

import flash.display.MovieClip;


public class Manager extends MovieClip {

    //stores which scene is currently loaded
    public var curScene:Scene=null;

    public function Manager() {
        //constructor
        trace("Manager Construct")
        GoToScene("menu");
    }


    public function GoToScene(name:String)
    {
        if (curScene) //there was a scene already
        {
        curScene.OnLeaveScene(); //call its OnLeaveScene function to remove all objects
        removeChild(curScene);
        }

        if(name=="menu") curScene = new MenuScene(this);
        if(name=="select") curScene = new SelectScene(this);
        if(name=="game1") curScene = new GameScene1(this);
        if(name=="game2") curScene = new GameScene2(this);
        if(name=="game3") curScene = new GameScene3(this);
        if(name=="credit") curScene = new CreditScene(this);

        addChild(curScene);
    }


}

【问题讨论】:

    标签: actionscript-3


    【解决方案1】:

    你的问题是你的类的关注点不是分开的:

    你的Scene 知道CharacterFood 对象,你在那里实例化这两个类,这没有错。

    当您尝试在 Food 对象中做某事时,问题就开始了,这需要角色的知识。问题是:Food 对象对Character 一无所知。

    您可以通过简单地将Character 的引用传递给您的Food 对象来解决此问题。为此,请像这样修改构造函数:

    private var character:Character;
    public function FoodObject(character:Character) {
         //constructor code
        this.addEventListener(Event.ENTER_FRAME, collisionTest)
        this.character = character;
    }
    

    Scene 中上述构造函数的用法变化如下:

    testFood = new FoodObject(mainCharacter);
    

    这样,Food 知道角色并可以用它做一些事情,例如进行碰撞测试:

       public function collisionTest(e:Event)
        {
            if (this.hitTestObject(character)) // ==== this line changed
            {
                trace("it works")
            }
        }
    

    但是,这引发了一个重要问题:为什么Food 应该知道Character

    果然,你想做碰撞测试,需要两个对象。 但是为什么要在Food 对象中这样做呢?

    Food 中进行碰撞检查很麻烦,因为您必须传递对Character 的引用才能在那里进行。

    首选的方法在参与检查的两个对象都已知的情况下进行碰撞检查。 在您的情况下,这是Scene

    想想签到Scene 是多么容易:

    testFood.hitTestObject(mainCharacter);
    

    就这么简单,因为你需要的一切都已经在那里了。


    回顾一下:

    • 碰撞检查需要了解 2 个您想要检查的对象 检查。
    • 为了检查其中任何一个,您必须通过参考 的另一个。 (CharacterFood 如上所示或其他方式 圆形)
    • 在已经知道的地方进行检查要容易得多 两个对象,因为不必传递引用。

    您的原始代码失败,因为FoodObject 中的Game1 从未分配过值,因此仍保留为null。 在null 上调用方法会导致您遇到的错误。

    【讨论】:

    • @null 回答有关 1009 错误的问题具有讽刺意味……哈哈。不过答案很好。
    【解决方案2】:

    您忘记使用 new 关键字获取 GameScene1 类的实例。

    public var Game1:GameScene1;
    
    public function FoodObject() {
         //constructor code
         var _manager:Manager = new Manager();
         Game1 = new GameScene1(_manager)
        this.addEventListener(Event.ENTER_FRAME, collisionTest);
    }
    
    public function collisionTest(e:Event):void{
        ....
    }
    

    【讨论】:

    • 这样做会创建 GameScene1 的无限循环
    • 我不知道为什么,但 GameScene1 一直在创建,每次创建时我都会留下痕迹。我认为这是因为 food 对象通过 new 关键字调用 GameScene1 但 GameScene1 在构造函数中创建 foodObjects 所以它不断重复
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-12-08
    相关资源
    最近更新 更多