事件属性
传统注册事件的方式有唯一性,也就是同一个元素同一个事件只能设置一个处理函数,最后注册添加的的处理函数会覆盖前面注册添加的处理函数
解决办法 => 事件监听
事件流
- 事件冒泡 : 事件从子元素向父元素传播
- 事件捕获 : 事件从父元素向子元素传播
事件对象
- event 就是一个事件对象,写在 侦听函数的 小括号 里当作形参
- 事件对象只有有了事件才会存在,它是系统给我们自动创建的,不需要我们传递参数
- 事件对象是事件的一系列相关数据的集合,跟事件相关的,比如鼠标点击里面就包含鼠标的相关信息,鼠标坐标之类
事件对象方法
event.target // 返回触发事件的对象
event.srcElement // IE 返回触发事件的对象
event.type // 返回事件的类型
阻止默认事件
- 方法1 : 如果是 a 标签,直接更改 href=“javascript:void(0);”
- 方法2 : return false
- 方法3 : 调用event属性
ev.preventDefault // 标准浏览器
ev.returnValue // IE浏览器
兼容性写法
function prevDefault(evt) {
var ev = evt || window.event;
ev.preventDefault ? ev.preventDefault() : ev.returnValue=false;
}
阻止事件冒泡
标准浏览器
对象.stopPropagation();
IE浏览器
对象.cancelBubble = true
兼容性写法
function stopPro(evt) {
var ev = evt || window.event;
ev.stopPropagation ? ev.stopPropagation() : ev.cancelBubble = true;
}
事件委托
不是每个子节点单独设置事件监听器,而是事件监听器设置在其父节点上,然后利用冒泡原理影响设置每个子节点,提高了程序性能
父节点事件内部(event){
event.target.各种操作
}
// 选中父节点下的某个子节点,点谁谁触发
事件监听
事件的重复使用时,会出现覆盖问题
事件流描述的是从页面中接受事件的顺序,事件发生时会在元素节点之间按照特定的顺序传播这个传播过程称为DOM事件流
添加事件监听
// 标准浏览器
addEventListener(事件名,函数,boolean)
// 事件名加引号,不带on
// 函数真么写 函数名 匿名函数 "函数名(参数)"
// boolean
// true 事件捕获
// false 默认 事件冒泡
// iE浏览器
attachEvent(事件名,函数 )
兼容性写法
function addE(obj,type,fn){
obj.addEventListener ? obj.addEventListener(type,fn) : obj.attachEvent("on"+type,fn);
}
移除事件监听
removeEventListener(事件名,函数,boolean)
// 三个参数必须与添加的事件完全相同,才能移除事件
//IE浏览器
detachEvent(事件名,函数)
兼容性写法
function removeE(obj,type,fn){
obj.removeEventListener ? obj.removeEventListener(type,fn) : obj.detachEvent("on"+type,fn);
}
总结 : 平时用的时候,首推标准浏览器的事件监听,如果遇到要传递 this ,记得使用 call 来调用 fn
标准浏览器和ie浏览器的区别
- IE没有事件捕获
- IE的事件绑定, this 指向的 window ; 而标准浏览器指向的是调用该方法的 dom 对象
- IE不支持 event 对象,
但是IE支持 window.event 他就是标准浏览器的 event 对象
兼容性写法为
// 假如传入的参数是e
var ev = e || window.event
通过 attach 绑定的事件支持
注意 : 上面两种解决办法还有一个 bug : 无法获取 e.target 属性
IE支持的是 ev.srcElement
标准浏览器支持的是 ev.targe
function getTarget(ev) {
return ev.target ? ev.target : window.event.srcElement;
}