zoukankan      html  css  js  c++  java
  • (91)Wangdao.com第二十四天_Mutation Observer API 突变监视器

    Mutation Observer API 突变监视接口

    用来监视 DOM 变动。

    DOM 的任何变动,比如节点的增减属性的变动文本内容的变动,这个 API 都可以得到通知

    概念上,它很接近事件,可以理解为 DOM 发生变动就会触发 Mutation Observer 事件。

     

    但是,Mutation Observer 与 事件 有一个本质不同:

      • 事件是同步触发,也就是说,DOM 的变动立刻会触发相应的事件;
      • Mutation Observer 则是异步触发,DOM 的变动并不会马上触发,而是要等到当前所有 DOM 操作都结束才触发

     

    Mutation Observer 有以下特点:

      • 它等待所有脚本任务完成后,才会运行(即异步触发方式)。
      • 它把 DOM 变动记录封装成一个数组进行处理,而不是一条条个别处理 DOM 变动。
      • 它既可以观察 DOM 的所有类型变动,也可以指定只观察某一类变动。

     

    Mutation Observer 构造函数

    • 使用
      • 使用 MutationObserver 构造函数,新建一个观察器实例,同时指定这个实例的回调函数。
        • var box = document.getElementById("test_box");

          // 1. 定义一个 监视器 实例
          var
          mo = new MutationObserver(function(mutations, observer){ mutations.forEach(function(mutation){ console.log(mutation); }); });

          // 2. 定义要监听的 类型集合 对象
          var chgType = {
          "childList": true, // 子节点变动 监视
          "attributes": true, // 属性变动 监视
          "characterData": true, // 节点内容 或者 节点文本 的变动
          };

          // 3. 启动监听
          mo.observe(box, chgType);

    .observe()            启动监视器

    • 第一个参数是 所要观察的DOM元素是article
    • 第二个参数是 所要观察的变动类型        

    至少指定一种要监听的变动类型,否则报错

    "childList": true,            子节点 变动

    "attributes": true,              属性 变动

    "characterData": true,                        节点内容 或者 节点文本 变动

    还可指定监听属性

    "subtree": true,            是否同时监视该节点的所有后代节点

    "attributeOldValue": true,            监视 attributes 变动时,是否需要记录变动前的属性值

    "characterDataOldValue": true,            监视 characterData 变动时,是否需要记录变动前的属性值

    "attributeFilter": 数组,            表示需要观察的特定属性(比如['class','src'])

    • 实例:观察新增的子节点
    • var insertedNodes = [];
      var mo = new MutationObserver(function(mutations) { mutations.forEach(function(mutation) { for (var i = 0; i < mutation.addedNodes.length; i++) insertedNodes.push(mutation.addedNodes[i]); }) });
      mo.observe(document, { childList:
      true }); console.log(insertedNodes);

     

    .disconnect();            停止监视

    .takeRecords();            清除变动记录,即不再处理未处理的变动____该方法返回变动记录的数组

    • // 保存所有没有被观察器处理的变动
      var changes = mutationObserver.takeRecords();

     

    MutationRecord 对象

    DOM 每次发生变化,就会生成一条变动记录(MutationRecord 实例)。该实例包含了与变动相关的所有信息。

    Mutation Observer 处理的就是一个个 MutationRecord 实例所组成的数组

    • MutationRecord 对象包含了 DOM 的相关信息,有如下属性:

     

    type        观察的 突变类型(attributes、characterData 或者 childList)
    target        发生突变的 DOM 节点
    addedNodes        新增的 DOM 节点
    removedNodes        删除的 DOM 节点
    previousSibling        前一个同级节点,如果没有则返回 null
    nextSibling        下一个同级节点,如果没有则返回 null
    attributeName        发生突变的属性。如果设置了 attributeFilter,则只返回预先指定的属性
    oldValue        突变前的值。这个属性只对 attribute 和 characterData 突变有效,如果发生 childList 突变,则返回 null

     

    • 实例: 观察<body>的所有下级节点, 回调函数会在控制台显示所有变动的类型和目标节点
    • var callback = function (records){
          records.map(function(record){
              console.log('Mutation type: ' + record.type);
              console.log('Mutation target: ' + record.target);
          });
      };
      
      var mo = new MutationObserver(callback);
      
      var chgType = {
          'childList': true,
          'subtree': true
      };
      
      mo.observe(document.body, chgType);
    • 实例: 属性变动('attributes': true), 实际发生变动时,会将变动前的值显示在控制台。
    • var callback = function (records) {
          records.map(function (record) {
              console.log('Previous attribute value: ' + record.oldValue);
          });
      };
      
      var mo = new MutationObserver(callback);
      
      var element = document.getElementById('#my_element');
      
      var options = {
          'attributes': true,
          'attributeOldValue': true
      }
      
      mo.observe(element, options);

     

    • 封装: 目标元素 只要在 DOM 上已加载, 则执行 fn
    • (function(win){
          'use strict';
          var doc = win.document;
          var MutationObserver = win.MutationObserver || win.WebKitMutationObserver;
          
          var targets = [];
          var mo;
          
          function isReadyOrNot(){
              // 检查是否匹配已储存的节点
              for(var i = 0; i < targets.length; i++){
                  var target = targets[i];
                  var elements = doc.querySelectorAll(target.selector);    // 检查指定节点是否有匹配
                  for(var j = 0; j < elements.length; j++){
                      var element = elements[j];
                      
                      // 确保回调函数只会对该元素调用一次
                      if(!element.isReady){
                          element.isReady = true;
                          // 对该节点调用回调函数
                          target.fn.call(element, element);
                      };
                  };
              };
          };
          
          /**** 目标元素 只要在 DOM 上已加载, 则执行 fn ****/ 
          win.eleReady = function(selector, fn){
              // 储存选择器和回调函数
              targets.push({
                  selector: selector,
                  fn: fn
              });
              
              if(!mo){
                  mo = new MutationObserver(isReadyOrNot);    // 定义 突变监听器
                  mo.observe(doc.documentElement, {    // 开始监听 document变化
                      childList: true,    // 监听 子节点
                      subtree: true    // 同时监听 后代节点
                  });
              };
              
              isReadyOrNot();    // 检查该节点是否已经在DOM中
          };
      })(window);
      
      eleReady('.foo', function(element){
          // ...
      });

     

    --------小尾巴 ________一个人欣赏-最后一朵颜色的消逝-忠诚于我的是·一颗叫做野的心.决不受人奴役.怒火中生的那一刻·终将结束...
  • 相关阅读:
    eXtremeDB 简单开发
    MFC PostMessage SendMessage
    char string 区别
    div 水平垂直居中
    npm—小记
    ECharts简单运行例子
    HTML在表格中添加echarts图表
    Sublime Text 3配置JavaScript运行环境
    bjdctf_2020_YDSneedGrirlfriend
    wdb_2018_2nd_easyfmt
  • 原文地址:https://www.cnblogs.com/tianxiaxuange/p/9894382.html
Copyright © 2011-2022 走看看