13.1 事件流
事件流描述的是從頁面中接收事件的順序。
當(dāng)瀏覽器發(fā)展到第四代時(shí)继低,瀏覽器開發(fā)團(tuán)隊(duì)遇到了一個(gè)很有意思的問題:頁面的哪一部分會(huì)擁有某個(gè)特定事件黑界?
針對(duì)這一個(gè)問題,IE提出了事件冒泡羹蚣,Netscape提出了事件捕獲
13.1.1 事件冒泡
即事件開始時(shí)由最具體的元素(文檔中嵌套層次最深的那個(gè)節(jié)點(diǎn))接收原探,然后逐級(jí)向上傳播到較為不具體的節(jié)點(diǎn)(文檔)。
13.1.2 事件捕獲
即不太具體的節(jié)點(diǎn)應(yīng)該更早接收到事件顽素,而最具體的節(jié)點(diǎn)應(yīng)該最后接收到事件踢匣。
由于老版本的瀏覽器不支持,因此很少有人使用事件捕獲戈抄。我們也建議大家放心的使用事件冒泡离唬,在有特殊需要時(shí)再使用事件捕獲。
13.1.3 DOM事件流
13.2 事件處理程序
響應(yīng)某個(gè)事件的函數(shù)叫做事件處理程序划鸽,比如onclick
13.2.1 HTML事件處理程序
<input type = 'button' value="Click me" onclick = 'showMsg()' />
function showMsg(){
}
缺點(diǎn):
(1) 存在時(shí)差問題输莺。如果showMsg定位在頁面最底部,用戶在showMsg函數(shù)未解析之前點(diǎn)擊按鈕裸诽,會(huì)發(fā)生錯(cuò)誤嫂用。
(2) 不同瀏覽器對(duì)其中作用域鏈理解不一樣。
(3) html和js耦合太嚴(yán)重丈冬。
13.2 DOM0級(jí)事件處理程序
var btn = document.getElementById('myBtn');
btn.onclick = function(){
alert(this.id); //myBtn
}
使用DOM0級(jí)方法指定的事件處理程序被認(rèn)為是元素的方法嘱函,因此,程序中的this引用當(dāng)前元素埂蕊。
13.2.3 DOM2級(jí)事件處理程序
即事件監(jiān)聽往弓。使用addEventListener()和removeEventListener();
13.2.4 IE事件處理程序
事件監(jiān)聽。attachEvent() 和 detachEvent()
13.3 事件對(duì)象
即event蓄氧,在觸發(fā)DOM上的某個(gè)事件時(shí)函似,會(huì)產(chǎn)生一個(gè)事件對(duì)象event,這個(gè)對(duì)象包含著所有與事件有關(guān)的信息喉童。
13.3.1 DOM中的事件對(duì)象撇寞。
在需要通過一個(gè)函數(shù)處理多個(gè)事件時(shí),可以這樣:
var btn = document.getElementById('myBtn');
var handler = function(event){
switch(event.type){
case "click":
alert('Clicked');
break;
case 'mouseover':
alert('mouseover');
break;
case 'mouseout':
alert(mouseout);
break;
}
}
btn.onclick = handler;
btn.onmouseover = handler;
btn.mouseout = mouseout;
阻止默認(rèn)行為:
event.preventDefault();
阻止冒泡
event.stopPropagation();
event.eventPhase 用來確定事件當(dāng)前正位于事件流的哪個(gè)階段堂氯。
1: 捕獲階段
2: 處于目標(biāo)對(duì)象上
3: 冒泡階段
13.4 事件類型
13.4.1 UI事件
指的是那些不一定與用戶操作有關(guān)的事件
這些事件都與window對(duì)象有關(guān)
(1) load事件(圖像蔑担,JS,CSS文件等都可以)
在相應(yīng)對(duì)象上監(jiān)聽load事件即可
(2) unload事件
(3) resize事件
(4) scroll事件
13.4.2 焦點(diǎn)事件
(1) blur 在元素失去焦點(diǎn)時(shí)觸發(fā)咽白,這個(gè)事件不會(huì)冒泡啤握。
(2) focus 在元素獲得焦點(diǎn)時(shí)觸發(fā),這個(gè)事件不會(huì)冒泡局扶。
13.4.3 鼠標(biāo)與滾輪事件
(1) click
(2) dblclick
(3) mousedown 用戶按下任意鼠標(biāo)按鈕時(shí)觸發(fā)恨统。不能通過鍵盤觸發(fā)叁扫。
(4) mouseenter 鼠標(biāo)光標(biāo)從元素外部首次移動(dòng)到元素范圍之內(nèi)時(shí)觸發(fā)。這個(gè)事件不冒泡畜埋,而且在光標(biāo)移動(dòng)到后代元素上不會(huì)觸發(fā)莫绣。
(5) mouseleave 在位于元素上方的鼠標(biāo)光標(biāo)移動(dòng)到元素范圍之內(nèi)時(shí)觸發(fā)。這個(gè)事件不冒泡悠鞍,而且在光標(biāo)移動(dòng)到后代元素上不會(huì)觸發(fā)对室。
(6) mousemove 當(dāng)鼠標(biāo)指針在元素內(nèi)部移動(dòng)時(shí) 重復(fù) 觸發(fā)。
(7) mouseout 在鼠標(biāo)指針位于一個(gè)元素上方咖祭,然后用戶將其移入另一個(gè)元素時(shí)觸發(fā)掩宜。又移入的另一個(gè)元素可能位于前一個(gè)元素的外部,
也可能是這個(gè)元素的子元素么翰。
(8) mouseover 在鼠標(biāo)指針位于一個(gè)元素外部牺汤,然后用戶將其首次移入另一個(gè)元素邊界之內(nèi)時(shí)觸發(fā)。
(9) mouseup 用戶釋放鼠標(biāo)按鈕時(shí)觸發(fā)浩嫌。
頁面上所有元素都支持鼠標(biāo)事件檐迟。除了mouseenter 和 mouseleave,所有鼠標(biāo)事件都會(huì)冒泡码耐,也可以被取消器腋,而取消鼠標(biāo)事件將會(huì)影響瀏覽器的默認(rèn)行為熏挎。
1. 客戶區(qū)坐標(biāo)位置
以頁面文檔左上角為原點(diǎn)集晚。
clientX:發(fā)生事件時(shí)鼠標(biāo)指針在視口中的水平坐標(biāo)
clientY:發(fā)生事件時(shí)鼠標(biāo)指針在視口中的垂直坐標(biāo)
2. 頁面坐標(biāo)位置
在頁面沒有滾動(dòng)情況下炸渡,pageX和pageY的值與clientX和clientY的值相等
有滾動(dòng)情況下:
pageY = 鼠標(biāo)舉例文檔頂部距離 + 垂直滾動(dòng)距離
clientY = 鼠標(biāo)舉例文檔頂部距離
3. 屏幕坐標(biāo)位置
鼠標(biāo)事件發(fā)生時(shí),不僅會(huì)有相對(duì)于瀏覽器窗口的位置束铭,還有一個(gè)相對(duì)于整個(gè)電腦屏幕的位置
screenX和screenY
13.4.5 復(fù)合事件
13.4.7 HTML5事件
1. contextmenu 用以表示何時(shí)應(yīng)該顯示上下文菜單廓块,以便開發(fā)人員取消默認(rèn)的上下文菜單而提供自定義的菜單。
禁止默認(rèn)行為纯露,正常瀏覽器:event.preventDefault() IE:event.returnValue = false;
2. beforeunload 事件
3. DOMContentLoaded剿骨。在形成完整的DOM樹之后就會(huì)觸發(fā),不理會(huì)圖像埠褪,JS文件,CSS文件或其他資源是否已經(jīng)下載完畢挤庇。
13.5 內(nèi)存和性能
在js中钞速,添加到頁面上的事件處理程序數(shù)量將直接關(guān)系到頁面的整體運(yùn)行性能。事實(shí)上嫡秕,從如何利用好事件處理程序的角度出發(fā)渴语,還是有一些方法能夠提升性能的。
13.5.1 事件委托
當(dāng)頁面上很多元素需要觸發(fā)同一事件時(shí)昆咽,可考慮使用事件委托來提高性能驾凶。
<ul id="myLinks">
<li id="doSomeWhere">doSomeWhere</li>
<li id="doSomeThing">doSomeThing</li>
<li id="sayHi">sayHi</li>
</ul>
var list = $('#myLinks')
$(list).on('click', function(e){
var target = $(e.target)[0];
e.stopPropagation();
switch(target.id){
case 'doSomeWhere':
alert('doSomeWhere');
break;
case 'doSomeThing':
alert('doSomeThing');
break;
case 'sayHi':
alert('sayHi');
break;
}
})
13.5.2 移除事件處理程序
解綁事件
13.6 模擬事件
13.6.1 DOM中的事件模擬
小結(jié):
在使用事件時(shí)牙甫,需要考慮如下一些內(nèi)存與性能方面的問題: