6

我无法让选择器正常工作。

我有这个 HTML:

<div.wrapper>
    <div.ui-controlgroup-controls>
        <form>
            <div.ui-btn></div>
        </form>
        <div.ui-btn></div>
        <div.ui-btn></div>
        <div.ui-btn></div>
        <div.ui-btn></div>
    </div>
</div>

我正在尝试选择div标签,它们是ui-controlgroup-controls- 这意味着排除表单内的内容。

这就是我正在尝试的:

// el is my div.wrapper element
el.children[0].getElementsByTagName("div");

但是这不起作用,因为表单内的 div 最终出现在选择中。

问题
当我不想使用 jQuery 时,如何正确选择元素?

4

4 回答 4

5

一种方法是遍历生成的节点列表并检查父节点:

var nodes = el.children[0].getElementsByTagName("div");
nodes = Array.prototype.slice.call(nodes);
nodes = nodes.filter(function(v, i){
    return v.parentElement === el.children[0]; 
});

这是这种方法的演示:http: //jsfiddle.net/WLhY2/

一种更简单(尽管效率较低)的方法是使用querySelectorAll选择器表达式来检索相关节点:

var divs = document.querySelectorAll('div.ui-controlgroup-controls > div')
于 2013-04-01T20:08:57.397 回答
2

对于支持querySelectorAll的浏览器:

var divs = el.children[0].querySelectorAll("div");

对于支持在 NodeList 上使用slice的浏览器(例如不是 IE,至少不是 IE < 9):

var slice = Function.call.bind(Array.prototype.slice);

var divs = slice(el.children[0].children).filter(function(node) { 
               return node.tagName === "DIV"
           });

对于不支持的浏览器:

var nodes = el.children[0].children;
var divs = [];

for (var l = nodes.length, node; node = nodes[--l];) {
  if (node.tagName === "DIV")
    divs.push(node);
}
于 2013-04-01T20:42:28.347 回答
1

在大多数浏览器中,您可以执行以下操作:

el.querySelectorAll(".ui-controlgroup-controls > div")

".ui-controlgroup-controls"但是,如果您想避免更深的嵌套,这可能会产生误报。

如果是这种情况,只需迭代.children, 并构建嵌套 div 的集合。

var divs = [];

for (var i = 0, len = el.children.length; i < len; i++) {
    if (el.children[i].classname === "ui-controlgroup-controls") {
        for (var j = 0, lenj = el.children[i].children.length; j <, lenj; j++) {
            if (el.children[i].children[j].nodeName === "DIV") {
                divs.push(el.children[i].children[j])
            }
        }
    }
}

如果知道您只有一个ui-controlgroup-controls元素,那么您可以摆脱外部循环,只需使用children[0].

var divs = [];

for (var j = 0, lenj = el.children[0].children.length; j <, lenj; j++) 
    if (el.children[0].children[j].nodeName === "DIV") 
        divs.push(el.children[o].children[j])
于 2013-04-01T20:09:54.960 回答
1
<your-element>.querySelectorAll(":scope > div");

:scope是表示父元素的伪类。IE 中不支持,但有一个shim

于 2017-11-19T23:34:43.347 回答