一篇文章包你學會使用pure.css框架,理解其原理,并學會其包含css知識,學會自己寫css組件
前提知識
選擇器介紹
優先級就是分配給指定css聲明的一個權重,它由匹配的選擇器中的每一種選擇器類型的數值決定。而當優先級與多個css聲明中任何一個聲明的優先級相等時,css中最后的那個聲明將會被應用到元素上。
選擇器是用于定位文檔中的元素以便設定相應的樣式代碼
-
選擇器分類
基礎選擇器
選擇器 | 含義 | 實例 |
---|---|---|
* | 通用選擇器,匹配任何元素 | *{font-size:16px} |
E | 標簽選擇器,匹配所有使用E標簽的元素 | a{font-size:16px} |
.error | class選擇器,匹配所有class屬性中包含error的元素 | .error{font-weight:bold;} |
#correct | id選擇器,匹配所有id屬性值為correct的元素 | #correct{font-style:italic;} |
? 組合選擇器
選擇器 | 含義 | 實例 | |
---|---|---|---|
E,F | 多元素選擇器,同時匹配所有E元素或F元素 | div,p{background-attachment:fixed;} | |
E F | 后代元素選擇器,匹配所有屬于E元素的后代F元素 | div a{background-color:blue;} | |
E>F | 子元素選擇器,匹配所有E元素的子元素F | ||
E+F | 毗鄰元素選擇器,匹配所有緊隨E元素之后的同級元素F |
屬性選擇器
選擇器 | 含義 | 實例 |
---|---|---|
E[att] | 匹配所有具有att屬性的E元素 | p[style]{background-repeat:repeat:repeat-y;} |
E[att=val] | 匹配所有att屬性等于"val"的E元素 | div[class="c1"] |
E[att~=val] | 匹配所有att屬性具有多個空格分隔的值、其中一個值等于"val"的E元素 | div[class~=c2] |
E[att=val] | 匹配所有att屬性具有多個連字號分隔(hyphen-separated)的值、其中一個值以"val"開頭的E元素 | p[lang =en] |
? 偽類選擇器
選擇器 | 含義 | 實例 |
---|---|---|
E:first-child | 匹配父元素E下的第一個子元素 | div:first-child{text-align:center;} |
E:link | 匹配所有未被點擊的鏈接 | |
E:visited | 匹配所有已被點擊的鏈接 | |
E:active | 匹配鼠標懸停其上的E元素 | |
E:hover | 匹配鼠標懸停其上的E元素 | |
E:focus | 匹配獲得焦點的E | |
E:lang(c) | 匹配lang屬性等于c的E元素 |
? 偽元素
選擇器 | 含義 | 實例 |
---|---|---|
E:first-line | 匹配E元素的第一行 | p:first-line{color:red;} |
E:first-letter | 匹配E元素的第一個字母 | .c1:first-letter{color:blue;} |
E:before | 在E元素之前插入生成的內容 | .ctn before{} |
E:after | 在E元素之后插入生成的內容 | .ctn after{} |
優先級的計算
(解釋了眾多css樣式被覆蓋的問題)
首先!important的css定義是擁有最高的優先級
優先級計算分為a,b,c,d四個位數,這四個位數的優先級依次遞減。
內聯樣式:a=1;
ID選擇器:b=1;
屬性選擇器和類選擇器:c=1;
元素選擇器和偽類選擇器: d=1;
li {} /* a=0 b=0 c=0 d=1 -> specificity = 0,0,0,1 */
li:first-line {} /* a=0 b=0 c=0 d=2 -> specificity = 0,0,0,2 */
ul li {} /* a=0 b=0 c=0 d=2 -> specificity = 0,0,0,2 */
ul ol+li {} /* a=0 b=0 c=0 d=3 -> specificity = 0,0,0,3 */
h1 + *[rel=up]{} /* a=0 b=0 c=1 d=1 -> specificity = 0,0,1,1 */
ul ol li.red {} /* a=0 b=0 c=1 d=3 -> specificity = 0,0,1,3 */
li.red.level {} /* a=0 b=0 c=2 d=1 -> specificity = 0,0,2,1 */
#x34y {} /* a=0 b=1 c=0 d=0 -> specificity = 0,1,0,0 */
style="" /* a=1 b=0 c=0 d=0 -> specificity = 1,0,0,0 */
文檔流
(主要應用于menu中,垂直和水平導航欄)
css文檔流(document flow)和普通流(normal flow)實際上指的是同一個概念。
文檔流 指的是元素按照在HTML中為的位置順序決定排布的過程,在排布過程中,將窗體自上而下分為一行行,并在每行中從左至右的順序排放元素。
非浮動的塊級元素(block)獨占一行,行內元素(inline)不會獨占一行。
塊級元素的效果
<div style=" width:100px; height:100px; border: 1px solid">div1</div>
<div style=" width:100px; height:100px; border: 1px solid">div2</div>
內聯元素的效果
<a href="http:">超鏈接1</a>
<a href="http:">超鏈接2</a>
絕對定位
(主要是用于含有重疊菜單的子菜單定位問題)
絕對定位其實是相對了某個東西的,而這個東西就是元素的第一個有position且position不能為static的祖先元素。就是這個東西必須是有一定地位的(position:absolute或position:relative),不能是一個窮鬼(position:static)或者沒有地位的(position).這個時候,絕對定位,它才能以之為標桿。
給他爸爸加上相對定位,然后他是絕對定位
<div style=" border:1px solid Red; padding:10px; width: 340px; height: 400px"">
紅色:太公
<div style="border:1px solid Green; padding:10px; width: 320px; height: 360px;">
綠色:爺爺
<div style="border:1px solid Yellow; padding:10px; width: 300px; height: 320px;position:relative; ">
黃色:老爸
<div style="width: 100px; height: 100px;border:1px solid">
div1</div>
<div style="width: 100px; height: 100px;border:1px solid;position:absolute;left:120px; top:100px;">
div2</div>
<div style="width: 100px; height: 100px;border:1px solid">
div3</div>
</div>
</div>
</div>
基礎
所有pure模塊都是基于normalize.css構建,對比base.css詳細normalize.css內容請查看《Normalize.css》
<link rel="stylesheet" >
Normalize.css是一個小的CSS文件,為HTML元素樣式提供跨瀏覽器的一致性。它是一個現代的、支持HTML5的、傳統CSS重置的替代。
html {
font-family: sans-serif; /* 1 */
//無襯線體,字的比劃開始及結束地方沒有額外裝飾
-ms-text-size-adjust: 100%; /* 2 */
-webkit-text-size-adjust: 100%; /* 2 */
//iPhone 和 Android 的瀏覽器縱向 (Portrate mode) 和橫向 (Landscape mode) 模式皆有自動調整字體大小的功能。控制它的就是 CSS 中的 -webkit-text-size-adjust。text-size-adjust 設為 none 或者 100% 關閉字體大小自動調整功能.
}
abbr[title] {
border-bottom: 1px dotted;
}
//縮略詞顯示詳情,含有title屬性的abbr標簽縮略詞的底部邊線
svg:not(:root){
overflow: hidden;
}
//svg(可縮放矢量圖形),是基于可擴展標記語言(XML),用于描述二維矢量圖形
:root,匹配文檔的根元素,在HTML中,根元素永遠是HTML
:not(selector)選擇器匹配非指定元素
則以上是svg非根元素的元素
隱藏元素
[hidden],
template {
//template模板標簽
display: none;
}
.hidden,
[hidden] {
//!important最高優先級
display: none !important;
}
html元素添加hidden屬性,可以實現display:none !important;
<input type="text" name="_csrf" hidden>
響應式圖片
添加class .pure-img,配合viewport可以實現圖片伸縮
.pure-img {
//最小寬度(min-width)與最大寬度(max-width)用于設置圖片最小最大寬度限制比較多。
比如一個圖片為主列表,對象里圖片大小不定時候,為了不想讓他太小不統一這個時候我們可以使用css最小寬度樣式。再如,一個盒子里有文章有圖片混排的時候,有時圖片寬度不能確定,這個時候如果html img圖片寬度超出了盒子寬度,可能圖片就會撐破div盒子造成圖片混亂。
max-width: 100%;
height: auto;
display: block;
}
max-width詳細情況可以查看《CSS max-width 屬性》
柵格
.pure-g的樣式
letter-spacing: -0.31em;
1em == 16px,因為瀏覽器默認的字體大小是16px,em可以在瀏覽器改變字體大小時作出相應的放大和縮小,彈性布局
*word-spacing: -0.43em
在樣式屬性名前加*,這樣的樣式可以被IE6和IE7所識別,而其它瀏覽器則會當做錯誤忽略,所以,這樣的樣式寫法只對IE6/7生效.
而_開頭的屬性只有IE6才能識別.
關于letter-spacing和word-spacing的區別
word-spacing屬性增加或減少單詞之間的空白
letter-spacing屬性增加或減少字符之間的空白
text-rendering: optimizespeed;
text-rendering屬性常被用在windows和linux系統中,用來給渲染引擎提供信息,讓文本在速度和可讀性方面得到優化,控制在線字體的微妙細節,目前只有firefos和google支持。
optimizespeed取值 Gecko內核的瀏覽器將強調可讀性和幾何精度,同時繪制文本渲染速度,禁用字距和連寫
font-family: FreeSans, Arimo, "Droid Sans", Helvetica, Arial, sans-serif;
常用的字體
display: -webkit-box;/* Chrome 4+, Safari 3.1, iOS Safari 3.2+ */
display: -webkit-flex;/* Chrome 21+, Safari 6.1+, iOS Safari 7+, Opera 15/16 */
display: -ms-flexbox;/* IE 10 */
display: flex; /* Chrome 29+, Firefox 22+, IE 11+, Opera 12.1/17/18, Android 4.4+ */
webkit是一個開源的瀏覽器引擎,與之對應的有Gecko和Trident,加上之后表示私有屬性
-moz代表firefox瀏覽器私有屬性
-ms代表IE瀏覽器私有屬性
-webkit代表chrome、safari私有屬性
關于display:box和display:flex的區別
flex是2012年以后的標準語法,大部分瀏覽器已經實現了無前綴版本,box是2009年語法,需要加上前綴
以上其實是該屬性的兼容性代碼
flex布局,彈性布局,用來為盒裝模型提供最大的靈活性
通過添加.pure-g和未添加進行對比,可以發現,.pure-g的效果主要就是flex屬性,而flex屬性在此處的重要作用是給.pure-u元素添加float浮動屬性
-webkit-flex-flow: row wrap;
-ms-flex-flow: row wrap;
flex-flow: row wrap;
flex-flow:<flex-direction>||<flex-wrap>
row表示行內方向,即彈性項目在彈性容器中的起始放置方向,flex-wrap表示需要拆行以使得彈性項目能被容器包含
-webkit-align-content: flex-start;
-ms-flex-line-pack: start;
align-content: flex-start;
多行項目時,讓彈性元素始終排在頭部,中間沒有間距,詳細flex教程請查看《Flex布局教程:語法篇》
@media all and (min-width:xxx) and (max-width:xxx){
/*這段查詢的all是針對所有設備(有些設備不一定是屏幕,也許是打字機,盲人閱讀器)*/
table .pure-g {
display: block;
}
}
寫這一行是因為flex在ie10中的table時不起作用
.pure-g [class *= "pure-u"] {font-family: sans-serif;}
表示的是設置class屬性值包含有pure-u 字符串的所有pure-g元素的樣式
div[class^="something"] { }表示以之開始
div[class$="something"] { }表示以之結尾
.pure-u的樣式
.pure-u {
display: inline-block;
*display: inline; /* IE < 8: fake inline-block */
zoom: 1;
letter-spacing: normal;
word-spacing: normal;
vertical-align: top;
text-rendering: auto;
}
zoom: normal | <number> | <percentage>
? normal:使用對象的實際尺寸
? <number>:用浮點數來定義縮放比例
? <percentage>:用百分比來定義縮放比例
vertical-align垂直對齊屬性
.pure-u-x-y{
display: inline-block;
*display: inline;
zoom: 1;
letter-spacing: normal;
word-spacing: normal;
vertical-align: top;
text-rendering: auto;
}
這個樣式和.pure-u是相同的
pure柵格默認支持5列和24列
x/y表示的是列數所占的比重
.pure-u-1-24 {
width: 4.1667%;
*width: 4.1357%;
}
可以發現IE6\7和其他瀏覽器之間的寬度存在細微差別,微調后可修復
表單
.pure-form樣式
.pure-form input[type="text"]
不同的表單類型
padding: 0.5em 0.6em;
//設置表單內部填充
display: inline-block;
//顯示為行內元素
border: 1px solid #ccc;
//邊界線
box-shadow: inset 0 1px 3px #ddd;
//盒子陰影,inset設置在內邊框
border-radius: 4px;
//圓框邊角
vertical-align: middle;
//讓行內元素居中顯示,主要是表單
box-sizing: border-box;
//設置盒子尺寸
input:not([type]) //這個屬性需要分離出來,因為ie8在一堆css2.1中包含一個css3屬性的時候不會執行
:not()否定選擇器,可以讓你定位不該匹配該選擇器的元素,IE6-8瀏覽器不支持:not()選擇器
.pure-form input[type="color"]{
? padding: 0.2em 0.5em;
} //chrome顯示色彩選擇器需要額外的空間
input[type="text"]:focus {
outline:0;
border-color:#129FEA;
}
為聚焦的時候添加樣式
outline和boder區別
outline是不占空間的,既不會增加額外的width或者height
border可應用于幾乎所有有形的html元素,而outline是針對鏈接、表單控件和imageMap等元素,outline會隨元素focus出現,隨blur而消失
詳細的情況可以查看《深入淺析border和outline區別》
input[type="text"][disabled]
input[readonly]
這兩種寫法都會使顯示出來的文本框不能輸入文字
但disabled會使文本框變灰,而且通過request.getParameter("name")得不到文本框中的內容(如果有的話)
而readonly只是使文本框不能輸入,外觀沒有變化,而且通過request.getParameter("name")可以得到內容,可以復制
input:focus:invalid
同類型的方法
:required必須,要求input不能為空
:valid有效,即當填寫內容符合要求時觸發
:invalid無效,即當填寫內容不符合要求時觸發
可以看到符合要求時,顯示的邊框顏色為藍,右邊的沒有添加:focus選擇器的表單在無效的時候一直都是紅色
疑問:
input:focus:invalid和input:focus:invalid:focus差別并沒有試驗出來
.pure-form fieldset
.pure-form legend
fieldset和legend標簽的組合使用
實現的手段是添加border:0和border-bottom
.pure-form-stacked樣式
可以生成堆疊式表單,即為同一列
實現的手段是添加display:block將它變成塊級元素,獨占整行和margin: 0.25em 0;
.pure-form-aligned樣式
可以生成對齊式表單,label顯示在input左邊末端對齊
實現方式是將lable標簽display:inline-block顯示成行內元素,然后設置width使之可以撐滿,再設置text-align:right使之向右對齊,此時與表單過于靠近,添加margin屬性,使和表單之間間距變大。考慮到字數過長產生換行,使用vertical-align讓行內元素居中顯示
.pure-group樣式
可以為表單標簽分組,使用方法是為fieldset添加該class
其實兩者之間的差別并不大,主要是陰影部分,以及結束部分相連
方法是,先使用boder-radius:0將圓角樣式去除,然后使用:first-child和:last-child選擇器,重新設置這兩個元素的圓角等樣式,達到此效果
.pure-form .pure-group input:first-child:last-child
通過偽類選擇器設置第一個和最后一個同類標簽的樣式
.pure-form .pure-input-2-3
設置表單大小
按鈕
.pure-button樣式
//這個樣式應該主要是運用在移動端
display: inline-block;
//行內元素
zoom: 1;
//縮放比例
line-height: normal;
//默認行高
white-space: nowrap;
//如何處理元素內的空白,normal空白會被瀏覽器忽略,nowrap文本不會換行
vertical-align: middle;
//實現行內元素的水平居中
text-align: center;
//使文本水平居中
cursor: pointer;
-webkit-user-drag: none;
//user-drag:auto | element | none設置和檢索一個元素能否被拖拽
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
//user-select:none | text | all | element設置和檢索是否允許選中文本
box-sizing: border-box;
//設置的內邊距和邊框不會增加寬度
//網頁端主要樣式
.pure-button {
font-family: inherit;
font-size: 100%;
padding: 0.5em 1em;
color: #444; /* rgba not supported (IE 8) */
color: rgba(0, 0, 0, 0.80); /* rgba supported */
border: 1px solid #999; /*IE 6/7/8*/
border: none rgba(0, 0, 0, 0); /*IE9 + everything else*/
background-color: #E6E6E6;
text-decoration: none;
border-radius: 2px;
}
偽類選擇器樣式
//設置鼠標在上和焦點在上時的樣式
.pure-button-hover,
.pure-button:hover,
.pure-button:focus {
/* csslint ignore:start */
filter: alpha(opacity=90);
//透明度使用
/* csslint ignore:end */
background-image: -webkit-linear-gradient(transparent, rgba(0,0,0, 0.05) 40%, rgba(0,0,0, 0.10));
background-image: linear-gradient(transparent, rgba(0,0,0, 0.05) 40%, rgba(0,0,0, 0.10));
}
//用線性漸變創建圖像 rgba(0,0,0, 0.05) 40%和rgba(0,0,0, 0.10));分別為起始顏色和終止顏色,第一個參數一般是漸變方向,top 是從上到下、left 是從左到右,如果定義成 left top,那就是從左上角到右下角
線性漸變
linear-gradient([ [<angle>|to<side-or-cornor>],]?<color-stop>[,<color-stop>]+)
<color-stop> 用于指定漸變的起止顏色
詳細情況可以查看《css參考手冊》
疑問:
background-image: linear-gradient(transparent, rgba(0,0,0, 0.05) 40%, rgba(0,0,0, 0.10));
transparent這個參數的作用和效果
表格
.pure-table的樣式
.pure-table {
/* Remove spacing between table cells (from Normalize.css) */
border-collapse: collapse;
//為表格設置合并邊框模型
//collapse邊框會合并成一個單一邊框,忽略border-spacing和empty-cells屬性,而separate會使邊框分開,inherit規定應該從父元素繼承border-collapse屬性
border-spacing: 0;
//設置相鄰單元格邊框間的距離,不過僅用于邊框分離模式
empty-cells: show;
//設置是否顯示表格中的空單元格,僅適用于邊框分離模式
border: 1px solid #cbcbcb;
}
.pure-table caption表格標題
.pure-table td,.pure-table th,.pure-table thead
th:表頭單元格-包含表頭信息
td: 標準單元格-包含數據
thead:結合tbody和tfoot元素結合使用
.pure-table-odd td{
? background-color: #f2f2f2;
}
隔行添加可以實現斑馬紋的效果或者直接加上pure-table-striped
.pure-table-striped tr:nth-child(2n-1) td{
? background-color: #f2f2f2;
}
:nth-child(n)選擇器 規定屬于其父元素的第n格子元素,不論元素類型
:nth-of-type() 選擇器的意思是“規定屬于其父元素的第二個 p 元素”,這個需要從同類元素開始機選
.pure-table-bordered tbody > tr:last-child > td
有邊框的表格,>選擇器,可以縮小范圍,只選擇某個元素的子元素
菜單
.pure-menu的樣式
縱向菜單的實現
//設置盒子大小不因為boder變化
.pure-menu {
box-sizing: border-box;
}
//清除列表原有樣式
.pure-menu-list{
list-style: none;
margin: 0;
padding: 0;
}
//清除a標簽原有樣式,填充a標簽,并變為塊級元素
.pure-menu-link{
display: block;
text-decoration: none;
white-space: nowrap;
color: #777;
padding: .5em 1em;
}
//在父級元素使用inline-block將之變為行級元素并同一高度
.custom-restricted-width {
/* To limit the menu width to the content of the menu: */
display: inline-block;
/* Or set the width explicitly: */
/* width: 10em; */
}
//添加:hover,:link等樣式
.pure-menu-link:hover,
.pure-menu-link:focus {
background-color: #eee;
}
疑問之處:
inline-block怎樣自動確定并統一行級元素的寬度
橫向菜單的實現
//頭部樣式
.pure-menu-heading{
padding: .5em 1em;
display: block;
text-decoration: none;
white-space: nowrap;
text-transform: uppercase;
color: #565d64;
}
//給a標簽的父級標簽li標簽添加display:inline-block,使三個a標簽同行
.pure-menu-horizontal .pure-menu-item,
.pure-menu-horizontal .pure-menu-heading,
.pure-menu-horizontal .pure-menu-separator {
display: inline-block;
*display: inline;
zoom: 1;
vertical-align: middle;
}
//為li的父級ul標簽添加display:inline-block,使所有標簽同行
.pure-menu-horizontal .pure-menu-list {
display: inline-block;
}
//清除列表原有樣式,統一間距
.pure-menu-list{
list-style: none;
margin: 0;
padding: 0;
}
關鍵樣式
- 清除列表原有樣式
- 使用padding: .5em 1em填充a標簽
- 清除a標簽原有樣式
- 為a標簽的父級標簽li標簽添加display:inline-block,使三個a標簽同行
- 為標題的a標簽和li的父級ul標簽添加display:inline-block,使所有標簽同行
- 為ul標簽添加margin:0和padding:0清除ul原有樣式
含有子菜單的橫向菜單的實現
//樣式整合
.pure-menu-link{
display: block;
text-decoration: none;
white-space: nowrap;
//可自定義部分
color: #777;
padding: .5em 1em;
}
.pure-menu-list{
list-style: none;
margin: 0;
padding: 0;
}
//實現橫向菜單
.pure-menu-horizontal .pure-menu-list{
display: inline-block;
}
//實現下拉菜單符號
.pure-menu-horizontal .pure-menu-has-child > .pure-menu-lin:after{
content: "\25BE";
}
//子菜單的樣式
.pure-menu-children{
display: none;
position: absolute;
left: 100%;
top:0;
margin: 0;
padding: 0;
z-index: 3;
background-color: #fff;
}
//鼠標移動顯示下拉菜單
.pure-menu-allow-hover:hover > .pure-menu-child{
display: block;
position: absolute;
}
//子菜單移動至下方
.pure-menu-horizontal .pure-menu-children {
left: 0;
top: auto;
width: inherit;
}
content屬性與:before和:after偽元素配合使用,來插入生成內容
特殊字符 | 對應號碼 |
---|---|
? | 9658 25BA |
▲ | 9650 25B2 |
▼ | 9660 25BC |
? | 9668 25C4 |
含有子菜單的縱向菜單的實現
//顯示向右的箭頭
.pure-menu-has-children > .pure-menu-link:after {
padding-left: 0.5em;
content: "\25B8";
font-size: small;
}
//顯示隱藏的子元素
.pure-menu-allow-hover:hover > .pure-menu-children{
display: block;
position: absolute;
}
滾動菜單的實現
//限制了邊框才顯示滾動條
.custom-restricted {
height: 160px;
width: 150px;
border: 1px solid gray;
border-radius: 4px;
}
//y軸可滾動,x軸溢出隱藏
.pure-menu-scrollable {
overflow-y: scroll;
overflow-x: hidden;
}
//將li標簽設為塊級元素
.pure-menu-scrollable .pure-menu-list {
display: block;
}
//水平菜單時,顯示為行級元素
.pure-menu-horizontal.pure-menu-scrollable .pure-menu-list {
display: inline-block;
}
//水平菜單針對的只是移動端,觸摸橫向滾動
.pure-menu-horizontal.pure-menu-scrollable {
white-space: nowrap;
overflow-y: hidden;
overflow-x: auto;
//指示元素不顯示滾動條或者篩選指標,即使內容溢出
-ms-overflow-style: none;
//可以讓頁面在native端滾動時模擬原生的彈性滾動
-webkit-overflow-scrolling: touch;
/* a little extra padding for this style to allow for scrollbars */
padding: .5em 0;
}
//存在疑問
.pure-menu-horizontal .pure-menu-scrollable::-webkit-scrollbar {
display: none;
}