摘要:表示的是滿足第一個選擇器的前提下,從它匹配到的元素后,去尋找位于同一層級,且在該元素后面的所有滿足第二個選擇器的元素。
本篇文章已授權微信公眾號 dasu_Android(大蘇)獨家發(fā)布
本系列文章內容全部梳理自以下四個來源:
作為一個前端小白,入門跟著這四個來源學習,感謝作者的分享,在其基礎上,通過自己的理解,梳理出的知識點,或許有遺漏,或許有些理解是錯誤的,如有發(fā)現(xiàn),歡迎指點下。
首先需要清楚,CSS 職責是控制 HTEM 文檔里的文本內容在網(wǎng)頁上樣式呈現(xiàn)的效果,寫的每一個樣式最終是通過選擇器作用到具體的元素上面。
互聯(lián)網(wǎng)其實都是通過網(wǎng)頁相互連接組成的,每個網(wǎng)頁都是一份 HTML 文檔,因此瀏覽器與后端的首次通信是以 HTML 文檔為基準,那么整個流程的第一步也就是解析 HTML 文檔。
如果在解析 HTML 文檔過程中發(fā)現(xiàn)有通過 標簽引用了外部的 CSS 文件時,那么瀏覽器會去下載相對應的 CSS 文件。
當 HTML 文檔解析完畢后會生成一個 DOM 文檔結構,DOM 文檔結構中記錄著每個節(jié)點的元素,各元素之間的關系,有點類似于 Android 中的 View 樹。
最后,通過 CSS 的選擇器將相對應的樣式作用到 DOM 中選擇器找到的元素節(jié)點,然后瀏覽器渲染呈現(xiàn)在網(wǎng)頁上。
以上是一個 CSS 的典型結構,總共由兩部分組成:選擇器 + 樣式
{} 大括號內部的都是具體的某種樣式,可用來控制元素的背景、大小、排版位置等樣式效果。而 {} 左邊的則是選擇器,用來指定說后面跟隨的樣式列表要作用到 HTML 文檔中的哪個元素上。
選擇器類型很多,規(guī)則也很多,因此會有一種現(xiàn)象,就是某個元素被不止一個選擇器匹配到,如果某個樣式屬性起沖突了,那么就會按照一定的優(yōu)先級順序處理。
樣式屬性也很多,具體也后面介紹,但有一點需要先明確一下,如果使用了未知的樣式屬性,或者給某個樣式屬性賦予了無效值,那么該樣式屬性會被視為無效,瀏覽器的 CSS 引擎會完全忽略它。
跟 Android 很類似,每個元素在頁面上都是占據(jù)一個矩形區(qū)域,也分 margin 和 padding,唯一不同的就是這里的模型多了個 border,雖然在 Android 中也有 border 的概念,但它是在 padding 區(qū)域內的,不多帶帶占據(jù)某塊區(qū)域,所以這里需要區(qū)分一下。
因此,一個元素在頁面上的寬高就是由四個部分共同影響的了:content 區(qū)域,padding 區(qū)域,border 區(qū)域,margin 區(qū)域。
需要注意的是,上圖中的盒子模式的 box-sizing 屬性為默認值 content-box 模式。
這種模式下,width 和 height 指的只是content區(qū)域的寬高。
box-sizing 屬性的取值有:content-box, padding-box, border-box, margin-box。四種,對應的就是指明 width 和 height 表示的是包含哪些區(qū)域的寬高。
CSS 基本結構是由選擇器和樣式屬性列表組成,那么如何跟 HTML 文檔關聯(lián)起來使用呢?一共有三種方式:
使用 HTML 元素的全局屬性 style 聲明,僅影響一個元素,除非工作環(huán)境受限,比如只允許編輯 HTML 的 body,否則強烈不推薦這種方式。
示例:
點擊跳轉
在 HTML 中的
內使用將 CSS 保存在一個獨立的擴展名為 .css 的文件中,并在 HTML 的
?里使用? ?元素中引用它,這種方法可以說是最好的,因為你可以使用一個樣式表來設置多個文檔的樣式,并且需要更新 CSS 的時候只要在一個地方更新。
選擇器,顧名思義,就是將 css 代碼選擇到 HTML 文檔中具體的元素對象,并作用在它身上。
基本選擇器其實是一些比較常用、簡單的選擇器,包括:元素選擇器、id 選擇器、class 選擇器、屬性選擇器、組合選擇器。這些在第一篇前端入門1-基礎概念中已經(jīng)介紹過了,這里不就詳細說了。
基本選擇器規(guī)則很簡單,選擇器基本就是一兩個條件,滿足了即可匹配上,如 a.class,p#id 等,即使有稍微經(jīng)過組合,但仍舊不復雜,但有些應用場景下需要通過復雜的規(guī)則,即需要滿足多個條件下才能匹配上。
在第一篇中介紹的屬性選擇器其實是最基本用法的一種,而它還支持其他很多規(guī)則的用法,如下:
[attr] | 選擇定義attr屬性的元素,不管屬性的取值具體是什么 |
---|---|
[attr=”val”] | 選擇定義attr屬性,且屬性值為val的元素 |
[attr^=”val”] | 選擇定義attr屬性,且屬性值以字符串val打頭的元素 |
[attr$=”val”] | 選擇定義attr屬性,且屬性值以字符串val結尾的元素 |
[attr*=”val”] | 選擇定義attr屬性,且屬性值包含字符串val的元素 |
[attr~=”val”] | 選擇定義attr屬性,且屬性值具有多個值,其中一個為字符串val的元素。 |
[attr|=”val”] | 選擇定義attr屬性,且屬性值為連字符(-)分割的多個值,其中第一個為字符串val的元素。 |
也就是說,屬性選擇器不僅可以用來匹配那些具有指定屬性的元素,還可以進一步根據(jù)不同屬性值來匹配。
結構:<選擇器>, <選擇器>
并集選擇器是通過 ,
逗號將不同選擇器組合使用的一種選擇器,這種情況下,各個選擇器之間是沒有任何關系,都是相互獨立的,就是他們具有相同的樣式屬性表而已。
這只是一種簡便寫法的用法而已,具有相同樣式屬性表的不同再復制粘貼,可以直接通過 ,逗號將不同選擇器分開即可。只有 HTML 文檔中的元素滿足其中一個選擇器即可。
示例:
a, h1, span, div {
background-color: black;
}
上述示例中有四個選擇器含有同樣的樣式屬性,HTML 文檔中只要滿足其中一個選擇器即可被匹配到。
結構:<第一個選擇器> <第二個選擇器>
多個選擇器之間通過空格
分隔開的話表示這是一個后代選擇器,也就是說,需要先滿足第一個選擇器的前提下,在第一個選擇器匹配到的元素的后代元素中去匹配第二個選擇器。
這里的后代包括了子孫后代。
示例:
p span {
background-color: black;
}
第一個span
第二個span
以上示例中,選擇器要匹配的元素是位于 p 元素的后代元素中的 span 元素,因此第一個 span 元素就不符合規(guī)則,而第二個 span 則會被匹配到。
結構:<第一個選擇器> > <第二個選擇器>
兒子選擇器是多個選擇器之間通過 >
右箭頭符號連接,表示的是在滿足第一個選擇器的前提下,從它匹配到的元素的直接子元素中尋找第二個選擇器。
跟后代選擇器的區(qū)別就在于它只能在直接子元素中匹配第二個選擇器。
示例:
p > span {
background-color: black;
}
第一個span
第二個span
第三個span
第一個 span 元素不是 p 元素的后代,第二個 span 元素是 p 元素的直接子元素,第三個 span 元素是 p 元素的孫子元素,因此只有第二個 span 元素滿足規(guī)則被匹配到。
結構:<第一個選擇器> + <第二個選擇器>
兄弟選擇器是多個選擇器之間通過 +
加號連接。表示的是,在滿足第一個選擇器的前提下,從它匹配到的元素的緊跟著的位于同一層級的下一個元素,看該元素是否符合第二個選擇器。
也就是說,兄弟選擇器,兩個選擇器所匹配的元素要求,位于同一層級,且相鄰。
示例:
p + a {
background-color: #6a90d9;
}
第一個a
第二個a
第三個a
第四個a
上述示例中,同時滿足位于同一層級,且相鄰,且需要先滿足第一個選擇器的前提下,還滿足第二個選擇器這四個條件的 a 元素就是第三個 a 元素了。
結構:<第一個選擇器> ~ <第二個選擇器>
普通兄弟選擇器,是多個選擇器之間通過 ~
波浪符號連接。表示的是滿足第一個選擇器的前提下,從它匹配到的元素后,去尋找位于同一層級,且在該元素后面的所有滿足第二個選擇器的元素。
兄弟選擇器只匹配相鄰的一個元素,而普通兄弟選擇器則是可以匹配位于元素后面的所有符合第二個選擇器的元素。
示例:
p ~ a {
background-color: #6a90d9;
}
第一個a
第二個a
第三個a
第四個a
同時滿足同層級,且在 p 元素后面的兄弟元素有兩個,第三個 a 元素和第四個 a 元素,因此這里可以匹配到這兩個元素。
選擇器的目的就是為了匹配到 HTML 文檔中的滿足條件的元素,然后將樣式屬性作用在元素上。
元素是什么,在基礎一節(jié)中有介紹過,元素其實就是包含了標簽以及文本內容的整塊內容。因此被選擇器匹配到的元素,都是直接將 CSS 樣式作用到整個元素上,也就是作用到整個文本內容上。
那么,如果有一些需求并不是直接去匹配 HTML 文檔中的具體元素,而是指定了一些狀態(tài)、行為,然后讓瀏覽器動態(tài)去根據(jù)當前情況選擇符合這些狀態(tài)、行為的元素。
或者有一些需求是并不想將 CSS 樣式作用到整個元素上,而是只作用到元素標記的文本內容的某一部分。
這個時候,這種選擇器就稱作偽選擇器,因為它有區(qū)別于普通選擇器的行為
偽選擇器總共分成兩種:偽元素選擇器,偽類選擇器
當偽選擇器最終將 CSS 作用的對象并不是整個元素,而是滿足條件的元素標記的文本內容的某一部分時,稱偽元素選擇器。
偽元素選擇器不多,如下:
::first-line | 匹配滿足條件的元素標記的文本內容的首行部分 |
---|---|
::first-letter | 匹配滿足條件的元素標記的文本內容的首字母部分 |
:before | 在滿足條件的元素之前插入生成的內容 |
:after | 在滿足條件的元素之后插入生成的內容 |
偽元素選擇器的用法基本都是和其他選擇器組合使用,比如 p::first-line 表示匹配 p 元素標記的文本內容的首行部分。
而 :before 和 :after 與之前的選擇器都不大一樣,因為之前介紹的選擇器作用都只是用于匹配選擇 HTML 文檔中的元素或文本內容而已。但這兩個偽元素選擇器會生成內容,并插入到匹配到元素的文本內容中去。
因此,它們的基本用法通常都是這樣:
a:before {
content: "在文本內容之前插入";
}
a:after {
content: "在文本內容之后插入";
}
有一種應用場景很適合使用這兩種偽元素選擇器,當需要對列表動態(tài)的生成復雜的編號規(guī)則時,可以結合 :before 和 counter() 使用。在 CSS 中也是可以使用一些內置的方法功能。
當不是通過 HTML 文檔中元素的一些基本性質,比如 id,class,標簽名,屬性這些基本特征來匹配這些元素時,就可以稱作偽類選擇器。
偽類選擇器是通過滿足一些指定狀態(tài)、行為下來匹配元素的一種選擇器,比如滿足是否獲取焦點等等。
偽類選擇器相對來說,比較多,如下:
:first-child | 選擇元素的第一個子元素 |
---|---|
:last-child | 選擇元素的最后一個子元素 |
:only-child | 選取元素的唯一一個子元素 |
:only-of-type | 選取屬于父元素的特定類型的唯一子元素 |
:nth-child(n) | 選取元素的第n個子元素 |
:nth-last-child(n) | 選取元素的倒數(shù)第n個子元素 |
:nth-of-type(n) | 選取屬于父元素的特定類型的第n個子元素 |
:nth-last-of-type(n) | 選取屬于父元素的特定類型的倒數(shù)第n個子元素 |
:enabled | 選取啟用狀態(tài)的元素 |
:disable | 選取被禁用狀態(tài)的元素 |
:checked | 選取所有選中的復選框和單選按鈕元素 |
:default | 選取默認的元素 |
:valid :invalid | 選取基于輸入驗證判定的有效或者無效的input元素 |
:in-range :out-of-range | 選取被限定在指定范圍之內或之外的input元素 |
:required :optional | 根據(jù)是否允許使用required屬性選取input元素 |
:link | 選取未訪問的鏈接元素 |
:visited | 選取用戶已訪問的鏈接元素 |
:hover | 選取鼠標指針懸停的元素 |
:active | 選取當前被用戶激活的元素,這通常意味著用戶即將點擊該元素 |
:focus | 選取獲得焦點的元素 |
:not(<選擇器>) | 否定選擇,(如選擇所有不匹配<選擇器>的元素) |
:empty | 選取不包含任何子元素或文本的元素 |
:lang(<語言>) | 選取lang屬性為指定值的元素 |
:target | 選取URL片段標識符指向的元素 |
一些偽類選擇器看下說明應該就清楚怎么使用,不明白的再具體去查找相關文檔即可。
由于一個元素通常會被多個選擇器命中,而這些選擇器又有可能是通過不同方式作用到元素上,因此這里存在了兩種場景下的優(yōu)先級問題,但請記住,只有當作用到同一個元素上的樣式屬性起了沖突時才會存在優(yōu)先級問題。
如果不同選擇器作用到同一個元素上,但它們各自的樣式屬性列表中沒有重復的,那就不存在沖突,也就不存在優(yōu)先級問題,都會一起合并作用到元素上。
CSS 有三種使用方式,另外瀏覽器也有默認樣式,因此這些構成了一個優(yōu)先級順序:
以上優(yōu)先級從高到低,同層級之間,如果存在沖突的樣式屬性的話,以文檔中最后出現(xiàn)的屬性為準,采用覆蓋規(guī)則。
當作用到同一個元素上的不同選擇器存在樣式屬性沖突時,優(yōu)先以場景1考慮優(yōu)先級,如果不存在場景1的情況,即起沖突的選擇器在場景1中處于同一層優(yōu)先級,那么才會考慮不同選擇器之間的優(yōu)先級。
以上優(yōu)先級從高到低,同層級之間,如果存在沖突的樣式屬性的話,以文檔中最后出現(xiàn)的屬性為準,采用覆蓋規(guī)則。
但,有時候,使用的是組合選擇器,那么這時候就需要依靠一定的算法來計算出誰的優(yōu)先級高了,這個算法叫做層疊算法:
通過對以上不同選擇器賦予某個數(shù)值來計算整個組合選擇器的最終數(shù)值,然后比較大小。
比如,上面三個優(yōu)先級的選擇器中,1優(yōu)先級的表示100,2優(yōu)先級的表示10,3優(yōu)先級的表示1,以此來計算一個組合選擇器的數(shù)值大小。
通常來說,組合選擇器不會過于離譜,長達十幾個選擇器的組合,因此以上述賦予每個優(yōu)先級的數(shù)值足夠覆蓋絕大多數(shù)場景。
示例:
h1,和 #indentifier 都只是簡單選擇器,不通過這種層疊算法計算也行。
h1 + p::first-letter 和 li > a[href*=”zh-CN”] > .inline-warning 這種比較復雜的組合選擇器,就可以根據(jù)賦予每一層級優(yōu)先級對應的數(shù)值來進行計算,最終根據(jù)數(shù)值大小比較誰的優(yōu)先級高。
這種賦予不同優(yōu)先級某個具體數(shù)值具現(xiàn)化的思想叫做層疊算法,通常是用于比較復雜的組合選擇器時。
但實際開發(fā)中,很少會需要用到層疊算法,掌握場景1和場景2下簡單的優(yōu)先級分辨理論基礎足夠了。實際開發(fā)過程中,沒必要這么復雜,借助開發(fā)工具或者運行查看下效果就可以確認誰的優(yōu)先級高低了。
大家好,我是 dasu,歡迎關注我的公眾號(dasuAndroidTv),如果你覺得本篇內容有幫助到你,可以轉載但記得要關注,要標明原文哦,謝謝支持~
文章版權歸作者所有,未經(jīng)允許請勿轉載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉載請注明本文地址:http://systransis.cn/yun/1627.html
摘要:個人前端文章整理從最開始萌生寫文章的想法,到著手開始寫,再到現(xiàn)在已經(jīng)一年的時間了,由于工作比較忙,更新緩慢,后面還是會繼更新,現(xiàn)將已經(jīng)寫好的文章整理一個目錄,方便更多的小伙伴去學習。 showImg(https://segmentfault.com/img/remote/1460000017490740?w=1920&h=1080); 個人前端文章整理 從最開始萌生寫文章的想法,到著手...
摘要:前言月份開始出沒社區(qū),現(xiàn)在差不多月了,按照工作的說法,就是差不多過了三個月的試用期,準備轉正了一般來說,差不多到了轉正的時候,會進行總結或者分享會議那么今天我就把看過的一些學習資源主要是博客,博文推薦分享給大家。 1.前言 6月份開始出沒社區(qū),現(xiàn)在差不多9月了,按照工作的說法,就是差不多過了三個月的試用期,準備轉正了!一般來說,差不多到了轉正的時候,會進行總結或者分享會議!那么今天我就...
摘要:派生選擇器依據(jù)元素的位置關系來定義樣式。稱其為上下文選擇器,稱其為派生選擇器。在現(xiàn)在布局中,選擇器常常用于建立派生選擇器。和一樣,也可被用作派生選擇器。 文章大綱來源:【Day 3】HTML復習 + CSS基礎 初識CSS 入門CSS 初識CSS 層疊樣式表(Cascading Style Sheets),即前端常說的CSS。 內容引用:CSS 簡介 樣式解決了什么問題? HTML...
閱讀 2139·2021-11-23 10:06
閱讀 3513·2021-11-11 16:54
閱讀 3366·2019-08-29 17:31
閱讀 3603·2019-08-29 17:05
閱讀 2185·2019-08-26 13:36
閱讀 2180·2019-08-26 12:17
閱讀 548·2019-08-26 12:12
閱讀 1694·2019-08-26 10:19