I have this piece of code
// TR Fading when deleted
$('.delete').live('click', function() {
$.ajax({
type: 'POST',
url: 'history/delete/id/'+$(this).attr('id')
});
$(this).closest('tr').fadeOut('slow', function() {
$(this).remove();
if($(this).closest('table').find('tbody').is(':empty'))
$('#latest').remove();
});
return false;
});
It triggers when I want to delete a table row through the delete button (as shows the image) image http://aviary.com/viewfull?fguid=433f68f6-d18d-102d-a9f3-0030488e168c&nowatermark=true
It may happen that the table becomes empty of table rows. I want to delete the whole table when this occurs, but the table isn't being removed. The line code $(this).remove();
works and this
seems to refer to the tr
element in that scope 'cause the whole row is being removed but the next 2 lines doesn't work. The table isn't being removed.
I changed the if($(this).closest('table').find('tbody').is(':empty'))
to if(!$(this).closest('table').find('tbody').is(':empty'))
(exclamation mark) to see if it removes and it removed the whole table, but I inspected the table element before and after deleting the last row and got this
image http://rookery9.aviary.com.s3.amazonaws.com/4344000/4344383_4fbd.png
JS says that tbody is not empty, google chrome says otherwise. I don't know how to fix it
It looks like remove()
and detach()
do leave some kind of crud behind after they remove a tr element. It's like a whitespace or a linebreak, so since the :empty
selector also checks for textnodes, it's not empty at all.
so
if($('#latest tbody').children().length() < 1)
$('#latest').remove();
should do the trick.
Reference: http://jsbin.com/esaye3/2/edit
update
Like Nick Craver mentioned, this behavior is caused by the HTML markup
itself.
<tbody><tr><td>Something</td><td>Anything?</td><td><button class="delete">delete</button></td></tr></tbody>
for instance, WILL work with :empty
aswell.
The problem is that once you remove it, relative selectors like .closest()
won't do anything, since that element doesn't have a parent anymore. Also :empty
isn't working because it includes text nodes, from the docs:
Select all elements that have no children (including text nodes).
So :empty
won't match if there's any white-space left (alert or log $("latest tbody").html())
to see what I mean), which is almost certainly the case, the same goes for my example below. Instead you can use :has(tr)
to check for table rows, and :not()
to negate that, like this:
$('.delete').live('click', function() {
$(this).closest('tr').fadeOut('slow', function() {
$(this).remove();
$("#latest tbody:not(:has(tr))").parent().remove();
});
return false;
});
You can view a quick demo here, if the :not(:has(tr))
selector doesn't match anything...and it won't if there's not a row-less <tbody>
, it just won't remove anything.