《CSS选择器世界》知识和技巧汇总
大家好,我是做工程师不做码农!聚焦大前端技术和程序员成长的干货公众号,点击关注,每天给你精彩!
纯CSS实现input失焦聚焦效果
当我们聚焦输入框的时候,如果希望后面的提示文字显示,则可以借助相邻兄弟选择符轻松实现,原理很简单,把提示文字预先埋在输入框的后面,当触发focus行为的时候,让提示文字显示即可,HTML和CSS如下:
使用属性选择器的时候不需要带上标签选择器
很多开发者在使用属性选择器的时候习惯把标签选择器也带上,例如:
/* 不推荐 */
input[type='radio'] {}
a[href='http'] {}
img[alt] {}
实际上,这里的标签选择器是可以省略掉的,而且推荐省略。因为,很多原生属性是某些标签元素特有的。例如,’radio‘类型的单选框一定是 input 标签,所以直接将它写成下面这样就可以了:
[type='radio'] {}
这样,选择器的优先级和类选择器保持一致,可维护性得到提高,类似的还有:
div#cs-some-id {}
由于ID是唯一的,因此没有任何理由在这里使用 div 标签选择器。
增加CSS选择器优先级的小技巧
实际开发时,难免会遇到需要增加CSS选择器优先级的场景。例如,希望增加下面 .foo 类名选择器的权重:
.foo {color: #333;}
很多人的做法是增加嵌套,例如:
.father .foo {}
div.foo {}
但这些都不是最好的方法,因为这些方法增加了耦合,降低了可维护性,一旦哪天父元素类名变化了,或者标签换了,样式岂不是就失效了?
这里给大家介绍一个增加CSS选择器优先级的小技巧,那就是重复选择器自身。例如,可以像下面这样做,既提高了优先级,又不会增加耦合,实在是上上之选:
.foo.foo {}
如果你实在不喜欢这种写法,借助必然会存在的属性选择器也是不错的方法。例如:
.foo[class] {}
#foo[id] {}
尽量不用子选择符
能不用子选择符就尽量不用,虽然它的性能优于后代选择符,但与其日后带来的维护成本比,这实在不值一提。
举个例子,有一个模块容器,类名是.cs-module-x,这个模块在 A 区域和 B 区域的样式有一些差异,需要重置,我们通常的做法是给容器外层元素重新命名一个类进行重置,如.cs-module-reset-b,此时,很多开发者(也没想太多)就使用了子选择符:
.cs-module-reset-b > .cs-module-x {
width: fit-content;
}
作为过来人,建议大家使用后代选择符代替
.cs-module-reset-b .cs-module-x {
width: fit-content;
}
因为一旦使用了子选择符,元素的层级关系就被强制绑定了,日后需要维护或者需求发生变化的时候一旦调整了层级关系,整个样式就失效了,这时还要对CSS代码进行同步调整,增加了维护成本。
记住:使用子选择符的主要目的是避免冲突。本例中,.cs-module-x容器内部不可能再有一个.cs-module-x,因此使用后代选择符绝对不会出现冲突问题,反而会让结构变得更加灵活,就算日后再嵌套一层标签,也不会影响布局。
通配符选择器可省略的场景
通配符选择并不足以覆盖所有元素,因为有些元素是无特征的,如:::before和::after构成的伪元素,因此,很多人重置所有元素的盒模型的时候会这样设置:
*, *::before, *::after { Box-sizing: border-Box; }
后面两个星号其实是可以省略的,可以直接用:
*, ::before, ::after { Box-sizing: border-Box; }
当通配符选择器和其他选择器级联使用的时候,星号都是可以省略的。例如,下面这些选择器d都是一样的:
- *[hreflang|=en]的等同于[hreflang|=en]
- *.warning等同于.warning
- *#myId等同于#myId
只有当单独使用通配符选择器的时候我们才需要把*字符呈现出来,例如。若要选择所有<body>元素的子元素,可以:
body > * {}
由于通配符选择器匹配所有元素,因此它是比较消耗性能的一种CSS选择器,同时由于其影响甚广,容易出现一些意料之外的样式问题,因此建议谨慎使用。
转发 @杭州程序员小张: 《CSS选择器世界》知识和技巧汇总1
0/2000字
转发