Egret屏蔽父类点击事件和事件流

Egret屏蔽父类点击事件和事件流

      • 屏蔽父类点击事件
      • Egret事件流
      • 总结

屏蔽父类点击事件

在父容器上添加sprite_1,在sprite_1上添加子对象sprite_2,分别添加点击事件
代码如下:

        let sprite_1: egret.Sprite = new egret.Sprite();
        sprite_1.touchEnabled = true;
        sprite_1.name = "sprite_1"
        sprite_1.graphics.beginFill(0x000);        
        sprite_1.graphics.drawRect(0, 0, 300, 300);
        sprite_1.graphics.endFill();
        this.addChild(sprite_1);

        let sprite_2: egret.Sprite = new egret.Sprite();
        sprite_2.touchEnabled = true;
        sprite_2.name = "sprite_2"
        sprite_2.graphics.beginFill(0xffffff);        
        sprite_2.graphics.drawRect(0, 0, 100, 100);
        sprite_2.graphics.endFill();
        sprite_1.addChild(sprite_2);
        sprite_1.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            console.log("sprite_1 点击");
        }, this);
        sprite_2.addEventListener(egret.TouchEvent.TOUCH_TAP,  (e: egret.TouchEvent)=> {
            console.log("sprite_2 点击");
        }, this);

Egret屏蔽父类点击事件和事件流_第1张图片

点击白块sprite_2运行结果:
运行结果1
可以看出点击时先触发了子对象sprite_2的事件然后又触发了父类sprite_1的点击事件。

sprite_2.addEventListener(egret.TouchEvent.TOUCH_TAP,  (e: egret.TouchEvent)=> {
    e.stopPropagation();
    console.log("sprite_2 点击");
}, this);

只需要在sprite_2的点击事件中调用stopPropagation即可防止对事件流中当前节点的后续节点中的所有事件侦听器进行处理

再次点击白块sprite_2运行结果:
运行结果2

Egret事件流

只要发生事件Egret就会调度(dispatchEvent)事件,如果事件在显示列表中,Egret则会将事件对象调度到显示列表,事件将在显示列表中穿行,直到到达事件目标。这个过程称为:捕获(CAPTURING_PHASE)->目标(AT_TARGET),当达到目标节点后事件会重新“回流”到根节点这个过程为:目标(AT_TARGET)->冒泡(BUBBLING_PHASE)

整个流程如图所示:

Egret屏蔽父类点击事件和事件流_第2张图片

怎么理解 举个例子还是上面的两个显示对象,分别给两个精灵添加冒泡和捕获事件,如下:

        // 监听冒泡阶段        
        sprite_1.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            console.log("sprite_1 冒泡");
        }, this, false);
        sprite_2.addEventListener(egret.TouchEvent.TOUCH_TAP,  (e: egret.TouchEvent)=> {
            console.log("sprite_2 冒泡");
        }, this, false);
        
        // 监听捕获阶段
        sprite_1.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            console.log("sprite_1 捕获");
        }, this, true);
        sprite_2.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            console.log("sprite_2 捕获");
        }, this, true);

点击子对象sprite_2,运行结果:

Egret屏蔽父类点击事件和事件流_第3张图片
阻止事件的捕获和冒泡:

        // 监听冒泡阶段        
        sprite_1.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            console.log("sprite_1 冒泡");
        }, this, false);
        sprite_2.addEventListener(egret.TouchEvent.TOUCH_TAP,  (e: egret.TouchEvent)=> {
            console.log("sprite_2 冒泡");
        }, this, false);
        
        // 监听捕获阶段
        sprite_1.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            e.stopPropagation();            
            console.log("sprite_1 捕获");
        }, this, true);
        sprite_2.addEventListener(egret.TouchEvent.TOUCH_TAP, (e: egret.TouchEvent)=> {
            console.log("sprite_2 捕获");
        }, this, true);

运行结果:
运行结果4

总结

  • 事件捕获由根节点向目标节点
  • 事件冒泡由目标节点向根节点
  • stopPropagation 可防止对事件流中当前节点的后续节点中的所有事件侦听器进行处理

你可能感兴趣的:(Egret游戏开发)