本文目錄一覽:
- 1、如何在JavaScript中使用自定義事件
- 2、請說明JavaScript中處理事件的步驟
- 3、js添加事件和移除事件:addEventListener()與removeEventListener()
如何在JavaScript中使用自定義事件
在javascript中實現自定義事件的原理是創建一個管理事件的對象.如下代碼是事件的定義:
function EventTarget(){
this.handlers = {};//存儲事件處理程序,由n個鍵值對組成,鍵表示事件名,值是一個由事件處理程序組成的數組
}
EventTarget.prototype = {
constructor:EventTarget,
//添加事件
addHandler:function(type,handler){
if(typeof this.handlers[type] == “undefined”){
this.handlers[type] = [];
}
this.handlers[type].push(handler);
},
//觸發事件
fire:function(event){
if(!event.target){
event.target = this;
}
if(this.handlers[event.type] instanceof Array){
var handlers = this.handlers[event.type];
for(var i=0,len=handlers.length;i len;i++){
//將event傳遞給事件處理程序,event.target代表對象本身,
event.type代表事件名,你可以根據情況為添加event屬性
handlers[i](event);
}
}
},
//移除事件
removeHandler:function(type,handler){
if(this.handlers[type] instanceof Array){
var handlers=this.handlers[type];
for(var i=0,len=handlers.length;i len; i++){
if(handlers[i] == handler){
break;
}
}
handlers.splice(i,1);
}
}
};
首先是定義了一個名為EventTarget的構造函數,為其定義的屬性handlers用於存儲事件處理程序,
然後有三個操作方法添加到EventTarget的原型中,分別是addHandler fire remocveHander.
addHander是向handlers中添加事件處理程序
fire是觸發handlers中的事件處理程序
removeHandler是向handlers中移除事件處理程序
注:事件處理程序通俗的講就是事件被觸發時需要執行的方法.
請說明JavaScript中處理事件的步驟
事件處理程序的方式了:
1. 設置HTML標籤屬性為事件處理程序
文檔元素的事件處理程序屬性,其名字由「on」後面跟著事件名組成,例如:onclick、onmouseover。當然了,這種形式只能為DOM元素註冊事件處理程序。實例:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow:hidden;}
#div2{margin:50px auto; width: 200px; height: 200px; background: green; overflow:hidden;}
#div3{margin:50px auto; width: 100px; height: 100px; background: blue;}
/style
/head
body
div id=”div1″ onClick=”console.log(‘div1’);”div1
div id=”div2″ oNClick=”console.log(‘div2’);”div2
div id=”div3″ onclick=”console.log(‘div3’);” onclick=”console.log(‘div3333’);”div3
/div
/div
/div
script type=”text/javascript”
/script
/body
/html
結果(滑鼠點擊div3區域後):
從結果中可以看出:
①因為HTML裡面不區分大小寫,所以這裡事件處理程序屬性名大寫、小寫、大小混寫均可,屬性值就是相應事件處理程序的JavaScript代碼;
②若給同一元素寫多個onclick事件處理屬性,瀏覽器只執行第一個onclick裡面的代碼,後面的會被忽略;
③這種形式是在事件冒泡過程中註冊事件處理程序的;
2.設置JavaScript對象屬性為事件處理程序
可以通過設置某一事件目標的事件處理程序屬性來為其註冊相應的事件處理程序。事件處理程序屬性名字由「on」後面跟著事件名組成,例如:onclick、onmouseover。實例:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow:hidden;}
#div2{margin:50px auto; width: 200px; height: 200px; background: green; overflow:hidden;}
#div3{margin:50px auto; width: 100px; height: 100px; background: blue;}
/style
/head
body
div id=”div1″div1
div id=”div2″div2
div id=”div3″div3
/div
/div
/div
script type=”text/javascript”
var div1 = document.getElementById(‘div1’);
var div2 = document.getElementById(‘div2’);
var div3 = document.getElementById(‘div3’);
div1.onclick = function(){
console.log(‘div1’);
};
div2.onclick = function(){
console.log(‘div2’);
};
div3.onclick = function(){
console.log(‘div3’);
};
div1.onclick = function(){
console.log(‘div11111’);
};
div1.onClick = function(){
console.log(‘DIV11111’);
};
/script
/body
/html
結果(滑鼠點擊div3區域後):
從結果中可以看出:
①因為JavaScript是嚴格區分大小寫的,所以,這種形式下屬性名只能按規定小寫;
②若給同一元素對象寫多個onclick事件處理屬性,後面寫的會覆蓋前面的(ps:這就是在修改一個對象屬性的值,屬性的值是唯一確定的);
③這種形式也是在事件冒泡過程中註冊事件處理程序的;
3.addEventListener()
前兩種方式出現在Web初期,眾多瀏覽器都有實現。而addEventListener()方法是標準事件模型中定義的。任何能成為事件目標的對象——這些對象包括Window對象、Document對象和所有文檔元素等——都定義了一個名叫addEventListener()的方法,使用這個方法可以為事件目標註冊事件處理程序。addEventListener()接受三個參數:第一個參數是要註冊處理程序的事件類型,其值是字元串,但並不包括前綴「on」;第二個參數是指當指定類型的事件發生時應該調用的函數;第三個參數是布爾值,其可以忽略(某些舊的瀏覽器上不能忽略這個參數),默認值為false。這種情況是在事件冒泡過程中註冊事件處理程序。當其為true時,就是在事件捕獲過程中註冊事件處理程序。實例:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow:hidden;}
#div2{margin:50px auto; width: 200px; height: 200px; background: green; overflow:hidden;}
#div3{margin:50px auto; width: 100px; height: 100px; background: blue;}
/style
/head
body
div id=”div1″div1
div id=”div2″div2
div id=”div3″div3
/div
/div
/div
script type=”text/javascript”
var div1 = document.getElementById(‘div1’);
var div2 = document.getElementById(‘div2’);
var div3 = document.getElementById(‘div3’);
div1.addEventListener(‘click’, function(){ console.log(‘div1-bubble’); }, false);
div2.addEventListener(‘click’, function(){ console.log(‘div2-bubble’); }, false);
div3.addEventListener(‘click’, function(){ console.log(‘div3-bubble’); }, false);
div3.addEventListener(‘click’, function(){ console.log(‘div3-bubble222’); }, false);
div1.addEventListener(‘click’, function(){ console.log(‘div1-capturing’); }, true);
div2.addEventListener(‘click’, function(){ console.log(‘div2-capturing’); }, true);
div3.addEventListener(‘click’, function(){ console.log(‘div3-capturing’); }, true);
/script
/body
/html
結果(滑鼠點擊div3區域後):
從結果中可以看出:
①addEventListener()第三個參數的作用正如上面所說;
②通過addEventListener()方法給同一對象註冊多個同類型的事件,並不會發生忽略或覆蓋,而是會按順序依次執行;
相對addEventListener()的是removeEventListener()方法,它同樣有三個參數,前兩個參數自然跟addEventListener()的意義一樣,而第三個參數也只需跟相應的addEventListener()的第三個參數保持一致即可,同樣可以省略,默認值為false。它表示從對象中刪除某個事件處理函數。實例:
div1.addEventListener(‘click’, div1BubbleFun, false);
div1.removeEventListener(‘click’, div1BubbleFun, false);
function div1BubbleFun(){
console.log(‘div1-bubble’);
}
4.attachEvent()
但是,IE8以及其之前版本的瀏覽器並不支持addEventListener()和removeEventListener()。相應的,IE定義了類似的方法attachEvent()和detachEvent()。因為IE8以及其之前版本瀏覽器也不支持事件捕獲,所以attachEvent()並不能註冊捕獲過程中的事件處理函數,因此attachEvent()和detachEvent()要求只有兩個參數:事件類型和事件處理函數。而且,它們的第一個參數使用了帶「on」前綴的事件處理程序屬性名。實例:
var div1 = document.getElementById(‘div1’);
div1.attachEvent(‘onclick’, div1BubbleFun);
function div1BubbleFun(){
console.log(‘div1-bubble’);
}
相應的,從對象上刪除事件處理程序函數使用detachEvent()。例如:
div1.detachEvent(‘onclick’, div1BubbleFun);
到此為止,我們已經說了瀏覽器中事件傳播機制以及各種註冊事件處理程序的方法。下面我們就再說說事件處理程序調用時的一些問題吧!
二.事件處理程序的調用
1.事件處理程序的參數:正如前面所說,通常事件對象作為參數傳遞給事件處理函數,但IE8以及其之前版本的瀏覽器中全局變數event才是事件對象。所以,我們在寫相關代碼時應該注意兼容性問題。實例(給頁面上id為div1的元素添加點擊事件,當點擊該元素時在控制台輸出事件類型和被點擊元素本身):
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow: hidden;}
/style
/head
body
div id=”div1″div1/div
script type=”text/javascript”
var div1 = document.getElementById(‘div1’);
if(div1.addEventListener){
div1.addEventListener(‘click’, div1Fun, false);
}else if(div1.attachEvent){
div1.attachEvent(‘onclick’, div1Fun);
}
function div1Fun(event){
event = event || window.event;
var target = event.target || event.srcElement;
console.log(event.type);
console.log(target);
}
/script
/body
/html
2.事件處理程序的運行環境:關於事件處理程序的運行環境,也就是在事件處理程序中調用上下文(this值)的指向問題,可以看下面四個實例。
實例一:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow: hidden;}
/style
/head
body
div id=”div1″ onclick=”console.log(‘html:’); console.log(this);”div1/div
script type=”text/javascript”
/script
/body
/html
結果一:
從結果可以看出:
①第一種方法事件處理程序中this指向這個元素本身;
實例二:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow: hidden;}
/style
/head
body
div id=”div1″ onclick=”console.log(‘html:’); console.log(this);”div1/div
script type=”text/javascript”
var div1 = document.getElementById(‘div1’);
div1.onclick = function(){
console.log(‘div1.onclick:’);
console.log(this);
};
/script
/body
/html
結果二:
從結果可以看出:
①第二種方法事件處理程序中this也指向這個元素本身;
②存在第二種方法時,它會覆蓋第一種方法註冊的事件處理程序;
實例三:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow: hidden;}
/style
/head
body
div id=”div1″ onclick=”console.log(‘html:’); console.log(this);”div1/div
script type=”text/javascript”
var div1 = document.getElementById(‘div1’);
div1.onclick = function(){
console.log(‘div1.onclick:’);
console.log(this);
};
div1.addEventListener(‘click’, function(){
console.log(‘div1.addEventListener:’);
console.log(this);
}, false);
/script
/body
/html
結果三:
從結果可以看出:
①第三種方法事件處理程序中this也指向這個元素本身;
②第三種方法並不會覆蓋第一種或第二種方法註冊的事件處理程序;
實例四:
!DOCTYPE HTML
html
head
meta http-equiv=”Content-Type” content=”text/html; charset=utf-8″/
titletest/title
style type=”text/css”
#div1{width: 300px; height: 300px; background: red; overflow: hidden;}
/style
/head
body
div id=”div1″ onclick=”console.log(‘html:’); console.log(this);”div1/div
script type=”text/javascript”
var div1 = document.getElementById(‘div1’);
div1.onclick = function(){
console.log(‘div1.onclick:’);
console.log(this);
};
div1.attachEvent(‘onclick’, function(){
console.log(‘div1.attachEvent:’);
console.log(this === window);
});
/script
/body
/html
結果四:
從結果可以看出:
①第四種方法事件處理程序中this指向全局對象Window;
②第四種方法也不會覆蓋第一種或第二種方法註冊的事件處理程序;
3.事件處理程序的調用順序:多個事件處理程序調用規則如下:
①通過HTML屬性註冊的處理程序和通過設置對象屬性的處理程序一直優先調用;
②使用addEventListener()註冊的處理程序按照它們的註冊順序依次調用;
③使用attachEvent()註冊的處理程序可能按照任何順序調用,所以代碼不應該依賴於調用順序;
js添加事件和移除事件:addEventListener()與removeEventListener()
addEventListener()與removeEventListener()用於處理指定和刪除事件處理程序操作。
它們都接受3個參數:如 addEventListener(“事件名” , “事件處理函數” , “布爾值”); (註:事件名不含”on”,如「click」) 現在的版本可以省略第三個參數,默認值為false
通過addEventListener()添加的事件處理程序只能使用removeEventListener()來移除;移除時傳入的參數與添加處理程序時使用的參數相同。這也意味著通過addEventListener()添加的匿名函數無法移除
這個例子中,使用addEventListener()添加一個事件處理程序。雖然調用removeEventListener(0是看似使用了相同的參數,但實際上,第二個參數與傳入addEventListener()中的那一個完全不同的函數。而傳入removeEventListener()中的事件處理程序函數必須與傳addEventListener()中的相同
重寫後的這個例子在addEventListener()和removeEventListener()中用的是相同的函數。
1:相同事件綁定和解除,需要使用共用函數;綁定和解除事件時 事件沒有”on” 即onclick寫成click
2:共用函數不能帶參數;
布爾值參數是true,表示在捕獲階段調用事件處理程序;就是最不具體的節點先接收事件,最具體的節點最後接收事件
原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-tw/n/287280.html