节点触摸事件和全局触摸事件之间的关系有点问题?

引擎版本是3.3.1

1.希望达到的效果
大家应该玩过大掌门这样子的游戏。这种游戏当你的手指在屏幕任意位置滑动的时候,手指的落点处都会有一个樱花的特效。同时你点击游戏里的按钮,滑动框之类的都是正常的可以交互的。也就是说这个手指落点的监听是不会影响到游戏里其他UI的监听的。它就像一个第三者一样,可以监听游戏里的任何位置的触摸事件。同时不会影响这些触摸事件的传递和分发。

2.于是我写了个例子,想要实现这个功能。

sprite1上监听的是节点的触摸事件:

@ccclass('Sprite1')
export class Sprite1 extends Component {
  // [1]
  // dummy = '';

  // [2]
  // @property
  // serializableDummy = 0;

  start() {
    this.node.on(Node.EventType.TOUCH_START, this.onTouchStart, this);
    this.node.on(Node.EventType.TOUCH_MOVE, this.onTouchMove, this);
    this.node.on(Node.EventType.TOUCH_END, this.onTouchEnd, this);
    this.node.on(Node.EventType.TOUCH_CANCEL, this.onTouchCancel, this);
  }


  onTouchStart() {
    log('Spr1 onTouchStart');
  }

  onTouchMove() {
    log('Spr1 onTouchMove');
  }

  onTouchEnd() {
    log('Spr1 onTouchEnd');
  }

  onTouchCancel() {
    log('Spr1 onTouchCancel');
  }
}

sprite2上监听的是全局的触摸事件

@ccclass('Sprite2')
export class Sprite2 extends Component {
  start() {
    systemEvent.on(SystemEvent.EventType.TOUCH_START, this.onTouchStart, this);
    systemEvent.on(SystemEvent.EventType.TOUCH_MOVE, this.onTouchMove, this);
    systemEvent.on(SystemEvent.EventType.TOUCH_END, this.onTouchEnd, this);
    systemEvent.on(SystemEvent.EventType.TOUCH_CANCEL, this.onTouchCancel, this);
  }


  onTouchStart() {
    log('Spr2 onTouchStart');
  }

  onTouchMove() {
    log('Spr2 onTouchMove');
  }

  onTouchEnd() {
    log('Spr2 onTouchEnd');
  }

  onTouchCancel() {
    log('Spr2 onTouchCancel');
  }
}

如上所示。但是运行起来的结果是,如果手指的落点先落在sprite1里的话,那么sprite2的触摸监听就无法触发。等我把sprite2上的sprite组件给禁用了之后。也是如此。
请问,这个效果合理吗? sprite1上的节点触摸事件吞噬了sprite2节点上的全局触摸事件。

如果就是这样子设计的话,那么请问我希望达到的效果应该怎么设计才合理?
yangqun.zip (1.0 MB)
附上demo。 场景是Test.scene.

全局触摸 不应该是挂在 canvas上面吗

let canvas = cc.director.getScene().getChildByName("Canvas");
canvas.on(cc.Node.EventType.TOUCH_START, this.onFullScreenTouchStart, this, true);
canvas.on(cc.Node.EventType.TOUCH_MOVE, this.onFullScreenTouchMove, this, true);
canvas.on(cc.Node.EventType.TOUCH_END, this.onFullScreenTouchEnd, this, true);
canvas.on(cc.Node.EventType.TOUCH_CANCEL, this.onFullScreenTouchCancel, this, true);

:relaxed:
666 挂在Canvas上。这个思路可以的

这是个思路,2.x适用
不知道3.3.x适不适用

canvas应该是最底层吧?这样的话点按钮事件不是会被吞噬然后就不会有樱花的特效了嘛?

挂在Canvas下,部分情况下,touchend不会触发

你看监听的第四个参数,是父节点在冒泡阶段捕获。这样子不管什么情况。,Canvas都会优先捕获到触摸事件的。

touchEnd和touchCancel会触发其中的一个。具体是那个要看你手指触摸的控件触发了哪个的

原来还可以这样,受教了

挂在canvas上,当sprite触发touchEnd时,canvas触发touchEnd,当sprite触发touchCancel时,canvas触发touchCancel, 总会触发一个

以前写2dx的,类似需求都是setSwallowTouches(false)去做的,冒泡这种还没用习惯

是的~~~

我加了一个粒子效果,touchEnd和touchCancel的时候this.Partic.stopSystem();但是有时候粒子一直在界面上,不会消失

该主题在最后一个回复创建后14天后自动关闭。不再允许新的回复。