这是我参与更文挑战的第2天,活动详情查看:
更文挑战
Javascript
javascript由DOM
、BOM
、ECMAScript
组成。
DOM
: document object model 文档对象模型 体现在代码中是document
BOM
:browser object model 浏览器对象模型 体现在代码中是window
ECMAScript
: 核心语法。
包含如何定义变量、循环语句、运算符、表达式、流程控制语句、数据类型。
DOM
可以通过dom的getElementById来获取元素
可以通过dom的onclick, onmousedown, onmouseup来添加事件
可以通过dom的style来设置样式,等等……
DOM的组成
dom是由节点组成。 元素/标签仅仅是节点的一种。
节点一共分为12种:
我们需要记住的有四种:
1:元素类型
3:文本类型
8:注释类型
9:文档类型
全部节点类型:
元素节点 Node.ELEMENT_NODE(1)
属性节点 Node.ATTRIBUTE_NODE(2)
文本节点 Node.TEXT_NODE(3)
CDATA节点 Node.CDATA_SECTION_NODE(4)
实体引用名称节点 Node.ENTRY_REFERENCE_NODE(5)
实体名称节点 Node.ENTITY_NODE(6)
处理指令节点 Node.PROCESSING_INSTRUCTION_NODE(7)
注释节点 Node.COMMENT_NODE(8)
文档节点 Node.DOCUMENT_NODE(9)
文档类型节点 Node.DOCUMENT_TYPE_NODE(10)
文档片段节点 Node.DOCUMENT_FRAGMENT_NODE(11)
DTD声明节点 Node.NOTATION_NODE(12)
复制代码
节点类型
每一个元素都是节点,但是每一个节点不一定是元素。 元素只是节点的一个分类。
元素.nodeType
文本.nodeType
注释.nodeType
文档.nodeType
childNodes属性
它指向调用该属性的节点的所有子节点的集合。
DOM结构:
<div id="box">
<div class="one"></div>
你好
<!-- 我是一个注释 -->
</div>
复制代码
执行代码:
// 获取元素
var box = document.getElementById("box");
// 输出box的所有子节点
console.log(box.childNodes);
复制代码
控制台结果:
经过观察,我们明明写了3个节点, 但是在输出的时候却输出5个节点。
这是因为,高级浏览器会将空白折叠现象形成的空白符当做一个文本类型的节点存在。
我们再到IE中去观察:由于IE中的控制台打不开,我们输出box.childNodes.length
查看结果:
此时,IE反而比高级浏览器好用。
封装轮子统一浏览器的变现
function ChildNodes(dom) {
// 定义一个空数组
var arr = [];
// 查看元素所有子节点的类型有没有文本类型,
// 如果有文本类型,还要查看是否是空文本
for (var i = 0; i < dom.childNodes.length; i++) {
// 查看节点类型
console.log(dom.childNodes[i].nodeType);
if (dom.childNodes[i].nodeType === 3) {
// 说明是文本类型,查看是否是空文本
// 通过data属性可以查看文本类型的内容
// 定义正则表达式
var reg = /^\s+$/;
// 验证
if (reg.test(dom.childNodes[i].data)) {
console.log("第" + i + "项" + "是纯空白");
17} else {
// 不是空白符,就要进入数组中
arr.push(dom.childNodes[i]);
}
} else {
// 不是文本类型的,直接进入数组
arr.push(dom.childNodes[i]);
}
}
// 返回数组
return arr;
}
复制代码
节点属性
nodeType: 该属性标记节点的类型
nodeName: 该属性标记节点的名称
nodeValue: 该属性标记节点的值
Dom结构:
<div id="box">
<div class="one"></div>
你好,世界
<!-- 我是一个注释 -->
</div>
复制代码
执行代码:
// 获取元素
var box = document.getElementById("box");
// 输出box的所有子节点
var arr = ChildNodes(box);
for (var i = 0; i < arr.length; i++) {
// nodeType属性标记该节点的类型
console.log(arr[i].nodeType);
// nodeName属性标记该节点的名称
console.log(arr[i].nodeName);
// nodeValue属性标记该节点的值
console.log(arr[i].nodeValue);
}
复制代码
输出结果:
元素类型的节点名称,是元素标签名称大写字符串
// 文本类型的节点名称,永远是#text字符串
// 注释类型的节点名称,永远是#comment
// 文档类型的节点名称,是#document
// 元素类型的节点值, 是Null
// 文本类型的节点值, 就是书写的文本内容
// 注释类型的值,就是注释的内容
// 文档类型的值, 也是null
复制代码
节点关系
一共分为3种:父子、子父、兄弟
父子
father.childNodes[index] // 获取某一个儿子节点
father.firstChild // 获取第一个子节点
father.lastChild // 获取最后一个子节点
复制代码
子父
child.parentNode // 父节点
复制代码
兄弟
node.previousSibling // 获取上一个兄弟节点
node.nextSibling // 获取下一个兄弟节点
复制代码
代码演示:
// 获取ul的第一个子节点
var first = ul.firstChild;
// 获取ul的最后一个子节点
var last = ul.lastChild;
// 中间的li没有办法直接获取,可以通过childNodes[1|2|3]来获取某一个。
// 获取父节点
var father = first.parentNode;
var father1 = last.parentNode;
console.log(father === father1);
// 兄弟之间的关系
var li3 = ul.childNodes[2];
// 获取上一个兄弟节点
var li2 = li3.previousSibling;
// 获取下一个兄弟节点
var li4 = li3.nextSibling;
复制代码
元素操作
创建元素
使用方式:
document.createElement(type)
type: 元素类型(标签名字符串)
返回值: 创建出来的元素。
上树
使用方式:
father.appendChild(child)
child: 要追加的子节点
father: 父节点
返回值:child
最终效果:将child追加到father中,作为father的childNodes中的最后一个子元素存在
结构:
<div id="box"></div>
复制代码
执行代码:
// 获取box
var box = document.getElementById("box");
// 将创建出来的p元素追加到box中
box.appendChild(p);
复制代码
结果:
下树
使用方式:
father.removeChild(child)
child: 要移除的子节点
father: 父节点
返回值: child
最终效果: child从father的子节点中移除
举例:
//点击btn让p元素下树
// 获取btn
var btn = document.getElementById("btn");
btn.onclick = function() {
box.removeChild(p);
}
复制代码
结果: