Less是一门CSS预处理语言,它扩展了CSS语言,增加了变量、Mixin、函数等特性,使CSS更易维护和扩展。
Less可以运行在Node或浏览器端。
Less编译工具:
- Koala
- vscode的Easy Less插件
在Node.js环境中使用Less:
npm install -g less > lessc style.less styles.css
在浏览器环境中使用Less:
<link rel="stylesheet/less" type="text/css" href="style.less"/>
<script src="https://cdn.jsdelivr.net/npm/less@4"><script>
以//开头的注释,不会被编译到CSS文件中。
以/**/包裹的注释会被编译到CSS文件中。
声明变量,作为普通属性值使用:@pink:pink;
@width: 10px;
@height: @width + 10px;
#header {
width: @width;
height: @height;
}
编译为:
#header {
width: 10px;
height: 20px;
}
变量用于选择器名、属性名、URL、@import语句
@my-selector: banner;
// 需要添加 {}
.@{my-selector} {
font-weight: bold;
line-height: 40px;
margin: 0 auto;
}
@property: color;
.widget {
@{property}: #0ee;
background-@{property}: #999;
}
// Variables
@images: '../img';
// Usage
body {
color: #444;
background: url('@{images}/white-sand.png');
}
// Variables
@themes: '../../src/themes';
// Usage
@import '@{themes}/tidal-wave.less';
当一个变量被声明多次,会取最后一次的值,并从当前作用域往外寻找变量。
@var: 0;
.class {
@var: 1;
.brass {
@var: 2;
three: @var;
@var: 3;
}
one: @var;
}
编译后:
.class {
one: 1;
}
.class .brass {
three: 3;
}
.widget {
color: #efefef;
background-color: $color;
}
编译后:
.widget {
color: #efefef;
background-color: #efefef;
}
Less提供了使用嵌套(nesting)代替层叠或与层叠结合使用的能力。
#header {
color: black;
.navigation {
font-size: 12px;
}
.logo {
width: 300px;
}
}
编译后:
#header {
color: black;
}
#header .navigation {
font-size: 12px;
}
#header .logo {
width: 300px;
}
在嵌套规则中,&表示父选择器,常用域给现有选择器添加伪类。
.header {
a {
color: blue;
&:hover {
color: green;
}
}
}
编译后:
.header a {
color: blue;
}
.header a:hover {
color: green;
}
如果没有&,会被编译成后代选择器 a:hover。
除此之外,&还能用于生成重复类名:
button {
&-ok {
background-image: url('ok.png');
}
&-cancel {
background-image: url('cancel.png');
}
&-custom {
background-image: url('custom.png');
}
}
编译后:
.button-ok {
background-image: url('ok.png');
}
.button-cancel {
background-image: url('cancel.png');
}
.button-custom {
background-image: url('custom.png');
}
混合就是将一系列属性从一个规则引入到另一个规则集的方式。
.bordered {
border-top: dotted 1px black;
border-bottom: solid 2px black;
}
#menu a {
color: #111;
.bordered();
}
.post a {
color: red;
.bordered();
}
编译后:
.bordered {
border-top: dotted 1px black;
border-bottom: solid 2px black;
}
#menu a {
color: #111;
border-top: dotted 1px black;
border-bottom: solid 2px black;
}
.post a {
color: red;
border-top: dotted 1px black;
border-bottom: solid 2px black;
}
.border(@width, @style, @color) {
border: @width @style @color;
}
div {
.border(1px, solid, #ccc);
}
编译后:
div {
border: 1px solid #ccc;
}
需要注意的是:就算有默认值,也要按顺序传递
.border(@width, @style, @color: #ccc) {
border: @width @style @color;
}
div {
.border(1px, solid);
}
// 编译后:
div {
border: 1px solid #ccc;
}
.border(@width: 1px, @style, @color) {
border: @width @style @color;
}
div {
.border(solid, #ccc);
}
//会出错
可以在向混合传参是指定参数名称,从而不需要按顺序传入。
.border(@width, @style, @color: #ccc) {
border: @width @style @color;
}
div {
.border(@style: solid, @color: red, @width: 100px);
}
//编译后:
div {
border: 100px solid red;
}
@arguments变量包含了传入的所有参数
.box-shadow(@x: 0, @y: 0, @blur: 1px, @color: #000) {
-webkit-box-shadow: @arguments;
-moz-box-shadow: @arguments;
box-shadow: @arguments;
}
.big-block {
.box-shadow(2px, 5px);
}
编译后:
.big-block {
-webkit-box-shadow: 2px 5px 1px #000;
-moz-box-shadow: 2px 5px 1px #000;
box-shadow: 2px 5px 1px #000;
}
在多个相同的混合中(参数个数必须相同),匹配特定的混合。
.mixin(dark, @color) {
color: darken(@color, 10%);
}
.mixin(light, @color) {
color: lighten(@color, 10%);
}
// @_ 表示匹配所有
.mixin(@_, @color) {
display: block;
}
@switch: light;
.class {
.mixin(@switch, #888);
}
编译后:
.class {
color: #a2a2a2;
display: block;
}
计算结果以操作最左侧的单位类型为准。
@conversion-1: 5cm + 10mm; // 6cm
@conversion-2: 2 - 3cm - 5mm; // -1.5cm
@conversion-3: 3.1 * 2cm; // 6.2cm
@conversion-4: 4px / 2; // 4px / 2
// conversion is impossible
@incompatible-units: 1cm - 1px; // 0.97354167cm
// example with variables
@base: 5%;
@filler: @base * 2; // 10%
@other: @base + @filler; // 15%
@color: #224488 / 2; // #112244
background-color: #112244 + #111; // #223355
nav ul {
&:extend(.inline);
background: blue;
}
.inline {
color: red;
}
编译后:
nav ul {
background: blue;
}
.inline,
nav ul {
color: red;
}
把all前的选择器出现的地方全都替换为extend前的选择器。
即把.test替换为.replacement生成一个新的选择器应用样式,且不破坏原有的选择器。
.a.b.test,
.test.c {
color: orange;
}
.test {
&:hover {
color: green;
}
}
.replacement:extend(.test all) {
}
编译后:
.a.b.test,
.test.c,
.a.b.replacement,
.replacement.c {
color: orange;
}
.test:hover,
.replacement:hover {
color: green;
}
通过加引号 ‘ ’ 可以避免Less编译,直接吧内容输出到CSS中。
.banner .inline .header {
width: '100px + 100px';
height: 100px + 100px;
}
编译后:
.banner .inline .header {
width: '100px + 100px';
height: 200px;
}