CSS 中的新值和函数

176 阅读7分钟

本文翻译自 New Values and Functions in CSS ,原作者: Alvaro Montoro,略有删改。

在2024年9月13日,CSS工作组发布了CSS值和单位模块 Level 5 的首个公开工作草案。这是对前一级别的扩展,包含了一些有趣的新增内容。

不久之前还无法想象的事物现在正逐渐进入规范:随机值、在任何属性中使用属性作为值、能够在计算中使用顺序……现在看起来很有前景。

这些特性都有一个共同点:它们简化了CSS代码。以前需要多条规则或hacky解决方案的事情,现在可以用一两行CSS代码实现。正如我所说,看起来很有前景。

以下是新变化的列表:

  • attr()函数的变化:使其可以与任何属性一起使用,并在任何CSS属性中使用(不仅仅在内容上)。

  • calc-size()函数:在计算中使用固有值,如auto或min-content。

  • 新的first-valid()函数:避免自定义属性中无效值的问题。

  • 新的*-mix()函数族:带有新的比例表示法。

  • 新的*-progress()函数族:计算在范围或媒体或容器内的进度比率。

  • 随机化的新random()random-item()函数:从范围或列表中返回随机值。

  • 新的sibling-count()sibling-index()函数:提供整数值以根据顺序和大小进行操作。

  • 新的toggle()函数:轻松循环遍历一系列值以样式化嵌套元素。

  • 新的函数参数表示法:使用逗号分隔的值列表,以避免与参数分隔的逗号混淆。

  • 位置类型的扩展:可以指定相对于文本流和方向的值。

新特性和更新

attr()函数的变化

在CSS中读取属性并使用它并不是新事物。这已经可以通过attr()实现,但一个常见的抱怨是功能有限,只能与字符串一起工作,并且只能在content中使用。

attr()函数将进行一些更新,因此任何数据属性无论其数据类型如何都可以在任何属性中使用。它将像指定类型一样简单,如果需要的话,还可以指定一个后备值以防万一出现问题。

这是一个期待已久的更新,将使许多开发人员感到高兴。

使用calc-size()进行固有值操作

该模块还引入了一个新的函数,能够安全地与固有值(automax-contentfit-content等)一起操作。这将是一个特别有用的特性,尤其是在过渡和动画中。

它还添加了新的关键字(size),为计算提供更多的灵活性,使尺寸工作更加容易。

为什么已经有了calc()还要有一个全新的函数呢?正如文档所解释的,这样做有向后兼容性和实际原因(例如,在所有情况下平滑插值,特别是在操作百分比时)。

新的first-valid()函数

引入了一种新的方法:first-valid()。这个想法是向函数传递一个值列表;它们将被解析,第一个有效的值将被使用。这在处理CSS自定义属性(即CSS变量)时将特别有用。

在操作CSS变量时遇到的一个问题是,在声明中,即使实际包含的值无效,它们也被认为是有效值。设置后备值也没有帮助,后备声明也会被忽略。

有了这个方法,我们可以通过first-valid()将所有后备声明合并为一个,从而简化代码。

新的*-mix()函数族

它还引入了一个新的函数mix(),可以用来简化不同的*-mix函数。你想混合颜色吗?你可以做类似color-mix(red 60%, blue)或者更简单的mix(60%, red, blue)。正如我们所说的颜色,我们也可以混合长度、变换函数等。

这种表示法也扩展到了其他*-mix函数族:

  • calc-mix()
  • color-mix()
  • cross-fade()
  • palette-mix()

如果在进度参数(第一个)中没有指定缓动函数,将默认应用linear

新的*-progress()函数族

它们表示从起始值到结束值的给定值的比例进度。结果是一个介于0和1之间的数字,可以在操作中使用,但当与前面描述的*-mix函数族结合使用时,将特别方便。

这个家族中有三种函数:

  • progress():通用的,适用于任何数学函数。
  • media-progress():适用于媒体特性。
  • content-progress():适用于容器查询。

CSS中的随机化函数

有趣的设计有一定的随机化程度,这是CSS中缺失的。但是这个模块引入了两个新函数,它们可以从列表(random-item())或范围(random())返回随机值。

不再需要hacky技巧或依赖其他语言来实现这一点。语法简单而强大,也可以通过选择器或元素计算随机数。

新的同级函数

有时你可能希望根据元素在容器中的顺序提供不同的样式。不幸的是,计数器不能像那样在CSS中使用(我会在另一天留下这个抱怨)。

随着两个新函数的引入,它们返回一个数字,使得可以操作它们,这个障碍被移除了:

  • sibling-count():返回兄弟元素的数量。
  • sibling-index():返回元素在兄弟元素列表中的位置/顺序。

不再需要在每个元素上设置自定义属性或编写具有nth-child的单独选择器。

新的toggle()函数

引入了一种方便的新方法来定义嵌套元素中的值。toggle()函数设置了元素及其后代将循环遍历的值,大大简化了代码。忘记复杂的规则或重新定义——一切都将在一行代码中完成。

例如,想象我们有一个具有四个嵌套级别的列表。我们希望奇数级别有圆点,偶数级别是正方形。我们可以在不同级别做一些有趣的事情ul > li ul > li ul > li ul { ... },或者我们可以直接做一些像ul { list-style-type: disc, square; }。完成了!

关于这个函数唯一有点令人担忧的是它的名字。也许只是我,但“toggle”这个词有“二元性”的含义:开/关,是/否——两个值在彼此之间切换/切换。toggle()函数可以有你想要的任意多的参数,所以它被命名为“toggle”感觉很奇怪。

新的函数参数表示法

你可能已经注意到,一些新函数(例如,random()toggle())可以接受逗号分隔的值列表作为参数。

我们如何在这些情况下区分一个参数和下一个参数?这就是为什么有“逗号升级”功能表示法的提议。这意味着我们可以使用分号(;)而不是逗号(,)来无歧义地分隔参数。

例如,假设你希望你的页面上有一个随机的字体族,并指定不同的选项:

  • Times, serif
  • Arial, sans-serif
  • Roboto, sans-serif

所有这些参数都是逗号分隔的值列表。如果我们用逗号来分隔参数,那将是一场灾难。但是有了新的表示法,很容易识别一个参数在哪里结束,下一个参数在哪里开始:

.random-font {
  font-family: random-item(
     Times, serif;
     Arial, sans-serif;
     Roboto, sans-serif
   );
}

位置类型的扩展

CSS已经为marginpaddingborder提供了逻辑属性——这些值是相对于文本书写方向的,并且可能因一种语言而异。

现在为位置类型(不要与position属性混淆)引入了这种特性。表示位置的属性(例如,background-positionobject-position等)可以指定相对于文本流和方向的值。

可以使用的新值有:

  • x-start
  • x-end
  • y-start
  • y-end
  • block-start
  • block-end
  • inline-start
  • inline-end

结论

以上仍然处于早期阶段,可能会改变,但CSS值和单位模块Level 5中包含的一些新特性和功能看起来非常有前景。

有兴趣的可以查看CSS值和单位模块Level 5工作草案 (www.w3.org/TR/css-valu…) 以获取更多详细信息和信息。如果你有任何问题或评论,可以提交在他们的GitHub仓库。