如何在纯JS中的一行之后插入一组表行 [英] How to insert a a set of table rows after a row in pure JS

查看:81
本文介绍了如何在纯JS中的一行之后插入一组表行的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有以下问题:
我需要在行X之后插入N行。我需要插入的行组作为由TR元素组成的HTML块传递给我的函数。我也可以访问TR,之后我需要插入。

I have the following problem: I need to insert N rows after row X. The set of rows I need to insert is passed to my function as chunk of HTML consisting of TR elements. I also have access to the TR after which I need to insert.

与我之前做过的工作略有不同,在那里我用另一个TBODY替换TBODY。

This is slightly different then what I have done before where I was replacing TBODY with another TBODY.

我遇到的问题是 appendChild 需要一个元素,但我必须插入一个集合。

The problem I am having is that appendChild requires a single element, but I have to insert a set.

编辑

这是解决方案

function appendRows(node, html){ 
    var temp = document.createElement("div");
    var tbody = node.parentNode;
    var nextSib = node.nextSibling;

    temp.innerHTML = "<table><tbody>"+html;
    var rows = temp.firstChild.firstChild.childNodes;

    while(rows.length){
        tbody.insertBefore(rows[i], nextSib);
    }
} 






看到这个行动:


see this in action:

http:// programmingdrunk。 com / test.htm

推荐答案

if(node.nextSibling && node.nextSibling.nodeName.toLowerCase() === "tr")

?我不认为你需要它如果node.nextSibling为null,那没关系。您可以将其传递给insertBefore,它将与appendChild相同。

What's this for? I don't think you need it. If node.nextSibling is null, it doesn't matter. You can pass that to insertBefore and it will act the same as appendChild.

无论如何,tbody内部还没有其他元素允许。对于(var i = 0; i< rows.length; i ++){
tbody.insertBefore(rows [i],node)的

And there's no other element allowed inside a tbody than ‘tr’ anyway.

for(var i = 0; i < rows.length; i++){
    tbody.insertBefore(rows[i], node.nextSibling);

这对于多行不起作用。一旦你完成了一个insertBefore,node.nextSibling现在将指向你刚插入的行;你最终将以相反的顺序插入所有行。您将需要记住原来的nextSibling。

This won't work for multiple rows. Once you've done one insertBefore, node.nextSibling will now point to the row you just inserted; you'll end up inserting all your rows in reverse order. You'll need to remember the original nextSibling.

ETA:加上,如果'rows'是一个活的DOM NodeList,每次将一行插入到新的身体,它从旧身体去除它!因此,当您重复列表时,您正在摧毁该列表。这是每一个其他错误的常见原因:您处理列表中的项目0,并将其从列表中移除,将项目1移动到项目0的位置。接下来,您可以访问新的项目1,它是原始项目2,原始项目1从未被看到。

ETA: plus, if ‘rows’ is a live DOM NodeList, every time you insert one of the rows into the new body, it removes it from the old body! Thus, you are destroying the list as you iterate over it. This is a common cause of ‘every other one’ errors: you process item 0 of the list, and in doing so remove it from the list, moving item 1 down into where item 0 was. Next you access the new item 1, which is the original item 2, and the original item 1 never gets seen.

-live'Array',或者如果你知道它将是一个实时列表,你可以使用一个更简单的循环形式:

Either make a copy of the list in a normal non-live ‘Array’, or, if you know it's going to be a live list, you can actually use a simpler form of loop:

var parent= node.parentNode;
var next= node.nextSibling;
while (rows.length!=0)
    parent.insertBefore(rows[0], next);




我必须插入一个。

i have to insert a set.

通常当您考虑一次插入一组元素时,您想要使用DocumentFragment。但是,不幸的是,您无法在DocumentFragment上设置'innerHTML',因此您必须在上面的表上设置行,然后将它们逐个移动到DocumentFragment中,然后在documentFragment之前插入。虽然这可能理论上比追加到最终目标表(由于较少的孩子节点列表冲击)更快,但在实际中,我的测试实际上并不可靠地显着加快。

Usually when you think about inserting a set of elements at once, you want to be using a DocumentFragment. However, unfortunately, you can't set ‘innerHTML’ on a DocumentFragment, so you'd have to set the rows on a table like above, then move them one by one into a DocumentFragment, then insertBefore the documentFragment. Whilst this could theoretically be faster than appending into the final target table (due to less childNodes list-bashing), in practice by my testing it isn't actually reliably significantly faster.

另一种方法是insertAdjacentHTML,一个IE只是扩展方法。您不能在tbody的孩子上调用insertAdjacentHTML,不幸的是,由于IE错误,您无法设置tbody.innerHTML的相同方式。您可以将其设置为DocumentFragment:

Another approach is insertAdjacentHTML, an IE only extension method. You can't call insertAdjacentHTML on the child of a tbody, unfortunately, in the same way as you can't set tbody.innerHTML due to the IE bug. You can set it inside a DocumentFragment:

var frag= document.createDocumentFragment();
var div= document.createElement(div);
frag.appendChild(div);
div.insertAdjacentHTML('afterEnd', html);
frag.removeChild(div);
node.parentNode.insertBefore(frag, node.nextSibling);

不幸的是,不知何故insertAdjacentHTML在这个上下文中工作非常慢,有些神秘的原因。对于我来说,上述方法大约是一个接一个插入的速度的一半。 : - (

Unfortunately, somehow insertAdjacentHTML works very slowly in this context for some mysterious reason. The above method is about half the speed of the one-by-one insertBefore for me. :-(

这篇关于如何在纯JS中的一行之后插入一组表行的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆