Form input fields are native and according to this their look & feel depends on the OS and the browser, in which they are displayed. Especially native checkboxes and radio buttons suffer follwing drawbacks:
- Layout is cross-plattform inconsistend
- Unable to zoom (looks very awkward being next to a zoomable label)
- No control over color, style and behavior
Those issues can be fixed with a little CSS, but without changing the functionality.
Based on following 3 checkboxes and their HTML:
<input id="html" type="checkbox" name="type[]" checked="checked">
<label for="html">HTML</label>
<input id="css" type="checkbox" name="type[]">
<label for="css">CSS</label>
<input id="javascript" type="checkbox" name="type[]">
<label for="javascript">Javascript</label>
and the result:
The styled checkboxes for direct comparison (just click them, it is a live demo):
First the native checkboxes have to disappear:
input[type=checkbox] { opacity: 0; }
Then the empty checkboxes themselves are drawed by:
input[type=checkbox] + label:before {
width: 17px;
height: 17px;
display: inline-block;
position: absolute;
left: 0;
top: 3px;
margin-left: -20px;
content: "";
border: 1px solid #888;
border-radius: 3px;
background-color: #fff;
}
with a height and width of 17 pixels. Setting content with a blank String is fundamental. The leftovers are plain layout: backgroundcolor, border and position (should be a little more left than its width).
The pseudo :focus selector is for for simulating the equivalent effect:
input[type=checkbox]:focus + label:before {
outline: thin dotted;
outline: 5px auto -webkit-focus-ring-color; // for WebKit
}
The second box element is the check hook and can displayed with the help of a scalable icon font. Therefore an appropriate font (e.G. AwesomeFonts) has to be included . In this case Bootstraps Glyphicon-Halflings was used:
@font-face{
font-family: 'Glyphicons Halflings';
src: url(path/to/glyphicon.eot);
src: url(path/to/glyphicon.svg) format('svg'),
url(path/to/glyphicon.woff) format('woff'),
url(path/to/glyphicon.ttf) format('ttf')
}
The check hook has to take advantage of the :after pseudo selector:
input[type=checkbox]:checked + label:before {
background-color: #22760c;
border-color: #22760c;
}
input[type=checkbox]:checked + label:after {
font-family: "Glyphicons Halflings";
content: '\e013';
color: #FFF;
top: 3px;
}
After clicking the checkbox (in reality it is actually the label), its background color changes and the check hook is displayed:
input[type=checkbox]:checked + label:before {
background-color: #22760c;
border-color: #22760c;
}
input[type=checkbox]:checked + label:after {
font-family: "Glyphicons Halflings";
content: '\e013';
color: #FFF;
top: 3px;
}
The correct content font code is important.
Finally the spacings for the label:
input[type=checkbox] + label {
display: inline-block;
position: relative;
padding-left: 5px;
margin-right: 30px;
}
Basically the same approach works for radio buttons as well, but without the need for an icon font.
Before:
And after:
Simply use the browser HTML inspector to find out the used CSS in detail.
Conclusion:
- Layout is consistent cross-platform
- Zoomable
- Complete control over color, shape and behavior
Awesome!