1. CSS 权重的计算规则
CSS 权重由四个部分组成,格式为 (a, b, c, d)
:
-
a
: 内联样式(style="..."
)的数量。 -
b
: ID 选择器的数量。 -
c
: 类选择器、属性选择器、伪类选择器的数量。 -
d
: 元素选择器、伪元素选择器的数量。
每个部分的权重值是累加的,优先级从左到右依次递减。
2. 分析选择器
比如 #layouts div.layout__center div.protyle-content:not([data-fullwidth="true"]) div.protyle-wysiwyg
分解选择器:
#layouts div.layout__center div.protyle-content:not([data-fullwidth="true"]) div.protyle-wysiwyg
逐部分分析:
-
**ID 选择器 (**
#layouts
) :- 匹配一个 ID 选择器:
#layouts
。 - 权重贡献:
b = 1
。
- 匹配一个 ID 选择器:
-
类选择器和伪类选择器:
-
.layout__center
:类选择器。 -
.protyle-content
:类选择器。 -
:not([data-fullwidth="true"])
:伪类选择器。 - 权重贡献:
c = 3
(2 个类选择器 + 1 个伪类选择器)。
-
-
元素选择器:
-
div
(出现 3 次):div.layout__center
、div.protyle-content
、div.protyle-wysiwyg
。 - 权重贡献:
d = 3
。
-
总结:
-
a
(内联样式):0(没有内联样式)。 -
b
(ID 选择器):1(#layouts
)。 -
c
(类选择器、属性选择器、伪类选择器):4(.layout__center
、.protyle-content
、:not([data-fullwidth="true"]
)。 -
d
(元素选择器):3(div
出现 3 次)。
因此,最终的权重为:(0, 1, 4, 3)
。
3. 权重表示法
在某些工具中,权重可能会以简化的形式表示,例如:
-
(1, 4, 3)
表示(0, 1, 4, 3)
。 - 工具可能省略了第一个
0
,因为内联样式通常不参与此类选择器。
4. 权重比较
如果需要与其他选择器比较优先级,可以按照以下规则:
- 比较
a
(内联样式)。 - 如果
a
相同,比较b
(ID 选择器)。 - 如果
b
相同,比较c
(类选择器、属性选择器、伪类选择器)。 - 如果
c
相同,比较d
(元素选择器)。
例如:
-
(0, 1, 4, 3)
>(0, 0, 5, 10)
(因为b
更高)。 -
(0, 1, 4, 3)
<(0, 2, 0, 0)
(因为b
更低)。
5. 工具验证
使用工具(如 Specificity Calculator 或Css Specificity Calculator或其他在线工具)可以验证该选择器的权重为 (1, 4, 3)
,这与手动计算的结果一致。
6. 总结
选择器 #layouts div.layout__center div.protyle-content:not([data-fullwidth="true"]) div.protyle-wysiwyg
的 CSS 权重为 (0, 1, 4, 3)
,工具显示为 (1, 4, 3)
是合理的,因为它省略了第一个 0
。
如果两个选择器的权重计算结果都是 (0, 1, 4, 3)
(或简化为 143
),那么它们的优先级是相同的。在这种情况下,CSS 的 层叠规则(Cascading Rules)会决定哪个样式最终生效。
以下是 CSS 层叠规则的详细说明:
1. 如果权重相同,优先级如何决定?
当两个选择器的权重相同时,CSS 按照以下顺序决定优先级:
(1) 后声明的样式优先
-
在同一个样式表中,后声明的规则会覆盖先前的规则。
-
示例:
.example { color: red; /* 这个会被覆盖 */ } .example { color: blue; /* 这个生效 */ }
最终颜色为蓝色,因为它是后声明的。
(2) 外部样式表 vs 内部样式表
-
如果样式来自不同的来源,优先级顺序如下:
- 用户代理样式(浏览器默认样式)。
- 外部样式表(如
<link>
引入的样式文件)。 - 内部样式表(如
<style>
标签中的样式)。 - 内联样式(如
style="..."
)。
(3) 使用 !important
-
如果某个样式规则使用了
!important
,它会覆盖所有未使用!important
的规则,无论权重如何。 -
示例:
.example { color: red !important; /* 这个生效 */ } .example { color: blue; }
最终颜色为红色,因为
!important
提升了优先级。
2. 实际案例分析
假设你有两个权重均为 (0, 1, 4, 3)
的选择器:
选择器 A:
#layouts div.layout__center div.protyle-content:not([data-fullwidth="true"]) div.protyle-wysiwyg {
color: red;
}
选择器 B:
#layouts div.layout__center div.protyle-content:not([data-fullwidth="true"]) div.protyle-wysiwyg {
color: blue;
}
优先级判定:
-
权重相同:两个选择器的权重都是
(0, 1, 4, 3)
。 -
后声明优先:如果选择器 B 在样式表中出现在选择器 A 之后,则 B 的样式会覆盖 A 的样式。
- 最终颜色为蓝色。
特殊情况:
如果其中一个选择器使用了 !important
,例如:
#layouts div.layout__center div.protyle-content:not([data-fullwidth="true"]) div.protyle-wysiwyg {
color: red !important;
}
即使选择器 A 出现在前面,由于 !important
的存在,最终颜色仍为红色。
3. 总结
当两个选择器的权重相同时:
- 后声明的样式优先。
- 如果一个样式使用了
!important
,它会覆盖其他未使用!important
的样式。 - 如果仍然无法区分优先级,可以检查样式来源(如外部样式表、内部样式表等)。
