Question

I'm trying to use replaceWith(...) function with a jQuery Object but it does not work, when i try do it with inserted DOM elements it works, but not in jQuery objects.

I have this:

var obj = $('<div id="obj">Text</div>');
obj.replaceWith('<span>New text</span>');

"obj" is not replaced with the new HTML.

Here is the demo: http://jsfiddle.net/v7EA2/

Maybe i did not understand how replaceWith() function works,

Thanks by your help.


UPDATE

Please look at here: http://jsfiddle.net/v7EA2/6/

Was it helpful?

Solution 3

You can replace it before appending into the dom by the following code,

  var obj = $('<div>Text</div>').not('div').add('<span>New text</span>');

Theory : First you have to exclude the div from the intial Jquery object and then you have to add the new set of html into it.

DEMO

OTHER TIPS

It happens because your element does not have a parent. Append it to the DOM or to another jQuery collection and it will work.

I created a little demo that might help in understanding what this method does.

DETAILS:

I will sum up the research that is detailed in the comments below this answer. Thanks to PSL, calberts, Jason P and A. Wolff.

  1. The documentation of replaceWith states the following:

    As of jQuery 1.4, .replaceWith() can also work on disconnected DOM nodes. For example, with the following code, .replaceWith() returns a jQuery set containing only a paragraph.:

    $( "<div/>" ).replaceWith("<p></p>" );

  2. This means that the example provided by the OP should indeed work. And it works till version 1.8. Unfortunately, from version 1.9 it stops working. This seemed to be a bug and only happens if you are trying to replace the "root element" of the jQuery object.

  3. Actually the change in 1.9 was documented:

    Prior to 1.9, .after(), .before(), and .replaceWith() would attempt to add or change nodes in the current jQuery set if the first node in the set was not connected to a document, and in those cases return a new jQuery set rather than the original set. This created several inconsistencies and outright bugs--the method might or might not return a new result depending on its arguments! As of 1.9, these methods always return the original unmodified set and attempting to use .after(), .before(), or .replaceWith() on a node without a parent has no effect--that is, neither the set or the nodes it contains are changed.

    Problem is that the change never made it to the official docs. I found a bug posted about this, but it was closed because it belongs to a different tracker.


Quick Solution:

In the OP's situation, the easiest way to "replace" the element would be

var obj = $('<div id="obj">Text</div>');
obj = $('<span>New text</span>');

but only if it is not in the DOM yet :).

Jsfillde: http://jsfiddle.net/v7EA2/3/

first make the DOM available and then change the html using $.replaceWith

var obj = $('<div>Text</div>');
$('#result').text(obj[0].outerHTML);
$('#result').replaceWith('<span>Text</span>');
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top