Jeff Huang
Web designer based in Taiwan.
AUTHOR : YELLOWJEFF
$brand-color: #fc3;
a { color: $brand-color; }
nav { background-color:$brand-color; }
@mixin default-type {
margin-bottom: 20px;
font-size: 14px;
line-height: 1.5; }
header { @include default-type; }
footer { @include default-type; }
Andy Hunt and Dave Thomas in their book The Pragmatic Programmer.
Variables is a way to store information that you want to reuse throughout your stylesheet.
$font-stack:Helvetica, sans-serif;
$primary-color: #333;
body {
font: 100% $font-stack;
color: $primary-color;
}
body {
font: 100% Helvetica, sans-serif;
color: #333;
}
Don’t be too vague when naming your Variables.
// Bad
$red: red;
$yellow: yellow;
// Better
$brand-color: red;
$accent-color: yellow;
// Base colors
$base-color: #333;
$brand-color: red;
$brand-80-color: rgba($color-brand, 0.8);
$accent-color: yellow;
Sass will let you nest your CSS selectors in a way that follows the same visual hierarchy of your HTML.
Be aware that overly nested rules will result in over-qualified CSS that could prove hard to maintain and is generally considered bad practice.
nav { ul { margin: 0; padding: 0; list-style: none; } li { display: inline-block; } a { display: block; padding: 6px 12px; text-decoration: none; } }
nav ul {
margin: 0;
padding: 0;
list-style: none;
}
nav li {
display: inline-block;
}
nav a {
display: block;
padding: 6px 12px;
text-decoration: none;
}
Too much Nesting can leads to overly specific selectors.
Like a monster.
body {
div.container {
div.content {
div.articles {
& > div.post {
div.title {
h1 {
a {
}
}
}
div.content {
p { ... }
ul {
li { ... }
}
}
div.author {
a.display {
img { ... }
}
h4 {
a { ... }
}
p {
a { ... }
}
ul {
li { ... }
}
}
}
}
}
}
}
This looks "all good", right?
body { ... }
body div.content div.container { ... }
body div.content div.container div.articles { ... }
body div.content div.container div.articles > div.post { ... }
body div.content div.container div.articles > div.post div.title { ... }
body div.content div.container div.articles > div.post div.title h1 { ... }
body div.content div.container div.articles > div.post div.title h1 a { ... }
body div.content div.container div.articles > div.post div.content { ... }
body div.content div.container div.articles > div.post div.content p { ... }
body div.content div.container div.articles > div.post div.content ul { ... }
body div.content div.container div.articles > div.post div.content ul li { ... }
body div.content div.container div.articles > div.post div.author { ... }
body div.content div.container div.articles > div.post div.author a.display { ... }
body div.content div.container div.articles > div.post div.author a.display img { ... }
body div.content div.container div.articles > div.post div.author h4 { ... }
body div.content div.container div.articles > div.post div.author h4 a { ... }
body div.content div.container div.articles > div.post div.author p { ... }
body div.content div.container div.articles > div.post div.author p a { ... }
body div.content div.container div.articles > div.post div.author ul { ... }
body div.content div.container div.articles > div.post div.author ul li { ... }
After compiling the Sass, we take a look at the result on to find that we've created a CSS monster. Ugh!
You can create partial Sass files that contain little snippets of CSS that you can include in other Sass files.
stylesheets/
|
|-- modules/ # Common modules
| |-- _all.scss # Include to get all modules
| |-- _utility.scss # Module name
| |-- _colors.scss # Etc...
| ...
|
|-- partials/ # Partials
| |-- _base.sass # imports for all mixins + global project variables
| |-- _buttons.scss # buttons
| |-- _figures.scss # figures
| |-- _grids.scss # grids
| |-- _typography.scss # typography
| |-- _reset.scss # reset
| ...
|
|-- vendor/ # CSS or Sass from other projects
| |-- _colorpicker.scss
| |-- _jquery.ui.core.scss
| ...
|
`-- main.scss # primary Sass file
"I like to layout my Sass projects like this"
John W. Long
Instead of requiring an HTTP request, Sass will take the file that you want to import and combine it with the file you're importing into so you can serve a single CSS file to the web browser.
// Modules and Variables
@import "partials/base";
// Partials
@import "partials/reset";
@import "partials/typography";
@import "partials/buttons";
@import "partials/figures";
@import "partials/grids";
// ...
// Third-party
@import "vendor/colorpicker";
@import "vendor/jquery.ui.core";
A mixin lets you make groups of CSS declarations that you want to reuse throughout your site. You can even pass in values to make your mixin more flexible.
@mixin border-radius($radius) { -webkit-border-radius: $radius; -moz-border-radius: $radius; -ms-border-radius: $radius; border-radius: $radius; } .box { @include border-radius(10px); }
.box {
-webkit-border-radius: 10px;
-moz-border-radius: 10px;
-ms-border-radius: 10px;
border-radius: 10px;
}
For some uses, the @extend directive may be a better choice
Using @extend lets you share a set of CSS properties from one selector to another. It helps keep your Sass very DRY.
.message { border: 1px solid #ccc; padding: 10px; color: #333; } .success { @extend .message; border-color: green; } .error { @extend .message; border-color: red; } .warning { @extend .message; border-color: yellow; }
.message, .success, .error, .warning {
border: 1px solid #cccccc;
padding: 10px;
color: #333;
}
.success {
border-color: green;
}
.error {
border-color: red;
}
.warning {
border-color: yellow;
}
If you find yourself extending your .clearfix class twenty times, you may consider adding it to your HTML.
Unlike mixins, %placeholders can be used multiple times without adding any duplicate code. This makes them a much friendlier option for outputting DRY CSS
%bg-image {
width: 100%;
background-position: center center;
background-size: cover;
background-repeat: no-repeat;
}
.image-one {
@extend %bg-image;
background-image:url(/img/image-one.jpg");
}
.image-two {
@extend %bg-image;
background-image:url(/img/image-two.jpg");
}
.image-one, .image-two {
width: 100%;
background-position: center center;
background-size: cover;
background-repeat: no-repeat;
}
.image-one {
background-image:url(/img/image-one.jpg") ;
}
.image-two {
background-image:url(/img/image-two.jpg") ;
}
Functions are used to perform calculations. A Sass function does not output any CSS. Instead, it returns a value that can be used in the CSS.
@function calculate-width ($col-span) { @return 100% / $col-span } .span-two { width: calculate-width(2); // spans 2 columns, width = 50% } .span-three { width: calculate-width(3); // spans 3 columns, width = 33.3% }
Overusing nested rules in Sass can cause a lot of issues, from complex code to over-specificity and too much reliance on the HTML structure of a page.
Use nesting when it makes sense to, not as a default option.
All Sass features are useful when used in the correct situations and in moderation.
http://sass-lang.com/
http://thesassway.com
http://css-tricks.com/sass-style-guide/
http://alistapart.com/article/getting-started-with-sass
http://alistapart.com/article/a-vision-for-our-sass
http://thesassway.com/intermediate/using-source-maps-with-sass
By Jeff Huang