forked from olton/metroui
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathrating.js
More file actions
251 lines (215 loc) · 7.67 KB
/
rating.js
File metadata and controls
251 lines (215 loc) · 7.67 KB
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
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
/**
* jQuery plugin for rating component of MetroUiCss framework
* use attribute data-role="rating" or class="rating" to initialize rating plugin for some element
* or use $(ratingElement).rating({parameters})
*
* available parameters (attributes):
* data-role-stars="integer" stars count for this rating element (default 5)
* data-role-rating="integer" current average rating (default 0)
* data-role-vote="string" ('on' or 'off') (default 'on')
*
* to control rating you can use:
* $('ratingID').RatingValue(float) - set rating
* $('ratingID').RatingValue() - return rating
* $('ratingID').RatingPercents(0 < float < 100) - set rating by percents
* $('ratingID').RatingPercents() - return rating percents
* $('ratingID').RatingVote(true or 'on') - set vote=on rating mode
* $('ratingID').RatingVote(false or 'off') - set vote=off rating mode
*/
(function($) {
var pluginName = 'Rating',
initAllSelector = '[data-role=rating], .rating',
paramKeys = ['Stars', 'Rating', 'Vote'];
$[pluginName] = function(element, options) {
if (!element) {
return $()[pluginName]({initAll: true});
}
var defaults = {
// stars count
stars: 5,
// init value
rating: 0,
// voting mode
vote: 'on'
};
var plugin = this;
plugin.settings = {};
var $element = $(element),
starElements = [],
$starElements,
$innerElement, // for vote=off mode
currentRating;
plugin.init = function() {
plugin.settings = $.extend({}, defaults, options);
currentRating = plugin.settings.rating;
if (plugin.settings.vote === 'on') {
voteOnInit();
} else {
voteOffInit();
}
};
/**
* public methods to set and get rating (value, percent)
* use it like this: $('#ratingElementID').data('Rating').setRating(4)
*/
plugin.setRating = function (rating) {
setRating(rating);
return rating;
};
plugin.setRatingPercents = function (ratingPercents) {
setRating((ratingPercents / 100) * plugin.settings.stars);
return ratingPercents;
};
plugin.getRating = function () {
return currentRating;
};
plugin.getRatingPercents = function () {
return currentRating / plugin.settings.stars * 100;
};
/**
* public method for change vote mode
*/
plugin.voteOn = function () {
plugin.settings.vote = 'on';
voteOnInit();
};
plugin.voteOff = function () {
plugin.settings.vote = 'off';
voteOffInit();
};
/**
* init vote=off mode rating
*/
var voteOffInit = function () {
var width,
settings = plugin.settings;
$element.empty();
// special class for vote=off mode
$element.addClass('static-rating');
width = ($element.hasClass('small') ? '14' : '27') * settings.stars;
$element.css('width', width);
$innerElement = $('<div class="rating-value"></div>');
$innerElement.appendTo($element);
setRating(currentRating);
};
/**
* init vote=on mode rating
*/
var voteOnInit = function () {
var settings = plugin.settings,
a, i;
$element.empty();
$element.removeClass('static-rating');
// create stars (count starts from 1)
for (i = 1; i <= settings.stars; i++) {
a = starElements[i] = $('<a href="javascript:void(0)"></a>');
a.data('starIndex', i);
a.appendTo($element);
}
// event handlers for voting
$starElements = $element.find('a');
$starElements.on('mouseenter', function () {
var index = $(this).data('starIndex');
lightStars(0, true);
lightStars(index);
$element.trigger('hovered', [index]);
});
$starElements.on('mouseleave', function () {
lightStars(0);
lightStars(currentRating, true);
});
$starElements.on('click', function(){
var index = $(this).data('starIndex');
currentRating = index;
$element.trigger('rated', [index]);
});
setRating(currentRating);
};
/**
* make stars fired (from first to (starIndex - 1))
* or turn off stars if starIndex = 0
* @param starIndex
* @param rated if true - add 'rated' class, else 'hover'
*/
var lightStars = function (starIndex, rated) {
var class_ = rated ? 'rated' : 'hover';
starIndex = Math.round(starIndex);
$starElements.removeClass(class_);
$starElements.filter(':lt(' + starIndex + ')').addClass(class_);
};
/**
* light stars and store rating
* @param rating
*/
var setRating = function (rating) {
var settings = plugin.settings,
percents;
currentRating = rating;
if (settings.vote === 'on') {
lightStars(rating, true);
} else {
percents = rating / settings.stars * 100;
$innerElement.css('width', percents + '%');
}
};
plugin.init();
};
/**
* get or set rating value to/from first element in set
*/
$.fn.RatingValue = function(value) {
var ratingPlugin = $(this.get(0)).data('Rating');
if (typeof ratingPlugin !== 'undefined') {
if (typeof value !== 'undefined') {
return ratingPlugin.setRating(value);
} else {
return ratingPlugin.getRating();
}
}
};
/**
* get or set rating percents to/from first element in set
*/
$.fn.RatingPercents = function(value) {
var ratingPlugin = $(this.get(0)).data('Rating');
if (typeof ratingPlugin !== 'undefined') {
if (typeof value !== 'undefined') {
return ratingPlugin.setRatingPercents(value);
} else {
return ratingPlugin.getRatingPercents();
}
}
};
/**
* changes rating mode
*/
$.fn.RatingVote = function(vote) {
var ratingPlugin = $(this.get(0)).data('Rating');
if (typeof ratingPlugin !== 'undefined') {
if (vote === true || vote === 'on') {
ratingPlugin.voteOn();
} else if (vote === false || vote === 'off') {
ratingPlugin.voteOff();
}
}
};
$.fn[pluginName] = function(options) {
var elements = options && options.initAll ? $(initAllSelector) : this;
return elements.each(function() {
var that = $(this),
params = {},
plugin;
if (undefined == that.data(pluginName)) {
$.each(paramKeys, function(index, key){
params[key[0].toLowerCase() + key.slice(1)] = that.data('param' + key);
});
plugin = new $[pluginName](this, params);
that.data(pluginName, plugin);
}
});
};
// autoinit
$(function(){
$()[pluginName]({initAll: true});
});
})(jQuery);