March 28, 2008

EventDispatcherでつまずいた

一秒ごとにイベント発行するクラスを作ろうと思ったらEventDispatcherを使うところでつまずいた。

import mx.transitions.OnEnterFrameBeacon;
import mx.events.EventDispatcher;

class TimeBeacon
{
   private var time:Date;
   
   private var nowTime:Number;
   private var prevTime:Number;
   
   function TimeBeacon()
   {
      OnEnterFrameBeacon.init();
      EventDispatcher.initialize(this);
   }
   
   function start()
   {
      time = new Date();
      nowTime = prevTime = time.getTime();
      this.dispatchEvent( { type:"onCountStart", target:this } );
      
      _global.MovieClip.addListener(this);
   }
   
   function stop()
   {
      nowTime = null;
      prevTime = null;
      
      _global.MovieClip.removeListener(this);
   }
   
   function onEnterFrame()
   {
      time = new Date();
      nowTime = time.getTime();
      if (nowTime - prevTime >= 1000)
      {
         this.dispatchEvent( { type:"onOneSecond", target:this } );
         prevTime = nowTime;
      }
   }
}

これで毎秒onOneSecondが発行される予定だったんだけど、「'dispatchEvent' という名前のメソッドはありません。」って怒られる。現象としてはインスタンスにdispathEventが実装されてないって事だからEventDispatcherにインスタンスの参照が渡されてないんだと思ったけどtraceしたらそうでもないみたい。なんじゃこら。

で、趣向を変えてEventDispatcherを継承してみたらすんなりイベントが発行されるようになった。

import mx.transitions.OnEnterFrameBeacon;

class TimeBeacon extends mx.events.EventDispatcher
{
   private var time:Date;
   
   private var nowTime:Number;
   private var prevTime:Number;
   
   function TimeBeacon()
   {
      OnEnterFrameBeacon.init();
   }
   
   function start()
   {
      time = new Date();
      nowTime = prevTime = time.getTime();
      this.dispatchEvent( { type:"onCountStart", target:this } );
      
      _global.MovieClip.addListener(this);
   }
   
   function stop()
   {
      nowTime = null;
      prevTime = null;
      
      _global.MovieClip.removeListener(this);
   }
   
   function onEnterFrame()
   {
      time = new Date();
      nowTime = time.getTime();
      if (nowTime - prevTime >= 1000)
      {
         this.dispatchEvent( { type:"onOneSecond", target:this } );
         prevTime = nowTime;
      }
   }
}

でもinitializeコメントアウトしても動作してるのを見るとなんか正攻法じゃない気がする。

助けてエロい人。

posted at 06:15 AM

 

トラックバック

このエントリーのトラックバックURL:
http://source-laboratory.net/mt/mt-tb.cgi/26

コメント

bk-zen

AS2 の EventDispatcher について調べてみたけど
EventDispatcher.initialize(obj) で obj に
addEventListener, removeEventListener, dispatchEvent, dispatchQueue
この4つのメソッドを追加させる。
EventDispatcher を継承した場合は EventDispatcher に上の4つのメソッドがあるから、initialize しなくても動くってことだと思いますよ。
むしろこのつくりなら EventDispatcher を継承するのが正解ってきがしますね。

>「'dispatchEvent' という名前のメソッドはありません。」って怒られる。
多分コンパイル時のエラーだと思いますが、
4つのメソッドが追加されるのはコンパイル時には解決していない部分なので怒られるんだと思います。

2008年3月28日 14:36



Bouze

コメントありがとうございます。
なるほどそういうことですか、じゃあとりあえず問題なさそうなのでこれで行きます。

あ、あとちょっと疑問が…、

>4つのメソッドが追加されるのはコンパイル時には解決していない部分なので怒られるんだと思います。

ということはどのタイミングでdispatchEventするのがいいんでしょうか?
時系列上は問題がないように思ってたんですが…。

2008年3月28日 14:51



bk-zen

> ということはどのタイミングでdispatchEventするのがいいんでしょうか?

dispatchEvent するタイミングはたぶんこれで良いと思うんですが、コンパイルするときに this.dispatchEvent っていうメソッドが無いので怒られるんだと思います。

2008年3月28日 15:05



Bouze

ようやく分かってきました。

クラスにEventDispatcherを実装するときは、initializeする前にチェックが入るから、dispatchEventはまだ存在してないって事ですね。

すみません、ありがとうございました。

2008年3月28日 15:14



heko

継承しない例の場合、classをdynamic指定するか、あるいはdispatchEvent(と、addEventListenerとremoveEventListenerなど)て名前の空のプロパティをあらかじめ用意しておけばいけると思います。

2008年3月28日 23:37



Bouze

おお、なるほど。
あらかじめプロパティで予約しておけばいいんですね。

dynamicは知らなかったです。
勉強しておきます。

ありがとうございました!

2008年3月29日 06:07



コメント





About the author

西村斉輝(にしむらなおき)

1984年兵庫県生まれ。
現在多摩美術大学GD科在籍。
パーソナルサイト
source laboratory™運営。

Syndication

Powerd by
MovableType 4.1