1. 程式人生 > >選擇器優先順序介紹

選擇器優先順序介紹

特殊性

從CSS選擇器文章中我們知道,與多種不同的方法選擇元素。所以當我們使用多種規則的時候,我們必須要明確其中的優先順序。但是在CSS選擇器的規則中,稱之為特殊性,特殊性越高,自然優先順序越高。

此時我們會先得到一個特殊性說明:

  • !important 特殊性最高,詳情訪問重要性
  • 對於內聯樣式,加1000
  • 對於選中器中給定的ID屬性值,加0100
  • 對於選擇器中給定的類屬性值,屬性選擇或偽類,加0010
  • 對於選擇器中給定的元素選擇器和偽元素,加0001.
  • 結合符和萬用字元選擇器對特殊性沒有任何貢獻,0000

   

我們還是通過舉例說明上面的情況,親自去測試一下:

<!DOCTYPE html>  
<html lang="en">  
    <head>  
        <meta charset="UTF-8">  
        <title>Document</title>  
        <style>
            #ID-selector {
                font-size: 10px;
            }

            .class-selector {
                font-size: 12px;
            }

            *[proprty-selector] {
                font-size: 14px;
            }

            *:first-child {
                font-size: 16px;
            }

            div {
                font-size: 18px;
            }

            * div {
                font-size: 20px;
            }

            div::first-line {
                font-size: 22px;
            }

            * {
                font-size: 24px;
            }
        </style>
    </head>  
    <body>  
        <div style="font-size: 6px;" proprty-selector="true" id="ID-selector" class="class-selector">
            測試CSS選擇器的特殊性
        </div>
    </body>  
</html>  

看這個例子之前先明確兩點:

  • 當選擇器出於同一種特殊性的時候,位於css檔案下部的樣式會覆蓋上面的樣式。
  • 萬用字元選擇器對於特殊性沒有任何貢獻,所以下面我用了許多的萬用字元(強烈說明日常開發最好不要使用過多萬用字元,這裡只是為了舉例子)來代替div屬性,是因為要將div自身的特殊性影響排除。


可以看到我們的css檔案程式碼書寫的順序是按照我最上面圖的順序去加的樣式,所以現在我們對照上圖中紅色框的樣式來對比,如果是處於同一層級,那麼下面的css樣式會覆蓋上面的css樣式。

現在我們的到的特殊性的順序是:

內聯樣式 > ID選擇器 > 類選擇器 = 屬性選擇器 = 偽類選擇器 > 元素選擇器 = 關係選擇器 = 偽元素選擇器 > 萬用字元選擇器

說明:偽元素選擇器的順序說明請看(3)

(1)對於順序中有兩部分存在等於號的,因為紅色框中匹配樣式的順序與我寫的程式碼的順序相反,所以他們之間是平級的,所以導致程式碼後面的css樣式覆蓋了程式碼前面的樣式(因為css的解析是從上面往下的)。

(2)我們再來說一下一開始談到的特殊性說明中的:結合符和萬用字元選擇器對特殊性沒有任何貢獻,0000, 對於萬用字元就是這樣定義的,對於結合符說的是什麼呢?說的就是關係選擇器中幾種通過文件結果父子關係進行的選擇器。所以程式碼的中* div的特殊性還是和元素選擇器相同。

(3)相信大家可以看到上面的紅色框最後有一個偽元素的樣式應用起來。看起來好像偽元素的優先順序很高啊,比內聯樣式的優先順序好高。其實呢不是這樣的?我現在將上面的例子修改偽元素的樣式:

*::first-line {
    font-size: 22px;
}

接下來就要藉助IE瀏覽器了,因為在chorme瀏覽器看不到我想要的結果。


相信大家已經看到紅色框中結果了,是的現在我們可以看到偽元素選擇器存在元素的樣式上面,而且位於元素選擇器和關係選擇器的上面。

但是現在我們只解決一個問題,雖然得到了樣式的順序,可是為什麼html還是應用了偽元素的樣式,請看下圖我們可以看到隨著我取消/新增偽元素的樣式,html的字型會相應的變化。這裡原因如下:

偽元素的樣式應用是相當於新增一個元素,這裡就是添加了一個<first-line>元素在div中,然後由於字型的樣式是可以繼承(繼承相關的內容可以訪問文章)的,所以當前first-line中的樣式集成了父元素的first-line的字型為22px的樣式。可能你會問就算繼承為什麼不是繼承最終的內聯樣式的屬性,這裡可能就是偽元素的規則了。


重要性

上面提到的是一般情況下,當然如果對於很複雜的頁面樣式來說,可能你想講之前的所有樣式都覆蓋,那麼就需要使用特殊手段了。有時某個宣告可能非常重要,超過了所有其他宣告,CSS2.1稱之為重要宣告。重要宣告在宣告的結束分號之前插入!important來標誌,如果!important放在宣告的任何其他位置,整個宣告都將無效

如果一個宣告是重要宣告,則超過所有的非重要宣告。現在我們將上面的例子中的萬用字元樣式加上重要說明:如下

#ID-selector {
    font-size: 10px;
}

.class-selector {
    font-size: 12px;
}

*[proprty-selector] {
    font-size: 14px;
}

*:first-child {
    font-size: 16px;
}

div {
    font-size: 18px;
}

* div {
    font-size: 20px;
}

*::first-line {
    font-size: 22px;
}

* {
    font-size: 24px !important;
}

然後我們看一下當前的頁面展示效果,可以看到現在應用到的是萬用字元的屬性。


繼承

上面已經提到一次繼承。這裡我們再來看繼承的相關知識。對於的繼承的總結可以訪問繼承

繼承是從一個元素向其後代元素傳遞屬性值所採用的機制。基於繼承機制,樣式不僅可以應用到指定的元素,還會應用到它的後代元素。在兩個比較特殊的情況需要注意:一個是在HTML中,應用到body元素的背景樣式可以傳遞到html元素;另一個是<a>標籤不會繼承父元素的文字樣式

繼承的屬性沒有特殊性,所以當我們對於元素進行新增選擇器的時候,會直接覆蓋掉繼承來的屬性。

繼承是CSS中最基本的內容之一,除非有必要的理由,否則一般不會去考慮。

萬用字元具有特殊性,雖然特殊性是0,但是還是比繼承高的。

層疊

最重要的來了,因為一般我們的開發中不會只有簡單的樣式,而是很多的樣式在一起,那麼我們就需要一個規則去辨別最後渲染的樣式。

CSS層疊樣式表的層疊特性就是讓樣式層疊在一起,通過特殊性、重要性、來源及繼承機制來排列層疊樣式的順序及選出勝出者。

1、重要性和來源需要同時考慮,因為二者的結合使用與否會存在不同的順序

(1) 不考慮來源的情況下,!important最高。
(2) 在不考慮重要性的前提下,來源優先順序順序為:
  • 讀者的重要宣告
  • 創作人員的重要宣告
  • 創作人員的正常宣告
  • 讀者的正常宣告
  • 使用者代理宣告
(3) 二者一起考慮的情況下,user(使用者)的優先順序大於author(作者)的優先順序,這樣做是試圖平衡author(作者)和user(使用者)。所以,最終的優先順序排序為:

user(使用者)!important > author(作者)!important > author > user > user agent

簡單解釋一下:這裡說的是我們通過瀏覽器設定使用者css樣式的情況下愛,至於如何設定使用者樣式可以檢視文章

舉個例子

<!DOCTYPE html>  
<html lang="en">  
    <head>  
        <meta charset="UTF-8">  
        <title>Document</title>  
        <link rel="stylesheet" type="text/css" href="index.css">
    </head>  
    <body>  
        <div>
            測試CSS宣告。
        </div>
    </body>  
</html>   
/* index.css: author's style sheet  */
div {
    font-size: 14px;
}

div {
    font-size: 16px !important;
}
/* user.css: user's style sheet */
div {
    font-size: 8px;
}

div {
    font-size: 10px !important;
}

我們可以看到上面有兩個css檔案,但是我們檔案中只使用了index.css檔案,這個就是創作人員的宣告,對於user.css就是我們即將需要操作的user宣告。


從上面的操作中可以看到,在沒有應用user.css的時候,頁面上的文字大小為16px,但是當我們將user.css的樣式應用之後,可以看到當前頁面的樣式變為10px。這裡的原因就是上面給的優先順序順序決定的。

2、接著,對於非重要宣告來說,按照特殊性排序。特殊性越高的規則,權重越大

3、最後,如果特殊性相同,則按照出現順序排序。宣告在樣式表或文件中越靠後出現,權重越大。如果樣式表中有通過@import匯入的樣式表,一般認為出現在匯入樣式表中的宣告在前,主樣式表的所有宣告在後。