CSS all:initial工作原理及属性默认值继承异常问题咨询
all: initial的p元素看起来会继承父div的line-height和text-align 首先明确两个属性的CSS规范初始值:
line-height初始值为normal:默认16px font-size场景下,normal对应行高系数约1.2,计算行高约19.2pxtext-align初始值为start:从左到右排版环境下等价于左对齐
复现代码
div { width: 50%; font-size: 20px; line-height: 2; padding: 20px; text-align: justify; background-color: #11a683; } p { all: initial; }
<div> <p> Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like Aldus PageMaker including versions of Lorem Ipsum... </p> </div>
核心原因
这个表现和CSS继承规则无关,本质是all: initial的重置逻辑和普遍认知存在偏差:它会无差别将所有CSS属性重置为CSS规范定义的初始值,完全忽略浏览器用户代理(UA)给元素内置的默认样式。对于<p>标签来说,浏览器默认给它设置的display: block会被直接重置为display属性的规范初始值inline,后续所有“异常继承”的视觉表现,都是p变成纯行内元素导致的。
具体表现拆解
1. 看似继承的text-align
text-align仅对块容器、行内块、表格单元格这类能独立创建文本排版上下文的元素生效,对纯inline行内元素没有任何作用。
当p变为行内元素后,它自身被all:initial设置的text-align: start完全不生效,内部的文本会直接寻找最近的块级排版祖先(也就是外层设置了text-align: justify的div)来决定对齐规则,视觉上就和继承了div的对齐属性完全一致。
2. 看似继承的line-height
line-height对块级元素和行内元素的作用并不相同:
- 作用在块级元素上时,会指定内部生成的行盒的最小高度
- 作用在纯行内非替换元素上时,仅用来计算元素自身内容区的高度
当p变为行内元素后,它自身的line-height: normal是生效的,对应自己被重置为medium(约16px)的font-size,内容区实际行高约19px。但外层div作为块级元素设置了line-height: 2,会把内部所有行盒的最小高度撑到40px(2*20px),加上行内元素默认的vertical-align: baseline对齐规则,视觉上的行间距和div设置的2倍行高完全一致,看起来就像继承了div的行高。
3. 为什么表现和all: unset类似,仅font-size不继承
这种相似只是视觉错觉:line-height和text-align本身是可继承属性,但在这个场景下它们并没有真的被设置为继承值,只是p变为行内元素后,自身的对应属性要么失效、要么被父元素的排版规则覆盖,才和all: unset(继承属性取继承值、非继承属性取初始值)的效果看起来接近。
而font-size的作用不依赖元素的display类型,它的初始值medium(约16px)会直接作用在p的文本上,所以确实没有继承父div的20px,完全符合all: initial的预期。
修复方案
如果需要重置p的所有样式,同时保留p默认的块级特性,只需要在all: initial之后补回p的默认display值即可:
p { all: initial; display: block; }
设置后p会恢复为块级元素,此时text-align: start、line-height: normal都会正常生效,不再受父div对应属性的影响,表现符合初始预期。
内容的提问来源于stack exchange,提问作者Add3r

