首頁 >web前端 >js教程 >對於函數事件的總結

對於函數事件的總結

jacklove
jacklove原創
2018-05-21 15:42:341507瀏覽

在學習函數的時候會遇見很多的函數事件,本篇將對其進行詳細的講解。

什麼是事件?

JavaScript與HTML之間的互動是透過事件實現的。事件,就是文件或瀏覽器視窗中發生的一些特定的互動瞬間。可以使用監聽器(或處理程序)來預定事件,以便在事件發生時執行對應的程式碼。這種在傳統軟體工程中被稱為觀察員模式的模型,支援頁面的行為(JavaScript)與頁面的外觀(HTML與CSS)之間的鬆散耦合。

事件流

事件流描述的是從頁面中接受事件的順序。假設如下程式碼:

<!DOCTYPE html><html lang="en"><head>
    <meta charset="UTF-8">
    <title>Document</title></head><body>
    <div id="div1"></div></body></html>

點擊div,這個點擊不只發生在div上,其父容器body也會被點擊。那到底誰先被點擊或說事件是怎麼傳播的?事件流描述的就是這樣一個接受事件的順序。

IE事件流(事件冒泡)

IE事件流也叫事件冒泡,即事件開始時由最具體的元素(文檔中嵌套層最深的那個節點)接收,然後逐級傳播到較為不具體的節點(文件)。
以上面的程式碼為例,如果你點擊了div元素,那麼這個click事件會如下順序傳播:

1.<div>
2.<body>
3.<html>
4.document

就是說,click事件首先發生在div元素上,而這個元素就是我們點擊的元素,然後click事件沿著DOM樹向上傳播,在每一層節點上都會發生,直到傳播到document物件。

所有的現代瀏覽器都支援事件冒泡,但有些差異。 IE5.5及更早版本中的事件冒泡會跳過html元素,從body直接到document。 IE9、Firefox、Chrome和Safari則將事件一直冒泡到window物件。 (舊IE瀏覽器只支援事件冒泡)。

事件捕獲

事件捕獲的想法是不太具體的節點應該更早接收到事件,而具體的節點應該最後接收到事件,正好與事件冒泡相反,再以上面的例子為例,點選div,事件擷取的事件觸發順序如下:

1.document
2.<html>
3.<body>
4.<div>

在事件擷取過程中,document物件先接受到click事件,然後事件沿著DOM樹依序向下,一直傳播到事件的實際目標。

IE9,Firefox、Chrome、Safari和Opera都支援事件擷取。雖然DOM2級事件規範要求事件應該從document物件開始傳播,但這些瀏覽器都是從window物件開始捕捉事件的。

DOM事件流

DOM2級事件規定的事件流包含三個階段:事件擷取階段、處於目標階段、事件冒泡階段。首先發生的是事件捕獲,為截取事件提供機會。然後是實際的目標接受到事件。最後一個階段是冒泡階段,可以在這個階段對事件做出反應。

在DOM事件流中,實際的目標在捕獲階段不會接受到事件。這意味著在捕獲階段,事件從document到html再到body就停止了。下一階段是處於目標階段,於是事件在div上發生,並在事件處理中被看成冒泡階段的一部分。然後,冒泡階段發生,事件傳回ducument。
但實際上,IE9,Firefox、Chrome、Safari和Opera9.5及更高版本都會在捕獲階段觸發事件物件上的事件。結果就是有兩個機會在目標物件上面操作事件。 (IE8及更早版本不支援DOM事件流)。

事件處理程序

事件就是使用者或瀏覽器本身執行的某種動作。像是click、load和mousover,都是事件的名字。回應某個事件的函數叫做事件處理程序(事件監聽器)。事件處理程序的名字以"on"開頭,所以click事件的事件處理程序就是onclick,load事件的處理程序就是onload。有以下幾種為事件指定處理程序的方法。

HTML事件處理程序

某個元素支援的每個事件,都可以使用一個與對應事件處理程序同名的HTML屬性來指定。這個屬性的值應該是能夠執行的JavaScript程式碼,範例:

<button id="myButton" onclick="alert(&#39;Clicked&#39;)">Click Me</button>//定义了一个按钮,点击时会显示一个警告框;

在HTML中定義事件處理程序可以包含要執行的特定動作,也可以呼叫在頁面其他地方定義的腳本,範例:

<button id="myButton" onclick="showMsg()">Click Me</button>  //点击按钮就会调用showMsg()函数;<script>
    function showMsg() {
      alert(&#39;Hello world!&#39;)
}</script>

透過HTML指定事件處理程序有兩個缺點:1.時差問題,因為使用者可能會在HTML元素一出現頁面就觸發對應事件,但此時事件處理程序有可能尚未具備執行條件;2.HTML與JavaScript程式碼緊密耦合,如果要更換事件處理程序,就要改變HTML程式碼和JavaScript程式碼。

DOM0級事件處理程序

透過JavaScript指定事件處理程序的傳統方式,就是將一個函數賦值給一個事件處理程序屬性。每一個元素都有自己的事件處理程序屬性,這些屬性通常全部小寫,如onclick。將此屬性的值設為函數,就可以指定事件處理程序,範例:

 var btn = document.getElementById(&#39;myButton&#39;);
  btn.onclick = function() {
    alert("Clicked")
  }

使用DOM0级方法指定的事件处理程序被认为是元素的方法。因此,这时候事件处理程序是在元素的作用域中运行;换句话说,程序中的this引用当前元素。
也可以通过DOM0级方法删除事件处理程序,示例:

btn.onclick = null;   //删除事件处理程序;
DOM2级事件处理程序

DOM2级事件定义了两个方法,用于处理指定和删除事件处理程序的操作:addEventListener()和removeEventListener()。所有DOM节点都包含这两个方法,并且它们都接受3个参数:要处理的事件名、作为事件处理程序的函数和一个布尔值。最后的布尔值如果是true,表示在捕获阶段调用事件处理程序;如果是false,表示在冒泡阶段调用事件处理程序。示例:

 var btn = document.getElementById(&#39;myButton&#39;);  //为按钮添加了click事件和处理程序;
  btn.addEventListener(&#39;click&#39;,function() {
    alert(this.id)
  },false)

与DOM0级方法一样,这里添加的事件处理程序也是在其依附的元素的作用域中运行的。使用DOM2级方法添加事件处理程序可以添加多个事件处理程序,示例:

 var btn = document.getElementById(&#39;myButton&#39;);  //为按钮添加了多个click事件和处理程序;
  btn.addEventListener(&#39;click&#39;,function() {
    alert(this.id);
  },false);  var btn = document.getElementById(&#39;myButton&#39;);  ;
  btn.addEventListener(&#39;click&#39;,function() {
    alert(&#39;hello world!&#39;);
  },false);

这里为按钮添加了2个事件处理程序。这两个事件处理程序会按照添加它们的顺序触发。
通过addEventListener()添加的事件处理程序只能用removeEventListener()来移除;移除时传入的参数与添加处理程序时使用的参数相同,意味着addEventListener()添加的匿名函数无法移除:

//该代码无法运行;btn.removeEventListener(&#39;click&#39;,function() {
  alert(this.id);
},false);
//该代码工作正常;//removeEventListener()和addEventListener()使用了相同函数;var btn = document.getElementById(&#39;myButton&#39;); 
  var function handler() {
    alert(this.id);
  }
btn.addEventListener(&#39;click&#39;,handler,false);
btn.removeEventListener(&#39;click&#39;,handler,false);

本篇对js事件进行了总结,更多相关内容请关注php中文网。

相关推荐:

关于正则表达式的相关理解

Javascript中关于this的用法

关于Math、数组、Date的相关例子

以上是對於函數事件的總結的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn