实际开发网页的时候,大家可能对CSS选择器优先级的规则和原理不太了解,不知道某个元素究竟是如何计算出当前样式的。

本篇文章就是要解决这个痛点,让你遇到没法覆盖样式情况的时候不再是

!important 一把缩!
内联样式一把缩!

首先要清楚CSS选择器在优先级规则应用上分为哪几大类

  1. 通配选择器

    • * { color: black; }
  2. 元素选择器

    • html { color: black; }
  3. 类选择器

    • .container { color: black; }
  4. ID选择器

    • #submit { color: black; }
  5. 属性选择器

    • a[title] { color: black; }
  6. 伪类选择器

    • a:hover { color: black; }
    • a:first-child { color: black; }
    • a:lang(fr) { color: black; }
  7. 伪元素选择器

    • a::after { color: black; }
    • a::before { color: black; }

然后在计算当前元素样式的时候,需要引出一个概念——特殊性值

特殊性值的初始量为 0, 0, 0, 0

计算特殊性值规则:

  • 对于选择器中给定的各个ID属性值,加

    • 0,1,0,0
  • 对于选择器中给定的各个类属性值、属性选择或伪类,加

    • 0,0,1,0
  • 对于选择器中给定的各个元素和伪元素,加

    • 0,0,0,1
  • 如果一个重要声明和一个非重要声明冲突,胜出的总是重要声明

其中比较特殊性值大小的方法:

  • 0, 1, x, x 总比 0, 0, x, x 优先,哪怕后者为 0, 0, 13, 0 也是如此
    因为比较特殊性值大小的规则会从左往右比较同一位的数字,如果数值相同,往右一位继续比较,直到有一方较大,则该方胜出,不再往右比较数值。

比较特殊性值时,总会分开重要声明和非重要声明比较。
也就是说同个元素同一个样式有多个重要声明时,它们也会在重要声明的一个组内计算特殊性值并且比较

在上述计算特殊性值规则中,并没有提到通配选择器,这是因为它的特殊性为 0, 0, 0, 0 ,但这与没有特殊性值有区别,通配选择器声明的样式,依旧会继承下去,并且在最低优先级应用。

上述计算特殊性值规则中也没有提到第一位数值是怎么增加的,实际上第一个0是为内联样式声明保留的。
也就是说内联样式声明要高于其他声明的特殊性

如果特殊性值大小相等且在同一个比较组内,则实际样式取决于在样式表内的声明顺序,后声明的会覆盖先声明的

一些简单例子

h1 { color: red; }    /* 0, 0, 0, 1 */
p em { color: purple; }    /* 0, 0, 0, 2 */
.grape { color: purple; }    /* 0, 0, 1, 0 */
*.bright { color: yellow; }    /* 0, 0, 1, 0 */
p.bright em.dark { color: maroon; }    /* 0, 0, 2, 2 */
#id216 { color: blue; }    /* 0, 1, 0, 0 */
div#sidebar *[href] { color: silver; }    /* 0, 1, 1, 1*/

具体一点的例子

  1. 特殊性值相等且在同一个组内的情况
.class1 {
    color: blue;
}
.class2 {
    color: pink;
}
<html>
    <div class="class1 class2">
        test
    </div>
</html>

由于css声明中,class2的color属性在class1的color属性后声明,所以会覆盖class1的color声明
故test的实际应用样式为 color: pink;

  1. 特殊性值不相等的情况
.class1 {
    color: blue;
}
div.class2 {
    color: purple !important;
}
.class3 {
    color: pink !important;
}
.class4 {
    color: yellow !important;
}
<html>
    <div class="class1 class2 class3 class4" style="color: grey;">
        test
    </div>
</html>

答案是purple