在我们的关于选择器的最后一篇文章中,我们将探讨组合器和多个选择器 — 将多个选择器组合在一起以用于进一步有用的选择能力的两种方式。
组合器
一次使用一个选择器是很有用的,但在某些情况下却可能效率低下。 CSS选择器变得更加有用,当你开始结合他们进行细粒度的选择。CSS有几种方法可以选择元素基于它们如何彼此相关。这些关系与组合子表示如下(A和B代表任何选择器见上图):
| Combinators | Select |
|---|---|
| A,B | 匹配满足A(和/或)B的任意元素(参见下方 同一规则集上的多个选择器). |
| A B | 匹配任意元素,满足条件:B是A的后代结点(B是A的子节点,或者A的子节点的子节点) |
| A > B | 匹配任意元素,满足条件:B是A的直接子节点 |
| A + B | 匹配任意元素,满足条件:B是A的下一个兄弟节点(AB有相同的父结点,并且B紧跟在A的后面) |
| A ~ B | 匹配任意元素,满足条件:B是A之后的兄弟节点中的任意一个(AB有相同的父节点,B在A之后,但不一定是紧挨着A) |
组合器示例
接下来看几个例子,演示一下他们是怎么工作的:
<table lang="en-US" class="with-currency">
<thead>
<tr>
<th scope="col">Product</th>
<th scope="col">Qty.</th>
<th scope="col">Price</th>
</tr>
</thead>
<tfoot>
<tr>
<th colspan="2" scope="row">Total:</th>
<td>148.55</td>
</tr>
</tfoot>
<tbody>
<tr>
<td>Lawnchair</td>
<td>1</td>
<td>137.00</td>
</tr>
<tr>
<td>Marshmallow rice bar</td>
<td>2</td>
<td>1.10</td>
</tr>
<tr>
<td>Book</td>
<td>1</td>
<td>10.45</td>
</tr>
</tbody>
</table>
对以上元素应用下面的样式表:
/* Basic table setup */
table {
font: 1em sans-serif;
border-collapse: collapse;
border-spacing: 0;
}
/* All <td>s within a <table> and all <th>s within a <table>
Comma is not a combinator, it just allows you to target
several selectors with the same CSS ruleset */
table td, table th {
border : 1px solid black;
padding: 0.5em 0.5em 0.4em;
}
/* All <th>s within <thead>s that are within <table>s */
table thead th {
color: white;
background: black;
}
/* All <td>s preceded by another <td>,
within a <tbody>, within a <table> */
table tbody td + td {
text-align: center;
}
/* All <td>s that are a last child,
within a <tbody>, within a <table> */
table tbody td:last-child {
text-align: right
}
/* All <th>s, within a <tfoot>s, within a <table> */
table tfoot th {
text-align: right;
border-top-width: 5px;
border-left: none;
border-bottom: none;
}
/* All <td>s preceded by a <th>, within a <table> */
table th + td {
text-align: right;
border-top-width: 5px;
color: white;
background: black;
}
/* All pseudo-elements "before" <td>s that are a last child,
appearing within elements with a class of "with-currency" that
also have an attribute "lang" with the value "en-US" */
.with-currency[lang="en-US"] td:last-child::before {
content: '$';
}
/* All pseudo-elements "after" <td>s that are a last child,
appearing within elements with the class "with-currency" that
also have an attribute "lang" with the value "fr" */
.with-currency[lang="fr"] td:last-child::after {
content: ' €';
}
这给了我们如下漂亮的表样式:
主动学习: 写出属于你自己的组合器
上面设计的例子是为了向你展示,你可以开始使用一些稍微复杂点的组合选择器。在这次的主动学习中,我们将会带你写点你自己的、更简单的组合选择器。在这个练习中,你需要在2~4规则集中添加选择器,来实现如下效果:
- 设计链接的样式,但是只针对ul无序列表中的链接有效;
- 设计ul列表里的链接样式,但是只当鼠标停留在上面时有效;
- 设计只紧接着最大标题下的段落样式。
如果你遇到问题, 你可以点击“Reset”按钮来重置。 要是真的不会了, 按下“Show solution ”按钮去参考一下答案。
Playable code 7
<div class="body-wrapper" style="font-family: 'Open Sans Light',Helvetica,Arial,sans-serif;">
<h2>HTML Input</h2>
<textarea id="code" class="html-input" style="width: 90%;height: 10em;padding: 10px;border: 1px solid #0095dd;"><ul>
<li><a href="#">Home</a></li>
<li><a href="#">Portfolio</a></li>
<li><a href="#">About</a></li>
</ul>
<h1>Welcome to my website</h1>
<p>Hello, and welcome! I hope you enjoy your time here.</p>
<h2>My philosophy</h2>
<p>I am a believer in chilling out, and not getting grumpy. I think everyone else should follow this ideal, and <a href="#">drink green tea</a>.</p></textarea>
<h2>CSS Input</h2>
<textarea id="code" class="css-input" style="width: 90%;height: 10em;padding: 10px;border: 1px solid #0095dd;">ul {
padding: 0;
list-style-type: none;
}
{
text-decoration: none;
display: block;
color: black;
background-color: red;
padding: 5px;
margin-bottom: 10px;
}
{
color: red;
background-color: black;
}
{
font-style: bold;
color: blue;
}</textarea>
<h2>Output</h2>
<div class="output" style="width: 90%;height: 10em;padding: 10px;border: 1px solid #0095dd;overflow:auto;"></div>
<div class="controls">
<input id="reset" type="button" value="Reset" style="margin: 10px 10px 0 0;">
<input id="solution" type="button" value="Show solution" style="margin: 10px 0 0 10px;">
</div>
</div>
var htmlInput = document.querySelector(".html-input");
var cssInput = document.querySelector(".css-input");
var reset = document.getElementById("reset");
var htmlCode = htmlInput.value;
var cssCode = cssInput.value;
var output = document.querySelector(".output");
var solution = document.getElementById("solution");
var styleElem = document.createElement('style');
var headElem = document.querySelector('head');
headElem.appendChild(styleElem);
function drawOutput() {
output.innerHTML = htmlInput.value;
styleElem.textContent = cssInput.value;
}
reset.addEventListener("click", function() {
htmlInput.value = htmlCode;
cssInput.value = cssCode;
drawOutput();
});
solution.addEventListener("click", function() {
htmlInput.value = htmlCode;
cssInput.value = 'ul {\n padding: 0;\n list-style-type: none;\n}\n\nul a {\n text-decoration: none;\n display: block;\n color: black;\n background-color: red;\n padding: 5px;\n margin-bottom: 10px;\n}\n\nul a:hover {\n color: red;\n background-color: black;\n}\n\nh1 + p {\n font-style: bold;\n color: blue;\n}';
drawOutput();
});
htmlInput.addEventListener("input", drawOutput);
cssInput.addEventListener("input", drawOutput);
window.addEventListener("load", drawOutput);
同一规则集上的多个选择器
你已经见过了这种情况的许多例子,但是为了更明确,让我们清楚地把它拼写出来。书写多个选择器时,为了让相同规则集一次性作用于多组被选择的元素,你可以用逗号来隔开。例如:
p, li {
font-size: 1.6em;
}
或者这样:
h1, h2, h3, h4, h5, h6 {
font-family: helvetica, 'sans serif';
}
接下来是什么
恭喜,你已经来到了我们关于选择器学习的长途旅行的终点。即使是富有经验的web开发者仍然会惊讶于使用选择器时会发生什么结果——不要对你记不住所有的选择而感到不适——你需要的话,可以把这个最主要的选择器页面添加到书签里,方便你日后的回顾。
在我们的下一篇文章里,我们将会转向另一个非常重要的基础CSS话题——其拥有的各种各样的属性和值,以及表示长度、颜色或者其他你想要的值的单位是什么。让我们来探索CSS的值和单位。