20条书写 CSS 代码的建议
`在这篇文章中,我想跟你分享 20 条由CSS
社区推荐的约定和最佳实践。 有些建议可能比较适合新手,而有些则更高级一些,但我希望每个人都可以在本篇文章中收获自己不知道的知识。
1. 谨慎使用外边距属性
与其它的属性不同,垂直方向上的外边距相遇时将会发生折叠。这意味着如果一个元素的下边距遇到了另一个元素的上边距,那么二者中较大的一个将被留下。下面是一个简单的例子。
<div class="square red"></div>
<div class="square blue"></div>
.square {
width: 80px;
height: 80px;
}
.red {
background-color: #F44336;
margin-bottom: 40px;
}
.blue {
background-color: #2196F3;
margin-top: 30px;
}
其实上述两个元素在垂直方向上的距离并不是 70px, 而是 40px, 蓝色正方形的margin
没有被计算在内。 有很多的方法消除这种默认的行为,但最好的方法是只使用一个方向上的margin
属性,比如说margin-bottom
。
2. 利用盒子模型布局
盒子模型自然有其存在的理由。float
和inline-block
当然也可以工作,但它们都是样式化文档的基础工具,而不是整个网站。从某种意义来说,Flexbox
是为更容易更精确创建我们想要的布局而设计的。
Flexbox
模型提供的一系列属性给了开发者更大的灵活性,而且你一旦熟悉了它们,那创建任何响应式布局都是轻而易举的事。浏览器对Flexbox
的支持也已经接近完美,所以已经没有什么理由能够阻止你使用Flexbox
了。
.container {
display: flex;
/* Don't forget to add prefixes for Safari */
display: -webkit-flex;
}
3. 执行 CSS 重置
尽管这些年来情形已经有所好转,但是各浏览器的默认行为还是存在很多分歧。解决这个问题最好的办法就是使用一个CSS
重置文件为所有元素重新设置默认样式。这可以让你在一个纯净的样式环境下工作,并且在所有浏览器中产生相同的结果。
有很多的库做这个工作做的非常不错,比如 normalize.css, minireset, 和 ress, 纠正了浏览器间的不一致。如果你不想使用库,你也可以自己制作一个简单的CSS
重置,像下面这样。
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
这可能看上去比较苛刻,但是消除了默认的margin
和padding
我们将更容易的摆放我们的元素,而不用担心它会占用额外的空间。`box-sizing: border-box是一个很受用的属性,我们将在下面介绍这个属性。
4. 为所有元素使用 Border-box
许多初学者不知道box-sizing属性,但它的确很重要。了解它的最好办法就是看看它的两个可选值。
-
content-box
(default) - 当我们为元素设置了宽度和高度,但那只是内容的尺寸。所有的padding
和border
都在不包含在内容当中,也就是在内容的外部。举例来说,如果我们有一个div
它的宽度为 100px,padding为 10px, 那么它的实际宽度为 120px。 -
border-box
-padding
和border
被包含在 宽度和高度当中。 如果一个div
的宽度为100px,而被设置了box-sizing
:border-box
, 那么它的宽度将始终是100px, 无论你添加多少padding
和border
。
为所有元素设置border-box
将有利于样式化,而且你在也不用做乏味的数学运算了。
5. 图像作为背景
当你为自己的站点添加图片时,尤其是你想做响应式设计的时候,利用一个div
标签并为其设置background
属性,而不是使用<img>
元素。
似乎额外的工作并没有起到任何作用,但实际上这更利于你对图片设置样式,保持它们原有的尺寸或者根据比例变化,这需要借助background-size
,background-size
还有一些其它的属性。
<section>
<p>Img element</p>
<img src="" alt="bicycle">
</section>
<section>
<p>Div with background image</p>
<div></div>
</section>
img {
width: 300px;
height: 200px;
}
div {
width: 300px;
height: 200px;
background: url('');
background-position: center center;
background-size: cover;
}
section{
float: left;
margin: 15px;
}
这种技术的一个缺点是你页面的可访问性可能略有打击,因为你的图片不会被屏幕阅读器和引擎正确抓取。 这个问题可以被 object-fit 解决,但它还不被所有浏览器支持。
6. 更好的 Table 边框
HTML
中的table
没什么意思。它们非常古怪,难以设计成响应式的,而且很难与整体风格一致。比如说,你想为table
和其中的元素添加上边框,你可能会得到下面的结果。
正如你所见到的,它有很多重复的边框而且看起来不是很好,有一个非常快速且简单的去除双边框的方法,就是将
border-collapse: collapse
添加到table
.这样看起来就好多了。
7. 更好的注释方式
CSS
可能不是一门编程语言但它的代码仍然需要被记录,所以一些简单的注释将会对你的同事或者未来的自己很有帮助!
对于CSS
中的一些比较大的模块,比如主要模块或者媒体查询,使用风格化的注释并且在其后留下一些空行。
/*---------------
#Header
---------------*/
header { }
header nav { }
/*---------------
#Slideshow
---------------*/
.slideshow { }
设计中的一些细节或那些不是特别重要的模块,可以用单行注释。
/* Footer Buttons */
.footer button { }
.footer button:hover { }
另外,值得注意的是,CSS
中没有//
注释,所以当你需要注释的时候你需要使用/* */
符号。
/* Do */
p {
padding: 15px;
/*border: 1px solid #222;*/
}
/* Don't */
p {
padding: 15px;
// border: 1px solid #222;
}
8. 命名连接
当class
或者id
不止一个单词的时候,需要使用-
符号连接,CSS
对大小写不敏感,所以骆驼命名法不是一个好的选择。很久以前,下划线不被支持所以破折号成为了默认约定。
/* Do */
.footer-column-left { }
/* Don't */
.footerColumnLeft { }
.footer_column_left { }
9. 不要重复设置
CSS
的许多属性值都是从DOM树中的上一级继承下来的,因此命名为层叠样式表。让我们以font
为例 - 它几乎总是继承自父节点,你不需要为页面中的每一个元素设置该属性。
你只需要为<html>
或者<body>
设置font
样式,然后让它一级一级流传下去就可以了。 下面是一个很好的例
子。
html {
font: normal 16px/1.4 sans-serif;
}
当然,在任何一个子元素中你都可以按照自己的需求改变这一样式。我要说的就是能使用继承获得的属性就不要再去一一指定了。
10. CSS 动画与变换
不要通过直接更改元素的宽度和高度去动画元素,或者是更改left/right/top/bottom
。最好的办法是使用transform()
属性因为它提供了更加圆滑的过渡效果而且可以让你的意图在阅读代码时更加易于理解。下面是一个例子,我们想动画一个ball
,让它往右滑动。 不要去改变left
的值,最好是使用translateX()
。
.ball {
left: 50px;
transition: 0.4s ease-out;
}
/* Not Cool*/
.ball.slide-out {
left: 500px;
}
/* Cool*/
.ball.slide-out {
transform: translateX(450px);
}
transform
以及它的所有方法(translate, rotate, scale
等)拥有几乎一致的浏览器兼容性,你可以自由使用它们。
11. 不要 DIY, 使用库
CSS
社区非常的庞大而且不断出现新的库。 库被提供于各种用途,从小片段到完善的框架,用于构建响应式程序,而且它们当中大部分都是开源的。
所以下次当你碰到CSS
问题的时候,在你想自己动手去解决问题的时候,最好先去Github
或者CodePen
找找是否已经存在可用的解决方案。
12. 保持选择器的特指度低
不是所有CSS
选择器都是生而相等的,当新手开发者书写CSS
代码的时候通常期望它们写的选择器能够覆盖之前所有已存在的样式。 但是事情并不总像我们想的那样,就像下面这个例子:
a{
color: #fff;
padding: 15px;
}
a#blue-btn {
background-color: blue;
}
a.active {
background-color: red;
}
我们想为所有按钮添加.active
类使其变为红色,但这是不起作用的,因为按钮已经被一个id
选择器设置了background-color
,而id
选择器具有更高的特指度。它们之间的规则就像下面这样:
ID (#id
) > Class (.class
) > Type (比如header
)。
特指度是可以堆叠的,所以a#button.active
的特指度是高于a#button
的。 使用特指度高的选择器将使你不断的使用更高的去覆盖那些原本存在的选择器,这将最终导致!important
效果。
13. 不要使用 !important
很认真的告诉你,不要使用!important
。 即时的一个快速修复在将来可能导致大量的重写。相反,找出你CSS
选择器不工作的原因,并且尝试去修复它。
只有在一种情景中使用!important
是可以接受的,那就是你想覆盖那些在HTML
中定义的行内样式。而且书写行内样式也是一种非常糟糕的方式,建议停止使用。
14. 使用 text-transform
在HTML
中,当你使用大写字母的时候可能是出于某种语义目的,比如说你想强调一个单词的重要性。
<h3>Employees MUST wear a helmet!</h3>
如果出于某种目的你将一组文本都设置成大写,可以在HTML
中正常书写文本,然后利用CSS
转换其大小写。 它们看起来都是一样的,但是如果不在上下文中,你的内容将更有意义。
<div class="movie-poster">Star Wars: The Force Awakens</div>
.movie-poster { text-transform: uppercase;}
这同样适用于大写或者小写的字符串 -text-transform
属性可以将它们处理的很好。
15. Em, Rem 和 Pixel
人们在对元素和文本设置尺寸应该用em
,rem
还是px
有很多的争论。事实是,这三者都是可行的,有自己的优点和缺点。
所有的开发者和项目都是不同的,所以不应该有什么严格的规则说明什么时候该用哪一种。下面是一些提示和良好的做法:
-
em
-1em
的大小与直接父元素的字体大小有关。 通常用于媒体查询,em
对响应式设计而言是非常棒的 ,但是将每个元素的em
值转换为p
的比例是非常难以计算的,因为你可能要在DOM
树上逐级跟踪元素。 -
rem
- 以<html>
元素中的font-size
为基准,rem
将比例化页面中的标题和段落变得很容易。保持<html>
中默认的font-size
并且为其它的元素设置rem
是一种非常棒的方法。 -
px
- 像素是最精确的控制方式,但是在 响应式设计中它并不友好,因为它不会随屏幕大小变化而自动缩放。它们是可靠的,易于理解的,并且在值和实际结果之间呈现出良好的视觉联系。
下面我要说的是,不要害怕尝试。去使用它们并且找出哪一种是你最喜欢的。 有时候em
和rem
很省事,尤其对于响应式界面。
16. 在大项目中使用预处理器
你可能已经听说过它们了 - Sass, Less, PostCSS, Stylus 。预处理器是CSS
发展的下一阶段。 它们提供的功能诸如变量,CSS
函数,选择器嵌套以及其它一些非常酷的东西。这使得CSS
代码非常易于管理,尤其在大项目中。
举个简单的例子,下面是使用了CSS
变量和函数的Sass
代码片段。
$accent-color: #2196F3;
a { padding: 10px 15px; background-color: $accent-color; }
a:hover { background-color: darken($accent-color,10%); }
使用CSS
预处理器的唯一缺点是,它们需要编译成真正的CSS
代码,但是如果你已经决定在你的项目中使用一个构建脚本,那么这就不再是你应该烦恼的问题了。
如果你想了解更多关于预处理器的知识,请查看目前最受欢迎的两个系统的教程 - Sass 和 Less.
17. Autoprefixers
为各个浏览器添加前缀算得上是书写CSS
代码最恼人的问题了。它们不一致,你永远无法精确的你需要哪一个,而且如果你真的去一个个适配并将它们都放到样式表中,你会发现这是一场噩梦。
感谢上天,有很多工具可以自动的帮你实现这一过程,甚至可以让你指定你需要支持的浏览器 :
- 在线工具: Autoprefixer
- 文本编辑器插件 - Sublime Text, Atom
- 库 - Autoprefixer
18. 在项目中使用精简代码
为了提高网站或app
的页面加载速度我们需要总是使用精简代码 . 代码的精简版本会移除掉空白和重复的部分,这样会削减文件的大小. 当然,这样的话你的CSS
代码将会变得非常难以阅读,所以最好总是提供一个.min
的精简版本和一个常规的发展版本.
有很多不同的方法去精简CSS
代码 :
- 在线工具 - CSS Minifier, CSS Compressor
- 文本编辑插件 - Sublime Text, [Atom]* (https://atom.io/packages/atom-minify)
- 库 - Minfiy , CSSO 和 CSSNano
根据你的工作流程,你可以选用上述一个选项,但是建议你总是使用某种方式自动执行此过程.
19. Can I Use
不同的浏览器仍然存在着很多不一致的兼容性问题, 利用 caniuse 或者其它类似的服务检测你正在使用的属性是否被广泛支持, 是否需要添加前缀, 或者说是否会在某平台下出现bug
.
仅仅检测是否仍然是不够的, 你仍然需要测试布局是否会无缘无故的崩溃. 充分了解用户经常使用的浏览器也会提供很大的帮助, 因此你可以看到好的支持是非常关键的.
20. Validate
验证CSS
代码可能没有验证HTML
或者JavaScript
代码重要, 但是在一个CSS
验证器上运行你的代码还是有帮助的, 它会提示你是否书写了错误或者比较糟糕的代码, 甚至会给出一些比较中肯的建议帮助你改进代码.
有很多的工具可以完成这一工作.
-
在线工具 - W3 Validator, CSS Lint
-
文本编辑器插件 - Sublime Text, Atom
-
库 - stylelint (Node.js, PostCSS), css-validator (Node.js)
当然,你可以 查看原文
Ending...