目录
一、DOM
1.1 简介
DOM,全称Document Object Model文档对象模型。
JS中通过DOM来对HTML文档进行操作。
- 文档:文档表示的就是整个的HTML网页文档
- 对象:对象表示将网页中的每个部分都转换为了一个对象
- 模型:使用模型来表示对象之间的关系,这样方便我们获取对象
1.1.1 模型
1.1.2 节点
节点Node,是构成我们网页的最基本的组成部分,网页中的每一个部分都可以称为是一个节点,比如:HTML标签、属性、文本、注释、整个文档等都是一个节点。
虽然都是节点,但是实际上他们的具体类型是不同的,比如:标签我们称为元素节点、属性称为属性节点、文本称为文本节点、文档称为文档节点。
节点的类型不同,属性和方法也都不尽相同。
常用节点分为四类:
- 文档节点:整个HTML文档
- 元素节点:HTML文档中的HTML标签
- 属性节点:元素的属性
- 文本节点:HTML标签中的文本内容
1.1.3 节点的属性
浏览器已经为我们提供了文档节点对象,这个对象是window属性,可以再页面中直接使用,文档节点代表的是整个网页。
<body>
<button id="btn">button</button>
<script type="text/javascript">
// 获取到button对象
let btn = document.getElementById("btn");
// 修改按钮文字
btn.innerHTML = "I'm button";
</script>
</body>
1.2 事件
事件,就是用户和浏览器之间的交互行为,比如:点击按钮、拖动窗口。。。
我们可以在事件对应的属性中设置一些JS代码,这样当事件被触发时,代码被执行。但是这种写法我们称为结构和行为耦合,不方便维护。
可以为按钮的对应事件绑定处理函数的形式来响应事件,这样当事件被触发时,其对应的函数将会被调用。
// 绑定一个单机事件
btn.onclick = function() {
alert(111);
};
1.3 文档的加载
浏览器在加载一个页面时,是按照自上向下的顺序加载的,读取到一行就运行一行,如果将script标签写到页面的上边,在代码执行时,页面还没有加载。
onload事件会在整个页面加载完成之后才触发。
// 为window绑定一个onload事件
window.onload = function() {
alert("hello");
};
为window绑定一个onload事件,该事件对应的响应函数将会在页面加载完成之后执行,这样可以确保我们的代码执行时,所有的DOM对象已经加载完毕。
1.4 DOM查询
1.4.1 获取元素节点
innerHTML 通过这个属性可以获取到元素内部的HTML代码
alert(bj.innerHTML);
innerHTML用于获取元素内部的HTML代码,对于自结束标签,这个属性没有意义
如果需要读取元素节点属性,直接使用 元素.属性名
- 但是,class属性不能采用这种方式,读取class时,使用className
1.4.2 获取元素节点的子节点
childNodes 属性会返回包括文本节点在内的所有节点。
根据DOM标准,标签间的空白也会被当作文本节点。
- 注意:在IE8及以下的浏览器中,不会将空白文本当成文本节点。
children属性可以获取当前元素的所有子元素。
一定要注意元素与节点的区别。
firstChild可以火圈当前元素的第一个子节点(包括空白文本节点)
firstElementChild可以获取当前元素的第一个元素,但是其不兼容IE8及以下的浏览器
1.4.3 获取父节点和兄弟节点
定义一个函数,专门用来为指定元素绑定单击响应函数。
参数:
- idStr 要绑定单击响应函数的对象的id属性值
- fun 事件的回调函数,当单击元素时,该函数将会被触发
function myClick(idStr, fun) {
let btn = document.getElementById(idStr);
btn.onclick = fun;
}
innerText
- 该属性可以获取到元素内部的文本内容
- 它和innerHTML类似,不同的是,它会自动将HTML去除
全选练习
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script type="text/javascript">
window.onload = function() {
let checkedAllBtn = document.getElementById("checkedAllBtn");
// 为id为checkedAllBrn的按钮绑定一个单击响应函数
checkedAllBtn.onclick = function () {
// 获取四个多选框items
let items = document.getElementsByName("items");
// 遍历items
for (let i=0; i<items.length; i++) {
// 设置四个多选框变成选中状态
// 通过多选框的checked属性可以来获取或设置多选框的选中状态
items[i].checked = true;
}
};
let checkedNoBtn = document.getElementById("checkedNoBtn");
checkedNoBtn.onclick = function () {
let items = document.getElementsByName("items");
for (let i=0; i<items.length; i++) {
items[i].checked = false;
}
};
let checkedRevBtn = document.getElementById("checkedRevBtn");
checkedRevBtn.onclick = function () {
let items = document.getElementsByName("items");
for (let i=0; i<items.length; i++) {
items[i].checked = !items[i].checked;
}
};
let sendBtn = document.getElementById("sendBtn");
sendBtn.onclick = function () {
let items = document.getElementsByName("items");
for (let i=0; i<items.length; i++) {
if (items[i].checked) {
alert(items[i].value)
}
}
};
let checkedAllBox = document.getElementById("checkedAllBox");
checkedAllBox.onclick = function () {
let items = document.getElementsByName("items");
for (let i=0; i<items.length; i++) {
items[i].checked = this.checked;
}
};
let items = document.getElementsByName("items");
for (let i=0; i<items.length; i++) {
items[i].onclick = function () {
checkedAllBox.checked = true;
for (let j=0; j<items.length; j++) {
if (!items[j].checked) {
checkedAllBox.checked = false;
}
}
}
}
};
</script>
</head>
<body>
<form method="post" action="">
你爱好的运动是?
<input type="checkbox" id="checkedAllBox" />全选/全不选
<br />
<input type="checkbox" name="items" value="足球" />足球
<input type="checkbox" name="items" value="篮球" />篮球
<input type="checkbox" name="items" value="羽毛球" />羽毛球
<input type="checkbox" name="items" value="乒乓球" />乒乓球
<br />
<input type="button" id="checkedAllBtn" value="全 选" />
<input type="button" id="checkedNoBtn" value="全不选" />
<input type="button" id="checkedRevBtn" value="反 选" />
<input type="button" id="sendBtn" value="提 交" />
</form>
</body>
</html>
在事件的响应函数中,响应函数是给谁绑定的this就是谁。
1.4.4 其他方法
document.body
在document中有一个属性body,它保存的是body的引用
let body = document.body;
document.documentElement
保存的是HTML根标签
document.all
代表页面中的所有元素
let all = document.all;
let all = document.getElementByTagName("*");
根据元素的class属性值查询一组元素节点对象
document.getElementByClassName()
可以根据class属性值获取一组元素节点对象,但是仅支持IE8以上的版本
document.querySelector()
需要一个选择器的字符串作为参数,可以根据一个CSS选择器来查询一个元素节点对象。
- 虽然IE8没有getElementByClassName()但是用其来代替
- 该方法只能返回一个元素,若有多个,则返回第一个
let div = document.querySelector(".box1 div");
let box1 = document.querySelector(".box1");
document.querySelectorAll()
该方法与querySelector()类似,但是它可以返回多个对象,并将他们封装成一个数组
1.5 DOM的增删改
document.createElement()
可以用于创建一个元素节点对象,它需要一个标签名作为参数,将会根据该标签名创建元素节点对象,并将创建好的对象作为返回值返回。
document.createTextNode()
可以用来创建一个文本节点,需要一个文本内容作为参数,将会根据该内容创建文本节点,并将创建好的对象作为返回值返回
appendChild()
可以向一个父节点中添加一个新的子节点
- 用法: 父节点.appendChild(子节点)
insertBefore()
可以在指定的子节点前插入新的子节点
- 语法:父节点.insertBefore(新节点, 旧节点)
replaceChild()
可以使用指定的子节点替换原来的节点,语法与前面的一样。
removeChild()
删除子节点
- 语法:父节点.removeChild(子节点)
bi,parentNode.removeChild(bi);
innerHTML
获取节点里的代码,使用innerHTML也可以完成DOM增删改的相关操作,一般我们会两种方式结合使用
let li = document.createElement("li");
li.innerHTML = "广州";
city.appendChild(li);
confirm()
用于弹出一个带有确认和取消按钮的提示框,需要一个字符串作为参数,该字符串将会作为提示文字显示出来,如果用户点击确认则返回true,如果点击取消则返回false
for循环会在页面加载完成后立即执行,而响应函数会在超链接被点击时才执行;当响应函数执行时,for循环早已执行完毕。
1.6 使用DOM操作CSS
1.6.1 修改内联样式
通过JS修改元素的样式:
- 语法:元素.style.样式名 = 样式值
box1.style.width = "300px";
注意:如果CSS的样式中含有-,这种名称在JS中是不合法的,需要将这种样式名修改为驼峰命名法,去掉-,将-后的首字母大写
box1.style.backgroundColor = "yellow";
我们通过style属性设置的样式都是内联样式,而内联样式有较高的优先级,所以通过JS修改的样式往往会立即显示。
读取样式:
- 语法:元素.style.样式名
通过style属性读取和设置的都是内联样式,所以它读取不了样式表中的样式
1.6.2 获取元素的样式
读取元素当前显示的样式:
- 语法:元素.currentStyle.样式名
如果当前元素没有设置该样式,则获取它的默认值,但是其只有IE支持。
在其他浏览器中可以使用:
getComputedStyle()
这个方法来获取元素当前的样式,这个方法是window的方法,可以直接使用
- 其需要两个参数,第一个是要获取样式的元素,第二个可以传递一个伪元素,一般直接传null
- 该方法会返回一个对象,对象中封装了当前元素对应的样式,可以通过对象
.样式名来读取样式,如果获取的样式没有设置,则会获取到真实的值,而不是默认值,比如:没有设置width,它不会获取到auto,而是一个长度,但是其不支持IE8及以下的浏览器
getComputedStyle(box1, null).width;
// 定义一个函数,用来获取指定元素的当前的样式
// 参数:obj 要获取的元素 name 要获取的样式名
function getStyle(obj, name) {
if (window.getComputedStyle) {
// 正常浏览器的方式
return getComputedStyle(obj, null)[name];
} else {
// IE8的方式
return obj.currentStyle[name];
}
}
通过getComputedStyle和currentStyle获取的样式都是只读的。
1.6.3 其他样式相关的属性
clinetWidth
clientHeight
这两个属性可以返回元素的可见宽度和高度,这些属性返回的都是数字,不带px,可以直接计算
- 会获取元素宽度和高度,包括内容区和内边距
- 这些属性都是只读的,无法修改
offsetWidth
offsetHeight
获取元素整个的宽度和高度,包括内容区,内边距和边框
offsetParent
可以获取当前元素的定位父元素,会获取到离当前元素最近的开启了定位的祖先元素,如果所有的祖先元素都没有开启定位,则返回body
offsetLeft
当前元素相对于定位父元素的水平偏移量
offsetTop
当前元素相对于其定位父元素的垂直偏移量
scrollWidth
scrollHeight
获取元素整个滚动区域的宽度和高度
scrollLeft
scrollTop
获取水平、垂直滚动条滚动的距离
当满足scrollHeight - scrollTop == clientHeight时,说明垂直滚动条滚动条到底了
window.onload = function () {
let info = document.getElementById("info")
let inputs = document.getElementsByTagName("input")
info.onscroll = function () {
if (info.scrollHeight - info.scrollTop === info.clientHeight) {
inputs[0].disabled = false;
inputs[0].disabled = false;
}
};
};
学习的是B站尚硅谷的视频课程: