如何给 Checkbox 添加自定义样式?
各位老铁大家好,又是一个风和日丽的日子,人生苦短,不能总是留恋美好的风景,亦要时时刻刻学习,所谓活到老学到老。今天我们一起来学习一下如何给 html 中的 ckeckbox 添加自定义样式。
如何在 html 中实现 checkbox?
其实,html 中根本没有checkbox
这种控件,也就是说,你不能这样写:
1
| <checkbox>remember me</checkbox>
|
而是要像下面这样通过input
来实现checkbox
1 2
| <label for="remember-me">Remember me</label> <input id="remember-me" type="checkbox" />
|
与之类似的控件还有radio
,也需要用input
来实现,如果大家对 input 控件感兴趣,可以看看这篇,可以这样说,掌握了input
,基本上就掌握了 html 中form
的半壁江山!
如何给 checkbox 添加样式?
给定如下 html,如果实现自定义 checkbox 的样式?包括颜色和选择框的形状。为了方便操作,我们在checkbox
外层包裹了一层div
。
1 2 3 4 5 6
| <body> <div class="checkbox-container"> <input id="remember-me" type="checkbox" /> <label class="checkbox-label" for="remember-me">Remember me</label> </div> </body>
|
有的同学可能认为,这不是很简单的事吗?想要啥样式,直接写不就行了吗?呵呵,你可以试试,你会发现事情并不像你想象的那么简单,好了,长话短说,checkbox 的自定义样式主要分两个方面。
自定义选择框的颜色
默认情况下,checkbox 的选择框被选中时,应该显示蓝色背景+白色对勾,如果想更改这个颜色,那么可以直接使用 CSS 中的accent-color
,这里accent
不是口音的意思,而是强调的意思,accent-color
也就是强调色。
假如要使上面的 checkbox 复选框被选中时变为紫色,那么可以按照如下方式书写 CSS。
1 2 3
| input[id="remember-me"] { accent-color: purple; }
|
自定义选择框的形状
如果我想把 checkbox 选中时的对勾变成小方块该怎么办呢?改变checkbox外形可比改变它的颜色复杂多了,这时候你会发现无论你怎么写样式,都不生效。这是因为默认的样式是无法覆盖的,所以只能换策略,采用先禁用默认样式,然后添加自定义样式的方法。
禁用默认样式
禁用默认样式的方式有很多,比如隐藏 input 元素:
1 2 3 4
| input[id="remember-me"] { position: absolute; z-index: -1; }
|
但是,最推荐的还是下面这种。
1 2 3
| input[id="remember-me"] { appearance: none; }
|
自定义 checkbox 样式
总体的思路就是使用before
伪元素来绘制 checkbox 选择框,然后添加各种状态下的样式,比如鼠标悬停时、选中时、禁用时的样式等等。
完整代码如下,关键点都写到注释里面了。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54
| <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8" /> <title>Title</title> <style> input[id="remember-me"] { appearance: none; }
input[id="remember-me"] + label::before { content: ""; display: inline-block; width: 20px; height: 20px; border: 1px solid purple; background-color: #fff; border-radius: 4px; margin-right: 16px; text-align: center; line-height: 20px; }
input[id="remember-me"]:hover + label::before { background-color: #dd94dd; }
input[id="remember-me"]:checked + label::before { content: "\2713"; color: white; background-color: purple; }
.checkbox-label { display: flex; align-items: center; cursor: pointer; user-select: none; } </style> </head> <body> <div class="checkbox-container"> <input id="remember-me" type="checkbox" /> <label class="checkbox-label" for="remember-me">Remember me</label> </div> </body> </html>
|
伪元素的居中对齐
可以对伪元素的宿主元素采用 flex 布局,比如上面例子中的label
标签,这样伪元素和字符串Remember-me
就可以作为 flex 布局中的子元素进行对齐了。
上面的例子采用的是for/id
形式的 label,如果是包裹式 label,情况则又不同了。
包裹式 label
如果采用的是包裹式 label,那么自定义的方式又有所不同,包裹式 label 如下所示,用一个 label 标签包裹住 input 控件。
1 2 3 4 5 6
| <div class="checkbox-container"> <label class="checkbox-label"> Remember me <input type="checkbox" /> </label> </div>
|
这种方式下,当隐藏掉 label 包裹的 input 时,label 内部就空了,这导致添加伪元素十分不便,所以我们在 input 后面添加一个 span 元素,这个元素的作用无他,不过是为了方便添加伪元素。另外 label 已经是最外层元素了,所以 label 外层的 div 也就没有存在的必要了,将其删除,修改后的代码如下:
1 2 3 4 5
| <label class="checkbox-container"> <input id="remember-me" type="checkbox" /> Remember me <span class="checkmark"></span> </label>
|
样式文件如下,思路都在注释里面了,直接看吧。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46
| <style> .checkbox-container { position: relative; padding-left: 36px; cursor: pointer; user-select: none; } input[type="checkbox"] { appearance: none; } .checkmark { position: absolute; top: 0; left: 0; height: 24px; width: 24px; background-color: #eee; } .checkbox-container:hover input ~ .checkmark { background-color: #ccc; } .checkbox-container input:checked ~ .checkmark { background-color: #2196f3; } .checkmark:after { content: ""; position: absolute; display: none; left: 9px; top: 5px; width: 5px; height: 10px; border: solid white; border-width: 0 3px 3px 0; transform: rotate(45deg); } .checkbox-container input:checked ~ .checkmark:after { display: block; } </style>
|
今天就写到这里啦,大家有什么想法,欢迎留言讨论,我们下期再见。