stageの参照があーだこーだっていうこと
Flash CS3を買い久しぶりにMacを触ったら、コマンドキーの場所とか忘れていて、ちょっと変な感じ。「アクションパネルを開く」とか、「パブリッシュ」のショートカットもWindowsと違っているので、F9押したらExposeが起動したりして、ひとりであわあわしてしまいました。
さて、今更ながらPapervision 3Dを使ってみようと、こちらのblogのPV3Dの第1回目のソースをダウンロードし、クラスコンストラクタを見てふと疑問に思った。
public function main() addEventListener(Event.ADDED , initialize ); } private function initialize( e:Event ):void { removeEventListener( Event.ADDED , initialize ); //以下省略 }
まず「Event.ADDED」っていうイベントを知らなかったのでMoock本で調べてみたら、どうやらこれはDispalyオブジェクトが、DispalyObjectContainerに追加されると発生するものらしい。
このサンプルでは、mainクラスのインスタンスをドキュメントのルートで、
import main; addChild( new main() );
のようにaddChildしているので、つまりルートオブジェクトにmainオブジェクトがaddChildされたらinitializeがコールされ、直後にイベントリスナーを削除するという仕組みらしい。
んー、でもどうして単純にmainのコンストラクタ内で直接initializeを呼ばないんだろう?って、しばし考えてたんだけれど、以前Alpha FLASHerの方々が、stageの参照について言及していたことを思い出した。というのも上記initialize()の「以下省略」としたコードに、stageを参照する部分があったのだ。
で、fladdictさんのこの記事とか、taka@niumさんのこの記事とかを読み直し、自分で確認してみてやっと分かりました。
mainのコンストラクタでいきなりinitializeを呼んでしまうと、mainオブジェクトはstageを参照することができないのです。だから、一度自分自身がルートオブジェクトにaddChildされたのを確認してから、initializeを呼んで、その中でstageのプロパティを参照していたわけですねー。んー納得。
更にniumさんのところで「ドキュメントクラスで参照する場合はEvent.ADDEDで待つ必要はない」というコメントがあったので、ルートスクリプトでmainクラスのインスタンスをaddChildする代わりに、ドキュメントクラスにmainを指定。mainクラスでは、Event.ADDEDを使用せずに直接コンストラクタからinitializeを呼ぶように変更してみたところ、やはりstageが参照できました。
ということで、改めて思ったこと。
- 自分で手を動かして初めて理解に到るということ。
- たくさんのFLASHerの方に助けてもらっているということ。
日頃blogを購読させていただいている多数のFLASHerの方々。いつか勉強会などでお会いできたら直接お礼を言わせていただきますが、それまでは感謝の気持ちを忘れずにオイラも頑張りますー。多謝です。