Javascript 在原型中绑定事件处理程序,并且仍然保持对元素的引用
我希望能够在原型中使用绑定事件处理程序并保留我的“this”上下文。但这样做似乎破坏了prototype为事件处理程序提供的方便的默认绑定 从文档中: 处理程序的上下文(该值)设置为被观察的扩展元素(即使事件实际上发生在子元素上并冒泡) 这正是我想要的。一旦我将函数绑定到自己的上下文中,我能以任何方式访问这个“正在观察的元素”吗?我不能依赖e.element()来给我观察到的元素(它可能是子元素): 我知道有一个bindAsEventListener,但在这里似乎没有必要,而且我不知道在绑定函数后如何访问目标元素Javascript 在原型中绑定事件处理程序,并且仍然保持对元素的引用,javascript,events,prototypejs,Javascript,Events,Prototypejs,我希望能够在原型中使用绑定事件处理程序并保留我的“this”上下文。但这样做似乎破坏了prototype为事件处理程序提供的方便的默认绑定 从文档中: 处理程序的上下文(该值)设置为被观察的扩展元素(即使事件实际上发生在子元素上并冒泡) 这正是我想要的。一旦我将函数绑定到自己的上下文中,我能以任何方式访问这个“正在观察的元素”吗?我不能依赖e.element()来给我观察到的元素(它可能是子元素): 我知道有一个bindAsEventListener,但在这里似乎没有必要,而且我不知道在绑定函数
我也知道有一个e.currentTarget,但它在IE中不起作用,是吗?我最近也遇到了这个问题。我的答案是将函数封装在另一个函数中,该函数完成您需要的工作。我可能弄乱了订单,但是
curry
会将this
添加到匿名函数的参数中,然后您从那里重新订购
initialize: function() {
Event.observe('foo', 'click',
function(e,that) { that.addItem(e,this); }.curry(this)
);
},
addItem: function(evt, evtElm) {
...
}
当您使用
.bind
时,您通过对观察到的元素的引用将被覆盖。如果您具有以下标记:
<div id="foo">
I am the Foo
<button id="bar">I am the Bar</button>
</div>
但是,如果希望使用类方法作为事件处理程序,因此需要使用.bind
,那么解决方案是在首次绑定事件时将观察到的元素的标识符作为事件处理程序的参数之一,如下所示:
var Test = Class.create({
initialize: function() {
Event.observe('foo', 'click', this.greenEggsAndHam.bind(this, 'foo'));
},
greenEggsAndHam: function (el, evt) {
console.log('Observed Element: %o', $(el));
console.log('Clicked Element: %o', $(evt.element()));
console.log('Class reference: %o', this);
}
});
var T = new Test();
也就是说,为了保持一致性,我建议您使用.bindAsEventListener
而不是.bind
,并将事件处理程序更改为函数(evt,el){
,以便事件对象是第一个参数,观察到的元素是第二个参数
function greenEggsAndHam (evt) {
console.log('Observed Element: %o', this);
console.log('Clicked Element: %o', $(evt.element()));
}
Event.observe('foo', 'click', greenEggsAndHam);
var Test = Class.create({
initialize: function() {
Event.observe('foo', 'click', this.greenEggsAndHam.bind(this, 'foo'));
},
greenEggsAndHam: function (el, evt) {
console.log('Observed Element: %o', $(el));
console.log('Clicked Element: %o', $(evt.element()));
console.log('Class reference: %o', this);
}
});
var T = new Test();