postcss_PostCSS改进选择器和媒体查询的指南

鲜于雨石
2023-12-01

postcss

Recent changes to the CSS specifications have introduced quite a few interesting features. Unfortunately, some of them are still in a draft state and the ones that aren’t lack broad browser support. As usual, it will take a while for the new suggestions to be reviewed, accepted and implemented by the browsers. However, we can spare ourselves the long wait and try out some of these features already using PostCSS.

CSS规范的最新更改引入了许多有趣的功能。 不幸的是,其中一些仍处于草稿状态,而某些缺乏缺乏广泛的浏览器支持。 与往常一样,浏览器会花一些时间来审核,接受和实施新建议。 但是,我们可以省去漫长的等待时间,并尝试使用PostCSS来尝试其中的某些功能。

PostCSS has a variety of plugins aiming at implementing polyfills for the newest CSS features. Since the spectrum of these plugins is broad, it would be difficult to cover all of them in a single article. Instead, we will narrow our gaze to a selection of plugins that focus on adding new capabilities to selectors and media queries. Many of them will allow us to significantly improve the structure of our stylesheets while others may just add some sweet syntax sugar on top.

PostCSS有许多插件,旨在为最新CSS功能实现polyfills。 由于这些插件的范围很广,因此很难在一篇文章中涵盖所有插件。 取而代之的是,我们将目光集中在一些插件上,这些插件专注于为选择器和媒体查询添加新功能。 他们中的许多人将使我们能够显着改善样式表的结构,而另一些人可能只是在顶部添加了一些甜美的语法糖。

We won’t get into the details of configuring and installing PostCSS in this article. This has already been covered in “An introduction to PostCSS” and “Improving the quality of your CSS with PostCSS“. For a quick reference you can also check out the PostCSS page on GitHub.

我们不会在本文中详细介绍配置和安装PostCSS的细节。 “ PostCSS简介 ”和“ 使用PostCSS改善CSS的质量 ”中已经对此进行了介绍 。 作为快速参考,您还可以在GitHub上查看PostCSS页面。

规则嵌套 (Rule Nesting)

Let’s start with what is likely to be the most basic feature of all — and certainly familiar to every pre-processor user — nesting. The postcss-nesting plugin implements style rule nesting according to the W3C nesting module proposal.

让我们从可能是所有嵌套中最基本的功能(当然,每个预处理器用户都熟悉)开始。 postcss-nesting插件根据W3C嵌套模块建议实现样式规则嵌套。

The proposal introduces a new & nesting selector which references the parent selector. As opposed to Less or Sass, according to the specification, this selector is mandatory and must be the first basic selector in a chain of selectors to enable nesting. Any selectors which do not contain the nesting selector will be ignored. For example:

提案中提出了一个新的&嵌套选择它引用父选择。 与Less或Sass相比,根据规范,此选择器是必需的,并且必须是选择器链中启用嵌套的第一个基本选择器。 任何不包含嵌套选择器的选择器都将被忽略。 例如:

.article {
  color: #333;

  &.popular {
    background: #DDD;
  }

  & .title {
    font-weight: bold;
  }
}

Will be translated into:

将被翻译成:

.article {
  color: #333
}
.article.popular {
  background: #DDD
}
.article .title {
  font-weight: bold
}

Note that the following code is invalid, since it doesn’t use the & selector as specified.

请注意,以下代码无效,因为它没有使用指定的&选择器。

.article {
  color: #333;

  /* no nested-selector */
  .popular {
    background: #DDD;
  }

  /* the nested selector is not the fist selector in the chain */
  .latest & {
    border: 1px solid red;
  }
}

To allow inserting of the parent selector into any place in a selector (instead of just the beginning), the proposal defines an alternative syntax using the nesting at-rule @nest. We can fix the .latest & selector from the previous example in the following way:

为了允许将父选择器插入选择器中的任何位置(而不仅仅是开始位置),建议使用嵌套at-rule @nest定义替代语法。 我们可以通过以下方式修复上一个示例中的.latest &选择器:

.article {
  color: #333;

  @nest .latest & {
    border: 1px solid red;
  }
}

Which will compile into:

可以编译成:

.article {
  color: #333
}
.latest .article {
  border: 1px solid red
}

The @nest syntax is also a tad more expressive then just &.

@nest语法也比&更具表现力。

自定义选择器 (Custom Selectors)

When writing CSS, we tend to write a lot of repeating selectors. This may be simple boilerplate code to select all links or any button, or a more complex selector that needs to be repeated over and over. This can introduce a lot of code duplication along with all the related problems of code maintenance. The new CSS extensions specification introduces a way to store selectors in variables and reference them from other parts of the stylesheets. Thus, a repeating selector can be defined only once and safely reused elsewhere.

在编写CSS时,我们倾向于编写很多重复的选择器。 这可能是用于选择所有链接或任何按钮的简单样板代码,也可能是一遍又一遍重复的更复杂的选择器。 这会引入很多代码重复以及代码维护的所有相关问题。 新的CSS扩展规范引入了一种将选择器存储在变量中并从样式表的其他部分引用它们的方法。 因此,重复选择器只能定义一次,并可以在其他地方安全地重用。

PostCSS has a postcss-custom-selectors plugin that implements this feature. Here’s a simple example that defines a selector for all header elements:

PostCSS有一个实现此功能的postcss-custom-selectors插件。 这是一个为所有标头元素定义选择器的简单示例:

@custom-selector :--heading h1, h2, h3, h4, h5, h6;

:--heading {
  font-weight: bold;
}

It will compile into:

它将编译为:

h1,
h2,
h3,
h4,
h5,
h6 {
  font-weight: bold;
}

Custom selectors are implemented as pseudo-classes, hence the odd looking :-- syntax.

自定义选择实现为伪类,因此奇看:--语法。

Custom selectors can be effectively used together with basic selectors. For example:

自定义选择器可以与基本选择器一起有效使用。 例如:

.article :--heading .author {
  color: blue;
}

Gets compiled into:

编译成:

.article h1 .author,
.article h2 .author,
.article h3 .author,
.article h4 .author,
.article h5 .author,
.article h6 .author {
  color: blue;
}

You can even combine multiple custom selectors in a single selector to achieve more complex permutations.

您甚至可以将多个自定义选择器组合到一个选择器中,以实现更复杂的排列。

@custom-selector :--links a, a:focus, a:visited, a:hover, a:active;
article :--heading :--links {
  color: #333;
}

Will result in:

将导致:

article h1 a,
article h2 a,
article h3 a,
article h4 a,
article h5 a,
article h6 a,
article h1 a:focus,
article h2 a:focus,
article h3 a:focus,
article h4 a:focus,
article h5 a:focus,
article h6 a:focus,
article h1 a:visited,
article h2 a:visited,
article h3 a:visited,
article h4 a:visited,
article h5 a:visited,
article h6 a:visited,
article h1 a:hover,
article h2 a:hover,
article h3 a:hover,
article h4 a:hover,
article h5 a:hover,
article h6 a:hover,
article h1 a:active,
article h2 a:active,
article h3 a:active,
article h4 a:active,
article h5 a:active,
article h6 a:active {
  color: #333;
}

This example might be slightly exaggerated, but it gives a nice demonstration of the power of this feature.

该示例可能有些夸张,但是很好地演示了此功能的强大功能。

新的伪类 (New Pseudo-Classes)

The Selectors Level 4 specification introduced a whole bunch of new pseudo-classes, but due to the dynamic nature of most of them, only several are available as PostCSS plugins.

Selectors Level 4规范引入了一大堆新的伪类,但是由于大多数伪类具有动态特性,因此只有少数几个可以用作PostCSS插件。

:matches()伪类 (The :matches() Pseudo-class)

The postcss-selector-matches plugin implements the new :matches() pseudo-class. It is a functional class that filters only the elements that match the selectors in the argument. If you pass multiple selectors, then the element has to match at least one of them. In short:

postcss-selector-matches插件实现了新的:matches()伪类。 它是一个函数类,仅过滤与参数中的选择器匹配的元素。 如果传递多个选择器,则元素必须至少匹配其中之一。 简而言之:

button:matches(:hover, :focus) {
  color: red;
}

Is compiled into:

编译成:

button:hover, button:focus {
  color: red;
}

:not()伪类 (The :not() Pseudo-class)

The :not() pseudo-class filters elements that do not match any of the given arguments. It is implemented in the postcss-selector-not plugin.

:not()伪类过滤与任何给定参数都不匹配的元素。 它是在postcss-selector-not插件中实现的。

section:not(:first-child, :last-child) {
  background: white;
}

Results in:

结果是:

section:not(:first-child):not(:last-child) {
  background: white;
}

The postcss-pseudo-class-any-link plugin implements the :any-link pseudo-class. It was introduced to help resolve the confusion around the :link pseudo class. Unlike the latter, it matches all links — including visited ones.

postcss-pseudo-class-any-link插件实现了:any-link伪类。 引入它是为了解决围绕:link伪类的困惑。 与后者不同,它匹配所有链接,包括访问过的链接。

a:any-link {
  color: blueviolet;
}

Is compiled into:

编译成:

a:link,a:visited {
  color: blueviolet;
}

媒体查询的改进 (Improvements to Media Queries)

There’s a couple of plugins in the arsenal of PostCSS designed to make media queries easier to use. They are postcss-custom-media and postcss-media-minmax.

PostCSS军械库中有几个插件旨在使媒体查询更易于使用。 它们是postcss-custom-mediapostcss-media-minmax

定制媒体 (Custom Media)

Writing media queries yields the same problem as regular selectors — they are repeated frequently across stylesheets. Probably even more frequently than plain selectors. Luckily, there’s a solution similar to custom selectors. The postcss-custom-media plugin implements the custom media query specification which adds the ability to save media queries into variables.

编写媒体查询会产生与常规选择器相同的问题-它们在样式表中频繁重复。 可能比普通选择器更为频繁。 幸运的是,有一种类似于自定义选择器的解决方案。 postcss-custom-media插件实现了自定义媒体查询规范,该规范增加了将媒体查询保存到变量中的功能。

The syntax closely resembles custom selectors. Here’s a simple example:

语法与自定义选择器非常相似。 这是一个简单的例子:

@custom-media --medium-viewport (min-width: 768px) and (max-width: 992px);

@media (--medium-viewport) {
  /* your styles here */
}

Is compiled into:

编译成:

@media (min-width: 768px) and (max-width: 992px) {
  /* your styles here */
}

Of course, you can use multiple custom media queries at once:

当然,您可以一次使用多个自定义媒体查询:

@custom-media --landscape (orientation: landscape);
@media (--medium-viewport) and (--landscape) {
  /* your styles here */
}

Will result in:

将导致:

@media (min-width: 768px) and (max-width: 992px) and (orientation: landscape) {
  /* your styles here */
}

As you can see, now it’s much easier to change your definition of a “medium viewport” as well as look for any related CSS code.

如您所见,现在更改“中等视口”的定义以及查找任何相关CSS代码要容易得多。

最小和最大语法 (Min and Max Syntax)

Although media queries are a great thing, the min- and max- syntax has received a lot of hatred from the community. W3C responded by introducing a more intuitive syntax using comparison operators. The postcss-media-minmax plugin adds support for >, >=, < and <= operators. It also allows us to use the value-in-the-middle syntax, that is, min-value < property < max-value.

尽管媒体查询是一件很了不起的事情,但min-max-语法已引起了社区的极大憎恨。 作为回应,W3C使用比较运算符引入了更直观的语法。 postcss-media-minmax插件增加了对>>=<<=运算符的支持。 它还允许我们使用中间值语法,即min-value < property < max-value

We can simplify the previous examples using the new syntax, which will yield the same result.

我们可以使用新语法简化前面的示例,这将产生相同的结果。

@custom-media --medium-viewport (768px <= width <= 992px);

@media (--medium-viewport) {
  /* your styles here */
}

Of course, the plugin will also work without using custom media.

当然,该插件也可以在不使用自定义媒体的情况下运行。

不要在这里停下来 (Don’t Stop Here)

Unfortunately, not many of the new CSS features can be implemented as a PostCSS plugin because of their dynamic nature and dependency on the DOM. We’ll need to wait for native support for most of them. But there are still plenty of plugins to explore and test in your workflow. This article focused on the plugins related to selectors and media queries, but we hope to bring you overviews of other novelties as well. If you’re curious and impatient, you can find more of them at postcss.parts. Keep exploring!

不幸的是,由于它们的动态特性和对DOM的依赖性,因此许多新CSS功能无法实现为PostCSS插件。 我们将需要等待其中大多数的本地支持。 但是,您的工作流程中仍然有许多插件可供探索和测试。 本文重点介绍与选择器和媒体查询相关的插件,但我们也希望为您带来其他新颖性的概述。 如果您好奇和不耐烦,可以在postcss.parts中找到更多它们。 继续探索!

翻译自: https://www.sitepoint.com/the-postcss-guide-to-improving-selectors-and-media-queries/

postcss

 类似资料: