隨筆 - 8  文章 - 55  trackbacks - 0
          <2025年5月>
          27282930123
          45678910
          11121314151617
          18192021222324
          25262728293031
          1234567

          常用鏈接

          留言簿(6)

          隨筆分類

          隨筆檔案

          文章分類

          文章檔案

          朋友的Blog

          最新評論

          閱讀排行榜

          評論排行榜

          從AsBroadcaster到EventDispatcher(上) [作者:wiyiflash]

          [ 2005-07-29 01:16:12 | 發布: N神 ]
          字體大小: | |
          前言:論壇里關于AsBroadcaster(廣播)類的討論很多,有很多精妙的講述,但為了和EventDispatcher(派遣)類有個比較,不得不把這位"老兄"拉來客串一下。對它我不會講的很詳細,不解的地方可以去搜搜前輩的帖子哦。

          AsBroadcaster(廣播)類在MX(flash6)里寫做"ASBroadcaster",這是為什么有時會發生以前的程序在2004版里發生異常的原因之一。AsBroadcaster 類具有四個靜態的方法:
          ------------------------------------------------------------------------------
          static function initialize(o:Object);
          //o:對象
          //initialize:初始化方法,為對象o附加上作為事件源的各項功能。那么事件源都有什么功能呢?
          static function broadcastMessage(msg:String);
          //msg:消息
          //broadcastMessage:廣播方法,事件源的一個主要功能就是向外界廣播一條消息,告知聽廣播的人"某一事件發生啦!"
          static function addListener(o:Object);
          //o:對象
          //addListener:注冊監聽者方法,也就是決定廣播消息給誰聽的意思
          static function removeListener(o:Object);
          //o:對象
          //removeListener:注銷監聽者方法,也就是消息不再廣播給誰聽
          --------------------------------------------------------------------------------
          如此看來AsBroadcaster類也不怎么復雜嘛,下面看看它的具體使用吧!

          -----AsBroadcaster測試.fla 開始------
          import mx.events.AsBroadcaster;
          //mx.events.AsBroadcaster:AsBroadcaster類的完整路徑,這里用'import'關鍵字將它導入,以后就可以直接用'AsBroadcaster'來引用它。
          var 司令部=new Object();
          //啊,司令部是個發布指揮消息的地方,用它做事件源是個不錯的選擇
          AsBroadcaster.initialize(司令部);
          //這里直接用AsBroadcaster來引用mx.events.AsBroadcaster類,原因如上述
          //調用AsBroadcaster類的靜態方法initialize,為司令部附加上作為事件源的各項功能
          var 步兵=new Object();
          //生成步兵對象
          步兵.on進攻=function(){
          //on進攻: 這里之所以用'on'做前綴,是為了表明這個方法是響應一定事件的方法
          trace("步兵接到司令部來電,輕裝上陣,火速向敵方陣地前進!");
          // 接到'on進攻'消息后采取的措施
          }
          步兵.on駐守=function(){
          //同上
          trace("步兵接到司令部來電,就地待命,多設崗哨,嚴防來犯之敵!");
          }
          司令部.addListener(步兵);
          //將步兵添加為司令部的監聽者,從現在起他將聽從司令部的指令行事
          //以下雷同的地方,恕不贅述
          var 裝甲兵=new Object();
          裝甲兵.on進攻=function(){
          trace("裝甲兵接到司令部來電,加足馬力,火速向敵方陣地開進!");
          }
          裝甲兵.on駐守=function(){
          trace("裝甲兵接到司令部來電,就地待命,檢修裝甲,作好隨時進攻的準備!");
          }
          司令部.addListener(裝甲兵);
          var 炮兵=new Object();
          炮兵.on進攻=function(){
          trace("炮兵接到司令部來電,向敵方陣地猛烈轟擊!");
          }
          炮兵.on駐守=function(){
          trace("炮兵接到司令部來電,就地待命,保證彈藥準備充足!");
          }
          司令部.addListener(炮兵);
          //-------------------下面開始演示------------------------------------
          trace("司令部一號指示");
          司令部.broadcastMessage("on進攻");
          //司令部用'broadcastMessage' 方法廣播'on進攻'指令
          trace("司令部二號指示");
          司令部.removeListener(步兵);
          //"將在外,君令有所不授",司令部用'removeListener'方法注銷了'步兵'聽從指令的義務
          司令部.broadcastMessage("on駐守");
          //司令部用'broadcastMessage' 方法廣播'on駐守'指令。注意:步兵現在不會駐守哦
          -----AsBroadcaster測試.fla 結束-----

          具體的測試結果,大家試試便知。現在我們看看AsBroadcaster類的局限所在:
          1、如果司令部發出的指令是"向一號高地進攻",這個消息應該怎么廣播呢?
          我們當然可以為步兵定義一個'on向一號高地進攻'的方法,然后監聽司令部廣播的'on向一號高地進攻'的消息。可是如果需要發出N個'向某高地進攻'的指令,豈不是要定義N個類似的事件方法?如果進攻的目標是隨即確定的,那又該怎么去寫?如果步兵同時監聽"戰地指揮部"的廣播,他怎樣根據不同的指揮者采取不同的措施?步兵并不能確定一個'on進攻'消息是來自司令部還是'戰地指揮部'呀。所以說,AsBroadcaster類的第一個局限就是它雖然廣播了一個'消息',卻不能給出消息的具體說明。
          2、我們知道戰爭時期為了做到策略的"因時因地制宜",常常會設一個"戰地指揮部"。假設我們希望把步兵的進攻的指揮權交給"戰地指揮部",而把步兵的駐守權交給"司令部"。因為司令部同時擁有裝甲兵和炮兵的進攻與駐守的指揮權,所以它可以廣播"on進攻"消息,但一件意想不到事將會發生:步兵也跟著進攻了!
          為了防止出現差錯,司令部就不得不在進攻前"removeListener(步兵)"。但為了防止廣播 "on駐守"消息時步兵不再駐守,所以在廣播完"on進攻"消息后必須再次"addListener(步兵)"。司令部何其累哉!所以說,AsBroadcaster類的第二個局限就是它注冊了一個監聽者,卻并不關心監聽者到底是監聽它的什么事件。
          3、AsBroadcaster類的第三個局限其實是由第二個局限來的,就是它有些情況下會造成運行的低效。假設還有一支空軍, 它有"on空襲"事件方法,并且歸司令部指揮。當司令部廣播"on空襲"消息時,得,步兵、裝甲兵和炮兵就會也試圖執行"on空襲"事件方法,當然是浪費時間啦.

          說了AsBroadcaster類這么多局限的地方,并不是說AsBroadcaster類不好,而是說要根據情況選擇使用不同的事件機制。如果不涉及到上面說的幾種情況,用AsBroadcaster類其實很方便的(比EventDispatcher類要省事)。也正因為AsBroadcaster類有這么多局限的地方,才使我們的主角EventDispatcher類等上了光輝的舞臺,請看我們下篇的講述吧!
          ------------------------------------------------------------------------
          補充1:
          AsBroadcaster.initialize(o)方法會為o創建一個"_listener"數組,它用來存儲所有的監聽者對象。
          補充2:
          FlashMX 2004里還有個mx.transitions.BroadcasterMX類,它比mx.events.AsBroadcaster的功能要強大,支持廣播消息時附帶更多的參數,可以對消息進行更多描述。感興趣的朋友可以訪問我的論壇
          http://www.wiyiflash.com/bbs 里的特別教程。

          轉貼請注明:[維藝--Flash]原創作品 ,謝謝!


          從AsBroadcaster到EventDispatcher(下) [作者:wiyiflash]

          [ 2005-07-29 01:19:42 | 發布: N神 ]
          字體大小: | |
          在上篇中我們提到了AsBroadcaster類包裝的廣播器作為事件源的諸多限制,現在就看看EventDispatcher(派遣)類是如何拓展事件源的功能吧。
          EventDispatcher類有2個靜態方法:
          ----------------------------------------------
          static function initialize(object:Object):Void
          //object:對象
          //initialize:初始化方法,為對象object附加上作為事件源(在這里可以理解為派遣中心吧)的各項功能。
          static function _removeEventListener(queue:Object, event:String, handler):Void
          //一個內部方法,注銷監聽事件源相關事件的監聽者
          -------------------------------------------------
          EventDispatcher類有4個公共方法:
          function dispatchEvent(eventObj:Object):Void
          /*事件派遣方法,向外界廣播一個消息,并附有關于消息的相關描述(請與broadcastMessage(msg:String)方法比較)
          eventObj:事件對象,它至少應含有2個屬性,假設司令部為一個事件派遣中心,一般定義如下:
          var eventObj=new Object();
          eventObj.target=司令部;//定義廣播消息的對象
          eventObj.type="on進攻";//定義消息的具體類型

          其中target屬性也可以不定義,dispatchEvent方法會將它設為默認的廣播消息的對象。
          */
          function dispatchQueue(queueObj:Object, eventObj:Object):Void
          /*這個方法的中文意思,我根據它的功能將它稱為"事件傳達"。
          queueObj:一個事件派遣中心對象
          eventObj:事件對象,注意:與 dispatchEvent不同,它的target并無默認值,需要你手工設定.
          為什么將這個方法稱為事件傳達呢?因為它可以讓當前的事件派遣中心指示另一個事件派遣中心(方法的第一個參數)向外界廣播消息。其實在dispatchEvent方法的內部就調用了dispatchQueue,只是將參數queueObj設為當前的事件派遣中心罷了。
          */
          function addEventListener(event:String, handler):Void
          /*注冊某個事件的監聽者
          event:監聽的事件名稱
          handler:監聽事件的對象
          這個方法與AsBroadcaster類的addListener方法相比,多出了參數event,
          明確了所監聽的具體事件。
          */
          function removeEventListener(event:String, handler)
          /*注銷某個事件的監聽者
          event:事件名稱
          handler:要注銷的監聽事件的對象
          這個方法與AsBroadcaster類的removeListener方法相比,多出了參數event,明確了從哪個事件中注銷監聽對象。
          */
          ----------------------------------------------------------
          下面就讓我們在戰場上實戰一下EventDispatcher吧。假設有兩個指揮中心,一個是司令部,一個是戰地指揮部。有三個兵種,分別是炮兵、步兵和敢死隊。司令部可以指揮炮兵的進攻、駐守和步兵的駐守,戰地指揮部可以指揮步兵的進攻、沖鋒和敢死隊的沖鋒,并且司令部可以向戰地指揮部傳達指示。下面是實現上述復雜關系的代碼:
          -----EventDispatcher測試.fla 開始-----
          import mx.events.EventDispatcher;
          //導入 mx.events.EventDispatcher類
          var 司令部 = new Object();
          司令部.名稱 = "司令部";
          EventDispatcher.initialize(司令部);
          //為司令部對象附加上派遣中心的相關功能。
          var 戰地指揮部 = new Object();
          戰地指揮部.名稱="戰地指揮部";
          EventDispatcher.initialize(戰地指揮部);
          //為戰地指揮部對象附加上派遣中心的相關功能。

          var 步兵 = new Object();
          步兵.on進攻 = function(eventObj) {
               //步兵的'on進攻'事件處理方法,記住需要有參數
          var 來自=eventObj.target.名稱;
               //eventObj.target引用廣播'on進攻'事件的對象,用它可以訪問事件源并反饋消息。
          var 陣地=eventObj.陣地;
                //獲取事件的關于' 陣地'屬性值
          trace("步兵接到"+來自+"來電,輕裝上陣,火速向敵方"+陣地+"前進!");
          };
          步兵.on駐守 = function(eventObj) {
          var 來自=eventObj.target.名稱;
          trace("步兵接到"+來自+"來電,就地待命,多設崗哨,嚴防來犯之敵!");
          };
          步兵.on沖鋒=function(eventObj){
          var 來自=eventObj.target.名稱;
          var 陣地=eventObj.陣地;
          trace("步兵接到"+來自+"來電,向敵方"+陣地+"發起沖鋒!");

          }
          司令部.addEventListener("on駐守", 步兵);
          //向司令部的'on駐守'事件注冊監聽對象'步兵'
          戰地指揮部.addEventListener("on進攻", 步兵);
          //向司令部的'on進攻'事件注冊監聽對象'步兵'
          戰地指揮部.addEventListener("on沖鋒",步兵);
          //向戰地指揮部的'on沖鋒'事件注冊監聽對象'步兵'
          var 炮兵 = new Object();
          炮兵.on進攻 = function(eventObj) {
          var 來自=eventObj.target.名稱;
          var 陣地=eventObj.陣地;
          trace("炮兵接到"+來自+"來電,向敵方"+陣地+"陣地猛烈轟擊!");
          };
          炮兵.on駐守 = function(eventObj) {
          var 來自=eventObj.target.名稱;
          trace("炮兵接到"+來自+"來電,就地待命,保證彈藥準備充足!");
          };
          司令部.addEventListener("on駐守", 炮兵);
          司令部.addEventListener("on進攻", 炮兵);
          var 敢死隊=new Object();
          敢死隊.on沖鋒=function(eventObj){
          var 來自=eventObj.target.名稱;
          var 陣地=eventObj.陣地;
          trace("敢死隊接到"+來自+"來電,向敵方"+陣地+"發起沖鋒!拼死也要拿下!");
          }
          戰地指揮部.addEventListener("on沖鋒",敢死隊);

          //---------------------------------------------------------------------
          trace("司令部指示:");
          var eventObj1 = new Object();
          //定義事件對象eventObj1
          eventObj1.target = 司令部;
          //定義事件對象eventObj1的target屬性值為司令部
          eventObj1.type = "on進攻";
          //定義事件對象的事件類型為'on進攻'
          eventObj1.陣地="505陣地"
          //一個自定義的屬性'陣地',你可以附加更多其他的屬性
          司令部.dispatchEvent(eventObj1);
          //司令部將定義好的事件對象廣播出去,只有向它注冊了'on進攻'屬性的監聽對象才能收到。步兵并不會發動進攻。
          trace("戰地指揮部指示:");
          var eventObj2=new Object();
          //eventObj2.target=戰地指揮部;
          //因為dispatchEvent方法會自動將事件對象的target屬性設為默認的廣播消息的對象,所以這句也可以注釋掉。
          eventObj2.type = "on進攻";
          eventObj2.陣地="105陣地"
          戰地指揮部.dispatchEvent(eventObj2);
          trace("傳達司令部指示:");
          var eventObj3=new Object();
          eventObj3.target=戰地指揮部;
          //這里必須設定事件對象的target屬性。因為dispatchQueue不會為target屬性設定默認值
          eventObj3.type="on沖鋒";
          eventObj3.陣地="123陣地";
          司令部.dispatchQueue(戰地指揮部,eventObj3);
          //戰爭時期也許司令部并不知道前線部隊的布置情況,所以它可以將指令傳達給戰地指揮部,由戰地指揮部將事件對象廣播給向自己的相關事件注冊的監聽對象
          -----EventDispatcher測試.fla 結束-----
          具體的測試結果我就不貼出來了。最后說說EventDispatcher類的幾個有趣的地方:
          1、監聽事件的對象可以是Object、MovieClip,還可以是Function.例如:
          假設在戰場上每當發起沖鋒時,都要吶喊助威,可以這樣寫:
          function 鼓勵士氣(){
          trace("沖啊!殺啊!");
          }
          戰地指揮部.addEventListener("on沖鋒",鼓勵士氣);
          2、當監聽事件的對象是自身時,一般的寫法是這樣的:
          戰地指揮部.on沖鋒=function(){
          trace("同志們,我們一定會取得最后的勝利!");
          }
          戰地指揮部.addEventListener("on沖鋒",戰地指揮部);
          但是還有一種更簡潔的寫法:
          戰地指揮部.on沖鋒Handler=function(){
          trace("同志們,我們一定會取得最后的勝利!");
          }
          這種寫法不再需要用"addEventListener"來注冊了。它有兩點需要注意,一是它總在其他監聽對象的事件處理之前執行,再就是它無法用'removeEventListener'方法注銷監聽。
          3、監聽對象的事件處理程序也可以這樣寫:
          步兵.handlerEvent=function(eventObj){
          var 來自=eventObj.target.名稱;
          var 陣地=eventObj.陣地;
          var e=eventObj.type;
          switch(e){
          case "on進攻":
          trace("步兵接到"+來自+"來電,輕裝上陣,火速向敵方"+陣地+"前進!");
          break;
          case "on駐守":
          trace("步兵接到"+來自+"來電,就地待命,多設崗哨,嚴防來犯之敵!");
          break;
          case "on沖鋒":
          trace("步兵接到"+來自+"來電,向敵方"+陣地+"發起沖鋒!");
          break;
          default:
          break;
          }
          司令部.addEventListener("on駐守", 步兵);
          戰地指揮部.addEventListener("on進攻", 步兵);
          戰地指揮部.addEventListener("on沖鋒",步兵);

          好了,關于EventDispatcher類到此就介紹完了,希望大家能夠掌握Flash的事件機制并靈活地運用它們。
          如果文章對你有幫助,請支持Google+Firefox





          永久地址永久地址: http://www.nshen.net/blog/feed.asp?q=comment&id=329

          瀏覽模式: 閱讀全文 | 評論: 3 | 引用: 27 | Toggle Order | 閱讀: 2039
          1 | 2 | >
          引用2ss*
          [ 2005-10-07 09:19:05 ]
          你好:
          我看了你的教程,寫得很不錯啊!可是我在用下面的代碼測試時,對象方法中的代碼沒有執行,不知道是為什么?下面是我用的代碼!
          /*-----EventDispatcher測試.fla 開始-----*/
          //導入 mx.events.EventDispatcher類
          import mx.events.EventDispatcher;
          var command:Object = new Object();
          EventDispatcher.initialize(command);
          command.addEventListener("onAssault", soldiers;
          var soldiers:Object = new Object();
          soldiers.onAssault = function(eventObj:Object) {
          ??trace("沖啊!");
          };
          command.dispatchEvent({type:"onAssault"});
          引用N神
          [ 2005-10-07 11:07:47 ]
          soldiers.onAssault = function 這種方式賦值函數的話要在后邊再addListener,正確代碼在下邊

          import mx.events.EventDispatcher;
          var command:Object = new Object();
          EventDispatcher.initialize(command);
          var soldiers:Object = new Object();
          soldiers.onAssault = function(eventObj:Object) {
          trace("沖啊!");
          };
          command.addEventListener("onAssault", soldiers)
          command.dispatchEvent({type:"onAssault"});

          [redface] ps。這篇教程是轉載的,是wiyi寫的
          posted on 2006-10-08 11:21 blog搬家了--[www.ialway.com/blog] 閱讀(434) 評論(0)  編輯  收藏 所屬分類: AS2.0
          主站蜘蛛池模板: 罗城| 武威市| 伊金霍洛旗| 郑州市| 宁波市| 绵阳市| 建始县| 乐亭县| 平遥县| 南投县| 南充市| 临夏县| 筠连县| 舟曲县| 宁远县| 平乐县| 望奎县| 读书| 肥东县| 尚志市| 高台县| 延寿县| 远安县| 临夏县| 阿拉善右旗| 富源县| 陆河县| 屏东县| 宣城市| 嵩明县| 贵南县| 体育| 精河县| 山丹县| 白朗县| 晋城| 泸西县| 长宁县| 建瓯市| 绥化市| 五原县|