标签:
以前学习js的时候,就看到不少关于JS 事件介绍的资料,有些零零散散,都没有个统一的文章,自己也没记录过统一的资料,只知道平时敲onlcik,on,bind,linve之类的事件代码,也没太关注过事件模型的整体概览.
1.什么时候事件?
可以说是网页上发生的事,当我们浏览页面进行某些类型的交互时,事件就发生了,一个鼠标动作,键盘操作,比如用户点击按钮提交个表单会有个submit事件.点击个按钮弹出个弹出层等等,这些都是事件.事件被封装成(evet)对象,这个对象包含改事件发生时所产生的相关信息.
1.2event事件对象的常用属性,方法:clientX/clientY,鼠标距离浏览器可视区域X,Y点的距离pageX/pageY,距离页面X/Y点的距离screenX/screenY,距离屏幕X/Y点距离,offsetX/offsetY.距离定位属性的父元素上的距离
2.事件的三中模型
书写方式直接通过JS代码作为HTML性质值完成事件绑定:1.HTML代码中指定属性值:<input type=”button” onclick=”chanBack()” value=""/>
2.在js中指定属性:
var input = document.getElementsByTagName(‘input’);
input.onclick(function(){
alert(‘点击了input‘);
});
IE事件中,IE把它作为全局对象window的一个属性”.用IE8执行了代码alert(window.event),结果弹出是null,说明该属性已经定义,只是值为null(与undefined不同).在IE中,每个元素和window对象都有两个方法:attachEvent方法和detachEvent方法。
1 element.attachEvent("onevent",eventListener);
此方法的意思是在IE中要想给一个元素的事件附加事件处理函数,必须调用attachEvent方法才能创建一个事件监听器。attachEvent方法允许外界注册该元素多个事件监听器。
attachEvent接受两个参数。第一个参数是事件类型名,第二个参数eventListener是回调处理函数。这里得说明一下,有个经常会出错的地方,IE下
利用attachEvent注册的处理函数调用时this指向不再是先前注册事件的元素,这时的this为window对象。还有一点是此方法的事件类型名称必须加上一个”on”的前缀(如onclick)。
1 element.attachEvent("onevent",eventListener);
var test = document.getElementById("test");
test.attachEvent(‘onclick‘,function(){
alert(‘给我个东西‘);
});
2.要想移除先前元素注册的事件监听器,可以使用detachEvent方法进行删除,参数相同
ps:这里是不是想起了JQ中的on
$(‘#id‘).on(‘click‘,function(){
});
此模型是W3C制定的标准模型,既然是标准,那大家都得按这个来,我们现在使用的现代浏览器(指IE6~8除外的浏览器)都已经遵循这个规范。W3C制定的事件模型中,一次事件的发生包含三个过程:
(1)capturing phase:事件捕获阶段。事件被从document一直向下传播到目标元素,在这过程中依次检查经过的节点是否注册了该事件的监听函数,若有则执行。
(2)target phase:事件处理阶段。事件到达目标元素,执行目标元素的事件处理函数.
(3)bubbling phase:事件冒泡阶段。事件从目标元素上升一直到达document,同样依次检查经过的节点是否注册了该事件的监听函数,有则执行。
所有的事件类型都会经历captruing phase但是只有部分事件会经历bubbling phase阶段,例如submit事件就不会被冒泡。
标准的事件监听器绑定:
addEventListener("eventType","handler","true|false");
监听器的移除:removeEventListner("eventType","handler","true!false");
1 //标准语法 element.addEventListener(‘event‘, eventListener, useCapture);
2 //默认 element.addEventListener(‘event‘, eventListener, false);
addEventListener 方法接受3个参数。第一个参数是事件类型名,值得注意的是,这里事件类型名称与IE的不同,事件类型名是没’on’开头的;第二个参数eventListener是回调处理函数(即监听器函数);第三个参数注明该处理回调函数是在事件传递过程中的捕获阶段被调用还是冒泡阶段被调用 ,通常此参数通常会设置为false(为false时是冒泡),那么,如果将其值设置为true,那就创建一个捕捉事件监听器.
移除已注册的事件监听器调用element的removeEventListener方法即可,参数相同.
语法:
1.//标准语法element.removeEventListener(‘event‘, eventListener, useCapture);
2 //默认 element.removeEventListener(‘event‘, eventListener, false);
以上便是事件的三种模型,我们在开发的时候需要兼顾IE与非IE浏览器,所以注册一个监听器应该这样写:
var a = document.getElementById(‘a‘);
if(a.attachEvent){
a.attachEvent(‘onclick‘,func);
}else{
a.addEventListener(‘click‘,func,false);
}
事件冒泡:我们来看个例子
<div id=“div1”>
<div id=“div2”>
<div id=“div3”></div>
</div>
</div>
事件冒泡:当一个元素接收到事件的时候,会把他接收到的所有传播给他的父级,一直到顶层window。我们称为事件冒泡机制
想要阻止事件冒泡 可以用 取消事件冒泡(stopPropagation)和取消事件的默认行为(preventDefault)。
preventDefault 取消事件的默认动作
stopPropagation 函数可以阻止当前事件向祖辈元素的冒泡传递,就是阻止冒泡
dispatchEvent 事件触发器这个不常用过,参考网上找到相关资料说是对自定义事件的一个触发
var btn = document.getElementById(‘A‘);
btn.onclick=function(e){
alert(‘点击了a‘);
e.stopProgagation();
//某些时候也用 return false
}
先假设我们有一个自定义事件类型MyEvent.OPEN_QQ(打开QQ的自定义事件)
首先定义一个显示对象(注意所有显示对象都是EventDispatcher的直接或间接子类,EventDispatcher中定义了dispatchEvent方法)
var a:Sprite = new Sprite();
a.addEventListener(MyEvent.OPEN_QQ, openqq); //添加打开QQ这个事件的监听器
最关键的地方来了:当你打开qq时,理论上讲你已经触发了打开qq这个事件。但是由于MyEvent.OPEN_QQ事件是一个自定义事件,flash系统是不可能通知a对象已经发生了MyEvent.OPEN_QQ这个事件的,这里就必须有一种让a知道发生了MyEvent.OPEN_QQ这个事件的一种机制,于是dispatchEvent登场了,你在任何时候调用如下面的语句3,flash都会告知a已经发生了MyEvent.OPEN_QQ这个事件,你可以执行了相应的事件处理函数了(此处为openqq),于是openqq(e:MyEvent)函数被执行。
a.dispatchEvent(new MyEvent(MyEvent.OPEN_QQ));
事件代理:
在传统的事件处理中,你根据需求给每一个元素添加或者 删除事件处理器
1利用冒泡的原理把事件加到父级上触发执行效果.
2好处,提高性能.新添加的标签也能应用事件.
看个例子
实际开发中,我们可能会动态生成很多个。此时就需要我们每生成一个li 就给这个li 绑定一个点击事件。效率低,容易出错,如果有N多个,就可以改成事件代理的方式
Oul.onmouseover=function(){
This//这里的this指向了oul 而不是想象中指向操作的种指定的元素,这里就可以用到target了
}
event对象中有个事件源:不管在哪个事件中,只要你操作的那个元素就是事件源
ie : window.event.srcElement 标准下:event.target
不用循环了,根据事件源就能找到当前操作的那个元素.上面的列子种看到target 的用法,下面我们再来看看WEC上官方的给的例子
E.target 和e.currentTarget
target 属性规定哪个 DOM 元素触发了该事件。显示哪个 DOM 元素触发了事件:
来看看w3c上的例子
<h1>这是一个标题</h1>
<h2>这是另一个标题</h2>
<p>这是一个段落</p>
<button>这是一个按钮</button>
<p>标题、段落和按钮元素定义了一个点击事件。如果您触发了事件,下面的 div 会显示出哪个元素触发了该事件。</p>
<div></div>
$(document).ready(function(){
$(“p,button,h1,h2”).click(function(e){
$(“div”).html(“点击事件由一个”+e.target.nodeName+”元素触发”);
})
});
也来看看W3C上资料说事件属性返回其监听器触发事件的节点,即当前处理该事件的元素、文档或窗口.我的理解是 返还当前是那个元素处理的,返还改元素
<p id="p1" onmousedown="getEventTrigger(event)">
Click on this paragraph. An alert box will
show which element triggered the event.
</p>
function getEventTrigger(event)
{
x=event.currentTarget;
alert("The id of the triggered element: "
+ x.id);
}
currentTarget在事件流的捕获,目标及冒泡阶段。只有当事件流处在目标阶段的时候,两个的指向才是一样的, 而当处于捕获和冒泡阶段的时候,target指向被单击的对象而currentTarget指向当前事件活动的对象(一般为父级)
标签:
原文地址:http://www.cnblogs.com/f2eo/p/5647246.html