[英]Remove element nodes in post-order traversal
說我有以下HTML(濃縮):
<div><div><div><ul><li>Text</li></ul></div></div></div>
<div><div><div><ul><li>Text 2</li></ul></div></div></div>
<div><div><div><ul><li>Text 3</li></ul></div></div></div>
我想首先刪除最低的子元素,直到最終刪除父元素,然后轉到下一個父元素及其子元素。 這可以通過一個簡單的循環輕松完成,該循環遍歷每個子元素,刪除它,然后刪除下一個子元素(即前一個子元素的父元素):
var children = $("body").find("*");
var i = children.length;
function loop() {
$(children[i]).remove();
i--;
if (i > -1) {
setTimeout(loop, 20);
}
}
loop();
但問題是,它首先從最低的父元素中刪除子元素。 如果您使用我的測試標記運行此代碼 ,您可以看到我的意思。
我想從最頂層的父節點中刪除子元素,然后向下工作,從而顛倒上述代碼的順序。 我能用以下代碼完成此操作 :
var parents = $("body").children(":not(:empty)");
var i = 0;
var speed = 1000;
function loop() {
var children = $(parents[i]).find("*");
var x = children.length;
function inside() {
$(children[x]).remove();
x--;
if (x > -1) {
setTimeout(inside, speed);
} else if (i < parents.length) {
$(parents[i - 1]).remove();
loop();
} else if (i === parents.length) {
$(parents[i - 1]).remove();
}
}
inside();
i++;
}
loop();
但是,此代碼的問題在於它只反轉了相對於父元素的刪除順序。 如果父項中有多個子元素,它仍將按默認升序(從下到上)刪除它們 。
因此,我的問題是,如何以更清晰的方式刪除所有元素,無論有多少子元素,都按降序刪除? 必須有比我嘗試的更好的方法。 jQuery也不是必需的。 setTimeout
的原因是因為我需要在刪除元素之間有一個延遲。 像往常一樣,我可能忽略了一些相對簡單的事情,所以請耐心等待。
重申一下,如果HTML看起來像這樣:
<div>
<div>Child 1</div>
<div>Child 2</div>
<div>
<div>Child 3</div>
<div>Child 4</div>
</div>
</div>
我希望它按以下順序刪除:
偽代碼中的算法思想:
RemoveNode( node) {
for(i=node.children.length-1;i>=0;i--){
RemoveNode(node.children[i]);
}
remove(self);
return;
}
根據偽代碼添加了實際代碼:
function RemoveNode(node){
for(var i = node.children.length - 1; i >= 0; i--){
RemoveNode(node.children[i]);
}
$(node).remove();
}
帶有中斷的偽代碼,看看算法是如何工作的。 不知道為什么,但我不能讓它延遲工作。
function RemoveNode(node){
for(var i = node.children.length - 1; i >= 0; i--){
RemoveNode(node.children[i]);
alert("hi");
}
$(node).remove();
}
RemoveNode($(".parent")[0]);
首先使用以下遞歸函數構建DOM樹的后序(aka child first)版本:
var nodes = [];
function generate()
{
$(this).children().each(generate);
nodes.push(this);
}
generate.call($('body'));
然后,按正常方式迭代:
var i = 0;
function loop()
{
$(nodes[i]).remove();
if (++i < nodes.length) {
setTimeout(loop, 1000);
}
}
loop();
我認為這樣做你想要的:
removeLast();
function removeLast(){
var o = document.getElementById("root"), p = o;
while (p.lastChild) p = p.lastChild;
p.parentNode.removeChild(p);
if(o != p) setTimeout(removeLast,20);
}
我不確定我完全理解這個問題,但也許這就是你要找的東西?
演示: http : //jsfiddle.net/xT3Au/1/
var $parents = $('.parent');
$parents.each(function(i) {
var $tree = $(this).find('*').addBack();
$tree.sort(function(a, b) {
return $(a).find('*').length - $(b).find('*').length;
}).each(function(j, el) {
var speed = 1000 * (j + 1 + i * $tree.length);
setTimeout(function(){ $(el).remove() }, speed);
});
});
我認為使用類來了解哪些父母應該遵循哪種順序會更容易。 否則很難弄清楚訂單。 如果我弄錯了,請嘗試使用排序功能。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.