目录
(1). 获取或修改元素开始标签到结束标签之间的原始的HTML内容
【前文回顾】👉 DOM概述及DOM操作之如何查找元素_01
一. 修改: 3种东西
1. 元素的内容: 3种
(1). 获取或修改元素开始标签到结束标签之间的原始的HTML内容
a. 元素.innerHTML
内部的html
b. 指的是<开始标签>原始HTML代码内容</结束标签> 包含html标签
(2). 获取或修改元素开始标签到结束标签之间的纯文本内容
a. 元素.textContent
文本 内容
b. 与 innerHTML 相比多做了两件事:
1). 去掉了内嵌的标签 不包含html标签
2). 将特殊符号翻译为正文
(3). 获取或修改表单元素的值
a. 问题: 大部分input表单元素都是单标记,没有结束标签,所以无法使用innerHTML和textContent
b. 解决: 今后,只要想获得表单元素的值,都用表单元素.value
(4). 示例: 比较三种内容属性的不同:
0_content.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
</head>
<body>
<!-- 什么也不做 -->
<p id="p1">来自<a href="javascript:;"><<新华社>></a>的消息</p>
<input /><button id="btn">百度一下</button>
<script>
var p1 = document.getElementById("p1");
//想获取p元素的内容
console.log(p1.innerHTML);
//想获得p元素的内容,但是想去掉内嵌的标签和特殊符号,只获取文字
console.log(p1.textContent);
//想点击按钮,获得旁边文本框的内容
var btn = document.getElementById("btn");
btn.onclick = function () {
//获得当前按钮的前一个兄弟input元素
var input = this.previousElementSibling;
console.log(`查找 ${input.value} 相关的内容...`);
};
</script>
</body>
</html>
运行结果:
(5). 示例: 动态开关门效果:
0_door.html
<!DOCTYPE html>
<html>
<head>
<title>读取并修改元素的内容</title>
<meta charset="utf-8" />
<style>
div {
float: left;
height: 100px;
line-height: 100px;
}
#d1,
#d3 {
background-color: #ccff00;
}
#d2 {
cursor: pointer;
background-color: #ffcc00;
}
</style>
</head>
<body>
<div id="d1" style="">树形列表</div>
<div id="d2"><<</div>
<div id="d3">内容的主体</div>
<script>
//DOM 4步
//1. 查找触发事件的元素
//本例中: 用户点d2触发事件
var d2 = document.getElementById("d2");
//2. 绑定事件处理函数
d2.onclick = function () {
//3. 查找要修改的元素
//本例中: 用户点d2,改的是d1
var d1 = document.getElementById("d1");
//4. 修改元素
//如果d2的内容是>>,说明d1是关着的!
if (d2.innerHTML == ">>") {
//就打开d1: 其实就是让d1显示出来,其实就是去掉d1的display属性
d1.style.display = "";
//等效于<div id="d1" style="">
//d2的内容变为<<
d2.innerHTML = "<<";
} else {
//否则如果d1是开着的
//就关闭d1: 其实就是让d1隐藏, 其实就是修改d1的display属性为none
d1.style.display = "none";
//等效于: <div id="d1" style="display:none">
//d2的内容变为>>
d2.innerHTML = ">>";
}
};
</script>
</body>
</html>
运行结果:
2. 元素的属性: 3种
(1). 字符串类型的HTML标准属性
a. 什么是HTML标准属性: HTML标准中规定的属性
b. 如何获取或修改: 2种:
1). 旧核心DOM 4个函数:
i. 获取一个元素的一个属性值:
元素.getAttribute("属性名")
获取 属性
ii. 修改一个元素的属性值:
元素.setAttribute("属性名","属性值")
修改 属性
iii. 判断元素上是否包含某个属性
var bool值=元素.hasAttribute("属性名")
有 属性(吗)?
iv. 移除元素上一个属性
元素.removeAttribute("属性名")
移除 属性
v. 示例: 使用核心DOM4个函数操作元素的属性
1_attribute.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
</head>
<body>
<a id="a1" href="http://tmooc.cn" title="欢迎访问tmooc">go to tmooc</a>
<script>
var a1 = document.getElementById("a1");
//想获得a1的href属性值
var href = a1.getAttribute("href");
console.log(href);
//修改a1的title属性值
a1.setAttribute("title", "Welcome tmooc");
//判断a1是否包含target属性
var bool = a1.hasAttribute("target");
console.log(bool); //false
//移除a1的id属性
a1.removeAttribute("id");
console.log(a1);
</script>
</body>
</html>
运行结果:
vi. 问题: 旧核心DOM函数名太长,不好用!
2). 新HTML DOM:
i. 什么是HTML DOM: 是专门对常用的HTML对象和属性提供的简化版DOM
ii. 如何简化: HTML DOM已经提前将所有HTML标准属性都保存在了内存中的元素对象身上,只不过暂时不用的属性值,默认都为""。可以直接用.方式,访问对象中的标准属性。
iii. 示例: 使用新HTML DOM简化版属性实现和旧版核心DOM 相同的功能
1_attribute2.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
</head>
<body>
<a id="a1" href="http://tmooc.cn" title="欢迎访问tmooc">go to tmooc</a>
<script>
var a1 = document.getElementById("a1");
//想获得a1的href属性值
console.log(a1.href);
//修改a1的title属性值
a1.title = "Welcome tmooc";
//判断a1是否包含target属性
console.log(a1.target !== "");
//移除a1的id属性
a1.id = "";
console.log(a1);
console.dir(a1);
</script>
</body>
</html>
运行结果:
iv. 问题: HTML中有class属性来定义元素的样式类,而巧了,js中也有class关键字定义一种类型。两个class冲突了!
解决: DOM妥协了!从此修改元素的class属性,都必须更名为className。反之,修改className,就等效于修改元素的class属性。
v. 示例: 下拉菜单 手风琴效果
1_menu.html
<!DOCTYPE html>
<html>
<head>
<title>1. 实现伸缩二级菜单</title>
<meta charset="utf-8" />
<style>
li {
list-style: none;
}
li span {
padding-left: 20px;
cursor: pointer;
background: url("images/add.png") no-repeat center left;
}
li ul {
display: none;
}
.open {
background: url("images/minus.png") no-repeat center left;
}
.open + ul {
display: block;
}
</style>
</head>
<body>
<ul class="tree">
<li>
<span class="open">考勤管理</span>
<ul>
<li>日常考勤</li>
<li>请假申请</li>
<li>加班/出差</li>
</ul>
</li>
<li>
<span>信息中心</span>
<ul>
<li>通知公告</li>
<li>公司新闻</li>
<li>规章制度</li>
</ul>
</li>
<li>
<span>协同办公</span>
<ul>
<li>公文流转</li>
<li>文件中心</li>
<li>内部邮件</li>
<li>即时通信</li>
<li>短信提醒</li>
</ul>
</li>
</ul>
<script>
//DOM 4步
//1. 查找触发事件的元素
//本例中: 查找所有li下的span
var spans = document.querySelectorAll("li>span");
//2. 绑定事件处理函数
//本例中: 遍历找到的每个span,为每个span绑定单击事件
for (var span of spans) {
span.onclick = function () {
//3. 查找要修改的元素
//4. 修改元素
//本例中:
//如果当前span自己是开着的
//其实就是看当前span的class属性值是不是open
// if(this.getAttribute("class")=="open"){
if (this.className == "open") {
//只要把自己关上即可!不用管别的span
//其实就是清除当前span的class属性值
// this.setAttribute("class","")
this.className = "";
} else {
//否则如果当前span不是开着的
//先遍历所有span,清除每个span的class
for (var span of spans) {
// span.setAttribute("class","");
span.className = "";
}
//再只给当前单击的span自己加class open
// this.setAttribute("class","open");
this.className = "open";
}
};
}
</script>
</body>
</html>
运行结果:
(2). bool类型的HTML标准属性
a. 什么是bool类型的HTML标准属性: 在HTML标准属性中,有一类属性只要放在元素上,即使不提供=属性值,也能发挥作用!
b. 比如: <input type="button" disabled>
<input type="radio" checked>
c. 问题: 因为这种属性没有=属性值,所以不能用旧的核心DOM4个函数来操作。
d. 解决: 今后只要访问bool类型的HTML标准属性,都只能用HTML DOM打.访问。比如: 元素.disabled 元素.checked。且属性值必须是bool类型的true或false。
e. 补: css中其实已经提供了一套伪类选择器,专门选择处于某种状态的元素!——状态伪类,包括:
1) :checked —— 专门选择被选中的元素
2) :disabled —— 专门选择被禁用的元素
... ...
f. 示例: 全选 取消全选
2_selectAll.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title>全选和取消全选</title>
</head>
<body>
<h2>管理员列表</h2>
<table border="1px" width="500px">
<thead>
<tr>
<th><input type="checkbox" />全选</th>
<th>管理员ID</th>
<th>姓名</th>
<th>操作</th>
</tr>
</thead>
<tbody>
<tr>
<td><input type="checkbox" /></td>
<td>1</td>
<td>Tester</td>
<td>修改 删除</td>
</tr>
<tr>
<td><input type="checkbox" /></td>
<td>2</td>
<td>Manager</td>
<td>修改 删除</td>
</tr>
<tr>
<td><input type="checkbox" /></td>
<td>3</td>
<td>Analyst</td>
<td>修改 删除</td>
</tr>
<tr>
<td><input type="checkbox" /></td>
<td>4</td>
<td>Admin</td>
<td>修改 删除</td>
</tr>
</tbody>
</table>
<script>
/*点上方的全选,控制下方的所有checkbox*/
//DOM 4步
//1. 查找触发事件的元素
//本例中: 查找表头中的input
var inputAll = document.querySelector(
"table>thead input" //复习第二阶段选择器
);
//2. 绑定事件处理函数
inputAll.onclick = function () {
//3. 查找要修改的元素
//本例中: 查找tbody下的所有input
var inputs = document.querySelectorAll("table>tbody input");
//4. 修改元素
//本例中: 让下边每个input的checked状态和当前点击的全选checkbox的checked状态一致
for (var input of inputs) {
input.checked = this.checked;
}
};
/*点下方的每个,都有可能影响上方的全选*/
//DOM 4步
//1. 查找触发事件的元素
//本例中: 查找tbody下所有input
var inputs = document.querySelectorAll("table>tbody input");
//2. 绑定事件处理函数
//本例中: 遍历找到的每个input元素
for (var input of inputs) {
//每遍历一个input,就绑定单击事件
input.onclick = function () {
//3. 查找要修改的元素
//本例中: 无论点下方哪个input,都只可能影响thead中的一个input
var inputAll = document.querySelector("table>thead input");
//4. 修改元素
//尝试查找tbody下未选中的一个input
var unchecked = document.querySelector("tbody input:not(:checked)"); //复习第二阶段选择器
//如果找到未选中的
if (unchecked != null) {
//上方的全选就不选中!
inputAll.checked = false;
} else {
//否则如果没找到未选中的
//上方的全选就选中!
inputAll.checked = true;
}
};
}
</script>
</body>
</html>
运行结果:
(3). 自定义扩展属性
a. 什么是自定义扩展属性: HTML标准中没有规定的,程序员根据自己的需要,自发的添加到元素上的自定义属性。
b. 何时会使用到自定义扩展属性: 2种情况:
1). 自定义扩展属性经常代替id, class, 元素等其他选择器,作为查找触发事件的元素的条件。
i. id选择器的问题: 一次只能找一个元素
ii. 元素选择器的问题: 实现同一种页面效果,完全可能使用不同的元素
比如,想要在页面上实现一种按钮,我们可以有多种元素作为备选,如button、input,想要做的好看一点div、span、a标签等元素都可以,所以我们发现可选的元素选择器不是唯一的,因此,实现同一种页面效果,完全可能使用不同的元素。
这就会影响js的操作,比如使用DOM查找元素,你一开始是按照button标签来查找元素的,后来有人发现使用button做的按钮太难看了,直接换成了a或span标签做按钮,然后按照a或span标签写了很好看的css的样式,但是对方在用a或span替换button做按钮时,如果不知道你写的js是以button元素作为查询条件来写的,这就会导致你的js不能正常执行,如此说来,元素选择器太容易发生变化了,此时,可以使用自定义扩展属性就是一个好的选择。
iii. class选择器的问题: class属性本职工作是为元素添加样式!因为样式经常发生变化,所以class属性也经常变化!
2). 在客户端元素上临时缓存业务所需的数据
c. 如何使用自定义扩展属性: HTML5标准
1). 手工在HTML元素上添加自定义属性:
<元素 data-属性名="属性值"> 注意:属性值可以没有,大部分情况下都会有值
2). js程序中访问自定义扩展属性:
i. 问题: 因为自定义扩展属性不是HTML标准规定的标准属性,所以HTML DOM并没有把自定义扩展属性提前保存到内存中的元素对象上!就无法用.方式快速访问!
ii. 解决: 2种:
① 用回旧核心DOM函数:
元素.getAttribute("data-自定义属性名")
元素.setAttribute("data-自定义属性名","新属性值")
②HTML5标准中提供了简写: HTML5标准用dataset属性将所有data-开头的自定义属性集中保存起来!访问时,可以用"元素.dataset.自定义属性名"访问自定义扩展属性
d. 示例: 使用自定义属性记录按钮的点击次数:
3_data-.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
</head>
<body>
<!--用自定义属性悄悄记录按钮的点击次数-->
<button data-n="0">click me</button>
<script>
//DOM 4步
//1. 查找触发事件的元素
//本例中: 查找带有data-n属性的元素
//复习第二阶段属性选择器
var btn = document.querySelector("[data-n]");
//2. 绑定事件处理函数
btn.onclick = function () {
//3. 查找要修改的元素
//本例中: 不用找,因为就是要修改自己
//4. 修改元素
//4.1 取出当前按钮身上自定义属性data-n的值
var n = parseInt(
//this.getAttribute("data-n")
this.dataset.n
//页面上的一切都是字符串
);
//4.2 数量+1
n++;
//4.3 将新值放回自定义属性中
//this.setAttribute("data-n",n);
this.dataset.n = n;
};
</script>
</body>
</html>
运行结果:
🌱 小常识: 前端中:
1. Attribute: 特指写在HTML代码中元素的开始标签中的HTML属性,比如: <a href="http://tmooc.cn" target="_blank">
2. Property: 特指js程序中对象中保存的可用.访问的属性,比如:
lilei.sname lilei.sage
⬛总结: DOM 5件事: 增删改查+事件绑定:
1. 查找元素: 4种查找方式
2. 修改元素: 3种东西可修改
(1). 修改内容: 3种内容可修改:
a. 获取或修改元素的HTML内容:
1). 元素.innerHTML
2). 获取时: 返回原始HTML内容
3). 修改时: 先将新内容交给浏览器编译,再显示给人看
b. 获取或修改元素的纯文本内容:
1). 元素.textContent
2). 获取时: 返回去掉内嵌标签,将特殊符号翻译为正文后的纯文本
3). 修改时: 不会将新内容交给浏览器编译,而是原样显示给人看
c. 获取或修改表单元素的值:
表单元素.value
(2). 修改属性: 3种
a. 字符串类型的HTML标准属性: 2种:
1). 旧核心DOM: 4个函数
i. 元素.getAttribute("属性名");
ii. 元素.setAttribute("属性名", "属性值")
iii. var bool=元素.hasAttribute("属性名")
iv. 元素.removeAttribute("属性名")
优点: 万能, 缺点: 繁琐
2). 新HTML DOM:
i. 元素.属性名
ii. 元素.属性名="属性值"
iii. 元素.属性名!==""
iv. 元素.属性名=""
优点: 简单, 缺点: 不万能
b. bool类型的HTML标准属性:
1). 不能用旧核心DOM4个函数修改
2). 只能用HTML DOM的"元素.属性名"方式获取或修改,且值为bool类型
c. 自定义扩展属性:
1) HTML中: <元素 data-自定义属性名="属性值">
2). js中: 2种: (不能用.访问)
i. 核心DOM:
var 属性值=元素.getAttribute("data-自定义属性名")
元素.setAttribute("data-自定义属性名","属性值")
ii. HTML5标准: 元素.dataset.自定义属性名
【后文传送门】👉 DOM操作之如何修改元素的样式_03
如果这篇【文章】有帮助到你,希望可以给【青春木鱼】点个赞👍,创作不易,相比官方的陈述,我更喜欢用【通俗易懂】的文笔去讲解每一个知识点,如果有对【前端技术】感兴趣的小可爱,也欢迎关注❤️❤️❤️【青春木鱼】❤️❤️❤️,我将会给你带来巨大的【收获与惊喜】💕💕!