Очень часто на самых разнообразных сайтах можно видеть блок для голосования. Это очень полезный инструмент, который позволяет посетителю Вашего сайта оценить прочитанный материал, а автору получить объективную оценку своего творчества.
База данных
Первым делом подготовим место хранения отзывов пользователей. В базе MySQL создайте таблицу со следующей структурой:
id - уникальный идентификатор каждого голоса;
idarticle - уникальный идентификатор статьи;
vote – голос посетителя;
date - текущая дата;
SQL-запрос
CREATE TABLE IF NOT EXISTS `vote` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`idarticle` int(11) NOT NULL,
`vote` int(11) NOT NULL,
`date` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=MyISAM DEFAULT CHARSET=cp1251 COLLATE=cp1251_general_cs AUTO_INCREMENT=1;
Взаимодействие с базой
Таблица в Базе создана, однако это полдела, далее приступим к написанию php скриптов, задача которых, добавлять в базу и запрашивать из базы голосов посетителей.
Файл vote.php
Скрипт находящийся в файл vote.php используя функции, описанные в следующей главе, добавляет в базу новые голоса пользователей, а также запрашивает из базы все голоса принадлежащих данной статье.
Файл vote.php будет запрашиваться jQuery функцией $.ajax(). находящейся в плагине который также будет рассмотрен ниже.
<?
//Переменные, полученные от функции $.ajax()
$idarticle=$_POST["idarticle"];
$vote=$_POST["vote"];
//Подключается php файл с функциями
include_once "funcs.php";
//Добавление в базу нового голоса
if(!empty($vote)){
voteAdd($idarticle,$vote);
}
//Запрос и отправка результата в функцию $.ajax()
print votesGet($idarticle);
?>
Файл funcs.php
//Функция для добавления нового голоса в Базу
function voteAdd($idarticle,$vote){
//Соединение с БД
$db = mysql_connect("localhost", "root", "");
mysql_select_db("script");
mysql_query("SET NAMES CP1251");
$idarticle=intval($idarticle);
$vote=intval($vote);
//Запрос в БД
$query = "INSERT INTO `vote`
VALUES (
NULL,
'{$idarticle}',
'{$vote}',
NOW()
)";
$result = mysql_query($query);
mysql_close($db);
return $result;
}
/*
Функция для запроса из базы всех голосов и нахождение среднего арифметического
*/
function votesGet($idarticle){
//Соединение с БД
$db = mysql_connect("localhost", "root", "");
mysql_select_db("script");
mysql_query("SET NAMES CP1251");
$idarticle=intval($idarticle);
$query="Select *
From `vote`
Where `idarticle`='{$idarticle}'";
$result = mysql_query($query);
$vote=0;$kol=0;
while ($row = mysql_fetch_array($result,MYSQL_BOTH)) {
$kol++;
$vote+=$row["vote"];
}
mysql_close($db);
return "quantityVote={$kol};votes={$vote};";
}
Плагин для оценки статьи на jQuery
Переходим, пожалуй, к основному действу - написание плагина. Его задача, помещение в указанный DIV блок изображений со звездами. Создание функционала, в который входит, к примеру, подсветка активных звезд. Использование функции $.ajax() для обмена данными с php файлом на серверной стороне. С одной стороны функция передает данные для занесения их в базу (оценка статьи), с другой получает данные для предоставления их пользователю (количество голосов, средний балл).
Полный листинг плагина:
(function( $ ){
$.fn.blockVote = function( options ) {
//Опции по умолчанию
var settings=$.extend({
QuantityStars:5, //Количество звезд внедряемых в блок
Class:"voteActive", //Класс, присваивается блоку
AjaxFileURL:"vote.php", //Путь к php файлу
IdArticle:0, //ID статьи
Vote:0 //Оценка выставленная за статью
},options);
return this.each(function(){
//Ссылка на объект
var $this=$(this);
function VoteResult (){
//Очистка блока от содержимого
$this.html("");
//Блоку для оценки присваивается указанный в опциях класс
$this.addClass(settings.Class);
/*
В блок встраиваются два DIV`а:
В первый помещается указанное количество gif изображений со звездам. Причем на одной картинке изображены звезды в трех цветовых тонах (серый - неактивный, желтый = активный, красный - выбранный).
Во второй общая информация в текстовом виде: количество проголосовавших и средней балл
*/
$this.append("<div></div><div></div>");
//CSS стили DIV`ов
$this.children("div :first").css({
"height":"15px",
"overflow":"hidden",
"float":"left"
});
$this.children("div :last").css({
"padding-left":"10px",
"float":"left"
});
//Внедрение звезд в первый DIV
for (i=1;i<=settings.QuantityStars;i++){
$this.children("div :first").append("<img src="imgs/star.gif" />");
}
/*
Первому DIV`у задается ширина из расчета: количество звезд умноженных на 16(ширина изображения со звездами в пикселях). Далее изображениям со звездами назначаются стили.
*/
$this.children("div :first").width(settings.QuantityStars*16);
$this.children("div :first").children("img").css({
"position":"relative",
"cursor":"pointer"
});
/*
С помощью технологии $.ajax() в файл указанный в параметре (settings.AjaxFileURL) передаются оценка выставленная посетителем (settings.Vote. При первоначальном запуске плагина параметр равен 0, что позволяет только запросить данные из базы, ничего не добавляя в нее) и уникальный идентификатор статьи (settings.IdArticle). Скрипт находящийся в файле заносит новый голос в базу. Затем из базы запрашиваются голоса, принадлежащие указанной статье. Скрипт формирует строку-отчет из количества голосов, их общей суммы и возвращает обратно в функцию $.ajax(), где она помещается в переменную data
*/
$.ajax({
url: settings.AjaxFileURL,
type: "POST",
cache:false,
data: {idarticle:settings.IdArticle,vote:settings.Vote},
success: function(data){
/*
С помощью регулярного выражения полученная строка разбивается на составляющие
*/
var matches=data.match(/=(.*?);/ig);
//Количество голосов
var quantityVote=matches[0].substr(1,matches[0].length-2);
//Общая сумма голосов
var sumBalls=matches[1].substr(1,matches[1].length-2);
//Средний балл
settings.QuantityStarsActive=Math.round(sumBalls/quantityVote);
// Исходя из среднего балла и класса, подсвечиваются звезды
switch (settings.Class){
case "voteActive":
$this.children("div :first").
children("img:lt("+settings.QuantityStarsActive+")").
css({"top":"-32px"});
break;
case "voteSelect":
$this.children("div :first").
children("img:lt("+settings.QuantityStarsActive+")").
css({"top":"-16px"});
break;
}
//Во второй DIV помещается подробная текстовая информация
var info=" (<b>"+quantityVote+"</b> голосов"
if (quantityVote!=0) {
info+=", средний балл: <b>"+(sumBalls/quantityVote).toFixed(2)+"</b> из "+settings.QuantityStars;
}
info+=")";
$this.children("div:last").append(info);
}
});
//~~~~~~~~~~~~~~~~~~ФУНКЦИИ~~~~~~~~~~~~~~~~~~~~~~~~
/*
Далее расположены функции, которые изменяя положение изображения со звездами, обеспечивают интерактивное общение посетителя с инструментом для голосования. Т.к. изображение состоит из трех звезд в разной цветовой гамме расположенных вертикально, то для отображения звезды в нужном цвете, функции перемещают gif изображение по вертикали и на конкретное количество пикселей.
Ниже расположены три позиции изображения:
css({"top":"0px"}) - неактивная, серая звезда;
css({"top":"-16px"}) - выбранная, красная звезда;
css({"top":"-32px"}) - активная, при наведении курсора мыши;
*/
//Срабатывает при наведении курсора мыши на одну из звезд
$this.children("div :first").children("img").hover(function(){
if ($this.attr("class")=="voteActive"){
$(this).css({"top":"-32px"}).prevAll().css({"top":"-32px"});
$(this).nextAll().css({"top":"0px"});
}
});
//Срабатывает при клике на одну из звезд
$this.children("div :first").children("img").click(function(){
if ($this.attr("class")=="voteActive"){
//Порядковый номер нажатой звезды или по-другому балл выставленный посетителем
settings.Vote=$(this).index()+1;
/*
В параметр присваиваем одно из значений:
Если необходимо заблокировать блок после голосования присвойте settings.Class значение voteSelect как сделано ниже
Если необходима бесконечная рекурсия присвойте voteActive
*/
settings.Class="voteSelect";
//Рекурсия функции (Функция вызывает саму себя)
VoteResult ();
}
});
//Срабатывает при отведении курсора мыши от блока со звездами.
$this.children("div :first").mouseleave(function(){
if ($this.attr("class")=="voteActive"){
$this.children("div :first").children("img"). css({"top":"0px"}).nextAll().css({"top":"0px"});
$this.children("div :first").children("img:lt("+(settings.QuantityStarsActive)+")").css({"top":"-32px"});
}
});
}
//Первоначальное исполнение функции
VoteResult();
})
};
})(jQuery);
Опции, которые может принимать плагин:
QuantityStars – количество звезд в блоке;
Class - параметр содержит один из трех ниже перечисленных классов, который присваивается “блоку для оценки статьи”:
voteBlock – класс указывает, что блок заблокирован. Визуально в нем будут отображаться только серые звезды;
voteActive – класс указывает, что блок активен;
voteSelect – класс присваивается блоку в момент клика на одну из звезд, при этом блок переходит в неактивный режим;
AjaxFileURL - путь к php файлу;
IdArticle – уникальный идентификатор объекта, который оценивают пользователи (статья);
Сборка модулей в главном файле index.html
Создание инструмента для голосования близко к завершению, следующий шаг - сборка всего того что было написано ранее в логический порядок. В <HEAD> подключаются модули:
Библиотека jquery v1.7.2.js;
Плагин jquery.blockvote;
В <HEAD> помещается jQuery скрипт, активирующий плагин для оценки статьи после загрузки веб-страницы. В тело документа помещается DIV блок, к которому применяется плагин.
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=win1251" />
<title>Скрипт для оценки статьи на jQuery</title>
<script src="jquery v1.7.2.js" type="text/javascript"></script>
<script src="plugins/blockvote/jquery.blockvote.js" type="text/javascript"></script>
<script src="plugins/listen/jquery.listen.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function(){
$("#vote1").blockVote({
Class:"voteActive",
AjaxFileURL:"vote.php",
IdArticle:1
});
});
</script>
</head>
<body>
<div id="vote1"></div>
</body>
</html>