今天給大家分享一下,修真院官網JS-2任務中可能會使用到的知識點:
1.背景介紹
講到js的事件機制,我們就能來了解一下什麼是事件,先舉個例子:
比如說,人都會睡覺,但隻有人感到困倦的時候才會去睡覺。讓我們來用程式寫一下
function sleep() {
do sleep;
}
people.ontired = function(){
sleep();
}
當然我們修真院的師兄弟們都是修仙之人,當然不與這等凡人苟同。
function coding() {
coding;
}
people.ontried=function(){
coding();
}
是以事件這種東西是廣泛存于我們周圍的,也就是一個觸發點,就像一個開關一樣,按下燈開關燈就亮了,再按一下就關了,這就是一個事件
把事件放在web中,準确的說是放到浏覽器中,事件就會變為使用者對浏覽器所做的行為的響應。比如簡單的點選、鍵盤、移動滑鼠、關閉網頁等等,隻要浏覽器能對使用者行為做出響應的,都是web的事件,比如讓德國boy怒砸電腦,抱歉浏覽器真的無法監聽這個“事件”是以算不上web事件
是以,事件是浏覽器對使用者行為的一個響應。
2.知識剖析
2.1 js的事件驅動
js是事件驅動,正是有這些事件的存在,前端才能和使用者聯系起來,我們一般不清楚使用者對網頁做了什麼,但是外門知道使用者做了那些行為後應該給與怎麼樣的處理。可以把自己想象成一個地雷兵,在頁面中布滿地雷了大大小小的“事件地雷”,隻要使用者不睬上去,我們的代碼隻能老老實實躺在js中不會觸發,隻要使用者踩到了“地雷”,那麼我們的地雷就可以瞬間boom
document.body.οnclick=function(){
alert('boom');
}
如果使用者隻是打開了網頁,沒有進行點選,那麼這個boom就永遠不會彈出,因為js是事件驅動的。
講了這麼多事件驅動,那麼總結一下什麼是事件驅動好了,事件沒有發生,那麼我們寫的js代碼就不會執行,事件是觸發代碼執行的直接原因。
一般來講,如果在一個點選事件裡寫上幾個邏輯錯誤,頁面加載的時候是不會給你報錯的,浏覽器隻是看了一眼onclick裡面的内容,但不會去執行,自然是不會看到裡面的邏輯錯誤,除非你在裡面謝了幾個文法錯誤,加載的時候發現,卧槽,讀不通啊,他才會提示錯誤。當你點選事件觸發的時候,js執行了代碼,發現裡面的邏輯狗屁不通,就會自然而然的報錯了
通常我們都會寫個window.onload,頁面加載完成觸發的事件,把要執行的代碼放在裡面,這樣資源加載好了js好操作。但是頁面中還存在一個硬性的事件,就是read,js引擎閱讀代碼事件。如果讀到了function 函數名(){...}活着var 函數名=function(){...}這樣的結構,它會匆匆掃一眼,不執行裡面的代碼,然後繼續讀下去,其他的語句一旦遇到了,js就會去執行它。比如var 變量名或着函數名()這樣。這個是read事件,其他事件也類似,隻有目前浏覽器對使用者行為的響應時,js才會執行裡面的代碼。
2.2 js常見事件
1、視窗事件,隻在body和frameset元素中才有效
onload 頁面或圖檔加載完成時
onunload 使用者離開頁面時
2、表單元素事件,在表單元素中才有效
onchange 框内容改變時
onsubmit 點選送出按鈕時
onreset 重新點選滑鼠按鍵時
onselect 文本被選擇時
onblur 元素失去焦點時
onfocus 當元素擷取焦點時
3、鍵盤事件,在base,bdo,br,frame,frameset,head,html,iframe,meta,param,script,style,title元素裡都無效
onkeydown 按下鍵盤按鍵時
onkeypress 按下或按住鍵盤按鍵時
onkeyup 放開鍵盤按鍵時
4、滑鼠事件,在base,bdo,br,frame,frameset,head,html,iframe,meta,param,script,style,title元素裡都無效
onclick 滑鼠點選一個對象時
ondblclick 滑鼠輕按兩下一個對象時
onmousedown 滑鼠被按下時
onmousemove 滑鼠被移動時
onmouseout 滑鼠離開元素時
onmouseover 滑鼠經過元素時
onmouseup 釋放滑鼠按鍵時
5、其他
onresize 當視窗或架構被重新定義尺寸時
onabort 圖檔下載下傳被打斷時
onerror 當加載文檔或圖檔時發生錯誤時
2.3 js中事件處理程式的幾種方式
産生了事件,我們就要去處理它,js中事件處理程式主要有3種方式:
1、HTML事件處理程式
即我們直接在HTML代碼中添加事件處理程式,如下面這段代碼:
<input id="btn" value="按鈕" type="button" οnclick="showmsg();">
<script>
function showmsg(){
alert("HTML添加事件處理");
}
</script>
2、DOM0級事件處理程式
即為指定對象添加事件處理,看下面的一段代碼:
input id="btn" value="按鈕" type="button">
<script>
var btn= document.getElementById("btn");
btn.οnclick=function(){
alert("DOM級添加事件處理");
}
btn.οnclick=null;//如果想要删除btn的點選事件,将其置為null即可
</script>
3、DOM2級事件處理程式
DOM2也是對特定的對象添加事件處理程式,但是主要涉及到兩個方法,用于處理指定和删除事件處理程式的操作:addEventListener()和 removeEventListener()。它們都接收三個參數:要處理的事件名、作為事件處理程式的函數和一個布爾值(是否在捕獲階段處理事件)如果為true,表示在捕獲階段調用事件處理程式,如果是false,表示在冒泡階段調用事件處理程式,看下面的一段代碼:
<input id="btn" value="按鈕" type="button">
<script>
var btn=document.getElementById("btn");
btn.addEventListener("click",showmsg,false);//這裡我們把最後一個值置為false,即不在捕獲階段處理,一般來說冒泡處
理在各浏覽器中相容性較好
function showmsg(){
alert("DOM級添加事件處理程式");
}
btn.removeEventListener("click",showmsg,false);//如果想要把這個事件删除,隻需要傳入同樣的參數即可
</script>
2.4 事件的三個階段事件的三個階段
①捕獲階段:
事件從根節點流向目标節點,途中流經各個DOM節點,在各個節點上觸發捕獲事件,直到達到目标節點。
捕獲階段的主要任務是建立傳播路經,在冒泡階段根據這個路經回溯到文檔根節點
②目标階段
事件到達目标節點時,就到了目标階段,事件在目标節點上被觸發
③冒泡階段
事件在目标節點上觸發後,不會終止,一層層向上冒,回溯到根節點。
1.事件冒泡(常用)
![](https://img.laitimes.com/img/__Qf2AjLwojIjJCLyojI0JCLicmbw5COzMGN0UGZ3EWZlNWLyQTO40CM5EGNtU2Y2ETLiJWZ0MzMkVzLclHbpFGZvwFbsl2az9CXt92Yu4Wd5N3aucmbppWalJWLuNWLzM3auQXZrNWdi5yZtlmLz5mavw1LcpDc0RHaiojIsJye.png)
IE中采用的事件流是事件冒泡,先從具體的接收元素,然後逐漸向上傳播到不具體的元素。
<body style="height:500px">
<div id="all">
<div>div1</div>
<div>div2</div>
</div>
<script>
document.getElementsByTagName('body')[0].addEventListener('click', function(e) {
alert(1);
}, false);
document.getElementById('all').addEventListener('click', function(e) {
alert(2);
}, false);
</script>
2.事件捕獲(少用)
Netscapte采用事件捕獲,先由不具體的元素接收事件,最具體的節點最後才接收到事件。
<body style="height:500px">
<div id="all">
<div>div1</div>
<div>div2</div>
</div>
<script>
//将這裡的false,改成true.表明body的綁定事件發生在捕獲階段
document.getElementsByTagName('body')[0].addEventListener('click', function(e) {
alert(1);
}, true);
document.getElementById('all').addEventListener('click', function(e) {
alert(2);
}, false);
</script>
3.DOM事件流
3.常見問題
4.解決方案
5.編碼實戰
6.拓展思考
關于阻止冒泡事件和預設事件
6.1 阻止冒泡事件
其實在非IE浏覽器中提供了一個事件對象 stopPropagation,那麼在IE浏覽器中有通過cancelBubble事件對象可以阻止。
文法部分:
stopPropagation() 方法
定義和用法
不再派發事件。
終止事件在傳播過程的捕獲、目标處理或起泡階段進一步傳播。調用該方法後,該節點上處理該事件的處理程式将被調用,事件不再被分派到其他節點。
文法
event.stopPropagation()
說明
該方法将停止事件的傳播,阻止它被分派到其他 Document 節點。在事件傳播的任何階段都可以調用它。注意,雖然該方法不能阻止同一個 Document 節點上的其他事件句柄被調用,但是它可以阻止把事件分派到其他節點。
實作效果:
6.2、首先了解一下預設事件:
浏覽器的預設事件就是浏覽器自己的行為,比如我們在點選<a href="#" target="_blank" rel="external nofollow" >的時候,浏覽器跳轉到指定頁面。
文法部分
preventDefault() 方法
定義和用法
取消事件的預設動作。
文法
event.preventDefault()
說明
該方法将通知 Web 浏覽器不要執行與事件關聯的預設動作(如果存在這樣的動作)。例如,如果 type 屬性是 "submit",在事件傳播的任意階段可以調用任意的事件句柄,通過調用該方法,可以阻止送出表單。注意,如果 Event 對象的 cancelable 屬性是 fasle,那麼就沒有預設動作,或者不能阻止預設動作。無論哪種情況,調用該方法都沒有作用。
代碼部分:
實作效果:
7.參考文獻
JavaScript事件處理的方式(三種):http://www.jb51.net/article/83052.htm
js事件機制:https://segmentfault.com/q/1010000006975586
8.更多讨論
Q1:事件冒泡有什麼作用
A1:事件冒泡允許多個操作被集中處理
Q2:事件冒泡和事件捕獲是什麼?
A2:他們是描述事件觸發時序問題的術語。事件捕獲指的是從document到觸發事件的那個節點,即自上而下的去觸發事件。相反的,事件冒泡是自下而上的去觸發事件。綁定事件方法的第三個參數,就是控制事件觸發順序是否為事件捕獲。true,事件捕獲;false,事件冒泡。預設false,即事件冒泡。
Q3:DOM0級事件與DOM2級事件的差別
A3:dom2級事件比起dom0級事件的好處就是,addEventListener() 增加多個dom事件,觸發時都會依次發生,而DOM0級隻能覆寫,不會連續觸發。