5. 混合器;

    混合器使用标识符定义。看上去很像其他的CSS @标识符,比如说@media或者-face。这个标识符给一大段样式赋予一个名字,这样你就可以轻易地通过引用这个名字重用这段样式。下边的这段sass代码,定义了一个非常简单的混合器,目的是添加跨浏览器的圆角边框。

    然后就可以在你的样式表中通过@include来使用这个混合器,放在你希望的任何地方。调用会把混合器中的所有样式提取出来放在@include被调用的地方。如果像下边这样写:

    1. notice {
    2. background-color: green;
    3. border: 2px solid #00aa00;
    4. @include rounded-corners;
    5. }
    6. //sass最终生成:
    1. .notice {
    2. background-color: green;
    3. border: 2px solid #00aa00;
    4. -webkit-border-radius: 5px;
    5. border-radius: 5px;
    6. }

    .notice中的属性border-radius-moz-border-radius-webkit-border-radius全部来自rounded-corners这个混合器。这一节将介绍使用混合器来避免重复。通过使用参数,你可以使用混合器把你样式中的通用样式抽离出来,然后轻松地在其他地方重用。实际上,混合器太好用了,一不小心你可能会过度使用。大量的重用可能会导致生成的样式表过大,导致加载缓慢。所以,首先我们将讨论混合器的使用场景,避免滥用。

    利用混合器,可以很容易地在样式表的不同地方共享样式。如果你发现自己在不停地重复一段样式,那就应该把这段样式构造成优良的混合器,尤其是这段样式本身就是一个逻辑单元,比如说是一组放在一起有意义的属性。

    判断一组属性是否应该组合成一个混合器,一条经验法则就是你能否为这个混合器想出一个好的名字。如果你能找到一个很好的短名字来描述这些属性修饰的样式,比如rounded-cornersfancy-font或者no-bullets,那么往往能够构造一个合适的混合器。如果你找不到,这时候构造一个混合器可能并不合适。

    混合器在某些方面跟css类很像。都是让你给一大段样式命名,所以在选择使用哪个的时候可能会产生疑惑。最重要的区别就是类名是在html文件中应用的,而混合器是在样式表中应用的。这就意味着类名具有语义化含义,而不仅仅是一种展示性的描述:用来描述html元素的含义而不是html元素的外观。而另一方面,混合器是展示性的描述,用来描述一条css规则应用之后会产生怎样的效果。

    有时候仅仅把属性放在混合器中还远远不够,可喜的是,sass同样允许你把css规则放在混合器中。

    混合器中不仅可以包含属性,也可以包含css规则,包含选择器和选择器中的属性,如下代码:

    当一个包含css规则的混合器通过包含在一个父规则中时,在混合器中的规则最终会生成父规则中的嵌套规则。举个例子,看看下边的sass代码,这个例子中使用了no-bullets这个混合器:

    1. ul.plain {
    2. color: #444;
    3. @include no-bullets;
    4. }

    sass@include指令会将引入混合器的那行代码替换成混合器里边的内容。最终,上边的例子如下代码:

    1. ul.plain {
    2. color: #444;
    3. list-style: none;
    4. }
    5. ul.plain li {
    6. list-style-image: none;
    7. list-style-type: none;
    8. margin-left: 0px;

    混合器中的规则甚至可以使用sass的父选择器标识符&。使用起来跟不用混合器时一样,sass解开嵌套规则时,用父规则中的选择器替代&

    如果一个混合器只包含css规则,不包含属性,那么这个混合器就可以在文档的顶部调用,写在所有的规则之外。如果你只是为自己写一些混合器,这并没有什么大的用途,但是当你使用一个类似于Compass的库时,你会发现,这是提供样式的好方法,原因在于你可以选择是否使用这些样式。

    混合器并不一定总得生成相同的样式。可以通过在混合器时给混合器传参,来定制混合器生成的精确样式。当@include混合器时,参数其实就是可以赋值给css属性值的变量。如果你写过JavaScript,这种方式跟JavaScriptfunction很像:

    当混合器被时,你可以把它当作一个css函数来传参。如果你像下边这样写:

    1. a {
    2. @include link-colors(blue, red, green);
    3. }
    4. //Sass最终生成的是:
    5. a { color: blue; }
    6. a:hover { color: red; }
    7. a:visited { color: green; }

    当你@include混合器时,有时候可能会很难区分每个参数是什么意思,参数之间是一个什么样的顺序。为了解决这个问题,sass允许通过语法$name: value的形式指定每个参数的值。这种形式的传参,参数顺序就不必再在乎了,只需要保证没有漏掉参数即可:

    1. a {
    2. @include link-colors(
    3. $normal: blue,
    4. $visited: green,
    5. $hover: red
    6. );

    尽管给混合器加参数来实现定制很好,但是有时有些参数我们没有定制的需要,这时候也需要赋值一个变量就变成很痛苦的事情了。所以sass允许混合器声明时给参数赋默认值。

    为了在混合器时不必传入所有的参数,我们可以给参数指定一个默认值。参数默认值使用$name: default-value的声明形式,默认值可以是任何有效的css属性值,甚至是其他参数的引用,如下代码:

    如果像下边这样调用:@include link-colors(red) $hover$visited也会被自动赋值为red