我有一个包含多个backbone.js视图的单页Web应用程序。这些观点有时必须相互沟通。两个例子:
要尽可能地分离视图,我目前使用自定义事件来传递数据($(document).trigger('customEvent', data)
)。有一个更好的方法吗?
答案 0 :(得分:14)
一种广泛使用的技术是扩展Backbone.Events
对象以创建您的个人全局事件聚合器。
var vent = {}; // or App.vent depending how you want to do this
_.extend(vent, Backbone.Events);
根据您是否使用requirejs或其他内容,您可能希望将其分隔为自己的模块或将其作为Application对象的属性。现在,您可以在应用中的任何位置触发和收听事件。
// View1
vent.trigger('some_event', data1, data2, data3, ...);
// View2
vent.on('some_event', this.reaction_to_some_event);
这也允许您使用事件聚合器在模型,集合,路由器等之间进行通信。Here is Martin Fowler's concept for the event aggregator(不是在javascript中)。这是一个更多的backboney实现和反思这个主题,更多的是Backbone.Marionette,但大部分都适用于vanilla Backbone。
希望这有帮助!
答案 1 :(得分:8)
我同意@jakee的第一部分
var vent = {};
_.extend(vent, Backbone.Events);
然而,用" on"听一个全球性的事件。可能会导致内存泄漏和僵尸视图问题,并且还会导致多个操作处理程序调用等。
而不是" on",你应该使用" listenTo"在你看来
this.listenTo(vent, "someEvent", yourHandlerFunction);
因此,当您通过view.remove()
删除视图时,此处理程序也将被删除,因为处理程序已绑定到您的视图。
触发全局事件时,只需使用
即可vent.trigger("someEvent",parameters);
答案 2 :(得分:0)
jakee's answer建议我自己使用的一种很好的方法,但还有另一种有趣的方法,那就是将一个对象的引用注入到每个视图实例中,注入的对象依次包含对as的引用。你希望聚合的许多观点。
本质上,view-aggregator是一种“App”对象,可以附加视图旁边的东西,例如集合。它确实涉及扩展视图,因此可能不是每个人的口味,但另一方面,扩展是一个简单的例子。
我使用http://arturadib.com/hello-backbonejs/docs/1.html的代码作为我的ListView的基础,然后我得到了以下工作:
define(
['./listView'],
function (ListView) {
var APP = {
VIEWS : {}
}
ListView.instantiator = ListView.extend({
initialize : function() {
this.app = APP;
ListView.prototype.initialize.apply(this, arguments);
}
});
APP.VIEWS.ListView = new ListView.instantiator();
console.log(APP.VIEWS.ListView.app);
}
);