PageSourceSearch

https://www.txirula.com/modules/gformbuilderpro/views/js/front/jquery.minicolors.js?f&rand=65310

js txirula.com collected 2026-09-25 05:59:29 UTC 41,480 bytes, 1,134 lines download raw bytes

1/**
2* This is jQuery MiniColors file. A tiny color picker built on jQuery. Don't edit the file if you want to update module in future.
3* 
4* @author    A Beautiful Site  <http://www.abeautifulsite.net>
5* @copyright 2015 A Beautiful Site
6* @link	     https://github.com/claviska/jquery-minicolors
7* @license   http://opensource.org/licenses/MIT
8*/
9
10(function (factory) {
11    /* jshint ignore:start */
12    if (typeof define === 'function' && define.amd) {
13        // AMD. Register as an anonymous module.
14        define(['jquery'], factory);
15    } else if (typeof exports === 'object') {
16        // Node/CommonJS
17        module.exports = factory(require('jquery'));
18    } else {
19        // Browser globals
20        factory(jQuery);
21    }
22    /* jshint ignore:end */
23}(function ($) {
24
25    'use strict';
26
27    // Defaults
28    $.minicolors = {
29        defaults: {
30            animationSpeed: 50,
31            animationEasing: 'swing',
32            change: null,
33            changeDelay: 0,
34            control: 'hue',
35            dataUris: true,
36            defaultValue: '',
37            format: 'hex',
38            hide: null,
39            hideSpeed: 100,
40            inline: false,
41            keywords: '',
42            letterCase: 'lowercase',
43            opacity: false,
44            position: 'bottom left',
45            show: null,
46            showSpeed: 100,
47            theme: 'default',
48            swatches: []
49        }
50    };
51
52    // Public methods
53    $.extend($.fn, {
54        minicolors: function(method, data) {
55
56            switch(method) {
57
58                // Destroy the control
59                case 'destroy':
60                    $(this).each( function() {
61                        destroy($(this));
62                    });
63                    return $(this);
64
65                // Hide the color picker
66                case 'hide':
67                    hide();
68                    return $(this);
69
70                // Get/set opacity
71                case 'opacity':
72                    // Getter
73                    if( data === undefined ) {
74                        // Getter
75                        return $(this).attr('data-opacity');
76                    } else {
77                        // Setter
78                        $(this).each( function() {
79                            updateFromInput($(this).attr('data-opacity', data));
80                        });
81                    }
82                    return $(this);
83
84                // Get an RGB(A) object based on the current color/opacity
85                case 'rgbObject':
86                    return rgbObject($(this), method === 'rgbaObject');
87
88                // Get an RGB(A) string based on the current color/opacity
89                case 'rgbString':
90                case 'rgbaString':
91                    return rgbString($(this), method === 'rgbaString');
92
93                // Get/set settings on the fly
94                case 'settings':
95                    if( data === undefined ) {
96                        return $(this).data('minicolors-settings');
97                    } else {
98                        // Setter
99                        $(this).each( function() {
100                            var settings = $(this).data('minicolors-settings') || {};
101                            destroy($(this));
102                            $(this).minicolors($.extend(true, settings, data));
103                        });
104                    }
105                    return $(this);
106
107                // Show the color picker
108                case 'show':
109                    show( $(this).eq(0) );
110                    return $(this);
111
112                // Get/set the hex color value
113                case 'value':
114                    if( data === undefined ) {
115                        // Getter
116                        return $(this).val();
117                    } else {
118                        // Setter
119                        $(this).each( function() {
120                            if( typeof(data) === 'object' ) {
121                                if( data.opacity ) {
122                                    $(this).attr('data-opacity', keepWithin(data.opacity, 0, 1));
123                                }
124                                if( data.color ) {
125                                    $(this).val(data.color);
126                                }
127                            } else {
128                                $(this).val(data);
129                            }
130                            updateFromInput($(this));
131                        });
132                    }
133                    return $(this);
134
135                // Initializes the control
136                default:
137                    if( method !== 'create' ) data = method;
138                    $(this).each( function() {
139                        init($(this), data);
140                    });
141                    return $(this);
142
143            }
144
145        }
146    });
147
148    // Initialize input elements
149    function init(input, settings) {
150
151        var minicolors = $('<div class="minicolors" />'),
152            defaults = $.minicolors.defaults,
153            size,
154            swatches,
155            swatch,
156            panel,
157            i;
158
159        // Do nothing if already initialized
160        if( input.data('minicolors-initialized') ) return;
161
162        // Handle settings
163        settings = $.extend(true, {}, defaults, settings);
164
165        // The wrapper
166        minicolors
167            .addClass('minicolors-theme-' + settings.theme)
168            .toggleClass('minicolors-with-opacity', settings.opacity)
169            .toggleClass('minicolors-no-data-uris', settings.dataUris !== true);
170
171        // Custom positioning
172        if( settings.position !== undefined ) {
173            $.each(settings.position.split(' '), function() {
174                minicolors.addClass('minicolors-position-' + this);
175            });
176        }
177
178        // Input size
179        if( settings.format === 'rgb' ) {
180            size = settings.opacity ? '25' : '20';
181        } else {
182            size = settings.keywords ? '11' : '7';
183        }
184
185        // The input
186        input
187            .addClass('minicolors-input')
188            .data('minicolors-initialized', false)
189            .data('minicolors-settings', settings)
190            .prop('size', size)
191            .wrap(minicolors)
192            .after(
193                '<div class="minicolors-panel minicolors-slider-' + settings.control + '">' +
194                    '<div class="minicolors-slider minicolors-sprite">' +
195                        '<div class="minicolors-picker"></div>' +
196                    '</div>' +
197                    '<div class="minicolors-opacity-slider minicolors-sprite">' +
198                        '<div class="minicolors-picker"></div>' +
199                    '</div>' +
200                    '<div class="minicolors-grid minicolors-sprite">' +
201                        '<div class="minicolors-grid-inner"></div>' +
202                        '<div class="minicolors-picker"><div></div></div>' +
203                    '</div>' +
204                '</div>'
205            );
206        
207        // The swatch
208        if( !settings.inline ) {
209            input.after('<span class="minicolors-swatch minicolors-sprite minicolors-input-swatch"><span class="minicolors-swatch-color"></span></span>');
210            input.next('.minicolors-input-swatch').on('click', function(event) {
211                event.preventDefault();
212                input.focus();
213            });
214        }
215
216        // Prevent text selection in IE
217        panel = input.parent().find('.minicolors-panel');
218        panel.on('selectstart', function() { return false; }).end();
219        
220        // Swatches
221        if (settings.swatches && settings.swatches.length !== 0) {
222            if (settings.swatches.length > 7) {
223                settings.swatches.length = 7;
224            }
225            panel.addClass('minicolors-with-swatches');
226            swatches = $('<ul class="minicolors-swatches"></ul>')
227                .appendTo(panel);
228            for(i = 0; i < settings.swatches.length; ++i) {
229                swatch = settings.swatches[i];
230                swatch = isRgb(swatch) ? parseRgb(swatch, true) : hex2rgb(parseHex(swatch, true));
231                $('<li class="minicolors-swatch minicolors-sprite"><span class="minicolors-swatch-color"></span></li>')
232                    .appendTo(swatches)
233                    .data('swatch-color', settings.swatches[i])
234                    .find('.minicolors-swatch-color')
235                    .css({
236                        backgroundColor: rgb2hex(swatch),
237                        opacity: swatch.a
238                    });
239                settings.swatches[i] = swatch;
240            }
241                
242        }
243
244        // Inline controls
245        if( settings.inline ) input.parent().addClass('minicolors-inline');
246
247        updateFromInput(input, false);
248
249        input.data('minicolors-initialized', true);
250
251    }
252
253    // Returns the input back to its original state
254    function destroy(input) {
255
256        var minicolors = input.parent();
257
258        // Revert the input element
259        input
260            .removeData('minicolors-initialized')
261            .removeData('minicolors-settings')
262            .removeProp('size')
263            .removeClass('minicolors-input');
264
265        // Remove the wrap and destroy whatever remains
266        minicolors.before(input).remove();
267
268    }
269
270    // Shows the specified dropdown panel
271    function show(input) {
272
273        var minicolors = input.parent(),
274            panel = minicolors.find('.minicolors-panel'),
275            settings = input.data('minicolors-settings');
276
277        // Do nothing if uninitialized, disabled, inline, or already open
278        if( !input.data('minicolors-initialized') ||
279            input.prop('disabled') ||
280            minicolors.hasClass('minicolors-inline') ||
281            minicolors.hasClass('minicolors-focus')
282        ) return;
283
284        hide();
285
286        minicolors.addClass('minicolors-focus');
287        panel
288            .stop(true, true)
289            .fadeIn(settings.showSpeed, function() {
290                if( settings.show ) settings.show.call(input.get(0));
291            });
292
293    }
294
295    // Hides all dropdown panels
296    function hide() {
297
298        $('.minicolors-focus').each( function() {
299
300            var minicolors = $(this),
301                input = minicolors.find('.minicolors-input'),
302                panel = minicolors.find('.minicolors-panel'),
303                settings = input.data('minicolors-settings');
304
305            panel.fadeOut(settings.hideSpeed, function() {
306                if( settings.hide ) settings.hide.call(input.get(0));
307                minicolors.removeClass('minicolors-focus');
308            });
309
310        });
311    }
312
313    // Moves the selected picker
314    function move(target, event, animate) {
315
316        var input = target.parents('.minicolors').find('.minicolors-input'),
317            settings = input.data('minicolors-settings'),
318            picker = target.find('[class$=-picker]'),
319            offsetX = target.offset().left,
320            offsetY = target.offset().top,
321            x = Math.round(event.pageX - offsetX),
322            y = Math.round(event.pageY - offsetY),
323            duration = animate ? settings.animationSpeed : 0,
324            wx, wy, r, phi;
325
326        // Touch support
327        if( event.originalEvent.changedTouches ) {
328            x = event.originalEvent.changedTouches[0].pageX - offsetX;
329            y = event.originalEvent.changedTouches[0].pageY - offsetY;
330        }
331
332        // Constrain picker to its container
333        if( x < 0 ) x = 0;
334        if( y < 0 ) y = 0;
335        if( x > target.width() ) x = target.width();
336        if( y > target.height() ) y = target.height();
337
338        // Constrain color wheel values to the wheel
339        if( target.parent().is('.minicolors-slider-wheel') && picker.parent().is('.minicolors-grid') ) {
340            wx = 75 - x;
341            wy = 75 - y;
342            r = Math.sqrt(wx * wx + wy * wy);
343            phi = Math.atan2(wy, wx);
344            if( phi < 0 ) phi += Math.PI * 2;
345            if( r > 75 ) {
346                r = 75;
347                x = 75 - (75 * Math.cos(phi));
348                y = 75 - (75 * Math.sin(phi));
349            }
350            x = Math.round(x);
351            y = Math.round(y);
352        }
353
354        // Move the picker
355        if( target.is('.minicolors-grid') ) {
356            picker
357                .stop(true)
358                .animate({
359                    top: y + 'px',
360                    left: x + 'px'
361                }, duration, settings.animationEasing, function() {
362                    updateFromControl(input, target);
363                });
364        } else {
365            picker
366                .stop(true)
367                .animate({
368                    top: y + 'px'
369                }, duration, settings.animationEasing, function() {
370                    updateFromControl(input, target);
371                });
372        }
373
374    }
375
376    // Sets the input based on the color picker values
377    function updateFromControl(input, target) {
378
379        function getCoords(picker, container) {
380
381            var left, top;
382            if( !picker.length || !container ) return null;
383            left = picker.offset().left;
384            top = picker.offset().top;
385
386            return {
387                x: left - container.offset().left + (picker.outerWidth() / 2),
388                y: top - container.offset().top + (picker.outerHeight() / 2)
389            };
390
391        }
392
393        var hue, saturation, brightness, x, y, r, phi,
394
395            hex = input.val(),
396            opacity = input.attr('data-opacity'),
397
398            // Helpful references
399            minicolors = input.parent(),
400            settings = input.data('minicolors-settings'),
401            swatch = minicolors.find('.minicolors-input-swatch'),
402
403            // Panel objects
404            grid = minicolors.find('.minicolors-grid'),
405            slider = minicolors.find('.minicolors-slider'),
406            opacitySlider = minicolors.find('.minicolors-opacity-slider'),
407
408            // Picker objects
409            gridPicker = grid.find('[class$=-picker]'),
410            sliderPicker = slider.find('[class$=-picker]'),
411            opacityPicker = opacitySlider.find('[class$=-picker]'),
412
413            // Picker positions
414            gridPos = getCoords(gridPicker, grid),
415            sliderPos = getCoords(sliderPicker, slider),
416            opacityPos = getCoords(opacityPicker, opacitySlider);
417
418        // Handle colors
419        if( target.is('.minicolors-grid, .minicolors-slider, .minicolors-opacity-slider') ) {
420
421            // Determine HSB values
422            switch(settings.control) {
423
424                case 'wheel':
425                    // Calculate hue, saturation, and brightness
426                    x = (grid.width() / 2) - gridPos.x;
427                    y = (grid.height() / 2) - gridPos.y;
428                    r = Math.sqrt(x * x + y * y);
429                    phi = Math.atan2(y, x);
430                    if( phi < 0 ) phi += Math.PI * 2;
431                    if( r > 75 ) {
432                        r = 75;
433                        gridPos.x = 69 - (75 * Math.cos(phi));
434                        gridPos.y = 69 - (75 * Math.sin(phi));
435                    }
436                    saturation = keepWithin(r / 0.75, 0, 100);
437                    hue = keepWithin(phi * 180 / Math.PI, 0, 360);
438                    brightness = keepWithin(100 - Math.floor(sliderPos.y * (100 / slider.height())), 0, 100);
439                    hex = hsb2hex({
440                        h: hue,
441                        s: saturation,
442                        b: brightness
443                    });
444
445                    // Update UI
446                    slider.css('backgroundColor', hsb2hex({ h: hue, s: saturation, b: 100 }));
447                    break;
448
449                case 'saturation':
450                    // Calculate hue, saturation, and brightness
451                    hue = keepWithin(parseInt(gridPos.x * (360 / grid.width()), 10), 0, 360);
452                    saturation = keepWithin(100 - Math.floor(sliderPos.y * (100 / slider.height())), 0, 100);
453                    brightness = keepWithin(100 - Math.floor(gridPos.y * (100 / grid.height())), 0, 100);
454                    hex = hsb2hex({
455                        h: hue,
456                        s: saturation,
457                        b: brightness
458                    });
459
460                    // Update UI
461                    slider.css('backgroundColor', hsb2hex({ h: hue, s: 100, b: brightness }));
462                    minicolors.find('.minicolors-grid-inner').css('opacity', saturation / 100);
463                    break;
464
465                case 'brightness':
466                    // Calculate hue, saturation, and brightness
467                    hue = keepWithin(parseInt(gridPos.x * (360 / grid.width()), 10), 0, 360);
468                    saturation = keepWithin(100 - Math.floor(gridPos.y * (100 / grid.height())), 0, 100);
469                    brightness = keepWithin(100 - Math.floor(sliderPos.y * (100 / slider.height())), 0, 100);
470                    hex = hsb2hex({
471                        h: hue,
472                        s: saturation,
473                        b: brightness
474                    });
475
476                    // Update UI
477                    slider.css('backgroundColor', hsb2hex({ h: hue, s: saturation, b: 100 }));
478                    minicolors.find('.minicolors-grid-inner').css('opacity', 1 - (brightness / 100));
479                    break;
480
481                default:
482                    // Calculate hue, saturation, and brightness
483                    hue = keepWithin(360 - parseInt(sliderPos.y * (360 / slider.height()), 10), 0, 360);
484                    saturation = keepWithin(Math.floor(gridPos.x * (100 / grid.width())), 0, 100);
485                    brightness = keepWithin(100 - Math.floor(gridPos.y * (100 / grid.height())), 0, 100);
486                    hex = hsb2hex({
487                        h: hue,
488                        s: saturation,
489                        b: brightness
490                    });
491
492                    // Update UI
493                    grid.css('backgroundColor', hsb2hex({ h: hue, s: 100, b: 100 }));
494                    break;
495
496            }
497            
498            // Handle opacity
499            if( settings.opacity ) {
500                opacity = parseFloat(1 - (opacityPos.y / opacitySlider.height())).toFixed(2);
501            } else {
502                opacity = 1;
503            }
504            
505            updateInput(input, hex, opacity);
506        }
507        else {
508            // Set swatch color
509            swatch.find('span').css({
510                backgroundColor: hex,
511                opacity: opacity
512            });
513
514            // Handle change event
515            doChange(input, hex, opacity);
516        }
517    }
518    
519    // Sets the value of the input and does the appropriate conversions
520    // to respect settings, also updates the swatch
521    function updateInput(input, value, opacity) {
522        var rgb,
523        
524        // Helpful references
525        minicolors = input.parent(),
526        settings = input.data('minicolors-settings'),
527        swatch = minicolors.find('.minicolors-input-swatch');
528        
529        if( settings.opacity ) input.attr('data-opacity', opacity);
530        
531        // Set color string
532        if( settings.format === 'rgb' ) {
533            // Returns RGB(A) string
534            
535            // Checks for input format and does the conversion
536            if ( isRgb(value) ) {
537                rgb = parseRgb(value, true);
538            }
539            else {
540                rgb = hex2rgb(parseHex(value, true));
541            }
542            
543            opacity = input.attr('data-opacity') === '' ? 1 : keepWithin( parseFloat( input.attr('data-opacity') ).toFixed(2), 0, 1 );
544            if( isNaN( opacity ) || !settings.opacity ) opacity = 1;
545
546            if( input.minicolors('rgbObject').a <= 1 && rgb && settings.opacity) {
547                // Set RGBA string if alpha
548                value = 'rgba(' + rgb.r + ', ' + rgb.g + ', ' + rgb.b + ', ' + parseFloat( opacity ) + ')';
549            } else {
550                // Set RGB string (alpha = 1)
551                value = 'rgb(' + rgb.r + ', ' + rgb.g + ', ' + rgb.b + ')';
552            }
553        } else {
554            // Returns hex color
555            
556            // Checks for input format and does the conversion
557            if ( isRgb(value) ) {
558                value = rgbString2hex(value);
559            }
560            
561            value = convertCase( value, settings.letterCase );
562        }
563
564        // Update value from picker
565        input.val( value );
566        
567        // Set swatch color
568        swatch.find('span').css({
569            backgroundColor: value,
570            opacity: opacity
571        });
572
573        // Handle change event
574        doChange(input, value, opacity);
575    }
576
577    // Sets the color picker values from the input
578    function updateFromInput(input, preserveInputValue) {
579
580        var hex,
581            hsb,
582            opacity,
583            keywords,
584            alpha,
585            value,
586            x, y, r, phi,
587
588            // Helpful references
589            minicolors = input.parent(),
590            settings = input.data('minicolors-settings'),
591            swatch = minicolors.find('.minicolors-input-swatch'),
592
593            // Panel objects
594            grid = minicolors.find('.minicolors-grid'),
595            slider = minicolors.find('.minicolors-slider'),
596            opacitySlider = minicolors.find('.minicolors-opacity-slider'),
597
598            // Picker objects
599            gridPicker = grid.find('[class$=-picker]'),
600            sliderPicker = slider.find('[class$=-picker]'),
601            opacityPicker = opacitySlider.find('[class$=-picker]');
602
603        // Determine hex/HSB values
604        if( isRgb(input.val()) ) {
605            // If input value is a rgb(a) string, convert it to hex color and update opacity
606            hex = rgbString2hex(input.val());
607            alpha = keepWithin(parseFloat(getAlpha(input.val())).toFixed(2), 0, 1);
608            if( alpha ) {
609                input.attr('data-opacity', alpha);
610            }
611        } else {
612            hex = convertCase(parseHex(input.val(), true), settings.letterCase);
613        }
614
615        if( !hex ){
616            hex = convertCase(parseInput(settings.defaultValue, true), settings.letterCase);
617        }
618        hsb = hex2hsb(hex);
619
620        // Get array of lowercase keywords
621        keywords = !settings.keywords ? [] : $.map(settings.keywords.split(','), function(a) {
622            return $.trim(a.toLowerCase());
623        });
624
625        // Set color string
626        if( input.val() !== '' && $.inArray(input.val().toLowerCase(), keywords) > -1 ) {
627            value = convertCase(input.val());
628        } else {
629            value = isRgb(input.val()) ? parseRgb(input.val()) : hex;
630        }
631
632        // Update input value
633        if( !preserveInputValue ) input.val(value);
634
635        // Determine opacity value
636        if( settings.opacity ) {
637            // Get from data-opacity attribute and keep within 0-1 range
638            opacity = input.attr('data-opacity') === '' ? 1 : keepWithin(parseFloat(input.attr('data-opacity')).toFixed(2), 0, 1);
639            if( isNaN(opacity) ) opacity = 1;
640            input.attr('data-opacity', opacity);
641            swatch.find('span').css('opacity', opacity);
642
643            // Set opacity picker position
644            y = keepWithin(opacitySlider.height() - (opacitySlider.height() * opacity), 0, opacitySlider.height());
645            opacityPicker.css('top', y + 'px');
646        }
647
648        // Set opacity to zero if input value is transparent
649        if( input.val().toLowerCase() === 'transparent' ) {
650            swatch.find('span').css('opacity', 0);
651        }
652
653        // Update swatch
654        swatch.find('span').css('backgroundColor', hex);
655
656        // Determine picker locations
657        switch(settings.control) {
658
659            case 'wheel':
660                // Set grid position
661                r = keepWithin(Math.ceil(hsb.s * 0.75), 0, grid.height() / 2);
662                phi = hsb.h * Math.PI / 180;
663                x = keepWithin(75 - Math.cos(phi) * r, 0, grid.width());
664                y = keepWithin(75 - Math.sin(phi) * r, 0, grid.height());
665                gridPicker.css({
666                    top: y + 'px',
667                    left: x + 'px'
668                });
669
670                // Set slider position
671                y = 150 - (hsb.b / (100 / grid.height()));
672                if( hex === '' ) y = 0;
673                sliderPicker.css('top', y + 'px');
674
675                // Update panel color
676                slider.css('backgroundColor', hsb2hex({ h: hsb.h, s: hsb.s, b: 100 }));
677                break;
678
679            case 'saturation':
680                // Set grid position
681                x = keepWithin((5 * hsb.h) / 12, 0, 150);
682                y = keepWithin(grid.height() - Math.ceil(hsb.b / (100 / grid.height())), 0, grid.height());
683                gridPicker.css({
684                    top: y + 'px',
685                    left: x + 'px'
686                });
687
688                // Set slider position
689                y = keepWithin(slider.height() - (hsb.s * (slider.height() / 100)), 0, slider.height());
690                sliderPicker.css('top', y + 'px');
691
692                // Update UI
693                slider.css('backgroundColor', hsb2hex({ h: hsb.h, s: 100, b: hsb.b }));
694                minicolors.find('.minicolors-grid-inner').css('opacity', hsb.s / 100);
695                break;
696
697            case 'brightness':
698                // Set grid position
699                x = keepWithin((5 * hsb.h) / 12, 0, 150);
700                y = keepWithin(grid.height() - Math.ceil(hsb.s / (100 / grid.height())), 0, grid.height());
701                gridPicker.css({
702                    top: y + 'px',
703                    left: x + 'px'
704                });
705
706                // Set slider position
707                y = keepWithin(slider.height() - (hsb.b * (slider.height() / 100)), 0, slider.height());
708                sliderPicker.css('top', y + 'px');
709
710                // Update UI
711                slider.css('backgroundColor', hsb2hex({ h: hsb.h, s: hsb.s, b: 100 }));
712                minicolors.find('.minicolors-grid-inner').css('opacity', 1 - (hsb.b / 100));
713                break;
714
715            default:
716                // Set grid position
717                x = keepWithin(Math.ceil(hsb.s / (100 / grid.width())), 0, grid.width());
718                y = keepWithin(grid.height() - Math.ceil(hsb.b / (100 / grid.height())), 0, grid.height());
719                gridPicker.css({
720                    top: y + 'px',
721                    left: x + 'px'
722                });
723
724                // Set slider position
725                y = keepWithin(slider.height() - (hsb.h / (360 / slider.height())), 0, slider.height());
726                sliderPicker.css('top', y + 'px');
727
728                // Update panel color
729                grid.css('backgroundColor', hsb2hex({ h: hsb.h, s: 100, b: 100 }));
730                break;
731
732        }
733
734        // Fire change event, but only if minicolors is fully initialized
735        if( input.data('minicolors-initialized') ) {
736            doChange(input, value, opacity);
737        }
738
739    }
740
741    // Runs the change and changeDelay callbacks
742    function doChange(input, value, opacity) {
743
744        var settings = input.data('minicolors-settings'),
745            lastChange = input.data('minicolors-lastChange'),
746            obj,
747            sel,
748            i;
749
750        // Only run if it actually changed
751        if( !lastChange || lastChange.value !== value || lastChange.opacity !== opacity ) {
752            
753            // Remember last-changed value
754            input.data('minicolors-lastChange', {
755                value: value,
756                opacity: opacity
757            });
758
759            // Check and select applicable swatch
760            if (settings.swatches && settings.swatches.length !== 0) {
761                if(!isRgb(value)) {
762                    obj = hex2rgb(value);
763                }
764                else {
765                    obj = parseRgb(value, true);
766                }
767                sel = -1;
768                for(i = 0; i < settings.swatches.length; ++i) {
769                    if (obj.r === settings.swatches[i].r && obj.g === settings.swatches[i].g && obj.b === settings.swatches[i].b && obj.a === settings.swatches[i].a) {
770                        sel = i;
771                        break;
772                    }
773                }
774                
775                input.parent().find('.minicolors-swatches .minicolors-swatch').removeClass('selected');
776                if (i !== -1) {
777                    input.parent().find('.minicolors-swatches .minicolors-swatch').eq(i).addClass('selected');
778                }
779            }
780
781            // Fire change event
782            if( settings.change ) {
783                if( settings.changeDelay ) {
784                    // Call after a delay
785                    clearTimeout(input.data('minicolors-changeTimeout'));
786                    input.data('minicolors-changeTimeout', setTimeout( function() {
787                        settings.change.call(input.get(0), value, opacity);
788                    }, settings.changeDelay));
789                } else {
790                    // Call immediately
791                    settings.change.call(input.get(0), value, opacity);
792                }
793            }
794            input.trigger('change').trigger('input');
795        }
796
797    }
798
799    // Generates an RGB(A) object based on the input's value
800    function rgbObject(input) {
801        var hex = parseHex($(input).val(), true),
802            rgb = hex2rgb(hex),
803            opacity = $(input).attr('data-opacity');
804        if( !rgb ) return null;
805        if( opacity !== undefined ) $.extend(rgb, { a: parseFloat(opacity) });
806        return rgb;
807    }
808
809    // Generates an RGB(A) string based on the input's value
810    function rgbString(input, alpha) {
811        var hex = parseHex($(input).val(), true),
812            rgb = hex2rgb(hex),
813            opacity = $(input).attr('data-opacity');
814        if( !rgb ) return null;
815        if( opacity === undefined ) opacity = 1;
816        if( alpha ) {
817            return 'rgba(' + rgb.r + ', ' + rgb.g + ', ' + rgb.b + ', ' + parseFloat(opacity) + ')';
818        } else {
819            return 'rgb(' + rgb.r + ', ' + rgb.g + ', ' + rgb.b + ')';
820        }
821    }
822
823    // Converts to the letter case specified in settings
824    function convertCase(string, letterCase) {
825        return letterCase === 'uppercase' ? string.toUpperCase() : string.toLowerCase();
826    }
827
828    // Parses a string and returns a valid hex string when possible
829    function parseHex(string, expand) {
830        string = string.replace(/^#/g, '');
831        if( !string.match(/^[A-F0-9]{3,6}/ig) ) return '';
832        if( string.length !== 3 && string.length !== 6 ) return '';
833        if( string.length === 3 && expand ) {
834            string = string[0] + string[0] + string[1] + string[1] + string[2] + string[2];
835        }
836        return '#' + string;
837    }
838
839    // Parses a string and returns a valid RGB(A) string when possible
840    function parseRgb(string, obj) {
841
842        var values = string.replace(/[^\d,.]/g, ''),
843            rgba = values.split(',');
844
845        rgba[0] = keepWithin(parseInt(rgba[0], 10), 0, 255);
846        rgba[1] = keepWithin(parseInt(rgba[1], 10), 0, 255);
847        rgba[2] = keepWithin(parseInt(rgba[2], 10), 0, 255);
848        if( rgba[3] ) {
849            rgba[3] = keepWithin(parseFloat(rgba[3], 10), 0, 1);
850        }
851
852        // Return RGBA object
853        if( obj ) {
854            return {
855                r: rgba[0],
856                g: rgba[1],
857                b: rgba[2],
858                a: rgba[3] ? rgba[3] : null
859            };
860        }
861
862        // Return RGBA string
863        if( typeof(rgba[3]) !== 'undefined' && rgba[3] <= 1 ) {
864            return 'rgba(' + rgba[0] + ', ' + rgba[1] + ', ' + rgba[2] + ', ' + rgba[3] + ')';
865        } else {
866            return 'rgb(' + rgba[0] + ', ' + rgba[1] + ', ' + rgba[2] + ')';
867        }
868
869    }
870
871    // Parses a string and returns a valid color string when possible
872    function parseInput(string, expand) {
873        if( isRgb(string) ) {
874            // Returns a valid rgb(a) string
875            return parseRgb(string);
876        } else {
877            return parseHex(string, expand);
878        }
879    }
880
881    // Keeps value within min and max
882    function keepWithin(value, min, max) {
883        if( value < min ) value = min;
884        if( value > max ) value = max;
885        return value;
886    }
887
888    // Checks if a string is a valid RGB(A) string
889    function isRgb(string) {
890        var rgb = string.match(/^rgba?[\s+]?\([\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?/i);
891        return (rgb && rgb.length === 4) ? true : false;
892    }
893
894    // Function to get alpha from a RGB(A) string
895    function getAlpha(rgba) {
896        rgba = rgba.match(/^rgba?[\s+]?\([\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?,[\s+]?(\d+(\.\d{1,2})?|\.\d{1,2})[\s+]?/i);
897        return (rgba && rgba.length === 6) ? rgba[4] : '1';
898    }
899
900   // Converts an HSB object to an RGB object
901    function hsb2rgb(hsb) {
902        var rgb = {};
903        var h = Math.round(hsb.h);
904        var s = Math.round(hsb.s * 255 / 100);
905        var v = Math.round(hsb.b * 255 / 100);
906        if(s === 0) {
907            rgb.r = rgb.g = rgb.b = v;
908        } else {
909            var t1 = v;
910            var t2 = (255 - s) * v / 255;
911            var t3 = (t1 - t2) * (h % 60) / 60;
912            if( h === 360 ) h = 0;
913            if( h < 60 ) { rgb.r = t1; rgb.b = t2; rgb.g = t2 + t3; }
914            else if( h < 120 ) {rgb.g = t1; rgb.b = t2; rgb.r = t1 - t3; }
915            else if( h < 180 ) {rgb.g = t1; rgb.r = t2; rgb.b = t2 + t3; }
916            else if( h < 240 ) {rgb.b = t1; rgb.r = t2; rgb.g = t1 - t3; }
917            else if( h < 300 ) {rgb.b = t1; rgb.g = t2; rgb.r = t2 + t3; }
918            else if( h < 360 ) {rgb.r = t1; rgb.g = t2; rgb.b = t1 - t3; }
919            else { rgb.r = 0; rgb.g = 0; rgb.b = 0; }
920        }
921        return {
922            r: Math.round(rgb.r),
923            g: Math.round(rgb.g),
924            b: Math.round(rgb.b)
925        };
926    }
927
928    // Converts an RGB string to a hex string
929    function rgbString2hex(rgb){
930        rgb = rgb.match(/^rgba?[\s+]?\([\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?,[\s+]?(\d+)[\s+]?/i);
931        return (rgb && rgb.length === 4) ? '#' +
932        ('0' + parseInt(rgb[1],10).toString(16)).slice(-2) +
933        ('0' + parseInt(rgb[2],10).toString(16)).slice(-2) +
934        ('0' + parseInt(rgb[3],10).toString(16)).slice(-2) : '';
935    }
936
937    // Converts an RGB object to a hex string
938    function rgb2hex(rgb) {
939        var hex = [
940            rgb.r.toString(16),
941            rgb.g.toString(16),
942            rgb.b.toString(16)
943        ];
944        $.each(hex, function(nr, val) {
945            if (val.length === 1) hex[nr] = '0' + val;
946        });
947        return '#' + hex.join('');
948    }
949
950    // Converts an HSB object to a hex string
951    function hsb2hex(hsb) {
952        return rgb2hex(hsb2rgb(hsb));
953    }
954
955    // Converts a hex string to an HSB object
956    function hex2hsb(hex) {
957        var hsb = rgb2hsb(hex2rgb(hex));
958        if( hsb.s === 0 ) hsb.h = 360;
959        return hsb;
960    }
961
962    // Converts an RGB object to an HSB object
963    function rgb2hsb(rgb) {
964        var hsb = { h: 0, s: 0, b: 0 };
965        var min = Math.min(rgb.r, rgb.g, rgb.b);
966        var max = Math.max(rgb.r, rgb.g, rgb.b);
967        var delta = max - min;
968        hsb.b = max;
969        hsb.s = max !== 0 ? 255 * delta / max : 0;
970        if( hsb.s !== 0 ) {
971            if( rgb.r === max ) {
972                hsb.h = (rgb.g - rgb.b) / delta;
973            } else if( rgb.g === max ) {
974                hsb.h = 2 + (rgb.b - rgb.r) / delta;
975            } else {
976                hsb.h = 4 + (rgb.r - rgb.g) / delta;
977            }
978        } else {
979            hsb.h = -1;
980        }
981        hsb.h *= 60;
982        if( hsb.h < 0 ) {
983            hsb.h += 360;
984        }
985        hsb.s *= 100/255;
986        hsb.b *= 100/255;
987        return hsb;
988    }
989
990    // Converts a hex string to an RGB object
991    function hex2rgb(hex) {
992        hex = parseInt(((hex.indexOf('#') > -1) ? hex.substring(1) : hex), 16);
993        return {
994            /* jshint ignore:start */
995            r: hex >> 16,
996            g: (hex & 0x00FF00) >> 8,
997            b: (hex & 0x0000FF)
998            /* jshint ignore:end */
999        };
1000    }
1001
1002    // Handle events
1003    $(document)
1004        // Hide on clicks outside of the control
1005        .on('mousedown.minicolors touchstart.minicolors', function(event) {
1006            if( !$(event.target).parents().add(event.target).hasClass('minicolors') ) {
1007                hide();
1008            }
1009        })
1010        // Start moving
1011        .on('mousedown.minicolors touchstart.minicolors', '.minicolors-grid, .minicolors-slider, .minicolors-opacity-slider', function(event) {
1012            var target = $(this);
1013            event.preventDefault();
1014            $(document).data('minicolors-target', target);
1015            move(target, event, true);
1016        })
1017        // Move pickers
1018        .on('mousemove.minicolors touchmove.minicolors', function(event) {
1019            var target = $(document).data('minicolors-target');
1020            if( target ) move(target, event);
1021        })
1022        // Stop moving
1023        .on('mouseup.minicolors touchend.minicolors', function() {
1024            $(this).removeData('minicolors-target');
1025        })
1026        // Selected a swatch
1027        .on('click.minicolors', '.minicolors-swatches li', function(event) {
1028            event.preventDefault();
1029            var target = $(this), input = target.parents('.minicolors').find('.minicolors-input'), color = target.data('swatch-color');
1030            updateInput(input, color, getAlpha(color));
1031            updateFromInput(input);
1032        })
1033        // Show panel when swatch is clicked
1034        .on('mousedown.minicolors touchstart.minicolors', '.minicolors-input-swatch', function(event) {
1035            var input = $(this).parent().find('.minicolors-input');
1036            event.preventDefault();
1037            show(input);
1038        })
1039        // Show on focus
1040        .on('focus.minicolors', '.minicolors-input', function() {
1041            var input = $(this);
1042            if( !input.data('minicolors-initialized') ) return;
1043            show(input);
1044        })
1045        // Update value on blur
1046        .on('blur.minicolors', '.minicolors-input', function() {
1047            var input = $(this),
1048                settings = input.data('minicolors-settings'),
1049                keywords,
1050                hex,
1051                rgba,
1052                swatchOpacity,
1053                value;
1054
1055            if( !input.data('minicolors-initialized') ) return;
1056
1057            // Get array of lowercase keywords
1058            keywords = !settings.keywords ? [] : $.map(settings.keywords.split(','), function(a) {
1059                return $.trim(a.toLowerCase());
1060            });
1061
1062            // Set color string
1063            if( input.val() !== '' && $.inArray(input.val().toLowerCase(), keywords) > -1 ) {
1064                value = input.val();
1065            } else {
1066                // Get RGBA values for easy conversion
1067                if( isRgb(input.val()) ) {
1068                    rgba = parseRgb(input.val(), true);
1069                } else {
1070                    hex = parseHex(input.val(), true);
1071                    rgba = hex ? hex2rgb(hex) : null;
1072                }
1073
1074                // Convert to format
1075                if( rgba === null ) {
1076                    value = settings.defaultValue;
1077                } else if( settings.format === 'rgb' ) {
1078                    value = settings.opacity ?
1079                        parseRgb('rgba(' + rgba.r + ',' + rgba.g + ',' + rgba.b + ',' + input.attr('data-opacity') + ')') :
1080                        parseRgb('rgb(' + rgba.r + ',' + rgba.g + ',' + rgba.b + ')');
1081                } else {
1082                    value = rgb2hex(rgba);
1083                }
1084            }
1085
1086            // Update swatch opacity
1087            swatchOpacity = settings.opacity ? input.attr('data-opacity') : 1;
1088            if( value.toLowerCase() === 'transparent' ) swatchOpacity = 0;
1089            input
1090                .closest('.minicolors')
1091                .find('.minicolors-input-swatch > span')
1092                .css('opacity', swatchOpacity);
1093
1094            // Set input value
1095            input.val(value);
1096
1097            // Is it blank?
1098            if( input.val() === '' ) input.val(parseInput(settings.defaultValue, true));
1099
1100            // Adjust case
1101            input.val( convertCase(input.val(), settings.letterCase) );
1102
1103        })
1104        // Handle keypresses
1105        .on('keydown.minicolors', '.minicolors-input', function(event) {
1106            var input = $(this);
1107            if( !input.data('minicolors-initialized') ) return;
1108            switch(event.keyCode) {
1109                case 9: // tab
1110                    hide();
1111                    break;
1112                case 13: // enter
1113                case 27: // esc
1114                    hide();
1115                    input.blur();
1116                    break;
1117            }
1118        })
1119        // Update on keyup
1120        .on('keyup.minicolors', '.minicolors-input', function() {
1121            var input = $(this);
1122            if( !input.data('minicolors-initialized') ) return;
1123            updateFromInput(input, true);
1124        })
1125        // Update on paste
1126        .on('paste.minicolors', '.minicolors-input', function() {
1127            var input = $(this);
1128            if( !input.data('minicolors-initialized') ) return;
1129            setTimeout( function() {
1130                updateFromInput(input, true);
1131            }, 1);
1132        });
1133
1134}));

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.