18

我正在动态生成内容,因此我经常documentFragments使用querySelectorAllquerySelector返回nodeList我的 documentFragment 中的一个元素进行查询。

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

我试过这样:

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

和这个:

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

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

问题:
是否可以手动将元素添加到 NodeList?我想,不是,而是问。

感谢您的一些见解?

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

4

5 回答 5

22

编辑:正如@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]);
  }
}

将 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
于 2013-11-19T15:30:08.830 回答
12

我还有一个建议。您可以通过查询分隔符 ( ,) 选择多个节点,此代码将保存节点变量中保存的所有 h2 和 h3 标签:

var nodes = document.querySelectorAll('h2, h3');
于 2018-08-26T14:58:21.660 回答
7

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]

The NodeList in 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.

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

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

于 2013-11-19T15:18:04.977 回答
0

为了不涉及数组方法的技术细节,有时制作一个节点名称列表并在列表上循环可能更具可读性。

在此示例中,我将相同的事件处理程序分配给两个不同单选按钮组中的所有按钮(其中组中的每个按钮具有相同的名称):

<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> 

示例事件处理程序:

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

并分配:

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

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

于 2018-02-10T02:26:15.097 回答
0

使用 ES6 设置():

var elems = new Set([
    ...document.querySelectorAll(query1),
    ...document.querySelectorAll(query2)
]);
于 2020-04-16T08:16:22.457 回答