【第五部分 | JS WebAPI】3:DOM 节点操作

news2024/11/25 16:57:02

目录

| 节点操作

1-1 概述

2-1 获取父节点

3-1 获取子节点(获取所有子对象 不推荐)

3-2 获取子节点(获取所有子【元素节点】)

3-3 获取首尾子节点

4-1 获取兄弟节点

5-1 动态创建、添加节点

5-2 案例:评论区

5-4 删除节点

5-5 复制节点

| 综合案例:动态生成表格

| 三种动态创建元素的区别

| 总结


| 节点操作


1-1 概述

什么是节点?

  • 网页中的所有内容都是节点(标签、属性、文本、注释等),在DOM 中,节点使用 node 来表示。我们常用的是元素节点

  • HTML DOM 树中的所有节点均可通过 JavaScript 进行访问,所有 HTML 元素(节点)均可被修改,也可以 创建或删除。

  • 一般地,节点至少拥有nodeType(节点类型)、nodeName(节点名称)和nodeValue(节点值)这三个 基本属性。

  • 我们在实际开发中,节点操作主要操作的是元素节点

什么是节点操作?

代码示例

<!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>
</head>
<body>
    <div>
        <span></span>
    </div>

    <script>
        // 如果以前想得到div和span元素,需要进行两步
        var divObj = document.getElementsByTagName('div');
        var spanObj = document.getElementsByTagName('span');

        // 而我们若使用节点操作来获取父元素,则只需要获取某一个元素对象,然后根据这个元素对象和其它元素对象的层级关系,使用对应的函数即可
        // span是div的父节点。我们得到了span,则只需要操作这个节点,使用parentNode就可以获取其父节点对象div了
        var spanObj2 = document.getElementsByTagName('span');
        divObj2 = spanObj2[0].parentNode;
        console.log(divObj2);  //div
    </script>
</body>
</html>

 


2-1 获取父节点


3-1 获取子节点(获取所有子对象 不推荐)

 

子元素的标签、换行符会被认为是节点。 如下列代码,若使用

var ul = document.getElementsByTags('ul');

var lis = ul.childNodes;

代码,则会获得的不仅仅是一个含有2个li的元素对象伪数组,而是一个含有5个元素对象的伪数组

具体原因如下

<ul>(换行 第一个节点)
	<li(标签,第二个节点)>XXX</li>(换行,第三个节点)
	<li(标签,第四个节点)>XXX</li>(换行,第五个节点)
</ul>

 


  • 综上,因为返回值里面包含了所有的子节点,包括元素节点,文本节点等。 如果只想要获得里面的元素节点,则需要专门处理。 所以我们一般不提倡使用childNodes


3-2 获取子节点(获取所有子【元素节点】)

parentNode.children

代码示例(childNode 和 children 的对比)

<!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>
</head>
<body>
    <div>
        <span></span>
        <span></span>
        <span></span>
        <span></span>
    </div>

    <script>
        var divObj = document.querySelector('div');
        var children1 = divObj.childNodes;
        var children2 = divObj.children;

        var str1 = '';
        var str2 = '';

        for(var i=0 ; i<children1.length ; i++) {
            str1 += children1[i];
        }
        for(var i=0 ; i<children2.length ; i++) {
            str2 += children2[i];
        }

        console.log(str1); //[object Text][object HTMLSpanElement][object Text][object HTMLSpanElement][object Text][object HTMLSpanElement][object Text][object HTMLSpanElement][object Text]
        console.log(str2); //[object HTMLSpanElement][object HTMLSpanElement][object HTMLSpanElement][object HTMLSpanElement]

    </script>
</body>
</html>

 

 

3-3 获取首尾子节点

注意:firstChild得到的  该子节点包含“换行符等非元素节点”

下列两个方法可以获取的是首尾子【元素】节点

 


实际开发中,如何用兼容IE9以下版本浏览器的方法得到 firstElementChild 和 lastElementChild ?

实际开发中,firstChild 和 lastChild 包含其他节点,操作不方便,而 firstElementChild 和 lastElementChild 又有兼容性问题,那么我们如何获取第一个子元素节点或最后一个子元素节点呢?

解决方案:

1.如果想要第一个子元素节点,可以使用 parentNode.chilren[0]

2.如果想要最后一个子元素节点,可以使用 parentNode.chilren[parentNode.chilren.length - 1]


4-1 获取兄弟节点

注意:该方法得到的 兄弟节点包含“换行符等非元素节点”

 node.nextSibling  //返回当前元素的下一个兄弟元素节点,找不到则返回null。同样,也是包含所有的节点。
 node.previousSibling  // 返回当前元素上一个兄弟元素节点,找不到则返回null。同样,也是包含所有的节点。

下列两个方法可以获取的是兄弟子【元素】节点

 node.nextElementSibling   //返回当前元素下一个兄弟元素节点,找不到则返回null。
 node.previousElementSibling   //g 返回当前元素上一个兄弟节点,找不到则返回null。

可以自己封装一个兼容IE9以下浏览器的获取兄弟子【元素】节点的函数

 function getNextElementSibling(element) {
 	var el = element;
 	while (el = el.nextSibling) {
	 	if (el.nodeType === 1) {
	 		return el;
 		}
 	}
 	return null;
 } 

5-1 动态创建、添加节点

  • 使用场景:如想给 ul 中动态地添加 li


代码示例

基本步骤:获取父节点元素 → 创建要插入的元素 → 插入元素

<!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>
</head>
<body>
    <ul>

    </ul>
    <script>
        // 动态创建元素节点
        var liElement = document.createElement('li');
        // 把创建的元素节点加入(获取父节点 → 添加子节点)
        var ulNode = document.querySelector('ul');
        ulNode.appendChild(liElement);
    </script>
</body>
</html>

 


5-2 案例:评论区

核心思路︰点击按钮之后,就动态创建一个li,添加到ul里面。创建li的同时,把文本域里面的值通过li.innerHTML赋值给li

<!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>
        * {
            margin: 0;
            padding: 0;
        }

        li {
            list-style: none;
        }

        textarea{
            display: block;

            resize:none;  /* 取消拖拽 */
            outline: none;/* 取消选中高亮 */
            height: 200px;
            width: 500px;
            margin: 100px auto;
            margin-bottom: 30px;
            background-color: aliceblue;
            padding: 10px;

            font-family: 'Microsoft YaHei';
            font-size: 20px;
        }

        button {
            display: block;

            background-color: lightskyblue;
            width: 100px;
            height: 40px;
            margin: 0 auto;
        }

        ul {
            width: 500px;
            margin: 40px auto;
            background-color: lightgoldenrodyellow;
        }

        li {
            width: 500px;
            margin: 5px auto;
            height: 30px;
            border-bottom: 1px solid grey;
        }

    </style>
</head>
<body>
    <textarea placeholder="输入评论" name="comment"></textarea>
    <button>发布</button>
    <ul>
    </ul>

    <!-- 点击按钮,获取文本域,然后添加li -->
    <script>
        var btn = document.querySelector('button');
        var text = document.querySelector('textarea');

        btn.onclick = function(){
            // 获取文本域文本
            var textContent = text.value;
            //创建li节点
            var newLi = document.createElement('li');
            //添加li节点
            var ul = document.querySelector('ul');
            ul.appendChild(newLi);
            // 向li节点中添加内容 innerHTML
            newLi.innerHTML = textContent;
            // 清空文本
            text.value = '';
        }
    </script>
</body>
</html>

5-4 删除节点

代码示例

 


5-5 复制节点

代码示例

 


| 综合案例:动态生成表格

目前还没学习Ajax,无法动态通过数据库获取数据。因此我们把数据写在对象中

注意体会上述知识的综合使用:

  • CSS 和 Html的知识

  • 数组存放对象

  • 循环创建事件

  • 如何在table的tbody中插入行、在行中插入列

  • 注意删除按钮的书写 要使用innerHTML方法以渲染html标签

  • 注意删除的时候,删除的是 相对于a 的父亲(tr)的父亲(td),即删除行的那个元素节点。

示例代码:

<!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>
        table {
            width: 500px;
            margin: 100px auto;
            border-collapse: collapse;
            text-align: center;
        }
        
        td,
        th {
            border: 1px solid #333;
        }
        
        thead tr {
            height: 40px;
            background-color: #ccc;
        }
    </style>
</head>

<body>
    <table cellspacing="0">
        <thead>
            <tr>
                <th>姓名</th>
                <th>科目</th>
                <th>成绩</th>
                <th>操作</th>
            </tr>
        </thead>
        <tbody>

        </tbody>
    </table>
    <script>
        // 1.先去准备好学生的数据
        var datas = [{
            name: '魏璎珞',
            subject: 'JavaScript',
            score: 100
        }, {
            name: '弘历',
            subject: 'JavaScript',
            score: 98
        }, {
            name: '傅恒',
            subject: 'JavaScript',
            score: 99
        }, {
            name: '明玉',
            subject: 'JavaScript',
            score: 88
        }, {
            name: '大猪蹄子',
            subject: 'JavaScript',
            score: 0
        }];
        // 2. 往tbody 里面创建行: 有几个人(通过数组的长度)我们就创建几行
        var tbody = document.querySelector('tbody');
        for (var i = 0; i < datas.length; i++) { // 外面的for循环管行 tr
            // 1. 创建 tr行
            var tr = document.createElement('tr');
            tbody.appendChild(tr);
            // 2. 行里面创建单元格(跟数据有关系的3个单元格) td 单元格的数量取决于每个对象里面的属性个数  for循环遍历对象 datas[i]
            for (var k in datas[i]) { // 里面的for循环管列 td
                // 创建单元格 
                var td = document.createElement('td');
                // 把对象里面的属性值 datas[i][k] 给 td  
                // console.log(datas[i][k]);
                td.innerHTML = datas[i][k];
                tr.appendChild(td);
            }
            // 3. 创建有删除2个字的单元格 
            var td = document.createElement('td');
            td.innerHTML = '<a href="javascript:;">删除 </a>';
            tr.appendChild(td);

        }
        // 4. 删除操作 开始 
        var as = document.querySelectorAll('a');
        for (var i = 0; i < as.length; i++) {
            as[i].onclick = function() {
                // 点击a 删除 当前a 所在的行(链接的爸爸的爸爸)  a的爸爸是tr,tr的爸爸是td,因此删除的是td。注意使用的是this 
                tbody.removeChild(this.parentNode.parentNode)
            }
        }
        // for(var k in obj) {
        //     k 得到的是属性名
        //     obj[k] 得到是属性值
        // }
    </script>
</body>

</html>

 


| 三种动态创建元素的区别

 

| 总结

 

 

 

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/27834.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

性能测试_JMeter_connection timed out :connect

jmeter报错:failed:connection timed out :connect/java.net.BindException: Address already in use: connect java.net.BindException: Address already in use: connectat java.net.DualStackPlainSocketImpl.connect0(Native Method)at java.net.DualStackPlainSocketImpl…

Linux系统上安装软件

安装jdk&#xff0c;安装tomcat&#xff0c;安装Mysql 四种安装方式&#xff1a; 安装jdk 1.去这个网站上下载linux版本的jdk Java Archive Downloads - Java SE 8 2.在虚拟机中的服务器终端中输入ifconfig&#xff08;注意不是ipconfig&#xff0c;而是ifconfig…

智慧机场解决方案-最新全套文件

智慧机场解决方案-最新全套文件一、建设背景二、建设思路三、建设方案四、获取 - 智慧机场全套最新解决方案合集一、建设背景 中国处在机场持续大规模建设过程中&#xff0c;政府也有意愿建设机场作为城市名片&#xff0c;经济持续增长会带来机场的持续建设&#xff1b;我国机…

螺旋模型的优点与缺点

螺旋模型&#xff1a; 特点&#xff1a; 螺旋模型在“瀑布模型”的每一个开发阶段前引入一个非常严格的风险识别、风险分析和风险控制&#xff0c;它把软件项目分解成一个个小项目。每个小项目都标识一个或多个主要风险&#xff0c;直到所有的主要风险因素都被确定 螺旋模型强…

Copilot:AI自动写代码,人工智能究竟还能取代什么?

Copilot&#xff1a;AI自动写代码&#xff0c;人工智能究竟还能取代什么&#xff1f; 前言 在AI绘画掀起一阵热潮之后&#xff0c;AI写代码又逐渐进入了我们的视野&#xff0c;似乎这一步我们还没想到就迅速到来了&#xff0c;难道说AI在取代画家之后&#xff0c;还要取代程序…

引擎入门 | Unity UI简介–第1部分(7)

本期我们继续为大家进行Unity UI简介&#xff08;第一部分&#xff09;的后续教程 本篇内容 14.放置标题图像 15.添加开始按钮 16.定位按钮 文章末尾可免费获取教程源代码 本篇Unity UI简介&#xff08;第一部分&#xff09;篇幅较长&#xff0c;分为十篇&#xff0c;本篇…

sqli-labs/Less-48

欢迎界面还是以sort为注入参数 接下来进行注入类型的判断 首先输入一下内容 sortrand() 多尝试几次 发现界面会发生变化 所以这一关属于数字型注入 然后我们选择使用报错注入 尝试输入一下内容 sortupdatexml(1,if(11,concat(0x7e,database(),0x7e),1),1)-- 回显如下 呦…

网络层 408真题 大题详解

1、【2009】 第一问有两种分配可能性&#xff0c;要想到位 记住&#x1f6a9; 路由器到互联网的路由相当于默认路由0/0 即目的地址0.0.0.0 子网掩码0.0.0.0 2、【2015】 注意&#x1f6a9;DHCP服务器不能转发信息 要观察到本图网络拓扑是同一个网络&#xff0c;在同一个网络中…

Linux系统man帮助一文通-尚文网络xUP楠哥

~~全文共1453字&#xff0c;阅读需约5分钟。 进Q群11372462&#xff0c;领取专属报名福利&#xff0c;包含云计算学习路线图代表性实战训练大厂云计算面试题资料! Linux帮助手册的常见章节 man是Manual的缩写&#xff0c;用来查看系统中命令和配置的帮助信息。Linux本地系统上…

Java#21(抽象与接口)

目录 一.抽象方法和抽象类 1.抽象方法: 2.抽象类: 3.注意: 二.接口 1.接口的定义 2.注意 3.接口中成员的特点 三.接口中的方法 1.JDK7以前: 接口中只能定义抽象方法2.JDK8: 接口中可以定义有方法体的方法(默认、静态) 3.JDK9: 接口中可以定义私有方法 一.抽象方法和…

【Call for papers】DSN-2023(CCF-B/截稿日期: 2022年12月7日)

文章目录1.会议信息2.时间节点3.论文主题On behalf of the Organizing Committee, we extend you a warm welcome to the 53rd Annual IEEE/IFIP International Conference on Dependable Systems and Networks (DSN 2023), organized by the University of Coimbra, Portugal.…

[ Linux ] 如何查看Linux系统版本

文章目录查看Linux内核Kernel的场景情况查看 Linux 版本的几种方式1、通过查看 redhat-release &#xff08;可查看小版本&#xff09;2、使用 lsb_release 命令 &#xff08;可查看小版本&#xff09;3、使用 hostnamectl 命令 &#xff08;只可查看大版本&#xff09;4、通过…

使用NNO区域进行色偏检测

想做图像的色偏检测&#xff0c;网上的资料全是同一套代码&#xff0c;就是2013年那个计算等价圆&#xff0c;然后直接用D-r>9 and K>0.6) or K>1.5&#xff0c;判断的代码&#xff08;相信大家都查到过了&#xff09; 但是色偏问题并不是这样简单的判断就可以的&…

一文掌握Python虚拟环境-提升你的开发效率

在真正开始Python代码编写、编译、运行、调试和开发项目之前&#xff0c;必须要了解下Python的虚拟环境的配置&#xff0c;熟悉使用后&#xff0c;会大大提升后续的开发效率&#xff0c;减少非代码原因导致的问题。virtualenv就是Python中的Virtual Environment-虚拟环境。本文…

C#界面里Form.HelpButton 属性的使用

C#界面里Form.HelpButton 属性的使用 Form.HelpButton 属性是获取或设置一个值,该值指示是否应在窗体的标题框中显示“帮助”按钮。 在一般的开发中,很少有人使用这个属性,因为程序比较简单,只要用户一上手就可以使用了。 如果界面比较复杂,或者说功能比较多,就需要使…

04【MyBatis的类型处理器】

四、MyBatis的类型处理器 4.1 typeAliases别名配置 类型别名是为 Java 类型设置一个短的名字&#xff0c;可以方便我们引用某个类。 我们仔细观察mapper.xml配置文件&#xff0c;会发现不管是入参&#xff08;paramterType&#xff09;还是出参&#xff08;ResultType&#…

大数据面试题(三):MapReduce核心高频面试题

文章目录 MapReduce核心高频面试题 一、ReduceTask工作机制 二、请描述mapReduce有几种排序及排序发生的阶段&#xff1f; 1、排序的分类 2、自定义排序WritableComparable 3、排序发生的阶段 三、请描述mapReduce中shuffle阶段的工作流程&#xff0c;如何优化shuffle阶…

Android App开发手机阅读中实现平滑翻书效果和卷曲翻书动画实战(附源码 简单易懂 可直接使用)

需要图片集和源码请点赞关注收藏后评论区留言~~~ 一、平滑翻书效果 与纸质书籍类似&#xff0c;手机上的电子书也有很多页&#xff0c;逐页浏览可采用翻页视图&#xff0c;然而翻页视图犹如一幅从左到右的绵长画卷&#xff0c;与现实生活中上下层叠的书籍并不相像&#xff0c;…

百度paddle框架 目标检测

random recording 随心记录 What seems to us as bitter trials are often blessings in disguise. 看起来对我们痛苦的试炼&#xff0c;常常是伪装起来的好运。 数据集准备 2183张图片&#xff0c;训练集1693张&#xff0c;验证集245&#xff0c;测试集245张。 包含7种昆虫&a…

数据挖掘算法原理与实践:k-均值

目录 第一关&#xff1a;什么是质心 任务描述&#xff1a; 相关知识&#xff1a; 什么是质心&#xff1a; 编程要求&#xff1a; 测试说明&#xff1a; 第二关&#xff1a;动手实现k-均值 任务描述&#xff1a; 相关知识&#xff1a; 一、数据集介绍 二、k-means算法…