JS6day(DOM结点的查找、增加、删除。实例化时间,时间戳,时间戳的案例,重绘和回流)

什么是DOM 节点?

DOM树里每一个内容都称之为节点

DOM节点的分类?

  • 元素节点(重点):
    所有的标签 比如 bodydiv
    html 是根节点
  • 属性节点:
    所有的属性 比如 href
  • 文本节点:
    所有的文本
  • 其他
    比如标签里的文字

查找节点:

父节点查找:

  • parentNode 属性
  • 返回最近一级的父节点 找不到返回为null
    -语法
子元素.parentNode

在这里插入图片描述

关闭二维码案例

  <style>
    .erweima {
      width: 149px;
      height: 152px;
      border: 1px solid #000;
      background: url(./images/456.png) no-repeat;
      position: relative;
    }

    .close {
      position: absolute;
      right: -52px;
      top: -1px;
      width: 50px;
      height: 50px;
      background: url(./images/bgs.png) no-repeat -159px -102px;
      cursor: pointer;
      border: 1px solid #000;
    }
  </style>

<body>
  <div class="erweima">
    <span class="close"></span>
  </div>   //5个这样的div
  <script>
    let closeBtn = document.querySelectorAll('.close')    //获取子节点
    console.log(closeBtn.parentNode)   //验证是否是父节点
    for (let i = 0; i < closeBtn.length; i++) {
      closeBtn[i].addEventListener('click', function () {
        // guanbi[i].parentNode.style.display = 'none'  //改变父节点样式
        // this.parentNode.style.display = 'none'  //改变父节点样式
        this.parentNode.style.visibility = 'hidden'   //这里不要用display,div会被占位置
        console.log(i)
      })
    }
  </script>
</body>

子节点查找:

  • childNodes(了解,几乎不用)
    获得所有子节点、包括文本节点(空格、换行)、注释节点等
  • children (重点)
    仅获得所有元素节点
    返回的还是一个伪数组
父元素.children

兄弟关系查找:

  1. 下一个兄弟节点
    nextElementSibling 属性
  2. 上一个兄弟节点
    previousElementSibling 属性
     let btn = document.querySelector('button')
     let two = document.querySelector('.two')
     btn.addEventListener('click', function () {
         two.style.color = 'red'
         two.nextElementSibling.style.color = 'red'
         two.previousElementSibling.style.color = 'red'
     })

增加节点:

在这里插入图片描述

  1. 创建节点

即创造出一个新的网页元素,再添加到网页内,一般先创建节点,然后插入节点
创建元素节点方法:

document.creatElement('标签名')
  1. 追加节点
    要想在界面看到,还得插入到某个父元素中,插入到父元素的最后一个子元素:
//插入到这个父元素的最后
父元素.appendChild(要插入的元素)

插入到父元素中某个子元素的前面

//插入到这个父元素的前面
父元素.insertBefore(要插入的元素,在哪个元素前面)

学成在线重构案例部分代码:

    let ul = document.querySelector('ul')
    // 1. 根据数据的个数,决定这小li的个数
    for (let i = 0; i < data.length; i++) {
        // 2. 创建小li
        let li = document.createElement('li')
        // console.log(li)

        // 4. 先准备好内容,再追加,li里面的标签不用再另外创建元素 
        li.innerHTML = `
        <img src=${data[i].src} alt="">
        <h4>
            ${data[i].title}
        </h4>
        <div class="info">
            <span>高级</span> • <span> ${data[i].num}</span>人在学习
        </div>
        `
        // 3. 追加给ul   父元素.appendChild(子元素)
        ul.appendChild(li)
    }

克隆节点

先克隆后追加!!
在这里插入图片描述
cloneNode会克隆出一个跟原标签一样的元素,括号内传入布尔值
 若为true,则代表克隆时会包含后代节点一起克隆
 若为false,则代表克隆时不包含后代节点
 默认为false

    <ul>
        <li>这是个例子</li>
    </ul>
    <script>
        let ul = document.querySelector('ul')
        let newUL = ul.cloneNode(true)  //先克隆,true代表后代节点一起克隆
        // console.log(newUL)
        document.body.appendChild(newUL)  //追加到父元素body中
    </script>

删除节点

  • 若一个节点在页面中已不需要时,可以删除它
  • 在 JavaScript 原生DOM操作中,要删除元素必须通过父元素删除
  • 语法
父元素.removeChild(要删除的元素)
  • 注:
     如不存在父子关系则删除不成功
     删除节点和隐藏节点(display:none) 有区别的:隐藏节点还是存在的,但是删除,则从html中删除节点。
    <button>点击</button>
    <ul>
        <li>这是个例子</li>
    </ul>
    <script>
        //点击按钮,删除小li
        let ul = document.querySelector('ul')
        let btn = document.querySelector('button')
        btn.addEventListener('click', function () {
            ul.removeChild(ul.children[0])
        })

实例化 (new)

  <script>
      //new 实例化 时间对象
      let date = new Date()  //创建一个时间对象并获取时间,空则得到当前时间
      document.write(date)   //输出Sun Jun 26 2022 21:40:42 GMT+0800 (中国标准时间)
  </script>

在这里插入图片描述
注意:月份和星期取值要+1才正常!!

案例:

        let arr = ['星期日', '星期一', '星期二', '星期三', '星期四', '星期五', '星期六']
        let div = document.querySelector('div')
        // 先调用,就省去了1秒的空白期
        getTime()    //就不会出现空白期
        setInterval(getTime, 1000)
        function getTime() {
            // 1. 实例化时间对象 一定写到定时器里面才可以额
            let date = new Date()
            let year = date.getFullYear()
            let month = date.getMonth() + 1
            let date1 = date.getDate()
            let hour = date.getHours()
            let min = date.getMinutes()
            let sec = date.getSeconds()
            let day = date.getDay()
            div.innerHTML = `今天是: ${year}${month}${date1}${hour}:${min}:${sec} ${arr[day]}`
        }

在这里插入图片描述

时间戳:

什么是时间戳

是指1970年01月01日00时00分00秒起至现在的毫秒数,它是一种特殊的计量时间的方式

三种方式获取时间:

  • date.getTime() 需要实例化

  • +new Date()

  • 使用 Date.now()

重点记住 +new Date() 因为可以返回当前时间戳或者指定的时间戳
无需实例化,但是只能得到当前的时间戳, 而前面两种可以返回指定时间的时间戳

        //第一种
        console.log(Date.now())  //1656332467573
        //第二种
        date = new Date()
        console.log(date.getTime())   //1656332467573
        //第三种 
        console.log(+new Date())    // 当前的时间戳 1656332467573
        console.log(+new Date('2022-6-27 12:00:00'))  // 指定时间的时间戳

浏览器是如何进行界面渲染的

  1. 解析(Parser)HTML,生成DOM树(DOM Tree)
  2. 同时解析(Parser) CSS,生成样式规则 (Style Rules)
  3. 根据DOM树和样式规则,生成渲染树(Render Tree)
  4. 进行布局 Layout(回流/重排):根据生成的渲染树,得到节点的几何信息(位置,大小)
  5. 进行绘制 Painting(重绘): 根据计算和获取的信息进行整个页面的绘制
  6. Display: 展示在页面上

重绘和回流(重排)

回流(重排)
当 Render Tree 中部分或者全部元素的尺寸、结构、布局等发生改变时,浏览器就会重新渲染部分或全部文档的过
程称为回流
重绘
由于节点(元素)的样式的改变并不影响它在文档流中的位置和文档布局时(比如:color、background-color、
outline
等), 称为重绘
重绘不一定引起回流,而回流一定会引起重绘。
在这里插入图片描述
在这里插入图片描述

一个经过我修改的下班倒计时完美案例

在这里插入图片描述

<!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>
    .countdown {
      width: 240px;
      height: 305px;
      text-align: center;
      line-height: 1;
      color: #fff;
      background-color: brown;
      /* background-size: 240px; */
      /* float: left; */
      overflow: hidden;
    }

    .countdown .next {
      font-size: 16px;
      margin: 25px 0 14px;
    }

    .countdown .title {
      font-size: 33px;
    }

    .countdown .tips {
      margin-top: 80px;
      font-size: 23px;
    }

    .countdown small {
      font-size: 17px;
    }

    .countdown .clock {
      width: 142px;
      margin: 18px auto 0;
      overflow: hidden;
    }

    .countdown .clock span,
    .countdown .clock i {
      display: block;
      text-align: center;
      line-height: 34px;
      font-size: 23px;
      float: left;
    }

    .countdown .clock span {
      width: 34px;
      height: 34px;
      border-radius: 2px;
      background-color: #303430;
    }

    .countdown .clock i {
      width: 20px;
      font-style: normal;
    }
  </style>
</head>

<body>
  <div class="countdown">
    <p class="next">今天是2021年8月28日</p>
    <p class="title">下班倒计时</p>
    <p class="clock">
      <span id="hour">00</span>
      <i>:</i>
      <span id="minutes">00</span>
      <i>:</i>
      <span id="scond">00</span>
    </p>
    <p class="tips">
      现在是18:30:00
    </p>
  </div>
  <script>
    //获取元素
    let next = document.querySelector('.next')
    let clock = document.querySelector('.clock')
    //获取时间
    getTime()
    setInterval(getTime, 500)
    function getTime() {
      let date = new Date()
      let year = date.getFullYear()
      let month = date.getMonth() + 1
      let day = date.getDate()
      let hour = date.getHours()
      let minute = date.getMinutes()
      let second = date.getSeconds()
      //显示现在时间
      next.innerHTML = `今天是${year}${month}${day}`
      let time = TimeMachine(hour, minute, second)  //时间转换器<10就加'0'
      clock.nextElementSibling.innerHTML = `现在是${time[0]}:${time[1]}:${time[2]}`
      //时间戳计算
      now = +new Date()
      future = +new Date(`${year}-${month}-${day} 22:00:00`)
      // future = +new Date(`${year}-${month}-${day} 22:00:00`)
      console.log(future)
      total = (future - now) / 1000  //转换成秒数
      if (total <= 0) {
        return
      }
      //显示倒计时
      let h = parseInt(total / 60 / 60 % 24) // 计算小时
      let m = parseInt(total / 60 % 60); // 计算分数
      let s = parseInt(total % 60); // 计算当前秒数
      let time2 = TimeMachine(h, m, s)  //时间转换器<10就加'0'
      clock.children[0].innerHTML = time2[0]
      clock.children[2].innerHTML = time2[1]
      clock.children[4].innerHTML = time2[2]
    }

    //时间转换器<10就加'0'
    function TimeMachine(hour, minute, second) {
      hour = hour < 10 ? '0' + hour : hour //小于10补0,别忘了重新给h赋值
      minute = minute < 10 ? '0' + minute : minute
      second = second < 10 ? '0' + second : second
      return [hour, minute, second]
    }
  </script>
</body>

</html>

微博发布案例部分代码(修改后):

    let area = document.querySelector('#area')
    let useCount = document.querySelector('#useCount')
    let send = document.querySelector('#send')
    area.addEventListener('input', function () {
      useCount.innerHTML = this.value.length
    }
    )
    send.addEventListener('click', function () {
      if (area.value.trim() === '') {   //   防止输入无意义空格, 使用字符串.trim()去掉首尾空格
        alert('不能输入为空!')
        area.value = ''
        useCount.innerHTML = '0'
        return
      }
      let list = document.querySelector('#list')
      let li = document.createElement('li')
      let random = Math.floor(Math.random() * dataArr.length)
      // 利用时间对象将时间动态化       new Date().toLocaleString()
      li.innerHTML = `
            <div class="info">
            <img class="userpic" src=${dataArr[random].imgSrc} />
            <span class="username">${dataArr[random].uname}</span>
            <p class="send-time">${new Date().toLocaleString()}</p>   
            </div>
            <div class="content">${area.value}</div>
            <span class="the_del">X</span>
        `
      list.insertBefore(li, list.children[0])
      // 将表单域内容重置为空
      // 将userCount里面的内容重置为0
      area.value = ''
      useCount.innerHTML = '0'
      let del = li.querySelector('.the_del')     // 使用 li.querySelector()
      del.addEventListener('click', function () {
        list.removeChild(li)
      })
    })

在这里插入图片描述
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值