JS中事件委托或事件代理
1、事件委托的原理:
不是每个子结点单独设置事件监听器,而是事件监听器设置在其父结点上,然后利用冒泡原理影响设置每个子节点。
2、不使用事件委托的写法,需要进行大量的dom操作,影响程序的性能。
<body>
<ul>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
</ul>
<script>
// 事件委托的核心原理:给父节点添加监听器,利用事件冒泡影响每一个子节点
var ul = document.querySelector('ul');
var lis = ul.querySelectorAll('li');
for (var i = 0; i < lis.length; i++) {
lis[i].addEventListener('click', function() {
alert('我是一个弹窗')
})
}
</script>
</body>
3、应用事件委托:给ul注册点击事件,然后利用事件对象的target 来找到当前点击的li,因为点击li,时间会冒泡到ul上,ul有注册事件,就会触发监听器。
<body>
<ul>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
</ul>
<script>
// 事件委托的核心原理:给父节点添加监听器,利用事件冒泡影响每一个子节点
var ul = document.querySelector('ul');
var lis = ul.querySelectorAll('li');
ul.addEventListener('click', function(e) {
//利用排他思想去除其他元素的背景色,留下当前元素背景色
for (var i = 0; i < lis.length; i++) {
lis[i].style.backgroundColor = '';
}
e.target.style.backgroundColor = 'blue';
})
</script>
</body>
4、上面的事件委托还存在一个问题,就是我们注册的ul,当我们点击li外面的ul部分时背景颜色也会变,这时我们可以利用 nodeName 获取当前元素的名字,并判断是否是 li。
<body>
<ul>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
<li>我是一个li</li>
</ul>
<script>
// 事件委托的核心原理:给父节点添加监听器,利用事件冒泡影响每一个子节点
var ul = document.querySelector('ul');
var lis = ul.querySelectorAll('li');
ul.addEventListener('click', function(e) {
//利用排他思想去除其他元素的背景色,留下当前元素背景色
for (var i = 0; i < lis.length; i++) {
lis[i].style.backgroundColor = '';
}
//判断当前节点的名字是否是li,当点击到li以外的部分时背景色不变
// e.target 这个可以得到我们点击的对象
if (e.target.nodeName.toLowerCase() == 'li') {
e.target.style.backgroundColor = 'blue';
}
})
</script>
</body>
这样只有当我们点击到 li 时背景颜色才会改变
5、总结:我们利用事件委托,只操作一次DOM,提高了程序的性能