节点介绍
节点 node : 网页一切内容皆为节点(DOM树分叉的地方)
节点作用 : 让渲染引擎准确的渲染dom树 (另一种获取元素的方式)
四种节点: 元素节点、 属性节点 、 文本节点 、 注释节点
最重要: 元素节点(标签)
查找节点
获取子节点:元素节点、注释节点、文本节点
元素.childNodes()
属性节点不通过此方法获取,属性节点直接: 元素.属性名
1.获取子元素 :元素节点
元素.children (拿到是是伪数组)(如果没有子元素拿到的是空数组)
//获取父元素
let ul = document.querySelector('ul')
//1.1 获取子节点
console.log( ul.childNodes )//获取 元素节点、文本节点、注释节点
//1.2 获取子元素
console.log( ul.children )// 获取子元素
2.获取兄弟元素
获取上一次元素 :== 元素.previousElementSibling()==
== 方法二: document.querySelector(’#li2-li’)==
获取下一次元素 :== 元素.nextElementSibling==
== 方法二: document.querySelector(’#li2+li’)==
(找不到上一个/下一个兄弟则为null)
//获取父元素
let ul = document.querySelector('ul')
//获取li2
let li2 = document.querySelector('#li2')
//1 获取子元素
console.log( ul.children )//获取 子元素
//2.获取兄弟元素
//2.1 获取上一个元素
console.log( li2.previousElementSibling )//班长1
//2.2 获取下一个元素
console.log( li2.nextElementSibling )//班长3
//点击按钮:修改兄弟元素颜色
document.querySelector('.btn').onclick = function(){
li2.previousElementSibling.style.backgroundColor = 'red'
li2.nextElementSibling.style.backgroundColor = 'red'
}
3.获取父元素
父节点一定是元素,因为只有元素节点才会有儿子
父元素.parentNode
父元素.parentElement(有兼容性问题)
//先获取元素
let li2 = document.querySelector('#li2')
//1.获取父元素
console.log( li2.parentNode )//ul
//2.获取父元素的父元素
console.log( li2.parentNode.parentNode )//body
//3.获取父元素的父元素的父元素
console.log( li2.parentNode.parentNode.parentNode )//html
//4.获取父元素的父元素的父元素的父元素
console.log( li2.parentNode.parentNode.parentNode.parentNode )//document
console.log(li2.parentNode.parentNode.parentNode.parentNode.parentNode )//null
节点操作
1.新增节点
dom新增元素 三种方式
(1) document.write(’’)
开发中几乎不用,可能会覆盖原来的内容
(2) 元素.innerHTML = ‘’
有性能问题,新增100以内的元素的时候可以用
覆盖操作: 元素.innerHTML = ‘标题’
新增操作: 元素.innerHTML += ‘标题’
(3) document.createElement() : dom推荐
document.createElement 用法:三步
①在内存中创建空标签 : document.createElement(‘标签名’)
②设置标签内容
新元素.innerText=’’
③添加到页面dom : 父元素.appendChild(子元素)
新增到最后面与新增到指定位置
① 新增到父元素的最后面:
父元素.appendChild(元素)
② 新增到某个元素前面 :
父元素.insertBefore(要新增的元素,哪一个元素前面)
== li2没拿也能使用是因为li2是id属性,具有唯一性,但是不拿不规范==
③新增到父元素的元素到最前面(新增到原来第一个元素的前面):
父元素.insertBefore(要新增的元素,父元素.children[0])
④元素上移(元素移动到它哥哥的前面)
如果已经是第一个,浏览器会移到最后,所以要判断是否是第一个
判断是否是第一个的方法
判断该元素的哥哥是否存在,存在则布尔值为true,不存在则为null,布尔值为false
⑤元素下移(元素移动到它弟弟的弟弟的前面)
如果已经是最后一个,浏览器会移到最前,所以要判断是否是最后一个
let li2=document.querySelector('#li2')
//1.在内存中创建空标签
let li = document.createElement('li')
//2.设置标签内容
li.innerText = '我是新来的'
li.style.backgroundColor = 'red'
console.log( li )
//3.添加到页面dom树 : 父元素.appendChild(子元素)
//3.1 新增到父元素最后面
// document.querySelector('ul').appendChild(li)
//3.2 新增到元素前面
let ul = document.querySelector('ul')
let li2 = document.querySelector('#li2')
ul.insertBefore(li, li2 )
//3.3新增到父元素的最前面
ul.insertBefore(li, ul.children[0] )
//3.4元素上移
if(li2.previousElementSibling){
ul.insertBefore(li2, li2.previousElementSibling)
}else{
alert('已经是第一个元素了')
//3.5元素下移
if(li2.nextElementSibling){
ul.insertBefore(li2, li2.nextElementSibling.nextElementSibling)
}else{
alert('已经是最后一个元素了')}
2.克隆节点
复制节点
被克隆的元素.cloneNode(true)
(1) 默认false : 浅克隆,只克隆元素自身
(2) true : 深克隆,克隆元素自身 + 所有后代元素
克隆得到的元素要添加到DOM数
//点击按钮 : 克隆box
document.querySelector('.btn').onclick = function () {
//1.获取元素box
let box = document.querySelector('.box')
//2.克隆元素 : 元素.cloneNode()
let newBox = box.cloneNode(true)
console.log(newBox)
//3.将克隆得到的元素新增到dom树
document.body.appendChild(newBox)
}
3.删除节点
父元素.removeChild(子元素)
元素只能删除自己的子元素,只能是爸爸删儿子,爷爷不行
//点击按钮删除li2
document.querySelector('.btn').onclick = function(){
//获取父元素和子元素
let ul = document.querySelector('ul')
let li2 = document.querySelector('#li2')
//删除子元素
ul.removeChild( li2 )
}
微薄发布案例
思路分析:
1.输入框 输入事件 oninput
获取输入框文本长度 赋值给 useCount.innerText
2.点击发布按钮
2.1非空判断:检测输入框有没有内容,有才继续,没有则弹出提示
!!!非空判断重点:如果文本为空,则return结束事件处理
str.trim() :清除字符串前后空格,中间的空格不能删除
2.2给页面新增li元素
(1)创建空标签
(2)设置标签内容
(3)添加到ul
2.3清空输入框 span文本归零
数组随机下标:Math.floor(Math.random()*数组长度)
日期对象
//1.创建日期对象
let d = new Date()
console.log(d)
//2.转换日期格式
console.log(d.toLocaleString()) //2022/1/18 下午3:02:53
console.log(d.toLocaleDateString()) //2022/1/18
console.log(d.toLocaleTimeString()) //下午3:03:29
//3.获取 年月日时分秒
console.log(d.getFullYear()) //2022
//范围下标 0-11 对应 1-12月
console.log(d.getMonth()) //0 下标 第1个月
console.log(d.getDate()) //18
//星期下标 0-6 对应 周日-周六
console.log(d.getDay()) //2 周二
console.log(d.getHours()) //15
console.log(d.getMinutes()) //5
console.log(d.getSeconds()) //44
//4.获取时间戳 : 1970年1月1日0秒 伦敦时间 -> 现在时间总毫秒数
//时间戳作用 : 解决浏览器时区兼容性 UTC时区:全球时区 GMT时区:东8区
console.log(Date.now()) //1642489741950
console.log(+new Date()) //1642489741950
console.log(new Date().getTime()) //1642489741950
定时器
1.定时器作用 : 一段代码 间隔时间 重复执行
2.定时器语法 :
2.1 setInterval : 永久定时器。 一旦开启,永久重复执行,只能手动清除
(1)开启: let timeID = setInterval( 回调函数 , 间隔时间 )
(2)清除: clearInterval( timeID )
2.2 setTimeout : 一次定时器。一旦开启,间隔时间只会执行一次,完成后自动清除。
(1)开启: let timeID = setTimeout( 回调函数 , 间隔时间 )
(2)清除: clearTimeout( timeID )
@description: 开启定时器
@param {function} 一段代码
回调函数 : 如果一个函数的参数也是函数,这个参数函数就叫做回调函数
@param {number} 间隔时间 单位毫秒 1s = 1000ms
@return: 定时器id
一个页面可以开启很多定时器,浏览器为了更好管理这些定时器。会给每一个定时器一个编号。称之为定时器id
num++有隐式转换,num=num+1没有
let timeID = setInterval( function(){
let pp = document.querySelector('#pp')
pp.innerText++//pp.innerText = Number( pp.innerText ) + 1
} ,1000 )
//点击按钮:关闭定时器
document.querySelector('.btn').onclick = function(){
//参数: 定时器id
clearInterval(timeID)
}
let timeID = setTimeout( function(){
document.querySelector('#pp').innerText++
} , 5000 )
//点击按钮:关闭定时器
document.querySelector('.btn').onclick = function(){
//参数: 定时器id
clearTimeout(timeID)
}
文本是值类型,修改之后对原来数据没有影响,需要重新赋值才会修改
let h=document.querySelector('#hour')
//DOM对象赋值给h,此时h为对象(引用类型),复制的是地址,修改之后对原来数据有影响,不用重新赋值
let m=document.querySelector('#minute').innerText
//文本赋值给m,此时m为字符串,复制的是值,修改之后对原来数据没有影响,需要重新赋值