Fancy CSS Checkboxes with FontAwesome

Checkboxes. They are pretty lame looking in the world of website design. Fortunately, we can use CSS and an icon font like FontAwesome to make them look a lot nicer!

fancy-checkbox-title

The problem with checkboxes is that the browser applies its default styling, and really not many CSS properties can be used to alter it. They are usually black (or blue in Chrome), not easy to resize for touch/mobile designs, and generally lack character.

There are some existing solutions out there that use a input["type=checkbox"]::before pseudo-element on the checkboxes to add a styled item in front of the checkbox. The problem with this is that IE and Firefox do not support the ::before pseudo-class on the input element. Whether this is correct according to the CSS specification is unclear, but the fact that it works in Chrome might actually be against the specification.

We can accomplish the same behavior using the CSS3 :checked and ~ (general sibling) selectors.

For this example, let’s make a checkbox to mute the microphone. Seems pretty reasonable, right?

Let’s start by laying out some HTML. We are going to use FontAwesome here to get some fun icons to replace our checkmark with, so first let’s include it into our page. Then we add some base styling for our site’s body. Here we made the text 1.5em and a shade of red, on a grey background.

<html>
<head>
    <link rel="stylesheet" type="text/css" href="http://netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.css">

    <style>
        body {
            font-size: 1.5em;
            color: #a22;
            background-color: #eee;
        }
    </style>
</head>
<body>
</body>
</html>

Next we can lay out the HTML that will represent our checkbox. We need to use a <label> here with a checkbox input inside of it. The checkbox will eventually be hidden, so the label gives us something to click to toggle the selection.
If you are not familiar with the label element, all you really need to know is that if the label element contains an <input type="checkbox"> element, then the two elements are associated with each other, and clicking on the label will toggle the checkbox contained within it. Basically, this allows you to toggle the checkbox by clicking on the text next to the checkbox, instead of only being able to click directly inside the checkbox.

<body>
    <label>
        <input type="checkbox" />
        Mute
    </label>
</body>

This results in:

fancy-checkbox-1

Wow, that looks terrible!

Now let’s make it look a lot nicer. First, let’s give our label element a class, so we can use default checkboxes where we want them, and nicer ones other places. I am using the CSS class “fancy-checkbox” for this example.

    <label class="fancy-checkbox">
        <input type="checkbox" />
        Mute
    </label>

Next let’s add two FontAwesome icons. One to represent the checked state, and one to represent the unchecked state. FontAwesome actually has two icons that will work well for our mute toggle; one is a microphone, the other is a microphone with a slash through it. I also use the “fa-fw” class here to tell FontAwesome that these should be fixed-width icons. Different icons can have different widths in an icon font, so if we did not do this, then togging between checked and unchecked states could cause the label text to shift left and right slightly, which would be jarring and ugly to the user.

    <label class="fancy-checkbox">
        <input type="checkbox" />
        <i class="fa fa-fw fa-microphone unchecked"></i>
        <i class="fa fa-fw fa-microphone-slash checked"></i>
        Mute
    </label>

Now we have:

fancy-checkbox-2

Not really a checkbox yet, is it… Next we need to add the CSS styling. Notice that I also added a class to each of the icons to indicate which state I will use it in. These classes are “checked” and “unchecked”. First let’s hide that ugly old default checkbox, and also hide the “.checked” icon, since the default state of the checkbox is unchecked.

.fancy-checkbox input[type="checkbox"],
.fancy-checkbox .checked {
    display: none;
}

Now we are getting somewhere! This is the correct “unchecked” state for the styled checkbox. You will notice that because we are using an icon font for the visual checkmark (the microphone icon) it also inherits the font sizing and color properties along with the rest of the label. This lets us maintain a visual style across the checkbox and the text, and have it better fit in with the page.

Finally we need to add some CSS to handle the “checked” state of the checkbox. For this we use the CSS3 “:checked” selector to target only checkboxes that are checked. Then, we can target the icons, which are siblings of the checkbox, using the general sibling selector “~”. When a checkbox is in the checked state, we just want to hide the “.unchecked” icon, and show the “.checked” icon.

.fancy-checkbox input[type="checkbox"],
.fancy-checkbox .checked {
    display: none;
}

.fancy-checkbox input[type="checkbox"]:checked ~ .checked
{
    display: inline-block;
}

.fancy-checkbox input[type="checkbox"]:checked ~ .unchecked
{
    display: none;
}

fancy-checkbox-3

Now we finally have a nice looking checkbox! It visually behaves like a toggle button, and since it is a regular input element, it can still be using in HTML forms and submitted to the server as usual. FontAwesome also has some round checkbox icons, “fa-circle-o” and “fa-check-circle-o” that you can use. You can see those here:

fancy-checkbox-title2

Unfortunately the “:checked” selector is not supported in IE until IE9, so this will not work in IE8, but IE9+, Firefox, Chrome, and Safari will all handle it just fine!

Next Step: Styling all checkboxes at once in CSS.

In the example above, I manually put in the FontAwesome icon classes “fa fa-fw fa-microphone”. That is nice for a one-off checkbox that is different from the rest, but if you were making a long list of checkboxes, it wouldn’t really be desirable to keep using those classes everywhere. Instead, we can move those off to CSS too!

We can actually clean up the HTML significantly. We can remove both of the <i> elements and instead wrap the text of the label into a <span>. We can then target the “:before” of the span in CSS.

<ul><li>
    <label class="fancy-checkbox">
        <input type="checkbox" />
        <span>Item One</span>
    </label>
</li><li>
    <label class="fancy-checkbox">
        <input type="checkbox" />
        <span>Item Two</span>
    </label>
</li><li>
    <label class="fancy-checkbox">
        <input type="checkbox" />
        <span>Item Three</span>
    </label>
</li></ul>

Because I put my checkboxes in a <ul&gt here to make it semantically nice, I also am going to add this CSS to remove the bullets from the list:

ul {
    list-style: none;
}

Now we can style the “span” element that is a child of “.fancy-checkbox” and a sibling of “input[type=checkbox]”.

This makes the full CSS for the example:

.fancy-checkbox input[type="checkbox"] {
    display: none;
}

.fancy-checkbox span:before {
    font-family: "FontAwesome";
    font-style: normal;
    width: 1em;
    height: 1em;
    content: '\f10c';
    margin-right: .3em;
}

.fancy-checkbox input[type="checkbox"]:checked ~ span:before {
    content: '\f05d';
}

fancy-checkbox-4

Now you know how to spice-up your checkboxes (and this will work for radio buttons too!) so don’t settle for those default browser-styled inputs any longer!

Advertisements
Tagged with: , , ,
Posted in Programming
2 comments on “Fancy CSS Checkboxes with FontAwesome
  1. I’m going to give this a try on my contact page. I’ve looked all over for a guide on how to make the checkbox larger and not so boring/corporate looking. Thanks for the tutorial.

  2. I have a issue with the checkboxes. The HTML is autogenerated from formidable pro and I’m trying to customize the checkboxes with CSS.

    CSS
    —–
    label[for=field_2hn10m-1] input[type=”checkbox”]{
    display: none;
    }
    label[for=field_2hn10m-1] input[type=”checkbox”] {
    background: url(‘http://www.uswebcompany.com/plugins/gravityforms/wp-content/uploads/2016/01/christmasLights.png’) 0 0px no-repeat;
    z-index: 10;
    display: inline-block;
    font-size: 12px;
    height: 75px;
    width: 75px;
    line-height: 16px;
    margin: -2px 6px 0 0;
    text-align: center;
    vertical-align: middle;
    position: relative;
    border-radius: 10px !important;
    background-color: #6283B2;
    -webkit-appearance:none;
    -moz-appearance:none;
    -ms-appearance:none;
    appearance:none;
    }

    label[for=field_2hn10m-1] input[type=”checkbox”]:checked{
    background: url(‘http://www.uswebcompany.com/plugins/gravityforms/wp-content/uploads/2016/01/checkmark.png’), url(‘http://www.uswebcompany.com/plugins/gravityforms/wp-content/uploads/2016/01/christmasLights.png’) 0 0px no-repeat;
    height: 75px;
    width: 75px;
    border-radius: 10px;
    background-color: #37924A;
    -webkit-appearance:none;
    -moz-appearance:none;
    -ms-appearance:none;
    appearance:none;
    }

    HTML
    ——-

    Option 1

    Option 2

    LINK
    http://www.uswebcompany.com/plugins/forms/formidable/

    Please let me know.. Thank you

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

CodingWithSpike is Jeff Valore. A professional software engineer, focused on JavaScript, Web Development, C# and the Microsoft stack. Jeff is currently a Software Engineer at Virtual Hold Technologies.


I am also a Pluralsight author. Check out my courses!

%d bloggers like this: