1. 程式人生 > >JavaScript(1)---繫結事件、解除繫結事件

JavaScript(1)---繫結事件、解除繫結事件

JavaScript(1)---繫結事件、解除繫結事件

一、事件概述

1、事件的幾個概念

· 事件

指的是文件或者瀏覽器視窗中發生的一些特定互動瞬間。我們可以通過偵聽器(或者處理程式)來預定事件,以便觸發事件的時候執行相應的程式碼。

事件處理程式

我們使用者在頁面中進行的點選動作(click)、滑鼠移動動作(mousemove)等,都可以稱之為事件名稱。響應某個事件的函式則稱為事件處理程式,或者叫做事件偵聽器。

事件型別

UI事件: load、unload、error、resize、scroll、select,是使用者與頁面上的元素互動時觸發的。

焦點事件:blur、DOMFocusIn、DOMFocusOut、focus、focusin、focusout,在元素獲得或失去焦點的時候觸發,這些事件當中,最為重要的是blur和focus,

有一點需要引起注意,這一類事件不會發生冒泡!

滑鼠與滾輪事件:click、dblclick、mousedown、mouseenter、mouseleave、mousemove、mouseout、mouseover、mouseup,是當用戶通過滑鼠在頁面執行

操作時所觸發的。

滾輪事件:mousewheel(IE6+均支援)、DOMMouseScroll(FF支援的,與mousewheel效果一樣)。是使用滑鼠滾輪時觸發的。

文字事件:textInput,在文件中輸入文字觸發。

鍵盤事件:keydown、keyup、keypress,當用戶通過鍵盤在頁面中執行操作時觸發。

2、事件三要素

事件有三要素 : 事件源

事件監聽器

事件源:在哪個元素上發生的。比如: p標籤、a標籤、div標籤、form表單 等等

​ 事件:到底發生了什麼事件。click(點選事件)、mouseover(滑鼠事件)、focus(焦點事件) 等

監聽器:事件源觸發事件後,如何迴應發生的事件,通常以函式(funtion)的形式來出現。

注意 事件不是以 on 開頭的那個名稱,如 onclick 不是事件,click才是事件。onclick引用的是一個元素物件的屬性,它指向click事件型別繫結的實際處理函式。


二、繫結事件、解綁事件

常用的事件繫結的幾種方式有三種:

1、直接在html元素上進行繫結事件。
2、用 on 繫結事件。
3、用 addEventListener、attachEvent 繫結事件。

1、直接在 html 元素上進行繫結

即以屬性的方式直接寫在行內

<input id="btn" type="button" onclick="test();" /> <!--點選按鈕 觸發事件-->

這樣有個很大的缺點就是:

HTML與js程式碼緊密耦合。如果要更換 事件,就要改動兩個地方:HTML程式碼和JS程式碼,這就不利於後期程式碼的維護。

2、用 on 繫結

相容性:在IE,FF,Chrome,Safari,Mozilla,Opera下都適用。

<body>
  <div id="id">on繫結事件</div>
  <script>
    var div=document.getElementById('id');
    // 甲
    div.onclick=function(){
        console.log('甲需要紅背景');
        div.setAttribute('style', 'background: #ff0000');
    };
    // 乙  
    div.onclick=function(){
        console.log('乙需要黃背景');
        div.setAttribute('style', 'background: #ffff00');
    };
    //這裡最總只會輸出 '乙需要黃背景' 因為用on繫結事件 同一事件下面會覆蓋上面的
    div.onclick=null;  //解綁只要事件 = null 就可以了
  </script>
</body>

優點:它最大的優點是就是相容性很好,所有瀏覽器都支援。

缺點:同一個 dom 元素上,on 只能繫結一個同類型事件,後者會覆蓋前者,不同型別的事件可以繫結多個。

這裡就有一個問題,無法允許團隊不同人員對同一元素監聽同一事件但做出不用的響應。

3、 addEventListener、attachEvent 繫結事件

同一個 dom 元素上,用 addEventListener、attachEvent 可以繫結多個同類型事件。

但是,addEventListener 事件執行順序按照事件繫結的先後順序執行;attachEvent 事件執行順序則是隨機的。

1)addEventListener

var oBox = document.getElementById("container");
//繫結事件
oBox.addEventListener("click",fn(),false);
//解綁事件
oBox.removeEventListener("click",fn(),false);
function fn(){//執行程式碼}

引數說明

第一個引數:事件名稱 比如onclick  onmouseover
第一個引數:作為事件處理程式的函式
第一個引數:若為false,函式在冒泡階段執行;若為true,函式在捕獲階段執行。預設為false。(有關冒泡和捕獲單獨抽時間講)

注意:removeEventListener 第二個引數要和 addEventListener 指向 同一個函式 才能解綁成功。

2)attachEvent

var oBox = document.getElementById("container");
//繫結
oBox.attach("click",fn());
//解綁
oBox.detach("click",fn());
function fn(){//執行函式}

3)區別

總結下 addEventListener、attachEvent的區別

 1)引數個數不一致
   addEventListener三個引數,attachEvent兩個引數
 2)相容問題
   addEventListener 谷歌,火狐,IE11支援,IE8不支援
   attachEvent 谷歌火狐不支援,IE11不支援,IE8支援
 3)this指向不同
   addEventListener 中的this是當前繫結事件的物件
   attachEvent中的this是window
 4)事件命名不同
   addEventListener中事件的型別(事件的名字)沒有on
   attachEvent中的事件的型別(事件的名字)有on

這裡再說下 addEventListener、attachEvent相對於上面兩種繫結事件的優缺點

優點 它們可以支援 繫結多個同類型事件

缺點 相容性並不好,它們只相容相對應的瀏覽器才有用。


三、事件的相容

上面說了3種繫結事件和解綁事件的方法,如果實際開發中如果只使用一種方法,那麼會產生要麼無法滿足同一元素監聽同一事件但做出不用的響應,要麼系統的相容性會有問題。

所以需要一個相容的方法。這裡舉一個完整的例子,包含相容繫結事件 和 相容解綁事件 ,也看下解綁的含義是什麼。

完整程式碼

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>事件繫結和解綁</title>
</head>
<body>
<input type="button" value="綁架事件" id="btn1"/>
<input type="button" value="解綁事件" id="btn2"/>
<script>
  //第一個按鈕 同時繫結兩個相同事件 執行不同方法
  addEventListener(my$("btn1"),"click",f1);
  addEventListener(my$("btn1"),"click",f2);
  //第二個按鈕點選後 讓第一個按鈕第一個事件解綁
  my$("btn2").onclick=function () {
    removeEventListener(my$("btn1"),"click",f1);
  };

    function f1() {
    alert("第一個事件");
  }
   function f2() {
    alert("第二個事件");
  }

function my$(id) {
    return document.getElementById(id);
}

  //繫結事件的相容
  function addEventListener(element,type,fn) {
    if(element.addEventListener){ //有沒有用
      element.addEventListener(type,fn,false);
    }else if(element.attachEvent){ //有沒有用
      element.attachEvent("on"+type,fn);
    }else{ //如果都不相容 那就用這種來繫結事件
      element["on"+type]=fn;
    }
  }
  //解綁事件的相容
  function removeEventListener(element,type,fnName) {
    if(element.removeEventListener){
      element.removeEventListener(type,fnName,false);
    }else if(element.detachEvent){
      element.detachEvent("on"+type,fnName);
    }else{
      element["on"+type]=null;
    }
  }

</script>
</body>
</html>

執行結果

從執行結果我們很明顯可以得出的結論:

1、一開始繫結事件的按鈕 綁定了兩個相同的事件。並且發現並沒有發生事件覆蓋,都成功了。
2、當點選解綁按鈕後,它解綁是繫結按鈕的第一個事件。
3、此時再點選繫結事件的按鈕,發現只綁定了一個事件,因為另一個事件已經被解綁了。


參考

1、JS中幾種繫結事件的方式

2、JS事件繫結的常用方式例項總結

3、javascript 中的事件機制




你如果願意有所作為,就必須有始有終。(20)