DOM编程
动态脚本
//<script src='dd.js'></script>引入外部脚本
//动态添加外部脚本
let a=document.createElement('script')
a.src='dd.js'
document.body.appendChild(a)
/*<script>
function a(){
console.log('a')
}
</script>内部脚本*/
//动态添加内部脚本
let b =document.createElement('script')
b.text='function a(){console.log('a')}'
document.body.appendChild(b)
//b.appendChild(document.createTextNode('function a(){console.log('a')}'))
注意通过innerHTML属性创建的<script>元素永远不会执行.
动态样式
//<link href='dd.css' rel='stylesheet' type='text/css'>//添加外部css样式
//动态添加外部脚本
let a=document.createElement('link')
a.href='dd.css'
a.rel='stylesheet'
a.type='text/css'
let head=document.getElementByTagName('head')[0]
document.head.appendChild(a)
/*<style>
div{
width:100px;
}
</style>
内部脚本*/
//动态添加内部脚本
let a=document.createElement('style')
a.stylesheet.cssText='div{width:100px}'
let head=document.getElementByTagName('head')[0]
document.head.appendChild(b)
//b.appendChild(document.createTextNode('div{width:100px}'))
操作表格
table元素的方法与属性:
caption 标题
tBodies 包含tbody元素的HTMLCollection
tFoot 指向tfoot元素
tHead 指向tHead元素
rows 表示所有行的Htmlcollection
createTHead()创建thead元素,返回引用
createTFoot()创建tfoot元素,返回引用
createCaption()创建caption元素,返回引用
deleteTHead()删除thead元素
deleteTFoot()删除tfoot元素
deleteCaption()删除caption元素
deleteRow(pos)删除给定位置的行
insertRow(pos)在行集合中给定位置插入一行
tbody元素的方法与属性:
rows 表示tbody元素所有行的Htmlcollection
deleteRow(pos)删除给定位置的行
insertRow(pos)在表元集合中给定位置插入一行,返回引用
tr元素 的方法与属性:
cells包含<tr>元素所有表元的HTMLCollection
deleteCell(pos)删除给定位置的表元
insertCell(pos)在表元集合给定位置插入一个表元,返回该表元的引用.
使用NodeList
通过node.Childnodes得到的为Nodelist对象.
通过Element.Attributes得到的为NamedNodeMap集合.
通过Document.getElementByTagName(),Document.getElementByName()返回的为HTMLCollection对象.
NodeList,NamedNodeMap,HTMLCollection都是实时查询的.
MutationObserver接口
MutationObserver可以在DOM发生改变时,异步执行回调.
基本用法
Mutation通过调用MutationObserver构造函数并传入一个回调函数来创建.
let observer=new MutationObserver((a)=>{console.log(a)})
observe()方法
新创建的MutationObserver实例不会关联到任何DOM节点,要把这个实例与DOM关联起来,需要使用observe()方法.
这个方法接收两个必需的参数:要观察的DOM节点,以及一个MutationObserverInit对象.
MutationObserverInit对象用于控制观察那些方面的变化,是一个键/值对形式配置选项 的字典(映射)
let server=new MutationObserver((a)=>{console.log(a)})
server.observe(document.body,{attributes:true})//绑定body的属性变化
回调中的console.log是后调用的,即异步调用.
回调与MutationRecord
每次回调都会收到MutationRecord实例数组,其中包含的信息包括发生了什么变化,以及DOM的哪一部分受到了影响.因此回调之前可能同时发生多个满足观察条件的事件,所以每次执行回调都会传入一个包含按顺序入队的MutationRecord实例的数组.
第二个参数为观察变化的mutationObserver实例.
let server=new MutationObserver((mutationRecords,mutationObserver)=>{console.log(mutationRecords,mutationObserver)})
MutationRecord实例的属性
target 被修改影响的目标节点
type 字符串表示变化的类型’attributes’,’characterData’,’childList’
oldValue 如果在MutationObserverInit对象中启用(attributeOldvalue或characterData Oldvalue为true),会设置这个属性为被替代的值.childList这个属性始终为null
attributeName 对于’attributes’类型的变化,这里保存被修改属性的名字.其他为null
attributeNamespace 对于使用命名空间的’attributes’类型的变化,这里保存被修改的属性名称其他为NULL.
addedNodes 对于’childList’类型 的变化,返回添加节点的NodeList,默认为空
removeNodes 对于’childList’类型 的变化,返回删除节点的NodeList,默认为空
PreviousSibling 对于’childList’类型 的变化,返回添加节点的前一个同胞节点
nextSibling 对于’childList’类型 的变化,返回添加节点的后一个同胞节点
disconnect()方法
如果要提前终止执行回调,可以调用disconnect()方法
调用disconnect方法,不仅会停止之后变化事件的回调,也会抛弃已经加入任务队列的执行回调.
let a=new MutationObserver((a,b)=>{console.log(a,b)})
a.observe(document,{childNode:true})
a.append(document.createElement('div'));
a.disconnect();
//如果不想抛弃进入任务队列的回调
//settimeout(a.disconnect();a.append(document.createElement('div'));,0)异步使用
a.append(document.createElement('div'));
takeRecords()方法
清除记录队列,返回其中的所有MutationRecord实例.
希望断开与观察目标的联系,又想处理记录队列中的MutationRecord实例时比较有用.
复用MutationObserver
多次调用observe()方法,可以复用一个MutationObserver对象观察多个不同的目标节点.
而调用disconnect()会断开所有观测目标.
重用MutationObserver
调用disconnect()并不会结束MutationObserver的生命,还可以重新调用observe()方法,重新关联目标节点.
MutationObserverInit与观察范围
MutationObserverInit对象用于控制对目标节点的观察范围.
下表列出了MutationObserverInit对象的属性
attributes |
设为 true 以观察受监视元素的属性值变更。默认值为 false。 |
attributeFilter |
字符串数组,表示要观察那些属性的变化,把这个值设置成true,会将attributes的值转化为true,默认值为观察所有属性 |
attributeOldValue |
布尔值,表示MutationRecord是否记录变化之前的属性值,把这个值设置成true,会将attributes的值转化为true,默认值为false |
characterData |
布尔值,表示修改字符数据是否触发变化事件 |
characterDataOldValue |
布尔值,表示MutationRecord是否记录变化之前的属性值,把这个值设置成true,会将characterData的值转化为true,默认值为false |
childList |
布尔值,设为 true 以监视目标节点(如果 subtree 为 true,则包含子孙节点)添加或删除新的子节点。默认值为 false。 |
subtree |
布尔值,表示除了目标节点,是否观察目标节点的子树(后代),如果为false,则只观察目标节点的变化,如果 subtree 为 true,则观察目标节点以及其子孙节点的变化 |
性能.内存与垃圾回收
1.MutationObserver的引用
MutationObserver实例与目标节点的引用关系是非对称的.MutationObserver拥有 对要观察目标节点的弱引用,因为弱引用,所有不会妨碍垃圾回收机制回收目标节点.
而目标节点却拥有对MutationObserver的强引用,如果目标对象 从DOM中被移除,然后被垃圾回收,则关联的MutationObserver也会被垃圾回收.
2.MutationRecord的引用
记录队列中的每个MutationRecord实例至少包含对已有DOM节点的引用.如果变化是ChildList类型,则会包含多个节点的引用.记录队列和回调处理的默认行为是耗尽这个队列,处理每个MutationRecord,然后让他们超出作用域被垃圾回收.
有时候可能需要保存某个观察者的完整变化记录,保存这些MUtationRecord实例,也就是要保持他们引用的节点,妨碍垃圾回收机制回收节点.如果需要尽快释放内存,建议从每个MutationRecord中抽取出最有用的信息.然后保存到一个新对象中.