JavaScript触发多个事件,但只处理一次

JavaScript触发多个事件,但只处理一次,javascript,jquery,events,event-handling,eventtrigger,Javascript,Jquery,Events,Event Handling,Eventtrigger,我不知道我是否是第一个碰到这个问题,不想继续前进的人,但在我看来,其他人也应该经历过。另外,不要介意代码,因为我正在为这个示例编写代码。实际应用在思想上是相似的 假设您有以下对象控制某个模型: var model = $({ name: 'user', age: 30, sex: 'male' }); model.on( 'namechange agechange sexchange', function ( event ) { console.log( 'Mo

我不知道我是否是第一个碰到这个问题,不想继续前进的人,但在我看来,其他人也应该经历过。另外,不要介意代码,因为我正在为这个示例编写代码。实际应用在思想上是相似的

假设您有以下对象控制某个模型:

var model = $({
    name: 'user',
    age: 30,
    sex: 'male'
});

model.on( 'namechange agechange sexchange', function ( event ) {
    console.log( 'Model experienced a ' + event.type );
});

model.triggerHandler( 'namechange' );
上述代码的输出将是
模型经历名称更改

如果我想触发多个事件,代码如下所示:

model.triggerHandler( 'namechange' );
model.triggerHandler( 'agechange' );
model.triggerHandler( 'sexchange' );
输出将相应地重复

但我真正想要的是,当trigger方法触发处理程序绑定到的一个或多个事件时,处理程序被触发一次

model.triggerHandler( 'namechange agechange' ); // hander is bound to both but called once
model.triggerHandler( 'agechange' ); // hander is bound to one and called once
model.triggerHandler( 'namechange carchange agechange' ); // hander is bound to two of the three but called once
我确实理解由于订阅的工作方式而产生的技术限制。实现必须找出谁订阅了所有这些事件,加入结果,然后发布事件。更重要的是,event.type不是用来表示单个事件名称的

然而,我确信这些需求有一些用例。在我的例子中,它是一个动态度量小部件仪表板。有一个表示各种度量的度量结构。不同的度量在不同的时间间隔更新。不同的小部件依赖于多个指标。从服务器获取度量值时,我希望为每个度量值更改触发一个事件。小部件将刷新其数据。但是,我不希望依赖多个指标的小部件多次刷新。相反,我希望处理程序在通知该小部件的哪些指标已更改后立即启动(这将过滤掉与小部件无关的指标,使其不会进入处理程序)

我意识到我可以创建一个
metrics.update
事件,并传递一组已更改的指标。在处理程序中,我可以确定这是否与小部件有关。但理想情况下,我希望避免这一步

一个想法是定义一个jquery插件来缓冲使用预定义的“魔术”协议的事件:

model.bulkTriggerHandler( 'namechange agechange' );

插件>代码> BulktrgEdgRetrys可以解析事件字符串并考虑事件范围,然后可以遍历内部对象并找出它们订阅的事件(非常哈希)<代码> $.yDATA(对象,“事件”)< /COD>方法,为每个对象聚合它们各自的相关事件列表,并触发某个事件处理程序。此批量事件处理程序必须通过('bulkUpdate')上的

model.on(
)分配。。。但这一切都非常令人讨厌


无论如何,如果有任何评论,即使是那些说我应该坚持使用
metrics.update
的评论,我都将不胜感激,不要为上面的内容操心;)

不应该围绕触发,而应该围绕事件绑定。提供您自己的函数来绑定多个事件。它将为各个事件绑定自己的处理程序。此函数将跟踪发生了哪些事件,当列表中的所有事件发生时,它将调用提供的处理程序函数。调用方将其称为:

model.multiBind('namechange agechange', function() {
    ...
});

我知道这篇文章有点过时了,但也许我还能帮上忙

//Define a single function that takes an event object
function handleChange(event)
{
    // Log a string parameterized with event.type
    console.log( 'Model experienced a ' + event.type );
}

// Register handlers one at a time but reuse the function
model.on( 'namechange', handleChange);
model.on( 'agechange', handleChange);
model.on( 'sexchange', handleChange);
一次为N个事件定义一个处理程序有点酷,但这似乎是避免重复代码的一种方法

您始终可以编写一个实用函数,该函数接受数组或任意数量的位置参数,并在上重复执行
。我将被称为:

handle(model, ["namechange", "agechange", "sexchange"], handleChange);

您考虑过jquery bind()吗?没有,除非最近对.bind进行了修订,否则它的工作原理与.on方法类似。这里的问题不是绑定到事件,而是触发和处理它们。不能使用.trigger('eventA eventB'),而是立即处理它们。我刚刚发现一个票证被引发并解析为jquery的“wontfix:。并不要求触发所有绑定事件。当我执行model.triggerHandler('namechange')时,应该调用上面的处理程序;和model.triggerHandler('agechange');和model.triggerHandler('namechange agechange');电话。也许multiBind应该绑定到上述事件和一个特殊的“flush”事件,它的处理程序应该创建一个触发事件队列。要触发,.multiTrigger应触发其指定的每个事件,并以触发“刷新”事件结束。Flush会让multiBind知道“事务”已经完成,它可以分发事件。我想我误解了你的意思。您编写的我真正想要的是在发生多个更改时触发一个处理程序。所以我认为您应该等到所有不同的更改事件发生后再运行处理程序。