5

When we try to add nested nodes in DOM using appendChild or innerHTML, the nested nodes do not come in the addedNodes of a mutation.

Initial HTML setUp:

<html> <body> <div id="container"> </div> </body> </html> 

Here is my Mutation Observer code:

var observer = new MutationObserver(function(mutations) { for (var i = 0; i < mutations.length; i++) { var mutation = mutations[i]; switch(mutation.type) { case 'childList': console.log(mutation.addedNodes); break; default: } } }); observer.observe(document, { childList: true, subtree: true, attributes: true, characterData: true }); 

If I now do appendChild with a nested img node in a div,

var img = document.createElement('img'); img.setAttribute("src", "http://img.zohostatic.com/discussions/v1/images/defaultPhoto.png"); var div = document.createElement('div'); div.appendChild(img); var container = document.getElementById("container"); container.appendChild(div); 

The Mutation Observer only logs the div which is appended to the container, but does not log the img as an addedNode in mutation.

Here is a working JSFiddle: https://jsfiddle.net/aedhefhn/

Is there a workaround for this?

1 Answer 1

5

That is the expected behavior. The div was all that was appended, it just happened to have some children. You can certainly walk through its child nodes yourself from .addedNodes though. .addedNodes is just an array of nodes, so you can go through each item recursively to get all the children.

Sign up to request clarification or add additional context in comments.

6 Comments

I agree. But, if instead we have a DOM structure with <div> <img src=""></img> </div>, why does Mutation Observer has image in the addedNodes? Shouldn't it behave in the same way. Because, either programatically or not, the DOM looks the same
The objective of MutationObserver is to list mutation operations that were performed, not explicitly track everything that was added. Your observer is listening to the subtree of document. The only mutation performed on the document was appending div. When the image was appended to the div, the div wasn't attached, so there was no mutation observer attached to div at the time that would have picked up the append operation for the image.
I'm using MutationObserver in a summernote editing program, but it does not fire for cuts or pastes. For keyboard events it will fire. So for cuts and pastes, I'm polling the DOM to look for a change when a cut or paste occurs. It would be convenient to have an "after-paste-completed event", but as there is none, I hoped MutationObserver would catch that. Alas, no.
@DennisH Definitely surprised to hear that, got a reproduction? I'd definitely expect it to work in that case too
Just found out. Summernote is wrapping the whole document in a <p> tag for some reason. I just found out when I couldn't get a nodeList.forEach to see the change even when polling the DOM as a whole detected one. I have to remove that pesky <p> tag and it should be fine. It was working ok before. I'm trying to use multiple summernotes and changed from <div id='summernote'> to <div class='summernote active'> and I think that's when the trouble started...
|

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.