Sass和Less这样的预处理器,让我们的CSS代码保持良好的结构和可维护性。像变量、混合(mixins)、循环控制等特性,增强了动态编写CSS的能力,从而减少重复代码,也加快了我们开发速度。
近年来,一些动态特性开始作为规范的一部分,出现在CSS语言中。CSS变量(CSS variables),或者用它的官方称谓,叫作自定义属性(custom properties),已经可用,并且有非常棒的浏览器支持,而CSS mixins也正在取得进展。
在本文,你将学会如何使用CSS变量,并把它集成到你的CSS开发流程中,让你的样式表更好维护,且减少重复。
让我们现在就开始吧!
什么是CSS变量?
如果你曾使用过某种编程语言,那么你已经很熟悉变量这个概念了。变量用于存储和更新你的程序所需要的值,以便使它运行。
例如,考虑下面的JavaScript代码
let number1 = 2;
let number2 = 3;
let total = number1 + number2;
console.log(total); // 5
number1 = 4;
total = number1 + number2;
console.log(total); // 7
nubmer1和 number2是两个变量,分别存储着数字2和3。
total同样是变量,存储着number1与number2之和。在这里它的值就是5。你可以动态地修改变量里的值,并在程序中使用它们。在上面的代码中,我把number1的值更新为4,然后再进行求和。使用相同的变量,这个时候total里存储的值就是5,而不再是7了。
使用变量的妙处在于,它可以让你在一个地方存储值,并且让你在后面能以各种理由去更新它。在程序中,你不需要为不同的值再添加额外的字符表示:任何值的更新都发生在同一个地方。正如,在你定义的变量上。
CSS在很大程度上是一种声明式的语言,而缺少动态能力。你也许会认为,让CSS拥有变量,几乎让上面的说法自相矛盾。如果前端开发仅仅是关于文字游戏,那可以这么说。幸运的是,Web的编程语言很像生活中的语言,它们会随着周围环境和实践需要而不断进化与适应。CSS也同样如此。
简单的说,变量已经成为CSS世界中激动人心的事实,并且你即将亲自看到,对于这个厉害的新技术,学习和使用起来都非常直观。
使用CSS变量有什么好处?
使用CSS变量的好处,跟在其他编程语言中使用变量的好处没什么大的区别。
规范是这样描述这一点的
使用CSS变量,给看似随机的值加上富有信息的名字,从而使得大文件更容易阅读和编辑,更少出错。因为,你只需要在自定义属性中改变一次值,所有应用了这个变量的地方都会自动跟着一起改变。W3C 规范
换句话说,通过给变量起一个对你来说在项目中有意义的名字,你能更容易的管理和维护你的代码。例如,当你为项目中的主色调设置一个变量名–primary-color,那么你后面再修改这个主色调时,只需要改动一处,而不需要在不同位置的多个CSS文件中去手动修改多次值。
CSS变量和预处理器中的变量有什么不同?
你可能已经在CSS预处理器中尝试过使用变量而带来的好处了,比如Sass和Less。
预处理器让你能设置变量,以及在函数、循环、数学计算等等地方中使用它们。这是否意味着CSS变量已经无关紧要了呢?
那可未必,主要是因为,CSS变量与预处理器中的变量其实是不同的东西。
这些不同基于一个事实:CSS变量是浏览器中直接可用的CSS属性,而预处理中的变量是用于编译成常规的CSS代码,浏览器其实对它们一无所知。
这意味着,你可以在样式表中,在内联样式中,在SVG的标签中直接更新CSS变量,甚至可以在运行时用JavaScript直接修改它。而你是无法对预处理器中的变量做上面这些操作的。CSS变量开启了一个充满可能性的新世界大门。
不是说你必须要在两者间做出选择:没有什么东西限制你,你可以同时使用CSS变量和预处理变量,并享有它们各自带来的巨大好处。
CSS变量:语法
虽然本文为了简洁,我使用了CSS变量(CSS variables)这个称呼,但官方的规范把它们称作作为级联变量的CSS自定义属性(CSS custom properties for cascading variables)。*CSS自定义属性(CSS custom property)*的部分看起来像这样:
–my-cool-background: #73a4f4;
在自定义属性前添加双横线前缀,然后像给普通CSS设值一样,给自定义属性设值。在上面的代码中,我给一个叫做–my-cool-backgroud的自定义属性设置了一个颜色值。
而 级联变量(cascading variable) 的部分,由通过val()来使用你的自定义属性组成,开起来像这样:
var(–my-cool-background);
自定义属性作用于CSS选择器中,val()可被当成一个真正的CSS属性一样使用。
:root {
–my-cool-background: #73a4f4;
}
/* CSS文件的其他部分 */
#foo {
background-color: var(–my-cool-background);
}
上面的代码片段把–my-cool-background这个自定义属性的作用域定义在:root这个伪类中,这让该自定义属性能被全局访问到(即在标签内部的任何地方)。然后,使用val()函数把ID为foo的容器的background-color设置为自定义属性的值,这时该容器就有了浅蓝的背景色。