对于一名学习前端开发的入门者而言,是否系统地掌握前端开发的规范,将会关系到其日后学习效率是否高效。然而很令人无奈的一个现状,通过网络学习前端知识,例如浏览博客和论坛社区,学到的知识基本上都是破碎的。
就拿浏览器兼容来说,很多人的博客内容,都是记述自己是如何解决了某个具体的兼容问题,然后便结束了。很少有人会写一系列的教程出来,总结浏览器的兼容问题。即使有人写了总结性的文章,如愚人码头的《IE6的疯狂》系列(http://www.css88.com/archives/579),也是不全的。当你遇上实际的兼容性问题时候,又得通过搜索引擎来寻找相关解决文章,这便导致我们学习的前端知识很零碎。
说回刚才提到的前端开发规范,它的内容比浏览器兼容更加琐碎。记得我刚刚学前端的时候,因为觉得给标签起名字很麻烦,于是便上网搜索“html标签命名”。学习后,当时虽然有些许关于前端规范的意识,但是却没有继续搜索下去。也便是这样的陆陆续续,在往后的学习中,我又了解了“CSS属性书写顺序”、“CSS类名组合”、“CSS reset”等知识。由于时间的跨度有点长,这些知识都不能很好的结合起来,形成不了系统性的体系。
学习了一年的前端,我越来越迫切地要将前端规范的知识系统梳理一遍,以提高自己代码的质量。由于之前工作室的两个项目,自己一直没空看一些经典的书目。近日阅读曹刘阳(网名阿当)的《编写高质量代码——Web前端开发修炼之道》时,才发现这正是我需要的前端规范书籍。
以下是我的读书笔记:
1、语义化
1 <div class="title"> 2 <h2>标签的语义</h2> 3 <a href="#">更多</a> 4 </div> 5 <p>内容内容内容<strong>需要重点突出的部分</strong></p>
学过前端的人,都听说过语义化。在本书里面,语义化包括:
a、html标签使用是否符合其自身语义,例如这里的<h2></h2>标签便体现了其语义——用于标题。
b、id或者class的命名是否语义化。例如我们给div添加class="nav",便是指明它将会用于网页的导航。
c、javascript的函数、变量是否语义化。在命名的时候,我们一般采用驼峰命名法。
再看一个例子:
1 <form action="#" method="post"> 2 <fieldset> 3 <legend>登陆表单</legend> 4 <p><label for="name">账号:</label><input type="text" id="name" /></p> 5 </fieldset> 6 </form>
这里面的要注意的是:
a、自己补全<fieldset>标签。虽然说不写的话,浏览器也会帮你自动生成,但是有写的话,加载速度会比没写快。
b、用<legend>标签的语义,说明form标签的用途。
c、用<label for="name">标签关联id为“name”的input标签。
table的例子:
1 <table border="1"> 2 <caption>动物数据</caption> 3 <thead> 4 <tr> 5 <th>编号</th> 6 <th>种类</th> 7 <th>保存方式</th> 8 </tr> 9 </thead> 10 <tbody> 11 <tr> 12 <td>1</td> 13 <td>小鼠</td> 14 <td>冷藏</td> 15 </tr> 16 </tbody> 17 </table>
注意点和上个例子差不多,就是补全语义化的标签。
2、base.css(片段)
1 .mb5{margin-bottom:5px}/*CSS reset*/ 2 body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,form,fieldset,input,textarea,p, 3 blockquote,th,td {margin:0;padding:0;} 4 table {border-collapse:collapse;border-spacing:0;} 5 fieldset,img {border:0} 6 address,caption,cite,code,dfn,em,strong,th,var 7 {font-style:normal;font-weight:normal} 8 ol,ul {list-style:none} 9 caption,th {text-align:left} 10 h1,h2,h3,h4,h5,h6 {font-size:100%;font-weight:normal} 11 q:before,q:after {content:\'\'} 12 abbr,acronym { border:0} 13 /*文字排版*/ 14 .f12{font-size:12px} 15 .f13{font-size:13px} 16 .f14{font-size:14px} 17 .f16{font-size:16px} 18 .f20{font-size:20px} 19 .fb{font-weight:bold} 20 .fn{font-weight:normal} 21 .t2{text-indent:2em} 22 .lh150{line-height:150%} 23 .lh180{line-height:180%} 24 .lh200{line-height:200%} 25 .unl{text-decoration:underline;} 26 .no_unl{text-decoration:none;} 27 /*定位*/ 28 .tl{text-align:left} 29 .tc{text-align:center} 30 .tr{text-align:right} 31 .bc{margin-left:auto;margin-right:auto;} 32 .fl{float:left;display:inline} 33 .fr{float:right;display:inline} 34 .cb{clear:both} 35 .cl{clear:left} 36 .cr{clear:right} 37 .clearfix:after{content:".";display:block;height:0;clear:both;visibility:hidden} 38 .clearfix{display:inline-block}* html .clearfix{height:1%}.clearfix{display:block} 39 .vm{vertical-align:middle} 40 .pr{position:relative} 41 .pa{position:absolute} 42 .abs-right{position:absolute;right:0} 43 .zoom{zoom:1} 44 .hidden{visibility:hidden} 45 .none{display:none} 46 /*长度高度*/ 47 .w10{width:10px} 48 .w20{width:20px}
这份清单里面的样式,主要是用于后面提到的css组合样式。
此外,这里面还提到了不同工程师命名空间的概念。(话说,这在JS里面就经常听说,但是css版的还是第一次)
假设有两位工程师,分别是A和B。
他们的css和html代码为了解决冲突,应该这样写:
css:
1 <style type=”text/CSS”> 2 /*made by 工程师A*/ 3 .ad-timeList{xxxxxxx} 4 .ad-timeList li{border-bottom:xxxx;} 5 .ad-timeList-lastItem{border-bottom:none;} 6 ... 7 /*made by 工程师B*/ 8 .zx-timeList{} 9 .zx-timeList li{border-bottom:xxxx;} 10 </style>
html:
1 <!--made by 工程师A--> 2 <ul class=”ad-timeList”> 3 <li>2009 年08 月(3)</li> 4 <li>2009 年07 月(12)</li> 5 <li>2009 年06 月(3)</li> 6 <li>2009 年05 月(8)</li> 7 <li>2009 年04 月(2)</li> 8 <li class=”ad-timeList-lastItem”>2009 年03 月(8)</li> 9 </ul> 10 ... 11 <!--made by 工程师B--> 12 <ol class=”zx-timeList”> 13 <li>2009-08-07</li> 14 <li>2009-08-06 </li> 15 <li>2009-08-05</li> 16 </ol>
通过使用前缀,避免命名冲突。
3、css组合(组件)
css组合,意思就是说一个标签里面含有多个class。这样做的好处,就是可以提取相似功能标签的相同属性出来,作为一个共用class,然后添加其他class来记录它们的不同。
现在很热门的bootstrap就用到css组合,我们不妨看一下例子:
1 <div class="btn-group btn-group-lg">...</div> 2 <div class="btn-group">...</div> 3 <div class="btn-group btn-group-sm">...</div> 4 <div class="btn-group btn-group-xs">...</div>
这里面的class="btn-group"定义了它们的作用是按钮组,然后class="btn-group"加上class="btn-group-lg",就产生了第一组按钮的效果,按钮比下面的几组都大块。
4、不确定宽度块元素水平居中。
a、使用table标签,利用其内容自动居中的属性布局。
1 <style type="text/css"> 2 ul{list-style: none;margin: 0;padding: 0;} 3 table{margin-left: auto;margin-right: auto;} 4 .test li{float: left;display: inline;margin-right: 5px;} 5 .test a{float: left;width: 20px;height: 20px;text-align: center;line-height: 20px;background-color: #316ac5;color: #fff;border: 1px solid #316ac5;text-decoration: none;} 6 .test a:hover{background: #fff;color: #316ac5;} 7 </style>
1 <div class="wrap"> 2 <table> 3 <tr> 4 <td> 5 <ul class="test"> 6 <li><a href="#">1</a></li> 7 </ul> 8 </td> 9 </tr> 10 </table> 11 <table> 12 <tr> 13 <td> 14 <ul class="test"> 15 <li><a href="#">1</a></li> 16 </ul> 17 </td> 18 </tr> 19 </table> 20 </div>
很明显,html代码里面,添加了很多非语义化的标签,这种方式,我是反对的。现在网上有种纯css打造二级导航效果,也是用到了table标签。个人觉得这种形式,挑战一下就好,工作中真心不提倡使用。
b、父元素添加text-align:center;子元素则用display:inline;
1 <style type="text/css"> 2 ul{list-style: none;margin: 0;padding: 0;} 3 .test{text-align: center;padding: 5px;} 4 .test li{display: inline;} 5 .test a{padding: 2px 6px;background: #316ac5;color: #fff;border: 1px solid #316ac5;text-decoration: none;} 6 .test a:hover{background: #fff;color: #316ac5;} 7 </style>
1 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 9 9 10 10 11 11 12 12 13 <div class="wrap"> 14 <ul class="test"> 15 <li><a href="#">1</a></li> 16 </ul> 17 <ul class="test"> 18 <li><a href="#">1</a></li> 19 <li><a href="#">2</a></li> 20 <li><a href="#">3</a></li> 21 <li><a href="#">4</a></li> 22 <li><a href="#">5</a></li> 23 </ul> 24 </div>
c、父元素添加 float:left; position:relative; left:50%;属性,子元素则添加 position:relative;left:-50%;属性。
1 <style type="text/css"> 2 ul{list-style: none;margin: 0;padding: 0;} 3 .wrap{background: #000;width: 500px;height: 100px;} 4 .test{clear: both;padding-top: 5px;float: left;position: relative;left: 50%} 5 .test li{float: left;display: inline;margin-right: 5px;position: relative;left: -50%;} 6 .test a{float: left;width: 20px;height: 20px;text-align: center;line-height: 20px;background: #316ac5;color: #fff;border: 1px solid #316ac5;text-decoration: none;} 7 .test a:hover{background: #fff;color: #316ac5;} 8 </style>
1 <div class="wrap"> 2 <ul class="test"> 3 <li><a href="#">1</a></li> 4 </ul> 5 <ul class="test"> 6 <li><a href="#">1</a></li> 7 <li><a href="#">2</a></li> 8 <li><a href="#">3</a></li> 9 <li><a href="#">4</a></li> 10 <li><a href="#">5</a></li> 11 </ul> 12 </div>
这里面不知道有人发现一个有趣的地方没, 就是a标签竟然一设置width和height,而且生效了。
我们都知道,设置width和height是块元素的属性,行内元素是设置不了的。但是这里的a标签为何又能设置呢。原因很简单,它有float属性。float对行内元素的意义,就是可以设置width和height;简单的来说,就是成块元素。