目录
2.三个人机交互的方法:alert()/confirm()(选择提示框)/prompt()
区别:localStorage和sessionStorage的异同
1.DOM
1.什么是DOM
文档对象的模型
运用方法对节点进行增删改查的操作。
html树状图:
2.查找节点
元素节点:标签;属性节点;文本节点。
//查找节点
// 1.通过getElementById来查找节点
// var box = document.getElementById('newId')
console.log(box)
// 2.通过getElementsByClassName,返回的是一个数组对象,数组保存是具有相同类名的节点列表
var box = document.getElementsByClassName('box')
// 3.通过getElementsByTagName,返回的是一个数组对象,数组保存是具有相同元素名的节点列表
var box = document.getElementsByTagName('div')
console.log(box[0])
// 4.h5新增的,通过css的选择器(*)
// 通过querySelector来查找元素,返回匹配的第一个元素,
var box = document.querySelector('.box')
var box = document.querySelector('#newId')
var box = document.querySelector('div')
console.log(box)
// 通过querySelectorAll,返回匹配指定css选择器的所有元素,返回数组(NodeList对象),
var box = document.querySelectorAll('.box')
console.log(box[0])
// 获取body元素
var body = document.body
console.log(body)
// 获取html元素
// documentElement代表文档根节点
var html = document.documentElement
console.log(html)
3.事件三要素
是可以被js检测到的行为。
事件源:事件被触发的对象。
事件类型:如果触发,什么事件。
事件处理程序:通过一个函数赋值的方式完成。
<!-- 事件源 -->
<button>dian</button>
<script>
// 事件类型
var btn = document.querySelector('button')
// 事件源:事件类型=事件处理程序
btn.onclick = function () {
alert('弹窗')
}
</script>
4.改变HTML内容
<div class="box" style="width: 10px;">box</div>
// 改变html内容
var box = document.querySelector('.box')
// 1.修改html文档的内容,通过innerHTML
// innerHTML就是元素中的内容,可以识别标签(*最常用)
box.innerHTML = '<p>xx</p>'
console.log(box)
// 2.innerText,不可以
box.innerText = 'aa'
console.log(box.innerHTML)
// 改变属性的值
console.log(box.className)
box.className = 'newBox'
console.log(box)
// 改变HTML的样式
box.style.width = '100px'
box.style.height = '100px'
box.style.border = '1px solid pink'
// css采取驼峰命名法
box.style.fontSize = '19px'
5.获取,设置,删除节点属性
<img src="./tutu.jpg" alt="" index="0">
<script>
// 获取节点属性
var img = document.querySelector('img')
// 法1.直接使用属性获取值,并且改变值,不可以获取自定义属性的值
img.src = './car.jpg'
console.log(img.src)
// undefined
console.log(img.index)
// 法2.通过getAttribute获取属性的值
console.log(img.getAttribute('src'))
// 0
console.log(img.getAttribute('index'))
// 设置节点的属性
// 通过setAttribute,添加属性,如果该元素中语句有了这个
img.setAttribute('index', '2')
console.log(img)
// 删除节点的属性
img.removeAttribute('index')
console.log(img)
</script>
图片切换案例
<!-- 大图片显示区域 -->
<div class="box"></div>
<!-- 小图片 -->
<ul>
<li><img src="./tutu0.jpg" alt=""></li>
<li><img src="./tutu1.jpg" alt=""></li>
<li><img src="./tutu2.jpg" alt=""></li>
<li><img src="./tutu3.jpg" alt=""></li>
</ul>
// 图片切换
var box = document.querySelector('.box')
var lis = document.querySelectorAll('li')
for (var i = 0; i < lis.length; i++) {
// 设置自定义属性
lis[i].setAttribute('index', i)
lis[i].onclick = function () {
// TypeError: Cannot read properties of undefined (reading 'getAttribute')at lis.<computed>.onclick
// console.log(lis[i].getAttribute('index'))
// console.log(this.getAttribute('index'))
// this指向谁调用了这个事件,指向谁
var index = this.getAttribute('index')
box.style.background = `url(./tutu${index}.jpg) no-repeat`
box.style.backgroundSize = '100% 100%'
}
}
console.log(lis)
启用禁用input
<input type="text" name="" id="">
<button>禁用</button>
<button>启用</button>
// 1.给定两个按钮一个表单,一个定义表单元素的禁用,一个启用
// 获取每个元素
var input = document.querySelector('input')
var btns = document.querySelectorAll('button')
// 写点击事件
btns[0].onclick = function () {
input.setAttribute('disabled', true)
}
btns[1].onclick = function () {
// input.setAttribute('disabled', false)不能启用
// 需要将disabled删除
input.removeAttribute('disabled')
}
全选,取消全选,反选案例
<button>全选</button>
<button>取消全选</button>
<button>反选</button><br>
爱好:
<label>
xx:
<input type="checkbox">
</label>
<label>
zz:
<input type="checkbox">
</label><label>
yy:
<input type="checkbox">
</label><label>
aa:
<input type="checkbox">
</label>
// 多选框的全选和反选
var btns = document.querySelectorAll('button')
var inputs = document.querySelectorAll('input')
console.log(btns)
console.log(inputs)
// 全选
btns[0].onclick = function () {
for (var i = 0; i < inputs.length; i++) {
inputs[i].checked = 'checked'
}
}
// 取消全选
btns[1].onclick = function () {
for (var i = 0; i < inputs.length; i++) {
inputs[i].checked = ''
}
}
// 反选
btns[2].onclick = function () {
for (var i = 0; i < inputs.length; i++) {
if (inputs[i].checked == true) {
inputs[i].checked = false
} else {
inputs[i].checked = true
}
}
}
2.DOM节点
1.dom节点
元素节点;
属性节点;
文本节点;
nodeType:
表示节点类型。
1->元素;2->属性;3->文本
nodeName:
取决于节点类型。
元素名称->元素;属性名称->属性;#text->文本
nodeValue:
取决于节点类型。
null->元素;属性值->属性;文本内容->文本
<div class="box">box</div>
<script>
var box = document.querySelector('.box')
console.log(box.nodeType)
console.log(box.nodeName)
console.log(box.nodeValue)
</script>
层次节点的属性
<div class="box">
<p class="p" id="newId">p1</p>
<p>p2</p>
box
</div>
<script>
var box = document.querySelector('.box')
var p = document.querySelectorAll('p')
// 获取当前元素的所有子节点,空白也算一个文本节点,所以这里一个是[1]
console.log(box.childNodes)
// innerHTML与nodeValue的区别
// 1.取值:innerHTML不能通过这个属性来输出!文本节点!中的内容,必须在获取!元素节点!的时候,才可以输出里面包含的内容
// p1不是文本节点的内容,是一个元素;而box是文本节点内容。
console.log(box.childNodes[1].innerHTML)//p1
console.log(box.childNodes[4].innerHTML)//undefined
console.log(box.childNodes[4].nodeValue)//box
// 2.赋值,innerHTML不可以对文本节点进行赋值
// box.childNodes[4].innerHTML = 'xx'->修改失败
box.childNodes[4].nodeValue = 'xx'
console.log(box)//修改成功
// 获取第一个元素(第一个是空格->文本)
console.log(box.firstChild)
console.log(box.childNodes[0])
// 获取最后一个元素
console.log(box.lastChild)
console.log(box.childNodes[box.childNodes.length - 1])
// 获取当前节点的父节点(父节点的所有内容,包括里面的内容)
console.log(p[0].parentNode)
// 获取当前节点的上一个节点
console.log(p[0].previousSibling)
// 获取当前节点的下一个节点
console.log(p[0].nextSibling)
// 获取该节点属性的集合,返回的是一个对象
console.log(p[0].attributes)
//获取第一个元素的节点,不包含文本节点(空格等)
console.log(box.firstElementChild)
// 获取最后一个元素的节点,不包含文本节点(空格等)
console.log(box.lastElementChild)
</script>
2.节点操作
<div class="box">
<p class="p" id="newId">p1</p>
<p>p2</p>
box
</div>
<script>
var box = document.querySelector('.box')
var p = document.querySelector('p')
//可以把任意字符添加到文档中
document.write('nn')
// 创建元素节点
var div = document.createElement('div')
div.innerHTML = '新增的标签'
// 将新的节点添加到子节点的尾部
// box.appendChild(div)
// 创建文本节点
var text = document.createTextNode('新的文本内容')
// 添加到body中
// document.body.appendChild(text)
// 添加到box标签尾部
box.appendChild(text)
// 将新节点添加到目标节点之前,两个参数,第一个:要添加的新节点;第二个:目标节点;里面的值不需要加引号
// p写在div前面
// box.insertBefore(div, p)
// 将新节点替换目标节点
var newP = box.replaceChild(div, p)
console.log(newP)
// 删除子节点
box.removeChild(div)
// 复制节点
// true:那么就是深克隆,它本身节点以及全部的子节点都会被复制
// false:浅克隆,只复制本身节点
// var newBox = box.cloneNode(true)
var newBox = box.cloneNode(false)
console.log(newBox)
</script>
tab切换案例
<ul>
<li>1</li>
<li>2</li>
<li>3</li>
<li>4</li>
</ul>
<div class="box">
<p>我是一号</p>
<p>我是二号</p>
<p>我是三号</p>
<p>我是四号</p>
</div>
<script>
//tab切换
var lis=document.querySelectorAll('li');
var box=document.querySelector('.box');
var p=document.querySelectorAll('p');
//遍历
for(var i=0;i<lis.length;i++){
//自定义属性,给点击对象添加
lis[i].setAttribute('index',i);
//点击事件
lis[i].onclick=function(){
//在每次进行点击时,都先将其他的li的样式清除
for(var i=0;i<lis.length;i++){
lis[i].className='';
}
this.className='items';
var index=this.getAttribute('index');
console.log(index);
//在显示本身之前,将其他的P标签的内容清除
for(var i=0;i<p.length;i++){
p[i].style.display='none';
}
p[index].style.display='block';
}
}
</script>
3.表单操作
<table border="1" width="100px">
<caption>个人表</caption>
<thead>
<tr>
<td>姓名</td>
<td>年龄</td>
</tr>
</thead>
<tbody>
<tr>
<td>xx</td>
<td>11</td>
</tr>
<tr>
<td>ww</td>
<td>11</td>
</tr>
</tbody>
</table>
// 不需要向这个一样,还需要获取节点
var trs = document.querySelectorAll('tr')
console.log(trs)//NodeList(3) [tr, tr, tr]
// table的方法
var table = document.querySelector('table')
// 获取表格的行数,返回的是集合,数组。
console.log(table.rows)//HTMLCollection(3) [tr, tr, tr]
console.log(table.rows.length)
console.log(table.rows[0])
// 获取表格的单元格的数量
console.log(table.rows[0].cells[0])
// 获取表格的单元格的内容(第一行的第一个单元格的内容)
console.log(table.rows[0].cells[0].innerHTML)
// 也可以修改
table.rows[0].cells[0].innerHTML = '秘密'
//head表头,tbody表格的主体
var table = document.querySelector('table')
// 获取表格中的表头
console.log(table.tHead)
// 获取表格中的主体,返回是一个集合,数组
console.log(table.tBodies)
// 获取表格标题
console.log(table.caption.innerHTML)
// 创建表格标题,注意表格标题不是写在括号里,不需要appendChild
var caption = table.createCaption()
caption.innerHTML = '个人信息表'
// 删除标题,表头,表尾,行,单元格
table.deleteCaption()//删除标题
table.deleteTHead()//删除表头
table.tBodies[0].deleteRow(0)//删除行
table.tBodies[0].rows[0].deleteCell(1)//删除对应行中的单元格
创建表格
//通过DOM创建一个表格
// 创建一个table
var table = document.createElement('table')
table.border = 1
// table.width = 300都可以
table.width = '300px'
// 创建标题
table.createCaption().innerHTML = '个人表'
// 创建表头
var thead = table.createTHead()
// 添加行
var tr1 = thead.insertRow(0)
// 添加单元格
var td1 = tr1.insertCell(0)
var td2 = tr1.insertCell(1)
//添加内容
td1.innerHTML = '姓名'
td2.innerHTML = '年龄'
// 创建表格的主体
var tBodies = table.createTBody()
// 创建行
var tr2 = tBodies.insertRow(0)
var tr3 = tBodies.insertRow(1)
// 创建单元格
var td3 = tr2.insertCell(0)
var td4 = tr2.insertCell(1)
var td5 = tr3.insertCell(0)
var td6 = tr3.insertCell(1)
td3.innerHTML = 'xx'
td4.innerHTML = 22
td5.innerHTML = 'xx'
td6.innerHTML = 22
document.body.appendChild(table)
4.元素大小
.box {
width: 200px;
height: 200px;
border: 1px solid pink;
margin: 20px;
padding: 10px;
overflow: scroll;
}
<div class="box">
我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx我是boxx
</div>
var box = document.querySelector('.box')
// 获取元素可视区的宽高
// 内边距和滚动条会影响大小,
console.log(box.clientWidth)
console.log(box.clientHeight)
// 获取滚动内容大小
console.log(box.scrollWidth)
console.log(box.scrollHeight)
// 获取元素的实际的大小(内容+边框+内边距)
console.log(box.offsetWidth)
console.log(box.offsetHeight)
5.周边大小
.box {
width: 200px;
height: 200px;
border: 1px solid pink;
margin: 20px;
padding: 10px;
overflow: scroll;
}
// 周边大小
// 获取元素周边大小
var box = document.querySelector('.box')
// 获取元素左边框和上边框的大小
console.log(box.clientLeft)
console.log(box.clientTop)
// 获取当前元素相对于父元素的位置的距离.如果没有父元素,以body为基准
// 注意:浏览器有自己设置的8px的差距
console.log(box.offsetLeft)
console.log(box.offsetTop)
// 获取滚动条离顶部或者左端的距离
console.log(box.scrollTop)
滚动事件
.box {
width: 200px;
height: 1200px;
border: 1px solid pink;
margin: 20px;
padding: 10px;
overflow: scroll;
}
// 滚动事件
// 小范围
box.onscroll = function () {
var scrollTop = box.scrollTop
console.log(scrollTop)
}
// 持续获取窗口滚动高度的方式:
// 整个页面
window.onscroll = function () {
// 在整个页面html根元素document.documentElement
var scrollTop = document.documentElement.scrollTop || document.body.scrollTop || window.pageYOffset
// 除了HTML还有body,pageYOffset(返回文档在窗口垂直方向滚动的像素)
console.log(scrollTop)
}
点击返回顶部案例
.box {
width: 100%;
height: 1500px;
border: 1px solid red;
}
.btn {
width: 50px;
height: 50px;
border: 5px solid skyblue;
border-radius: 50%;
text-align: center;
line-height: 25px;
position: fixed;
bottom: 120px;
right: 50px;
/* 隐藏 */
display: none;
}
<div class="box">内容</div>
<div class="btn">返回顶部</div>
<script>
// 1.返回顶部
// 要求:一开始不出现返回顶部的按钮
// 当滚动条滚到一定的位置,出现该按钮
// 点击,返回顶部,并且按钮消失
var btn = document.querySelector('.btn')
// 滚动事件
window.onscroll = function () {
//获取文档的滚动距离顶部的高度
var scrollTop = document.documentElement.scrollTop || document.body.scrollTop || window.pageYOffset
console.log(scrollTop)
//如果滚动的高度大于700,则出现返回顶部按钮
if (scrollTop > 700) {
btn.style.display = 'block'
}
}
// 点击事件
btn.onclick = function () {
//当点击按钮之后,让滚动的高度变为0,那么滚动条就会返回最顶端
document.documentElement.scrollTop = 0
//点击完按钮之后将按钮消失
btn.style.display = 'none'
}
</script>
6.注册事件
给元素添加事件:
- 传统注册方式 .onclick = function () {}
- 方法监听注册方式 .addEventListener('click', function () {} (ie9)
<button>传统注册方式</button>
<button>方法监听注册方式</button>
var btns = document.querySelectorAll('button')
// 注册事件
// 传统注册方式
// 同一个元素同一个事件,只能设置一个处理函数,最后注册的处理函数就会覆盖前面的组测的处理函数
btns[0].onclick = function () {
alert('传统注册方式')
}
btns[0].onclick = function () {
alert('2')
}
// 方法监听注册方式
// 第一个参数写事件类型,不需要添加on
// 同一个元素同一个事件可以注册多个监听器,会按照注册的顺序依次执行
btns[1].addEventListener('click', function () {
alert('方法监听注册方式')
})
btns[1].addEventListener('click', function () {
alert('2')
})
7.删除事件
- 传统事件删除事件 btns[0].onclick = null
- 删除事件(删除事件):removeEventListener第一个参数是事件;第二个参数是处理程序(如果要进行解绑事件的话,第二个参数不要写匿名函数,不要加括号)。btns[1].removeEventListener('click', fun1)
var btns = document.querySelectorAll('button')
// 注册事件
// 传统注册方式
// 同一个元素同一个事件,只能设置一个处理函数,最后注册的处理函数就会覆盖前面的组测的处理函数
btns[0].onclick = function () {
alert('传统注册方式')
}
btns[0].onclick = function () {
alert('2')
// 点击完后,删除onclick(点击第一次显示2,第二次及之后都不再显示2)
// 传统事件删除事件
btns[0].onclick = null
}
// 方法监听注册方式
// 第一个参数写事件类型,不需要添加on
// 同一个元素同一个事件可以注册多个监听器,会按照注册的顺序依次执行
btns[1].addEventListener('click', function fun1 () {
alert('方法监听注册方式')
// 删除事件(删除事件):removeEventListener第一个参数是事件;第二个参数是处理程序(如果要进行解绑事件的话,第二个参数不要写匿名函数,不要加括号)。
btns[1].removeEventListener('click', fun1)
})
btns[1].addEventListener('click', fun2)
function fun2 () {
alert('2')
btns[1].removeEventListener('click', fun2)
}
8.this关键字
谁调用了,就指向谁
<button>this</button>
<script>
// this关键字
// 1.如果一般函数,this指向全局对象window
var uname = 'zz'
function fun1 () {
var uname = 'wo'
console.log(this.uname)//zz
}
// fun1();window一般会省略掉
window.fun1()
// 2.对象的方法调用,this指向调用该方法的对象
var btn = document.querySelector('button')
btn.onclick = function () {
// alert(this.value)拿不到
alert(this.innerHTML)//this
}
// 3.构造函数里的this,指向创建出来的实例对象
function Person (name, age) {
this.name = name
this.age = age
}
var a = new Person('zz', 11)
var b = new Person('wo', 20)
console.log(a, b)
9.事件对象
当触发某个事件的时候,会产生一个事件对象,系统给我们自己创建的
<button>事件对象</button>
<script>
// 事件对象event
// 包含者所有与事件对象有关的信息,返回的一系列的相关数据的集合,对象
var btn = document.querySelector('button')
btn.addEventListener('click', function (event) {
console.log(event)
})
</script>
10.鼠标事件
// 鼠标事件
var btn = document.querySelector('button')
// 点击事件:click
// 鼠标左键被按下:mousedown
btn.addEventListener('mousedown', function () {
console.log('按下')
})
// 鼠标左键被松开:mouseup
btn.addEventListener('mouseup', function () {
console.log('松开')
})
// 鼠标在元素上移动:mousemove
btn.addEventListener('mousemove', function () {
console.log('放在上面移动')
})
// 鼠标移动某个元素的上面:mouseover
btn.addEventListener('mouseover', function () {
console.log('移上来了')
})
// 鼠标溢出某个元素的上面:mouseout
btn.addEventListener('mouseout', function () {
console.log('移走了')
})
11.可视区和屏幕的坐标
// 可视化和屏幕的坐标
document.addEventListener('click', function (e) {
console.log(e)
// 可视区和屏幕的坐标,圆点就是浏览器的左上角
console.log(e.clientX)
console.log(e.clientY)
// 页面的坐标,圆点就是页面的左上角
console.log(e.pageX)
console.log(e.pageY)
// 电脑屏幕的坐标,圆点就是屏幕的左上角(整个电脑的坐标)
console.log(e.screenX)
console.log(e.screenY)
})
12.键盘事件
// 键盘事件
// 某个按键被按下:keydown,不会区别大小写
document.addEventListener('keydown', function (e) {
console.log('被按下了')
console.log(e)
// key有兼容性问题
console.log('down', e.key)
console.log('down', e.keyCode)//e显示大写: 69
})
// 某个按键被弹起:keyup
document.addEventListener('keyup', function () {
console.log('被弹起了')
})
// 某个按键在被按下和松开的某个时刻:keypress,在keydown之后执行
// 可以识别大小写
document.addEventListener('keypress', function (e) {
console.log('被press按下了')
console.log('press', e.key)
console.log('press', e.keyCode)//e显示大写:101
})
13.表单事件
1.onblur
元素失去焦点
2.onfocus
元素获得焦点
3.onchange
(表单)域的内容被改变(不一定是表单)
4.onreset
重置按钮被点击
5.onsubmit
提交按钮被点击
<form action="" class="form">
<input type="text" class="input" />
<input type="reset" value="重置">
<input type="submit" value="提交">
</form>
// 表单事件
var form = document.querySelector('.form')
var input = document.querySelector('.input')
//失去焦点
input.addEventListener('blur', function () {
input.className = 'ipt'
})
// 获取焦点
input.addEventListener('focus', function () {
input.className = 'ipt1'
})
// 域(表单域)的内容发生改变
form.addEventListener('change', function () {
alert('内容发生改变了')
})
// 重置按钮被点击
form.addEventListener('reset', function () {
alert('重置成功')
})
// 提交按钮被点击
form.addEventListener('submit', function () {
alert('提交成功')
})
.ipt {
background-color: skyblue;
}
.ipt1 {
background-color: brown;
}
14.事件流
是从页面中接收事件的顺序。(事件流三个阶段:捕获阶段,当前目标阶段,冒泡阶段)
js中只可以执行捕获或者冒泡阶段其中一个
传统注册事件只能拿到冒泡阶段,所以只能使用方法监听注册方式。
第三个参数:布尔值,如果是true捕获阶段,false冒泡阶段。默认不写为冒泡阶段。
<div class="box">
父元素
<div class="one">子元素</div>
</div>
事件捕获阶段:
var one = document.querySelector('.one')
var box = document.querySelector('.box')
one.addEventListener('click', function () {
alert('子元素')
}, true)
box.addEventListener('click', function () {
alert('父元素')
}, true)
// 事件捕获阶段
// 点击子元素:先弹出父元素,再弹出子元素
// 点击父元素:弹出父元素(因为它已经到了当前目标阶段)
事件冒泡阶段
one.addEventListener('click', function () {
alert('子元素')
}, false)
box.addEventListener('click', function () {
alert('父元素')
}, false)
// 事件冒泡阶段
// 点击子元素:先弹出子元素,再弹出父元素
// 点击父元素:弹出父元素
15.事件对象的常见属性和方法
1.e.target
返回触发事件的对象(元素)。
<div class="box">box
<div class="one">子元素</div>
</div>
target和this的区别(*)
var box = document.querySelector('.box')
var one = document.querySelector('.one')
one.addEventListener('click', function (e) {
// 返回触发事件的对象
console.log(e.target)//点击子元素:返回子元素
console.log(this)//点击子元素:返回子元素
// 返回事件类型
console.log(e)
})
box.addEventListener('click', function (e) {
// target和this的区别(*)
// target返回的是触发事件的对象(元素)
// this返回的是绑定事件的对象(元素)
console.log(e.target)//点击子元素:返回子元素
console.log(this)//点击子元素:返回父元素(包括里面的子元素)
})
2.e.type
返回事件的类型
3.e.preventDefault( )
阻止默认事件
<!-- 只要包裹了a标签,就会跳转到href的指定页面(默认行为) -->
<a href="https://www.oschina.net/">OSCHINA</a>
var a = document.querySelector('a')
// 阻止默认事件
a.addEventListener('click', function (e) {
e.preventDefault()
})
4.e.stopPropagation( )
阻止冒泡事件
var one = document.querySelector('.one')
var box = document.querySelector('.box')
one.addEventListener('click', function (e) {
alert('子元素')
// 阻止冒泡事件
e.stopPropagation()
}, false)
box.addEventListener('click', function () {
alert('父元素')
}, false)
16.事件委托(事件代理)
原理:不需要给每个子节点去设置事件监听器,而是把监听器设置在其父节点上面,然后利用冒泡原理影响每一个子节点。
作用:只需要操作一次DOM,提高程序的性能。
案例:写一个导航栏,用事件委托的方式,每次点击里面的每个项目都会弹出一个对话框,并且当前项目的颜色改变
* {
margin: 0;
padding: 0;
}
ul {
list-style: none;
margin-top: 100px;
margin-left: 100px;
}
li {
width: 100px;
height: 50px;
border: 1px solid pink;
}
<ul>
<li>1</li>
<li>2</li>
<li>3</li>
<li>4</li>
<li>5</li>
</ul>
法一:
var ul = document.querySelector('ul')
var lis = document.querySelectorAll('li')
ul.addEventListener('click', function (e) {
// alert('ul')
console.log(e.target)
for (var i = 0; i < lis.length; i++) {
lis[i].style.backgroundColor = ''
}
e.target.style.backgroundColor = 'red'
})
法二:
.a {
/* 设置为透明色,不要设置为空 */
background-color: transparent;
}
.b {
background-color: red;
}
var ul = document.querySelector('ul')
var lis = document.querySelectorAll('li')
//写一个ul,利用冒泡到li去
ul.addEventListener('click', function (e) {
// alert('ul')
console.log(e.target)
for (var i = 0; i < lis.length; i++) {
// lis[i].style.backgroundColor = ''
lis[i].className = 'a'
}
// e.target.style.backgroundColor = 'red'
e.target.className = 'b'
})
总结(*)
1.如何持续获取滚动条的高度:scrollTop,scroll事件
2.this指向:三种情况,记住谁调用了就指向谁
3.事件冒泡和事件捕获
4.阻止事件冒泡和阻止默认事件
5.target和this区别
6.innerHTML和nodeValue的区别
innerHTML读取或设置节点的html内容,不适用读取文本节点的内容;nodeValue读取或设置指定节点的文本内容,适用于文本类型的节点。
7.为html页面上的一个元素添加一个点击事件,有几种方法(三种)
οnclick="";js中函数赋值;方法监听事件
8.DOM操作中,如何获取属性的值?
元素.属性名(不可以获取自定义属性);getAttribute(可以获取自定义属性)
BOM
1.BOM定义
可以使我们通过js去操作浏览器。
提供了一组对象,用来完成浏览器的操作。
2.常见的BOM对象
window:
代表整个浏览器的窗口,BOM中一个顶级对象,也是网页全局对象。
1.特殊属性:name
//window对象
//有一个特殊的属性 name
//var uname = 'zz'
// 注释后,name还是等于zz,只有退出页面,重新打开后,才会变成空
console.log(window)
2.三个人机交互的方法:alert()/confirm()(选择提示框)/prompt()
显示对话框时,js代码停止执行,只有当对话框关闭之后,js代码才会执行,不建议在实战中使用这三种
// confirm(),选择器提示框
var str = confirm('zho')
console.log(str)//true:确定;false:取消
if (str) {
console.log('点击确定true')
} else {
console.log('点击取消false')
}
3.常见的事件
onload:页面加载事件
当文档内容完全加载完之后,就会触发这个事件
注意:如果使用传统注册方式,只能可以设置一个onload事件,以最后一个为基准,如果想要设置多个,那么用方法监听方式
// onload事件
// 整个页面都加载完,才执行这个代码
!!传统!!
// 以最后的为基准
window.onload = function () {
var btns = document.querySelectorAll('button')
btns[0].onclick = function () {
alert('zz')
}
}
window.onload = function () {
var btns = document.querySelectorAll('button')
btns[1].onclick = function () {
alert('hi')
}
}
!!方法监听方式!!
window.onload = function () {
var btns = document.querySelectorAll('button')
btns[0].addEventListener('click', fun1)
function fun1 () {
alert('zz')
}
btns[1].addEventListener('click', fun2)
function fun2 () {
alert('hi')
}
}
</script>
<button>点击</button>
<button>点击1</button>
onresize:窗口大小加载事件
只要浏览器窗口发生了改变,就会触发事件;一般时放在响应式事件中使用
outerHeight:整个浏览器的高度
outerWidth:整个浏览器的宽度
<span></span>
<span></span>
window.onresize = function () {
console.log('窗口发生改变')
// 浏览器的宽度
var x = window.outerWidth
// 浏览器的高度
var y = window.outerHeight
// 持续获取宽度和高度
var span = document.querySelectorAll('span')
span[0].innerHTML = '浏览器宽度' + x + 'px'
span[1].innerHTML = '浏览器高度' + y + 'px'
}
onscroll:滚动事件
当页面出现滚动条,并且滚动了,才会触发此事件
.box {
width: 100%;
height: 1500px;
}
<div class="box"></div>
window.onscroll = function () {
console.log('滚动了')
var scrollTop = document.documentElement.scrollTop || document.body.scrollTop || window.pageYOffset
console.log(scrollTop)
}
4.打开和关闭窗口
打开:open(),四个参数都是可选的
第一个参数:URL:声明新窗口中显示网页文档的URL
第二个参数:name:声明新窗口的名称;如果指定了已经存在的窗口,open()方法,不会新创建一个窗口,返回对窗口的引用,第三个参数会被省略
第三个参数:声明新窗口的特征以及具体说明
第四个参数:可选布尔值
如果没有一个参数,那么就会弹出一个新窗口(没有标题,没有内容)
var btns = document.querySelectorAll('button')
// open()
btns[0].addEventListener('click', function () {
// 定义的是全局的窗口,在其他作用域下可以拿到
myWindow = window.open('./48.打开和关闭.html', './48.打开和关闭.html', 'width=300px,height=300px')
})
关闭:close()
关闭一个窗口
window的属性,closed,可以检测当前窗口是否关闭
<button>打开</button>
<button>关闭</button>
<script>
var btns = document.querySelectorAll('button')
// open()
btns[0].addEventListener('click', function () {
//在新窗口赋值给变量myWindow,不需要加var;定义的是全局的窗口,在其他作用域下可以拿到
myWindow = window.open('./48.打开和关闭.html', './48.打开和关闭.html', 'width=300px,height=300px')
})
// close()
// 如果要进行关闭自己设置窗口,赋值
btns[1].addEventListener('click', function () {
// 关闭自己创建的新窗口
myWindow.close()
// 关闭自身的窗口,整个页面的窗口关闭掉
// window.close()
console.log(myWindow.closed)
})
</script>
Navigator:
代表浏览器当前的信息,通过这个对象可以识别不同的浏览器。
// navigator.userAgent检测手机端还是PC端
console.log(window.navigator.userAgent)
if (/Android|webOS|iPhone|iPod|BlackBerry/i.test(navigator.userAgent)) {
console.log('手机端')
} else {
console.log('PC端')
}
Location:
代表浏览器当前的地址信息,通过这个对象可以获取或者设置当前地址信息,操作浏览器跳转页面。
href属性可以获取当前的URL地址,也可以设置href的属性值,进行页面跳转
search属性可以将参数传递给另外一个页面
location.html
<button>跳转</button>
<!-- 输入账号 -->
<form action="./51.search.html">
账号:
<!-- 要写name -->
<input type="text" name="username">
<input type="submit" value="提交">
</form>
// Location
console.log(location)
// 获取当前的URL地址
console.log(location.href)
// 通过设置href属性值进行页面跳转
var btn = document.querySelector('button')
btn.addEventListener('click', function () {
location.href = './48.打开和关闭.html'
})
// search查询->search.html
search.html
console.log(location)
console.log(location.search)
// ?username=zz
var str = location.search.substr(1)
console.log(str)
// // username=zz(属性名=属性值)
console.log(str.split('='))
// // ['username', 'zz']
console.log(str.split('=')[1])
// zz
var str1 = location.search.substr(1).split('=')[1]
alert(`欢迎${str1}`)
reload( ):可以重新装载当前文档,跟href一样
replace( ):可以替换当前文档,不可以回退,不会再去创建新的历史记录。如果是临时页面比较多,那么使用replace,这样临时页面不会存储在历史列表中
History:
代表浏览器的历史信息,出于用户的隐私考虑,这个对象不可以获取到具体的记录或者拿到所有的历史记录,通过这个对象实现上一步/刷新/下一步
回退:让location.html跳转到history去,history回退到location.html
// Location.html
location.href = './52.history.html'
//history.html
// 在历史记录后退
var btn = document.querySelector('button')
btn.addEventListener('click', function () {
window.history.back()
})
前进:location点击跳转,前进到history页面
// 在历史记录中前进
history.forward()
历史记录点
// 移动到指定历史记录点
btn.addEventListener('click', function () {
// 索引值:0->当前页面,1->下一页,-1->上一页,以此类推
window.history.go(-1)
})
Screen:
代表用户的屏幕信息,通过这个对象可以获取到用户显示器的信息
availHeight:可用屏幕的高度
availWidth:可用屏幕的宽度
以上的BOM对象在浏览器中都是作为window对象的属性保存的,都是全局对象
3.本地存储
1.localStorage
永久的把信息存储在客户端的本地
特点:
- 保存的数据是长期存在的,下一次去访问该网站的时候,网页可以直接读取以前保存的数据
- 保存的数据都是以“键值对”的形式存在(Storage {username: 'zz', length: 1})
- 在多个页面可以进行数据共享,但是得在同一个浏览器中
localStorage.html
账号:
<input type="text">
<button>localStorage存储</button>
<script>
// localStorage存储方法,20M
// cookie存储 4k
// 保存数据setItem('数据名',数据值)
var input = document.querySelector('input')
var btn = document.querySelector('button')
btn.addEventListener('click', function () {
var val = input.value
localStorage.setItem('username', val)
})
// 1.获取数据getItem('数据名')
console.log(localStorage.getItem('username'))
// localStorage是一个对象
console.log(localStorage)
// 2.用对象的方式获取数据
console.log(localStorage.username)
console.log(localStorage['username'])
// 删除数据
localStorage.removeItem('username')
</script>
a.html
<script>
console.log(localStorage)
// Storage {username: 'aa', length: 1}
</script>
2.sessionStorage
信息的会话存储
特点:
- 关闭浏览器之后数据就会消失
- 以键值对的形式存在
- 在同一个页面中数据共享
// sessionStorage存储方法,5M
// 保存数据setItem('数据名',数据值)
btns[1].addEventListener('click', function () {
var val = input.value
sessionStorage.setItem('username', val)
sessionStorage.setItem('age', 20)
})
console.log(sessionStorage)
// 获取数据
console.log(sessionStorage.getItem('username'))
// 删除数据
sessionStorage.removeItem('username')
区别:localStorage和sessionStorage的异同
相同点:
1.都保存在浏览器中
2.透明两个都不会自动把数据发给服务器,仅在本地保存
3.只能存储字符串,要想把他们转换为常见的JSON形式,JSON.stringfy( )
不同点:
1.存储大小的限制不同:
sessionStorage:5M
localStorage:20M
2.数据有效期不同:
sessionStorage:仅在当前浏览器窗口关闭前有效,不可能会持久保持
localStorage:始终有效,窗口或浏览器关闭也会一直保存,用作持久数据,除非手动删除
3.作用域不同:
sessionStorage:在不同浏览器窗口不会共享,只有在同一个页面中使用
localStorage:在所有的同源窗口中都是共享的
区别在于localStorage用于持久化存储,除非是手动删除,否则数据永远不会过期;而sessionStorage存储的数据只有在同一个会话中的页面才能访问,并且当会话结束,也随之销毁。
4.定时器
回调函数和普通函数区别:
普通函数是按照代码顺序的执行的;但是回调函数,要等到定义的时间到了或者是你触发事件,才会调用函数
1.setTimeout()
在指定的毫秒数执行完之后再去调用函数或者表达式
- 延时时间单位是毫秒,可以省略,如果省略默认是为0
- 可以给定时器赋值一个标识符,这样就可以使用多个定时器
- 清除定时器clearTimeout(time)
// setTimeout(调用函数(回调函数),延迟时间)
var time = setTimeout(function () {
alert('zz')
}, 2000)//2秒钟之后再去调用函数
alert('hello')
// 清除定时器
clearTimeout(time)
2.setTnterval()
按照指定周期(以毫秒数计数)来调用函数或者表达式,方法会不停调用函数。
清除定时器:clearInterval( )
// setTnterval(调用函数,间隔时间)
var times = setInterval(function () {
console.log('zz')
}, 2000)
// 清除定时器
clearInterval(times)
案例:
<input type="text" placeholder="请输入手机号码">
<button>发送验证码</button>
// 使用定时器,发送验证码,在等待验证码的过程中,按钮不能点击
var input = document.querySelector('input')
var btn = document.querySelector('button')
var num = 10
btn.addEventListener('click', function () {
btn.setAttribute('disabled', true)
var time = setInterval(function () {
// 当num等于0的时候
if (num === 0) {
alert('验证码' + 123344)
// 清除定时器
clearInterval(time)
// 恢复按钮原来的样子
btn.innerHTML = '发送验证码'
btn.removeAttribute('disabled')
// 当时间到了,恢复num为10
num = 10
}
else {
btn.innerHTML = '还剩' + num + '秒'
num--
}
}, 1000)
})
京东秒杀倒计时
span {
display: inline-block;
width: 50px;
height: 50px;
background-color: pink;
color: rgb(74, 63, 119);
font-size: 28px;
font-weight: 600;
text-align: center;
line-height: 50px;
}
<span></span>
<span></span>
<span></span>
// 拿到截止时间
var newDate = new Date('2022-06-25 00:00:00')
// 刷新后会等一秒才会出现时间的问题
getDate()
// 封装获取时间差函数
function getDate () {
// 获取当前时间
var date = new Date()
// 拿到相差的时间
var d = newDate - date
// console.log(d)
// 进行转换
// 转换为小时 d/秒/分钟/小时
var hours = parseInt(d / 1000 / 60 / 60)
// 判断一下数字是否小于10
hours = hours > 9 ? hours : '0' + hours
// console.log(hours)
// 转换为分钟
var minutes = parseInt(d / 1000 / 60 % 60)
minutes = minutes > 9 ? minutes : '0' + minutes
// console.log(minutes)
// 转换为秒
var mili = parseInt(d / 1000 % 60)
mili = mili > 9 ? mili : '0' + mili
// console.log(mili)
// 获取三个span元素
var span = document.querySelectorAll('span')
span[0].innerHTML = hours
span[1].innerHTML = minutes
span[2].innerHTML = mili
if (d == 0) {
clearInterval(time)
}
}
// 让秒钟动起来
// 定时器
var time = setInterval(getDate, 1000)
3.第一个参数不单单只能写回调函数,也可以写函数名
BOM总结:
1.BOM和DOM的区别:
DOM是通过js去操作我们网页的
BOM是通过js去操作浏览器
2.常见BOM对象:
window对象,navigator对象,location对象,history对象,srceen对象
3.本地存储,定时器
(*)
1.如何识别浏览器的类型:
navigator.userAgent
2.如何拆解url部分
通过location,href,search
3.在历史记录中后退有几种方式
history.back();history.go(-1)