[CSS] 样式规则的书写顺序

1. 背景

最近看到了一个有趣的CSS问题,
来源是Max Stoiber的一条Twitter,How well do you know CSS?

结果两个div都为蓝色

[CSS] 样式规则的书写顺序_第1张图片

2. 原因

这个问题涉及到了样式的层叠顺序问题,
CSS1规范 3.2 Cascading order有详细的说明,

Conflicting rules are intrinsic to the CSS mechanism. To find the value for an element/property combination, the following algorithm must be followed:

  1. Find all declarations that apply to the element/property in question. Declarations apply if the selector matches the element in question. If no declarations apply, the inherited value is used. If there is no inherited value (this is the case for the 'HTML' element and for properties that do not inherit), the initial value is used.
  2. Sort the declarations by explicit weight: declarations marked '!important' carry more weight than unmarked (normal) declarations.
  3. Sort by origin: the author's style sheets override the reader's style sheet which override the UA's default values. An imported style sheet has the same origin as the style sheet from which it is imported.
  4. Sort by specificity of selector: more specific selectors will override more general ones. To find the specificity, count the number of ID attributes in the selector (a), the number of CLASS attributes in the selector (b), and the number of tag names in the selector (c). Concatenating the three numbers (in a number system with a large base) gives the specificity. Some examples:
LI            {...}  /* a=0 b=0 c=1 -> specificity =   1 */
UL LI         {...}  /* a=0 b=0 c=2 -> specificity =   2 */
UL OL LI      {...}  /* a=0 b=0 c=3 -> specificity =   3 */
LI.red        {...}  /* a=0 b=1 c=1 -> specificity =  11 */
UL OL LI.red  {...}  /* a=0 b=1 c=3 -> specificity =  13 */ 
#x34y         {...}  /* a=1 b=0 c=0 -> specificity = 100 */ 

Pseudo-elements and pseudo-classes are counted as normal elements and classes, respectively.

  1. Sort by order specified: if two rules have the same weight, the latter specified wins. Rules in imported style sheets are considered to be before any rules in the style sheet itself.

3. 计算

3.1 选择器的权重

specificity是相对于选择器而言的,

/* a=0 b=1 c=0 -> specificity = 10 */
.red {
    background: red;
}

/* a=0 b=1 c=0 -> specificity = 10 */
.blue {
    background: blue;
}

这两条样式规则的specificity都为10

3.2 样式规则的书写顺序

/* 顺序靠前 */
.red {
    background: red;
}

/* 顺序靠后 */
.blue {
    background: blue;
}

对于相同specificity的选择器而言,顺序靠后的优先级高,
.blue {...} 优先级总是高于.red {...}
所以,这两个方块都是蓝色的。


参考

CSS1: 3.2 Cascading order
CSS2.1: 6.4.1 Cascading order

你可能感兴趣的:([CSS] 样式规则的书写顺序)