WEB_Day07(DOM中元素节点的选择、属性操作、创建元素的三种方式、节点层级、事件)
DOM中元素节点的选择
所有的选择器都是document对象的方法
根据id获取元素:
在html中 所有的标签都具有id属性,且id属性的值是不能重复的
//id选择器
var div = document.getElementById("d");
console.log(div.nodeName);
根据标签名获取元素:
根据标签名称进行选择,选择得到结果是所有的相同标签的元素,是一个数组
//标签名选择器
var divs = document.getElementsByTagName("div");
for (var i = 0; i < divs.length; i++) {
console.log(divs[i]);
}
根据name获取元素:
//名称选择器
var radios = document.getElementsByName("sex");
for (var i = 0; i < radios.length; i++) {
console.log(radios[i]);
}
根据类名获取元素:
所有元素都具有class属性,class属性是用来绑定样式的,所以不同的元素可以使用相同的样式
//类名选择器
var stys = document.getElementsByClassName("sty");
for (var i = 0; i < stys.length; i++) {
console.log(stys[i]);
}
根据选择器获取元素:
//根据选择器选择元素
var d1 = document.querySelector("#d1");//使用id选择
console.log(d1);
var divClass = document.querySelectorAll(".sty");//使用类名选择
for (var i = 0; i < divClass.length; i++) {
console.log(divClass[i]);
}
var divs = document.querySelectorAll("div");//使用标签名选择
for (var i = 0; i < divs.length; i++) {
console.log(divs[i]);
}
选择器的使用和css一样,#是id,.是类名,标签名直接写标签的名称,name属性在此暂时不用
querySelector和querySelectorAll的使用的区别:
当我们使用的选择器选择到的目标元素是唯一的的时候则使用querySelector。反之,不唯一则使用querySelectorAll
掌握:
- getElementById()
- getElementsByTagName()
了解: - getElementsByName()
- getElementsByClassName()
- querySelector()
- querySelectorAll()
案例:点击按钮切换图片
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
.pic {
width: 300px;
height: 200px;
}
</style>
<script type="text/javascript">
window.onload = function () {
//使用id选择器选择a标签
var btn = document.getElementById("btn");
var flag = true;
//给a标签绑定一个点击事件 点击a执行相应的方法
btn.onclick = function () {
// var src = document.getElementsByClassName("pic")[0].src;//获取img标签的src的属性值
//改变img的src属性的值
// document.getElementsByClassName("pic")[0].src = "imgs/b.jpg";
if (flag) {
document.getElementsByClassName("pic")[0].src = "imgs/a.jpg";
flag = false;
} else {
document.getElementsByClassName("pic")[0].src = "imgs/b.jpg";
flag = true;
}
}
}
</script>
</head>
<body>
<a id="btn" href="javascript:void(0)">切换图片</a>
<div>
<img src="imgs/a.jpg" class="pic" alt="">
</div>
</body>
</html>
属性操作
非表单元素的属性:
href、title、id、src、className(对应class属性)
案例:点击按钮 改变div的背景色
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
div {
width: 200px;
height: 200px;
}
.red {
background-color: red;
}
.green {
background-color: green;
}
</style>
<script type="text/javascript">
window.onload = function () {
document.getElementsByTagName("div")[0].className = "red";
var flag = false;
document.getElementById("clor").onclick = function () {
if (flag) {
document.getElementsByTagName("div")[0].className = "red";
flag = false;
} else {
document.getElementsByTagName("div")[0].className = "green";
flag = true;
}
}
}
</script>
</head>
<body>
<input id="clor" type="button" value="改变背景色">
<div class="red">
</div>
</body>
</html>
点击按钮显示和隐藏div:
var f = false;
document.getElementById("sh").onclick = function () {
if (f) {
document.getElementsByTagName("div")[0].style.display = "block";
document.getElementById("sh").value = "隐藏";
f = false;
} else {
//隐藏div 因为display是style的一个属性 因此style.display
document.getElementsByTagName("div")[0].style.display = "none";
document.getElementById("sh").value = "显示";
f = true;
}
}
美女相册:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
a img {
width: 100px;
height: 70px;
}
.place {
width: 400px;
height: 250px;
}
</style>
<script type="text/javascript">
window.onload = function () {
var as = document.getElementsByTagName("a");
for (var i = 0; i < as.length; i++) {
as[i].onclick = function () {
var title = this.title;
document.getElementById("place").src = title;
}
}
}
</script>
</head>
<body>
<div>
<a href="javascript:void(0)" title="imgs/1.jpg">
<img src="imgs/1-small.jpg" />
</a>
<a href="javascript:void(0)" title="imgs/2.jpg">
<img src="imgs/2-small.jpg" />
</a>
<a href="javascript:void(0)" title="imgs/3.jpg">
<img src="imgs/3-small.jpg" />
</a>
<a href="javascript:void(0)" title="imgs/4.jpg">
<img src="imgs/4-small.jpg" />
</a>
</div>
<div>
<img id="place" class="place" src="imgs/placeholder.png" alt="">
</div>
</body>
</html>
innerHTML和innerText:
window.onload = function () {
var text = document.getElementsByTagName("div");
console.log(text[0].innerHTML);//这是一个<strong>DIV</strong>
console.log(text[0].innerText);//这是一个DIV
}
window.onload = function () {
var text = document.getElementsByTagName("div");
//text[0].innerHTML = "<img src='imgs/a.jpg'/>";
text[0].innerText = "<img src='imgs/a.jpg'/>";
}
innerHTML和innerText 区别:
在获取值的时候:
- InnerHTML:将元素中的所有内容全部原样取出。可以获取文本及其其中所包含的其他的html元素及其内容
- innerText:获取其中的 所有的文本内容 对于html标签不会获取
在设置值的时候:
- InnerHTML:如果赋予的值 包含HTML标签 则将被浏览器解析,显示为html标签的解析之后的内容
- innerText 赋予的值 均被当作文本直接输出
表单元素属性:
- value 用于大部分表单元素的内容获取(option除外)
- type 可以获取input标签的类型(输入框或复选框等)
- disabled 禁用属性
- checked 复选框选中属性
- selected 下拉菜单选中属性
案例:
检测用户名是否是3-6位,密码是否是6-8位,如果不满足要求高亮显示文本框
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<script type="text/javascript">
window.onload = function () {
document.getElementById("submit").onclick = function () {
var username = document.getElementById("username").value;
var pwd = document.getElementById("pwd").value;
//检测用户名是否是3-6位,密码是否是6-8位,如果不满足要求高亮显示文本框
if (username.length < 3 || username.length > 6) {
document.getElementById("username").style.backgroundColor = "yellow";
document.getElementById("usernamemsg").innerText = "用户名的长度必须是3-6位"
} else {
document.getElementById("username").style.backgroundColor = "white";
document.getElementById("usernamemsg").innerText = ""
}
if (pwd.length < 6 || pwd.length > 8) {
document.getElementById("pwd").style.backgroundColor = "yellow";
} else {
document.getElementById("pwd").style.backgroundColor = "white"
}
}
}
</script>
</head>
<body>
<form action="javascript:void(0)">
用户名:<input type="text" name="username" id="username"><br /><br />
密码:<input type="password" name="pwd" id="pwd"><br /><br />
<input type="submit" id="submit" value="提交">
</form>
</body>
</html>
全选反选:
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<style>
* {
padding: 0;
margin: 0;
}
.wrap {
width: 300px;
margin: 100px auto 0;
}
table {
border-collapse: collapse;
border-spacing: 0;
border: 1px solid #c0c0c0;
width: 300px;
}
th,
td {
border: 1px solid #d0d0d0;
color: #404060;
padding: 10px;
}
th {
background-color: #09c;
font: bold 16px "微软雅黑";
color: #fff;
}
td {
font: 14px "微软雅黑";
}
tbody tr {
background-color: #f0f0f0;
}
tbody tr:hover {
cursor: pointer;
background-color: #fafafa;
}
</style>
</head>
<body>
<div class="wrap">
<table>
<thead>
<tr>
<th>
<input type="checkbox" id="j_cbAll" />
</th>
<th>商品</th>
<th>价钱</th>
</tr>
</thead>
<tbody id="j_tb">
<tr>
<td>
<input type="checkbox" />
</td>
<td>iPhone8</td>
<td>8000</td>
</tr>
<tr>
<td>
<input type="checkbox" />
</td>
<td>iPad Pro</td>
<td>5000</td>
</tr>
<tr>
<td>
<input type="checkbox" />
</td>
<td>iPad Air</td>
<td>2000</td>
</tr>
<tr>
<td>
<input type="checkbox" />
</td>
<td>Apple Watch</td>
<td>2000</td>
</tr>
</tbody>
</table>
<input type="button" value=" 反 选 " id="btn">
</div>
<script type="text/javascript">
window.onload = function () {
//全选
document.getElementById("j_cbAll").onclick = function () {
var inputs = document.querySelectorAll("#j_tb input");
for (var i = 0; i < inputs.length; i++) {
inputs[i].checked = this.checked;
}
}
//单独选择每一个选择项的时候 对全选的影响
var inputs = document.querySelectorAll("#j_tb input");
for (var i = 0; i < inputs.length; i++) {
inputs[i].onclick = function () {
for (var i = 0; i < inputs.length; i++) {
if (!inputs[i].checked) {
document.getElementById("j_cbAll").checked = false;
break;
} else {
document.getElementById("j_cbAll").checked = true;
}
}
}
}
//反选
document.getElementById("btn").onclick = function () {
var inputs = document.querySelectorAll("#j_tb input");
for (var i = 0; i < inputs.length; i++) {
inputs[i].checked = !inputs[i].checked;
}
for (var i = 0; i < inputs.length; i++) {
if (!inputs[i].checked) {
document.getElementById("j_cbAll").checked = false;
break;
} else {
document.getElementById("j_cbAll").checked = true;
}
}
}
}
</script>
</body>
</html>
自定义属性操作:
- getAttribute() 获取标签行内属性
- setAttribute() 设置标签行内属性
- removeAttribute() 移除标签行内属性
- 与element.属性的区别: 上述三个方法用于获取任意的行内属性。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<script type="text/javascript">
window.onload = function () {
var lis = document.querySelectorAll("#u li");
for (var i = 0; i < lis.length; i++) {
var score = lis[i].getAttribute("score");//获取自定义属性
console.log(score);
//设置属性
lis[i].setAttribute("attr", "attr" + i);
if (i % 2 != 0) {
//移除属性
lis[i].removeAttribute("attr");
}
}
}
</script>
</head>
<body>
<ul id="u">
<li score="90">语文</li>
<li score="80">数学</li>
<li score="85">英语</li>
<li score="99">物理</li>
</ul>
</body>
</html>
样式操作:
- 使用style方式设置的样式显示在标签行内
类名操作:
- 修改标签的className属性相当于直接修改标签的类名
案例:
图片切换二维码案例
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<style>
.nodeSmall {
width: 50px;
height: 50px;
background: url(imgs/bgs.png) no-repeat -159px -51px;
position: fixed;
right: 10px;
top: 40%;
}
.erweima {
position: absolute;
top: 0;
left: -150px;
}
.nodeSmall a {
display: block;
width: 50px;
height: 50px;
}
.hide {
display: none;
}
.show {
display: block;
}
</style>
</head>
<body>
<div class="nodeSmall" id="node_small">
<div class="erweima hide" id="er">
<img src="imgs/456.png" alt="" />
</div>
</div>
<script>
// 鼠标经过显示二维码图片
document.getElementById("node_small").onmouseenter = function () {
document.getElementById("er").className = "erweima show";
}
// 鼠标离开隐藏二维码图片
document.getElementById("node_small").onmouseleave = function () {
document.getElementById("er").className = "hide";
}
</script>
</body>
</html>
列表隔行变色、高亮显示:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
.red {
background-color: red;
}
.green {
background-color: greenyellow;
}
.high {
background-color: gold;
}
</style>
<script type="text/javascript">
window.onload = function () {
var lis = document.getElementsByTagName("li");
for (var i = 0; i < lis.length; i++) {
if (i % 2 == 0) {
lis[i].className = "red";
} else {
lis[i].className = "green";
}
var clas = "";
lis[i].onmouseenter = function () {
clas = this.className;
this.className = "high";
}
lis[i].onmouseleave = function () {
this.className = clas;
}
}
//当鼠标经过的时候 高亮显示 当鼠标离开 恢复到原来的颜色
}
</script>
</head>
<body>
<ul>
<li>貂蝉</li>
<li>西施</li>
<li>杨玉环</li>
<li>王昭君</li>
</ul>
</body>
</html>
创建元素的三种方式
document.write()
document.write(‘新设置的内容<p>标签也可以生成</p>’);
innerHTML
var box = document.getElementById(‘box’); box.innerHTML = ‘新内容<p>新标签</p>’;
document.createElement()
var div = document.createElement(‘div’); document.body.appendChild(div);
性能问题:
- innerHTML方法由于会对字符串进行解析,需要避免在循环内多次使用。
- 可以借助字符串或数组的方式进行替换,再设置给innerHTML
- 优化后与document.createElement性能相近
案例:
根据数据动态创建表格
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
<style>
#box table {
border-collapse: collapse;
}
</style>
</head>
<body>
<div id="box">
</div>
<script>
var bodyData = [
{ name: 'zs', subject: '语文', score: 100 },
{ name: 'ls', subject: '数学', score: 80 },
{ name: 'sdb', subject: '体育', score: 0 },
{ name: 'gw', subject: '英语', score: 59 },
{ name: 'bzr', subject: '数学', score: 50 }
];
// 表头数据
var headData = ['姓名', '科目', '成绩', '操作'];
//创建表格
var table = document.createElement("table");
table.style.border = "1px solid black"
table.width = "500px"
table.height = "500px";
//创建表头
var thead = document.createElement("thead");
var tr = document.createElement("tr");
for (var i = 0; i < headData.length; i++) {
var th = document.createElement("th");
th.innerText = headData[i];
th.style.border = "1px solid black"
tr.append(th);
}
//将表头添加到thead
thead.append(tr);
//将thead添加到表格
table.append(thead);
//创建表体
var tbody = document.createElement("tbody");
for (var i = 0; i < bodyData.length; i++) {
var tr = document.createElement("tr");
for (var key in bodyData[i]) {
//alert(bodyData[i][key]);
var td = document.createElement("td");
td.style.border = "1px solid black"
td.innerText = bodyData[i][key]
tr.append(td);
}
var del = document.createElement("td");
del.innerHTML = "<a href='javascript:void(0)' οnclick='delFun()'>删除</a>"
del.style.border = "1px solid black"
tr.append(del);
tbody.append(tr);
}
table.append(tbody);
document.getElementById("box").append(table);
function delFun(e) {
var con = confirm("您确定要删除吗?");
if (con) {
var deltr = e.parentNode.parentNode;
console.log(deltr)
tbody.removeChild(deltr);
}
};
</script>
</body>
</html>
节点层级
console.log(box.parentNode);//body
console.log(box.childNodes);//text div text 子节点
console.log(box.children);//div 子元素
console.log(box.nextSibling);//文本节点
console.log(box.previousSibling);//文本节点
console.log(box.firstChild);//文本节点
console.log(box.lastChild);//文本节点
注意:
childNodes和children的区别:
- childNodes获取的是子节点,children获取的是子元素
- nextSibling和previousSibling获取的是节点,获取元素对应的属性是nextElementSibling和previousElementSibling获取的是元素
- nextElementSibling和previousElementSibling有兼容性问题,IE9以后才支持
事件
事件的注册方式:
<script type="text/javascript">
window.onload = function () {
var box = document.getElementById('box');
//方式一
box.onclick = function () {
alert("aaa");
}
// 方式二: click 表示事件类型 show事件对应的函数
box.addEventListener("click", show, false);
function show() {
alert("bbb");
}
}
</script>
事件的三个阶段:
- 事件捕获:
何为事件捕获(event capturing)?事件从最不精确的对象开始出发,到最精确的对象。即从window->document->documentElement->body->Dom元素->直到捕获到事件。
- 目标阶段:
当事件不断的传递直到目标节点的时候,最终在目标节点上触发这个事件,就是目标阶段。具体的元素本身 - 事件冒泡:
与事件捕获刚好相反。事件从最确定的事件目标到最不确定的事件目标。
addEventListener(“click”,function,“true”)方法,若第三参数为true,则采用事件捕获。若为false,则采用事件冒泡
当子元素和父元素都绑定了事件的时,当触发子元素的事件的时候,父元素的事件也会被触发,这称为事件冒泡
停止传播:event.stopPropagation()
function show(e) {
e.stopPropagation();
alert("bbb");
}
此时子元素的事件触发时将不再触发父元素的事件了。
事件对象的属性和方法:
- event.type 获取事件类型
- clientX/clientY 所有浏览器都支持,窗口位置
- pageX/pageY IE8以前不支持,页面位置
- event.target || event.srcElement 用于获取触发事件的元素
- event.preventDefault() 取消默认行为
- 事件传播的阻止方法:
在W3C中,使用stopPropagation()方法。
在IE下使用cancelBubble = true方法。
案例:
跟着鼠标移动的图片
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
<style>
img {
width: 100px;
height: 150px;
position: absolute;
}
</style>
<script type="text/javascript">
window.onload = function () {
this.onmousemove = function (e) {
console.log(e.pageX + "--" + e.pageY);
document.getElementById("mouseImg").style.left = e.pageX + "px";
document.getElementById("mouseImg").style.top = e.pageY + "px";
}
}
</script>
</head>
<body>
<img src="imags/1.gif" id="mouseImg">
</body>
</html>
常用的鼠标和键盘事件:
- onmouseup 鼠标按键放开时触发
- onmousedown 鼠标按键按下触发
- onmousemove 鼠标移动触发
- onkeyup 键盘按键按下触发
- onkeydown 键盘按键抬起触发
function print(e) {
console.log(e.key + "--" + e.keyCode)
}