vendor: 5,864 bytes, lines 1-173
1/* 2 * A highly customizable rating widget that supports images, utf8 glyphs and other html elements! 3 * https://github.com/auxiliary/rater 4 */ 5;(function ($, window){ 6 $.fn.textWidth = function() 7 { 8 var html_calc = $('<span>' + $(this).html() + '</span>'); 9 html_calc.css('font-size',$(this).css('font-size')).hide(); 10 html_calc.prependTo('body'); 11 var width = html_calc.width(); 12 html_calc.remove(); 13 14 if (width == 0) 15 { 16 var total = 0; 17 $(this).eq(0).children().each(function(){ 18 total += $(this).textWidth(); 19 }); 20 return total; 21 } 22 return width; 23 }; 24 25 $.fn.textHeight = function() 26 { 27 var html_calc = $('<span>' + $(this).html() + '</span>'); 28 html_calc.css('font-size',$(this).css('font-size')).hide(); 29 html_calc.prependTo('body'); 30 var height = html_calc.height(); 31 html_calc.remove(); 32 return height; 33 }; 34 35 /* 36 * IE8 doesn't support isArray! 37 */ 38 Array.isArray = function (obj) { 39 return Object.prototype.toString.call(obj) === "[object Array]"; 40 }; 41 42 /* 43 * Utf-32 isn't supported by default, so we have to use Utf-8 surrogates 44 */ 45 String.prototype.getCodePointLength = function() { 46 return this.length-this.split(/[\uD800-\uDBFF][\uDC00-\uDFFF]/g).length+1; 47 }; 48 49 String.fromCodePoint= function() { 50 var chars= Array.prototype.slice.call(arguments); 51 for (var i= chars.length; i-->0;) { 52 var n = chars[i]-0x10000; 53 if (n>=0) 54 chars.splice(i, 1, 0xD800+(n>>10), 0xDC00+(n&0x3FF)); 55 } 56 return String.fromCharCode.apply(null, chars); 57 }; 58 59 /* 60 * Starting the plugin itself 61 */ 62 $.fn.rate = function(options) 63 { 64 if (options === undefined || typeof options === 'object') 65 { 66 return this.each(function(){ 67 if (!$.data(this, "rate")) 68 { 69 $.data(this, "rate", new Rate(this, options)); 70 } 71 }); 72 } 73 else if (typeof options === 'string') 74 { 75 var args = arguments; 76 var returns; 77 this.each(function(){ 78 var instance = $.data(this, "rate"); 79 if (instance instanceof Rate && typeof instance[options] === 'function') 80 { 81 returns = instance[options].apply(instance, Array.prototype.slice.call(args, 1)); 82 } 83 if (options === 'destroy') 84 { 85 // Unbind all events and empty the plugin data from instance 86 $(instance.element).off(); 87 $.data(this, 'rate', null); 88 } 89 }); 90 91 return returns !== undefined ? returns : this; 92 } 93 }; 94 95 function Rate(element, options) 96 { 97 this.element = element; 98 this.settings = $.extend({}, $.fn.rate.settings, options); 99 this.set_faces = {}; // value, symbol pairs 100 this.build(); 101 } 102 103 Rate.prototype.build = function() 104 { 105 this.layers = {}; 106 this.value = 0; 107 this.raise_select_layer = false; 108 109 if (this.settings.initial_value) 110 { 111 this.value = this.settings.initial_value; 112 } 113 if ($(this.element).attr("data-rate-value")) 114 { 115 this.value = $(this.element).attr("data-rate-value"); 116 } 117 118 /* 119 * Calculate the selected width based on the initial value 120 */ 121 var selected_width = this.value / this.settings.max_value * 100; 122 123 /* 124 * Let's support single strings as symbols as well as objects 125 */ 126 if (typeof this.settings.symbols[this.settings.selected_symbol_type] === 'string') 127 { 128 var symbol = this.settings.symbols[this.settings.selected_symbol_type]; 129 this.settings.symbols[this.settings.selected_symbol_type] = {}; 130 this.settings.symbols[this.settings.selected_symbol_type]['base'] = symbol; 131 this.settings.symbols[this.settings.selected_symbol_type]['selected'] = symbol; 132 this.settings.symbols[this.settings.selected_symbol_type]['hover'] = symbol; 133 } 134 135 /* 136 * Making the three main layers (base, select, hover) 137 */ 138 var base_layer = this.addLayer("base-layer", 100, this.settings.symbols[ 139 this.settings.selected_symbol_type]["base"], true); 140 141 var select_layer = this.addLayer("select-layer", selected_width, 142 this.settings.symbols[this.settings.selected_symbol_type]["selected"], true); 143 144 var hover_layer = this.addLayer("hover-layer", 0, this.settings.symbols[ 145 this.settings.selected_symbol_type]["hover"], false); 146 147 /* var face_layer = this.addLayer("face-layer", 1, this.settings 148 .symbols[this.settings.face_layer_symbol_type][0], true); */ 149 150 this.layers["base_layer"] = base_layer; 151 this.layers["select_layer"] = select_layer; 152 this.layers["hover_layer"] = hover_layer; 153 154 /* 155 * Bind the container to some events 156 */ 157 $(this.element).on("mousemove", $.proxy(this.hover, this)); 158 $(this.element).on("click", $.proxy(this.select, this)); 159 $(this.element).on("mouseleave", $.proxy(this.mouseout, this)); 160 161 /* 162 * Set the main element as unselectable 163 */ 164 $(this.element).css({ 165 "-webkit-touch-callout": "none", 166 "-webkit-user-select": "none", 167 "-khtml-user-select": "none", 168 "-moz-user-select": "none", 169 "-ms-user-select": "none", 170 "user-select": "none", 171 }); 172 173 this.value = this.toValue(selected_width * $(base_layer).textWidth()
vendor: 12,123 bytes, lines 173-552
173); 174 175 /* 176 * Update custom input field if provided 177 */ 178 if (this.settings.hasOwnProperty("update_input_field_name")) 179 { 180 this.settings.update_input_field_name.val(this.value); 181 } 182 } 183 184 /* 185 * Function to add a layer 186 */ 187 Rate.prototype.addLayer = function(layer_name, visible_width, symbol, visible) 188 { 189 var layer_body = "<div>"; 190 for (var i = 0; i < this.settings.max_value; i++) 191 { 192 if (Array.isArray(symbol)) 193 { 194 if (this.settings.convert_to_utf8) 195 { 196 symbol[i] = String.fromCodePoint(symbol[i]); 197 } 198 layer_body += "<span>" + (symbol[i]) + "</span>"; 199 } 200 else 201 { 202 if (this.settings.convert_to_utf8) 203 { 204 symbol = String.fromCodePoint(symbol); 205 } 206 layer_body += "<span>" + symbol + "</span>"; 207 } 208 } 209 layer_body += "</div>"; 210 var layer = $(layer_body).addClass("rate-" + layer_name).appendTo(this.element); 211 212 $(layer).css({ 213 width: visible_width + "%", 214 height: $(layer).children().eq(0).textHeight(), 215 overflow: 'hidden', 216 position: 'absolute', 217 top: 0, 218 display: visible ? 'block' : 'none', 219 'white-space': 'nowrap' 220 }); 221 $(this.element).css({ 222 width: $(layer).textWidth() + "px", 223 height: $(layer).height(), 224 position: 'relative', 225 cursor: this.settings.cursor, 226 }); 227 228 return layer; 229 } 230 231 Rate.prototype.updateServer = function() 232 { 233 if (this.settings.url != undefined) 234 { 235 $.ajax({ 236 url: this.settings.url, 237 type: this.settings.ajax_method, 238 data: $.extend({}, { value: this.getValue() }, this.settings.additional_data), 239 success: $.proxy(function(data){ 240 $(this.element).trigger("updateSuccess", [data]); 241 }, this), 242 error: $.proxy(function(jxhr, msg, err){ 243 $(this.element).trigger("updateError", [jxhr, msg, err]); 244 }, this) 245 }); 246 } 247 } 248 249 Rate.prototype.getValue = function() 250 { 251 return this.value; 252 } 253 254 Rate.prototype.hover = function(ev) 255 { 256 var pad = parseInt($(this.element).css("padding-left").replace("px", "")); 257 var x = ev.pageX - $(this.element).offset().left - pad; 258 var val = this.toValue(x, true); 259 260 if (val != this.value) 261 { 262 this.raise_select_layer = false; 263 } 264 265 if (!this.raise_select_layer && !this.settings.readonly) 266 { 267 var visible_width = this.toWidth(val); 268 this.layers.select_layer.css({display: 'none'}); 269 if (!this.settings.only_select_one_symbol) 270 { 271 this.layers.hover_layer.css({ 272 width: visible_width + "%", 273 display: 'block' 274 }); 275 } 276 else 277 { 278 var index_value = Math.floor(val); 279 this.layers.hover_layer.css({ 280 width: "100%", 281 display: 'block' 282 }); 283 this.layers.hover_layer.children("span").css({ 284 visibility: 'hidden', 285 }); 286 this.layers.hover_layer.children("span").eq(index_value != 0 ? index_value - 1 : 0).css({ 287 visibility: 'visible', 288 }); 289 } 290 } 291 } 292 293 /* 294 * Event for when a rating has been selected (clicked) 295 */ 296 Rate.prototype.select = function(ev) 297 { 298 if (!this.settings.readonly) 299 { 300 var old_value = this.getValue(); 301 var pad = parseInt($(this.element).css("padding-left").replace("px", "")); 302 var x = ev.pageX - $(this.element).offset().left - pad; 303 var selected_width = this.toWidth(this.toValue(x, true)); 304 this.setValue(this.toValue(selected_width)); 305 this.raise_select_layer = true; 306 } 307 } 308 309 Rate.prototype.mouseout = function() 310 { 311 this.layers.hover_layer.css({display: 'none'}); 312 this.layers.select_layer.css({display: 'block'}); 313 } 314 315 /* 316 * Takes a width (px) and returns the value it resembles 317 */ 318 Rate.prototype.toWidth = function(val) 319 { 320 return val / this.settings.max_value * 100; 321 } 322 323 /* 324 * Takes a value and calculates the width of the selected/hovered layer 325 */ 326 Rate.prototype.toValue = function(width, in_pixels) 327 { 328 var val; 329 if (in_pixels) 330 { 331 val = width / this.layers.base_layer.textWidth() * this.settings.max_value; 332 } 333 else 334 { 335 val = width / 100 * this.settings.max_value; 336 } 337 338 // Make sure the division doesn't cause some small numbers added by 339 // comparing to a small arbitrary number. 340 var temp = val / this.settings.step_size; 341 if (temp - Math.floor(temp) < 0.00005) 342 { 343 val = Math.round(val / this.settings.step_size) * this.settings.step_size; 344 } 345 val = (Math.ceil(val / this.settings.step_size)) * this.settings.step_size; 346 val = val > this.settings.max_value ? this.settings.max_value : val; 347 return val; 348 } 349 350 Rate.prototype.getElement = function(layer_name, index) 351 { 352 return $(this.element).find(".rate-" + layer_name + " span").eq(index - 1); 353 } 354 355 Rate.prototype.getLayers = function() 356 { 357 return this.layers; 358 } 359 360 Rate.prototype.setFace = function(value, face) 361 { 362 this.set_faces[value] = face; 363 } 364 365 Rate.prototype.setAdditionalData = function(data) 366 { 367 this.settings.additional_data = data; 368 } 369 370 Rate.prototype.getAdditionalData = function() 371 { 372 return this.settings.additional_data; 373 } 374 375 Rate.prototype.removeFace = function(value) 376 { 377 delete this.set_faces[value]; 378 } 379 380 Rate.prototype.setValue = function(value) 381 { 382 if (!this.settings.readonly) 383 { 384 if (value < 0) 385 { 386 value = 0; 387 } 388 else if (value > this.settings.max_value) 389 { 390 value = this.settings.max_value; 391 } 392 393 var old_value = this.getValue(); 394 this.value = value; 395 396 /* 397 * About to change event, should support prevention later 398 */ 399 var change_event = $(this.element).trigger("change", { 400 "from": old_value, 401 "to": this.value 402 }); 403 404 /* 405 * Set/Reset faces 406 */ 407 $(this.element).find(".rate-face").remove(); 408 $(this.element).find("span").css({ 409 visibility: 'visible' 410 }); 411 var index_value = Math.ceil(this.value); 412 if (this.set_faces.hasOwnProperty(index_value)) 413 { 414 var face = "<div>" + this.set_faces[index_value] + "</div>"; 415 var base_layer_element = this.getElement('base-layer', index_value); 416 var select_layer_element = this.getElement('select-layer', index_value); 417 var hover_layer_element = this.getElement('hover-layer', index_value); 418 419 var left_pos = base_layer_element.textWidth() * (index_value - 1) 420 + (base_layer_element.textWidth() - $(face).textWidth()) / 2; 421 422 $(face).appendTo(this.element).css({ 423 display: 'inline-block', 424 position: 'absolute', 425 left: left_pos, 426 }).addClass("rate-face"); 427 428 base_layer_element.css({ 429 visibility: 'hidden' 430 }); 431 select_layer_element.css({ 432 visibility: 'hidden' 433 }); 434 hover_layer_element.css({ 435 visibility: 'hidden' 436 }); 437 } 438 439 /* 440 * Set styles based on width and value 441 */ 442 if (!this.settings.only_select_one_symbol) 443 { 444 var width = this.toWidth(this.value); 445 this.layers.select_layer.css({ 446 display: 'block', 447 width: width + "%", 448 height: this.layers.base_layer.css("height") 449 }); 450 this.layers.hover_layer.css({ 451 display: 'none', 452 height: this.layers.base_layer.css("height") 453 }); 454 } 455 else 456 { 457 var width = this.toWidth(this.settings.max_value); 458 this.layers.select_layer.css({ 459 display: 'block', 460 width: width + "%", 461 height: this.layers.base_layer.css("height") 462 }); 463 this.layers.hover_layer.css({ 464 display: 'none', 465 height: this.layers.base_layer.css("height") 466 }); 467 this.layers.select_layer.children("span").css({ 468 visibility: 'hidden', 469 }); 470 this.layers.select_layer.children("span").eq(index_value != 0 ? index_value - 1 : 0).css({ 471 visibility: 'visible', 472 }); 473 } 474 475 // Update the data-rate-value attribute 476 $(this.element).attr("data-rate-value", this.value); 477 478 if (this.settings.change_once) 479 { 480 this.settings.readonly = true; 481 } 482 this.updateServer(); 483 484 /* 485 * After change event 486 */ 487 var change_event = $(this.element).trigger("afterChange", { 488 "from": old_value, 489 "to": this.value 490 }); 491 492 /* 493 * Update custom input field if provided 494 */ 495 if (this.settings.hasOwnProperty("update_input_field_name")) 496 { 497 this.settings.update_input_field_name.val(this.value); 498 } 499 500 } 501 } 502 503 Rate.prototype.increment = function() 504 { 505 this.setValue(this.getValue() + this.settings.step_size); 506 } 507 508 Rate.prototype.decrement = function() 509 { 510 this.setValue(this.getValue() - this.settings.step_size); 511 } 512 513 $.fn.rate.settings = { 514 max_value: 5, 515 step_size: 0.5, 516 initial_value: 0, 517 symbols: { 518 utf8_star: { 519 base: '\u2606', 520 hover: '\u2605', 521 selected: '\u2605', 522 }, 523 utf8_hexagon: { 524 base: '\u2B21', 525 hover: '\u2B22', 526 selected: '\u2B22', 527 }, 528 hearts: '♥', 529 fontawesome_beer: '<i class="fa fa-beer"></i>', 530 fontawesome_star: { 531 base: '<i class="fa fa-star-o"></i>', 532 hover: '<i class="fa fa-star"></i>', 533 selected: '<i class="fa fa-star"></i>', 534 }, 535 utf8_emoticons: { 536 base: [0x1F625, 0x1F613, 0x1F612, 0x1F604], 537 hover: [0x1F625, 0x1F613, 0x1F612, 0x1F604], 538 selected: [0x1F625, 0x1F613, 0x1F612, 0x1F604], 539 }, 540 }, 541 selected_symbol_type: 'utf8_star', // Must be a key from symbols 542 convert_to_utf8: false, 543 cursor: 'default', 544 readonly: false, 545 change_once: false, // Determines if the rating can only be set once 546 only_select_one_symbol: false, // If set to true, only selects the hovered/selected symbol and nothing prior to it 547 ajax_method: 'POST', 548 additional_data: {}, // Additional data to send to the server 549 //update_input_field_name = some input field set by the user 550 }; 551 552}(jQuery, window));
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.