深入CSS
一、CSS的版本(level)
css Level 1- css Level 2(CSS2.2規範)
- css Level 3
- Color Module Level 3
- Selectors Level 3
- Media Queries
- Fonts Level 3
- ...
在css2.2之前,把css所有標準放在一起去管理,這樣推進起來版本升級比較難,後來在css3的版本中,將css標準分成幾個模組來管理。
二、css選擇器
1. 簡單選擇器
- 通配選擇器
*
- 標籤選擇器
E
- 類選擇器
.class-name
- Id選擇器
#id_name
2. 屬性選擇器
/* 具有某個屬性 */
[disabled]
/* 屬性為指定的值 */
[type="checkbox"]
/* 屬性值包含某個字串 */
[href*="example"]
/* 屬性值以某個字串開頭 */
[href^="http:"]
/* 屬性值以某個字串結束 */
[href$="jpg"]
/* 屬性值以空格分割後包含某個字串 */
[lang~="zh-cn"]
複製程式碼
3. 偽類選擇器
a:link { ... } /* 未訪問過的連結 */
a:visited { ... } /* 已訪問過的連結 */
a:hover { ... } /* 滑鼠移到連結上的樣式 */
a:active { ... } /* 滑鼠在連線上按下時的樣式 */
a:focus { ... } /* 獲得焦點時的樣式 */
input:disabled { ... } /* 禁用時的樣式 */
input:checked { ... } /* 選中時的樣式 */
複製程式碼
4. 結構性偽類
:first-child
:last-child
:nth-child
:first-of-type
:last-of-type
:nth-of-type
:empty
複製程式碼
詳細介紹在mdn 選擇器文件
5. 組合器(combinator)
後代組合器 E F
親子組合器 E > F
兄弟選擇器 E ~ F
相鄰兄弟 E + F
複製程式碼
6. 偽元素
::before
::after
::first-letter
::first-line
複製程式碼
舉個栗子?
<p>莫哈韋沙漠不僅緯度較高,而且溫度要稍微低些,是命名該公園
的短葉絲蘭——<a href="#">約書亞樹</a>的特殊棲息地。約書亞
樹以從茂密的森林到遠遠間隔等各種形式出現。除了約書亞樹森林之
外,該公園的西部包括加州沙漠裡發現的最有趣的地質外觀。</p>
<style>
p {
line-height: 1.7
}
p::first-letter {
line-height: 1.5;
background: #F44336;
color: #fff;
font-size: 200%;
float: left;
padding: 0 0.2em;
margin-right: 0.2em;
}
a::after {
content: '⚓'
}
</style>
複製程式碼
結果是這樣子的:
- 利用
::first-letter
把第一個文字選中,修改樣式。 - 利用
::after
把a標籤文字的最後面新增一個特殊文字。
再舉個栗子?
實現一個toggle
<div class="toggle">
<input type="checkbox" checked id="t">
<label for="t"></label>
</div>
<style>
.toggle {
width: 80px;
height: 26px;
background: #333;
margin: 20px auto;
position: relative;
border-radius: 50px;
box-shadow: inset 0px 1px 1px rgba(0,0,0,0.5),
0px 1px 0px rgba(255,255,255,0.2);
}
.toggle:after {
content: 'OFF';
color: #fff;
position: absolute;
right: 10px;
z-index: 0;
font: 12px/26px Arial, sans-serif;
font-weight: bold;
text-shadow: 1px 1px 0px rgba(255,255,255,.15);
}
.toggle:before {
content: 'ON';
color: #f66;
position: absolute;
left: 10px;
z-index: 0;
font: 12px/26px Arial, sans-serif;
font-weight: bold;
}
.toggle label {
display: block;
width: 34px;
height: 20px;
cursor: pointer;
position: absolute;
top: 3px;
left: 3px;
z-index: 1;
background: #fcfff4;
background: linear-gradient(top, #fcfff4 0%,
#dfe5d7 40%, #b3bead 100%);
border-radius: 50px;
transition: all 0.4s ease;
box-shadow: 0px 2px 5px 0px rgba(0,0,0,0.3);
}
.toggle input[type=checkbox] {
visibility: hidden;
}
.toggle input:checked + label {
left: 43px;
}
</style>
複製程式碼
toggle演示:
缺點:- 只能點選白色區域才能切換狀態
- 不能用鍵盤來控制
三、選擇器的特異度(權重)
解釋一下:- 特異度的演算法是:
- 內聯樣式在千位
- id在百位
- 類和偽類在十位
- 元素和偽元素在個位
#nav .list li a:link
包含1個id標籤#nav
,1個class類.list
,1個偽類:link
,2個標籤a
和li
,所以它的特異度(權重)是 122.hd ul.links a
包含兩個class類.hd
和.links
,兩個元素ul
和a
,所以它的特異度是 22
屬性覆蓋
- 同一個級別的下面的樣式會覆蓋上面的
- 優先順序高的會覆蓋優先順序低的相同屬性
! important
- 如果我們不想讓樣式被其他優先順序高的屬性覆蓋,我們可以給這個屬性後面加
!important
- 如果我們想把上面帶有
!important
的屬性覆蓋,就需要給下面的優先順序高的屬性也新增!important
就可以了
四、css樣式的來源
- 頁面開發者
- 使用者 (比如開放使用者對頁面字型的大小,樣式設定等等)
- 瀏覽器預設
使用者樣式:可以將設定後的樣式存在本地css檔案中,開啟頁面時自動載入 瀏覽器預設樣式:
哪條css樣式會起作用呢?(css優先順序)
-
找出匹配到的該屬性所有宣告
-
根據規則來源,優先順序從低到高:
- 瀏覽器預設
- 使用者設定
- 網頁樣式
-
同一來源中,越特殊優先順序越高
-
特異度一樣時,書寫順序在後面的優先順序高
有!important時的變化
- 找出匹配到的該屬性所有宣告
- 根據規則來源,優先順序從低到高:
- 瀏覽器預設
- 使用者設定
- 網頁樣式
- 含!important的網頁樣式
- 含!important的使用者設定樣式
- 同一來源中,越特殊優先順序越高
- 特異度一樣時,書寫順序在後面的優先順序高
五、課後練習題
- 單選題:關於標籤巢狀的正確說法是?
A. table標籤可以直接巢狀tr
B. video中可以巢狀img作為視訊的封面圖片
C. button中不能包含其他任何標籤
D. p標籤中可以巢狀div
答案:A
解析:video裡面可以放track、source等標籤,封面圖用poster屬性,所以B是錯誤的
button裡面可以巢狀標籤,如span標籤,但<input type='button'/>
是單標籤不能巢狀。
p是代表段落,裡面只能放段落內容,不包含div
知識點:<video>
<video>
的屬性
屬性 | 描述 |
---|---|
width | 視訊寬度 |
height | 視訊高度 |
controls | 顯示控制條 |
poster | 貼圖 |
autoplay | 自動播放 |
muted | 預設狀態下靜音 |
volume | 控制音量 |
preload | 預載入 |
loop | 迴圈播放 |
src | 資源路徑 |
currentSrc | 當前播放路徑 |
currentTime | 播放時間的控制 |
duration | 播放時長 |
volume 音量控制api
<video id="_volume" src="./test.mp4" width="200" height="200" muted preload controls autoplay></video>
<script>
// 獲取video元素
var v = document.getElementById("_volume");
// 音量範圍0-1,將音量設定為50%
v.volume = 0.5;
</script>
複製程式碼
currentTime 播放進度api
<!-- 播放時間控制 -->
<video id="_currentTime" src="./test.mp4" width="200" height="200" muted preload controls autoplay></video>
<script>
var v = document.getElementById("_currentTime");
// 播放進度設定為1分鐘
// currentTime的單位:秒
v.currentTime = 60;
</script>
複製程式碼
src 視訊資源api
<!-- 播放地址的切換 -->
<video id="_src" src="./test.mp4" width="200" height="200" muted preload controls autoplay></video>
<script>
var v = document.getElementById("_src");
setTimeout(() => {
// 兩秒後視訊資源切換為test2.mp4
// 場景:當使用者選擇高清,普清時,通過src地址來切換清晰度
v.src = './test2.mp4'
}, 2000);
</script>
複製程式碼
也可以在video裡面嵌入source標籤, 通過currentSrc
獲取當前視訊播放地址
<video id="_source" width="200" height="200" controls>
<source src="./video.mp4" type="video/mp4">
<!-- 備用地址 -->
<source src="./video.mp4" type="video/mp4">
</video>
<script>
var v = document.getElementById("_source");
// 場景:通過遍歷source的地址,找到currentSrc地址前的地址,上傳錯誤地址到伺服器
setTimeout(() => {
console.log('當前播放的src', v.currentSrc)
v.currentSrc = './test.mp4'
}, 2000);
</script>
複製程式碼
<video>
的事件
事件 | 描述 |
---|---|
loadstart | 視訊播放時觸發 |
durationchange | 當視訊的時長資料發生變化時觸發 |
loadedmetadata | 視訊源資料載入完成 |
loadeddata | 當前幀的資料已載入,但沒有足夠的資料來播放指定視訊的下一幀觸發。 |
progress | 當瀏覽器正在下載指定的視訊時觸發 |
canplay | 視訊有幀播放時觸發 |
canplaythrough | 當瀏覽器預計能夠在不停下來進行緩衝的情況下持續播放指定的視訊時觸發 |
play | 視訊播放時觸發 |
pause | 視訊暫停時觸發 |
ended | 視訊播放完畢 (用途:向視訊新增廣告) |
seeking | 使用者在視訊中移動/跳躍到新的位置時觸發 |
seeded | 尋找資源完畢 |
waiting | 當視訊無法繼續播放,且需要載入時觸發 |
timeupdate | 進度條進度每更新一次,觸發一次timeupdate 事件 |
error | 視訊出現錯誤 |
<video>
建立時,拿不到時長資訊,因此在初始狀態下,duration
為NaN
。
以chrome為例子,當視訊處於載入過程中時,會依次發生以下事件:
progress
(載入視訊資源)loadstart
(此時duration
為NaN)progress
(瀏覽器載入視訊視訊, 可觸發多次)durationchange
(此時duration
為總時長)loadedmetadata
(視訊源資料載入完畢)loadeddata
(當前幀載入完畢)canplay
(視訊可以播放,但沒有緩衝)progress
(瀏覽器載入視訊視訊, 可觸發多次)canplaythrough
(視訊緩衝完畢, 可以流暢的播放)progress
(瀏覽器自動快取資料, 可觸發多次)
場景1: 當使用者點選按鈕跳轉到新的位置時,會觸發下列事件
seeking
尋找資源progress
載入資源seeked
尋找完畢canplay
可以播放當前幀canplaythrough
可以連續播放
場景2: 當使用者播放時,點選跳轉按鈕,會觸發下列事件
seeking
尋找資源play
播放視訊progress
載入資源waiting
等待資源載入seeked
尋找完畢canplay
可以播放當前幀playing
播放狀態下,資源載入完畢,視訊繼續播放canplaythrough
視訊有足夠的緩衝可以持續播放