前言:原本这篇文章是打算6号书写出来的,但是基于某些私人原因,希望能够通过这篇文章尽可能的将事件讲解的更加详细和通俗易懂,因此,多花了一天时间,不多说了,接下来对“事件”来一个较为详细的介绍。
欢迎大家互相学习交流。独行冰海
需要了解事件的什么?
对于事件来讲,首先,我们需要了解这样几个概念:事件;事件处理程序;事件类型;事件流;事件冒泡;事件捕获;事件对象;事件方面的性能优化(事件委托、移除事件处理程序);常见的浏览器兼容问题。
事件的概念
事件:指的是文档或者浏览器窗口中发生的一些特定交互瞬间。我们可以通过侦听器(或者处理程序)来预定事件,以便事件发生的时候执行相应的代码。
事件处理程序
事件处理程序:我们用户在页面中进行的点击这个动作,鼠标移动的动作,网页页面加载完成的动作等,都可以称之为事件名称,即:click、mousemove、load等都是事件的名称。响应某个事件的函数则称为事件处理程序,或者叫做事件侦听器。
接下来我们用一段代码来再说明一下上面这两个抽象的概念,具体解释见代码注释:
<script><br/> var main = document.getElementById('main');<br/> // 此處click,點擊,是一種事件的名稱,是瀏覽器視窗中發生點擊的瞬間。 on這個單字,其實就是讓click這個事件得以相應,因此,onclick就叫做事件處理程序。下面這段程式碼,我們透過處理程序(onclick)為main這個元素預定了點擊(click),這樣在點擊(click)發生的時候,執行函數中的程式碼(彈出一個對話框)。 <br/> main.onclick = function(){<br/> alert('點擊了此處哦!');<br/> }<br/></script>
}
關於事件>
關於事件處理到現在之前的發展到次的變化。
事件處理程序的名字是以「on」開頭,因此click事件的處理程序就是onclick。在最初,是使用HTML事件處理程序的,也就是說,某個元素(如div),支援的每一種事件,都可以使用一個與對應事件處理程序同名的HTML特性來制定(也就是標籤的一個屬性),這個特性的值就是能夠執行的JavaScript程式碼。例如:
HTML事件處理程序
當然,我們也可以再onclick=」」當中進行函數的呼叫。
但是,無論哪種方法,都暴露出來HTML事件處理程序的許多問題:
首先,HTML程式碼域JavaScript程式碼緊密的耦合在一起,沒有實現相互分離,在進行程式碼的更新與維護的時候就顯得異常困難。
第二,擴充事件處理程序的作用域鏈在不同瀏覽器當中會導致不同的結果。
第三,如果不採用呼叫函數的方式,而是像例子中那樣直接書寫程式碼,那麼程式碼的通用性很差,會使得整站的程式碼量很大,通用性差。如果提取出來,存放在函數當中,那麼,會面臨另一個問題——當函數還沒有被定義,只是HTML、CSS程式碼載入完畢,用戶進行點擊,會完全沒有反應。
基於上述的這些問題,人們逐漸的去完善了事件處理程序,此時出現了DOM0級事件處理程序。 (第四代WEB瀏覽器中出現)
DOM0級事件處理程序是什麼樣子的呢?其實它就是我們平常最常用的事件綁定,如下面這個例子:
DOM0級事件處理程序
<script><br/> var btn = document.<br/><script>🎜 var btn = document.getElementById(' btn');🎜 btn.onclick = function(){🎜 alert(this.innerHTML);🎜 }🎜</script>🎜🎜 }🎜🎜🎜 }🎜🎜🎜但是,卻出現了這樣一個問題,當我希望為同一個元素/標籤綁定多個同類型事件的時候(如,為上面的這個p標籤綁定3個點擊事件),是不被允許的。那麼,此時,出現了另一個事件處理程序,就是DOM2級的事件處理程序,在DOM2級當中,定義了兩個基本方法,用於處理指定(即綁定)和刪除事件處理程序的操作,分別是addEventListener()和removeEventListener(),IE9+、FireFox、Safari、Chrome和Opera都是支援DOM2級事件處理程序的。對於IE8-,則使用的是IE專有的事件處理程序:兩個類似的方法-attachEvent()與detachEvent()。 🎜具體實例程式碼如下:(以addEventListener為例,給出了兩種書寫方式)🎜🎜🎜🎜 🎜
DOM0級事件處理程序
🎜🎜<script>🎜 var btn = document. getElementById('btn');🎜 btn.addEventListener("click", test, false);🎜 function test(){<br/> alert(this.innerHTML);<br/> }<br/></script>DOM0级事件处理程序
<script><br/> var btn = document.getElementById('btn');<br/> btn.addEventListener("click", function(){<br/> alert(this.innerHTML); <br/> }, false);<br/></script>
addEventListener()和removeEventListener()中的第三个参数,表示的是在哪个事件阶段进行事件处理,如果是false,则指的是冒泡阶段;如果是true,则指的是捕获阶段。
在事件方面,IE与FF存在着一系列的兼容问题,具体问题可查看博文《IE浏览器与FF火狐浏览器在事件上的兼容问题》
关于如何创建一个兼容全部浏览器的事件侦听器,我们在下一篇博文《跨浏览器的事件处理函数——处理DOM2级事件兼容 》当中再做详细的介绍和代码示范。
事件类型
之前在课程的讲解当中,我们把事件分为了三大类,分别是一般事件、表单事件和页面事件。当前我们可以再做细分:
UI事件:如load、unload、error、resize、scroll、select、DOMActive,是用户与页面上的元素交互时触发的。
焦点事件:如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,当用户通过键盘在页面中执行操作时触发。
合成事件:DOM3级新增,用于处理IME的输入序列。所谓IME,指的是输入法编辑器,可以让用户输入在物理键盘上找不到的字符。compositionstart、compositionupdate、compositionend三种事件。
变动事件:DOMsubtreeModified、DOMNodeInserted、DOMNodeRemoved、DOMAttrModified、DOMCharacterDataModified等,当底层DOM结构发生变化时触发。IE8-不支持。
变动名称事件:指的是当元素或者属性名变动时触发,当前已经弃用!
对于事件的基本类型,随着HTML5的出现和发展,又新增了HTML5事件、设备事件、触摸事件、手势事件等各种事件,在后面我们再详细介绍。
事件流
事件流:描述的是从页面中接收事件的顺序。
IE与原来的NetScape(网景),对于事件流提出的是完全不同的顺序。IE团队提出的是事件冒泡流;NetScape的事件流是事件捕获流。
事件冒泡
事件冒泡:表示的是,事件开始的时候由最具体的元素(文档中嵌套层次最深的那个节点)接收,然后逐级向上传播到较为不具体的节点(文档)。
事件捕获
事件捕获:表示的是,事件开始的时候由最不具体的节点接收,然后逐级向下传播到最具体的节点。
来看一个实例:
理解事件的基本概念
如果单击了p标签,那么,如果是事件冒泡流的事件流机制,则click事件将按照如下顺序进行执行:p —— div —— body —— html —— document。
如果采用捕获流的事件流机制,则click事件的执行顺序为:document —— html —— body —— div —— p
对于冒泡流的事件流机制,存在如下的兼容问题:
div -> body -> document
>=IE6.0 p -> div -> body -> html -> document
>=Mozilla 1.0 p -> div -> body -> html -> document -> window
欢迎大家互相学习交流。独行冰海
事件对象
事件对象:在触发DOM上的某个事件的时候,会产生一个事件对象event,而在这个对象当中会包含着所有与事件有关的信息。我们书写如下基本代码:
<script><br/> var main = document.getElementById('main');<br/> main.onclick = function(event){<br/> console.log(event);<br/> }<br/></script>
使用console.log打印出的结果如下图。
JavaScript事件 详细讲解 - 独行冰海 - 独行冰海
其中有两个信息,我们最为常用,分别是type和target。
type表示的是被触发事件的类型;
target表示的是事件的目标。
其他信息,如:
bubbles:表示事件是否冒泡
cancelable:表示是否可以取消事件的默认行为
currentTarget:表示事件处理程序当前正在处理事件的那个元素
defaultPrevented:表示是否调用了preventDefault()
detail:表示的是与事件相关的细节信息
eventPhase:调用事件处理处理程序的阶段:1表示捕获阶段、2表示处于目标、3表示冒泡阶段
在其中还有一些其他信息,在此就不再一一列举了。
事件方面性能优化
谈一谈事件方面如何优化性能——事件委托和事件处理程序的移除
在JavaScript代码当中,添加到页面中的事件越多,页面的性能也就越差。导致这一问题的原因主要有:
每个函数都是对象,都会占用内存。内存中对象越多,性能也就越差。
必须事先指定所有事件处理程序而导致的DOM访问次数,会延迟整个页面的交互就绪时间。
为了进行页面的性能优化,因此我们会采用两种方法,就是上面提到的——事件委托和事件处理程序的移除。
事件委托
很多人问我,什么时候使用事件委托,其实,简单来说,当时一个页面事件处理程序比较多的时候,我们通常情况下会使用它。
事件委托主要利用了事件冒泡,只指定一个事件处理程序,就可以管理一个类型的所有事件。例如:我们为整个一个页面制定一个onclick事件处理程序,此时我们不必为页面中每个可点击的元素单独设置事件处理程序(onclick)。还是,看一个例子。
效果:点击不同的元素执行不同的操作。
不使用事件委托:
左
1
2
3
右
<script><br/> var left = document.getElementById('left');<br/> var first = document.getElementById('first');<br/> var second = document.getElementById('second');<br/> var third = document.getElementById('third');<br/> var right = document.getElementById('right');<br/> left.addEventListener("click", function(){<br/> alert('点击的是左这个字,执行相关操作'); <br/> }, false);<br/> first.addEventListener("click", function(){<br/> alert('要执行第一个序号对应的相关操作'); <br/> }, false);<br/> second.addEventListener("click", function(){<br/> alert('要执行第二个序号对应的相关操作'); <br/> }, false);<br/> third.addEventListener("click", function(){<br/> alert('要执行第三个序号对应的相关操作'); <br/> }, false);<br/> right.addEventListener("click", function(){<br/> alert('点击的是右这个字,执行相关操作'); <br/> }, false);<br/></script>
不难看出,我们使用了5个事件侦听器,每设置一个就需要绑定一个。
使用事件委托:
左
1
2
3
右
<script><br/> var control = document.getElementById('control');<br/> control.addEventList ", function(e){<br/> 請注意器,如果想書寫相容全部瀏覽器的事件處理程序,請查看下一篇博文<br/> var target = e.target;<br/> // id){<br/> case "left" : {<br/> break;<br/> }<br/> case "first" : {的相關操作');<br/> break;<br/> }<br/> case "second" : {<br/> alert('要執行第二個序號對應的相關操作');<br/> break;<br/> }<br/> case "third" : {<br/> alert( '要執行第三序號對應的相關作業');<br/> break;<br/> case "right" : {<br/> alert('點選的是右這個字,為相關操作); }<br/> }<br/> }, false);<br/></script>
簡要的總結所謂的事件委託:給元素的父級或祖級,甚至頁面綁定事件,然後利用事件冒泡的基本原理,透過事件目標物件進行偵測,然後執行相關操作。其優點在於:
大大減少了事件處理程序的數量,在頁面中設定事件處理程序的時間就更少了(DOM引用減少——也就是上面我們透過id去獲取標籤,所需要的查找操作以及DOM引用也就更少了)。
document(註:上面的例子沒有綁定在document上,而是綁定到了父級的div上,最推薦的是綁定在document上)物件可以快速的存取到,而且可以在頁面生命週期的任何時點上為它添加事件處理程序,並不需要等待DOMContentLoaded或load事件。換句話說,只要可點擊的元素在頁面中呈現出來了,那麼它就立刻具備了對應的功能。
整個頁面佔用的記憶體空間會更少,從而提升了整體的效能。
移除事件處理程序
每當將一個事件處理程序指定給一個元素時,在運行中的瀏覽器程式碼與支援頁面互動的JavaScript程式碼之間就會建立一個連結。連線數量也直接影響頁面的執行速度。所以,當記憶體中存在著過時的「空事件處理程序」的時候,就會造成Web應用程式的記憶體和效能問題。
那麼什麼時候會造成「空事件處理程序」的出現呢?
文檔中元素存在事件,透過一些DOM節點操作(removeChild、replaceChild等方法),移除了這個元素,但是DOM節點的事件沒有被移除。
innerHTML去替換頁面中的某一部分,頁面中原來的部分存在事件,沒有移除。
頁面卸載引起的事件處理程序在記憶體中的滯留。
解決方法:
合理利用事件委託;
在執行相關操作的時候,先移除掉事件,再移除DOM節點;
在頁面卸載之前,先透過onunload事件移除所有事件處理程序。

理解JavaScript引擎內部工作原理對開發者重要,因為它能幫助編寫更高效的代碼並理解性能瓶頸和優化策略。 1)引擎的工作流程包括解析、編譯和執行三個階段;2)執行過程中,引擎會進行動態優化,如內聯緩存和隱藏類;3)最佳實踐包括避免全局變量、優化循環、使用const和let,以及避免過度使用閉包。

Python更適合初學者,學習曲線平緩,語法簡潔;JavaScript適合前端開發,學習曲線較陡,語法靈活。 1.Python語法直觀,適用於數據科學和後端開發。 2.JavaScript靈活,廣泛用於前端和服務器端編程。

Python和JavaScript在社區、庫和資源方面的對比各有優劣。 1)Python社區友好,適合初學者,但前端開發資源不如JavaScript豐富。 2)Python在數據科學和機器學習庫方面強大,JavaScript則在前端開發庫和框架上更勝一籌。 3)兩者的學習資源都豐富,但Python適合從官方文檔開始,JavaScript則以MDNWebDocs為佳。選擇應基於項目需求和個人興趣。

從C/C 轉向JavaScript需要適應動態類型、垃圾回收和異步編程等特點。 1)C/C 是靜態類型語言,需手動管理內存,而JavaScript是動態類型,垃圾回收自動處理。 2)C/C 需編譯成機器碼,JavaScript則為解釋型語言。 3)JavaScript引入閉包、原型鍊和Promise等概念,增強了靈活性和異步編程能力。

不同JavaScript引擎在解析和執行JavaScript代碼時,效果會有所不同,因為每個引擎的實現原理和優化策略各有差異。 1.詞法分析:將源碼轉換為詞法單元。 2.語法分析:生成抽象語法樹。 3.優化和編譯:通過JIT編譯器生成機器碼。 4.執行:運行機器碼。 V8引擎通過即時編譯和隱藏類優化,SpiderMonkey使用類型推斷系統,導致在相同代碼上的性能表現不同。

JavaScript在現實世界中的應用包括服務器端編程、移動應用開發和物聯網控制:1.通過Node.js實現服務器端編程,適用於高並發請求處理。 2.通過ReactNative進行移動應用開發,支持跨平台部署。 3.通過Johnny-Five庫用於物聯網設備控制,適用於硬件交互。

我使用您的日常技術工具構建了功能性的多租戶SaaS應用程序(一個Edtech應用程序),您可以做同樣的事情。 首先,什麼是多租戶SaaS應用程序? 多租戶SaaS應用程序可讓您從唱歌中為多個客戶提供服務

本文展示了與許可證確保的後端的前端集成,並使用Next.js構建功能性Edtech SaaS應用程序。 前端獲取用戶權限以控制UI的可見性並確保API要求遵守角色庫


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

SecLists
SecLists是最終安全測試人員的伙伴。它是一個包含各種類型清單的集合,這些清單在安全評估過程中經常使用,而且都在一個地方。 SecLists透過方便地提供安全測試人員可能需要的所有列表,幫助提高安全測試的效率和生產力。清單類型包括使用者名稱、密碼、URL、模糊測試有效載荷、敏感資料模式、Web shell等等。測試人員只需將此儲存庫拉到新的測試機上,他就可以存取所需的每種類型的清單。

WebStorm Mac版
好用的JavaScript開發工具

mPDF
mPDF是一個PHP庫,可以從UTF-8編碼的HTML產生PDF檔案。原作者Ian Back編寫mPDF以從他的網站上「即時」輸出PDF文件,並處理不同的語言。與原始腳本如HTML2FPDF相比,它的速度較慢,並且在使用Unicode字體時產生的檔案較大,但支援CSS樣式等,並進行了大量增強。支援幾乎所有語言,包括RTL(阿拉伯語和希伯來語)和CJK(中日韓)。支援嵌套的區塊級元素(如P、DIV),

VSCode Windows 64位元 下載
微軟推出的免費、功能強大的一款IDE編輯器

DVWA
Damn Vulnerable Web App (DVWA) 是一個PHP/MySQL的Web應用程序,非常容易受到攻擊。它的主要目標是成為安全專業人員在合法環境中測試自己的技能和工具的輔助工具,幫助Web開發人員更好地理解保護網路應用程式的過程,並幫助教師/學生在課堂環境中教授/學習Web應用程式安全性。 DVWA的目標是透過簡單直接的介面練習一些最常見的Web漏洞,難度各不相同。請注意,該軟體中