AI智能
改变未来

02【JS 高级】-【DOM】 DOM 简介, 获取元素,事件基础,操作元素 ,节点操作


第二天 DOM 简介, 获取元素,事件基础,操作元素 ,节点操作

 

1, DOM 简介

1.1 什么是 DOM

文档对象模型(Document Object Model,简称 DOM),是 W3C 组织推荐的处理可扩展标记语言(HTML 或者XML)的标准编程接口

W3C 已经定义了一系列的 DOM 接口,通过这些 DOM 接口可以改变网页的内容、结构和样式。

 

1.2 DOM 树

  1. 文档:一个页面就是一个文档,DOM 中使用 document 表示
  2. 元素:页面中的所有标签都是元素,DOM 中使用 element 表示
  3. 节点:网页中的所有内容都是节点(标签、属性、文本、注释等),DOM 中使用 node 表示 DOM

把以上容都看做是

 

2, 获取元素

2.1 如何获取页面元素?

DOM在我们实际开发中主要用来操作元素。我们如何来获取页面中的元素呢? 获取页面中的元素可以使用以下几种方式:

  1. 根据 ID 获取
  2. 根据标签名获取
  3. 通过 HTML5 新增的方法获取
  4. 特殊元素获取

 

2.2 根据 ID 获取

  • 使用 getElementById() 方法可以获取带有 ID 的元素对象。document.getElementById(\’id\’);
  • 使用 console.dir() 可以打印我们获取的元素对象,更好的查看对象里面的属性和方法。

        // 1. 因为我们文档页面从上往下加载,所以先得有标签 所以我们script写到标签的下面

        // 2. get 获得 element 元素 by 通过 驼峰命名法 

        // 3. 参数 id是大小写敏感的字符串

        // 4. 返回的是一个元素对象

        var timer = document.getElementById(\’time\’);

        console.log(timer);

        console.log(typeof timer);

        // 5. console.dir 打印我们返回的元素对象 更好的查看里面的属性和方法

        console.dir(timer);

 

 

2.3 根据标签名获取

  • 使用 getElementsByTagName() 方法可以返回带有指定标签名的象的集合。

document.getElementsByTagName(\’标签名\’);

注意:

1. 因为得到的是一个象的集合,所以我们想要操作里面的元素就需要遍

2. 得到元素对象是动态的

3. 如果取不到元素,返回空的伪数组(因为获取不到对象)

        // 1.返回的是 获取过来元素对象的集合 以伪数组的形式存储的

        var lis = document.getElementsByTagName(\’li\’);

        console.log(lis);

        console.log(lis[0]);

        // 2. 想要依次打印里面的元素对象我们可以采取遍历的方式

        for (var i = 0; i < lis.length; i++) {

            console.log(lis[i]);

        }

        // 3. 如果页面中只有一个li 返回的还是伪数组的形式 

        // 4. 如果页面中没有这个元素 返回的是空的伪数组的形式

        // 5. element.getElementsByTagName(\’标签名\’); 父元素必须是指定的单个元素

        // var ol = document.getElementsByTagName(\’ol\’); // 

            // console.log(ol[0].getElementsByTagName(\’li\’));

            var ol = document.getElementById(\’ol\’);

            console.log(ol.getElementsByTagName(\’li\’));

     

            // 5. element.getElementsByTagName(\’标签名\’); 父元素必须是指定的单个元素

            // var ol = document.getElementsByTagName(\’ol\’); // [ol]

            // console.log(ol[0].getElementsByTagName(\’li\’));

            var ol = document.getElementById(\’ol\’);

            console.log(ol.getElementsByTagName(\’li\’));

如果还有一组《li》 呢?给它 ul 加一个id= “nav”

  • 还可以取某元素(父元素)部所有指定标签的子元素.

       element.getElementsByTagName(\’标签名\’);

注意:父元素必须是单个对(必须指明是哪一个元素对象). 获取的时候不包括父元素自己

 

2.4 通过 HTML5 新增的方法获取

1. document.getElementsByClassName(‘类名’);// 根据类名返回元素对象集合

2. document.querySelector(\’选择器\’); // 根据指定选择器返回第一元素对象

3. document.querySelectorAll(\’选择器\’); // 根据指定选择器返回所有

注意:querySelector和querySelectorAll里面的选择器需要加符如:document.querySelector(\’#nav\’);

不考虑兼容性,用它会好一些的!!!!

        // 1. getElementsByClassName 根据类名获得某些元素集合

        var boxs = document.getElementsByClassName(\’box\’);

        console.log(boxs); //div.box 伪数组得方式存得

 

        // 2. querySelector 返回指定选择器的第一个元素对象  切记 !!!里面的选择器需要加符号 .box  #nav

        var firstBox = document.querySelector(\’.box\’);

        console.log(firstBox);

        var nav = document.querySelector(\’#nav\’);

        console.log(nav);

        var li = document.querySelector(\’li\’);

        console.log(li);

 

        // 3. querySelectorAll()返回指定选择器的所有元素对象集合,也是伪数组显示出来

        var allBox = document.querySelectorAll(\’.box\’);

        console.log(allBox);

        var lis = document.querySelectorAll(\’li\’);

        console.log(lis);

    

 

2.5 获取特殊元素(body,html)

取body元素; doucumnet.body // 返回body元素对象

取html元素;document.documentElement // 返回html元素对象

        // 1.获取body 元素

        var bodyEle = document.body;

        console.log(bodyEle);

        console.dir(bodyEle);

        // 2.获取html 元素

        // var htmlEle = document.html;

        var htmlEle = document.documentElement;

        console.log(htmlEle);

 

3, 事件基础

3.1 事件概述

[ol]

  • JavaScript 使我们有能力创建动态页面,事件是可以被 JavaScript 侦测到的行为。
  • 简单理解: 触发响应机制。 网页中的每个元素都可以产生某些可以触发 JavaScript 的事件,例如,我们可以在用户点击某按钮时产生一个 事件,然后去执行某些操作
  •  

    3.2 事件三要素

    • 事件源 (谁) :事件被触发的对象,(按钮等,可以给她起一个id名字)–获取事件源
    • 事件类型 (什么事件) :如何触发 什么事件?鼠标点击,经过,键盘按下
    • 事件处理程序 (做啥):通过函数赋值的方式完成

    【案例】:点击按钮弹出警示框

    【案例分析】:

    取事件源

    注册事件(绑定事件),使用 onclick

    编写事件处理程序,写一个弹出 alert 警示框

    【案例代码】:

    var btn = document.getElementById(\’btn\’);

    btn.onclick = function() { alert(\’你好吗\’); };

    行事件的步!!!重要!!!~~~~~~~~~~~~

    *** 1. 获取事件源

    *** 2. 注册事件(绑定事件)

    *** 3. 添加事件处理程序(采取函数赋值形式)

     

    3.3 常见的鼠标事件

     

    3.4 分析事件三要素

    【案例】下拉菜单三要素 / 关闭广告三要素

    【分析】

    1. 获取事件源 : 京东盒子 / ❌

    2. 注册事件(绑定事件) :鼠标经过 / 鼠标点击

    3. 添加事件处理程序(采取函数赋值形式):盒子显示和隐藏

     

    4, 操作元素 (核心 !!!~)

    JavaScript 的 DOM 操作可以变网页内容、结构和样式,我们可以利用 DOM 操作元素来改变元素里面的内容 、属等。注意以下都是属性

    4.1 改变元素内容

    1. element.innerText  从起始位置到终止位置的内容, 去除html标签 同时空格和换行也会去掉
    2. element.innerHTML 起始位置到终止位置的全部内容包括html标签,同时保留空格和换行

     

    4.2 常用元素的属性操作

    • innerText、innerHTML 改变元素内容
    • src、href
    • id、alt、title

    【案例】- 点击换图片

    【案例】分时显示不同图片,显示不同问候语

    根据不同时间,页面显示不同图片,同时显示不同的问候语。

    如果上午时间打开页面,显示上午好,显示上午的图片。

    如果下午时间打开页面,显示下午好,显示下午的图片。

    如果晚上时间打开页面,显示晚上好,显示晚上的图片

    【案例分析】:

    ① 根据不同时间来判断,所以需要用到日期

    ② 利用多分支来设置不同的图片

    ③ 需要一个图片,并且根据时间修改图片,就需要用到操作元素src属性

    ④ 需要一个div元素,显示不同问候语,修改元素内容即可

            // 根据系统不同时间来判断,所以需要用到日期内置对象

            // 利用多分支语句来设置不同的图片

            // 需要一个图片,并且根据时间修改图片,就需要用到操作元素src属性

            // 需要一个div元素,显示不同问候语,修改元素内容即可

            // 1.获取元素

            var img = document.querySelector(\’img\’);

            var div = document.querySelector(\’div\’);

            // 2. 得到当前的小时数

            var date = new Date(); 

            var h = date.getHours();

            // 3. 判断小时数改变图片和文字信息

            if (h < 12) {

                img.src = \’../../images/s.gif\’;

                div.innerHTML = \’亲,上午好,好好写代码\’;

            } else if (h < 18) {

                img.src = \’../../images/x.gif\’;

                div.innerHTML = \’亲,下午好,好好写代码\’;

            } else {

                img.src = \’../../images/w.gif\’;

                div.innerHTML = \’亲,晚上好,好好写代码\’;

            }

     

    4.3 表单元素的属性操作

    利用 DOM 可以操作如下表元素的性:type、value、checked、selected、disabled

        <button>按钮</button>

        <input type=\”text\” value=\”输入内容\”>

        <script>

            // 1. 获取元素

            var btn = document.querySelector(\’button\’);

            var input = document.querySelector(\’input\’);

            // 2. 注册事件 处理程序

            btn.onclick = function() {

                // input.innerHTML = \’\’;  这个是 普通盒子 比如 div 标签里面的内容

                // 表单里面的值 文字内容是通过 value 来修改的

                input.value = \’被点击了\’;

                // 如果想要某个表单被禁用 不能再点击 disabled  我们想要这个按钮 button禁用

                // btn.disabled = true;

                this.disabled = true;

                // this 指向的是事件函用者 btn

            }

        </script>

     

     

    案例:仿京东显示密

    点击按钮将密码框切换为文本框,并可以查看密码明文。

    【案例分析】:

    ① 核心思路: 点击眼睛按钮,把密码框类型改为文本框就可以看见里面的密码

    ② 一个按钮两个状态,点击一次,切换为文本框,继续点击一次切换为密码框

    ③ 算法:利用一个flag变量,来判断flag的值,如果是1 就切换为文本框,flag 设置为0,如果是0 就切换为密码框,flag设置为1

     

    4.4 样式属性操作

    我们可以通过 JS 修改元素的大小、颜色、位置等样式。

    • element.style 行内样式操作
    • element.className 类名样式操作

    注意: 1. JS 里面的样式采取驼峰命名法 比如 fontSize、 backgroundColor

                2. JS 修改 style 样式操作,产生的是行内样式,CSS 权重比较高

    【案例: 淘击关闭维码

    当鼠标点击二维码关闭按钮的时候,则关闭整个二维码。

    【案例分析】

    ① 核心思路: 利用样式的显示和隐藏完成, display:none 隐藏元素 display:block 显示元素

    ② 点击按钮,就让这个二维码盒子隐藏起来即可

    【实现代码】

    var btn = document.querySelector(\’.close-btn\’);

    var box = document.querySelector(\’.box\’); // 2.注册事件 程序处理

    btn.onclick = function() {

    box.style.display = \’none\’;

    【案例】: 循环精灵图背景

    可以利用 for 循环设置一组元素的精灵图背景

    【案例分析】

    ① 首先精灵图图片排列有规律的 (竖着排列得)

    ② 核心思路: 利用for循环 修改精灵图片的 背景位置 background-position

    ③ 剩下的就是考验你的数学功底了

    ④ 让循环里面的 i 索引 * 44 就是每个图片的y坐标

    【实现代码】

    var lis = document.querySelectorAll(\’li\’);

    for (var i = 0; i < lis.length; i++) {

    // 让索引号 乘以 44 就是每个li 的背景y坐标 index就是我们的y坐标

    var index = i * 44;

    lis[i].style.backgroundPosition = \’0 -\’ + index + \’px\’;

    }

     

    【案例】:藏文本框容(搜索

    当鼠标点击文本框时,里面的默认文字隐藏,当鼠标离开文本框时,里面的文字显示。

    【案例分析】

    ① 首先表单需要2个新事件,获得焦点 onfocus 失去焦点 onblur

    ② 如果获得焦点, 判断表单里面内容是否为默认文字,如果是默认文字,就清空表单内容

    ③ 如果失去焦点, 判断表单内容是否为空,如果为空,则表单内容改为默认文字

    我们可以通过 JS 修改元素的大小、颜色、位置等样式。

    1. element.style 行内样式操作

    2. element.className 类名样式操作

    注意:

      1. 如果样式修改较多,可以采取操作类名方式更改元素样式。

      2. class因为是个保留字,因此使用className来操作元素类名属性

      3. className 会直接更改元素的类名,会覆盖原先的类名。

    案例: 密框格式提示错误

    如果离,里面输入个数不是6~16,则提示错误信息,否则提示输入正确信息

    【案例分析】:

    ① 首先判断的事件是表单失去焦点 onblur

    ② 如果输入正确则提示正确的信息颜色为绿色小图标变化

    ③ 如果输入不是6到16位,则提示错误信息颜色为红色 小图标变化

    ④ 因为里面变化样式较多,我们采取className修改样式

    [code]<style>        div {            width: 600px;            margin: 100px auto;        }                .message {            display: inline-block;            font-size: 12px;            color: #999;            background: url(images/mess.png) no-repeat left center;            padding-left: 20px;        }                .wrong {            color: red;            background-image: url(images/wrong.png);        }                .right {            color: green;            background-image: url(images/right.png);        }    </style></head><body>    <div class=\"register\">        <input type=\"password\" class=\"ipt\">        <p class=\"message\">请输入6~16位密码</p>    </div>    <script>        // 首先判断的事件是表单失去焦点 onblur        // 如果输入正确则提示正确的信息颜色为绿色小图标变化        // 如果输入不是6到16位,则提示错误信息颜色为红色 小图标变化        // 因为里面变化样式较多,我们采取className修改样式        // 1.获取元素        var ipt = document.querySelector(\'.ipt\');        var message = document.querySelector(\'.message\');        //2. 注册事件 失去焦点        ipt.onblur = function() {            // 根据表单里面值的长度 ipt.value.length            if (this.value.length < 6 || this.value.length > 16) {                // console.log(\'错误\');                message.className = \'message wrong\';                message.innerHTML = \'您输入的位数不对要求6~16位\';            } else {                message.className = \'message right\';                message.innerHTML = \'您输入的正确\';            }        }    </script>

     

    操作元素总结

    操作元素是 DOM 核心内容

    4.5 排他思想

    如果有同一元素,我想要某一元素实现种样式, 需要用到循的排他思想算法

    1. 所有元素全部清除样式(干掉其他人)
    2. 给当前元素设置样式 (留下我自己)
    3. 注意顺序不能颠倒,首先干掉其他人,再置自

    案例:百度换肤

    【案例分析】

    ① 这个案例练习的是给一组元素注册事件 、

    ② 给4个小图片利用循环注册点击事件

    ③ 当我们点击了这个图片,让我们页面背景改为当前的图片

    ④ 核心算法: 把当前图片的src 路径取过来,给 body 做为背景即可

    【实现代码】

    // 1. 获取元素 var imgs = document.querySelector(\’.baidu\’).querySelectorAll(\’img\’);

    // 2. 循环注册事件

    for (var i = 0; i < imgs.length; i++) {

    imgs[i].onclick = function() {

    document.body.style.backgroundImage = \’url(\’ + this.src + \’)\’;

    }

    }

     

    案例:表格隔行

    【案例分析】

    ① 用到新的鼠标事件 鼠标经过 onmouseover 鼠标离开 onmouseout

    ② 核心思路:鼠标经过 tr 行,当前的行变背景颜色, 鼠标离开去掉当前的背景颜色

    ③ 注意: 第一行(thead里面的行)不需要变换颜色,因此我们获取的是 tbody 里面的行    

    [code]<style>        table {            width: 800px;            margin: 100px auto;            text-align: center;            border-collapse: collapse;            font-size: 14px;        }                thead tr {            height: 30px;            background-color: skyblue;        }                tbody tr {            height: 30px;        }                tbody td {            border-bottom: 1px solid #d7d7d7;            font-size: 12px;            color: blue;        }                .bg {            background-color: pink;        }    </style></head><body>    <table>        <thead>            <tr>                <th>代码</th>                <th>名称</th>                <th>最新公布净值</th>                <th>累计净值</th>                <th>前单位净值</th>                <th>净值增长率</th>            </tr>        </thead>        <tbody>            <tr>                <td>003526</td>                <td>农银金穗3个月定期开放债券</td>                <td>1.075</td>                <td>1.079</td>                <td>1.074</td>                <td>+0.047%</td>            </tr>            <tr>                <td>003526</td>                <td>农银金穗3个月定期开放债券</td>                <td>1.075</td>                <td>1.079</td>                <td>1.074</td>                <td>+0.047%</td>            </tr>            <tr>                <td>003526</td>                <td>农银金穗3个月定期开放债券</td>                <td>1.075</td>                <td>1.079</td>                <td>1.074</td>                <td>+0.047%</td>            </tr>            <tr>                <td>003526</td>                <td>农银金穗3个月定期开放债券</td>                <td>1.075</td>                <td>1.079</td>                <td>1.074</td>                <td>+0.047%</td>            </tr>            <tr>                <td>003526</td>                <td>农银金穗3个月定期开放债券</td>                <td>1.075</td>                <td>1.079</td>                <td>1.074</td>                <td>+0.047%</td>            </tr>            <tr>                <td>003526</td>                <td>农银金穗3个月定期开放债券</td>                <td>1.075</td>                <td>1.079</td>                <td>1.074</td>                <td>+0.047%</td>            </tr>        </tbody>    </table>    <script>        // 1.获取元素 获取的是 tbody 里面所有的行        var trs = document.querySelector(\'tbody\').querySelectorAll(\'tr\');        // 2. 利用循环绑定注册事件        for (var i = 0; i < trs.length; i++) {            // 3. 鼠标经过事件 onmouseover            trs[i].onmouseover = function() {                    // console.log(11);                    this.className = \'bg\';                }                // 4. 鼠标离开事件 onmouseout            trs[i].onmouseout = function() {                this.className = \'\';            }        }    </script>

     

    案例:表取消全

    业务需求:

    1. 点击上面全选复选框,下面所有的复选框都选中(全选)
    2. 再次点击全选复选框,下面所有的复选框都不中选(取消全选)
    3. 如果下面复选框全部选中,上面全选按钮就自动选中
    4. 如果下面复选框有一个没有选中,上面全选按钮就不选中
    5. 所有复选框一开始默认都没选中状态

    【案例分析】

    ① 全选和取消全选做法: 让下面所有复选框的checked属性(选中状态) 跟随 全选按钮即可

    ② 下面复选框需要全部选中, 上面全选才能选中做法: 给下面所有复选框绑定点击事件,每次点击,都 要循环查看下面所有的复选框是否有没选中的,如果有一个没选中的, 上面全选就不选中。

    ③ 可以设置一个变量,来控制全选是否选中

    【案例代码】

    [code]<!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>    </div>    <script>        // 1. 全选和取消全选做法:  让下面所有复选框的checked属性(选中状态) 跟随 全选按钮即可        // 获取元素        var j_cbAll = document.getElementById(\'j_cbAll\'); // 全选按钮        var j_tbs = document.getElementById(\'j_tb\').getElementsByTagName(\'input\'); // 下面所有的复选框        // 注册事件        j_cbAll.onclick = function() {                // this.checked 它可以得到当前复选框的选中状态如果是true 就是选中,如果是false 就是未选中                console.log(this.checked);                for (var i = 0; i < j_tbs.length; i++) {                    j_tbs[i].checked = this.checked;                }            }            // 2. 下面复选框需要全部选中, 上面全选才能选中做法: 给下面所有复选框绑定点击事件,每次点击,都要循环查看下面所有的复选框是否有没选中的,如果有一个没选中的, 上面全选就不选中。        for (var i = 0; i < j_tbs.length; i++) {            j_tbs[i].onclick = function() {                // flag 控制全选按钮是否选中                var flag = true;                // 每次点击下面的复选框都要循环检查者4个小按钮是否全被选中                for (var i = 0; i < j_tbs.length; i++) {                    if (!j_tbs[i].checked) {                        flag = false;                        break; // 退出for循环 这样可以提高执行效率 因为只要有一个没有选中,剩下的就无需循环判断了                    }                }                j_cbAll.checked = flag;            }        }    </script></body></html>

     

    4.6 自定义属性的操作

    1. 获取属性值

    1. element.属性 获取属性值。
    2. element.getAttribute(\’属性\’);

    区别:

    1. element. (元素本身自带的属性)
    2. element.getAttribute(‘性’); 主要得自定 (标准) 我们程序员自定义的属性

    2. 设置属性值

    1. element.性 = ‘值’
    2. element.setAttribute(\’性\’, \’值\’);

             区别:

    1. element.属性 设置内置属性值
    2. element.setAttribute(‘属性’); 主要设置自定义的属性 (标准)

    3. 移除属性

    1. element.removeAttribute(\’属性\’);

    案例:tab (重点案例!!!!!!!!

    当鼠标点击上面相应的选项卡(tab),下面内容跟随变化

    【案例分析】

    ① Tab栏切换有2个大的模块

    ② 上的模块选项卡,某一底色色,其余不(排他思想)修改名的方式

    下面的模块内容,会跟随上面的选项卡变化。所以下面模块变化写到点击事件里面。

    ④ 规律:下面的模块显示内容和上面的选项卡一一对应,相匹配。

    ⑤ 核心思路: 给上面的tab_list 里面的所有小li 添加自定义属性,属性值从0开始编号。

    ⑥ 当我们点击tab_list 里面的某个小li,让tab_con 里面对应序号的 内容显示,其余隐藏(排他 思想)

    【案例代码】

    [code]  <style>        * {            margin: 0;            padding: 0;        }                li {            list-style-type: none;        }                .tab {            width: 978px;            margin: 100px auto;        }                .tab_list {            height: 39px;            border: 1px solid #ccc;            background-color: #f1f1f1;        }                .tab_list li {            float: left;            height: 39px;            line-height: 39px;            padding: 0 20px;            text-align: center;            cursor: pointer;        }                .tab_list .current {            background-color: #c81623;            color: #fff;        }                .item_info {            padding: 20px 0 0 20px;        }                .item {            display: none;        }    </style></head><body>    <div class=\"tab\">        <div class=\"tab_list\">            <ul>                <li class=\"current\">商品介绍</li>                <li>规格与包装</li>                <li>售后保障</li>                <li>商品评价(50000)</li>                <li>手机社区</li>            </ul>        </div>        <div class=\"tab_con\">            <div class=\"item\" style=\"display: block;\">                商品介绍模块内容            </div>            <div class=\"item\">                规格与包装模块内容            </div>            <div class=\"item\">                售后保障模块内容            </div>            <div class=\"item\">                商品评价(50000)模块内容            </div>            <div class=\"item\">                手机社区模块内容            </div>        </div>    </div>    <script>        // 获取元素        var tab_list = document.querySelector(\'.tab_list\');        var lis = tab_list.querySelectorAll(\'li\');        var items = document.querySelectorAll(\'.item\');        // for循环绑定点击事件        for (var i = 0; i < lis.length; i++) {            // 开始给5个小li 设置索引号             lis[i].setAttribute(\'index\', i);            lis[i].onclick = function() {                // 1. 上的模块选项卡,点击某一个,当前这一个底色会是红色,其余不变(排他思想) 修改类名的方式                // 干掉所有人 其余的li清除 class 这个类                for (var i = 0; i < lis.length; i++) {                    lis[i].className = \'\';                }                // 留下我自己                 this.className = \'current\';                // 2. 下面的显示内容模块                var index = this.getAttribute(\'index\');                console.log(index);                // 干掉所有人 让其余的item 这些div 隐藏                for (var i = 0; i < items.length; i++) {                    items[i].style.display = \'none\';                }                // 留下我自己 让对应的item 显示出来                items[index].style.display = \'block\';            }        }    </script>

     

    4.7 H5自定义属性

    自定义属性目的:是为了保存并使用数据。有些数据可以保存到页面中而不用保存到数据库中。

    自定义属取是通getAttribute(‘属性’) 获取。 但是有些自定义属性很容易引起歧,不容易判是元素的是自定义属

    H5给我们新增了自定义属性:

    1. 设置H5自定义属性: H5定自定义属data-开头为属性名赋值
    2. 获取H5自定义属性
    3. 兼容性获取 element.getAttribute(‘data-index’);
    4. H5新增 element.dataset.index 或者 element.dataset[‘index’] ie 11才开始支持

     

    5, 节点操作

    5.1 为什么学节点操作

    获取元素通常使用两种方式

    1. 利用 DOM 提供的方法取元素

    1. document.getElementById()
    2. document.getElementsByTagName()
    3. document.querySelector 等
    1. 逻辑性不强、繁

    2. 利用层级关取元

    1. 利用父子兄取元素
    2. 逻辑性强, 但是兼容性稍差

    这两种方式都可以获取元素节点,我们后面都会使用,但是点操作更简单

     

    5.2 节点概述

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

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

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

    1. 元素节点 nodeType 为 1
    2. 属性节点 nodeType 为 2
    3. 文本节点 nodeType 为 3 (文本节点包含文字、空格、换行等)

    实际开发中,点操作主要操作的是元素

     

    5.3 节点层级

    利用 DOM 树可以把节点划分为不同的层级关系,常见的是父子兄层级关系

    1. 父级节点

    node.parentNode

    • parentNode 属性可返回某节点的父节点,注意是最近的一个父节点
    • 如果指定的节点没有父节点则返回 null

    2. 子节点

    •  parentNode.childNodes(标准)
    • parentNode.childNodes 返回包含指定节点的子节点的集合,该集合为即时更新的集合。

    注意:返回里面包含了所有的子点,包括元素点,文本等。 如果只想要得里面的元素点,需要专门处理。 所以我们一般不提倡使用childNodes,不提倡使用,但是需要用,用children

    var ul = document. querySelector(‘ul’);

    for(var i = 0; i < ul.childNodes.length;i++) {

    if (ul.childNodes[i].nodeType == 1) {

    // ul.childNodes[i] 是元素节点

    console.log(ul.childNodes[i]);

    } }

    2. parentNode.children(非标准)

    parentNode.children 是一个只读属性,返回所有的子元素节点。它只返回子元素,其余节点不返这个是我重点掌握的)

    虽然children 是一个非标准,但是得到了各个浏览器的支持,因此我们可以放心使用

         

    • parentNode.firstChild:  firstChild 返回第一,找不到则返回null。同样,也是包含所有的节点
    • parentNode.lastChild:ᅟᅵastChild 返回最后一点,找不到则返回null。同样,也是包含所有的节点
    •  
    • parentNode.firstElementChild: firstElementChild 返回第一子元素,找不到则返回null。
    • parentNode.lastElementChild:  lastElementChild 返回最后一子元素,找不到则返回null。

       注意:这两个方法有兼容性问题IE9 以上才支持。

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

    [解方案]:

    1. 如果想要第一个子元素节点,可以使用 parentNode.chilren[0];拿到所有的孩子取第一个就好

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

    案例:下拉菜

    【案例分析】

    ① 导航栏里面的li 都要有鼠标经过效果,所以需要循环注册鼠标事件

    ② 核心原理标经过li 里面的 第二孩子 ul 示, ul

    【实现代码】

    var nav = document.querySelector(\’.nav\’);

    var lis = nav.children; // 得到4个小li

    20000

    for (var i = 0; i < lis.length; i++) {

    lis[i].onmouseover = function() {

    this.children[1].style.display = \’block\’;

    } // ul 里的第二个孩子显示出来

    lis[i].onmouseout = function() {

    this.children[1].style.display=\’none\’;

    } }

      

    3. 兄弟节点

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

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

    3. node.nextElementSibling: 返回当前元素下一个兄弟元素节点,找不到则返回null。

    4. node.previousElementSibling: 返回当前元素上一个兄弟元素节点,找不到则返回null。

    注意:这两个方法有兼容性问题, IE9 以上才支持。

    【问:如何解决兼容性问题】 ? 答:自己封装一个兼容性的函数,但是用的少

    function getNextElementSibling(element) {

    var el = element;

    while (el = el.nextSibling) {

    if (el.nodeType === 1) { //说明是元素节点

     return el;

    }  // 循环一边都找不到的话

    } return null; }

     

    5.4 创建节点

    • document.createElement(\’tagName\’)

    document.createElement() 方法创建由 tagName 指定的 HTML 元素为这些元素原先不存在, 是根据我的需求动态生成的,所以我称为动态创建元素

     

    •       node.appendChild(child) 常用的!!

    方法将一个节点添加到指定父点的子点列表末尾。类似于 CSS 里面的 after 伪元素。

    •       node.insertBefore(child, 指定元素)

    方法将一个节点添加到父节点的指定子节点前面。类似于 CSS 里面的 before 伪元素。

    案例:简单布留言案例】!!!!

    案例分析

    ① 核心思路: 之后,就动态创建一li,添加到ul 里面

    建li 的同,把文本域里面的li.innerHTML 赋值给 li

    ③ 如果想要新的留言后面显示就用 appendChild 如果想要前面显示就用insertBefore

     

    5.5 删除节点

    • node.removeChild(child): 从 DOM 中删除一个子节点,返回删除的节点。

    【案例:删除留言案例】!!!!

    案例分析

    ① 当我们把文本域里面的值赋值给li 的时候,多添加一个删除的链接

    ② 需要把所有的链接获取过来,当我们点击当前的链接的时候,删除当前链接所在的li

    ③ 阻止链接跳转需要添加 javascript:void(0); 或者 javascript:;

     

    5.6 复制节点(克隆节点)

    node.cloneNode(): 返回调用该方法的节点的一个副本。 也称为克隆节点/拷贝节点

    注意:

    1. 如果括号参数为空或者 false ,则是即只克隆复制节点本身,不克隆里面的子节点。

    2. 如果括号参数为 true ,则是深度拷,会复制节点本身以及里面所有的子节点。

    【案例:动态生成表格】

    【案例分析】

    ① 因为里面的学生数据都是动态的,我们需要js 动态生成。 这里我们模拟数据,自己定义好 数据。 数据我们采取对象形式存储。

    ② 所有的数据都是放到tbody里面的行里面。

    ③ 因为行很多,我们需要循环创建多个行(对应多少人)

    ④ 每个行里面又有很多单元格(对应里面的数据),我们还继续使用循环创建多个单元格, 并且把数据存入里面(双重for循环)

    ⑤ 最后一列单元格是删除,需要单独创建单元格。

    ⑥ 最后添加删除操作,单击删除,可以删除当前行。

     

    5.8 三种动态创建元素区别

    1. document.write()
    2. element.innerHTML
    3. document.createElement()

    区别:

    1. document.write 是直接将内容写入页面的内容流,但是文档流执行完毕,则它会导致页面全部重绘

    2. innerHTML 是将内容写入某个 DOM 节点,不会导致页面全部重绘

    3. innerHTML 创建多个元素效率更高(不要拼接字符串,采取数组形式拼接),结构稍微复杂

    4. createElement() 创建多个元素效率稍低一点点,但是结构更清晰

    总结:不同浏览器下,innerHTML 效率要比 creatElement 高

     

    6. DOM 重点核心

    文档对象模型(Document Object Model,简称 DOM),是 W3C 组织推荐的处理可扩展标记语言 (HTML或者XML)的标准编程接口。

    W3C 已经定义了一系列的 DOM 接口,通过这些 DOM 接口可以改变网页的内容、结构和样式。

    1. 对于JavaScript,为了能够使JavaScript操作HTML,JavaScript就有了一套自己的dom编程接口。

    2. 对于HTML,dom使得html形成一棵dom树. 包含 文档、元素、节点

    我们获取过来的DOM元素是 一个对象(object),所以称 为 文档对象模型

    关于dom操作,我们主要针对于元素的操作。主要有创建、增、删、改、查、属性操作、事件操作。

     

    6.1 创建

    • document.write
    • innerHTML
    • createElement

    6.2 增

    • appendChild
    • insertBefore

    6.3 删

    • removeChild

    6.4 改

        主要修改dom的元素属性,dom元素的内容、属性, 表单的值等

    • 修改元素属性: src、href、title等
    • 修改普通元素内容: innerHTML 、innerText
    • 修改表单元素: value、type、disabled等
    • 修改元素样式: style、className

    6.5 查

    主要获取查询dom的元素

    1. DOM提供的API 方法: getElementById、getElementsByTagName 古老用法 不太推荐

    2. H5提供的新方法: querySelector、querySelectorAll 提倡

    3. 利用节点操作获取元素:父(parentNode),子(children)、兄(previousElementSibling,nextElementSibling) 提倡

    6.6 属性操作

    主要针对于自定义属性

    1. setAttribute:设置dom的属性值

    2. getAttribute:得到dom的属性值

    3. removeAttribute: 移除属性

    6.7 事件操作

    给元素注册事件, 采取 : 事件源.事件类型 = 事件处理程序

     

     

     

    赞(0) 打赏
    未经允许不得转载:爱站程序员基地 » 02【JS 高级】-【DOM】 DOM 简介, 获取元素,事件基础,操作元素 ,节点操作