如何在JavaScript中只删除父元素,而不是它的子元素?
我们说:
<div> some text <div class="remove-just-this"> <p>foo</p> <p>bar</p> some text node here </div> some text </div>
对此:
<div> some text <p>foo</p> <p>bar</p> some text node here some text </div>
我一直在找出使用Mootools,jQuery甚至(原始)JavaScript,但不知道如何做到这一点。
使用jQuery,你可以这样做:
var cnt = $(".remove-just-this").contents(); $(".remove-just-this").replaceWith(cnt);
快速链接到文档:
- 内容 (): jQuery
- replaceWith ( content :[ String | Element | jQuery ]): jQuery
独立于库的方法是在删除元素之前,先将要删除的元素的所有子节点(隐式地从旧元素中删除它们)插入:
while (nodeToBeRemoved.firstChild) { nodeToBeRemoved.parentNode.insertBefore(nodeToBeRemoved.firstChild, nodeToBeRemoved); } nodeToBeRemoved.parentNode.removeChild(nodeToBeRemoved);
这将以正确的顺序将所有子节点移动到正确的位置。
您应该确保使用DOM而不是innerHTML(如果使用由jk提供的jQuery解决scheme,请确保它移动DOM节点,而不是在内部使用innerHTML),以便保留事件处理程序之类的内容。
我的答案很像insin's,但是对于大型结构会更好(单独附加每个节点可能需要在每个appendChild重新应用CSS时重新征税);对于DocumentFragment,这只会发生一次,因为直到在它的孩子都被附加后,它被添加到文档中)。
var fragment = document.createDocumentFragment(); while(element.firstChild) { fragment.appendChild(element.firstChild); } element.parentNode.replaceChild(fragment, element);
$('.remove-just-this > *').unwrap()
更优雅的方式是
$('.remove-just-this').contents().unwrap();
无论您使用的是哪个库,都必须在从DOM中除去外部div之前克隆内部div。 然后,你必须将克隆的内部div添加到DOM中外部div所在的位置。 所以步骤是:
- 在外部variables中保存对外部div的引用
- 将内部div复制到另一个variables。 这可以通过将内部div的
innerHTML
保存为variables来以快速且肮脏的方式完成,或者可以逐个节点地recursion地复制内部树。 - 以外部div作为参数,调用外部div的父级上的
removeChild
。 - 将复制的内容插入到正确位置的外部div的父项。
有些图书馆会为你做一些或全部的工作,但是像上面这样的内容将会在后台进行。
而且,既然你也尝试过使用mootools,下面是mootools的解决scheme。
var children = $('remove-just-this').getChildren(); children.replaces($('remove-just-this');
请注意,这是完全没有经过testing的,但我以前使用过mootools,它应该工作。
http://mootools.net/docs/Element/Element#Element:getChildren
使用现代的JS!
const node = document.getElementsByClassName('.remove-just-this')[0]; node.replaceWith(...node.childNodes); // or node.children, if you don't want textNodes
oldNode.replaceWith(newNode)
是有效的ES5
...array
是传播运算符,传递每个数组元素作为参数
如果你想用睡衣做同样的事情,那么就是这样做的。 它很好(谢谢眼睑)。 我已经能够做出适当的丰富的文本编辑器,正确地做风格,而不会搞砸,感谢这一点。
def remove_node(doc, element): """ removes a specific node, adding its children in its place """ fragment = doc.createDocumentFragment() while element.firstChild: fragment.appendChild(element.firstChild) parent = element.parentNode parent.insertBefore(fragment, element) parent.removeChild(element)
在处理重要的DOM时,我一直在寻找性能最佳的答案。
无睑的答案指出,使用JavaScript的performance将是最好的。
我已经做了5000行以上的执行时间testing,并在要删除的部分内使用了复杂的DOM组合。 使用JavaScript时,为了方便,我使用的是ID而不是类。
使用$ .unwrap()
$('#remove-just-this').contents().unwrap();
201.237ms
使用$ .replaceWith()
var cnt = $("#remove-just-this").contents(); $("#remove-just-this").replaceWith(cnt);
156.983ms
在JavaScript中使用DocumentFragment
var element = document.getElementById('remove-just-this'); var fragment = document.createDocumentFragment(); while(element.firstChild) { fragment.appendChild(element.firstChild); } element.parentNode.replaceChild(fragment, element);
147.211ms
结论
在性能方面,即使在相对较大的DOM结构上,使用jQuery和JavaScript的差异也不是很大。 令人惊讶的$.unwrap()
是最昂贵的$.replaceWith()
。 testing已经用jQuery 1.12.4完成了。
如果你正在处理多行,就像在我的用例中那样,你可能会更好地使用这些行:
$(".card_row").each(function(){ var cnt = $(this).contents(); $(this).replaceWith(cnt); });