Creating A Pure CSS Star Rating Selection


A star rating system built with pure CSS. This can obviously be done with JavaScript, and for now it’s probably the better option for browser support, but hey, I had fun making it.

The functionality is achieved with radio buttons, and using the CSS :checked selector to decide how many stars are on show. This will look something like.
1
input[value="5"]:checked + .rating-fill{ /* some css */  }
This line of CSS says that, when the input with a value of 5 is checked, then apply whatever style to the element with a class of .rating-fill. The “+” selector means only apply the style to the element that appears directly after it.

First off let’s setup the HTML.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<div class="rating-wrap">
    <div class="radio-wrap">
        <input type="radio" name="rating" value="1"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="2"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="3"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="4"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="5"></input>
        <div class="rating-fill"></div>
    </div>
    <div class="rating-blank"></div>
</div>
Each radio button has a different value, and this is the key aspect that allows us to apply a different style (in our case the width) to each proceeding .rating-fill.
Near the bottom is an element with the class “rating-empty”. This will show the stars in a grayed out state. Then with CSS we will position all of these elements on top of each other, to achieve the desired effect.

The CSS

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
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
body{
    background:#23252b;
}
/* Wrappers */
.rating-wrap{
    width:150px;
    height:25px;
    position:relative;
}
.radio-wrap{
    width:100%;
    height:100%;
}
/* Radio Buttons */
input[type=radio] {
    display:inline-block;
    position:relative;
    z-index:2;
    margin:0;
    width:17.4%;
    height:100%;
    opacity:0;
}
/* Filled Rating */
.rating-fill{
    width:0;
    height:100%;
    background:url(star.png) #efaf16;
    position:absolute;
    top:0;
    left:0;
    z-index:1;
}
/* Checked Inputs */
input[value="5"]:checked + .rating-fill{
    width:100%;
}
input[value="4"]:checked + .rating-fill{
    width:80%;
}
input[value="3"]:checked + .rating-fill{
    width:60%;
}
input[value="2"]:checked + .rating-fill{
    width:40%;
}
input[value="1"]:checked + .rating-fill{
    width:20%;
}
/* Blank Stars */
.rating-blank{
    width:100%;
    height:100%;
    background:url(star.png) #ccc;
    position:absolute;
    top:0;
    left:0;
    z-index:0;
}

Creating A Pure CSS Star Rating Selection

on August 29, 2014

Creating A Pure CSS Star Rating Selection


A star rating system built with pure CSS. This can obviously be done with JavaScript, and for now it’s probably the better option for browser support, but hey, I had fun making it.

The functionality is achieved with radio buttons, and using the CSS :checked selector to decide how many stars are on show. This will look something like.
1
input[value="5"]:checked + .rating-fill{ /* some css */  }
This line of CSS says that, when the input with a value of 5 is checked, then apply whatever style to the element with a class of .rating-fill. The “+” selector means only apply the style to the element that appears directly after it.

First off let’s setup the HTML.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<div class="rating-wrap">
    <div class="radio-wrap">
        <input type="radio" name="rating" value="1"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="2"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="3"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="4"></input>
        <div class="rating-fill"></div>
        <input type="radio" name="rating" value="5"></input>
        <div class="rating-fill"></div>
    </div>
    <div class="rating-blank"></div>
</div>
Each radio button has a different value, and this is the key aspect that allows us to apply a different style (in our case the width) to each proceeding .rating-fill.
Near the bottom is an element with the class “rating-empty”. This will show the stars in a grayed out state. Then with CSS we will position all of these elements on top of each other, to achieve the desired effect.

The CSS

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
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
body{
    background:#23252b;
}
/* Wrappers */
.rating-wrap{
    width:150px;
    height:25px;
    position:relative;
}
.radio-wrap{
    width:100%;
    height:100%;
}
/* Radio Buttons */
input[type=radio] {
    display:inline-block;
    position:relative;
    z-index:2;
    margin:0;
    width:17.4%;
    height:100%;
    opacity:0;
}
/* Filled Rating */
.rating-fill{
    width:0;
    height:100%;
    background:url(star.png) #efaf16;
    position:absolute;
    top:0;
    left:0;
    z-index:1;
}
/* Checked Inputs */
input[value="5"]:checked + .rating-fill{
    width:100%;
}
input[value="4"]:checked + .rating-fill{
    width:80%;
}
input[value="3"]:checked + .rating-fill{
    width:60%;
}
input[value="2"]:checked + .rating-fill{
    width: