1. 什么是事件委托
事件:我们的点击(onclick), 鼠标经过/离开(onmouseover/onmouseout), 键盘摁下/松开(onkeypress/onkeyup)等行为就是一个个的事件。
委托:虽然是周末,我依然在上班,但我有个快递今天会到,我就让在家休假的女朋友帮我取了这个快递。这个过程称之为“委托”(本来该由我去做的事情我加到了别人-女朋友身上)。
事件委托: 由于事件的冒泡,我们点击子元素的时候,会把事件一层层的传递给父级元素。相反的,我们操作元素的时候,直接把事件绑定在父级元素上,而不是分别给子元素绑定事件。通过判断子元素,从而达到同样的效果,这就是所谓的“事件委托”。
2. 实现事件委托
我们要实现:鼠标移动到某个li的时候,字体颜色变为“红”,鼠标离开的时候,字体颜色变为“黑”。通常我们会遍历li元素,添加监听,代码如下:
<ul id="oParent">
<li>列表1</li>
<li>列表2</li>
<li>列表3</li>
<li>列表4</li>
<li>列表5</li>
</ul>
var oParent = document.getElementById('oParent');
var oChildren = oParent.getElementsByTagName('li');
var olen = oChildren.length;
for (var i = 0; i < olen; i++) {
oChildren[i].onmouseover = function() {
this.style.color = "red";
}
oChildren[i].onmouseout = function() {
this.style.color = "black";
}
}
效果如图所示:
试着把它改用事件委托的方式:
html代码不变,JS代码如下:
var oParent = document.getElementById('oParent');
var oChildren = oParent.getElementsByTagName('li');
oParent.onmouseover = function(element) {
var element = element || window.element;
var target = element.target || element.srcElement;
if (target.nodeName == "LI") {
target.style.color = 'red';
}
}
oParent.onmouseout = function(element) {
var element = element || window.element;
var target = element.target || element.srcElement;
if (target.nodeName == "LI") {
target.style.color = 'black';
}
}
我们假设这个时候有1000个li元素,此时要去循环1000次给每个li添加监听,这与我们所提倡的尽量减少DOM操作,尽可能提升性能是相违背的:占用内存大,耗费性能。用事件委托的方式,我们只用监听父元素oParent的事件,这样就减少了内存的占用,降低了性能损耗。