less
less是一种动态样式语言,属于css预处理器的范畴,它扩展了 CSS 语言,
增加了变量、Mixin、函数等特性,使 CSS 更易维护和扩展
LESS 既可以在 客户端 上运行 ,也可以借助Node.js在服务端运行。
less的中文官网:
bootstrap中less教程:
http://www.bootcss.com/p/lesscss/
Less编译工具
koala 官网:
www.koala-app.com
Less编译
- 用koala手动编译
- 借助less转css文件手动编译
- 利用打包工具编译
less中的注释
以//开头的注释,不会被编译到css文件中
以/**/包裹的注释会被编译到css文件中
less中的变量
LESS 中的变量为完全的 ‘常量’ ,所以只能定义一次.
使用@来申明一个变量:@pink:pink;
- 作为普通属性值只来使用:直接使用@pink
@nice-blue: #5B83AD;
@light-blue: @nice-blue + #111;
#header { color: @light-blue; }
=>
#header { color: #6c94be; }
- 作为选择器和属性名:@{selector的值}的形式
<div id="wrap"></div>
// less
@selector:#wrap;
@w:width;
@{selector}{
@{w}:100px;
height: 300px;
border: 1px solid;
}
// 编译为css后
#wrap{
width:100px;
height:300px;
border:1px solid;
}
- 作为URL:@{url}
// less
@url:"../img/zdy.jpg";
#wrap{
width: 100px;
height: 100px;
background: url("@{url}");
// 也可以将url作为变量,写成下面形式
// background: url(@url);
}
// 编译为css后
#wrap{
width:100px;
height:100px;
background:url("../img/zdy.jpg")
}
- 变量的延迟加载
// less
@var: 0;
.class {
@var: 1;
.brass {
@var: 2;
three: @var; //3
@var: 3;
}
one: @var; //1
}
// 编译为css后
.class {
one: 1;
}
.class .brass {
three: 3;
}
less作用域
首先会从本地查找变量或者混合模块,如果没找到的话会去父级作用域中查找,直到找到为止.
@var: red;
#page {
@var: white;
#header {
color: @var; // white
}
}
#footer {
color: @var; // red
}
less中的嵌套规则
- 基本嵌套规则
// html页面:
<ul id="list">
<li>
<a href="javascript:;">a1</a>
<span>b1</span>
</li>
</ul>
// less嵌套写法:
#list{
list-style: none;
line-height: 30px;
width: 300px;
background: pink;
margin: 0 auto;
li{height: 30px;}
a{
float: left;
/*&代表父级*/
&:hover{color: red;}
}
span{float: right;}
}
- &的使用(&代表父级)
如果想写串联选择器,而不是写后代选择器,就可以用到&了.
这点对伪类尤其有用如 :hover 和 :focus.
less中的混合
混合就是将一系列属性从一个规则集引入到另一个规则集的方式
任何 CSS class, id 或者 元素 属性集都可以以同样的方式引入.
以下测试,html模板均为
// html
<div id="box1">box1</div>
- 普通混合(会将混合内容输出到css文件中)
// less
.juzhong{
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
#box1{
width: 100px;
height: 100px;
background: pink;
.juzhong;
}
// 编译为css后
.juzhong { // 会将混合内容输出到css文件中
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
#box1 {
width: 100px;
height: 100px;
background: pink;
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
- 不带输出的混合
加()后就不会在css中输出混合内容了
// less
.juzhong(){
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
#box1{
width: 100px;
height: 100px;
background: pink;
.juzhong;
}
// 编译为css后
#box1 {
width: 100px;
height: 100px;
background: pink;
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
- 带参数的混合
// less
.juzhong(@w,@h,@c){
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
width: @w;
height: @h;
background: @c;
}
#box1{
.juzhong(100px,100px,pink);
z-index: 1;
}
// 编译为css后
#box1 {
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
width: 100px;
height: 100px;
background: #ffc0cb;
z-index: 1;
}
- 带参数并且有默认值的混合
// less
.juzhong(@w:100px,@h:100px,@c:pink){
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
width: @w;
height: @h;
background: @c;
}
#box1{
.juzhong;
z-index: 1;
}
// 编译为css后
#box1 {
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
width: 100px;
height: 100px;
background: #ffc0cb;
z-index: 1;
}
- 带多个参数的混合
- 命名参数(传实参时可以指定值给的是哪个参数)
命名参数就是引用mixin时可以通过参数名称而不是参数的位置来为mixin提供参数值。
任何参数都已通过它的名称来引用,这样就不必按照任意特定的顺序来使
// less
.juzhong(@w:100px,@h:100px,@c:pink){
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
width: @w;
height: @h;
background: @c;
}
#box1{
// 引入混合时可以改变参数位置
.juzhong(@h:200px;@c:deeppink;);
}
// 编译为css后
#box1 {
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
width: 100px;
height: 200px;
background: #ff1493;
}
- 匹配模式
根据传入的参数来改变混合的默认呈现。
// less
/*向上的三角*/
.triangle(top,@w:10px,@c:pink){
border-width:@w;
border-color: transparent transparent @c transparent ;
border-style:dashed dashed solid dashed ;
}
/*向下的三角*/
.triangle(bottom,@w:10px,@c:pink){
border-width:@w;
border-color: @c transparent transparent transparent ;
border-style:solid dashed dashed dashed ;
}
/*向左的三角*/
.triangle(left,@w:10px,@c:pink){
border-width:@w;
border-color: transparent @c transparent transparent ;
border-style: dashed solid dashed dashed ;
}
/*向右的三角*/
.triangle(right,@w:10px,@c:pink){
border-width:@w;
border-color: transparent transparent transparent @c;
border-style: dashed dashed dashed solid;
}
.triangle(@_,@w:10px,@c:pink){
width: 0;
height: 0;
overflow: hidden;
}
#box1{
// 向上三角图案
.triangle(top,50px,deeppink);
}
// 编译为css后
#box1 {
border-width: 50px;
border-color: transparent transparent #ff1493 transparent;
border-style: dashed dashed solid dashed ;
width: 0;
height: 0;
overflow: hidden;
}
导引表达式:
当我们想根据表达式进行匹配,而非根据值和参数匹配时,导引就显得非常有用。如果你对函数式编程非常熟悉,那么你很可能已经使用过导引。
为了尽可能地保留CSS的可声明性,LESS通过导引混合而非if/else语句来实现条件判断,因为前者已在@media query特性中被定义。
以此例做为开始:
.mixin (@a) when (lightness(@a) >= 50%) {
background-color: black;
}
.mixin (@a) when (lightness(@a) < 50%) {
background-color: white;
}
.mixin (@a) {
color: @a;
}
when关键字用以定义一个导引序列(此例只有一个导引)。接下来我们运行下列代码:
.class1 { .mixin(#ddd) }
.class2 { .mixin(#555) }
就会得到:
.class1 {
background-color: black;
color: #ddd;
}
.class2 {
background-color: white;
color: #555;
}
导引中可用的全部比较运算有: > >= = =< <。此外,关键字true只表示布尔真值,下面两个混合是相同的:
.truth (@a) when (@a) { ... }
.truth (@a) when (@a = true) { ... }
除去关键字true以外的值都被视示布尔假:
.class {
.truth(40); // Will not match any of the above definitions.
}
导引序列使用逗号‘,’—分割,当且仅当所有条件都符合时,才会被视为匹配成功。
.mixin (@a) when (@a > 10), (@a < -10) { ... }
导引可以无参数,也可以对参数进行比较运算:
@media: mobile;
.mixin (@a) when (@media = mobile) { ... }
.mixin (@a) when (@media = desktop) { ... }
.max (@a, @b) when (@a > @b) { width: @a }
.max (@a, @b) when (@a < @b) { width: @b }
最后,如果想基于值的类型进行匹配,我们就可以使用is*函式:
.mixin (@a, @b: 0) when (isnumber(@b)) { ... }
.mixin (@a, @b: black) when (iscolor(@b)) { ... }
下面就是常见的检测函式:
iscolor
isnumber
isstring
iskeyword
isurl
如果你想判断一个值是纯数字,还是某个单位量,可以使用下列函式:
ispixel
ispercentage
isem
最后再补充一点,在导引序列中可以使用and关键字实现与条件:
.mixin (@a) when (isnumber(@a)) and (@a > 0) { ... }
使用not关键字实现或条件
.mixin (@b) when not (@b > 0) { ... }
- arguments变量
@arguments包含了所有传递进来的参数. 如果你不想单独处理每一个参数的话就可以像这样写:
.border(@w:10px,@style:solid,@c:deeppink){
border: @arguments;
}
less运算
任何数字、颜色或者变量都可以参与运算
在less中可以进行加减乘除的运算
括号也同样允许使用
Color 函数 //有对应的API
Math 函数:
round(1.67); //四舍五入 returns `2`
ceil(2.4); // returns `3`
floor(2.6); // returns `2`
percentage(0.5); // returns `50%`
less避免编译 css中cacl()用来计算
有时候我们需要输出一些不正确的CSS语法或者使用一些 LESS不认识的专有语法.
要输出这样的值我们可以在字符串前加上一个 ~, 例如:
.class {
filter: ~"ms:alwaysHasItsOwnSyntax.For.Stuff()";
}
我们可以将要避免编译的值用 “”包含起来,输出结果为:
.class {
filter: ms:alwaysHasItsOwnSyntax.For.Stuff();
}
less继承
性能比混合高
灵活度比混合低
extend(继承的类 all)
// less
.common:hover{
background: pink;
}
.common{
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
.juzhong(@w:100px,@h:100px,@c:pink){
&:extend(.common all);
width: @w;
height: @h;
background: @c;
}
#box1{
.juzhong();
z-index: 1;
}
// 编译为css后
.common:hover{
background: pink;
}
.common{
position: absolute;
left: 0;
right: 0;
bottom: 0;
top: 0;
margin: auto;
}
.juzhong(@w:100px,@h:100px,@c:pink){
&:extend(.common all);
width: @w;
height: @h;
background: @c;
}
#box1{
.juzhong();
z-index: 1;
}
命名空间
有时候,你可能为了更好组织CSS或者单纯是为了更好的封装,将一些变量或者混合模块打包起来,
你可以像下面这样在#bundle中定义一些属性集之后可以重复使用:
#bundle {
.button () {
display: block;
border: 1px solid black;
background-color: grey;
&:hover { background-color: white }
}
.tab { ... }
.citation { ... }
}
只需要在 #header a中像这样引入 .button:
#header a {
color: orange;
#bundle > .button;
}
混合与继承区别
混合:
定义:就是将一系列属性从一个规则集引入到另一个规则集的方式,
任何 CSS class, id 或者 元素 属性集都可以以同样的方式引入。
参数:参数可带可不带。
编译后:编译后相当于ctrl c +ctrl v
继承不能带参数,性能比混合高,灵活度比混合低。
编译后再css中会将选择器组合在一起,代码减少。
JavaScript 表达式
慎用,测试报错
JavaScript 表达式也可以在.less 文件中使用. 可以通过反引号的方式使用:
@var: `"hello".toUpperCase() + '!'`;
输出:
@var: "HELLO!";
注意你也可以同时使用字符串插值和避免编译:
@str: "hello";
@var: ~`"@{str}".toUpperCase() + '!'`;
输出:
@var: HELLO!;
它也可以访问JavaScript环境:
@height: `document.body.clientHeight`;
如果你想将一个JavaScript字符串解析成16进制的颜色值, 你可以使用 color 函数:
@color: color(`window.colors.baseColor`);
@darkcolor: darken(@color, 10%);