JavaScript学习笔记(十五) 事件模型 上

简介: JavaScript学习笔记(十五) 事件模型

目录


0、DOM 标准

1、事件模型

2、事件处理程序

3、事件类型

4、事件对象


正文


0、DOM 标准


在开始学习 JavaScript 事件模型前,我们首先来了解一下什么是 DOM(Document Object Model)


简单来说,DOM 是 W3C 定义的访问 HTML 和 XML 文档的标准


按照不同的发展阶段,分为不同的级别,分别是 DOM0、DOM1、DOM2、DOM3


DOM0、DOM2、DOM3 都有定义与事件相关的内容,但是 DOM1 没有定义与事件相关的内容


1、事件模型


(1)事件捕获

事件从文档对象上开始,然后往下传递,直到目标对象(从父到子),低版本浏览器不支持事件捕获


d29aa81dc802b306ede27ffc38123bf2_watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dzbXJ6eA==,size_16,color_FFFFFF,t_70#pic_center.png

<!DOCTYPE html>
<html>
<head>
    <title>事件捕获</title>
</head>
<body>
    <ul>
        <li>Apple</li>
        <li>Banana</li>
        <li>Cherry</li>
    </ul>
</body>
<script>
    let html = document.documentElement
    html.addEventListener('click', () => { console.log('html') }, true)
    let body = document.body
    body.addEventListener('click', () => { console.log('body') }, true)
    let uls = document.getElementsByTagName('ul')
    for (let ul of uls) { ul.addEventListener('click', () => { console.log('ul') }, true) }
    let lis = document.getElementsByTagName('li')
    for (let li of lis) { li.addEventListener('click', () => { console.log('li') }, true) }
    // 点击列表项,打印结果为:html body ul li
</script>
</html>


(2)事件冒泡

事件从目标对象上开始,然后往上传递,直到文档对象(从子到父),所有的浏览器都支持事件冒泡

4f094ba665535726af7ee45f41543b13_watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dzbXJ6eA==,size_16,color_FFFFFF,t_70#pic_center.png



<!DOCTYPE html>
<html>
<head>
    <title>事件冒泡</title>
</head>
<body>
    <ul>
        <li>Apple</li>
        <li>Banana</li>
        <li>Cherry</li>
    </ul>
</body>
<script>
    let html = document.documentElement
    html.addEventListener('click', () => { console.log('html') }, false)
    let body = document.body
    body.addEventListener('click', () => { console.log('body') }, false)
    let uls = document.getElementsByTagName('ul')
    for (let ul of uls) { ul.addEventListener('click', () => { console.log('ul') }, false) }
    let lis = document.getElementsByTagName('li')
    for (let li of lis) { li.addEventListener('click', () => { console.log('li') }, false) }
    // 点击列表项,打印结果为:li ul body html
</script>
</html>


(3)事件流模型

DOM2 定义了事件流模型,这是目前广泛使用的 JavaScript 事件模型,规定事件传递先捕获后冒泡

8893021bad160759e8a1a86cd1fca2f6_watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3dzbXJ6eA==,size_16,color_FFFFFF,t_70#pic_center.png


<!DOCTYPE html>
<html>
<head>
    <title>事件流模型</title>
</head>
<body>
    <ul>
        <li>Apple</li>
        <li>Banana</li>
        <li>Cherry</li>
    </ul>
</body>
<script>
    let html = document.documentElement
    html.addEventListener('click', () => { console.log('Chtml') }, true)
    html.addEventListener('click', () => { console.log('Bhtml') }, false)
    let body = document.body
    body.addEventListener('click', () => { console.log('Cbody') }, true)
    body.addEventListener('click', () => { console.log('Bbody') }, false)
    let uls = document.getElementsByTagName('ul')
    for (let ul of uls) { ul.addEventListener('click', () => { console.log('Cul') }, true) }
    for (let ul of uls) { ul.addEventListener('click', () => { console.log('Bul') }, false) }
    let lis = document.getElementsByTagName('li')
    for (let li of lis) { li.addEventListener('click', () => { console.log('Cli') }, true) }
    for (let li of lis) { li.addEventListener('click', () => { console.log('Bli') }, false) }
    // 点击列表项,打印结果为:Chtml Cbody Cul Cli Bli Bul Bbody Bhtml
</script>
</html>


2、事件处理程序


(1)DOM0 事件处理程序

通过事件监听函数指定事件处理程序,事件处理程序在冒泡阶段执行

<button id="submit">提交</button>


<script>
    var button = document.getElementById('submit')
    // 对于 DOM0 事件处理函数,this 指向目标对象,这里 this 指向 button
    var handleEvent = function(e) { console.log(this) }
    // 添加事件处理函数 button.onclick = handleEvent
    // 删除事件处理函数 button.onclick = null
    button.onclick = handleEvent
</script>

DOM0 事件处理程序,同一个事件只能绑定一个事件处理函数,后面绑定的处理函数会覆盖前面绑定的处理函数

<button id="submit">提交</button>


<script>
    var button = document.getElementById('submit')
    var sayHello = function(e) { console.log('Hello') }
    var sayGoodbye = function(e) { console.log('Goodbye') }
    button.onclick = sayHello
    button.onclick = sayGoodbye
    // 只会打印 Goodbye
</script>


(2)DOM2 事件处理程序

通过 addEventListener() 添加事件处理程序,通过 removeEventListener() 删除事件处理程序

它们都接收三个参数,分别是事件名称、事件处理函数以及一个布尔类型的值,这个布尔值默认为


如果布尔值为 false,则在冒泡阶段执行处理函数,如果布尔值为 true,则在捕获阶段执行处理函数

<button id="submit">提交</button>


<script>
    var button = document.getElementById('submit')
    // 对于 DOM2 事件处理函数,this 指向目标对象,这里 this 指向 button
    var handleEvent = function(e) { console.log(this) }
    // 添加事件处理函数 button.addEventListener('click', handleEvent)
    // 删除事件处理函数 button.removeEventListener('click', handleEvent)
    button.addEventListener('click', handleEvent)
</script>


DOM2 事件处理程序,同一个事件可以绑定多个事件处理函数,先绑定先执行

<button id="submit">提交</button>


<script>
    var button = document.getElementById('submit')
    var sayHello = function(e) { console.log('Hello') }
    var sayGoodbye = function(e) { console.log('Goodbye') }
    button.addEventListener('click', sayHello)
    button.addEventListener('click', sayGoodbye)
    // 先打印 Hello,再打印 Goodbye
</script>


(3)低版本 IE 事件处理程序(IE9 之前)

通过 attachEvent() 添加事件处理程序,通过 detachEvent() 删除事件处理程序


它们都接收两个参数,分别是事件监听函数名称以及事件处理函数,将在冒泡阶段执行处理函数

<button id="submit">提交</button>


<script>
    var button = document.getElementById('submit')
    // 对于低版本 IE 事件处理函数,this 指向全局对象,这里 this 指向 window
    var handleEvent = function() { console.log(this) }
    // 添加事件处理函数 button.attachEvent('onclick', handleEvent)
    // 删除事件处理函数 button.detachEvent('onclick', handleEvent)
    button.attachEvent('onclick', handleEvent)
</script>


低版本 IE 事件处理程序,同一个事件可以绑定多个事件处理函数,先绑定后执行

<button id="submit">提交</button>


<script>
    var button = document.getElementById('submit')
    var sayHello = function() { console.log('Hello') }
    var sayGoodbye = function() { console.log('Goodbye') }
    button.attachEvent('onclick', sayHello)
    button.attachEvent('onclick', sayGoodbye)
    // 先打印 Goodbye,再打印 Hello
</script>


目录
相关文章
|
1天前
|
JavaScript 前端开发
JavaScript 提供了多种方法来操作 DOM(文档对象模型)
【5月更文挑战第11天】JavaScript 用于DOM操作的方法包括获取元素(getElementById, getElementsByClassName等)、修改内容(innerHTML, innerText, textContent)、改变属性、添加/删除元素(appendChild, removeChild)和调整样式。此外,addEventListener用于监听事件。注意要考虑兼容性和性能当使用这些技术。
6 2
|
3天前
|
前端开发 JavaScript UED
JavaScript 的事件循环机制是其非阻塞 I/O 模型的核心
JavaScript的事件循环机制是其非阻塞I/O的关键,通过单线程的调用栈和任务队列处理异步任务。当调用栈空时,事件循环从任务队列取出一个任务执行,形成循环。异步操作完成后,回调函数进入任务队列,等待被事件循环处理。微任务如Promise回调在每个宏任务结束后执行。此机制确保JavaScript能高效处理异步操作,不阻塞主线程,提供流畅的用户体验。
7 2
|
6天前
|
JavaScript 前端开发 开发者
javascript事件大全
javascript事件大全
10 1
|
6天前
|
JavaScript 前端开发
Javascript的一些监听事件
Javascript的一些监听事件
11 2
|
6天前
|
JavaScript 前端开发
js的事件介绍
js的事件介绍
11 1
|
6天前
|
JavaScript 前端开发
js的事件
js的事件
11 1
|
6天前
|
JavaScript 前端开发
js的交互事件
js的交互事件
12 1
|
10天前
|
JavaScript 前端开发 C++
【Web 前端】JavaScript window.onload 事件和 jQuery ready 函数有何不同?
【5月更文挑战第2天】【Web 前端】JavaScript window.onload 事件和 jQuery ready 函数有何不同?
|
13天前
|
存储 移动开发 JavaScript
学习javascript,前端知识精讲,助力你轻松掌握
学习javascript,前端知识精讲,助力你轻松掌握
|
20天前
|
JavaScript 前端开发 测试技术
学习JavaScript
【4月更文挑战第23天】学习JavaScript
13 1