如何監聽 DOM 變化

前言

在MVVM框架中,一是監聽數據變化,數據驅動。html

  • 咱們都知道經過Object.defineProperties(),來監聽數據的變化,或者使用,代理和反射。
  • 其實在MVVM中,也有操做DOM的場景。那麼,咱們是經過哪些API來監聽DOM的變化的呢?

當咱們,經過JS操做了DOM以後,咱們須要通知到DOM來更新視圖。在VUE中,是維護了一個異步的隊列。並非你修改了DOM就會直接更新到視圖上面。數組

監聽DOM變化的方法:

  • 輪詢
  • MutationEvents(基本已廢棄)
  • CSS 動畫

以上三種都不是很好的方法。那麼,咱們今天來介紹一下,如今比較經常使用的:瀏覽器

  • MutationObserver

咱們選擇Mutation Observer

概述

Mutation Observer API 用來監視 DOM 變更。DOM 的任何變更,好比節點的增減、屬性的變更、文本內容的變更,這個 API 均可以獲得通知。 Mutation Observer 則是異步觸發,DOM 的變更並不會立刻觸發,而是要等到當前全部 DOM 操做都結束才觸發。 這樣設計是爲了應付 DOM變更頻繁的特色。app

舉例來講,若是文檔中連續插入1000個li元素,就會連續觸發1000個插入事件,執行每一個事件的回調函數,這極可能形成瀏覽器的卡頓;而 Mutation Observer 徹底不一樣,只在 1000 個段落都插入結束後纔會觸發,並且只觸發一次。框架

Mutation Observer有如下特色:

  • 等待全部腳本任務完成後,纔會運行,即採用異步方式
  • 把 DOM 變更記錄封裝成一個數組進行處理,而不是一條條地個別處理 DOM 變更
  • 便可以觀察發生在 DOM 節點的全部變更,也能夠觀察某一類變更

使用

var observe = new MutationObserver(function(mutations, observer){
});
var el = document.querySelector('#app');
var  options = {
  'childList': true,
  'attributes':true
} ;
observer.observe(el, options);
// 建立並返回一個 MutationObserver 實例, 並偵聽el元素的變更。
複製代碼

小例子

MutationObserver的callback回調函數是異步的,只有在所有DOM操做完成以後纔會調用callback。異步

<div id='target' class='block' name='target'>
    target的第一個子節點
    <p>
       <span>target的後代</span>
    </p>
</div>

複製代碼
var target=document.getElementById('target');
var i=0
var observe=new MutationObserver(function (mutations,observe) {
    i++   
});
observe.observe(target,{ childList: true});
target.appendChild(docuemnt.createTextNode('1'));
target.appendChild(docuemnt.createTextNode('2'));
target.appendChild(docuemnt.createTextNode('3'));
console.log(i)  //1 callback的回調次數

複製代碼

應用

在不少狀況下,MutationObserver API 均可以派上用場。例如:函數

  • 你但願通知 Web 應用程序訪問者,他當前所在的頁面發生了一些更改。
  • 你正在開發一個新的 JavaScript 框架,須要根據 DOM 的變化動態加載 JavaScript 模塊。

總結

  • MutationObserver接口提供了監視對DOM樹所作更改的能力。它被設計爲舊的Mutation Events功能的替代品,該功能是DOM3 Events規範的一部分。(MDN)
  • DOM MutationObserver,在不影響瀏覽器性能的狀況下響應DOM更改
  • 等待全部腳本任務完成後,纔會運行,即採用異步方式
相關文章
相關標籤/搜索