2.1.1 DOM简介
1、DOM:文档对象模型,是W3C组织推荐的处理可扩展标记语言的标准编程接口。
2、DOM树
文档:一个页面就是一个文档,DOM中使用document表示
元素:页面中的所有标签都是元素,DOM中使用element表示
节点:网页中的所有内容都是节点,DOM中使用node表示
2.1.2 获取元素
1、根据ID获取:使用getElementById()方法可以获取带有ID的元素对象
<div id="time">2022-3-5</div> <script> //因为我们的文档从上往下加载,所以先有标签,所以script写在下面 //参数id是大小写敏感的字符串 //返回的是一个元素对象 var timer = document.getElementById('time'); console.log(timer); //打印返回的元素对象,更好的查看属性和方法 console.dir(timer);//div#time </script>
2、根据标签名获取:使用getElementsByTagName()方法可以返回带有指定标签名的对象集合(以伪数组形式存储)
<ul> <li>知否知否,应是等你好久1</li> <li>知否知否,应是等你好久2</li> <li>知否知否,应是等你好久3</li> <li>知否知否,应是等你好久4</li> <li>知否知否,应是等你好久5</li> </ul> <ol id="ol"> <li>生僻字</li> <li>生僻字</li> <li>生僻字</li> <li>生僻字</li> </ol> <script> //返回的是获取过来元素对象的集合,以伪数组的形式存储的 var lis = document.getElementsByTagName('li'); console.log(lis); console.log(lis[0]); //依次打印里面的元素对象,动态的 for(var i = 0;i < lis.length;i++) { console.log(lis[i]); } //element.getElementsByTagName('标签名'); //法1 var ol = document.getElementsByTagName('ol'); console.log(ol[0].getElementsByTagName('li')); //法2 var ol1 = document.getElementById('ol'); console.log(ol1.getElementsByTagName('li')); </script>
3、通过HTML5新增的方法获取
-
根据类名返回元素对象集合:document.getElementsByClassName('类名');
-
根据指定选择器返回第一个元素:document.querySelector('选择器');
-
根据指定选择器返回:
<div class="box">盒子1</div> <div class="box">盒子2</div> <div id="nav"> <ul> <li>首页</li> <li>产品</li> </ul> </div> <script> //getElementsByClassName var boxs = document.getElementsByClassName('box'); console.log(boxs); //querySelector var firstBox = document.querySelector('.box'); console.log(firstBox); var nav = document.querySelector('#nav') console.log(nav); //querySelectorAll var allBox = document.querySelectorAll('.box'); console.log(allBox); </script>
4、获取特殊元素(body、html)
-
获取body元素
var bodyEle = document.body; console.log(bodyEle); console.dir(bodyEle);
-
获取html元素
var htmlEle = document.documentElement; console.log(htmlEle); console.dir(htmlEle);
2.1.3 事件基础
1、事件三要素:事件源、事件类型、事件处理程序
//点击一个按钮,弹出对话框(点击是onclick) <button id="btn">点击这里</button> <script> var btn = document.getElementById('btn'); btn.onclick = function() { alert('事件出来了'); } </script>
2、常见的鼠标事件
鼠标事件 | 触发条件 |
---|---|
onclick | 鼠标点击左键触发 |
onmouseover | 鼠标经过触发 |
onmouseout | 鼠标离开触发 |
onfocus | 获得鼠标焦点触发 |
onblur | 失去鼠标焦点触发 |
onmousemove | 鼠标移动触发 |
onmouseup | 鼠标弹起触发 |
onmousedown | 鼠标按下触发 |
2.1.4 操作元素
1、改变元素内容
-
element.innerText:从起始位置到终止位置的内容,但他除去html标签,同时空格和换行也会去掉
-
element.innerHTML:起始位置到终止位置的全部内容,包括html标签,同时保留空格和换行
-
二者区别:innerText不识别标签,是非标准;innerHTML识别标签
<button>显示当前系统时间</button> <div>某个时间</div> <p>继续显示时间</p> <script> //点击按钮div发生变化 var btn = document.querySelector('button'); var div = document.querySelector('div'); btn.onclick = function() { // div.innerText = getTime(); div.innerHTML = getTime(); } function getTime() { var date = new Date(); var year = date.getFullYear(); var month = date.getMonth()+1; var dates = date.getDate(); var arr = ['星期日','星期一','星期二','星期三','星期四','星期五','星期六']; var day = date.getDay(); var time = year + '年' + month + '月' + dates + '日' + '\t' + arr[day]; return time; } //不添加事件直接显示 var p = document.querySelector('p'); //p.innerText = getTime(); p.innerHTML = getTime(); </script>
2、常用元素的属性操作
<button id="t1">图片1</button> <button id="t5">图片5</button> <img src="图一.jpg" alt=""> <script> var t1 = document.getElementById('t1'); var t5 = document.getElementById('t5'); var img = document.querySelector('img'); t5.onclick = function() { img.src = '图五.jpg'; } t1.onclick = function() { img.src = '图一.jpg'; } </script>
3、表单元素的属性操作
DOM可以操作如下表单元素:type、value、checked、selected、disabled
<button>按钮</button> <input type="text" value="输入内容"> <script> var input = document.querySelector('input'); var btn = document.querySelector('button'); btn.onclick = function() { input.value = '你好棒';//表单的文字是通过value进行修改的 //禁用按钮 //1 // btn.disabled = true; //2,this指向事件函数的调用者 this.disabled = true; } </script>
4、样式属性操作
-
行内样式操作:element.style
-
类名样式操作:element.className(若想保留原类名,采用多类名选择器)
//element.style div { width: 400px; height: 400px; background-color: pink; } <div></div> <script> var div = document.querySelector('div'); div.onclick = function() { this.style.backgroundColor = 'purple'; this.style.width = '200px'; } </script> //element.className div { width: 400px; height: 400px; background-color: pink; } .change { background-color: purple; width: 200px; } <div></div> <script> var div = document.querySelector('div'); div.onclick = function() { this.className = 'change'; } </script>
5、排他思想
有同一组元素,想要某一个实现一种样式,运用循环
步骤:
-
所有元素全部清除样式
-
给当前元素设计样式
<button>按钮1</button> <button>按钮2</button> <button>按钮3</button> <button>按钮4</button> <button>按钮5</button> <script> var btns = document.getElementsByTagName('button'); for(var i = 0;i < btns.length; i++){ btns[i].onclick = function() { for(var i = 0;i < btns.length; i++){ btns[i].style.backgroundColor = ''; } this.style.backgroundColor = 'pink'; } } </script>
6、自定义属性的操作
(1)获取属性值
-
element.属性:获得内置属性值
-
element.getAttribute('属性'):主要获得自定义属性
(2)设置属性值
-
element.属性 = '值':设置内置属性值
-
element.setAttribute('属性','值'):主要设置自定义属性值
(3)移除属性:element.removeAttribute('属性 ')
7、H5自定义属性
规定自定义属性由data-开头并赋值
获取属性:element.dataset.属性 或者 element.dataset['属性']
eg:属性是data-index,则获取属性写index;属性是data-list-name,则获取属性写listName
2.1.5 节点操作
1、节点概述
-
元素节点:nodeType为1
-
属性节点:nodeType为2
-
文本节点:nodeType为3
2、节点层级
(1)父级节点:element.parentNode(只返回最近的节点)
(2)子节点:
-
element.childNodes(所有的子节点,包含元素节点和子节点)
-
element.children(只有元素节点)
-
element.firstChild(获取第一个子节点,文本和元素)
-
element.lastChild(获取最后一个子节点,文本和元素)
-
element.firstElementChild(获取第一个子节点,元素)
-
element.lastElementChild(获取最后一个子节点,元素)
-
element.children[i](实际开发使用的)
(3)兄弟节点:
-
node.nextSibling(下一个兄弟节点,文本和元素)
-
node.previousSibling(上一个兄弟节点,文本和元素)
-
node.nextElementSibling(下一个兄弟节点,元素)
-
node.previousElementSibling(上一个兄弟节点,元素)
3、创建节点:document.createElement('tagName')
4、添加节点:
-
在后面添加:node.appendChild(child)(node是父节点,child是子节点)
-
在前面添加:node.insertBefore(child,指定元素)
5、删除节点:node.removeChild(child)
6、复制节点(克隆节点):node.cloneNode(true);(括号为空或false,则不拷贝里面的内容;若为true,则全拷贝)
7、三种动态创建元素区别
-
document.write():直接将内容写入页面内容中,但是文档流执行完毕,会导致页面重绘。
-
element.innerHTML:创建多个元素效率更高(不要拼接字符串,采用数组形式拼接),结构稍微复杂
-
document.createElement():创建多个元素效率低一点点,结构更加清晰
2.1.6 DOM重点核心
1、创建
-
document.write()
-
element.innerHTML
-
document.createElement()
2、增
-
node.appendChild(child)
-
node.insertBefore(child,指定元素)
3、删
-
node.removeChild(child)
4、改
主要修改dom的元素属性,dom元素的内容、属性、表单的值等。
-
修改元素属性:src、href、title等
-
修改普通元素内容:innerHTML、innerText
-
修改表单元素:value、type、disabled等
-
修改元素样式:style、className
5、查
主要获取查询dom的元素
-
DOM提供的API方法:getElementsById、getElementsByTagName(古老方法、不太推荐)
-
H5提供的新方法:querySelector、querySelectorAll(提倡)
-
利用节点操作获取元素:父(parentNode)、子(children)、兄(previousElementSibling、nextElementSibling)(提倡)
6、属性操作
主要针对自定义属性
-
setAttribute:设置dom的属性值
-
getAttribute:得到dom的属性值
-
removeAttribute:移除属性
7、事件操作
给元素注册时间,采取 事件源-事件类型=事件处理程序
鼠标事件 | 触发条件 |
---|---|
onclick | 鼠标点击左键触发 |
onmouseover | 鼠标经过触发 |
onmouseout | 鼠标离开触发 |
onfocus | 获得鼠标焦点触发 |
onblur | 失去鼠标焦点触发 |
onmousemove | 鼠标移动触发 |
onmouseup | 鼠标弹起触发 |
onmousedown | 鼠标按下触发 |
2.1.7 事件高级
1、注册事件
(1)注册方式
①传统注册方式
-
利用on开头的事件
-
<button οnclick="alert('hi~')"></button> btn.onclick = function(){}
-
特点:注册事件的唯一性
-
同一个元素同一个事件只能设置一个处理函数,最后注册的处理函数将会覆盖前面注册的处理函数
②方法监听注册方式
-
W3C标准(推荐方式)
-
addEventListener()他是一个方法
-
有兼容问题,之前的版本用attachEvent()代替
-
特点:同一个元素同一个事件可以注册多个监听器
(2)addEventListener事件监听方式
eventTarget.addEventListener(type, listener[, useCapture])
type:事件类型字符串,比如click、mouseover,不加on
listener:事件处理函数,事件发生时,会调用该监听函数
useCapture:可选参数,是一个布尔值,默认是false
(3)attachEvent注册事件(ie9以前的)
eventTarget.attachEvent(eventNameWithOn, callback)
eventNameWithOn:事件类型字符串,带on
callback:事件处理函数,当目标触发事件时回调函数被调用
(4)兼容解决方案
function addEventListener(element , eventName , fn) { //判断当前浏览器是否支持addEventListener方法 if (element.addEventListener) { element.addEventListener (eventName, fn); //第三个参数默认为false }else if (element.attachEvent) { element.attachEvent('on' + eventName, fn); }else { //相当于element.onclick =fn; element['on' + eventName] = fn; } }
2、删除事件
①传统删除事件
eventTarget.onclick = null;
②方法监听删除方式
-
eventTarget.removeEventListener(type, listener[, useCapture])
-
eventTarget.detachEvent(eventNameWithOn, callback)
//使用方式 <button>传统注册事件</button> <button>方法监听注册事件</button> <button>attachEvent</button> <script> var btns = document.querySelectorAll('button'); //方法1 btns[0].onclick = function() { alert('hello~'); btns[0].onclick = null; } //方法2 btns[1].addEventListener('click',fn); function fn() { alert('hello cc!'); btns[1].removeEventListener('click',fn); } //方法3 btns[2].attachEvent('onclick',fn1); function fn1() { alert('You are beautiful'); btns[2].detachEvent('onclick',fn1); } </script>
3、DOM事件流
(1)三个阶段:捕获阶段、当前目标阶段、冒泡阶段
(2)注意:
-
JS代码中只能执行捕获或者冒泡其中一个阶段
-
onclick和attachEvent只能得到冒泡阶段
-
addEventListener第三个参数为true是捕获阶段,为false或者省略为冒泡阶段
4、事件对象
(1)事件对象介绍
event可以自定义名字,存在兼容性问题,事件对象是系统创建的,包含属性和方法
解决兼容性:e || window.event
(2)事件对象的常见属性和方法
事件对象属性方法 | 说明 |
---|---|
e.target | 返回触发事件的对象(标准) |
e.srcElement | 返回触发事件的对象(非标准 ie6-8) |
e.type | 返回事件的类型(比如click、mouseover,不带on) |
e.cancelBubble | 该属性阻止冒泡(非标准 ie6-8) |
e.returnValue | 该属性阻止默认事件(默认行为)(非标准 ie6-8 比如不让链接跳转) |
e.preventDefault() | 该方法阻止默认事件(默认行为)(标准 比如不让链接跳转) |
e.stopPropagation() | 阻止冒泡(标准) |
(3)e.target与this区别
e.target:返回的是触发事件的对象(元素)
this:返回的是绑定事件的对象(元素)
5、阻止事件冒泡
事件冒泡:开始时由最具体的元素接收,然后逐级向上传播到DOM最顶层节点
方法:
-
标准:e.stopPropagation()
-
非标准:e.cancelBubble = true
6、事件委托(代理、委派)
原理:不是每个子节点单独设置事件监听器,而是事件监听器设置在其父节点上,然后利用冒泡原理影响设置每个子节点
//例子 <ul> <li>广平王</li> <li>许宣</li> <li>陆绎</li> <li>周生辰</li> <li>叶冲</li> </ul> <script> var ul = document.querySelector('ul'); ul.addEventListener('click',function() { alert('广平王') }) </script>
7、常用鼠标事件
鼠标事件 | 触发条件 |
---|---|
onclick | 鼠标点击左键触发 |
onmouseover | 鼠标经过触发 |
onmouseout | 鼠标离开触发 |
onfocus | 获得鼠标焦点触发 |
onblur | 失去鼠标焦点触发 |
onmousemove | 鼠标移动触发 |
onmouseup | 鼠标弹起触发 |
onmousedown | 鼠标按下触发 |
(1)禁止鼠标右键菜单:contextmenu
contextmenu主要控制应该何时显示上下文菜单,主要用于程序员取消默认的上下文菜单
document.addEventListener('contextmenu',function(e) { e.preventDefault(); })
(2)禁止鼠标选中:selectstart
document.addEventListener('selectstart',function(e) { e.preventDefault(); })
(3)鼠标事件对象:MouseEvent
鼠标事件对象 | 说明 |
---|---|
e.clientX | 返回鼠标相对于浏览器窗口可视区的X坐标 |
e.clientY | 返回鼠标相对于浏览器窗口可视区的Y坐标 |
e.pageX | 返回鼠标相对于文档页面的X坐标(IE9+支持) |
e.pageY | 返回鼠标相对于文档页面的Y坐标(IE9+支持) |
e.screenX | 返回鼠标相对于电脑屏幕的X坐标 |
e.screenY | 返回鼠标相对于电脑屏幕的Y坐标 |
8、常用的键盘事件
(1)常用键盘事件
键盘事件 | 触发条件 |
---|---|
onkeyup | 某个键盘按键被松开时触发 |
onkeydown | 某个键盘按键被按下时触发 |
onkeypress | 某个键盘按键被按下时触发(不识别功能键) |
是那个事件的执行顺序:keydown---keypress---keyup
(2)键盘事件对象
-
keyup和keydown事件不区分字母大小写
-
keypress区分字母大小写
-
返回该键的ASCII值:keyCode