在Dart中,如果我听两个听众的点击事件,我怎么知道哪个先发生?

时间:2013-04-20 22:23:13

标签: dart dart-html

如果我写下面的Dart代码,我怎么知道哪个点击处理程序首先发生?

main() {
  var button = new ButtonElement();
  var stream = button.onClick.asBroadcastStream();

  stream.listen(clickHandler1);
  stream.listen(clickHandler2);
}

假设我在其他代码中对前两个点击处理程序一无所知,但我注册了另一个。

  • 我可以知道该流有两个侦听器吗?
  • 我可以暂停或取消所有其他订阅者吗?
  • 如果我再次在其他地方写button.onClick.asBroadcastStream(),它是否指向与main中使用的流相同的流?
  • 我可以在其中一个处理程序中说不将事件传递给其他广播监听器吗?那是消费者吗?

2 个答案:

答案 0 :(得分:6)

  

假设我在其他代码中对第一个代码一无所知   两个点击处理程序,但我注册了另一个。

     

我能知道该流有两个监听器吗?

不,你不能。你可以扩展流类或包装它并自己提供这个功能,但它不是一个好的设计选择,因为我认为听众不应该知道其他的听众。你准备做什么?也许有一种比让听众了解对方更好的方式。

  

我可以暂停或取消所有其他订阅者吗?

您只能cancel/pause/resume您正在处理的订阅者。同样,您可能不应该触及其他侦听器,但我猜您可以包装/扩展Stream类以实现此行为。

  

如果我在其他地方再次编写button.onClick.asBroadcastStream(),它是否指向与main中使用的相同的流?

不,至少不是当前版本的SDK。因此,遗憾的是,您需要在某处存储对此广播流的引用,并引用它,因为多次调用asBroadcastStream()将不会产生您可能期望的结果。 (注意:至少基于快速测试:http://d.pr/i/Ip0K虽然documentation似乎表明不同,但是当我找到时间时,我还没有再测试一下。)

  

我可以在其中一个处理程序中说不将事件传递给其他广播监听器吗?

嗯,HTML中有stopPropagation()这意味着事件不会传播到其他元素,但它可能不是你想要的。

为了能够在其他监听器中停止事件触发,需要有一个监听器被调用的顺序。我相信订单是那些听众的注册顺序。从设计的角度来看,我认为让听众取消/暂停其他人不是一个好主意。

HTML中的事件传播是有意义的,因为它是关于层次结构的,但是在这里我们没有(甚至在HTML中的事件的情况下,单个元素可以有多个侦听器)。

没有办法为听众分配权重或定义重要性顺序,因此没有办法阻止事件发生就不足为奇了。

不是让听众彼此了解并互相操纵,也许你应该试着想出另一种方法来处理你的问题(无论是什么)。

  

这是消费者吗?

StreamConsumer只是一个可以实现的类,如果您想允许其他流通过管道输入您的类。

答案 1 :(得分:1)

  

我能知道该流有两个监听器吗?

不,你有一个包含DOM事件处理的'Streream'。没有这样的功能。

  

我可以暂停或取消所有其他订阅者吗?

请看Event.stopPropagation()Event.stopImmediatePropagation(),可能Event.preventDefault()

  

如果我在其他地方再次编写button.onClick.asBroadcastStream(),它是否指向与main中使用的相同的流?

[更新]不,current implementation不会为您提供相同的Stream,因为onClick getter每次调用时都会返回一个新流。但是,返回的流已经是广播流,因此您不应在其上调用asBroadcastStream()。如果你这样做,你只需要获得对同一个对象的引用。

Stream<T> asBroadcastStream() => this;
  

我可以在其中一个处理程序中说不将事件传递给其他广播监听器吗?那是消费者吗?

再次,请查看Event.stopPropagation()Event.stopImmediatePropagation(),以及Event.preventDefault()