6

Imagine I have the following code:

...
<div id="div1">
    <div id="div2">Original div2</div>
</div>

<div id="div3"></div>

...

if I run

$('#div1').html('');
$('#div3').html('<div id="div2">New div2</div>');

do I end up with problems because I didn't use .remove() to remove #div2 from the dom, or does clearing the html in this way do that for me?

What if div2 contained some javascript that attached a handler, say something like

$('#div2').on('click',function() { ... });

would that also be removed, or would I need to off() it?

Kevin B
  • 94,570
  • 16
  • 163
  • 180
Ben Holness
  • 2,457
  • 3
  • 28
  • 49
  • Overwriting HTML using `.html('')` will work. But any event handlers attached to the original `
    ` will be removed with the DOM node. So you will have to use a delegated event handler or bind the event handler to the new DOM node when you make the HTML change.
    – Jasper Apr 16 '13 at 18:44
  • You might have a problem with IE in some circumstances. This might be of interest: http://stackoverflow.com/questions/1462649/jquery-memory-leak-with-dom-removal – nullability Apr 16 '13 at 18:44
  • If the intent is to move `div2`, it'd be better to say `$('#div2').appendTo('#div3');`. Appending a node that's already in the document *moves* it to where you appended it, without destroying it or detaching the event handlers attached to it. You could say `$('#div2').appendTo('#div3').html('New div2');` if you wanted to change the content as well. – cHao Apr 16 '13 at 18:50

4 Answers4

3

do I end up with problems because I didn't use .remove() to remove #div2 from the dom, or does clearing the html in this way do that for me?

No, jQuery will use .remove for you internally (technically it uses cleanData, but it performs the same cleanup.)

Events will be lost, so you'll have to rebind them.

Kevin B
  • 94,570
  • 16
  • 163
  • 180
2

You should use $('#div1').empty(); rather than using $('#div1').html('') You can clone the element using $('#div3').html($('#div2').clone(true)); //this will carry over any data events attached to it.

If you are moving the elements to another container or another position you could just use append, prepend, before , after. Still all your data and events will be intact

See this:-

<div id="container1">Container
    <div id="div2">div2</div>
</div>
<div id="container2">cotainer2</div>

$('#div2').click(function () {
    alert('test')
});
$('#container2').append($('#div2'));//Clicking on div2 will still alert.
PSL
  • 123,204
  • 21
  • 253
  • 243
  • 1
    Yes but he is emptying div1 not div3 – PSL Apr 16 '13 at 18:46
  • Also I am interested specifically in html(). Imagine if the code was $('#div1').html('this is some text') then I wanted to know if div2 was removed from the dom and whether I could safely add another div with an id of div2 – Ben Holness Apr 16 '13 at 22:26
  • Yes, Div2 wil be removed from DOM once you do $('#div1').html('this is some text') – PSL Apr 16 '13 at 22:38
2

As your Event's will be lost you can use .on() like this , so you don't need to rebind event's

$(document).on('click','#div2',function() { ... });
Adil Shaikh
  • 44,509
  • 17
  • 89
  • 111
2

You should be ok using html() as above. Be careful in IE9< though. From the jquery docs:

Note: In Internet Explorer up to and including version 9, setting the text content of an HTML element may corrupt the text nodes of its children that are being removed from the document as a result of the operation. If you are keeping references to these DOM elements and need them to be unchanged, use .empty().html(string) instead of .html(string) so that the elements are removed from the document before the new string is assigned to the element.

If you want to keep the listeners, you should use delegated event listening. See the docs for on():

<div id="wrapper">
    <div id="div1">
        <div id="div2">Original div2</div>
    </div>

    <div id="div3"></div>
</div>

$('#wrapper').on('click', '#div2', function() {...});

cfs
  • 10,610
  • 3
  • 30
  • 43