0

嘿,这个问题是对Joel Hooks对我的一个较旧问题的评论的回复(如何从另一个类调用一个类中的函数?

我能够使用公共静态变量来引用我的一个类来解决我自己的问题,所以在另一个类中我只需要使用 this 关键字就可以调用它。

instance = this; // in Navigation Class
Navigation.instance.introPlayButtonClick(); // in Intro Class

现在看来,对于OOP,我并没有以最好或最纯粹的方式来做这件事(可以在这里感觉到辩论),所以我第二次提出这个问题,希望能正确地解决这个问题。

问题

我有 2 个课程,介绍和导航。在 Intro 类中创建了一个按钮,需要调用 Navigation 类中的函数。我还有一个 CustomEvent 类,用于设置自定义事件。下面是代码,我已经删除了与此问题相关的所有非必要代码。

介绍类

单击的函数被调用时,它会分派一个导航类正在侦听的事件。


package src.display
{
import flash.events.*;
 import flash.display.*;

 // ☼ --- Imported Classes
 import src.events.CustomEvent;
 import src.model.Navigation;

 public class Intro extends Sprite 
 {
  private var playBtn:MovieClip;
  private var colorTransform:ColorTransform;

  // ☼ --- Constructor
  public function Intro():void 
  {
      this.addEventListener(Event.ADDED_TO_STAGE, init);
  }

  // ☼ --- Init
  public function init(event:Event):void 
  {
      draw();
      this.removeEventListener(Event.ADDED_TO_STAGE, init);
  }

  public function draw():void 
  {
      playBtn = new PlayThumb;
      playBtn.buttonMode = true;   
      playBtn.x = 552;   
      playBtn.y = 289;
      playBtn.alpha = 1;

      // ☼ --- add button 
      addChild(playBtn);

      // ☼ --- button listeners
      playBtn.addEventListener(MouseEvent.MOUSE_UP, clicked);
  }
  //-----------------------------------------------------
  // ☼ --- My Old Function
  /*private function clicked(e:MouseEvent):void 
  {
      Navigation.instance.introPlayButtonClick(); // Open tab1
  }*/
  //-----------------------------------------------------
  // ♦♦♦ Added to dispatch Event to JStriedl's function ♦♦♦
  private function clicked(e:MouseEvent):void 
      {
      dispatchEvent (new CustomEvent(CustomEvent.INTRO_CLICKED, {}));
      trace("Dispatch Event INTRO_CLICKED");
      }
 }
}

导航类

这是导航类,其中包含介绍类需要能够调用的函数。


package src.model 
{
import flash.events.*;
import flash.display.*;

// ☼ ---Imported  Classes
import src.display.Intro;
import src.model.Fonts;
import src.events.CustomEvent;

public class Navigation extends MovieClip //Needs MovieClip
{  
    public var intro:Intro;
    public static var instance:Navigation;

    // ☼ --- Constructor
public function Navigation()
{
    this.addEventListener(Event.ADDED_TO_STAGE, init);
}

// ☼ --- Init
public function init():void
{
    instance = this;  
    intro = new Intro;
    attachListenerForIntro(intro);
    this.removeEventListener(Event.ADDED_TO_STAGE, init);
}

// ♦♦♦ JStriedl's code ♦♦♦
public function attachListenerForIntro(introToCheckForClick:Intro)
{
    intro = introToCheckForClick;
    intro.addEventListener("introClicked", introPlayButtonClick);
}

// Function that button in Intro needs to call
public function introPlayButtonClick(e:CustomEvent):void
{    
    trace("Navigation function called from Intro");
    intro.removeEventListener("introClicked", introPlayButtonClick);
}
}
}

问题或错误

到目前为止,当单击按钮时没有任何反应:(我假设我没有在导航类中正确设置 EventListener?

4

2 回答 2

4

通常,容器有责任在其子级上调用函数。

如果您想让(否则独立的)兄弟姐妹彼此交互,则您的容器充当两者之间的代理。

例如,如果您的应用程序的结构如下:

container
  |
  +-- introInstance
  |
  +-- navigationInstance
  1. containerCustomEvent.INTRO_CLICKED为 on 上的事件添加一个侦听器introInstance

  2. introInstance引发CustomEvent.INTRO_CLICKED事件。

  3. Incontainer的事件处理程序调用navigationInstance.introPlayButtonClick()

这样,您的Intro班级就不需要知道有关Navigation班级的任何事情,反之亦然,您的班级container形成了两个实例之间的粘合剂。

快速说明:container不一定是显示列表中包含两个项目的字面 DisplayObjectContainer,它只需要引用两个实例并知道如何处理它们。

于 2009-11-19T02:33:01.927 回答
1

Errr .. 我能想到的唯一方法是将您的 Intro 类扩展到 Navigation 类,以使其正常工作。

就像是..

public class Intro extends Navigation {}
于 2009-11-18T23:25:34.047 回答