有没有办法选择与任意选择器匹配(或不匹配)的每个第 n 个子项? 例如,我想选择每个奇数表行,但在行的子集中:
table.myClass tr.row:nth-child(odd) {
...
}
<table class="myClass">
<tr>
<td>Row
<tr class="row"> <!-- I want this -->
<td>Row
<tr class="row">
<td>Row
<tr class="row"> <!-- And this -->
<td>Row
</table>
但是:nth-child()
似乎只是计算了所有tr
元素,无论它们是否属于"row"类,所以我最终得到了一个甚至"row"元素,而不是我正在寻找的两个元素。同样的事情发生在:nth-of-type()
.
有人可以解释为什么吗?
非常普遍的问题,由于对:nth-child(An+B)
和:nth-of-type()
工作方式的误解而出现。
在选择器级别 3 中,伪类:nth-child()
将元素计入同一父级下的所有同级。它不仅计算与选择器其余部分匹配的同级
同样,伪类:nth-of-type()
计算共享相同元素类型的同级,该元素类型引用 HTML 中的标记名称,而不是选择器的其余部分。
这也意味着,如果同一父级的所有子元素都属于相同的元素类型,例如,表体的唯一子元素是tr
元素,或者列表元素的唯一子元素是li
元素,则 :nth-child()
和 :nth-of-type()
的行为将相同,即对于 An+B 的每个值, :nth-child(An+B)
和:nth-of-type(An+B)
将匹配同一组元素。
事实上,给定复合选择器中的所有简单选择器,包括伪类,如:nth-child()
和:not()
,彼此独立工作,而不是查看与选择器的其余部分匹配的元素子集。
这也意味着在每个单独的化合物选择器 1 中,简单选择器之间没有顺序的概念,这意味着例如以下两个选择器是等效的:
table.myClass tr.row:nth-child(odd)
table.myClass tr:nth-child(odd).row
翻译成英语,它们的意思都是:
选择与以下所有独立条件匹配的任何
tr
元素:
- 它是其父级的奇数子项;
- 它有类"行";和
- 它是具有类"myClass"的
table
元素的后代。
(你会注意到我在这里使用了一个无序列表,只是为了把重点带回家)
选择器级别 4 试图通过允许 :nth-child(An+B of S)
2 接受任意选择器参数 S 来纠正此限制,这也是由于选择器在复合选择器中如何独立运行,如现有选择器语法所示。所以在你的例子中,它看起来像这样:
table.myClass tr:nth-child(odd of .row)
当然,作为一个全新规范中的全新提案,这可能要到几年后才能实现。
同时,您必须使用脚本来过滤元素并相应地应用样式或额外的类名。例如,以下是使用 jQuery 的常见解决方法(假设表中只有一个行组填充了 tr
个元素):
$('table.myClass').each(function() {
// Note that, confusingly, jQuery's filter pseudos are 0-indexed
// while CSS :nth-child() is 1-indexed
$('tr.row:even').addClass('odd');
});
使用相应的 CSS:
table.myClass tr.row.odd {
...
}
如果您使用的是Selenium等自动化测试工具,或者使用BeautifulSoup等工具抓取HTML,则其中许多工具允许XPath作为替代方案:
//table[contains(concat(' ', @class, ' '), ' myClass ')]//tr[contains(concat(' ', @class, ' '), ' row ')][position() mod 2)=1]
使用不同技术的其他解决方案留给读者作为练习;这只是一个简短的、人为的例子,用于说明。
<小时 />1如果指定类型或通用选择器,则必须排在第一位。但是,这不会从根本上改变选择器的工作方式;这只不过是一种句法上的怪癖。
2这最初是作为:nth-match()
提出的,但是因为它仍然只计算相对于其兄弟姐妹的元素,而不是与给定选择器匹配的所有其他元素,因此自 2014 年起,它已被重新用作现有:nth-child()
的扩展。
不是真的。
引用自文档
伪类
:nth-child
匹配 具有 an+b-1 同级的元素 在文档树中之前,对于 给定 n 的正值或零值, 并具有父元素。
它是自己的选择器,不与类组合。在您的规则中,它只需要同时满足两个选择器,因此如果它们也恰好具有.row
类,它将显示:nth-child(even)
表行。
nth-of-type
根据相同类型元素的索引工作,但无论同级元素是什么类型的nth-child
都只能根据索引工作。
例如
<div class="one">...</div>
<div class="two">...</div>
<div class="three">...</div>
<div class="four">...</div>
<div class="five">...</div>
<div class="rest">...</div>
<div class="rest">...</div>
<div class="rest">...</div>
<div class="rest">...</div>
<div class="rest">...</div>
假设在上面的 html 中,我们想隐藏所有具有 rest 类的元素。
在这种情况下,nth-child
和nth-of-type
将完全相同,因为所有元素都属于相同的<div>
类型,因此 css 应该是
.rest:nth-child(6), .rest:nth-child(7), .rest:nth-child(8), .rest:nth-child(9), .rest:nth-child(10){
display:none;
}
或
.rest:nth-of-type(6), .rest:nth-of-type(7), .rest:nth-of-type(8), .rest:nth-of-type(9), .rest:nth-of-type(10){
display:none;
}
现在你一定想知道nth-child
和nth-of-type
有什么区别,所以这就是区别
假设 html 是
<div class="one">...</div>
<div class="two">...</div>
<div class="three">...</div>
<div class="four">...</div>
<div class="five">...</div>
<p class="rest">...</p>
<p class="rest">...</p>
<p class="rest">...</p>
<p class="rest">...</p>
<p class="rest">...</p>
在上面的html中,.rest
元素的类型与其他元素不同.rest
是段落,其他元素是div,所以在这种情况下,如果您使用nth-child
则必须这样写
.rest:nth-child(6), .rest:nth-child(7), .rest:nth-child(8), .rest:nth-child(9), .rest:nth-child(10){
display:none;
}
但是如果你使用第 n 种类型的 CSS 可以是这个
.rest:nth-of-type(1), .rest:nth-of-type(2), .rest:nth-of-type(3), .rest:nth-of-type(4), .rest:nth-of-type(5){
display:none;
}
由于
.rest
元素的类型是<p>
所以这里nth-of-type
正在检测.rest
的类型,然后他在<p>
的第 1、2、3、4、5 个元素上应用 css。
你可以用xpath做到这一点。 像//tr[contains(@class, 'row') and position() mod 2 = 0]
这样的东西可能会起作用。还有其他 SO 问题扩展了如何更精确地匹配类的细节。
这是你的答案
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>TEST</title>
<style>
.block {
background: #fc0;
margin-bottom: 10px;
padding: 10px;
}
/* .large > .large-item:nth-of-type(n+5) {
background: #f00;
} */
.large-item ~ .large-item ~ .large-item ~ .large-item ~ .large-item {
background: #f00;
}
</style>
</head>
<body>
<h1>Should be the 6th Hello Block that start red</h1>
<div class="small large">
<div class="block small-item">Hello block 1</div>
<div class="block small-item large-item">Hello block 2</div>
<div class="block small-item large-item">Hello block 3</div>
<div class="block small-item large-item">Hello block 4</div>
<div class="block small-item large-item">Hello block 5</div>
<div class="block small-item large-item">Hello block 6</div>
<div class="block small-item large-item">Hello block 7</div>
<div class="block small-item large-item">Hello block 8</div>
</div>
</body>
</html>
所有关于使用 nth 孩子和跳过隐藏标签的问题似乎都被重定向为这个问题的欺骗,所以我将把这个留在这里。我遇到了这个博客 https://blog.blackbam.at/2015/04/09/css-nth-child-selector-ignore-hidden-element/,它使用一种聪明的 css 方法让第 n 个孩子忽略隐藏元素,如下所示:
以下 CSS 为每秒钟可见元素添加一个边距,无论哪个元素具有 cpw 类。
.cpw {
display:none;
}
.video_prewrap {
margin-right:20px;
}
.video_prewrap:nth-child(2n) {
margin-right:0;
}
.cpw ~ .video_prewrap:nth-child(2n) {
margin-right:20px;
}
.cpw ~ .video_prewrap:nth-child(2n-1) {
margin-right:0;
}
希望可以帮助那些正在跟踪忽略隐藏元素问题的人!
如果所有选择器都有相同的父类,则使用该类document.querySelector("main .box-value:nth-child(3) select.priorityOption");
因为在这种情况下document.querySelector("main .box-value select.priorityOption:nth-child(3)");
不起作用。谢谢
<div class="card table">
<div class="box">
<div class="box-value">
<select class="priorityOption">
<option value="">--</option>
<option value="">LOREM</option>
<option value="">LOREM</option>
</select>
</div>
<div class="box-value">
<select class="priorityOption">
<option value="">--</option>
<option value="">LOREM</option>
<option value="">LOREM</option>
</select>
</div>
<div class="box-value">
<select class="priorityOption">
<option value="">--</option>
<option value="">LOREM</option>
<option value="">LOREM</option>
</select>
</div>
</div>
</div>
2023 年答案:现在可以了!
table.myClass tr:nth-child(odd of .row) {}
通用版本(规范):
:nth-child(<nth> [of <selector>]?) {}
。其中<nth>
是2
、3n + 1
、-n + 3
、odd
或其他有效值,<selector>
是选择器的列表,这可能很复杂。
Firefox 113+(2023/05/09,也适用于Android),Edge 111 +(2023/03/13)和Safari 9+(2015/10/01,也适用于iOS)中受支持。
试试吧:
/*** First example ***/
/* All odds (2n + 1) */
#example-1 > :nth-child(odd of .foo) {
background: red;
}
/* Odd evens (4n + 2) */
/* Note how .foo:not(...) is evaluated first */
#example-1 > :nth-child(odd of .foo:not(:nth-child(odd of .foo))) {
background: yellow;
}
/*** Second example ***/
/* This works */
#example-2 > :nth-of-type(3) {
background: red;
}
/* This too */
#example-2 > :nth-child(4 of div) {
background: yellow;
}
/* And so will this */
#example-2 > :nth-last-child(11 of div) {
background: green;
}
/* Use :nth-last-child() to select from last */
/* First 2 of last 3 of <div>s */
#example-2 > :nth-child(-n + 2 of :nth-last-child(-n + 3 of div)) {
background: cyan;
}
/* 1st, 4th, 7th... from last */
#example-2 > :nth-last-child(3n + 1 of div) {
text-decoration: underline;
}
/* ...of which odd elements will be selected */
#example-2 > :nth-last-child(odd of :nth-last-child(3n + 1)) {
outline: 3px solid black;
}
/*** Other styles ***/
.flex {
display: flex;
flex-flow: row wrap;
}
.grid {
display: grid;
grid-template: repeat(5, 1fr) / repeat(5, 1fr);
}
.flex > div,
.grid > div {
display: flex;
flex-direction: column;
align-items: center;
justify-content: center;
height: 100px;
width: 100px;
text-align: center;
}
/* 2nd, 3rd, 4th... of both .flex and .grid */
body > :nth-child(n + 2 of .flex, .grid) {
gap: 10px;
}
/* First 1 of [2nd, 3rd, 4th...] <div>s */
body > :nth-child(-n + 1 of :nth-child(n + 2 of div)) > div {
background: #ddd;
}
/* 2nd of last 2 of [1st, 2nd, 3rd...] non-<script> from last */
/* ...which means 1st from last */
:nth-child(odd of :nth-last-child(-n + 3 of body > :not(script))) > .foo {
border-radius: 50%;
}
:nth-child(odd of :nth-last-child(-n + 3 of body > :not(script))) > .foo::after {
content: '.foo';
display: block;
}
<div class="flex" id="example-1">
<div>odd</div>
<div>even</div>
<div class="foo">1st odd</div>
<div class="foo">1st even</div>
<div class="foo">2nd odd</div>
<div class="foo">2nd even</div>
<div class="foo">3rd odd</div>
<div class="foo">3rd even</div>
</div>
<hr>
<div class="flex" id="example-2">
<div>1 (15)</div>
<div class="foo">2 (14)</div>
<div>3 (13)</div>
<div class="foo">4 (12)</div>
<div>5 (11)</div>
<div>6 (10)</div>
<div class="foo">7 (9)</div>
<div>8 (8)</div>
<div>9 (7)</div>
<div class="foo">10 (6)</div>
<div class="foo">11 (5)</div>
<div>12 (4)</div>
<div class="foo">13 (3)</div>
<div>14 (2)</div>
<div>15 (1)</div>
</div>
不是"有人可以解释为什么吗?"的答案,因为其他答案已经解释了。
但是作为针对您的情况的一种可能解决方案,您可以对行和单元格使用自定义标签,例如<tr-row>
、<td-row>
,然后:nth-of-type()
应该可以工作。不要忘记分别设置样式display: table-row;
和display: table-cell;
,使它们仍然像表格单元格一样工作。