21

由于 DOM 突变被 w3c 标记为已弃用(请参阅http://www.w3.org/TR/DOM-Level-3-Events/#events-mutationevents),是否有(快速)替代方法来检测属性修改在 DOM 中?

4

4 回答 4

31

突变事件被弃用的原因是因为巨大的性能问题。

替代品是Mutation Observers,请查看http://updates.html5rocks.com/2012/02/Detect-DOM-changes-with-Mutation-Observershttps://developer.mozilla.org/en/DOM/DOM_Mutation_Observers

有关突变的信息作为 MutationRecords 的有序序列传递给观察者,代表观察到的已发生变化的序列

示例用法:

    var observer = new MutationObserver(function(mutationRecords) {
    // Handle mutations
     });

    observer.observe(myNode,
     {  // options:
     subtree: true,  // observe the subtree rooted at myNode
     childList: true,  // include information childNode insertion/removals
     attribute: true  // include information about changes to attributes within the subtree
    });

这在 Chrome 18 和 Firefox 和 Webkit nightly build 中受支持。Firefox 14 也将支持此功能。

于 2012-06-19T17:16:07.873 回答
13

与 CSS Animations 结合使用可以很好地替代已弃用的 DOM* 事件animationStart大卫沃尔什写了关于这种方法的文章。

首先,设置关键帧并将其应用于您想要监听的元素(不要忘记供应商前缀!):

@keyframes nodeInserted {  
  from { clip: rect(1px, auto, auto, auto); }
  to { clip: rect(0px, auto, auto, auto); }  
}

#parentElement > li {
  animation-duration: 0.001s;
  animation-name: nodeInserted;
}

接下来,添加监听器:

var insertListener = function(event){
  if (event.animationName == "nodeInserted") {
    // This is the debug for knowing our listener worked!
    // event.target is the new node!
    console.warn("Another node has been inserted! ", event, event.target);
  }
}
document.addEventListener("animationstart", insertListener, false); // standard + firefox
document.addEventListener("MSAnimationStart", insertListener, false); // IE
document.addEventListener("webkitAnimationStart", insertListener, false); // Chrome + Safari

达达!这是大卫的演示它在将 Facebook 图片添加到 Google Voice的 Chrome 扩展程序上非常适合我(请参阅 content.css 和注入的.js)。

于 2012-12-12T08:07:38.917 回答
12

一年后,DOM Level 4 出现了新的和闪亮Mutation Observers的(点击那里的链接,他们解释了很多!)。在一个Mutation Event被触发一千次的地方,MutationObserver只触发一次,所有的修改都包含并且可以访问。

适用于(截至 2017/03):

  • 火狐 14+
  • 即 11
  • 边缘
  • 歌剧 15+
  • Chrome 26+(18 到 25 前缀,window.WebKitMutationObserver
  • Safari 6.0 (前缀, window.WebKitMutationObserver)
于 2012-06-25T23:31:27.717 回答
7

据我所知,(还)没有其他选择,所以您只能坚持使用DOMAttrModified仅在 Firefox 和 Opera 中受支持的选项。在 IE 中,您有onpropertychanged事件,但无法在 Chrome/Safari 中获得类似的功能。根据您要完成的任务和目标浏览器,您可以做很多事情:

  • 为要监控的属性定义 getter 和 setter
  • 覆盖方法,如document.createAttribute, attributes.setNamedItem, ...

我自己一直在研究跨浏览器解决方案,但没有取得多大成功。您应该远离突变事件,因为它们不是跨浏览器并且非常慢。不推荐使用它们有充分的理由。如果您想了解更多信息,请阅读以下内容:

于 2011-04-05T15:42:29.683 回答