本文翻译自 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()
进行固有值操作
该模块还引入了一个新的函数,能够安全地与固有值(auto
、max-content
、fit-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已经为margin
、padding
和border
提供了逻辑属性——这些值是相对于文本书写方向的,并且可能因一种语言而异。
现在为位置类型(不要与position
属性混淆)引入了这种特性。表示位置的属性(例如,background-position
、object-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仓库。