是否可以将元素附加到 JavaScript nodeList?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/20075234/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-27 17:38:23  来源:igfitidea点击:

Is it possible to append an element to a JavaScript nodeList?

javascriptarraysappendnodelist

提问by frequent

I'm generating content dynamically, so I'm often ending up with documentFragmentswhich I'm querying using querySelectorAllor querySelectorreturning a nodeListof elements inside my documentFragment.

我是动态生成内容的,所以我经常会在我的文档documentFragments片段中使用querySelectorAllquerySelector返回nodeList元素进行查询。

From time to time I would like to add an item to a list, but I can't find anything online on whether this is even possible.

有时我想将一个项目添加到列表中,但我在网上找不到任何关于这是否可行的信息。

I tried it like this:

我是这样试的:

 document.querySelectorAll(".translate").item(length+1) = document.createElement("div");

and this:

还有这个:

 document.querySelectorAll(".translate").shift(document.createElement("div"));

But both don't work (as expected)

但两者都不起作用(如预期)

Question:
Is it possible to manually add elements to a NodeList? I guess, not but asking nevertheless.

问题:
是否可以手动向 NodeList 添加元素?我想,不是,但还是要问。

Thanks for some insights?

感谢您提供一些见解?

EDIT:
So more info: I'm generating a block of dynamic content, which I want to append to my page. By default the block is in English. Since the user is viewing the page in Chinese, I'm running a translator on the dynamic fragment, BEFORE appending it to the DOM. On my page, I also have an element, say a title, which should change depending on the dynamic content being added. My idea was to do this in one step = try to add an element to my nodeList. But from writing it now... I guess not possible :-)

编辑
更多信息:我正在生成一个动态内容块,我想将其附加到我的页面。默认情况下,块是英文的。由于用户正在查看中文页面,因此在将动态片段附加到 DOM 之前,我正在对动态片段运行翻译器。在我的页面上,我还有一个元素,比如标题,它应该根据添加的动态内容而改变。我的想法是在一个步骤中完成此操作 = 尝试向我的nodeList. 但是从现在开始写......我想不可能:-)

回答by Tibos

EDIT: As @Sniffer mentioned, NodeLists are read-only (both the length property and the items). You can manipulate everything else about them, like shown below, but it's probably better to convert them to arrays instead if you want to manipulate them.

编辑:正如@Sniffer 提到的,NodeLists 是只读的(长度属性和项目)。您可以操作关于它们的所有其他内容,如下所示,但如果您想操作它们,最好将它们转换为数组。

var list = document.querySelectorAll('div');
var spans = document.querySelectorAll('span');

push(list, spans);
forEach(list, console.log); // all divs and spans on the page

function push(list, items) {  
  Array.prototype.push.apply(list, items);
  list.length_ = list.length;
  list.length_ += items.length;
}

function forEach(list, callback) {
  for (var i=0; i<list.length_; i++) {
    callback(list[i]);
  }
}

It would probably be a better idea to turn the NodeList to an array instead (list = Array.prototype.slice(list)).

将 NodeList 改为数组可能是一个更好的主意 ( list = Array.prototype.slice(list))。

var list = Array.prototype.slice.call(document.querySelectorAll('div'));
var spans = Array.prototype.slice.call(document.querySelectorAll('span'));

list.push.apply(list, spans);
console.log(list); // array with all divs and spans on page

回答by Ibrahim Najjar

Unlike previously described element selection methods, the NodeList returned by querySelectorAll()is not live: it holds the elements that match the selector at the time the method was invoked, but it does not update as the document changes. [1]

与之前描述的元素选择方法不同,querySelectorAll() 返回的 NodeList 不是实时的:它保存在调用方法时与选择器匹配的元素,但不会随着文档的变化而更新。[1]

The NodeListin this case is not alive, so if you add/remove anything to/from it, then it won't have any effect on the document structure.

NodeList这种情况下是不是活的,所以如果你添加/删除任何东西,从它/,那么它将不会对文档的结构没有任何影响。

A NodeList is a read-only array-like object. [1]

NodeList 是一个只读的类似数组的对象。[1]

[1]:JavaScript: The Definitive Guid, David Flanagan

[1]:JavaScript:权威指南,大卫·弗拉纳根

回答by Amir Fo

I have another suggestion. You can select multiple nodes by query seperator(,):

我还有一个建议。您可以通过查询分隔符( ,)选择多个节点:

var nodes = document.querySelectorAll('h2, h3');

This code selects all h2and h3saved in nodes.

此代码选择全部h2h3保存在nodes.

回答by Dmitry Shashurov

Use ES6 Set():

使用 ES6 Set():

var elems = new Set([
    ...document.querySelectorAll(query1),
    ...document.querySelectorAll(query2)
]);

回答by flodis

To not get into technicalities with array methods it can sometimes be more readable to make a list of node names and loop over the list.

为了不涉及数组方法的技术问题,有时可以制作一个节点名称列表并遍历该列表更具可读性。

In this example I assign the same event handler to all buttons in two different radio button groups (where each button in the group has the same name):

在这个例子中,我为两个不同单选按钮组中的所有按钮分配了相同的事件处理程序(组中的每个按钮都具有相同的名称):

<div>
    <input type="radio" name="acmode" value="1" checked="checked">Phase<br>
    <input type="radio" name="acmode" value="2">Ssr<br>
    <input type="radio" name="acmode" value="3">Relay<br>
</div>
<div>
    <input type="radio" name="powermode" value="0"  checked="checked">Manual<br>
    <input type="radio" name="powermode" value="1">Automatic<br>
</div> 

Sample event handler:

示例事件处理程序:

var evtRbtnHandler =
    function rbtnHandler() {
        document.getElementById("response11").innerHTML = this.name + ": " + this.value;
    }

And assigning:

并分配:

var buttongroup = ["acmode", "powermode"];
buttongroup.forEach(function (name) {
    document.getElementsByName(name).forEach(function (elem) {
        elem.onclick = evtRbtnHandler;
    });
});

In any case once you get your hands on each single item it can be pushed() to an array using human readable code.

在任何情况下,一旦您掌握了每个项目,就可以使用人类可读的代码将其 push() 到一个数组中。