Top

Follow me and receive all the latest free scripts:

By Email:

Categories
Most Popular Posts

Very precise jQuery/Ajax Star Rating Plugin Tutorial

Very precise jQuery/Ajax Star Rating Plugin Tutorial

Published January 12, 2015 by , category jQuery

Star Rating PluginRating SystemStar Rating System TutorialjQueryAJAX

A 0.01 precise Multi-Star Rating Plugin using jQuery and Ajax

Project description

Building a Multi Star Rating System with jQuery, AJAX and PHP is not an easy task, especially if we want to keep it simple, efficient and easy to install.

With this new star rating plugin you will be able to rate any Media (movies, stories, articles, videos, items for ecommerce website…) simply by including a code snippet on your web page.

This is a 100% complete solution with a cookie stored to make sure people only vote once.

A multi-stars rating system!

This program is a multi-stars rating system. It means that you can easily choose the number of stars you need to rate your Media.

As many as you need per page

Also, you can add as many rating system as you need on your webpage. Imagine you own an ecommerce website. On a page you have 20 items and you want to allow your visitors to rate all these items. No problem! You can easily install 20 star bars below or around your items.

The code

After having installed the script, simply add this snippet to call a star rating bar:

echo starBar(5, 203, 25);

It is a function with three arguments:

  1. 1st argument: number of stars (5 in our case),
  2. 2nd argument: Media ID (the ID - from the database - of your Media),
  3. 3rd argument: width of your star graphic (in pixels - 25 in our case).

How the system works?

The star graphic

I chose a 25x25 pixels star. So I provide a 25x50 pixels graphic including the transparent star (empty state) on a white background and the hover star (highlighted state) which is a blue star on a white background.

Star Rating System Pic 1

Depending of your website layout you may choose a bigger star or a smaller one and a different color background. Just create your own graphic using Photoshop for example. But the empty state star must be transparent, you will understand why soon.

So basically the first transparent star is the one displayed by default, and the blue one is displayed when you want to rate and pass your mouse over.

The first layer

Below the stars you will find a first layer. The div layer is the size of your star multiplied by the number of stars you chose.

For a 5-star rating system it will be 25px high and 125px width (25x5px).

Star Rating System Pic 2
div example: yellow and grey color displayed below the stars.

So when you refresh your webpage, for a Media, a star bar is called by the function starBar(5, 203, 25);.

With a simple query we search in the database the average rate and the number of rate for this Media:

$query = $bdd->getOne('SELECT round(avg(rate), 2) AS average, count(rate) AS nbrRate FROM tc_tuto_rating WHERE media='.$mediaId.'');

With the formula...

$numEnlightedPX = round($nbrPixelsInDiv * $query['average'] / $numStar, 0);

...we calculate the number of pixels we have to colorize (in yellow #ffc600 for example) in our first div layer. The rest of the div will be colorized in grey (#cccccc for example).

We use the CSS linear-gradient function to colorize the number of pixels we need in our 25x125px div.

style="width: 125px; height:25px; background: linear-gradient(to right, #ffc600 0px,#ffc600 '.$numEnlightedPX.'px,#ccc '.$numEnlightedPX.'px,#ccc 125px);"

Now you see the process: a first layer made of an accurate number of pixels in yellow (depending of the rate average and number of rate) and the rest in grey (you may choose the color you want, just provide the hexadecimal color). Over are our star graphics (empty state), so the correct numbers of stars are colorized with precision!

Live demo

Page sample with 4 medias and different star number

3 stars rating system

Rating: 2.44/3 (925 votes)

5 stars rating system

Rating: 3.91/5 (1213 votes)

6 stars rating system

Rating: 4.56/6 (716 votes)

7 stars rating system

Rating: 5.03/7 (709 votes)

Examples with different number of stars


10 stars
Rating: 7.41/10 (679 votes)

20 stars
Rating: 13.98/20 (574 votes)

30 stars
Rating: 19.51/30 (428 votes)

40 stars
Rating: 22.17/40 (428 votes)

Files architecture

index.php
db.class.php

ajax

tuto-precise-star-rating.php

jquery

jquery-1.10.1.min.js

js

precise-star-rating.js

design

Database structure sample

id is an auto-increment field. media (an integer) is your Media ID. rate (an integer) is the visitor's rate (a number from 1 to 5 for a 5 star rating system).

Please check this tutorial to see how I handle MySQL database connection and this one to learn how to connect a MySQL database using PDO.

CREATE TABLE IF NOT EXISTS `tc_tuto_rating` (
  `id` int(6) NOT NULL AUTO_INCREMENT,
  `media` int(6) NOT NULL,
  `rate` int(3) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1 ;

HTML/PHP code

This is the index.php page (the complete structure). I include the CSS style lines (which may be placed in a style.css file) and the function starBar which can also be placed in a separate file. I have commented a maximum of lines.

<?PHP
include('db.class.php');
$bdd = new db();
?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en" dir="ltr">
<head>
<title>Very precise jQuery/Ajax Star Rating Plugin Tutorial</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
 
<link rel="stylesheet" href="bootstrap/css/bootstrap.min.css" type="text/css">
<script type="text/javascript" src="jquery/jquery-1.10.1.min.js"></script>
<style>
.star { display: inline-block; background: url("design/star.png") no-repeat; width: 25px; height: 25px }
.star_hover { display: inline-block; background: url("design/star.png") no-repeat; background-position: 0 -25px; width: 25px; height: 25px }
</style>
</head>
 
<body>
 
<div class="container">
<div class="row">
<div class="col-md-12">
<br /><br />
<?php
function starBar($numStar, $mediaId, $starWidth) {
    global $bdd;
    $cookie_name = 'tcRatingSystem2'.$mediaId;
    $nbrPixelsInDiv = $numStar * $starWidth; // Calculate the DIV width in pixel
    
    // Rate average and number of rate from the database
    $query = $bdd->getOne('SELECT round(avg(rate), 2) AS average, count(rate) AS nbrRate FROM tc_tuto_rating WHERE media='.$mediaId.'');
    
    //num of pixel to colorize (in yellow)
    $numEnlightedPX = round($nbrPixelsInDiv * $query['average'] / $numStar, 0);
    
    $getJSON = array('numStar' => $numStar, 'mediaId' => $mediaId); // We create a JSON with the number of stars and the media ID
    $getJSON = json_encode($getJSON);

    $starBar = '<div id="'.$mediaId.'">';
    $starBar .= '<div class="star_bar" style="width:'.$nbrPixelsInDiv.'px; height:'.$starWidth.'px; background: linear-gradient(to right, #ffc600 0px,#ffc600 '.$numEnlightedPX.'px,#ccc '.$numEnlightedPX.'px,#ccc '.$nbrPixelsInDiv.'px);" rel='.$getJSON.'>';
    for ($i=1; $i<=$numStar; $i++) {
        $starBar .= '<div title="'.$i.'/'.$numStar.'" id="'.$i.'" class="star"';
        if( !isset($_COOKIE[$cookie_name]) ) $starBar .= ' onmouseover="overStar('.$mediaId.', '.$i.', '.$numStar.'); return false;" onmouseout="outStar('.$mediaId.', '.$i.', '.$numStar.'); return false;" onclick="rateMedia('.$mediaId.', '.$i.', '.$numStar.', '.$starWidth.'); return false;"';
        $starBar .= '></div>';
    }
    $starBar .= '</div>';
    $starBar .= '<div class="resultMedia'.$mediaId.'" style="font-size: small; color: grey">'; // We show the rate score and number of rates
    if ($query['nbrRate'] == 0) $starBar .= 'Not rated yet';
    else $starBar .= 'Rating: ' . $query['average'] . '/' . $numStar . ' (' . $query['nbrRate'] . ' votes)';
    $starBar .= '</div>';
    $starBar .= '<div class="box'.$mediaId.'"></div>';
    $starBar .= '</div>';
    return $starBar;
}
// Display 4 star bar system for 4 different IDs
echo starBar(3, 502, 25); // 3 stars, Media ID 200, 25px star image
echo starBar(5, 201, 25); // 5 stars, Media ID 201, 25px star image
echo starBar(10, 202, 25); // 10 stars, Media ID 202, 25px star image
echo starBar(30, 203, 25); // 30 stars, Media ID 203, 25px star image
?>
</div>
</div>
</div>
 
<script type="text/javascript" src="js/precise-star-rating.js"></script>
 
</body>
</html>

PHP code

It's the ajax/tuto-precise-star-rating.php file, called by the Ajax function for data treatment.

<?php
include('../db.class.php');
$bdd = new db();

if($_POST) {
	$mediaId = $_POST['mediaId'];
	$rate = $_POST['rate'];
	
	$expire = 24*3600; // 1 day
	setcookie('tcRatingSystem2'.$mediaId, 'rated', time() + $expire, '/'); // Place a cookie
	
	$query = $bdd->execute('INSERT INTO tc_tuto_rating (media, rate) VALUES ('.$mediaId.', "'.$rate.'")'); // We insert the new rate
	
	$result = $bdd->getOne('SELECT round(avg(rate), 2) AS average, count(rate) AS nbrRate FROM tc_tuto_rating WHERE media='.$mediaId.'');
		
	$dataBack = array('avg' => $result['average'], 'nbrRate' => $result['nbrRate']);
	$dataBack = json_encode($dataBack);
	
	echo $dataBack;
}
?>

jQuery code

It's the js/precise-star-rating.js file.

function rateMedia(mediaId, rate, numStar, starWidth) {
    $('#' + mediaId + ' .star_bar #' + rate).removeAttr('onclick'); // Remove the onclick attribute: prevent multi-click
    $('.box' + mediaId).html('<img src="design/loader-small.gif" alt="" />'); // Display a processing icon
    var data = {mediaId: mediaId, rate: rate}; // Create JSON which will be send via Ajax
    $.ajax({ // JQuery Ajax
        type: 'POST',
        url: 'ajax/tuto-precise-star-rating.php', // URL to the PHP file which will insert new value in the database
        data: data, // We send the data string
        dataType: 'json',
        timeout: 3000,
        success: function(data) {
            $('.box' + mediaId).html('<div style="font-size: small; color: green">Thank you for rating</div>'); // Return "Thank you for rating"
            // We update the rating score and number of rates
            $('.resultMedia' + mediaId).html('<div style="font-size: small; color: grey">Rating: ' + data.avg + '/' + numStar + ' (' + data.nbrRate + ' votes)</div>');
            // We recalculate the star bar with new selected stars and unselected stars
            var nbrPixelsInDiv = numStar * starWidth;
            var numEnlightedPX = Math.round(nbrPixelsInDiv * data.avg / numStar);
            $('#' + mediaId + ' .star_bar').attr('style', 'width:' + nbrPixelsInDiv + 'px; height:' + starWidth + 'px; background: linear-gradient(to right, #ffc600 0%,#ffc600 ' + numEnlightedPX + 'px,#ccc ' + numEnlightedPX + 'px,#ccc 100%);');
            $.each($('#' + mediaId + ' .star_bar > div'), function () {
                $(this).removeAttr('onmouseover onclick');
            });
        },
        error: function() {
            $('#box').text('Problem');
        }
    });
}

function overStar(mediaId, myRate, numStar) {
    for ( var i = 1; i <= numStar; i++ ) {
        if (i <= myRate) $('#' + mediaId + ' .star_bar #' + i).attr('class', 'star_hover');
        else $('#' + mediaId + ' .star_bar #' + i).attr('class', 'star');
    }
}

function outStar(mediaId, myRate, numStar) {
    for ( var i = 1; i <= numStar; i++ ) {
        $('#' + mediaId + ' .star_bar #' + i).attr('class', 'star');
    }
}

Conclusion

I hope you like this tutorial. As you can see there is not a lot of code. With a minimum of effort you can install it on your website and start rating everything you want with the number of stars you need.

If you have any problem, please comment below, I will try to help as much as I can.

If you find a way to make it simpler or if you find nice new features, also post below .

About Simon Laroche
Simon Laroche on Google+
Simon Laroche on Twitter
Simon Laroche on Facebook
Simon Laroche on Pinterest
Simon Laroche on LinkedIn
: I am a Coder, Designer, Webmaster and Expert SEO Consulting, I'm also a wise traveller and an avid amateur photographer. I created the website TipoCode and many others such as Landolia: a World of Photos...

If you need help about this script, please leave a comment below. I reply as much as I can depending of my time, you may also get help from others.
I also offer a paid support, if you are in the need to adapt or create a script...

Leave a comment

Comments (42 comments)

robert Moses Posted on January 11, 2017
Where did you set the cookie that is looked for in the function starbar() ?
I have implemented this script however it for some reason is not recognizing a vote after page refresh.
Mickael Posted on November 12, 2016
Yes, thank you, but it doesn't work.
The problem seem to be around:
var data = {mediaId: mediaId, rate: rate};
I'm using another way (a category, integer) and it's ok.
Simon Laroche
Simon Laroche Posted on November 12, 2016
@Mickael: well, there are few things to change. For example:
1) The mysql requests, you have to add quotes, '.$mediaId.' will become "'.$mediaId.'" as it's a string
2) Database field, not INT anymore but VARCHAR
Mickael Posted on November 11, 2016
Thank you for your code, it works!
But I'd like to use strings for MediaID, not only numbers, because I want to use the same code accross my site, with different things (articles, topics, ...)
I've change the code (and database) but it doesn't work anymore on mouseover
Any idea?
Sergio Posted on November 05, 2016
Why a fully working script can not be attached? Do you like to watch the Cubs suffer? I have a lot of different class database created and produces one mistake !!!!
Fatal error: Class 'db' not found in C:\OpenServer\domains\rating-new-test\index.php on line 3
Sergio Posted on November 05, 2016
Please place the source code
Simon Laroche
Simon Laroche Posted on October 15, 2016
@vvanasperen:
For the hover, of course everything is possible, just adapt and change image/layer colors.
For the text, right now it shows 1/5, 2/5, 3/5... just change the text in the code.
vvanasperen Posted on October 14, 2016
Great tutorial! Just curious, but is it also possible when hovering above the stars, that all stars are grey and the stars you select are yellow? And now I'm asking questions. Is it also possible to have a text displayed with each choice? So 1 star is poor and 5 is excellent. Thanks again.
Simon Laroche
Simon Laroche Posted on September 11, 2016
@Facilitant : même réponse que Diesel, je ne peux pas débugger magiquement à distance sans avoir tous les fichiers du site installés sur mon ordinateur.
Mais pareil, pour ce genre de choses, veuillez me contacter pas email via la page contact pour un devis.
Facilitant Posted on September 10, 2016
Hello, i have the same problem than Diesel. How can i do ?

Bonjour j'ai le même problème que Diesel ?

Je ne vois pas comment faire, et l'ajax n'est pas mon fort. (c'est le moins qu'on puisse dire).
Merci d'avance pour ton aide.
Simon Laroche
Simon Laroche Posted on July 17, 2016
@André: hi, I don't have this "button" option, I will have to programme it. You may contact me via the contact page (there is my email there) if you need me to write the programme based on this one. It may take half day or so and we can discuss fees.
André Posted on July 17, 2016
Hi!
Thank you for this tutorial.
Is there a way to change this so that when you have selected a star rating, it will not be submitted until you click a button next to the stars. This way the user will have the ability to alter their rating if for some reason clicking on the wrong star at first?
Do you happen to have a code for this also?
Thank you!
Murat Posted on July 16, 2016
Hello. thank you for this article. How can we integrate this product to laravel ? Thank you in advance.
Simon Laroche
Simon Laroche Posted on July 13, 2016
@Park: no jsp version version, sorry, just what's displayed on this page.
Park Posted on July 13, 2016
I want jsp version.
Do you have a jsp version?
fernande Posted on April 04, 2016
c'est très bien expliqué mais malheureusement je ne suis pas capable de faire cela sur mon forum http://fernande-pub.forumgratuit.eu et je n'es trouvée personne qui peuvent m'aidée et pourtant sa me rendrait service car mon forum est ouvert depuis plusieurs mois et pas un membre alors si j'avais un système de vote ils viendront peut être merci de m'avoir lue
ne faite pas attention aux fautes car j'ai 72 ans
Simon Laroche
Simon Laroche Posted on March 11, 2016
@Diesel: yes probably in the
success: function(data)

You have to run some tests, maybe a value which is not sent back from ajax/tuto-precise-star-rating.php
Also check this line:
$('#' + mediaId + ' .star_bar').attr('style', 'width:' + nbrPixelsInDiv + 'px; height:' + starWidth + 'px; background: linear-gradient(to right, #ffc600 0%,#ffc600 ' + numEnlightedPX + 'px,#ccc ' + numEnlightedPX + 'px,#ccc 100%);');

Create some alert(); to display variables etc...
Diesel Posted on March 10, 2016
everything works, on page load rating and stars are displayed. When voting blue stars over are displayed, once star clicked it doesn't refresh, but vote is being stored in DB. If page refreshed it shows with re-calculated votes. Can't figure out why it doesn't refresh with new values and yellow stars once you click star to vote. It doesn't display "Thank you for rating". There must be a problem with passing
success: function(data)
. Can you help?
Chacalbis Posted on January 13, 2016
Ok the jQuery library was not installed correctly, could be a problem with the version ...
It works so thank you so much for your replies :)
Simon Laroche
Simon Laroche Posted on January 13, 2016
@Chacalbis: if you can't see the blue stars over, it means that the jQuery (JS file) is not called properly for a certain reason...
You have to make a test to check why.
Chacalbis Posted on January 13, 2016
I know that i need to click on stars. ^^
I add your code with the same files architecture and i have 4 star rating bars call by the snippet :

echo starBar(5, 200, 25);
echo starBar(5, 201, 25);
echo starBar(5, 202, 25);
echo starBar(5, 203, 25);

As i said, these star rating bars display the notations from the database and it works.
But I have no way to vote , so no blue star when I hover and I click .
As if the script wasnt called. Did i miss something ?
Thanks for helping me, i'm terrible with js :)
Simon Laroche
Simon Laroche Posted on January 13, 2016
@Chacalbis: to vote, you just need to click on stars. The vote is triggered by the function rateMedia. If you add the code as above in pages, it should work.
Chacalbis Posted on January 12, 2016
Thank you for your work.
I used your code and displaying notations from the database actually works but i don't understand how we can vote. I spetify i have no knowledge of jquery.
Am i supposed to call any function ?
Simon Laroche
Simon Laroche Posted on January 01, 2016
@Zeeshan: sorry you can't, just create the few files, name them like me and copy/paste the content inside. It will take you 2 minutes :)
Happy New Year
Zeeshan Posted on December 31, 2015
Hello
where from i can download a copy of this plugin to integrate in my theme
Simon Laroche
Simon Laroche Posted on December 24, 2015
@lakshman Gupta
db.class.php is here:
http://www.tipocode.com/database/mysql-php-oop-database-connection/

I explain how I manage my database connection.
But you can replace by your MySQL/MySQLI/PDO connection system, just adapt the queries :)
lakshman Gupta Posted on December 24, 2015
where is db.class.php?
Simon Laroche
Simon Laroche Posted on August 14, 2015
@Jong : I am not sure I understand the question.

"Is there anyway that I can use to show rating for individual items fetched from the database?"

This is EXACTLY what this tutorial is for. Just follow the tutorial :)
Jong Posted on August 14, 2015
Is there anyway that I can use to show rating for individual items fetched from the database?
Simon Laroche
Simon Laroche Posted on August 13, 2015
@CUIPAO
In my system I use cookies, check the part of the code below in ajax/tuto-precise-star-rating.php file

$expire = 24*3600; // 1 day
setcookie('tcRatingSystem2'.$mediaId, 'rated', time() + $expire, '/'); // Place a cookie


But you can replace and use IP address, both solutions are ok.
CUIPAO Posted on August 13, 2015
I'm confused as to how the system allows only one rating per user? Normally I use IP Address but in your code I can't seem to figure it out..
Asier Posted on May 18, 2015
I am trying your code with several browsers. I found a problem with Safari 5.1.7 . Only star_hover CSS code works, the star CSS code does not draw the shaded star.
<style>
.star { display: inline-block; background: url("../design/star.png") no-repeat; width: 25px; height: 25px }
.star_hover { display: inline-block; background: url("../design/star.png") no-repeat; background-position: 0 -25px; width: 25px; height: 25px }
</style>
staff76620 Posted on April 28, 2015
by modifying the script on this file "http://radio-oxygen.com/js/rating.js" his works
Simon Laroche
Simon Laroche Posted on April 28, 2015
I am not sure about what is (function ($) {}) (jQuery);

But maybe you have to replace all the $ by jQuery in these functions...
staff76620 Posted on April 28, 2015
His works when I put them overStar outStar and functions outside of a (function ($) {}) (jQuery);
staff76620 Posted on April 28, 2015
Yet I have insert the path like this
<script type = "text / javascript" src = "http://radio-oxygen.com/js/rating.js"> </ script>
Simon Laroche
Simon Laroche Posted on April 28, 2015
It means the system doesn't find function outStar and overStar...
You may have a problem with the js/precise-star-rating.js file path.
staff76620 Posted on April 28, 2015
Thank you Simon Laroche ;)

Now when I pass my cursor over the stars I errors :(

ReferenceError: overStar is not defined
<!DOCTYPE html>

ReferenceError: outStar is not defined
<!DOCTYPE html>


thank you for your answers ;)
Simon Laroche
Simon Laroche Posted on April 28, 2015
@staff76620
I think you have the answer here if you search for "jquery TypeError: $ is not a function"
http://stackoverflow.com/questions/12343714/typeerror-is-not-a-function-when-calling-jquery-function
staff76620 Posted on April 28, 2015
I have just added in my JS file

(function($){ My code })(jQuery);


Now when I pass my cursor over the stars I errors


ReferenceError: overStar is not defined
<!DOCTYPE html>

ReferenceError: outStar is not defined
<!DOCTYPE html>
staff76620 Posted on April 28, 2015
I have problem

TypeError: $ is not a function
$('#' + mediaId + ' .star_bar #' + i).attr('class', 'star');
Amid Posted on February 22, 2015
Great script, exactly what I was looking for.
Thank you so much