突变观察者未检测到文本变化

Posted

技术标签:

【中文标题】突变观察者未检测到文本变化【英文标题】:Mutation Observer Not Detecting Text Change 【发布时间】:2017-03-04 21:05:29 【问题描述】:

我对为什么 MutationObserver 没有检测到使用 textContent 完成的文本更改感到头疼。

html

<div id="mainContainer">
  <h1>Heading</h1>
  <p>Paragraph.</p>
</div>

javascript

function mutate(mutations) 
  mutations.forEach(function(mutation) 
    alert(mutation.type);
  );


jQuery(document).ready(function() 
  setTimeout(function() 
    document.querySelector('div#mainContainer > p').textContent = 'Some other text.';
  , 2000);

  var target = document.querySelector('div#mainContainer > p')
  var observer = new MutationObserver( mutate );
  var config =  characterData: true, attributes: false, childList: false, subtree: true ;

  observer.observe(target, config);
);

在上面的脚本中,段落元素的文本内容发生了明显的变化,但 MutationObserver 没有检测到。

但是,如果您将 textContent 更改为 innerHTML,则会提醒您“characterData”已更改。

为什么 MutationObserver 检测到 innerHTML 而不是 textContent?

这里是 JS 小提琴:

https://jsfiddle.net/0vp8t8x7/

请注意,只有将 textContent 更改为 innerHTML 时,您才会收到警报。

【问题讨论】:

【参考方案1】:

这是因为textContent 触发的change 与innerHTML 不同,并且您的观察者配置未配置为观察textContent 所做的更改。

textContent 更改目标的子文本节点。根据MDN设置textContent

在节点上设置此属性会删除其所有子节点,并且 将它们替换为具有给定值的单个文本节点。

innerHTML 改变了元素本身,它是子树。

所以要捕获innerHTML,您的配置应该是:

var config =  characterData: true, attributes: false, childList: false, subtree: true ;

同时捕捉textContent使用:

var config =  characterData: false, attributes: false, childList: true, subtree: false ;

演示:

function mutate(mutations) 
  mutations.forEach(function(mutation) 
    alert(mutation.type);
  );


  setTimeout(function() 
    document.querySelector('div#mainContainer > p').textContent = 'some other text.';
  , 1000);
  
  var target = document.querySelector('div#mainContainer > p')
  var observer = new MutationObserver( mutate );
  var config =  characterData: false, attributes: false, childList: true, subtree: false ;

  observer.observe(target, config);
<div id="mainContainer">
  <h1>Heading</h1>
  <p>Paragraph.</p>
</div>

【讨论】:

我假设使用 textContent 更改文本不会触发突变观察者回调,但在 Firefox 中它会触发观察者回调,而在 chrome 上则不会。你能分享一下为什么会这样吗?

以上是关于突变观察者未检测到文本变化的主要内容,如果未能解决你的问题,请参考以下文章

突变观察者未定义

如何使用突变观察者?

MutationObserver 无法观察 textarea

观察 NSArrayController 变化:检测插入或删除

观察 UIDatePicker 的变化

设计模式观察者模式