2010-01-06 80 views
2

我正在構建一個加載外部SWF的專用查看器應用程序。如何檢查鼠標是否可以點擊?

var content:Sprite = ... 
content.addChild(loader); 

我聽我的頂級內容Sprite MOUSE_OVER和MOUSE_OUT事件。 over處理程序隱藏默認光標並顯示一個自定義(縮放)光標。 輸出處理程序將光標變回默認值。

當鼠標位於外部加載的SWF中的可點擊項目(如按鈕或文本鏈接)上時,我想要實現的不是顯示縮放光標。

當前代碼完美適用於AVM1 swfs。 問題在於使用AS3加載的swfs。 對於這些內容MOUSE_OUT被觸發,並立即觸發MOUSE_OVER,所以光標仍然是錯誤的。

這可能歸結爲:如何檢查鼠標是否超過可點擊的內容子項?

回答

0

隨着一些測試和喬治給我的暗示,這是內容MOUSE_OVER監聽我只寫(在haXe的),這似乎工作:

public var mouseOverClickableContent:Bool; 

private function onOverContentChild(event) 
{ 
    mouseOverClickableContent = false; 
    if (event.target != content) 
    { 
     var obj:flash.display.InteractiveObject = cast event.target; 

     while (obj != content) 
     { 
      if ( obj.hasEventListener(flash.events.MouseEvent.CLICK) 
       || obj.hasEventListener(flash.events.MouseEvent.MOUSE_UP) 
       || obj.hasEventListener(flash.events.MouseEvent.MOUSE_DOWN) 
       || (Std.is(obj, Sprite) && cast(obj, Sprite).buttonMode) 
      ){ 
       mouseOverClickableContent = true; 
       break; 
      } 
      obj = obj.parent; 
     } 
    } 


} 

遺憾的是,似乎有沒有辦法檢測鼠標是否在TextField htmlText鏈接上,所以我可以在那裏添加一個TextField htmlText.indexOf("<a") != -1檢查。

除非有人知道檢測mouse-over-textfield-links的技巧嗎?

4

好問題!

我做了一個快速測試。有一種稱爲getObjectsUnderPoint()方法,其

返回位於 指定點下,並且是 孩子(或孫子,等等)對象的數組該DisplayObjectContainer的 實例

根據到文檔。

而且

是 無法進入安全考慮任何子對象 從返回數組省略。到 確定此安全 限制是否影響返回 陣列,調用 areInaccessibleObjectsUnderPoint() 方法。

所以我不知道這可能有多大的幫助。

這裏是我的測試還是:

//make some clips interactive 
for(var i:int = 0 ; i < numChildren ; i+=2){ 
    MovieClip(getChildAt(i)).mouseEnabled = true; 
    MovieClip(getChildAt(i)).buttonMode = true; 
    MovieClip(getChildAt(i)).mouseChildren = false; 
} 
//reuse this array 
var clips:Array; 
addEventListener(Event.ENTER_FRAME, checkClickables); 
function checkClickables(event:Event):void { 
    clips = this.getObjectsUnderPoint(new Point(mouseX,mouseY)); 
    for(i = 0 ; i < clips.length ; i++){ 
     if(isInteractiveObject(clips[i])){ 
      trace(clips[i]); 
     } 
    } 
} 
function isInteractiveObject(object:*):Boolean{ 
    var extendsClass:XMLList = describeType(object).extendsClass; 
    for each(var classDef:XML in extendsClass){ 
     if([email protected] == 'flash.display::InteractiveObject') return true; 
    } 
    return false; 
} 

我在舞臺上的一些片段,我正在做一些他們的「點擊」。 的onEnterFrame然後我檢查是否有InteractiveObject的子類 (超類的任何東西可點擊)

的任何實例出於某種原因,在我的測試,getObjectsUnderPoint()只返回形狀對象,沒有精靈。 也許它可能在你的配置中工作。

此外它似乎有點複雜。

這裏是我的第二個方法:

function getInteractiveObjects(container:DisplayObjectContainer):Array{ 
    var result:Array = []; 
    for(var i:int = 0 ; i < container.numChildren ; i++){ 
     if(container.getChildAt(i) is Sprite || container.getChildAt(i) is MovieClip) result.push(container.getChildAt(i)); 
     if(container.getChildAt(i) is DisplayObjectContainer){ 
      var clips:Array = getInteractiveObjects(DisplayObjectContainer(container.getChildAt(i))); 
      var clipsNum:int = clips.length; 
      for(var j:int = 0 ; j < clipsNum ; j++) 
       if(clips[j] is Sprite || clips[j] is MovieClip) result.push(clips[j]) 
     } 
    } 
    return result; 
} 

使用遞歸函數獲取潛在目標的交互剪輯一個內部(如加載的內容)。如果它是Sprite或MovieClip,它是'可點擊的'。

var iclips:Array = getInteractiveObjects(this); 
for(i = 0 ; i < iclips.length ; i++){ 
    trace(iclips[i].name); 
    //do extra tests here 
    if(iclips[i].hasEventListener(MouseEvent.ROLL_OVER)) trace(iclips[i].name + ' has roll over'); 
    //etc. 
} 

那麼你可以做額外的測試,這取決於正是你要尋找的(無論它有和事件偵聽器的鼠標事件,要麼是將mouseEnabled,具有buttonMode設置爲true,等等)

這樣你就不需要檢查任何鼠標了(不必等待用戶交互或者始終調用一個函數),一旦你得到的剪輯不符合你的想法,你可以改變他們的行爲(mouseChildren = false,或其他)。

HTH