PageSourceSearch

https://ahokoresidence.com/js/jquery-ui.js?1790904085

js ahokoresidence.com collected 2026-10-02 01:22:24 UTC 643,883 bytes, 18,706 lines download raw bytes

vendor: 9,868 bytes, lines 1-262
1/*! jQuery UI - v1.12.1 - 2016-09-14
2* http://jqueryui.com
3* Includes: widget.js, position.js, data.js, disable-selection.js, effect.js, effects/effect-blind.js, effects/effect-bounce.js, effects/effect-clip.js, effects/effect-drop.js, effects/effect-explode.js, effects/effect-fade.js, effects/effect-fold.js, effects/effect-highlight.js, effects/effect-puff.js, effects/effect-pulsate.js, effects/effect-scale.js, effects/effect-shake.js, effects/effect-size.js, effects/effect-slide.js, effects/effect-transfer.js, focusable.js, form-reset-mixin.js, jquery-1-7.js, keycode.js, labels.js, scroll-parent.js, tabbable.js, unique-id.js, widgets/accordion.js, widgets/autocomplete.js, widgets/button.js, widgets/checkboxradio.js, widgets/controlgroup.js, widgets/datepicker.js, widgets/dialog.js, widgets/draggable.js, widgets/droppable.js, widgets/menu.js, widgets/mouse.js, widgets/progressbar.js, widgets/resizable.js, widgets/selectable.js, widgets/selectmenu.js, widgets/slider.js, widgets/sortable.js, widgets/spinner.js, widgets/tabs.js, widgets/tooltip.js
4* Copyright jQuery Foundation and other contributors; Licensed MIT */
5
6(function( factory ) {
7    if ( typeof define === "function" && define.amd ) {
8
9        // AMD. Register as an anonymous module.
10        define([ "jquery" ], factory );
11    } else {
12
13        // Browser globals
14        factory( jQuery );
15    }
16}(function( $ ) {
17
18$.ui = $.ui || {};
19
20var version = $.ui.version = "1.12.1";
21
22
23/*!
24 * jQuery UI Widget 1.12.1
25 * http://jqueryui.com
26 *
27 * Copyright jQuery Foundation and other contributors
28 * Released under the MIT license.
29 * http://jquery.org/license
30 */
31
32//>>label: Widget
33//>>group: Core
34//>>description: Provides a factory for creating stateful widgets with a common API.
35//>>docs: http://api.jqueryui.com/jQuery.widget/
36//>>demos: http://jqueryui.com/widget/
37
38
39
40var widgetUuid = 0;
41var widgetSlice = Array.prototype.slice;
42
43$.cleanData = ( function( orig ) {
44    return function( elems ) {
45        var events, elem, i;
46        for ( i = 0; ( elem = elems[ i ] ) != null; i++ ) {
47            try {
48
49                // Only trigger remove when necessary to save time
50                events = $._data( elem, "events" );
51                if ( events && events.remove ) {
52                    $( elem ).triggerHandler( "remove" );
53                }
54
55            // Http://bugs.jquery.com/ticket/8235
56            } catch ( e ) {}
57        }
58        orig( elems );
59    };
60} )( $.cleanData );
61
62$.widget = function( name, base, prototype ) {
63    var existingConstructor, constructor, basePrototype;
64
65    // ProxiedPrototype allows the provided prototype to remain unmodified
66    // so that it can be used as a mixin for multiple widgets (#8876)
67    var proxiedPrototype = {};
68
69    var namespace = name.split( "." )[ 0 ];
70    name = name.split( "." )[ 1 ];
71    var fullName = namespace + "-" + name;
72
73    if ( !prototype ) {
74        prototype = base;
75        base = $.Widget;
76    }
77
78    if ( $.isArray( prototype ) ) {
79        prototype = $.extend.apply( null, [ {} ].concat( prototype ) );
80    }
81
82    // Create selector for plugin
83    $.expr[ ":" ][ fullName.toLowerCase() ] = function( elem ) {
84        return !!$.data( elem, fullName );
85    };
86
87    $[ namespace ] = $[ namespace ] || {};
88    existingConstructor = $[ namespace ][ name ];
89    constructor = $[ namespace ][ name ] = function( options, element ) {
90
91        // Allow instantiation without "new" keyword
92        if ( !this._createWidget ) {
93            return new constructor( options, element );
94        }
95
96        // Allow instantiation without initializing for simple inheritance
97        // must use "new" keyword (the code above always passes args)
98        if ( arguments.length ) {
99            this._createWidget( options, element );
100        }
101    };
102
103    // Extend with the existing constructor to carry over any static properties
104    $.extend( constructor, existingConstructor, {
105        version: prototype.version,
106
107        // Copy the object used to create the prototype in case we need to
108        // redefine the widget later
109        _proto: $.extend( {}, prototype ),
110
111        // Track widgets that inherit from this widget in case this widget is
112        // redefined after a widget inherits from it
113        _childConstructors: []
114    } );
115
116    basePrototype = new base();
117
118    // We need to make the options hash a property directly on the new instance
119    // otherwise we'll modify the options hash on the prototype that we're
120    // inheriting from
121    basePrototype.options = $.widget.extend( {}, basePrototype.options );
122    $.each( prototype, function( prop, value ) {
123        if ( !$.isFunction( value ) ) {
124            proxiedPrototype[ prop ] = value;
125            return;
126        }
127        proxiedPrototype[ prop ] = ( function() {
128            function _super() {
129                return base.prototype[ prop ].apply( this, arguments );
130            }
131
132            function _superApply( args ) {
133                return base.prototype[ prop ].apply( this, args );
134            }
135
136            return function() {
137                var __super = this._super;
138                var __superApply = this._superApply;
139                var returnValue;
140
141                this._super = _super;
142                this._superApply = _superApply;
143
144                returnValue = value.apply( this, arguments );
145
146                this._super = __super;
147                this._superApply = __superApply;
148
149                return returnValue;
150            };
151        } )();
152    } );
153    constructor.prototype = $.widget.extend( basePrototype, {
154
155        // TODO: remove support for widgetEventPrefix
156        // always use the name + a colon as the prefix, e.g., draggable:start
157        // don't prefix for widgets that aren't DOM-based
158        widgetEventPrefix: existingConstructor ? ( basePrototype.widgetEventPrefix || name ) : name
159    }, proxiedPrototype, {
160        constructor: constructor,
161        namespace: namespace,
162        widgetName: name,
163        widgetFullName: fullName
164    } );
165
166    // If this widget is being redefined then we need to find all widgets that
167    // are inheriting from it and redefine all of them so that they inherit from
168    // the new version of this widget. We're essentially trying to replace one
169    // level in the prototype chain.
170    if ( existingConstructor ) {
171        $.each( existingConstructor._childConstructors, function( i, child ) {
172            var childPrototype = child.prototype;
173
174            // Redefine the child widget using the same prototype that was
175            // originally used, but inherit from the new version of the base
176            $.widget( childPrototype.namespace + "." + childPrototype.widgetName, constructor,
177                child._proto );
178        } );
179
180        // Remove the list of existing child constructors from the old constructor
181        // so the old child constructors can be garbage collected
182        delete existingConstructor._childConstructors;
183    } else {
184        base._childConstructors.push( constructor );
185    }
186
187    $.widget.bridge( name, constructor );
188
189    return constructor;
190};
191
192$.widget.extend = function( target ) {
193    var input = widgetSlice.call( arguments, 1 );
194    var inputIndex = 0;
195    var inputLength = input.length;
196    var key;
197    var value;
198
199    for ( ; inputIndex < inputLength; inputIndex++ ) {
200        for ( key in input[ inputIndex ] ) {
201            value = input[ inputIndex ][ key ];
202            if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {
203
204                // Clone objects
205                if ( $.isPlainObject( value ) ) {
206                    target[ key ] = $.isPlainObject( target[ key ] ) ?
207                        $.widget.extend( {}, target[ key ], value ) :
208
209                        // Don't extend strings, arrays, etc. with objects
210                        $.widget.extend( {}, value );
211
212                // Copy everything else by reference
213                } else {
214                    target[ key ] = value;
215                }
216            }
217        }
218    }
219    return target;
220};
221
222$.widget.bridge = function( name, object ) {
223    var fullName = object.prototype.widgetFullName || name;
224    $.fn[ name ] = function( options ) {
225        var isMethodCall = typeof options === "string";
226        var args = widgetSlice.call( arguments, 1 );
227        var returnValue = this;
228
229        if ( isMethodCall ) {
230
231            // If this is an empty collection, we need to have the instance method
232            // return undefined instead of the jQuery instance
233            if ( !this.length && options === "instance" ) {
234                returnValue = undefined;
235            } else {
236                this.each( function() {
237                    var methodValue;
238                    var instance = $.data( this, fullName );
239
240                    if ( options === "instance" ) {
241                        returnValue = instance;
242                        return false;
243                    }
244
245                    if ( !instance ) {
246                        return $.error( "cannot call methods on " + name +
247                            " prior to initialization; " +
248                            "attempted to call method '" + options + "'" );
249                    }
250
251                    if ( !$.isFunction( instance[ options ] ) || options.charAt( 0 ) === "_" ) {
252                        return $.error( "no such method '" + options + "' for " + name +
253                            " widget instance" );
254                    }
255
256                    methodValue = instance[ options ].apply( instance, args );
257
258                    if ( methodValue !== instance && methodValue !== undefined ) {
259                        returnValue = methodValue && methodValue.jquery ?
260                            returnValue.pushStack( methodValue.get() ) :
261                            methodValue;
262                        return false;
vendor: 5,674 bytes, lines 263-465
263                    }
264                } );
265            }
266        } else {
267
268            // Allow multiple hashes to be passed on init
269            if ( args.length ) {
270                options = $.widget.extend.apply( null, [ options ].concat( args ) );
271            }
272
273            this.each( function() {
274                var instance = $.data( this, fullName );
275                if ( instance ) {
276                    instance.option( options || {} );
277                    if ( instance._init ) {
278                        instance._init();
279                    }
280                } else {
281                    $.data( this, fullName, new object( options, this ) );
282                }
283            } );
284        }
285
286        return returnValue;
287    };
288};
289
290$.Widget = function( /* options, element */ ) {};
291$.Widget._childConstructors = [];
292
293$.Widget.prototype = {
294    widgetName: "widget",
295    widgetEventPrefix: "",
296    defaultElement: "<div>",
297
298    options: {
299        classes: {},
300        disabled: false,
301
302        // Callbacks
303        create: null
304    },
305
306    _createWidget: function( options, element ) {
307        element = $( element || this.defaultElement || this )[ 0 ];
308        this.element = $( element );
309        this.uuid = widgetUuid++;
310        this.eventNamespace = "." + this.widgetName + this.uuid;
311
312        this.bindings = $();
313        this.hoverable = $();
314        this.focusable = $();
315        this.classesElementLookup = {};
316
317        if ( element !== this ) {
318            $.data( element, this.widgetFullName, this );
319            this._on( true, this.element, {
320                remove: function( event ) {
321                    if ( event.target === element ) {
322                        this.destroy();
323                    }
324                }
325            } );
326            this.document = $( element.style ?
327
328                // Element within the document
329                element.ownerDocument :
330
331                // Element is window or document
332                element.document || element );
333            this.window = $( this.document[ 0 ].defaultView || this.document[ 0 ].parentWindow );
334        }
335
336        this.options = $.widget.extend( {},
337            this.options,
338            this._getCreateOptions(),
339            options );
340
341        this._create();
342
343        if ( this.options.disabled ) {
344            this._setOptionDisabled( this.options.disabled );
345        }
346
347        this._trigger( "create", null, this._getCreateEventData() );
348        this._init();
349    },
350
351    _getCreateOptions: function() {
352        return {};
353    },
354
355    _getCreateEventData: $.noop,
356
357    _create: $.noop,
358
359    _init: $.noop,
360
361    destroy: function() {
362        var that = this;
363
364        this._destroy();
365        $.each( this.classesElementLookup, function( key, value ) {
366            that._removeClass( value, key );
367        } );
368
369        // We can probably remove the unbind calls in 2.0
370        // all event bindings should go through this._on()
371        this.element
372            .off( this.eventNamespace )
373            .removeData( this.widgetFullName );
374        this.widget()
375            .off( this.eventNamespace )
376            .removeAttr( "aria-disabled" );
377
378        // Clean up events and states
379        this.bindings.off( this.eventNamespace );
380    },
381
382    _destroy: $.noop,
383
384    widget: function() {
385        return this.element;
386    },
387
388    option: function( key, value ) {
389        var options = key;
390        var parts;
391        var curOption;
392        var i;
393
394        if ( arguments.length === 0 ) {
395
396            // Don't return a reference to the internal hash
397            return $.widget.extend( {}, this.options );
398        }
399
400        if ( typeof key === "string" ) {
401
402            // Handle nested keys, e.g., "foo.bar" => { foo: { bar: ___ } }
403            options = {};
404            parts = key.split( "." );
405            key = parts.shift();
406            if ( parts.length ) {
407                curOption = options[ key ] = $.widget.extend( {}, this.options[ key ] );
408                for ( i = 0; i < parts.length - 1; i++ ) {
409                    curOption[ parts[ i ] ] = curOption[ parts[ i ] ] || {};
410                    curOption = curOption[ parts[ i ] ];
411                }
412                key = parts.pop();
413                if ( arguments.length === 1 ) {
414                    return curOption[ key ] === undefined ? null : curOption[ key ];
415                }
416                curOption[ key ] = value;
417            } else {
418                if ( arguments.length === 1 ) {
419                    return this.options[ key ] === undefined ? null : this.options[ key ];
420                }
421                options[ key ] = value;
422            }
423        }
424
425        this._setOptions( options );
426
427        return this;
428    },
429
430    _setOptions: function( options ) {
431        var key;
432
433        for ( key in options ) {
434            this._setOption( key, options[ key ] );
435        }
436
437        return this;
438    },
439
440    _setOption: function( key, value ) {
441        if ( key === "classes" ) {
442            this._setOptionClasses( value );
443        }
444
445        this.options[ key ] = value;
446
447        if ( key === "disabled" ) {
448            this._setOptionDisabled( value );
449        }
450
451        return this;
452    },
453
454    _setOptionClasses: function( value ) {
455        var classKey, elements, currentElements;
456
457        for ( classKey in value ) {
458            currentElements = this.classesElementLookup[ classKey ];
459            if ( value[ classKey ] === this.options.classes[ classKey ] ||
460                    !currentElements ||
461                    !currentElements.length ) {
462                continue;
463            }
464
465            // We are doing this to create a new jQuery object because the _removeClass() call
vendor: 9,526 bytes, lines 466-729
466            // on the next line is going to destroy the reference to the current elements being
467            // tracked. We need to save a copy of this collection so that we can add the new classes
468            // below.
469            elements = $( currentElements.get() );
470            this._removeClass( currentElements, classKey );
471
472            // We don't use _addClass() here, because that uses this.options.classes
473            // for generating the string of classes. We want to use the value passed in from
474            // _setOption(), this is the new value of the classes option which was passed to
475            // _setOption(). We pass this value directly to _classes().
476            elements.addClass( this._classes( {
477                element: elements,
478                keys: classKey,
479                classes: value,
480                add: true
481            } ) );
482        }
483    },
484
485    _setOptionDisabled: function( value ) {
486        this._toggleClass( this.widget(), this.widgetFullName + "-disabled", null, !!value );
487
488        // If the widget is becoming disabled, then nothing is interactive
489        if ( value ) {
490            this._removeClass( this.hoverable, null, "ui-state-hover" );
491            this._removeClass( this.focusable, null, "ui-state-focus" );
492        }
493    },
494
495    enable: function() {
496        return this._setOptions( { disabled: false } );
497    },
498
499    disable: function() {
500        return this._setOptions( { disabled: true } );
501    },
502
503    _classes: function( options ) {
504        var full = [];
505        var that = this;
506
507        options = $.extend( {
508            element: this.element,
509            classes: this.options.classes || {}
510        }, options );
511
512        function processClassString( classes, checkOption ) {
513            var current, i;
514            for ( i = 0; i < classes.length; i++ ) {
515                current = that.classesElementLookup[ classes[ i ] ] || $();
516                if ( options.add ) {
517                    current = $( $.unique( current.get().concat( options.element.get() ) ) );
518                } else {
519                    current = $( current.not( options.element ).get() );
520                }
521                that.classesElementLookup[ classes[ i ] ] = current;
522                full.push( classes[ i ] );
523                if ( checkOption && options.classes[ classes[ i ] ] ) {
524                    full.push( options.classes[ classes[ i ] ] );
525                }
526            }
527        }
528
529        this._on( options.element, {
530            "remove": "_untrackClassesElement"
531        } );
532
533        if ( options.keys ) {
534            processClassString( options.keys.match( /\S+/g ) || [], true );
535        }
536        if ( options.extra ) {
537            processClassString( options.extra.match( /\S+/g ) || [] );
538        }
539
540        return full.join( " " );
541    },
542
543    _untrackClassesElement: function( event ) {
544        var that = this;
545        $.each( that.classesElementLookup, function( key, value ) {
546            if ( $.inArray( event.target, value ) !== -1 ) {
547                that.classesElementLookup[ key ] = $( value.not( event.target ).get() );
548            }
549        } );
550    },
551
552    _removeClass: function( element, keys, extra ) {
553        return this._toggleClass( element, keys, extra, false );
554    },
555
556    _addClass: function( element, keys, extra ) {
557        return this._toggleClass( element, keys, extra, true );
558    },
559
560    _toggleClass: function( element, keys, extra, add ) {
561        add = ( typeof add === "boolean" ) ? add : extra;
562        var shift = ( typeof element === "string" || element === null ),
563            options = {
564                extra: shift ? keys : extra,
565                keys: shift ? element : keys,
566                element: shift ? this.element : element,
567                add: add
568            };
569        options.element.toggleClass( this._classes( options ), add );
570        return this;
571    },
572
573    _on: function( suppressDisabledCheck, element, handlers ) {
574        var delegateElement;
575        var instance = this;
576
577        // No suppressDisabledCheck flag, shuffle arguments
578        if ( typeof suppressDisabledCheck !== "boolean" ) {
579            handlers = element;
580            element = suppressDisabledCheck;
581            suppressDisabledCheck = false;
582        }
583
584        // No element argument, shuffle and use this.element
585        if ( !handlers ) {
586            handlers = element;
587            element = this.element;
588            delegateElement = this.widget();
589        } else {
590            element = delegateElement = $( element );
591            this.bindings = this.bindings.add( element );
592        }
593
594        $.each( handlers, function( event, handler ) {
595            function handlerProxy() {
596
597                // Allow widgets to customize the disabled handling
598                // - disabled as an array instead of boolean
599                // - disabled class as method for disabling individual parts
600                if ( !suppressDisabledCheck &&
601                        ( instance.options.disabled === true ||
602                        $( this ).hasClass( "ui-state-disabled" ) ) ) {
603                    return;
604                }
605                return ( typeof handler === "string" ? instance[ handler ] : handler )
606                    .apply( instance, arguments );
607            }
608
609            // Copy the guid so direct unbinding works
610            if ( typeof handler !== "string" ) {
611                handlerProxy.guid = handler.guid =
612                    handler.guid || handlerProxy.guid || $.guid++;
613            }
614
615            var match = event.match( /^([\w:-]*)\s*(.*)$/ );
616            var eventName = match[ 1 ] + instance.eventNamespace;
617            var selector = match[ 2 ];
618
619            if ( selector ) {
620                delegateElement.on( eventName, selector, handlerProxy );
621            } else {
622                element.on( eventName, handlerProxy );
623            }
624        } );
625    },
626
627    _off: function( element, eventName ) {
628        eventName = ( eventName || "" ).split( " " ).join( this.eventNamespace + " " ) +
629            this.eventNamespace;
630        element.off( eventName ).off( eventName );
631
632        // Clear the stack to avoid memory leaks (#10056)
633        this.bindings = $( this.bindings.not( element ).get() );
634        this.focusable = $( this.focusable.not( element ).get() );
635        this.hoverable = $( this.hoverable.not( element ).get() );
636    },
637
638    _delay: function( handler, delay ) {
639        function handlerProxy() {
640            return ( typeof handler === "string" ? instance[ handler ] : handler )
641                .apply( instance, arguments );
642        }
643        var instance = this;
644        return setTimeout( handlerProxy, delay || 0 );
645    },
646
647    _hoverable: function( element ) {
648        this.hoverable = this.hoverable.add( element );
649        this._on( element, {
650            mouseenter: function( event ) {
651                this._addClass( $( event.currentTarget ), null, "ui-state-hover" );
652            },
653            mouseleave: function( event ) {
654                this._removeClass( $( event.currentTarget ), null, "ui-state-hover" );
655            }
656        } );
657    },
658
659    _focusable: function( element ) {
660        this.focusable = this.focusable.add( element );
661        this._on( element, {
662            focusin: function( event ) {
663                this._addClass( $( event.currentTarget ), null, "ui-state-focus" );
664            },
665            focusout: function( event ) {
666                this._removeClass( $( event.currentTarget ), null, "ui-state-focus" );
667            }
668        } );
669    },
670
671    _trigger: function( type, event, data ) {
672        var prop, orig;
673        var callback = this.options[ type ];
674
675        data = data || {};
676        event = $.Event( event );
677        event.type = ( type === this.widgetEventPrefix ?
678            type :
679            this.widgetEventPrefix + type ).toLowerCase();
680
681        // The original event may come from any element
682        // so we need to reset the target on the new event
683        event.target = this.element[ 0 ];
684
685        // Copy original event properties over to the new event
686        orig = event.originalEvent;
687        if ( orig ) {
688            for ( prop in orig ) {
689                if ( !( prop in event ) ) {
690                    event[ prop ] = orig[ prop ];
691                }
692            }
693        }
694
695        this.element.trigger( event, data );
696        return !( $.isFunction( callback ) &&
697            callback.apply( this.element[ 0 ], [ event ].concat( data ) ) === false ||
698            event.isDefaultPrevented() );
699    }
700};
701
702$.each( { show: "fadeIn", hide: "fadeOut" }, function( method, defaultEffect ) {
703    $.Widget.prototype[ "_" + method ] = function( element, options, callback ) {
704        if ( typeof options === "string" ) {
705            options = { effect: options };
706        }
707
708        var hasOptions;
709        var effectName = !options ?
710            method :
711            options === true || typeof options === "number" ?
712                defaultEffect :
713                options.effect || defaultEffect;
714
715        options = options || {};
716        if ( typeof options === "number" ) {
717            options = { duration: options };
718        }
719
720        hasOptions = !$.isEmptyObject( options );
721        options.complete = callback;
722
723        if ( options.delay ) {
724            element.delay( options.delay );
725        }
726
727        if ( hasOptions && $.effects && $.effects.effect[ effectName ] ) {
728            element[ method ]( options );
729        } else if ( effectName !== method && element[ effectName ] ) {
vendor: 5,621 bytes, lines 730-909
730            element[ effectName ]( options.duration, options.easing, callback );
731        } else {
732            element.queue( function( next ) {
733                $( this )[ method ]();
734                if ( callback ) {
735                    callback.call( element[ 0 ] );
736                }
737                next();
738            } );
739        }
740    };
741} );
742
743var widget = $.widget;
744
745
746/*!
747 * jQuery UI Position 1.12.1
748 * http://jqueryui.com
749 *
750 * Copyright jQuery Foundation and other contributors
751 * Released under the MIT license.
752 * http://jquery.org/license
753 *
754 * http://api.jqueryui.com/position/
755 */
756
757//>>label: Position
758//>>group: Core
759//>>description: Positions elements relative to other elements.
760//>>docs: http://api.jqueryui.com/position/
761//>>demos: http://jqueryui.com/position/
762
763
764( function() {
765var cachedScrollbarWidth,
766    max = Math.max,
767    abs = Math.abs,
768    rhorizontal = /left|center|right/,
769    rvertical = /top|center|bottom/,
770    roffset = /[\+\-]\d+(\.[\d]+)?%?/,
771    rposition = /^\w+/,
772    rpercent = /%$/,
773    _position = $.fn.position;
774
775function getOffsets( offsets, width, height ) {
776    return [
777        parseFloat( offsets[ 0 ] ) * ( rpercent.test( offsets[ 0 ] ) ? width / 100 : 1 ),
778        parseFloat( offsets[ 1 ] ) * ( rpercent.test( offsets[ 1 ] ) ? height / 100 : 1 )
779    ];
780}
781
782function parseCss( element, property ) {
783    return parseInt( $.css( element, property ), 10 ) || 0;
784}
785
786function getDimensions( elem ) {
787    var raw = elem[ 0 ];
788    if ( raw.nodeType === 9 ) {
789        return {
790            width: elem.width(),
791            height: elem.height(),
792            offset: { top: 0, left: 0 }
793        };
794    }
795    if ( $.isWindow( raw ) ) {
796        return {
797            width: elem.width(),
798            height: elem.height(),
799            offset: { top: elem.scrollTop(), left: elem.scrollLeft() }
800        };
801    }
802    if ( raw.preventDefault ) {
803        return {
804            width: 0,
805            height: 0,
806            offset: { top: raw.pageY, left: raw.pageX }
807        };
808    }
809    return {
810        width: elem.outerWidth(),
811        height: elem.outerHeight(),
812        offset: elem.offset()
813    };
814}
815
816$.position = {
817    scrollbarWidth: function() {
818        if ( cachedScrollbarWidth !== undefined ) {
819            return cachedScrollbarWidth;
820        }
821        var w1, w2,
822            div = $( "<div " +
823                "style='display:block;position:absolute;width:50px;height:50px;overflow:hidden;'>" +
824                "<div style='height:100px;width:auto;'></div></div>" ),
825            innerDiv = div.children()[ 0 ];
826
827        $( "body" ).append( div );
828        w1 = innerDiv.offsetWidth;
829        div.css( "overflow", "scroll" );
830
831        w2 = innerDiv.offsetWidth;
832
833        if ( w1 === w2 ) {
834            w2 = div[ 0 ].clientWidth;
835        }
836
837        div.remove();
838
839        return ( cachedScrollbarWidth = w1 - w2 );
840    },
841    getScrollInfo: function( within ) {
842        var overflowX = within.isWindow || within.isDocument ? "" :
843                within.element.css( "overflow-x" ),
844            overflowY = within.isWindow || within.isDocument ? "" :
845                within.element.css( "overflow-y" ),
846            hasOverflowX = overflowX === "scroll" ||
847                ( overflowX === "auto" && within.width < within.element[ 0 ].scrollWidth ),
848            hasOverflowY = overflowY === "scroll" ||
849                ( overflowY === "auto" && within.height < within.element[ 0 ].scrollHeight );
850        return {
851            width: hasOverflowY ? $.position.scrollbarWidth() : 0,
852            height: hasOverflowX ? $.position.scrollbarWidth() : 0
853        };
854    },
855    getWithinInfo: function( element ) {
856        var withinElement = $( element || window ),
857            isWindow = $.isWindow( withinElement[ 0 ] ),
858            isDocument = !!withinElement[ 0 ] && withinElement[ 0 ].nodeType === 9,
859            hasOffset = !isWindow && !isDocument;
860        return {
861            element: withinElement,
862            isWindow: isWindow,
863            isDocument: isDocument,
864            offset: hasOffset ? $( element ).offset() : { left: 0, top: 0 },
865            scrollLeft: withinElement.scrollLeft(),
866            scrollTop: withinElement.scrollTop(),
867            width: withinElement.outerWidth(),
868            height: withinElement.outerHeight()
869        };
870    }
871};
872
873$.fn.position = function( options ) {
874    if ( !options || !options.of ) {
875        return _position.apply( this, arguments );
876    }
877
878    // Make a copy, we don't want to modify arguments
879    options = $.extend( {}, options );
880
881    var atOffset, targetWidth, targetHeight, targetOffset, basePosition, dimensions,
882        target = $( options.of ),
883        within = $.position.getWithinInfo( options.within ),
884        scrollInfo = $.position.getScrollInfo( within ),
885        collision = ( options.collision || "flip" ).split( " " ),
886        offsets = {};
887
888    dimensions = getDimensions( target );
889    if ( target[ 0 ].preventDefault ) {
890
891        // Force left top to allow flipping
892        options.at = "left top";
893    }
894    targetWidth = dimensions.width;
895    targetHeight = dimensions.height;
896    targetOffset = dimensions.offset;
897
898    // Clone to reuse original targetOffset later
899    basePosition = $.extend( {}, targetOffset );
900
901    // Force my and at to have valid horizontal and vertical positions
902    // if a value is missing or invalid, it will be converted to center
903    $.each( [ "my", "at" ], function() {
904        var pos = ( options[ this ] || "" ).split( " " ),
905            horizontalOffset,
906            verticalOffset;
907
908        if ( pos.length === 1 ) {
909            pos = rhorizontal.test( pos[ 0 ] ) ?
vendor: 13,458 bytes, lines 910-1243
910                pos.concat( [ "center" ] ) :
911                rvertical.test( pos[ 0 ] ) ?
912                    [ "center" ].concat( pos ) :
913                    [ "center", "center" ];
914        }
915        pos[ 0 ] = rhorizontal.test( pos[ 0 ] ) ? pos[ 0 ] : "center";
916        pos[ 1 ] = rvertical.test( pos[ 1 ] ) ? pos[ 1 ] : "center";
917
918        // Calculate offsets
919        horizontalOffset = roffset.exec( pos[ 0 ] );
920        verticalOffset = roffset.exec( pos[ 1 ] );
921        offsets[ this ] = [
922            horizontalOffset ? horizontalOffset[ 0 ] : 0,
923            verticalOffset ? verticalOffset[ 0 ] : 0
924        ];
925
926        // Reduce to just the positions without the offsets
927        options[ this ] = [
928            rposition.exec( pos[ 0 ] )[ 0 ],
929            rposition.exec( pos[ 1 ] )[ 0 ]
930        ];
931    } );
932
933    // Normalize collision option
934    if ( collision.length === 1 ) {
935        collision[ 1 ] = collision[ 0 ];
936    }
937
938    if ( options.at[ 0 ] === "right" ) {
939        basePosition.left += targetWidth;
940    } else if ( options.at[ 0 ] === "center" ) {
941        basePosition.left += targetWidth / 2;
942    }
943
944    if ( options.at[ 1 ] === "bottom" ) {
945        basePosition.top += targetHeight;
946    } else if ( options.at[ 1 ] === "center" ) {
947        basePosition.top += targetHeight / 2;
948    }
949
950    atOffset = getOffsets( offsets.at, targetWidth, targetHeight );
951    basePosition.left += atOffset[ 0 ];
952    basePosition.top += atOffset[ 1 ];
953
954    return this.each( function() {
955        var collisionPosition, using,
956            elem = $( this ),
957            elemWidth = elem.outerWidth(),
958            elemHeight = elem.outerHeight(),
959            marginLeft = parseCss( this, "marginLeft" ),
960            marginTop = parseCss( this, "marginTop" ),
961            collisionWidth = elemWidth + marginLeft + parseCss( this, "marginRight" ) +
962                scrollInfo.width,
963            collisionHeight = elemHeight + marginTop + parseCss( this, "marginBottom" ) +
964                scrollInfo.height,
965            position = $.extend( {}, basePosition ),
966            myOffset = getOffsets( offsets.my, elem.outerWidth(), elem.outerHeight() );
967
968        if ( options.my[ 0 ] === "right" ) {
969            position.left -= elemWidth;
970        } else if ( options.my[ 0 ] === "center" ) {
971            position.left -= elemWidth / 2;
972        }
973
974        if ( options.my[ 1 ] === "bottom" ) {
975            position.top -= elemHeight;
976        } else if ( options.my[ 1 ] === "center" ) {
977            position.top -= elemHeight / 2;
978        }
979
980        position.left += myOffset[ 0 ];
981        position.top += myOffset[ 1 ];
982
983        collisionPosition = {
984            marginLeft: marginLeft,
985            marginTop: marginTop
986        };
987
988        $.each( [ "left", "top" ], function( i, dir ) {
989            if ( $.ui.position[ collision[ i ] ] ) {
990                $.ui.position[ collision[ i ] ][ dir ]( position, {
991                    targetWidth: targetWidth,
992                    targetHeight: targetHeight,
993                    elemWidth: elemWidth,
994                    elemHeight: elemHeight,
995                    collisionPosition: collisionPosition,
996                    collisionWidth: collisionWidth,
997                    collisionHeight: collisionHeight,
998                    offset: [ atOffset[ 0 ] + myOffset[ 0 ], atOffset [ 1 ] + myOffset[ 1 ] ],
999                    my: options.my,
1000                    at: options.at,
1001                    within: within,
1002                    elem: elem
1003                } );
1004            }
1005        } );
1006
1007        if ( options.using ) {
1008
1009            // Adds feedback as second argument to using callback, if present
1010            using = function( props ) {
1011                var left = targetOffset.left - position.left,
1012                    right = left + targetWidth - elemWidth,
1013                    top = targetOffset.top - position.top,
1014                    bottom = top + targetHeight - elemHeight,
1015                    feedback = {
1016                        target: {
1017                            element: target,
1018                            left: targetOffset.left,
1019                            top: targetOffset.top,
1020                            width: targetWidth,
1021                            height: targetHeight
1022                        },
1023                        element: {
1024                            element: elem,
1025                            left: position.left,
1026                            top: position.top,
1027                            width: elemWidth,
1028                            height: elemHeight
1029                        },
1030                        horizontal: right < 0 ? "left" : left > 0 ? "right" : "center",
1031                        vertical: bottom < 0 ? "top" : top > 0 ? "bottom" : "middle"
1032                    };
1033                if ( targetWidth < elemWidth && abs( left + right ) < targetWidth ) {
1034                    feedback.horizontal = "center";
1035                }
1036                if ( targetHeight < elemHeight && abs( top + bottom ) < targetHeight ) {
1037                    feedback.vertical = "middle";
1038                }
1039                if ( max( abs( left ), abs( right ) ) > max( abs( top ), abs( bottom ) ) ) {
1040                    feedback.important = "horizontal";
1041                } else {
1042                    feedback.important = "vertical";
1043                }
1044                options.using.call( this, props, feedback );
1045            };
1046        }
1047
1048        elem.offset( $.extend( position, { using: using } ) );
1049    } );
1050};
1051
1052$.ui.position = {
1053    fit: {
1054        left: function( position, data ) {
1055            var within = data.within,
1056                withinOffset = within.isWindow ? within.scrollLeft : within.offset.left,
1057                outerWidth = within.width,
1058                collisionPosLeft = position.left - data.collisionPosition.marginLeft,
1059                overLeft = withinOffset - collisionPosLeft,
1060                overRight = collisionPosLeft + data.collisionWidth - outerWidth - withinOffset,
1061                newOverRight;
1062
1063            // Element is wider than within
1064            if ( data.collisionWidth > outerWidth ) {
1065
1066                // Element is initially over the left side of within
1067                if ( overLeft > 0 && overRight <= 0 ) {
1068                    newOverRight = position.left + overLeft + data.collisionWidth - outerWidth -
1069                        withinOffset;
1070                    position.left += overLeft - newOverRight;
1071
1072                // Element is initially over right side of within
1073                } else if ( overRight > 0 && overLeft <= 0 ) {
1074                    position.left = withinOffset;
1075
1076                // Element is initially over both left and right sides of within
1077                } else {
1078                    if ( overLeft > overRight ) {
1079                        position.left = withinOffset + outerWidth - data.collisionWidth;
1080                    } else {
1081                        position.left = withinOffset;
1082                    }
1083                }
1084
1085            // Too far left -> align with left edge
1086            } else if ( overLeft > 0 ) {
1087                position.left += overLeft;
1088
1089            // Too far right -> align with right edge
1090            } else if ( overRight > 0 ) {
1091                position.left -= overRight;
1092
1093            // Adjust based on position and margin
1094            } else {
1095                position.left = max( position.left - collisionPosLeft, position.left );
1096            }
1097        },
1098        top: function( position, data ) {
1099            var within = data.within,
1100                withinOffset = within.isWindow ? within.scrollTop : within.offset.top,
1101                outerHeight = data.within.height,
1102                collisionPosTop = position.top - data.collisionPosition.marginTop,
1103                overTop = withinOffset - collisionPosTop,
1104                overBottom = collisionPosTop + data.collisionHeight - outerHeight - withinOffset,
1105                newOverBottom;
1106
1107            // Element is taller than within
1108            if ( data.collisionHeight > outerHeight ) {
1109
1110                // Element is initially over the top of within
1111                if ( overTop > 0 && overBottom <= 0 ) {
1112                    newOverBottom = position.top + overTop + data.collisionHeight - outerHeight -
1113                        withinOffset;
1114                    position.top += overTop - newOverBottom;
1115
1116                // Element is initially over bottom of within
1117                } else if ( overBottom > 0 && overTop <= 0 ) {
1118                    position.top = withinOffset;
1119
1120                // Element is initially over both top and bottom of within
1121                } else {
1122                    if ( overTop > overBottom ) {
1123                        position.top = withinOffset + outerHeight - data.collisionHeight;
1124                    } else {
1125                        position.top = withinOffset;
1126                    }
1127                }
1128
1129            // Too far up -> align with top
1130            } else if ( overTop > 0 ) {
1131                position.top += overTop;
1132
1133            // Too far down -> align with bottom edge
1134            } else if ( overBottom > 0 ) {
1135                position.top -= overBottom;
1136
1137            // Adjust based on position and margin
1138            } else {
1139                position.top = max( position.top - collisionPosTop, position.top );
1140            }
1141        }
1142    },
1143    flip: {
1144        left: function( position, data ) {
1145            var within = data.within,
1146                withinOffset = within.offset.left + within.scrollLeft,
1147                outerWidth = within.width,
1148                offsetLeft = within.isWindow ? within.scrollLeft : within.offset.left,
1149                collisionPosLeft = position.left - data.collisionPosition.marginLeft,
1150                overLeft = collisionPosLeft - offsetLeft,
1151                overRight = collisionPosLeft + data.collisionWidth - outerWidth - offsetLeft,
1152                myOffset = data.my[ 0 ] === "left" ?
1153                    -data.elemWidth :
1154                    data.my[ 0 ] === "right" ?
1155                        data.elemWidth :
1156                        0,
1157                atOffset = data.at[ 0 ] === "left" ?
1158                    data.targetWidth :
1159                    data.at[ 0 ] === "right" ?
1160                        -data.targetWidth :
1161                        0,
1162                offset = -2 * data.offset[ 0 ],
1163                newOverRight,
1164                newOverLeft;
1165
1166            if ( overLeft < 0 ) {
1167                newOverRight = position.left + myOffset + atOffset + offset + data.collisionWidth -
1168                    outerWidth - withinOffset;
1169                if ( newOverRight < 0 || newOverRight < abs( overLeft ) ) {
1170                    position.left += myOffset + atOffset + offset;
1171                }
1172            } else if ( overRight > 0 ) {
1173                newOverLeft = position.left - data.collisionPosition.marginLeft + myOffset +
1174                    atOffset + offset - offsetLeft;
1175                if ( newOverLeft > 0 || abs( newOverLeft ) < overRight ) {
1176                    position.left += myOffset + atOffset + offset;
1177                }
1178            }
1179        },
1180        top: function( position, data ) {
1181            var within = data.within,
1182                withinOffset = within.offset.top + within.scrollTop,
1183                outerHeight = within.height,
1184                offsetTop = within.isWindow ? within.scrollTop : within.offset.top,
1185                collisionPosTop = position.top - data.collisionPosition.marginTop,
1186                overTop = collisionPosTop - offsetTop,
1187                overBottom = collisionPosTop + data.collisionHeight - outerHeight - offsetTop,
1188                top = data.my[ 1 ] === "top",
1189                myOffset = top ?
1190                    -data.elemHeight :
1191                    data.my[ 1 ] === "bottom" ?
1192                        data.elemHeight :
1193                        0,
1194                atOffset = data.at[ 1 ] === "top" ?
1195                    data.targetHeight :
1196                    data.at[ 1 ] === "bottom" ?
1197                        -data.targetHeight :
1198                        0,
1199                offset = -2 * data.offset[ 1 ],
1200                newOverTop,
1201                newOverBottom;
1202            if ( overTop < 0 ) {
1203                newOverBottom = position.top + myOffset + atOffset + offset + data.collisionHeight -
1204                    outerHeight - withinOffset;
1205                if ( newOverBottom < 0 || newOverBottom < abs( overTop ) ) {
1206                    position.top += myOffset + atOffset + offset;
1207                }
1208            } else if ( overBottom > 0 ) {
1209                newOverTop = position.top - data.collisionPosition.marginTop + myOffset + atOffset +
1210                    offset - offsetTop;
1211                if ( newOverTop > 0 || abs( newOverTop ) < overBottom ) {
1212                    position.top += myOffset + atOffset + offset;
1213                }
1214            }
1215        }
1216    },
1217    flipfit: {
1218        left: function() {
1219            $.ui.position.flip.left.apply( this, arguments );
1220            $.ui.position.fit.left.apply( this, arguments );
1221        },
1222        top: function() {
1223            $.ui.position.flip.top.apply( this, arguments );
1224            $.ui.position.fit.top.apply( this, arguments );
1225        }
1226    }
1227};
1228
1229} )();
1230
1231var position = $.ui.position;
1232
1233
1234/*!
1235 * jQuery UI :data 1.12.1
1236 * http://jqueryui.com
1237 *
1238 * Copyright jQuery Foundation and other contributors
1239 * Released under the MIT license.
1240 * http://jquery.org/license
1241 */
1242
1243//>>label: :data Selector
vendor: 5,174 bytes, lines 1244-1407
1244//>>group: Core
1245//>>description: Selects elements which have data stored under the specified key.
1246//>>docs: http://api.jqueryui.com/data-selector/
1247
1248
1249var data = $.extend( $.expr[ ":" ], {
1250    data: $.expr.createPseudo ?
1251        $.expr.createPseudo( function( dataName ) {
1252            return function( elem ) {
1253                return !!$.data( elem, dataName );
1254            };
1255        } ) :
1256
1257        // Support: jQuery <1.8
1258        function( elem, i, match ) {
1259            return !!$.data( elem, match[ 3 ] );
1260        }
1261} );
1262
1263/*!
1264 * jQuery UI Disable Selection 1.12.1
1265 * http://jqueryui.com
1266 *
1267 * Copyright jQuery Foundation and other contributors
1268 * Released under the MIT license.
1269 * http://jquery.org/license
1270 */
1271
1272//>>label: disableSelection
1273//>>group: Core
1274//>>description: Disable selection of text content within the set of matched elements.
1275//>>docs: http://api.jqueryui.com/disableSelection/
1276
1277// This file is deprecated
1278
1279
1280var disableSelection = $.fn.extend( {
1281    disableSelection: ( function() {
1282        var eventType = "onselectstart" in document.createElement( "div" ) ?
1283            "selectstart" :
1284            "mousedown";
1285
1286        return function() {
1287            return this.on( eventType + ".ui-disableSelection", function( event ) {
1288                event.preventDefault();
1289            } );
1290        };
1291    } )(),
1292
1293    enableSelection: function() {
1294        return this.off( ".ui-disableSelection" );
1295    }
1296} );
1297
1298
1299/*!
1300 * jQuery UI Effects 1.12.1
1301 * http://jqueryui.com
1302 *
1303 * Copyright jQuery Foundation and other contributors
1304 * Released under the MIT license.
1305 * http://jquery.org/license
1306 */
1307
1308//>>label: Effects Core
1309//>>group: Effects
1310// jscs:disable maximumLineLength
1311//>>description: Extends the internal jQuery effects. Includes morphing and easing. Required by all other effects.
1312// jscs:enable maximumLineLength
1313//>>docs: http://api.jqueryui.com/category/effects-core/
1314//>>demos: http://jqueryui.com/effect/
1315
1316
1317
1318var dataSpace = "ui-effects-",
1319    dataSpaceStyle = "ui-effects-style",
1320    dataSpaceAnimated = "ui-effects-animated",
1321
1322    // Create a local jQuery because jQuery Color relies on it and the
1323    // global may not exist with AMD and a custom build (#10199)
1324    jQuery = $;
1325
1326$.effects = {
1327    effect: {}
1328};
1329
1330/*!
1331 * jQuery Color Animations v2.1.2
1332 * https://github.com/jquery/jquery-color
1333 *
1334 * Copyright 2014 jQuery Foundation and other contributors
1335 * Released under the MIT license.
1336 * http://jquery.org/license
1337 *
1338 * Date: Wed Jan 16 08:47:09 2013 -0600
1339 */
1340( function( jQuery, undefined ) {
1341
1342    var stepHooks = "backgroundColor borderBottomColor borderLeftColor borderRightColor " +
1343        "borderTopColor color columnRuleColor outlineColor textDecorationColor textEmphasisColor",
1344
1345    // Plusequals test for += 100 -= 100
1346    rplusequals = /^([\-+])=\s*(\d+\.?\d*)/,
1347
1348    // A set of RE's that can match strings and generate color tuples.
1349    stringParsers = [ {
1350            re: /rgba?\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
1351            parse: function( execResult ) {
1352                return [
1353                    execResult[ 1 ],
1354                    execResult[ 2 ],
1355                    execResult[ 3 ],
1356                    execResult[ 4 ]
1357                ];
1358            }
1359        }, {
1360            re: /rgba?\(\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
1361            parse: function( execResult ) {
1362                return [
1363                    execResult[ 1 ] * 2.55,
1364                    execResult[ 2 ] * 2.55,
1365                    execResult[ 3 ] * 2.55,
1366                    execResult[ 4 ]
1367                ];
1368            }
1369        }, {
1370
1371            // This regex ignores A-F because it's compared against an already lowercased string
1372            re: /#([a-f0-9]{2})([a-f0-9]{2})([a-f0-9]{2})/,
1373            parse: function( execResult ) {
1374                return [
1375                    parseInt( execResult[ 1 ], 16 ),
1376                    parseInt( execResult[ 2 ], 16 ),
1377                    parseInt( execResult[ 3 ], 16 )
1378                ];
1379            }
1380        }, {
1381
1382            // This regex ignores A-F because it's compared against an already lowercased string
1383            re: /#([a-f0-9])([a-f0-9])([a-f0-9])/,
1384            parse: function( execResult ) {
1385                return [
1386                    parseInt( execResult[ 1 ] + execResult[ 1 ], 16 ),
1387                    parseInt( execResult[ 2 ] + execResult[ 2 ], 16 ),
1388                    parseInt( execResult[ 3 ] + execResult[ 3 ], 16 )
1389                ];
1390            }
1391        }, {
1392            re: /hsla?\(\s*(\d+(?:\.\d+)?)\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
1393            space: "hsla",
1394            parse: function( execResult ) {
1395                return [
1396                    execResult[ 1 ],
1397                    execResult[ 2 ] / 100,
1398                    execResult[ 3 ] / 100,
1399                    execResult[ 4 ]
1400                ];
1401            }
1402        } ],
1403
1404    // JQuery.Color( )
1405    color = jQuery.Color = function( color, green, blue, alpha ) {
1406        return new jQuery.Color.fn.parse( color, green, blue, alpha );
1407    },
vendor: 19,559 bytes, lines 1408-2052
1408    spaces = {
1409        rgba: {
1410            props: {
1411                red: {
1412                    idx: 0,
1413                    type: "byte"
1414                },
1415                green: {
1416                    idx: 1,
1417                    type: "byte"
1418                },
1419                blue: {
1420                    idx: 2,
1421                    type: "byte"
1422                }
1423            }
1424        },
1425
1426        hsla: {
1427            props: {
1428                hue: {
1429                    idx: 0,
1430                    type: "degrees"
1431                },
1432                saturation: {
1433                    idx: 1,
1434                    type: "percent"
1435                },
1436                lightness: {
1437                    idx: 2,
1438                    type: "percent"
1439                }
1440            }
1441        }
1442    },
1443    propTypes = {
1444        "byte": {
1445            floor: true,
1446            max: 255
1447        },
1448        "percent": {
1449            max: 1
1450        },
1451        "degrees": {
1452            mod: 360,
1453            floor: true
1454        }
1455    },
1456    support = color.support = {},
1457
1458    // Element for support tests
1459    supportElem = jQuery( "<p>" )[ 0 ],
1460
1461    // Colors = jQuery.Color.names
1462    colors,
1463
1464    // Local aliases of functions called often
1465    each = jQuery.each;
1466
1467// Determine rgba support immediately
1468supportElem.style.cssText = "background-color:rgba(1,1,1,.5)";
1469support.rgba = supportElem.style.backgroundColor.indexOf( "rgba" ) > -1;
1470
1471// Define cache name and alpha properties
1472// for rgba and hsla spaces
1473each( spaces, function( spaceName, space ) {
1474    space.cache = "_" + spaceName;
1475    space.props.alpha = {
1476        idx: 3,
1477        type: "percent",
1478        def: 1
1479    };
1480} );
1481
1482function clamp( value, prop, allowEmpty ) {
1483    var type = propTypes[ prop.type ] || {};
1484
1485    if ( value == null ) {
1486        return ( allowEmpty || !prop.def ) ? null : prop.def;
1487    }
1488
1489    // ~~ is an short way of doing floor for positive numbers
1490    value = type.floor ? ~~value : parseFloat( value );
1491
1492    // IE will pass in empty strings as value for alpha,
1493    // which will hit this case
1494    if ( isNaN( value ) ) {
1495        return prop.def;
1496    }
1497
1498    if ( type.mod ) {
1499
1500        // We add mod before modding to make sure that negatives values
1501        // get converted properly: -10 -> 350
1502        return ( value + type.mod ) % type.mod;
1503    }
1504
1505    // For now all property types without mod have min and max
1506    return 0 > value ? 0 : type.max < value ? type.max : value;
1507}
1508
1509function stringParse( string ) {
1510    var inst = color(),
1511        rgba = inst._rgba = [];
1512
1513    string = string.toLowerCase();
1514
1515    each( stringParsers, function( i, parser ) {
1516        var parsed,
1517            match = parser.re.exec( string ),
1518            values = match && parser.parse( match ),
1519            spaceName = parser.space || "rgba";
1520
1521        if ( values ) {
1522            parsed = inst[ spaceName ]( values );
1523
1524            // If this was an rgba parse the assignment might happen twice
1525            // oh well....
1526            inst[ spaces[ spaceName ].cache ] = parsed[ spaces[ spaceName ].cache ];
1527            rgba = inst._rgba = parsed._rgba;
1528
1529            // Exit each( stringParsers ) here because we matched
1530            return false;
1531        }
1532    } );
1533
1534    // Found a stringParser that handled it
1535    if ( rgba.length ) {
1536
1537        // If this came from a parsed string, force "transparent" when alpha is 0
1538        // chrome, (and maybe others) return "transparent" as rgba(0,0,0,0)
1539        if ( rgba.join() === "0,0,0,0" ) {
1540            jQuery.extend( rgba, colors.transparent );
1541        }
1542        return inst;
1543    }
1544
1545    // Named colors
1546    return colors[ string ];
1547}
1548
1549color.fn = jQuery.extend( color.prototype, {
1550    parse: function( red, green, blue, alpha ) {
1551        if ( red === undefined ) {
1552            this._rgba = [ null, null, null, null ];
1553            return this;
1554        }
1555        if ( red.jquery || red.nodeType ) {
1556            red = jQuery( red ).css( green );
1557            green = undefined;
1558        }
1559
1560        var inst = this,
1561            type = jQuery.type( red ),
1562            rgba = this._rgba = [];
1563
1564        // More than 1 argument specified - assume ( red, green, blue, alpha )
1565        if ( green !== undefined ) {
1566            red = [ red, green, blue, alpha ];
1567            type = "array";
1568        }
1569
1570        if ( type === "string" ) {
1571            return this.parse( stringParse( red ) || colors._default );
1572        }
1573
1574        if ( type === "array" ) {
1575            each( spaces.rgba.props, function( key, prop ) {
1576                rgba[ prop.idx ] = clamp( red[ prop.idx ], prop );
1577            } );
1578            return this;
1579        }
1580
1581        if ( type === "object" ) {
1582            if ( red instanceof color ) {
1583                each( spaces, function( spaceName, space ) {
1584                    if ( red[ space.cache ] ) {
1585                        inst[ space.cache ] = red[ space.cache ].slice();
1586                    }
1587                } );
1588            } else {
1589                each( spaces, function( spaceName, space ) {
1590                    var cache = space.cache;
1591                    each( space.props, function( key, prop ) {
1592
1593                        // If the cache doesn't exist, and we know how to convert
1594                        if ( !inst[ cache ] && space.to ) {
1595
1596                            // If the value was null, we don't need to copy it
1597                            // if the key was alpha, we don't need to copy it either
1598                            if ( key === "alpha" || red[ key ] == null ) {
1599                                return;
1600                            }
1601                            inst[ cache ] = space.to( inst._rgba );
1602                        }
1603
1604                        // This is the only case where we allow nulls for ALL properties.
1605                        // call clamp with alwaysAllowEmpty
1606                        inst[ cache ][ prop.idx ] = clamp( red[ key ], prop, true );
1607                    } );
1608
1609                    // Everything defined but alpha?
1610                    if ( inst[ cache ] &&
1611                            jQuery.inArray( null, inst[ cache ].slice( 0, 3 ) ) < 0 ) {
1612
1613                        // Use the default of 1
1614                        inst[ cache ][ 3 ] = 1;
1615                        if ( space.from ) {
1616                            inst._rgba = space.from( inst[ cache ] );
1617                        }
1618                    }
1619                } );
1620            }
1621            return this;
1622        }
1623    },
1624    is: function( compare ) {
1625        var is = color( compare ),
1626            same = true,
1627            inst = this;
1628
1629        each( spaces, function( _, space ) {
1630            var localCache,
1631                isCache = is[ space.cache ];
1632            if ( isCache ) {
1633                localCache = inst[ space.cache ] || space.to && space.to( inst._rgba ) || [];
1634                each( space.props, function( _, prop ) {
1635                    if ( isCache[ prop.idx ] != null ) {
1636                        same = ( isCache[ prop.idx ] === localCache[ prop.idx ] );
1637                        return same;
1638                    }
1639                } );
1640            }
1641            return same;
1642        } );
1643        return same;
1644    },
1645    _space: function() {
1646        var used = [],
1647            inst = this;
1648        each( spaces, function( spaceName, space ) {
1649            if ( inst[ space.cache ] ) {
1650                used.push( spaceName );
1651            }
1652        } );
1653        return used.pop();
1654    },
1655    transition: function( other, distance ) {
1656        var end = color( other ),
1657            spaceName = end._space(),
1658            space = spaces[ spaceName ],
1659            startColor = this.alpha() === 0 ? color( "transparent" ) : this,
1660            start = startColor[ space.cache ] || space.to( startColor._rgba ),
1661            result = start.slice();
1662
1663        end = end[ space.cache ];
1664        each( space.props, function( key, prop ) {
1665            var index = prop.idx,
1666                startValue = start[ index ],
1667                endValue = end[ index ],
1668                type = propTypes[ prop.type ] || {};
1669
1670            // If null, don't override start value
1671            if ( endValue === null ) {
1672                return;
1673            }
1674
1675            // If null - use end
1676            if ( startValue === null ) {
1677                result[ index ] = endValue;
1678            } else {
1679                if ( type.mod ) {
1680                    if ( endValue - startValue > type.mod / 2 ) {
1681                        startValue += type.mod;
1682                    } else if ( startValue - endValue > type.mod / 2 ) {
1683                        startValue -= type.mod;
1684                    }
1685                }
1686                result[ index ] = clamp( ( endValue - startValue ) * distance + startValue, prop );
1687            }
1688        } );
1689        return this[ spaceName ]( result );
1690    },
1691    blend: function( opaque ) {
1692
1693        // If we are already opaque - return ourself
1694        if ( this._rgba[ 3 ] === 1 ) {
1695            return this;
1696        }
1697
1698        var rgb = this._rgba.slice(),
1699            a = rgb.pop(),
1700            blend = color( opaque )._rgba;
1701
1702        return color( jQuery.map( rgb, function( v, i ) {
1703            return ( 1 - a ) * blend[ i ] + a * v;
1704        } ) );
1705    },
1706    toRgbaString: function() {
1707        var prefix = "rgba(",
1708            rgba = jQuery.map( this._rgba, function( v, i ) {
1709                return v == null ? ( i > 2 ? 1 : 0 ) : v;
1710            } );
1711
1712        if ( rgba[ 3 ] === 1 ) {
1713            rgba.pop();
1714            prefix = "rgb(";
1715        }
1716
1717        return prefix + rgba.join() + ")";
1718    },
1719    toHslaString: function() {
1720        var prefix = "hsla(",
1721            hsla = jQuery.map( this.hsla(), function( v, i ) {
1722                if ( v == null ) {
1723                    v = i > 2 ? 1 : 0;
1724                }
1725
1726                // Catch 1 and 2
1727                if ( i && i < 3 ) {
1728                    v = Math.round( v * 100 ) + "%";
1729                }
1730                return v;
1731            } );
1732
1733        if ( hsla[ 3 ] === 1 ) {
1734            hsla.pop();
1735            prefix = "hsl(";
1736        }
1737        return prefix + hsla.join() + ")";
1738    },
1739    toHexString: function( includeAlpha ) {
1740        var rgba = this._rgba.slice(),
1741            alpha = rgba.pop();
1742
1743        if ( includeAlpha ) {
1744            rgba.push( ~~( alpha * 255 ) );
1745        }
1746
1747        return "#" + jQuery.map( rgba, function( v ) {
1748
1749            // Default to 0 when nulls exist
1750            v = ( v || 0 ).toString( 16 );
1751            return v.length === 1 ? "0" + v : v;
1752        } ).join( "" );
1753    },
1754    toString: function() {
1755        return this._rgba[ 3 ] === 0 ? "transparent" : this.toRgbaString();
1756    }
1757} );
1758color.fn.parse.prototype = color.fn;
1759
1760// Hsla conversions adapted from:
1761// https://code.google.com/p/maashaack/source/browse/packages/graphics/trunk/src/graphics/colors/HUE2RGB.as?r=5021
1762
1763function hue2rgb( p, q, h ) {
1764    h = ( h + 1 ) % 1;
1765    if ( h * 6 < 1 ) {
1766        return p + ( q - p ) * h * 6;
1767    }
1768    if ( h * 2 < 1 ) {
1769        return q;
1770    }
1771    if ( h * 3 < 2 ) {
1772        return p + ( q - p ) * ( ( 2 / 3 ) - h ) * 6;
1773    }
1774    return p;
1775}
1776
1777spaces.hsla.to = function( rgba ) {
1778    if ( rgba[ 0 ] == null || rgba[ 1 ] == null || rgba[ 2 ] == null ) {
1779        return [ null, null, null, rgba[ 3 ] ];
1780    }
1781    var r = rgba[ 0 ] / 255,
1782        g = rgba[ 1 ] / 255,
1783        b = rgba[ 2 ] / 255,
1784        a = rgba[ 3 ],
1785        max = Math.max( r, g, b ),
1786        min = Math.min( r, g, b ),
1787        diff = max - min,
1788        add = max + min,
1789        l = add * 0.5,
1790        h, s;
1791
1792    if ( min === max ) {
1793        h = 0;
1794    } else if ( r === max ) {
1795        h = ( 60 * ( g - b ) / diff ) + 360;
1796    } else if ( g === max ) {
1797        h = ( 60 * ( b - r ) / diff ) + 120;
1798    } else {
1799        h = ( 60 * ( r - g ) / diff ) + 240;
1800    }
1801
1802    // Chroma (diff) == 0 means greyscale which, by definition, saturation = 0%
1803    // otherwise, saturation is based on the ratio of chroma (diff) to lightness (add)
1804    if ( diff === 0 ) {
1805        s = 0;
1806    } else if ( l <= 0.5 ) {
1807        s = diff / add;
1808    } else {
1809        s = diff / ( 2 - add );
1810    }
1811    return [ Math.round( h ) % 360, s, l, a == null ? 1 : a ];
1812};
1813
1814spaces.hsla.from = function( hsla ) {
1815    if ( hsla[ 0 ] == null || hsla[ 1 ] == null || hsla[ 2 ] == null ) {
1816        return [ null, null, null, hsla[ 3 ] ];
1817    }
1818    var h = hsla[ 0 ] / 360,
1819        s = hsla[ 1 ],
1820        l = hsla[ 2 ],
1821        a = hsla[ 3 ],
1822        q = l <= 0.5 ? l * ( 1 + s ) : l + s - l * s,
1823        p = 2 * l - q;
1824
1825    return [
1826        Math.round( hue2rgb( p, q, h + ( 1 / 3 ) ) * 255 ),
1827        Math.round( hue2rgb( p, q, h ) * 255 ),
1828        Math.round( hue2rgb( p, q, h - ( 1 / 3 ) ) * 255 ),
1829        a
1830    ];
1831};
1832
1833each( spaces, function( spaceName, space ) {
1834    var props = space.props,
1835        cache = space.cache,
1836        to = space.to,
1837        from = space.from;
1838
1839    // Makes rgba() and hsla()
1840    color.fn[ spaceName ] = function( value ) {
1841
1842        // Generate a cache for this space if it doesn't exist
1843        if ( to && !this[ cache ] ) {
1844            this[ cache ] = to( this._rgba );
1845        }
1846        if ( value === undefined ) {
1847            return this[ cache ].slice();
1848        }
1849
1850        var ret,
1851            type = jQuery.type( value ),
1852            arr = ( type === "array" || type === "object" ) ? value : arguments,
1853            local = this[ cache ].slice();
1854
1855        each( props, function( key, prop ) {
1856            var val = arr[ type === "object" ? key : prop.idx ];
1857            if ( val == null ) {
1858                val = local[ prop.idx ];
1859            }
1860            local[ prop.idx ] = clamp( val, prop );
1861        } );
1862
1863        if ( from ) {
1864            ret = color( from( local ) );
1865            ret[ cache ] = local;
1866            return ret;
1867        } else {
1868            return color( local );
1869        }
1870    };
1871
1872    // Makes red() green() blue() alpha() hue() saturation() lightness()
1873    each( props, function( key, prop ) {
1874
1875        // Alpha is included in more than one space
1876        if ( color.fn[ key ] ) {
1877            return;
1878        }
1879        color.fn[ key ] = function( value ) {
1880            var vtype = jQuery.type( value ),
1881                fn = ( key === "alpha" ? ( this._hsla ? "hsla" : "rgba" ) : spaceName ),
1882                local = this[ fn ](),
1883                cur = local[ prop.idx ],
1884                match;
1885
1886            if ( vtype === "undefined" ) {
1887                return cur;
1888            }
1889
1890            if ( vtype === "function" ) {
1891                value = value.call( this, cur );
1892                vtype = jQuery.type( value );
1893            }
1894            if ( value == null && prop.empty ) {
1895                return this;
1896            }
1897            if ( vtype === "string" ) {
1898                match = rplusequals.exec( value );
1899                if ( match ) {
1900                    value = cur + parseFloat( match[ 2 ] ) * ( match[ 1 ] === "+" ? 1 : -1 );
1901                }
1902            }
1903            local[ prop.idx ] = value;
1904            return this[ fn ]( local );
1905        };
1906    } );
1907} );
1908
1909// Add cssHook and .fx.step function for each named hook.
1910// accept a space separated string of properties
1911color.hook = function( hook ) {
1912    var hooks = hook.split( " " );
1913    each( hooks, function( i, hook ) {
1914        jQuery.cssHooks[ hook ] = {
1915            set: function( elem, value ) {
1916                var parsed, curElem,
1917                    backgroundColor = "";
1918
1919                if ( value !== "transparent" && ( jQuery.type( value ) !== "string" ||
1920                        ( parsed = stringParse( value ) ) ) ) {
1921                    value = color( parsed || value );
1922                    if ( !support.rgba && value._rgba[ 3 ] !== 1 ) {
1923                        curElem = hook === "backgroundColor" ? elem.parentNode : elem;
1924                        while (
1925                            ( backgroundColor === "" || backgroundColor === "transparent" ) &&
1926                            curElem && curElem.style
1927                        ) {
1928                            try {
1929                                backgroundColor = jQuery.css( curElem, "backgroundColor" );
1930                                curElem = curElem.parentNode;
1931                            } catch ( e ) {
1932                            }
1933                        }
1934
1935                        value = value.blend( backgroundColor && backgroundColor !== "transparent" ?
1936                            backgroundColor :
1937                            "_default" );
1938                    }
1939
1940                    value = value.toRgbaString();
1941                }
1942                try {
1943                    elem.style[ hook ] = value;
1944                } catch ( e ) {
1945
1946                    // Wrapped to prevent IE from throwing errors on "invalid" values like
1947                    // 'auto' or 'inherit'
1948                }
1949            }
1950        };
1951        jQuery.fx.step[ hook ] = function( fx ) {
1952            if ( !fx.colorInit ) {
1953                fx.start = color( fx.elem, hook );
1954                fx.end = color( fx.end );
1955                fx.colorInit = true;
1956            }
1957            jQuery.cssHooks[ hook ].set( fx.elem, fx.start.transition( fx.end, fx.pos ) );
1958        };
1959    } );
1960
1961};
1962
1963color.hook( stepHooks );
1964
1965jQuery.cssHooks.borderColor = {
1966    expand: function( value ) {
1967        var expanded = {};
1968
1969        each( [ "Top", "Right", "Bottom", "Left" ], function( i, part ) {
1970            expanded[ "border" + part + "Color" ] = value;
1971        } );
1972        return expanded;
1973    }
1974};
1975
1976// Basic color names only.
1977// Usage of any of the other color names requires adding yourself or including
1978// jquery.color.svg-names.js.
1979colors = jQuery.Color.names = {
1980
1981    // 4.1. Basic color keywords
1982    aqua: "#00ffff",
1983    black: "#000000",
1984    blue: "#0000ff",
1985    fuchsia: "#ff00ff",
1986    gray: "#808080",
1987    green: "#008000",
1988    lime: "#00ff00",
1989    maroon: "#800000",
1990    navy: "#000080",
1991    olive: "#808000",
1992    purple: "#800080",
1993    red: " #65b544",
1994    silver: "#c0c0c0",
1995    teal: "#008080",
1996    white: "#ffffff",
1997    yellow: "#ffff00",
1998
1999    // 4.2.3. "transparent" color keyword
2000    transparent: [ null, null, null, 0 ],
2001
2002    _default: "#ffffff"
2003};
2004
2005} )( jQuery );
2006
2007/******************************************************************************/
2008/****************************** CLASS ANIMATIONS ******************************/
2009/******************************************************************************/
2010( function() {
2011
2012var classAnimationActions = [ "add", "remove", "toggle" ],
2013    shorthandStyles = {
2014        border: 1,
2015        borderBottom: 1,
2016        borderColor: 1,
2017        borderLeft: 1,
2018        borderRight: 1,
2019        borderTop: 1,
2020        borderWidth: 1,
2021        margin: 1,
2022        padding: 1
2023    };
2024
2025$.each(
2026    [ "borderLeftStyle", "borderRightStyle", "borderBottomStyle", "borderTopStyle" ],
2027    function( _, prop ) {
2028        $.fx.step[ prop ] = function( fx ) {
2029            if ( fx.end !== "none" && !fx.setAttr || fx.pos === 1 && !fx.setAttr ) {
2030                jQuery.style( fx.elem, prop, fx.end );
2031                fx.setAttr = true;
2032            }
2033        };
2034    }
2035);
2036
2037function getElementStyles( elem ) {
2038    var key, len,
2039        style = elem.ownerDocument.defaultView ?
2040            elem.ownerDocument.defaultView.getComputedStyle( elem, null ) :
2041            elem.currentStyle,
2042        styles = {};
2043
2044    if ( style && style.length && style[ 0 ] && style[ style[ 0 ] ] ) {
2045        len = style.length;
2046        while ( len-- ) {
2047            key = style[ len ];
2048            if ( typeof style[ key ] === "string" ) {
2049                styles[ $.camelCase( key ) ] = style[ key ];
2050            }
2051        }
2052
vendor: 9,851 bytes, lines 2053-2346
2053    // Support: Opera, IE <9
2054    } else {
2055        for ( key in style ) {
2056            if ( typeof style[ key ] === "string" ) {
2057                styles[ key ] = style[ key ];
2058            }
2059        }
2060    }
2061
2062    return styles;
2063}
2064
2065function styleDifference( oldStyle, newStyle ) {
2066    var diff = {},
2067        name, value;
2068
2069    for ( name in newStyle ) {
2070        value = newStyle[ name ];
2071        if ( oldStyle[ name ] !== value ) {
2072            if ( !shorthandStyles[ name ] ) {
2073                if ( $.fx.step[ name ] || !isNaN( parseFloat( value ) ) ) {
2074                    diff[ name ] = value;
2075                }
2076            }
2077        }
2078    }
2079
2080    return diff;
2081}
2082
2083// Support: jQuery <1.8
2084if ( !$.fn.addBack ) {
2085    $.fn.addBack = function( selector ) {
2086        return this.add( selector == null ?
2087            this.prevObject : this.prevObject.filter( selector )
2088        );
2089    };
2090}
2091
2092$.effects.animateClass = function( value, duration, easing, callback ) {
2093    var o = $.speed( duration, easing, callback );
2094
2095    return this.queue( function() {
2096        var animated = $( this ),
2097            baseClass = animated.attr( "class" ) || "",
2098            applyClassChange,
2099            allAnimations = o.children ? animated.find( "*" ).addBack() : animated;
2100
2101        // Map the animated objects to store the original styles.
2102        allAnimations = allAnimations.map( function() {
2103            var el = $( this );
2104            return {
2105                el: el,
2106                start: getElementStyles( this )
2107            };
2108        } );
2109
2110        // Apply class change
2111        applyClassChange = function() {
2112            $.each( classAnimationActions, function( i, action ) {
2113                if ( value[ action ] ) {
2114                    animated[ action + "Class" ]( value[ action ] );
2115                }
2116            } );
2117        };
2118        applyClassChange();
2119
2120        // Map all animated objects again - calculate new styles and diff
2121        allAnimations = allAnimations.map( function() {
2122            this.end = getElementStyles( this.el[ 0 ] );
2123            this.diff = styleDifference( this.start, this.end );
2124            return this;
2125        } );
2126
2127        // Apply original class
2128        animated.attr( "class", baseClass );
2129
2130        // Map all animated objects again - this time collecting a promise
2131        allAnimations = allAnimations.map( function() {
2132            var styleInfo = this,
2133                dfd = $.Deferred(),
2134                opts = $.extend( {}, o, {
2135                    queue: false,
2136                    complete: function() {
2137                        dfd.resolve( styleInfo );
2138                    }
2139                } );
2140
2141            this.el.animate( this.diff, opts );
2142            return dfd.promise();
2143        } );
2144
2145        // Once all animations have completed:
2146        $.when.apply( $, allAnimations.get() ).done( function() {
2147
2148            // Set the final class
2149            applyClassChange();
2150
2151            // For each animated element,
2152            // clear all css properties that were animated
2153            $.each( arguments, function() {
2154                var el = this.el;
2155                $.each( this.diff, function( key ) {
2156                    el.css( key, "" );
2157                } );
2158            } );
2159
2160            // This is guarnteed to be there if you use jQuery.speed()
2161            // it also handles dequeuing the next anim...
2162            o.complete.call( animated[ 0 ] );
2163        } );
2164    } );
2165};
2166
2167$.fn.extend( {
2168    addClass: ( function( orig ) {
2169        return function( classNames, speed, easing, callback ) {
2170            return speed ?
2171                $.effects.animateClass.call( this,
2172                    { add: classNames }, speed, easing, callback ) :
2173                orig.apply( this, arguments );
2174        };
2175    } )( $.fn.addClass ),
2176
2177    removeClass: ( function( orig ) {
2178        return function( classNames, speed, easing, callback ) {
2179            return arguments.length > 1 ?
2180                $.effects.animateClass.call( this,
2181                    { remove: classNames }, speed, easing, callback ) :
2182                orig.apply( this, arguments );
2183        };
2184    } )( $.fn.removeClass ),
2185
2186    toggleClass: ( function( orig ) {
2187        return function( classNames, force, speed, easing, callback ) {
2188            if ( typeof force === "boolean" || force === undefined ) {
2189                if ( !speed ) {
2190
2191                    // Without speed parameter
2192                    return orig.apply( this, arguments );
2193                } else {
2194                    return $.effects.animateClass.call( this,
2195                        ( force ? { add: classNames } : { remove: classNames } ),
2196                        speed, easing, callback );
2197                }
2198            } else {
2199
2200                // Without force parameter
2201                return $.effects.animateClass.call( this,
2202                    { toggle: classNames }, force, speed, easing );
2203            }
2204        };
2205    } )( $.fn.toggleClass ),
2206
2207    switchClass: function( remove, add, speed, easing, callback ) {
2208        return $.effects.animateClass.call( this, {
2209            add: add,
2210            remove: remove
2211        }, speed, easing, callback );
2212    }
2213} );
2214
2215} )();
2216
2217/******************************************************************************/
2218/*********************************** EFFECTS **********************************/
2219/******************************************************************************/
2220
2221( function() {
2222
2223if ( $.expr && $.expr.filters && $.expr.filters.animated ) {
2224    $.expr.filters.animated = ( function( orig ) {
2225        return function( elem ) {
2226            return !!$( elem ).data( dataSpaceAnimated ) || orig( elem );
2227        };
2228    } )( $.expr.filters.animated );
2229}
2230
2231if ( $.uiBackCompat !== false ) {
2232    $.extend( $.effects, {
2233
2234        // Saves a set of properties in a data storage
2235        save: function( element, set ) {
2236            var i = 0, length = set.length;
2237            for ( ; i < length; i++ ) {
2238                if ( set[ i ] !== null ) {
2239                    element.data( dataSpace + set[ i ], element[ 0 ].style[ set[ i ] ] );
2240                }
2241            }
2242        },
2243
2244        // Restores a set of previously saved properties from a data storage
2245        restore: function( element, set ) {
2246            var val, i = 0, length = set.length;
2247            for ( ; i < length; i++ ) {
2248                if ( set[ i ] !== null ) {
2249                    val = element.data( dataSpace + set[ i ] );
2250                    element.css( set[ i ], val );
2251                }
2252            }
2253        },
2254
2255        setMode: function( el, mode ) {
2256            if ( mode === "toggle" ) {
2257                mode = el.is( ":hidden" ) ? "show" : "hide";
2258            }
2259            return mode;
2260        },
2261
2262        // Wraps the element around a wrapper that copies position properties
2263        createWrapper: function( element ) {
2264
2265            // If the element is already wrapped, return it
2266            if ( element.parent().is( ".ui-effects-wrapper" ) ) {
2267                return element.parent();
2268            }
2269
2270            // Wrap the element
2271            var props = {
2272                    width: element.outerWidth( true ),
2273                    height: element.outerHeight( true ),
2274                    "float": element.css( "float" )
2275                },
2276                wrapper = $( "<div></div>" )
2277                    .addClass( "ui-effects-wrapper" )
2278                    .css( {
2279                        fontSize: "100%",
2280                        background: "transparent",
2281                        border: "none",
2282                        margin: 0,
2283                        padding: 0
2284                    } ),
2285
2286                // Store the size in case width/height are defined in % - Fixes #5245
2287                size = {
2288                    width: element.width(),
2289                    height: element.height()
2290                },
2291                active = document.activeElement;
2292
2293            // Support: Firefox
2294            // Firefox incorrectly exposes anonymous content
2295            // https://bugzilla.mozilla.org/show_bug.cgi?id=561664
2296            try {
2297                active.id;
2298            } catch ( e ) {
2299                active = document.body;
2300            }
2301
2302            element.wrap( wrapper );
2303
2304            // Fixes #7595 - Elements lose focus when wrapped.
2305            if ( element[ 0 ] === active || $.contains( element[ 0 ], active ) ) {
2306                $( active ).trigger( "focus" );
2307            }
2308
2309            // Hotfix for jQuery 1.4 since some change in wrap() seems to actually
2310            // lose the reference to the wrapped element
2311            wrapper = element.parent();
2312
2313            // Transfer positioning properties to the wrapper
2314            if ( element.css( "position" ) === "static" ) {
2315                wrapper.css( { position: "relative" } );
2316                element.css( { position: "relative" } );
2317            } else {
2318                $.extend( props, {
2319                    position: element.css( "position" ),
2320                    zIndex: element.css( "z-index" )
2321                } );
2322                $.each( [ "top", "left", "bottom", "right" ], function( i, pos ) {
2323                    props[ pos ] = element.css( pos );
2324                    if ( isNaN( parseInt( props[ pos ], 10 ) ) ) {
2325                        props[ pos ] = "auto";
2326                    }
2327                } );
2328                element.css( {
2329                    position: "relative",
2330                    top: 0,
2331                    left: 0,
2332                    right: "auto",
2333                    bottom: "auto"
2334                } );
2335            }
2336            element.css( size );
2337
2338            return wrapper.css( props ).show();
2339        },
2340
2341        removeWrapper: function( element ) {
2342            var active = document.activeElement;
2343
2344            if ( element.parent().is( ".ui-effects-wrapper" ) ) {
2345                element.parent().replaceWith( element );
2346
vendor: 22,427 bytes, lines 2347-3085
2347                // Fixes #7595 - Elements lose focus when wrapped.
2348                if ( element[ 0 ] === active || $.contains( element[ 0 ], active ) ) {
2349                    $( active ).trigger( "focus" );
2350                }
2351            }
2352
2353            return element;
2354        }
2355    } );
2356}
2357
2358$.extend( $.effects, {
2359    version: "1.12.1",
2360
2361    define: function( name, mode, effect ) {
2362        if ( !effect ) {
2363            effect = mode;
2364            mode = "effect";
2365        }
2366
2367        $.effects.effect[ name ] = effect;
2368        $.effects.effect[ name ].mode = mode;
2369
2370        return effect;
2371    },
2372
2373    scaledDimensions: function( element, percent, direction ) {
2374        if ( percent === 0 ) {
2375            return {
2376                height: 0,
2377                width: 0,
2378                outerHeight: 0,
2379                outerWidth: 0
2380            };
2381        }
2382
2383        var x = direction !== "horizontal" ? ( ( percent || 100 ) / 100 ) : 1,
2384            y = direction !== "vertical" ? ( ( percent || 100 ) / 100 ) : 1;
2385
2386        return {
2387            height: element.height() * y,
2388            width: element.width() * x,
2389            outerHeight: element.outerHeight() * y,
2390            outerWidth: element.outerWidth() * x
2391        };
2392
2393    },
2394
2395    clipToBox: function( animation ) {
2396        return {
2397            width: animation.clip.right - animation.clip.left,
2398            height: animation.clip.bottom - animation.clip.top,
2399            left: animation.clip.left,
2400            top: animation.clip.top
2401        };
2402    },
2403
2404    // Injects recently queued functions to be first in line (after "inprogress")
2405    unshift: function( element, queueLength, count ) {
2406        var queue = element.queue();
2407
2408        if ( queueLength > 1 ) {
2409            queue.splice.apply( queue,
2410                [ 1, 0 ].concat( queue.splice( queueLength, count ) ) );
2411        }
2412        element.dequeue();
2413    },
2414
2415    saveStyle: function( element ) {
2416        element.data( dataSpaceStyle, element[ 0 ].style.cssText );
2417    },
2418
2419    restoreStyle: function( element ) {
2420        element[ 0 ].style.cssText = element.data( dataSpaceStyle ) || "";
2421        element.removeData( dataSpaceStyle );
2422    },
2423
2424    mode: function( element, mode ) {
2425        var hidden = element.is( ":hidden" );
2426
2427        if ( mode === "toggle" ) {
2428            mode = hidden ? "show" : "hide";
2429        }
2430        if ( hidden ? mode === "hide" : mode === "show" ) {
2431            mode = "none";
2432        }
2433        return mode;
2434    },
2435
2436    // Translates a [top,left] array into a baseline value
2437    getBaseline: function( origin, original ) {
2438        var y, x;
2439
2440        switch ( origin[ 0 ] ) {
2441        case "top":
2442            y = 0;
2443            break;
2444        case "middle":
2445            y = 0.5;
2446            break;
2447        case "bottom":
2448            y = 1;
2449            break;
2450        default:
2451            y = origin[ 0 ] / original.height;
2452        }
2453
2454        switch ( origin[ 1 ] ) {
2455        case "left":
2456            x = 0;
2457            break;
2458        case "center":
2459            x = 0.5;
2460            break;
2461        case "right":
2462            x = 1;
2463            break;
2464        default:
2465            x = origin[ 1 ] / original.width;
2466        }
2467
2468        return {
2469            x: x,
2470            y: y
2471        };
2472    },
2473
2474    // Creates a placeholder element so that the original element can be made absolute
2475    createPlaceholder: function( element ) {
2476        var placeholder,
2477            cssPosition = element.css( "position" ),
2478            position = element.position();
2479
2480        // Lock in margins first to account for form elements, which
2481        // will change margin if you explicitly set height
2482        // see: http://jsfiddle.net/JZSMt/3/ https://bugs.webkit.org/show_bug.cgi?id=107380
2483        // Support: Safari
2484        element.css( {
2485            marginTop: element.css( "marginTop" ),
2486            marginBottom: element.css( "marginBottom" ),
2487            marginLeft: element.css( "marginLeft" ),
2488            marginRight: element.css( "marginRight" )
2489        } )
2490        .outerWidth( element.outerWidth() )
2491        .outerHeight( element.outerHeight() );
2492
2493        if ( /^(static|relative)/.test( cssPosition ) ) {
2494            cssPosition = "absolute";
2495
2496            placeholder = $( "<" + element[ 0 ].nodeName + ">" ).insertAfter( element ).css( {
2497
2498                // Convert inline to inline block to account for inline elements
2499                // that turn to inline block based on content (like img)
2500                display: /^(inline|ruby)/.test( element.css( "display" ) ) ?
2501                    "inline-block" :
2502                    "block",
2503                visibility: "hidden",
2504
2505                // Margins need to be set to account for margin collapse
2506                marginTop: element.css( "marginTop" ),
2507                marginBottom: element.css( "marginBottom" ),
2508                marginLeft: element.css( "marginLeft" ),
2509                marginRight: element.css( "marginRight" ),
2510                "float": element.css( "float" )
2511            } )
2512            .outerWidth( element.outerWidth() )
2513            .outerHeight( element.outerHeight() )
2514            .addClass( "ui-effects-placeholder" );
2515
2516            element.data( dataSpace + "placeholder", placeholder );
2517        }
2518
2519        element.css( {
2520            position: cssPosition,
2521            left: position.left,
2522            top: position.top
2523        } );
2524
2525        return placeholder;
2526    },
2527
2528    removePlaceholder: function( element ) {
2529        var dataKey = dataSpace + "placeholder",
2530                placeholder = element.data( dataKey );
2531
2532        if ( placeholder ) {
2533            placeholder.remove();
2534            element.removeData( dataKey );
2535        }
2536    },
2537
2538    // Removes a placeholder if it exists and restores
2539    // properties that were modified during placeholder creation
2540    cleanUp: function( element ) {
2541        $.effects.restoreStyle( element );
2542        $.effects.removePlaceholder( element );
2543    },
2544
2545    setTransition: function( element, list, factor, value ) {
2546        value = value || {};
2547        $.each( list, function( i, x ) {
2548            var unit = element.cssUnit( x );
2549            if ( unit[ 0 ] > 0 ) {
2550                value[ x ] = unit[ 0 ] * factor + unit[ 1 ];
2551            }
2552        } );
2553        return value;
2554    }
2555} );
2556
2557// Return an effect options object for the given parameters:
2558function _normalizeArguments( effect, options, speed, callback ) {
2559
2560    // Allow passing all options as the first parameter
2561    if ( $.isPlainObject( effect ) ) {
2562        options = effect;
2563        effect = effect.effect;
2564    }
2565
2566    // Convert to an object
2567    effect = { effect: effect };
2568
2569    // Catch (effect, null, ...)
2570    if ( options == null ) {
2571        options = {};
2572    }
2573
2574    // Catch (effect, callback)
2575    if ( $.isFunction( options ) ) {
2576        callback = options;
2577        speed = null;
2578        options = {};
2579    }
2580
2581    // Catch (effect, speed, ?)
2582    if ( typeof options === "number" || $.fx.speeds[ options ] ) {
2583        callback = speed;
2584        speed = options;
2585        options = {};
2586    }
2587
2588    // Catch (effect, options, callback)
2589    if ( $.isFunction( speed ) ) {
2590        callback = speed;
2591        speed = null;
2592    }
2593
2594    // Add options to effect
2595    if ( options ) {
2596        $.extend( effect, options );
2597    }
2598
2599    speed = speed || options.duration;
2600    effect.duration = $.fx.off ? 0 :
2601        typeof speed === "number" ? speed :
2602        speed in $.fx.speeds ? $.fx.speeds[ speed ] :
2603        $.fx.speeds._default;
2604
2605    effect.complete = callback || options.complete;
2606
2607    return effect;
2608}
2609
2610function standardAnimationOption( option ) {
2611
2612    // Valid standard speeds (nothing, number, named speed)
2613    if ( !option || typeof option === "number" || $.fx.speeds[ option ] ) {
2614        return true;
2615    }
2616
2617    // Invalid strings - treat as "normal" speed
2618    if ( typeof option === "string" && !$.effects.effect[ option ] ) {
2619        return true;
2620    }
2621
2622    // Complete callback
2623    if ( $.isFunction( option ) ) {
2624        return true;
2625    }
2626
2627    // Options hash (but not naming an effect)
2628    if ( typeof option === "object" && !option.effect ) {
2629        return true;
2630    }
2631
2632    // Didn't match any standard API
2633    return false;
2634}
2635
2636$.fn.extend( {
2637    effect: function( /* effect, options, speed, callback */ ) {
2638        var args = _normalizeArguments.apply( this, arguments ),
2639            effectMethod = $.effects.effect[ args.effect ],
2640            defaultMode = effectMethod.mode,
2641            queue = args.queue,
2642            queueName = queue || "fx",
2643            complete = args.complete,
2644            mode = args.mode,
2645            modes = [],
2646            prefilter = function( next ) {
2647                var el = $( this ),
2648                    normalizedMode = $.effects.mode( el, mode ) || defaultMode;
2649
2650                // Sentinel for duck-punching the :animated psuedo-selector
2651                el.data( dataSpaceAnimated, true );
2652
2653                // Save effect mode for later use,
2654                // we can't just call $.effects.mode again later,
2655                // as the .show() below destroys the initial state
2656                modes.push( normalizedMode );
2657
2658                // See $.uiBackCompat inside of run() for removal of defaultMode in 1.13
2659                if ( defaultMode && ( normalizedMode === "show" ||
2660                        ( normalizedMode === defaultMode && normalizedMode === "hide" ) ) ) {
2661                    el.show();
2662                }
2663
2664                if ( !defaultMode || normalizedMode !== "none" ) {
2665                    $.effects.saveStyle( el );
2666                }
2667
2668                if ( $.isFunction( next ) ) {
2669                    next();
2670                }
2671            };
2672
2673        if ( $.fx.off || !effectMethod ) {
2674
2675            // Delegate to the original method (e.g., .show()) if possible
2676            if ( mode ) {
2677                return this[ mode ]( args.duration, complete );
2678            } else {
2679                return this.each( function() {
2680                    if ( complete ) {
2681                        complete.call( this );
2682                    }
2683                } );
2684            }
2685        }
2686
2687        function run( next ) {
2688            var elem = $( this );
2689
2690            function cleanup() {
2691                elem.removeData( dataSpaceAnimated );
2692
2693                $.effects.cleanUp( elem );
2694
2695                if ( args.mode === "hide" ) {
2696                    elem.hide();
2697                }
2698
2699                done();
2700            }
2701
2702            function done() {
2703                if ( $.isFunction( complete ) ) {
2704                    complete.call( elem[ 0 ] );
2705                }
2706
2707                if ( $.isFunction( next ) ) {
2708                    next();
2709                }
2710            }
2711
2712            // Override mode option on a per element basis,
2713            // as toggle can be either show or hide depending on element state
2714            args.mode = modes.shift();
2715
2716            if ( $.uiBackCompat !== false && !defaultMode ) {
2717                if ( elem.is( ":hidden" ) ? mode === "hide" : mode === "show" ) {
2718
2719                    // Call the core method to track "olddisplay" properly
2720                    elem[ mode ]();
2721                    done();
2722                } else {
2723                    effectMethod.call( elem[ 0 ], args, done );
2724                }
2725            } else {
2726                if ( args.mode === "none" ) {
2727
2728                    // Call the core method to track "olddisplay" properly
2729                    elem[ mode ]();
2730                    done();
2731                } else {
2732                    effectMethod.call( elem[ 0 ], args, cleanup );
2733                }
2734            }
2735        }
2736
2737        // Run prefilter on all elements first to ensure that
2738        // any showing or hiding happens before placeholder creation,
2739        // which ensures that any layout changes are correctly captured.
2740        return queue === false ?
2741            this.each( prefilter ).each( run ) :
2742            this.queue( queueName, prefilter ).queue( queueName, run );
2743    },
2744
2745    show: ( function( orig ) {
2746        return function( option ) {
2747            if ( standardAnimationOption( option ) ) {
2748                return orig.apply( this, arguments );
2749            } else {
2750                var args = _normalizeArguments.apply( this, arguments );
2751                args.mode = "show";
2752                return this.effect.call( this, args );
2753            }
2754        };
2755    } )( $.fn.show ),
2756
2757    hide: ( function( orig ) {
2758        return function( option ) {
2759            if ( standardAnimationOption( option ) ) {
2760                return orig.apply( this, arguments );
2761            } else {
2762                var args = _normalizeArguments.apply( this, arguments );
2763                args.mode = "hide";
2764                return this.effect.call( this, args );
2765            }
2766        };
2767    } )( $.fn.hide ),
2768
2769    toggle: ( function( orig ) {
2770        return function( option ) {
2771            if ( standardAnimationOption( option ) || typeof option === "boolean" ) {
2772                return orig.apply( this, arguments );
2773            } else {
2774                var args = _normalizeArguments.apply( this, arguments );
2775                args.mode = "toggle";
2776                return this.effect.call( this, args );
2777            }
2778        };
2779    } )( $.fn.toggle ),
2780
2781    cssUnit: function( key ) {
2782        var style = this.css( key ),
2783            val = [];
2784
2785        $.each( [ "em", "px", "%", "pt" ], function( i, unit ) {
2786            if ( style.indexOf( unit ) > 0 ) {
2787                val = [ parseFloat( style ), unit ];
2788            }
2789        } );
2790        return val;
2791    },
2792
2793    cssClip: function( clipObj ) {
2794        if ( clipObj ) {
2795            return this.css( "clip", "rect(" + clipObj.top + "px " + clipObj.right + "px " +
2796                clipObj.bottom + "px " + clipObj.left + "px)" );
2797        }
2798        return parseClip( this.css( "clip" ), this );
2799    },
2800
2801    transfer: function( options, done ) {
2802        var element = $( this ),
2803            target = $( options.to ),
2804            targetFixed = target.css( "position" ) === "fixed",
2805            body = $( "body" ),
2806            fixTop = targetFixed ? body.scrollTop() : 0,
2807            fixLeft = targetFixed ? body.scrollLeft() : 0,
2808            endPosition = target.offset(),
2809            animation = {
2810                top: endPosition.top - fixTop,
2811                left: endPosition.left - fixLeft,
2812                height: target.innerHeight(),
2813                width: target.innerWidth()
2814            },
2815            startPosition = element.offset(),
2816            transfer = $( "<div class='ui-effects-transfer'></div>" )
2817                .appendTo( "body" )
2818                .addClass( options.className )
2819                .css( {
2820                    top: startPosition.top - fixTop,
2821                    left: startPosition.left - fixLeft,
2822                    height: element.innerHeight(),
2823                    width: element.innerWidth(),
2824                    position: targetFixed ? "fixed" : "absolute"
2825                } )
2826                .animate( animation, options.duration, options.easing, function() {
2827                    transfer.remove();
2828                    if ( $.isFunction( done ) ) {
2829                        done();
2830                    }
2831                } );
2832    }
2833} );
2834
2835function parseClip( str, element ) {
2836        var outerWidth = element.outerWidth(),
2837            outerHeight = element.outerHeight(),
2838            clipRegex = /^rect\((-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto),?\s*(-?\d*\.?\d*px|-?\d+%|auto)\)$/,
2839            values = clipRegex.exec( str ) || [ "", 0, outerWidth, outerHeight, 0 ];
2840
2841        return {
2842            top: parseFloat( values[ 1 ] ) || 0,
2843            right: values[ 2 ] === "auto" ? outerWidth : parseFloat( values[ 2 ] ),
2844            bottom: values[ 3 ] === "auto" ? outerHeight : parseFloat( values[ 3 ] ),
2845            left: parseFloat( values[ 4 ] ) || 0
2846        };
2847}
2848
2849$.fx.step.clip = function( fx ) {
2850    if ( !fx.clipInit ) {
2851        fx.start = $( fx.elem ).cssClip();
2852        if ( typeof fx.end === "string" ) {
2853            fx.end = parseClip( fx.end, fx.elem );
2854        }
2855        fx.clipInit = true;
2856    }
2857
2858    $( fx.elem ).cssClip( {
2859        top: fx.pos * ( fx.end.top - fx.start.top ) + fx.start.top,
2860        right: fx.pos * ( fx.end.right - fx.start.right ) + fx.start.right,
2861        bottom: fx.pos * ( fx.end.bottom - fx.start.bottom ) + fx.start.bottom,
2862        left: fx.pos * ( fx.end.left - fx.start.left ) + fx.start.left
2863    } );
2864};
2865
2866} )();
2867
2868/******************************************************************************/
2869/*********************************** EASING ***********************************/
2870/******************************************************************************/
2871
2872( function() {
2873
2874// Based on easing equations from Robert Penner (http://www.robertpenner.com/easing)
2875
2876var baseEasings = {};
2877
2878$.each( [ "Quad", "Cubic", "Quart", "Quint", "Expo" ], function( i, name ) {
2879    baseEasings[ name ] = function( p ) {
2880        return Math.pow( p, i + 2 );
2881    };
2882} );
2883
2884$.extend( baseEasings, {
2885    Sine: function( p ) {
2886        return 1 - Math.cos( p * Math.PI / 2 );
2887    },
2888    Circ: function( p ) {
2889        return 1 - Math.sqrt( 1 - p * p );
2890    },
2891    Elastic: function( p ) {
2892        return p === 0 || p === 1 ? p :
2893            -Math.pow( 2, 8 * ( p - 1 ) ) * Math.sin( ( ( p - 1 ) * 80 - 7.5 ) * Math.PI / 15 );
2894    },
2895    Back: function( p ) {
2896        return p * p * ( 3 * p - 2 );
2897    },
2898    Bounce: function( p ) {
2899        var pow2,
2900            bounce = 4;
2901
2902        while ( p < ( ( pow2 = Math.pow( 2, --bounce ) ) - 1 ) / 11 ) {}
2903        return 1 / Math.pow( 4, 3 - bounce ) - 7.5625 * Math.pow( ( pow2 * 3 - 2 ) / 22 - p, 2 );
2904    }
2905} );
2906
2907$.each( baseEasings, function( name, easeIn ) {
2908    $.easing[ "easeIn" + name ] = easeIn;
2909    $.easing[ "easeOut" + name ] = function( p ) {
2910        return 1 - easeIn( 1 - p );
2911    };
2912    $.easing[ "easeInOut" + name ] = function( p ) {
2913        return p < 0.5 ?
2914            easeIn( p * 2 ) / 2 :
2915            1 - easeIn( p * -2 + 2 ) / 2;
2916    };
2917} );
2918
2919} )();
2920
2921var effect = $.effects;
2922
2923
2924/*!
2925 * jQuery UI Effects Blind 1.12.1
2926 * http://jqueryui.com
2927 *
2928 * Copyright jQuery Foundation and other contributors
2929 * Released under the MIT license.
2930 * http://jquery.org/license
2931 */
2932
2933//>>label: Blind Effect
2934//>>group: Effects
2935//>>description: Blinds the element.
2936//>>docs: http://api.jqueryui.com/blind-effect/
2937//>>demos: http://jqueryui.com/effect/
2938
2939
2940
2941var effectsEffectBlind = $.effects.define( "blind", "hide", function( options, done ) {
2942    var map = {
2943            up: [ "bottom", "top" ],
2944            vertical: [ "bottom", "top" ],
2945            down: [ "top", "bottom" ],
2946            left: [ "right", "left" ],
2947            horizontal: [ "right", "left" ],
2948            right: [ "left", "right" ]
2949        },
2950        element = $( this ),
2951        direction = options.direction || "up",
2952        start = element.cssClip(),
2953        animate = { clip: $.extend( {}, start ) },
2954        placeholder = $.effects.createPlaceholder( element );
2955
2956    animate.clip[ map[ direction ][ 0 ] ] = animate.clip[ map[ direction ][ 1 ] ];
2957
2958    if ( options.mode === "show" ) {
2959        element.cssClip( animate.clip );
2960        if ( placeholder ) {
2961            placeholder.css( $.effects.clipToBox( animate ) );
2962        }
2963
2964        animate.clip = start;
2965    }
2966
2967    if ( placeholder ) {
2968        placeholder.animate( $.effects.clipToBox( animate ), options.duration, options.easing );
2969    }
2970
2971    element.animate( animate, {
2972        queue: false,
2973        duration: options.duration,
2974        easing: options.easing,
2975        complete: done
2976    } );
2977} );
2978
2979
2980/*!
2981 * jQuery UI Effects Bounce 1.12.1
2982 * http://jqueryui.com
2983 *
2984 * Copyright jQuery Foundation and other contributors
2985 * Released under the MIT license.
2986 * http://jquery.org/license
2987 */
2988
2989//>>label: Bounce Effect
2990//>>group: Effects
2991//>>description: Bounces an element horizontally or vertically n times.
2992//>>docs: http://api.jqueryui.com/bounce-effect/
2993//>>demos: http://jqueryui.com/effect/
2994
2995
2996
2997var effectsEffectBounce = $.effects.define( "bounce", function( options, done ) {
2998    var upAnim, downAnim, refValue,
2999        element = $( this ),
3000
3001        // Defaults:
3002        mode = options.mode,
3003        hide = mode === "hide",
3004        show = mode === "show",
3005        direction = options.direction || "up",
3006        distance = options.distance,
3007        times = options.times || 5,
3008
3009        // Number of internal animations
3010        anims = times * 2 + ( show || hide ? 1 : 0 ),
3011        speed = options.duration / anims,
3012        easing = options.easing,
3013
3014        // Utility:
3015        ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
3016        motion = ( direction === "up" || direction === "left" ),
3017        i = 0,
3018
3019        queuelen = element.queue().length;
3020
3021    $.effects.createPlaceholder( element );
3022
3023    refValue = element.css( ref );
3024
3025    // Default distance for the BIGGEST bounce is the outer Distance / 3
3026    if ( !distance ) {
3027        distance = element[ ref === "top" ? "outerHeight" : "outerWidth" ]() / 3;
3028    }
3029
3030    if ( show ) {
3031        downAnim = { opacity: 1 };
3032        downAnim[ ref ] = refValue;
3033
3034        // If we are showing, force opacity 0 and set the initial position
3035        // then do the "first" animation
3036        element
3037            .css( "opacity", 0 )
3038            .css( ref, motion ? -distance * 2 : distance * 2 )
3039            .animate( downAnim, speed, easing );
3040    }
3041
3042    // Start at the smallest distance if we are hiding
3043    if ( hide ) {
3044        distance = distance / Math.pow( 2, times - 1 );
3045    }
3046
3047    downAnim = {};
3048    downAnim[ ref ] = refValue;
3049
3050    // Bounces up/down/left/right then back to 0 -- times * 2 animations happen here
3051    for ( ; i < times; i++ ) {
3052        upAnim = {};
3053        upAnim[ ref ] = ( motion ? "-=" : "+=" ) + distance;
3054
3055        element
3056            .animate( upAnim, speed, easing )
3057            .animate( downAnim, speed, easing );
3058
3059        distance = hide ? distance * 2 : distance / 2;
3060    }
3061
3062    // Last Bounce when Hiding
3063    if ( hide ) {
3064        upAnim = { opacity: 0 };
3065        upAnim[ ref ] = ( motion ? "-=" : "+=" ) + distance;
3066
3067        element.animate( upAnim, speed, easing );
3068    }
3069
3070    element.queue( done );
3071
3072    $.effects.unshift( element, queuelen, anims + 1 );
3073} );
3074
3075
3076/*!
3077 * jQuery UI Effects Clip 1.12.1
3078 * http://jqueryui.com
3079 *
3080 * Copyright jQuery Foundation and other contributors
3081 * Released under the MIT license.
3082 * http://jquery.org/license
3083 */
3084
3085//>>label: Clip Effect
vendor: 6,882 bytes, lines 3086-3321
3086//>>group: Effects
3087//>>description: Clips the element on and off like an old TV.
3088//>>docs: http://api.jqueryui.com/clip-effect/
3089//>>demos: http://jqueryui.com/effect/
3090
3091
3092
3093var effectsEffectClip = $.effects.define( "clip", "hide", function( options, done ) {
3094    var start,
3095        animate = {},
3096        element = $( this ),
3097        direction = options.direction || "vertical",
3098        both = direction === "both",
3099        horizontal = both || direction === "horizontal",
3100        vertical = both || direction === "vertical";
3101
3102    start = element.cssClip();
3103    animate.clip = {
3104        top: vertical ? ( start.bottom - start.top ) / 2 : start.top,
3105        right: horizontal ? ( start.right - start.left ) / 2 : start.right,
3106        bottom: vertical ? ( start.bottom - start.top ) / 2 : start.bottom,
3107        left: horizontal ? ( start.right - start.left ) / 2 : start.left
3108    };
3109
3110    $.effects.createPlaceholder( element );
3111
3112    if ( options.mode === "show" ) {
3113        element.cssClip( animate.clip );
3114        animate.clip = start;
3115    }
3116
3117    element.animate( animate, {
3118        queue: false,
3119        duration: options.duration,
3120        easing: options.easing,
3121        complete: done
3122    } );
3123
3124} );
3125
3126
3127/*!
3128 * jQuery UI Effects Drop 1.12.1
3129 * http://jqueryui.com
3130 *
3131 * Copyright jQuery Foundation and other contributors
3132 * Released under the MIT license.
3133 * http://jquery.org/license
3134 */
3135
3136//>>label: Drop Effect
3137//>>group: Effects
3138//>>description: Moves an element in one direction and hides it at the same time.
3139//>>docs: http://api.jqueryui.com/drop-effect/
3140//>>demos: http://jqueryui.com/effect/
3141
3142
3143
3144var effectsEffectDrop = $.effects.define( "drop", "hide", function( options, done ) {
3145
3146    var distance,
3147        element = $( this ),
3148        mode = options.mode,
3149        show = mode === "show",
3150        direction = options.direction || "left",
3151        ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
3152        motion = ( direction === "up" || direction === "left" ) ? "-=" : "+=",
3153        oppositeMotion = ( motion === "+=" ) ? "-=" : "+=",
3154        animation = {
3155            opacity: 0
3156        };
3157
3158    $.effects.createPlaceholder( element );
3159
3160    distance = options.distance ||
3161        element[ ref === "top" ? "outerHeight" : "outerWidth" ]( true ) / 2;
3162
3163    animation[ ref ] = motion + distance;
3164
3165    if ( show ) {
3166        element.css( animation );
3167
3168        animation[ ref ] = oppositeMotion + distance;
3169        animation.opacity = 1;
3170    }
3171
3172    // Animate
3173    element.animate( animation, {
3174        queue: false,
3175        duration: options.duration,
3176        easing: options.easing,
3177        complete: done
3178    } );
3179} );
3180
3181
3182/*!
3183 * jQuery UI Effects Explode 1.12.1
3184 * http://jqueryui.com
3185 *
3186 * Copyright jQuery Foundation and other contributors
3187 * Released under the MIT license.
3188 * http://jquery.org/license
3189 */
3190
3191//>>label: Explode Effect
3192//>>group: Effects
3193// jscs:disable maximumLineLength
3194//>>description: Explodes an element in all directions into n pieces. Implodes an element to its original wholeness.
3195// jscs:enable maximumLineLength
3196//>>docs: http://api.jqueryui.com/explode-effect/
3197//>>demos: http://jqueryui.com/effect/
3198
3199
3200
3201var effectsEffectExplode = $.effects.define( "explode", "hide", function( options, done ) {
3202
3203    var i, j, left, top, mx, my,
3204        rows = options.pieces ? Math.round( Math.sqrt( options.pieces ) ) : 3,
3205        cells = rows,
3206        element = $( this ),
3207        mode = options.mode,
3208        show = mode === "show",
3209
3210        // Show and then visibility:hidden the element before calculating offset
3211        offset = element.show().css( "visibility", "hidden" ).offset(),
3212
3213        // Width and height of a piece
3214        width = Math.ceil( element.outerWidth() / cells ),
3215        height = Math.ceil( element.outerHeight() / rows ),
3216        pieces = [];
3217
3218    // Children animate complete:
3219    function childComplete() {
3220        pieces.push( this );
3221        if ( pieces.length === rows * cells ) {
3222            animComplete();
3223        }
3224    }
3225
3226    // Clone the element for each row and cell.
3227    for ( i = 0; i < rows; i++ ) { // ===>
3228        top = offset.top + i * height;
3229        my = i - ( rows - 1 ) / 2;
3230
3231        for ( j = 0; j < cells; j++ ) { // |||
3232            left = offset.left + j * width;
3233            mx = j - ( cells - 1 ) / 2;
3234
3235            // Create a clone of the now hidden main element that will be absolute positioned
3236            // within a wrapper div off the -left and -top equal to size of our pieces
3237            element
3238                .clone()
3239                .appendTo( "body" )
3240                .wrap( "<div></div>" )
3241                .css( {
3242                    position: "absolute",
3243                    visibility: "visible",
3244                    left: -j * width,
3245                    top: -i * height
3246                } )
3247
3248                // Select the wrapper - make it overflow: hidden and absolute positioned based on
3249                // where the original was located +left and +top equal to the size of pieces
3250                .parent()
3251                    .addClass( "ui-effects-explode" )
3252                    .css( {
3253                        position: "absolute",
3254                        overflow: "hidden",
3255                        width: width,
3256                        height: height,
3257                        left: left + ( show ? mx * width : 0 ),
3258                        top: top + ( show ? my * height : 0 ),
3259                        opacity: show ? 0 : 1
3260                    } )
3261                    .animate( {
3262                        left: left + ( show ? 0 : mx * width ),
3263                        top: top + ( show ? 0 : my * height ),
3264                        opacity: show ? 1 : 0
3265                    }, options.duration || 500, options.easing, childComplete );
3266        }
3267    }
3268
3269    function animComplete() {
3270        element.css( {
3271            visibility: "visible"
3272        } );
3273        $( pieces ).remove();
3274        done();
3275    }
3276} );
3277
3278
3279/*!
3280 * jQuery UI Effects Fade 1.12.1
3281 * http://jqueryui.com
3282 *
3283 * Copyright jQuery Foundation and other contributors
3284 * Released under the MIT license.
3285 * http://jquery.org/license
3286 */
3287
3288//>>label: Fade Effect
3289//>>group: Effects
3290//>>description: Fades the element.
3291//>>docs: http://api.jqueryui.com/fade-effect/
3292//>>demos: http://jqueryui.com/effect/
3293
3294
3295
3296var effectsEffectFade = $.effects.define( "fade", "toggle", function( options, done ) {
3297    var show = options.mode === "show";
3298
3299    $( this )
3300        .css( "opacity", show ? 0 : 1 )
3301        .animate( {
3302            opacity: show ? 1 : 0
3303        }, {
3304            queue: false,
3305            duration: options.duration,
3306            easing: options.easing,
3307            complete: done
3308        } );
3309} );
3310
3311
3312/*!
3313 * jQuery UI Effects Fold 1.12.1
3314 * http://jqueryui.com
3315 *
3316 * Copyright jQuery Foundation and other contributors
3317 * Released under the MIT license.
3318 * http://jquery.org/license
3319 */
3320
3321//>>label: Fold Effect
vendor: 9,683 bytes, lines 3322-3629
3322//>>group: Effects
3323//>>description: Folds an element first horizontally and then vertically.
3324//>>docs: http://api.jqueryui.com/fold-effect/
3325//>>demos: http://jqueryui.com/effect/
3326
3327
3328
3329var effectsEffectFold = $.effects.define( "fold", "hide", function( options, done ) {
3330
3331    // Create element
3332    var element = $( this ),
3333        mode = options.mode,
3334        show = mode === "show",
3335        hide = mode === "hide",
3336        size = options.size || 15,
3337        percent = /([0-9]+)%/.exec( size ),
3338        horizFirst = !!options.horizFirst,
3339        ref = horizFirst ? [ "right", "bottom" ] : [ "bottom", "right" ],
3340        duration = options.duration / 2,
3341
3342        placeholder = $.effects.createPlaceholder( element ),
3343
3344        start = element.cssClip(),
3345        animation1 = { clip: $.extend( {}, start ) },
3346        animation2 = { clip: $.extend( {}, start ) },
3347
3348        distance = [ start[ ref[ 0 ] ], start[ ref[ 1 ] ] ],
3349
3350        queuelen = element.queue().length;
3351
3352    if ( percent ) {
3353        size = parseInt( percent[ 1 ], 10 ) / 100 * distance[ hide ? 0 : 1 ];
3354    }
3355    animation1.clip[ ref[ 0 ] ] = size;
3356    animation2.clip[ ref[ 0 ] ] = size;
3357    animation2.clip[ ref[ 1 ] ] = 0;
3358
3359    if ( show ) {
3360        element.cssClip( animation2.clip );
3361        if ( placeholder ) {
3362            placeholder.css( $.effects.clipToBox( animation2 ) );
3363        }
3364
3365        animation2.clip = start;
3366    }
3367
3368    // Animate
3369    element
3370        .queue( function( next ) {
3371            if ( placeholder ) {
3372                placeholder
3373                    .animate( $.effects.clipToBox( animation1 ), duration, options.easing )
3374                    .animate( $.effects.clipToBox( animation2 ), duration, options.easing );
3375            }
3376
3377            next();
3378        } )
3379        .animate( animation1, duration, options.easing )
3380        .animate( animation2, duration, options.easing )
3381        .queue( done );
3382
3383    $.effects.unshift( element, queuelen, 4 );
3384} );
3385
3386
3387/*!
3388 * jQuery UI Effects Highlight 1.12.1
3389 * http://jqueryui.com
3390 *
3391 * Copyright jQuery Foundation and other contributors
3392 * Released under the MIT license.
3393 * http://jquery.org/license
3394 */
3395
3396//>>label: Highlight Effect
3397//>>group: Effects
3398//>>description: Highlights the background of an element in a defined color for a custom duration.
3399//>>docs: http://api.jqueryui.com/highlight-effect/
3400//>>demos: http://jqueryui.com/effect/
3401
3402
3403
3404var effectsEffectHighlight = $.effects.define( "highlight", "show", function( options, done ) {
3405    var element = $( this ),
3406        animation = {
3407            backgroundColor: element.css( "backgroundColor" )
3408        };
3409
3410    if ( options.mode === "hide" ) {
3411        animation.opacity = 0;
3412    }
3413
3414    $.effects.saveStyle( element );
3415
3416    element
3417        .css( {
3418            backgroundImage: "none",
3419            backgroundColor: options.color || "#ffff99"
3420        } )
3421        .animate( animation, {
3422            queue: false,
3423            duration: options.duration,
3424            easing: options.easing,
3425            complete: done
3426        } );
3427} );
3428
3429
3430/*!
3431 * jQuery UI Effects Size 1.12.1
3432 * http://jqueryui.com
3433 *
3434 * Copyright jQuery Foundation and other contributors
3435 * Released under the MIT license.
3436 * http://jquery.org/license
3437 */
3438
3439//>>label: Size Effect
3440//>>group: Effects
3441//>>description: Resize an element to a specified width and height.
3442//>>docs: http://api.jqueryui.com/size-effect/
3443//>>demos: http://jqueryui.com/effect/
3444
3445
3446
3447var effectsEffectSize = $.effects.define( "size", function( options, done ) {
3448
3449    // Create element
3450    var baseline, factor, temp,
3451        element = $( this ),
3452
3453        // Copy for children
3454        cProps = [ "fontSize" ],
3455        vProps = [ "borderTopWidth", "borderBottomWidth", "paddingTop", "paddingBottom" ],
3456        hProps = [ "borderLeftWidth", "borderRightWidth", "paddingLeft", "paddingRight" ],
3457
3458        // Set options
3459        mode = options.mode,
3460        restore = mode !== "effect",
3461        scale = options.scale || "both",
3462        origin = options.origin || [ "middle", "center" ],
3463        position = element.css( "position" ),
3464        pos = element.position(),
3465        original = $.effects.scaledDimensions( element ),
3466        from = options.from || original,
3467        to = options.to || $.effects.scaledDimensions( element, 0 );
3468
3469    $.effects.createPlaceholder( element );
3470
3471    if ( mode === "show" ) {
3472        temp = from;
3473        from = to;
3474        to = temp;
3475    }
3476
3477    // Set scaling factor
3478    factor = {
3479        from: {
3480            y: from.height / original.height,
3481            x: from.width / original.width
3482        },
3483        to: {
3484            y: to.height / original.height,
3485            x: to.width / original.width
3486        }
3487    };
3488
3489    // Scale the css box
3490    if ( scale === "box" || scale === "both" ) {
3491
3492        // Vertical props scaling
3493        if ( factor.from.y !== factor.to.y ) {
3494            from = $.effects.setTransition( element, vProps, factor.from.y, from );
3495            to = $.effects.setTransition( element, vProps, factor.to.y, to );
3496        }
3497
3498        // Horizontal props scaling
3499        if ( factor.from.x !== factor.to.x ) {
3500            from = $.effects.setTransition( element, hProps, factor.from.x, from );
3501            to = $.effects.setTransition( element, hProps, factor.to.x, to );
3502        }
3503    }
3504
3505    // Scale the content
3506    if ( scale === "content" || scale === "both" ) {
3507
3508        // Vertical props scaling
3509        if ( factor.from.y !== factor.to.y ) {
3510            from = $.effects.setTransition( element, cProps, factor.from.y, from );
3511            to = $.effects.setTransition( element, cProps, factor.to.y, to );
3512        }
3513    }
3514
3515    // Adjust the position properties based on the provided origin points
3516    if ( origin ) {
3517        baseline = $.effects.getBaseline( origin, original );
3518        from.top = ( original.outerHeight - from.outerHeight ) * baseline.y + pos.top;
3519        from.left = ( original.outerWidth - from.outerWidth ) * baseline.x + pos.left;
3520        to.top = ( original.outerHeight - to.outerHeight ) * baseline.y + pos.top;
3521        to.left = ( original.outerWidth - to.outerWidth ) * baseline.x + pos.left;
3522    }
3523    element.css( from );
3524
3525    // Animate the children if desired
3526    if ( scale === "content" || scale === "both" ) {
3527
3528        vProps = vProps.concat( [ "marginTop", "marginBottom" ] ).concat( cProps );
3529        hProps = hProps.concat( [ "marginLeft", "marginRight" ] );
3530
3531        // Only animate children with width attributes specified
3532        // TODO: is this right? should we include anything with css width specified as well
3533        element.find( "*[width]" ).each( function() {
3534            var child = $( this ),
3535                childOriginal = $.effects.scaledDimensions( child ),
3536                childFrom = {
3537                    height: childOriginal.height * factor.from.y,
3538                    width: childOriginal.width * factor.from.x,
3539                    outerHeight: childOriginal.outerHeight * factor.from.y,
3540                    outerWidth: childOriginal.outerWidth * factor.from.x
3541                },
3542                childTo = {
3543                    height: childOriginal.height * factor.to.y,
3544                    width: childOriginal.width * factor.to.x,
3545                    outerHeight: childOriginal.height * factor.to.y,
3546                    outerWidth: childOriginal.width * factor.to.x
3547                };
3548
3549            // Vertical props scaling
3550            if ( factor.from.y !== factor.to.y ) {
3551                childFrom = $.effects.setTransition( child, vProps, factor.from.y, childFrom );
3552                childTo = $.effects.setTransition( child, vProps, factor.to.y, childTo );
3553            }
3554
3555            // Horizontal props scaling
3556            if ( factor.from.x !== factor.to.x ) {
3557                childFrom = $.effects.setTransition( child, hProps, factor.from.x, childFrom );
3558                childTo = $.effects.setTransition( child, hProps, factor.to.x, childTo );
3559            }
3560
3561            if ( restore ) {
3562                $.effects.saveStyle( child );
3563            }
3564
3565            // Animate children
3566            child.css( childFrom );
3567            child.animate( childTo, options.duration, options.easing, function() {
3568
3569                // Restore children
3570                if ( restore ) {
3571                    $.effects.restoreStyle( child );
3572                }
3573            } );
3574        } );
3575    }
3576
3577    // Animate
3578    element.animate( to, {
3579        queue: false,
3580        duration: options.duration,
3581        easing: options.easing,
3582        complete: function() {
3583
3584            var offset = element.offset();
3585
3586            if ( to.opacity === 0 ) {
3587                element.css( "opacity", from.opacity );
3588            }
3589
3590            if ( !restore ) {
3591                element
3592                    .css( "position", position === "static" ? "relative" : position )
3593                    .offset( offset );
3594
3595                // Need to save style here so that automatic style restoration
3596                // doesn't restore to the original styles from before the animation.
3597                $.effects.saveStyle( element );
3598            }
3599
3600            done();
3601        }
3602    } );
3603
3604} );
3605
3606
3607/*!
3608 * jQuery UI Effects Scale 1.12.1
3609 * http://jqueryui.com
3610 *
3611 * Copyright jQuery Foundation and other contributors
3612 * Released under the MIT license.
3613 * http://jquery.org/license
3614 */
3615
3616//>>label: Scale Effect
3617//>>group: Effects
3618//>>description: Grows or shrinks an element and its content.
3619//>>docs: http://api.jqueryui.com/scale-effect/
3620//>>demos: http://jqueryui.com/effect/
3621
3622
3623
3624var effectsEffectScale = $.effects.define( "scale", function( options, done ) {
3625
3626    // Create element
3627    var el = $( this ),
3628        mode = options.mode,
3629        percent = parseInt( options.percent, 10 ) ||
vendor: 7,096 bytes, lines 3630-3882
3630            ( parseInt( options.percent, 10 ) === 0 ? 0 : ( mode !== "effect" ? 0 : 100 ) ),
3631
3632        newOptions = $.extend( true, {
3633            from: $.effects.scaledDimensions( el ),
3634            to: $.effects.scaledDimensions( el, percent, options.direction || "both" ),
3635            origin: options.origin || [ "middle", "center" ]
3636        }, options );
3637
3638    // Fade option to support puff
3639    if ( options.fade ) {
3640        newOptions.from.opacity = 1;
3641        newOptions.to.opacity = 0;
3642    }
3643
3644    $.effects.effect.size.call( this, newOptions, done );
3645} );
3646
3647
3648/*!
3649 * jQuery UI Effects Puff 1.12.1
3650 * http://jqueryui.com
3651 *
3652 * Copyright jQuery Foundation and other contributors
3653 * Released under the MIT license.
3654 * http://jquery.org/license
3655 */
3656
3657//>>label: Puff Effect
3658//>>group: Effects
3659//>>description: Creates a puff effect by scaling the element up and hiding it at the same time.
3660//>>docs: http://api.jqueryui.com/puff-effect/
3661//>>demos: http://jqueryui.com/effect/
3662
3663
3664
3665var effectsEffectPuff = $.effects.define( "puff", "hide", function( options, done ) {
3666    var newOptions = $.extend( true, {}, options, {
3667        fade: true,
3668        percent: parseInt( options.percent, 10 ) || 150
3669    } );
3670
3671    $.effects.effect.scale.call( this, newOptions, done );
3672} );
3673
3674
3675/*!
3676 * jQuery UI Effects Pulsate 1.12.1
3677 * http://jqueryui.com
3678 *
3679 * Copyright jQuery Foundation and other contributors
3680 * Released under the MIT license.
3681 * http://jquery.org/license
3682 */
3683
3684//>>label: Pulsate Effect
3685//>>group: Effects
3686//>>description: Pulsates an element n times by changing the opacity to zero and back.
3687//>>docs: http://api.jqueryui.com/pulsate-effect/
3688//>>demos: http://jqueryui.com/effect/
3689
3690
3691
3692var effectsEffectPulsate = $.effects.define( "pulsate", "show", function( options, done ) {
3693    var element = $( this ),
3694        mode = options.mode,
3695        show = mode === "show",
3696        hide = mode === "hide",
3697        showhide = show || hide,
3698
3699        // Showing or hiding leaves off the "last" animation
3700        anims = ( ( options.times || 5 ) * 2 ) + ( showhide ? 1 : 0 ),
3701        duration = options.duration / anims,
3702        animateTo = 0,
3703        i = 1,
3704        queuelen = element.queue().length;
3705
3706    if ( show || !element.is( ":visible" ) ) {
3707        element.css( "opacity", 0 ).show();
3708        animateTo = 1;
3709    }
3710
3711    // Anims - 1 opacity "toggles"
3712    for ( ; i < anims; i++ ) {
3713        element.animate( { opacity: animateTo }, duration, options.easing );
3714        animateTo = 1 - animateTo;
3715    }
3716
3717    element.animate( { opacity: animateTo }, duration, options.easing );
3718
3719    element.queue( done );
3720
3721    $.effects.unshift( element, queuelen, anims + 1 );
3722} );
3723
3724
3725/*!
3726 * jQuery UI Effects Shake 1.12.1
3727 * http://jqueryui.com
3728 *
3729 * Copyright jQuery Foundation and other contributors
3730 * Released under the MIT license.
3731 * http://jquery.org/license
3732 */
3733
3734//>>label: Shake Effect
3735//>>group: Effects
3736//>>description: Shakes an element horizontally or vertically n times.
3737//>>docs: http://api.jqueryui.com/shake-effect/
3738//>>demos: http://jqueryui.com/effect/
3739
3740
3741
3742var effectsEffectShake = $.effects.define( "shake", function( options, done ) {
3743
3744    var i = 1,
3745        element = $( this ),
3746        direction = options.direction || "left",
3747        distance = options.distance || 20,
3748        times = options.times || 3,
3749        anims = times * 2 + 1,
3750        speed = Math.round( options.duration / anims ),
3751        ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
3752        positiveMotion = ( direction === "up" || direction === "left" ),
3753        animation = {},
3754        animation1 = {},
3755        animation2 = {},
3756
3757        queuelen = element.queue().length;
3758
3759    $.effects.createPlaceholder( element );
3760
3761    // Animation
3762    animation[ ref ] = ( positiveMotion ? "-=" : "+=" ) + distance;
3763    animation1[ ref ] = ( positiveMotion ? "+=" : "-=" ) + distance * 2;
3764    animation2[ ref ] = ( positiveMotion ? "-=" : "+=" ) + distance * 2;
3765
3766    // Animate
3767    element.animate( animation, speed, options.easing );
3768
3769    // Shakes
3770    for ( ; i < times; i++ ) {
3771        element
3772            .animate( animation1, speed, options.easing )
3773            .animate( animation2, speed, options.easing );
3774    }
3775
3776    element
3777        .animate( animation1, speed, options.easing )
3778        .animate( animation, speed / 2, options.easing )
3779        .queue( done );
3780
3781    $.effects.unshift( element, queuelen, anims + 1 );
3782} );
3783
3784
3785/*!
3786 * jQuery UI Effects Slide 1.12.1
3787 * http://jqueryui.com
3788 *
3789 * Copyright jQuery Foundation and other contributors
3790 * Released under the MIT license.
3791 * http://jquery.org/license
3792 */
3793
3794//>>label: Slide Effect
3795//>>group: Effects
3796//>>description: Slides an element in and out of the viewport.
3797//>>docs: http://api.jqueryui.com/slide-effect/
3798//>>demos: http://jqueryui.com/effect/
3799
3800
3801
3802var effectsEffectSlide = $.effects.define( "slide", "show", function( options, done ) {
3803    var startClip, startRef,
3804        element = $( this ),
3805        map = {
3806            up: [ "bottom", "top" ],
3807            down: [ "top", "bottom" ],
3808            left: [ "right", "left" ],
3809            right: [ "left", "right" ]
3810        },
3811        mode = options.mode,
3812        direction = options.direction || "left",
3813        ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
3814        positiveMotion = ( direction === "up" || direction === "left" ),
3815        distance = options.distance ||
3816            element[ ref === "top" ? "outerHeight" : "outerWidth" ]( true ),
3817        animation = {};
3818
3819    $.effects.createPlaceholder( element );
3820
3821    startClip = element.cssClip();
3822    startRef = element.position()[ ref ];
3823
3824    // Define hide animation
3825    animation[ ref ] = ( positiveMotion ? -1 : 1 ) * distance + startRef;
3826    animation.clip = element.cssClip();
3827    animation.clip[ map[ direction ][ 1 ] ] = animation.clip[ map[ direction ][ 0 ] ];
3828
3829    // Reverse the animation if we're showing
3830    if ( mode === "show" ) {
3831        element.cssClip( animation.clip );
3832        element.css( ref, animation[ ref ] );
3833        animation.clip = startClip;
3834        animation[ ref ] = startRef;
3835    }
3836
3837    // Actually animate
3838    element.animate( animation, {
3839        queue: false,
3840        duration: options.duration,
3841        easing: options.easing,
3842        complete: done
3843    } );
3844} );
3845
3846
3847/*!
3848 * jQuery UI Effects Transfer 1.12.1
3849 * http://jqueryui.com
3850 *
3851 * Copyright jQuery Foundation and other contributors
3852 * Released under the MIT license.
3853 * http://jquery.org/license
3854 */
3855
3856//>>label: Transfer Effect
3857//>>group: Effects
3858//>>description: Displays a transfer effect from one element to another.
3859//>>docs: http://api.jqueryui.com/transfer-effect/
3860//>>demos: http://jqueryui.com/effect/
3861
3862
3863
3864var effect;
3865if ( $.uiBackCompat !== false ) {
3866    effect = $.effects.define( "transfer", function( options, done ) {
3867        $( this ).transfer( options, done );
3868    } );
3869}
3870var effectsEffectTransfer = effect;
3871
3872
3873/*!
3874 * jQuery UI Focusable 1.12.1
3875 * http://jqueryui.com
3876 *
3877 * Copyright jQuery Foundation and other contributors
3878 * Released under the MIT license.
3879 * http://jquery.org/license
3880 */
3881
3882//>>label: :focusable Selector
vendor: 4,523 bytes, lines 3883-4037
3883//>>group: Core
3884//>>description: Selects elements which can be focused.
3885//>>docs: http://api.jqueryui.com/focusable-selector/
3886
3887
3888
3889// Selectors
3890$.ui.focusable = function( element, hasTabindex ) {
3891    var map, mapName, img, focusableIfVisible, fieldset,
3892        nodeName = element.nodeName.toLowerCase();
3893
3894    if ( "area" === nodeName ) {
3895        map = element.parentNode;
3896        mapName = map.name;
3897        if ( !element.href || !mapName || map.nodeName.toLowerCase() !== "map" ) {
3898            return false;
3899        }
3900        img = $( "img[usemap='#" + mapName + "']" );
3901        return img.length > 0 && img.is( ":visible" );
3902    }
3903
3904    if ( /^(input|select|textarea|button|object)$/.test( nodeName ) ) {
3905        focusableIfVisible = !element.disabled;
3906
3907        if ( focusableIfVisible ) {
3908
3909            // Form controls within a disabled fieldset are disabled.
3910            // However, controls within the fieldset's legend do not get disabled.
3911            // Since controls generally aren't placed inside legends, we skip
3912            // this portion of the check.
3913            fieldset = $( element ).closest( "fieldset" )[ 0 ];
3914            if ( fieldset ) {
3915                focusableIfVisible = !fieldset.disabled;
3916            }
3917        }
3918    } else if ( "a" === nodeName ) {
3919        focusableIfVisible = element.href || hasTabindex;
3920    } else {
3921        focusableIfVisible = hasTabindex;
3922    }
3923
3924    return focusableIfVisible && $( element ).is( ":visible" ) && visible( $( element ) );
3925};
3926
3927// Support: IE 8 only
3928// IE 8 doesn't resolve inherit to visible/hidden for computed values
3929function visible( element ) {
3930    var visibility = element.css( "visibility" );
3931    while ( visibility === "inherit" ) {
3932        element = element.parent();
3933        visibility = element.css( "visibility" );
3934    }
3935    return visibility !== "hidden";
3936}
3937
3938$.extend( $.expr[ ":" ], {
3939    focusable: function( element ) {
3940        return $.ui.focusable( element, $.attr( element, "tabindex" ) != null );
3941    }
3942} );
3943
3944var focusable = $.ui.focusable;
3945
3946
3947
3948
3949// Support: IE8 Only
3950// IE8 does not support the form attribute and when it is supplied. It overwrites the form prop
3951// with a string, so we need to find the proper form.
3952var form = $.fn.form = function() {
3953    return typeof this[ 0 ].form === "string" ? this.closest( "form" ) : $( this[ 0 ].form );
3954};
3955
3956
3957/*!
3958 * jQuery UI Form Reset Mixin 1.12.1
3959 * http://jqueryui.com
3960 *
3961 * Copyright jQuery Foundation and other contributors
3962 * Released under the MIT license.
3963 * http://jquery.org/license
3964 */
3965
3966//>>label: Form Reset Mixin
3967//>>group: Core
3968//>>description: Refresh input widgets when their form is reset
3969//>>docs: http://api.jqueryui.com/form-reset-mixin/
3970
3971
3972
3973var formResetMixin = $.ui.formResetMixin = {
3974    _formResetHandler: function() {
3975        var form = $( this );
3976
3977        // Wait for the form reset to actually happen before refreshing
3978        setTimeout( function() {
3979            var instances = form.data( "ui-form-reset-instances" );
3980            $.each( instances, function() {
3981                this.refresh();
3982            } );
3983        } );
3984    },
3985
3986    _bindFormResetHandler: function() {
3987        this.form = this.element.form();
3988        if ( !this.form.length ) {
3989            return;
3990        }
3991
3992        var instances = this.form.data( "ui-form-reset-instances" ) || [];
3993        if ( !instances.length ) {
3994
3995            // We don't use _on() here because we use a single event handler per form
3996            this.form.on( "reset.ui-form-reset", this._formResetHandler );
3997        }
3998        instances.push( this );
3999        this.form.data( "ui-form-reset-instances", instances );
4000    },
4001
4002    _unbindFormResetHandler: function() {
4003        if ( !this.form.length ) {
4004            return;
4005        }
4006
4007        var instances = this.form.data( "ui-form-reset-instances" );
4008        instances.splice( $.inArray( this, instances ), 1 );
4009        if ( instances.length ) {
4010            this.form.data( "ui-form-reset-instances", instances );
4011        } else {
4012            this.form
4013                .removeData( "ui-form-reset-instances" )
4014                .off( "reset.ui-form-reset" );
4015        }
4016    }
4017};
4018
4019
4020/*!
4021 * jQuery UI Support for jQuery core 1.7.x 1.12.1
4022 * http://jqueryui.com
4023 *
4024 * Copyright jQuery Foundation and other contributors
4025 * Released under the MIT license.
4026 * http://jquery.org/license
4027 *
4028 */
4029
4030//>>label: jQuery 1.7 Support
4031//>>group: Core
4032//>>description: Support version 1.7.x of jQuery core
4033
4034
4035
4036// Support: jQuery 1.7 only
4037// Not a great way to check versions, but since we only support 
vendor: 4,162 bytes, lines 4037-4179
40371.7+ and only
4038// need to detect <1.8, this is a simple check that should suffice. Checking
4039// for "1.7." would be a bit safer, but the version string is 1.7, not 1.7.0
4040// and we'll never reach 1.70.0 (if we do, we certainly won't be supporting
4041// 1.7 anymore). See #11197 for why we're not using feature detection.
4042if ( $.fn.jquery.substring( 0, 3 ) === "1.7" ) {
4043
4044    // Setters for .innerWidth(), .innerHeight(), .outerWidth(), .outerHeight()
4045    // Unlike jQuery Core 1.8+, these only support numeric values to set the
4046    // dimensions in pixels
4047    $.each( [ "Width", "Height" ], function( i, name ) {
4048        var side = name === "Width" ? [ "Left", "Right" ] : [ "Top", "Bottom" ],
4049            type = name.toLowerCase(),
4050            orig = {
4051                innerWidth: $.fn.innerWidth,
4052                innerHeight: $.fn.innerHeight,
4053                outerWidth: $.fn.outerWidth,
4054                outerHeight: $.fn.outerHeight
4055            };
4056
4057        function reduce( elem, size, border, margin ) {
4058            $.each( side, function() {
4059                size -= parseFloat( $.css( elem, "padding" + this ) ) || 0;
4060                if ( border ) {
4061                    size -= parseFloat( $.css( elem, "border" + this + "Width" ) ) || 0;
4062                }
4063                if ( margin ) {
4064                    size -= parseFloat( $.css( elem, "margin" + this ) ) || 0;
4065                }
4066            } );
4067            return size;
4068        }
4069
4070        $.fn[ "inner" + name ] = function( size ) {
4071            if ( size === undefined ) {
4072                return orig[ "inner" + name ].call( this );
4073            }
4074
4075            return this.each( function() {
4076                $( this ).css( type, reduce( this, size ) + "px" );
4077            } );
4078        };
4079
4080        $.fn[ "outer" + name ] = function( size, margin ) {
4081            if ( typeof size !== "number" ) {
4082                return orig[ "outer" + name ].call( this, size );
4083            }
4084
4085            return this.each( function() {
4086                $( this ).css( type, reduce( this, size, true, margin ) + "px" );
4087            } );
4088        };
4089    } );
4090
4091    $.fn.addBack = function( selector ) {
4092        return this.add( selector == null ?
4093            this.prevObject : this.prevObject.filter( selector )
4094        );
4095    };
4096}
4097
4098;
4099/*!
4100 * jQuery UI Keycode 1.12.1
4101 * http://jqueryui.com
4102 *
4103 * Copyright jQuery Foundation and other contributors
4104 * Released under the MIT license.
4105 * http://jquery.org/license
4106 */
4107
4108//>>label: Keycode
4109//>>group: Core
4110//>>description: Provide keycodes as keynames
4111//>>docs: http://api.jqueryui.com/jQuery.ui.keyCode/
4112
4113
4114var keycode = $.ui.keyCode = {
4115    BACKSPACE: 8,
4116    COMMA: 188,
4117    DELETE: 46,
4118    DOWN: 40,
4119    END: 35,
4120    ENTER: 13,
4121    ESCAPE: 27,
4122    HOME: 36,
4123    LEFT: 37,
4124    PAGE_DOWN: 34,
4125    PAGE_UP: 33,
4126    PERIOD: 190,
4127    RIGHT: 39,
4128    SPACE: 32,
4129    TAB: 9,
4130    UP: 38
4131};
4132
4133
4134
4135
4136// Internal use only
4137var escapeSelector = $.ui.escapeSelector = ( function() {
4138    var selectorEscape = /([!"#$%&'()*+,./:;<=>?@[\]^`{|}~])/g;
4139    return function( selector ) {
4140        return selector.replace( selectorEscape, "\\$1" );
4141    };
4142} )();
4143
4144
4145/*!
4146 * jQuery UI Labels 1.12.1
4147 * http://jqueryui.com
4148 *
4149 * Copyright jQuery Foundation and other contributors
4150 * Released under the MIT license.
4151 * http://jquery.org/license
4152 */
4153
4154//>>label: labels
4155//>>group: Core
4156//>>description: Find all the labels associated with a given input
4157//>>docs: http://api.jqueryui.com/labels/
4158
4159
4160
4161var labels = $.fn.labels = function() {
4162    var ancestor, selector, id, labels, ancestors;
4163
4164    // Check control.labels first
4165    if ( this[ 0 ].labels && this[ 0 ].labels.length ) {
4166        return this.pushStack( this[ 0 ].labels );
4167    }
4168
4169    // Support: IE <= 11, FF <= 37, Android <= 2.3 only
4170    // Above browsers do not support control.labels. Everything below is to support them
4171    // as well as document fragments. control.labels does not work on document fragments
4172    labels = this.eq( 0 ).parents( "label" );
4173
4174    // Look for the label based on the id
4175    id = this.attr( "id" );
4176    if ( id ) {
4177
4178        // We don't search against the document in case the element
4179        // is disconnected from the DOM
vendor: 4,594 bytes, lines 4180-4351
4180        ancestor = this.eq( 0 ).parents().last();
4181
4182        // Get a full set of top level ancestors
4183        ancestors = ancestor.add( ancestor.length ? ancestor.siblings() : this.siblings() );
4184
4185        // Create a selector for the label based on the id
4186        selector = "label[for='" + $.ui.escapeSelector( id ) + "']";
4187
4188        labels = labels.add( ancestors.find( selector ).addBack( selector ) );
4189
4190    }
4191
4192    // Return whatever we have found for labels
4193    return this.pushStack( labels );
4194};
4195
4196
4197/*!
4198 * jQuery UI Scroll Parent 1.12.1
4199 * http://jqueryui.com
4200 *
4201 * Copyright jQuery Foundation and other contributors
4202 * Released under the MIT license.
4203 * http://jquery.org/license
4204 */
4205
4206//>>label: scrollParent
4207//>>group: Core
4208//>>description: Get the closest ancestor element that is scrollable.
4209//>>docs: http://api.jqueryui.com/scrollParent/
4210
4211
4212
4213var scrollParent = $.fn.scrollParent = function( includeHidden ) {
4214    var position = this.css( "position" ),
4215        excludeStaticParent = position === "absolute",
4216        overflowRegex = includeHidden ? /(auto|scroll|hidden)/ : /(auto|scroll)/,
4217        scrollParent = this.parents().filter( function() {
4218            var parent = $( this );
4219            if ( excludeStaticParent && parent.css( "position" ) === "static" ) {
4220                return false;
4221            }
4222            return overflowRegex.test( parent.css( "overflow" ) + parent.css( "overflow-y" ) +
4223                parent.css( "overflow-x" ) );
4224        } ).eq( 0 );
4225
4226    return position === "fixed" || !scrollParent.length ?
4227        $( this[ 0 ].ownerDocument || document ) :
4228        scrollParent;
4229};
4230
4231
4232/*!
4233 * jQuery UI Tabbable 1.12.1
4234 * http://jqueryui.com
4235 *
4236 * Copyright jQuery Foundation and other contributors
4237 * Released under the MIT license.
4238 * http://jquery.org/license
4239 */
4240
4241//>>label: :tabbable Selector
4242//>>group: Core
4243//>>description: Selects elements which can be tabbed to.
4244//>>docs: http://api.jqueryui.com/tabbable-selector/
4245
4246
4247
4248var tabbable = $.extend( $.expr[ ":" ], {
4249    tabbable: function( element ) {
4250        var tabIndex = $.attr( element, "tabindex" ),
4251            hasTabindex = tabIndex != null;
4252        return ( !hasTabindex || tabIndex >= 0 ) && $.ui.focusable( element, hasTabindex );
4253    }
4254} );
4255
4256
4257/*!
4258 * jQuery UI Unique ID 1.12.1
4259 * http://jqueryui.com
4260 *
4261 * Copyright jQuery Foundation and other contributors
4262 * Released under the MIT license.
4263 * http://jquery.org/license
4264 */
4265
4266//>>label: uniqueId
4267//>>group: Core
4268//>>description: Functions to generate and remove uniqueId's
4269//>>docs: http://api.jqueryui.com/uniqueId/
4270
4271
4272
4273var uniqueId = $.fn.extend( {
4274    uniqueId: ( function() {
4275        var uuid = 0;
4276
4277        return function() {
4278            return this.each( function() {
4279                if ( !this.id ) {
4280                    this.id = "ui-id-" + ( ++uuid );
4281                }
4282            } );
4283        };
4284    } )(),
4285
4286    removeUniqueId: function() {
4287        return this.each( function() {
4288            if ( /^ui-id-\d+$/.test( this.id ) ) {
4289                $( this ).removeAttr( "id" );
4290            }
4291        } );
4292    }
4293} );
4294
4295
4296/*!
4297 * jQuery UI Accordion 1.12.1
4298 * http://jqueryui.com
4299 *
4300 * Copyright jQuery Foundation and other contributors
4301 * Released under the MIT license.
4302 * http://jquery.org/license
4303 */
4304
4305//>>label: Accordion
4306//>>group: Widgets
4307// jscs:disable maximumLineLength
4308//>>description: Displays collapsible content panels for presenting information in a limited amount of space.
4309// jscs:enable maximumLineLength
4310//>>docs: http://api.jqueryui.com/accordion/
4311//>>demos: http://jqueryui.com/accordion/
4312//>>css.structure: ../../themes/base/core.css
4313//>>css.structure: ../../themes/base/accordion.css
4314//>>css.theme: ../../themes/base/theme.css
4315
4316
4317
4318var widgetsAccordion = $.widget( "ui.accordion", {
4319    version: "1.12.1",
4320    options: {
4321        active: 0,
4322        animate: {},
4323        classes: {
4324            "ui-accordion-header": "ui-corner-top",
4325            "ui-accordion-header-collapsed": "ui-corner-all",
4326            "ui-accordion-content": "ui-corner-bottom"
4327        },
4328        collapsible: false,
4329        event: "click",
4330        header: "> li > :first-child, > :not(li):even",
4331        heightStyle: "auto",
4332        icons: {
4333            activeHeader: "ui-icon-triangle-1-s",
4334            header: "ui-icon-triangle-1-e"
4335        },
4336
4337        // Callbacks
4338        activate: null,
4339        beforeActivate: null
4340    },
4341
4342    hideProps: {
4343        borderTopWidth: "hide",
4344        borderBottomWidth: "hide",
4345        paddingTop: "hide",
4346        paddingBottom: "hide",
4347        height: "hide"
4348    },
4349
4350    showProps: {
4351        borderTopWidth: "show",
vendor: 5,261 bytes, lines 4352-4525
4352        borderBottomWidth: "show",
4353        paddingTop: "show",
4354        paddingBottom: "show",
4355        height: "show"
4356    },
4357
4358    _create: function() {
4359        var options = this.options;
4360
4361        this.prevShow = this.prevHide = $();
4362        this._addClass( "ui-accordion", "ui-widget ui-helper-reset" );
4363        this.element.attr( "role", "tablist" );
4364
4365        // Don't allow collapsible: false and active: false / null
4366        if ( !options.collapsible && ( options.active === false || options.active == null ) ) {
4367            options.active = 0;
4368        }
4369
4370        this._processPanels();
4371
4372        // handle negative values
4373        if ( options.active < 0 ) {
4374            options.active += this.headers.length;
4375        }
4376        this._refresh();
4377    },
4378
4379    _getCreateEventData: function() {
4380        return {
4381            header: this.active,
4382            panel: !this.active.length ? $() : this.active.next()
4383        };
4384    },
4385
4386    _createIcons: function() {
4387        var icon, children,
4388            icons = this.options.icons;
4389
4390        if ( icons ) {
4391            icon = $( "<span>" );
4392            this._addClass( icon, "ui-accordion-header-icon", "ui-icon " + icons.header );
4393            icon.prependTo( this.headers );
4394            children = this.active.children( ".ui-accordion-header-icon" );
4395            this._removeClass( children, icons.header )
4396                ._addClass( children, null, icons.activeHeader )
4397                ._addClass( this.headers, "ui-accordion-icons" );
4398        }
4399    },
4400
4401    _destroyIcons: function() {
4402        this._removeClass( this.headers, "ui-accordion-icons" );
4403        this.headers.children( ".ui-accordion-header-icon" ).remove();
4404    },
4405
4406    _destroy: function() {
4407        var contents;
4408
4409        // Clean up main element
4410        this.element.removeAttr( "role" );
4411
4412        // Clean up headers
4413        this.headers
4414            .removeAttr( "role aria-expanded aria-selected aria-controls tabIndex" )
4415            .removeUniqueId();
4416
4417        this._destroyIcons();
4418
4419        // Clean up content panels
4420        contents = this.headers.next()
4421            .css( "display", "" )
4422            .removeAttr( "role aria-hidden aria-labelledby" )
4423            .removeUniqueId();
4424
4425        if ( this.options.heightStyle !== "content" ) {
4426            contents.css( "height", "" );
4427        }
4428    },
4429
4430    _setOption: function( key, value ) {
4431        if ( key === "active" ) {
4432
4433            // _activate() will handle invalid values and update this.options
4434            this._activate( value );
4435            return;
4436        }
4437
4438        if ( key === "event" ) {
4439            if ( this.options.event ) {
4440                this._off( this.headers, this.options.event );
4441            }
4442            this._setupEvents( value );
4443        }
4444
4445        this._super( key, value );
4446
4447        // Setting collapsible: false while collapsed; open first panel
4448        if ( key === "collapsible" && !value && this.options.active === false ) {
4449            this._activate( 0 );
4450        }
4451
4452        if ( key === "icons" ) {
4453            this._destroyIcons();
4454            if ( value ) {
4455                this._createIcons();
4456            }
4457        }
4458    },
4459
4460    _setOptionDisabled: function( value ) {
4461        this._super( value );
4462
4463        this.element.attr( "aria-disabled", value );
4464
4465        // Support: IE8 Only
4466        // #5332 / #6059 - opacity doesn't cascade to positioned elements in IE
4467        // so we need to add the disabled class to the headers and panels
4468        this._toggleClass( null, "ui-state-disabled", !!value );
4469        this._toggleClass( this.headers.add( this.headers.next() ), null, "ui-state-disabled",
4470            !!value );
4471    },
4472
4473    _keydown: function( event ) {
4474        if ( event.altKey || event.ctrlKey ) {
4475            return;
4476        }
4477
4478        var keyCode = $.ui.keyCode,
4479            length = this.headers.length,
4480            currentIndex = this.headers.index( event.target ),
4481            toFocus = false;
4482
4483        switch ( event.keyCode ) {
4484        case keyCode.RIGHT:
4485        case keyCode.DOWN:
4486            toFocus = this.headers[ ( currentIndex + 1 ) % length ];
4487            break;
4488        case keyCode.LEFT:
4489        case keyCode.UP:
4490            toFocus = this.headers[ ( currentIndex - 1 + length ) % length ];
4491            break;
4492        case keyCode.SPACE:
4493        case keyCode.ENTER:
4494            this._eventHandler( event );
4495            break;
4496        case keyCode.HOME:
4497            toFocus = this.headers[ 0 ];
4498            break;
4499        case keyCode.END:
4500            toFocus = this.headers[ length - 1 ];
4501            break;
4502        }
4503
4504        if ( toFocus ) {
4505            $( event.target ).attr( "tabIndex", -1 );
4506            $( toFocus ).attr( "tabIndex", 0 );
4507            $( toFocus ).trigger( "focus" );
4508            event.preventDefault();
4509        }
4510    },
4511
4512    _panelKeyDown: function( event ) {
4513        if ( event.keyCode === $.ui.keyCode.UP && event.ctrlKey ) {
4514            $( event.currentTarget ).prev().trigger( "focus" );
4515        }
4516    },
4517
4518    refresh: function() {
4519        var options = this.options;
4520        this._processPanels();
4521
4522        // Was collapsed or no panel
4523        if ( ( options.active === false && options.collapsible === true ) ||
4524                !this.headers.length ) {
4525            options.active = false;
vendor: 6,393 bytes, lines 4526-4715
4526            this.active = $();
4527
4528        // active false only when collapsible is true
4529        } else if ( options.active === false ) {
4530            this._activate( 0 );
4531
4532        // was active, but active panel is gone
4533        } else if ( this.active.length && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {
4534
4535            // all remaining panel are disabled
4536            if ( this.headers.length === this.headers.find( ".ui-state-disabled" ).length ) {
4537                options.active = false;
4538                this.active = $();
4539
4540            // activate previous panel
4541            } else {
4542                this._activate( Math.max( 0, options.active - 1 ) );
4543            }
4544
4545        // was active, active panel still exists
4546        } else {
4547
4548            // make sure active index is correct
4549            options.active = this.headers.index( this.active );
4550        }
4551
4552        this._destroyIcons();
4553
4554        this._refresh();
4555    },
4556
4557    _processPanels: function() {
4558        var prevHeaders = this.headers,
4559            prevPanels = this.panels;
4560
4561        this.headers = this.element.find( this.options.header );
4562        this._addClass( this.headers, "ui-accordion-header ui-accordion-header-collapsed",
4563            "ui-state-default" );
4564
4565        this.panels = this.headers.next().filter( ":not(.ui-accordion-content-active)" ).hide();
4566        this._addClass( this.panels, "ui-accordion-content", "ui-helper-reset ui-widget-content" );
4567
4568        // Avoid memory leaks (#10056)
4569        if ( prevPanels ) {
4570            this._off( prevHeaders.not( this.headers ) );
4571            this._off( prevPanels.not( this.panels ) );
4572        }
4573    },
4574
4575    _refresh: function() {
4576        var maxHeight,
4577            options = this.options,
4578            heightStyle = options.heightStyle,
4579            parent = this.element.parent();
4580
4581        this.active = this._findActive( options.active );
4582        this._addClass( this.active, "ui-accordion-header-active", "ui-state-active" )
4583            ._removeClass( this.active, "ui-accordion-header-collapsed" );
4584        this._addClass( this.active.next(), "ui-accordion-content-active" );
4585        this.active.next().show();
4586
4587        this.headers
4588            .attr( "role", "tab" )
4589            .each( function() {
4590                var header = $( this ),
4591                    headerId = header.uniqueId().attr( "id" ),
4592                    panel = header.next(),
4593                    panelId = panel.uniqueId().attr( "id" );
4594                header.attr( "aria-controls", panelId );
4595                panel.attr( "aria-labelledby", headerId );
4596            } )
4597            .next()
4598                .attr( "role", "tabpanel" );
4599
4600        this.headers
4601            .not( this.active )
4602                .attr( {
4603                    "aria-selected": "false",
4604                    "aria-expanded": "false",
4605                    tabIndex: -1
4606                } )
4607                .next()
4608                    .attr( {
4609                        "aria-hidden": "true"
4610                    } )
4611                    .hide();
4612
4613        // Make sure at least one header is in the tab order
4614        if ( !this.active.length ) {
4615            this.headers.eq( 0 ).attr( "tabIndex", 0 );
4616        } else {
4617            this.active.attr( {
4618                "aria-selected": "true",
4619                "aria-expanded": "true",
4620                tabIndex: 0
4621            } )
4622                .next()
4623                    .attr( {
4624                        "aria-hidden": "false"
4625                    } );
4626        }
4627
4628        this._createIcons();
4629
4630        this._setupEvents( options.event );
4631
4632        if ( heightStyle === "fill" ) {
4633            maxHeight = parent.height();
4634            this.element.siblings( ":visible" ).each( function() {
4635                var elem = $( this ),
4636                    position = elem.css( "position" );
4637
4638                if ( position === "absolute" || position === "fixed" ) {
4639                    return;
4640                }
4641                maxHeight -= elem.outerHeight( true );
4642            } );
4643
4644            this.headers.each( function() {
4645                maxHeight -= $( this ).outerHeight( true );
4646            } );
4647
4648            this.headers.next()
4649                .each( function() {
4650                    $( this ).height( Math.max( 0, maxHeight -
4651                        $( this ).innerHeight() + $( this ).height() ) );
4652                } )
4653                .css( "overflow", "auto" );
4654        } else if ( heightStyle === "auto" ) {
4655            maxHeight = 0;
4656            this.headers.next()
4657                .each( function() {
4658                    var isVisible = $( this ).is( ":visible" );
4659                    if ( !isVisible ) {
4660                        $( this ).show();
4661                    }
4662                    maxHeight = Math.max( maxHeight, $( this ).css( "height", "" ).height() );
4663                    if ( !isVisible ) {
4664                        $( this ).hide();
4665                    }
4666                } )
4667                .height( maxHeight );
4668        }
4669    },
4670
4671    _activate: function( index ) {
4672        var active = this._findActive( index )[ 0 ];
4673
4674        // Trying to activate the already active panel
4675        if ( active === this.active[ 0 ] ) {
4676            return;
4677        }
4678
4679        // Trying to collapse, simulate a click on the currently active header
4680        active = active || this.active[ 0 ];
4681
4682        this._eventHandler( {
4683            target: active,
4684            currentTarget: active,
4685            preventDefault: $.noop
4686        } );
4687    },
4688
4689    _findActive: function( selector ) {
4690        return typeof selector === "number" ? this.headers.eq( selector ) : $();
4691    },
4692
4693    _setupEvents: function( event ) {
4694        var events = {
4695            keydown: "_keydown"
4696        };
4697        if ( event ) {
4698            $.each( event.split( " " ), function( index, eventName ) {
4699                events[ eventName ] = "_eventHandler";
4700            } );
4701        }
4702
4703        this._off( this.headers.add( this.headers.next() ) );
4704        this._on( this.headers, events );
4705        this._on( this.headers.next(), { keydown: "_panelKeyDown" } );
4706        this._hoverable( this.headers );
4707        this._focusable( this.headers );
4708    },
4709
4710    _eventHandler: function( event ) {
4711        var activeChildren, clickedChildren,
4712            options = this.options,
4713            active = this.active,
4714            clicked = $( event.currentTarget ),
4715            clickedIsActive = clicked[ 0 ] === active[ 0 ],
vendor: 6,459 bytes, lines 4716-4896
4716            collapsing = clickedIsActive && options.collapsible,
4717            toShow = collapsing ? $() : clicked.next(),
4718            toHide = active.next(),
4719            eventData = {
4720                oldHeader: active,
4721                oldPanel: toHide,
4722                newHeader: collapsing ? $() : clicked,
4723                newPanel: toShow
4724            };
4725
4726        event.preventDefault();
4727
4728        if (
4729
4730                // click on active header, but not collapsible
4731                ( clickedIsActive && !options.collapsible ) ||
4732
4733                // allow canceling activation
4734                ( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
4735            return;
4736        }
4737
4738        options.active = collapsing ? false : this.headers.index( clicked );
4739
4740        // When the call to ._toggle() comes after the class changes
4741        // it causes a very odd bug in IE 8 (see #6720)
4742        this.active = clickedIsActive ? $() : clicked;
4743        this._toggle( eventData );
4744
4745        // Switch classes
4746        // corner classes on the previously active header stay after the animation
4747        this._removeClass( active, "ui-accordion-header-active", "ui-state-active" );
4748        if ( options.icons ) {
4749            activeChildren = active.children( ".ui-accordion-header-icon" );
4750            this._removeClass( activeChildren, null, options.icons.activeHeader )
4751                ._addClass( activeChildren, null, options.icons.header );
4752        }
4753
4754        if ( !clickedIsActive ) {
4755            this._removeClass( clicked, "ui-accordion-header-collapsed" )
4756                ._addClass( clicked, "ui-accordion-header-active", "ui-state-active" );
4757            if ( options.icons ) {
4758                clickedChildren = clicked.children( ".ui-accordion-header-icon" );
4759                this._removeClass( clickedChildren, null, options.icons.header )
4760                    ._addClass( clickedChildren, null, options.icons.activeHeader );
4761            }
4762
4763            this._addClass( clicked.next(), "ui-accordion-content-active" );
4764        }
4765    },
4766
4767    _toggle: function( data ) {
4768        var toShow = data.newPanel,
4769            toHide = this.prevShow.length ? this.prevShow : data.oldPanel;
4770
4771        // Handle activating a panel during the animation for another activation
4772        this.prevShow.add( this.prevHide ).stop( true, true );
4773        this.prevShow = toShow;
4774        this.prevHide = toHide;
4775
4776        if ( this.options.animate ) {
4777            this._animate( toShow, toHide, data );
4778        } else {
4779            toHide.hide();
4780            toShow.show();
4781            this._toggleComplete( data );
4782        }
4783
4784        toHide.attr( {
4785            "aria-hidden": "true"
4786        } );
4787        toHide.prev().attr( {
4788            "aria-selected": "false",
4789            "aria-expanded": "false"
4790        } );
4791
4792        // if we're switching panels, remove the old header from the tab order
4793        // if we're opening from collapsed state, remove the previous header from the tab order
4794        // if we're collapsing, then keep the collapsing header in the tab order
4795        if ( toShow.length && toHide.length ) {
4796            toHide.prev().attr( {
4797                "tabIndex": -1,
4798                "aria-expanded": "false"
4799            } );
4800        } else if ( toShow.length ) {
4801            this.headers.filter( function() {
4802                return parseInt( $( this ).attr( "tabIndex" ), 10 ) === 0;
4803            } )
4804                .attr( "tabIndex", -1 );
4805        }
4806
4807        toShow
4808            .attr( "aria-hidden", "false" )
4809            .prev()
4810                .attr( {
4811                    "aria-selected": "true",
4812                    "aria-expanded": "true",
4813                    tabIndex: 0
4814                } );
4815    },
4816
4817    _animate: function( toShow, toHide, data ) {
4818        var total, easing, duration,
4819            that = this,
4820            adjust = 0,
4821            boxSizing = toShow.css( "box-sizing" ),
4822            down = toShow.length &&
4823                ( !toHide.length || ( toShow.index() < toHide.index() ) ),
4824            animate = this.options.animate || {},
4825            options = down && animate.down || animate,
4826            complete = function() {
4827                that._toggleComplete( data );
4828            };
4829
4830        if ( typeof options === "number" ) {
4831            duration = options;
4832        }
4833        if ( typeof options === "string" ) {
4834            easing = options;
4835        }
4836
4837        // fall back from options to animation in case of partial down settings
4838        easing = easing || options.easing || animate.easing;
4839        duration = duration || options.duration || animate.duration;
4840
4841        if ( !toHide.length ) {
4842            return toShow.animate( this.showProps, duration, easing, complete );
4843        }
4844        if ( !toShow.length ) {
4845            return toHide.animate( this.hideProps, duration, easing, complete );
4846        }
4847
4848        total = toShow.show().outerHeight();
4849        toHide.animate( this.hideProps, {
4850            duration: duration,
4851            easing: easing,
4852            step: function( now, fx ) {
4853                fx.now = Math.round( now );
4854            }
4855        } );
4856        toShow
4857            .hide()
4858            .animate( this.showProps, {
4859                duration: duration,
4860                easing: easing,
4861                complete: complete,
4862                step: function( now, fx ) {
4863                    fx.now = Math.round( now );
4864                    if ( fx.prop !== "height" ) {
4865                        if ( boxSizing === "content-box" ) {
4866                            adjust += fx.now;
4867                        }
4868                    } else if ( that.options.heightStyle !== "content" ) {
4869                        fx.now = Math.round( total - toHide.outerHeight() - adjust );
4870                        adjust = 0;
4871                    }
4872                }
4873            } );
4874    },
4875
4876    _toggleComplete: function( data ) {
4877        var toHide = data.oldPanel,
4878            prev = toHide.prev();
4879
4880        this._removeClass( toHide, "ui-accordion-content-active" );
4881        this._removeClass( prev, "ui-accordion-header-active" )
4882            ._addClass( prev, "ui-accordion-header-collapsed" );
4883
4884        // Work around for rendering bug in IE (#5421)
4885        if ( toHide.length ) {
4886            toHide.parent()[ 0 ].className = toHide.parent()[ 0 ].className;
4887        }
4888        this._trigger( "activate", null, data );
4889    }
4890} );
4891
4892
4893
4894var safeActiveElement = $.ui.safeActiveElement = function( document ) {
4895    var activeElement;
4896
vendor: 5,437 bytes, lines 4897-5052
4897    // Support: IE 9 only
4898    // IE9 throws an "Unspecified error" accessing document.activeElement from an <iframe>
4899    try {
4900        activeElement = document.activeElement;
4901    } catch ( error ) {
4902        activeElement = document.body;
4903    }
4904
4905    // Support: IE 9 - 11 only
4906    // IE may return null instead of an element
4907    // Interestingly, this only seems to occur when NOT in an iframe
4908    if ( !activeElement ) {
4909        activeElement = document.body;
4910    }
4911
4912    // Support: IE 11 only
4913    // IE11 returns a seemingly empty object in some cases when accessing
4914    // document.activeElement from an <iframe>
4915    if ( !activeElement.nodeName ) {
4916        activeElement = document.body;
4917    }
4918
4919    return activeElement;
4920};
4921
4922
4923/*!
4924 * jQuery UI Menu 1.12.1
4925 * http://jqueryui.com
4926 *
4927 * Copyright jQuery Foundation and other contributors
4928 * Released under the MIT license.
4929 * http://jquery.org/license
4930 */
4931
4932//>>label: Menu
4933//>>group: Widgets
4934//>>description: Creates nestable menus.
4935//>>docs: http://api.jqueryui.com/menu/
4936//>>demos: http://jqueryui.com/menu/
4937//>>css.structure: ../../themes/base/core.css
4938//>>css.structure: ../../themes/base/menu.css
4939//>>css.theme: ../../themes/base/theme.css
4940
4941
4942
4943var widgetsMenu = $.widget( "ui.menu", {
4944    version: "1.12.1",
4945    defaultElement: "<ul>",
4946    delay: 300,
4947    options: {
4948        icons: {
4949            submenu: "ui-icon-caret-1-e"
4950        },
4951        items: "> *",
4952        menus: "ul",
4953        position: {
4954            my: "left top",
4955            at: "right top"
4956        },
4957        role: "menu",
4958
4959        // Callbacks
4960        blur: null,
4961        focus: null,
4962        select: null
4963    },
4964
4965    _create: function() {
4966        this.activeMenu = this.element;
4967
4968        // Flag used to prevent firing of the click handler
4969        // as the event bubbles up through nested menus
4970        this.mouseHandled = false;
4971        this.element
4972            .uniqueId()
4973            .attr( {
4974                role: this.options.role,
4975                tabIndex: 0
4976            } );
4977
4978        this._addClass( "ui-menu", "ui-widget ui-widget-content" );
4979        this._on( {
4980
4981            // Prevent focus from sticking to links inside menu after clicking
4982            // them (focus should always stay on UL during navigation).
4983            "mousedown .ui-menu-item": function( event ) {
4984                event.preventDefault();
4985            },
4986            "click .ui-menu-item": function( event ) {
4987                var target = $( event.target );
4988                var active = $( $.ui.safeActiveElement( this.document[ 0 ] ) );
4989                if ( !this.mouseHandled && target.not( ".ui-state-disabled" ).length ) {
4990                    this.select( event );
4991
4992                    // Only set the mouseHandled flag if the event will bubble, see #9469.
4993                    if ( !event.isPropagationStopped() ) {
4994                        this.mouseHandled = true;
4995                    }
4996
4997                    // Open submenu on click
4998                    if ( target.has( ".ui-menu" ).length ) {
4999                        this.expand( event );
5000                    } else if ( !this.element.is( ":focus" ) &&
5001                            active.closest( ".ui-menu" ).length ) {
5002
5003                        // Redirect focus to the menu
5004                        this.element.trigger( "focus", [ true ] );
5005
5006                        // If the active item is on the top level, let it stay active.
5007                        // Otherwise, blur the active item since it is no longer visible.
5008                        if ( this.active && this.active.parents( ".ui-menu" ).length === 1 ) {
5009                            clearTimeout( this.timer );
5010                        }
5011                    }
5012                }
5013            },
5014            "mouseenter .ui-menu-item": function( event ) {
5015
5016                // Ignore mouse events while typeahead is active, see #10458.
5017                // Prevents focusing the wrong item when typeahead causes a scroll while the mouse
5018                // is over an item in the menu
5019                if ( this.previousFilter ) {
5020                    return;
5021                }
5022
5023                var actualTarget = $( event.target ).closest( ".ui-menu-item" ),
5024                    target = $( event.currentTarget );
5025
5026                // Ignore bubbled events on parent items, see #11641
5027                if ( actualTarget[ 0 ] !== target[ 0 ] ) {
5028                    return;
5029                }
5030
5031                // Remove ui-state-active class from siblings of the newly focused menu item
5032                // to avoid a jump caused by adjacent elements both having a class with a border
5033                this._removeClass( target.siblings().children( ".ui-state-active" ),
5034                    null, "ui-state-active" );
5035                this.focus( event, target );
5036            },
5037            mouseleave: "collapseAll",
5038            "mouseleave .ui-menu": "collapseAll",
5039            focus: function( event, keepActiveItem ) {
5040
5041                // If there's already an active item, keep it active
5042                // If not, activate the first item
5043                var item = this.active || this.element.find( this.options.items ).eq( 0 );
5044
5045                if ( !keepActiveItem ) {
5046                    this.focus( event, item );
5047                }
5048            },
5049            blur: function( event ) {
5050                this._delay( function() {
5051                    var notContained = !$.contains(
5052                        this.element[ 0 ],
vendor: 2,769 bytes, lines 5053-5141
5053                        $.ui.safeActiveElement( this.document[ 0 ] )
5054                    );
5055                    if ( notContained ) {
5056                        this.collapseAll( event );
5057                    }
5058                } );
5059            },
5060            keydown: "_keydown"
5061        } );
5062
5063        this.refresh();
5064
5065        // Clicks outside of a menu collapse any open menus
5066        this._on( this.document, {
5067            click: function( event ) {
5068                if ( this._closeOnDocumentClick( event ) ) {
5069                    this.collapseAll( event );
5070                }
5071
5072                // Reset the mouseHandled flag
5073                this.mouseHandled = false;
5074            }
5075        } );
5076    },
5077
5078    _destroy: function() {
5079        var items = this.element.find( ".ui-menu-item" )
5080                .removeAttr( "role aria-disabled" ),
5081            submenus = items.children( ".ui-menu-item-wrapper" )
5082                .removeUniqueId()
5083                .removeAttr( "tabIndex role aria-haspopup" );
5084
5085        // Destroy (sub)menus
5086        this.element
5087            .removeAttr( "aria-activedescendant" )
5088            .find( ".ui-menu" ).addBack()
5089                .removeAttr( "role aria-labelledby aria-expanded aria-hidden aria-disabled " +
5090                    "tabIndex" )
5091                .removeUniqueId()
5092                .show();
5093
5094        submenus.children().each( function() {
5095            var elem = $( this );
5096            if ( elem.data( "ui-menu-submenu-caret" ) ) {
5097                elem.remove();
5098            }
5099        } );
5100    },
5101
5102    _keydown: function( event ) {
5103        var match, prev, character, skip,
5104            preventDefault = true;
5105
5106        switch ( event.keyCode ) {
5107        case $.ui.keyCode.PAGE_UP:
5108            this.previousPage( event );
5109            break;
5110        case $.ui.keyCode.PAGE_DOWN:
5111            this.nextPage( event );
5112            break;
5113        case $.ui.keyCode.HOME:
5114            this._move( "first", "first", event );
5115            break;
5116        case $.ui.keyCode.END:
5117            this._move( "last", "last", event );
5118            break;
5119        case $.ui.keyCode.UP:
5120            this.previous( event );
5121            break;
5122        case $.ui.keyCode.DOWN:
5123            this.next( event );
5124            break;
5125        case $.ui.keyCode.LEFT:
5126            this.collapse( event );
5127            break;
5128        case $.ui.keyCode.RIGHT:
5129            if ( this.active && !this.active.is( ".ui-state-disabled" ) ) {
5130                this.expand( event );
5131            }
5132            break;
5133        case $.ui.keyCode.ENTER:
5134        case $.ui.keyCode.SPACE:
5135            this._activate( event );
5136            break;
5137        case $.ui.keyCode.ESCAPE:
5138            this.collapse( event );
5139            break;
5140        default:
5141            preventDefault = false;
vendor: 8,611 bytes, lines 5142-5391
5142            prev = this.previousFilter || "";
5143            skip = false;
5144
5145            // Support number pad values
5146            character = event.keyCode >= 96 && event.keyCode <= 105 ?
5147                ( event.keyCode - 96 ).toString() : String.fromCharCode( event.keyCode );
5148
5149            clearTimeout( this.filterTimer );
5150
5151            if ( character === prev ) {
5152                skip = true;
5153            } else {
5154                character = prev + character;
5155            }
5156
5157            match = this._filterMenuItems( character );
5158            match = skip && match.index( this.active.next() ) !== -1 ?
5159                this.active.nextAll( ".ui-menu-item" ) :
5160                match;
5161
5162            // If no matches on the current filter, reset to the last character pressed
5163            // to move down the menu to the first item that starts with that character
5164            if ( !match.length ) {
5165                character = String.fromCharCode( event.keyCode );
5166                match = this._filterMenuItems( character );
5167            }
5168
5169            if ( match.length ) {
5170                this.focus( event, match );
5171                this.previousFilter = character;
5172                this.filterTimer = this._delay( function() {
5173                    delete this.previousFilter;
5174                }, 1000 );
5175            } else {
5176                delete this.previousFilter;
5177            }
5178        }
5179
5180        if ( preventDefault ) {
5181            event.preventDefault();
5182        }
5183    },
5184
5185    _activate: function( event ) {
5186        if ( this.active && !this.active.is( ".ui-state-disabled" ) ) {
5187            if ( this.active.children( "[aria-haspopup='true']" ).length ) {
5188                this.expand( event );
5189            } else {
5190                this.select( event );
5191            }
5192        }
5193    },
5194
5195    refresh: function() {
5196        var menus, items, newSubmenus, newItems, newWrappers,
5197            that = this,
5198            icon = this.options.icons.submenu,
5199            submenus = this.element.find( this.options.menus );
5200
5201        this._toggleClass( "ui-menu-icons", null, !!this.element.find( ".ui-icon" ).length );
5202
5203        // Initialize nested menus
5204        newSubmenus = submenus.filter( ":not(.ui-menu)" )
5205            .hide()
5206            .attr( {
5207                role: this.options.role,
5208                "aria-hidden": "true",
5209                "aria-expanded": "false"
5210            } )
5211            .each( function() {
5212                var menu = $( this ),
5213                    item = menu.prev(),
5214                    submenuCaret = $( "<span>" ).data( "ui-menu-submenu-caret", true );
5215
5216                that._addClass( submenuCaret, "ui-menu-icon", "ui-icon " + icon );
5217                item
5218                    .attr( "aria-haspopup", "true" )
5219                    .prepend( submenuCaret );
5220                menu.attr( "aria-labelledby", item.attr( "id" ) );
5221            } );
5222
5223        this._addClass( newSubmenus, "ui-menu", "ui-widget ui-widget-content ui-front" );
5224
5225        menus = submenus.add( this.element );
5226        items = menus.find( this.options.items );
5227
5228        // Initialize menu-items containing spaces and/or dashes only as dividers
5229        items.not( ".ui-menu-item" ).each( function() {
5230            var item = $( this );
5231            if ( that._isDivider( item ) ) {
5232                that._addClass( item, "ui-menu-divider", "ui-widget-content" );
5233            }
5234        } );
5235
5236        // Don't refresh list items that are already adapted
5237        newItems = items.not( ".ui-menu-item, .ui-menu-divider" );
5238        newWrappers = newItems.children()
5239            .not( ".ui-menu" )
5240                .uniqueId()
5241                .attr( {
5242                    tabIndex: -1,
5243                    role: this._itemRole()
5244                } );
5245        this._addClass( newItems, "ui-menu-item" )
5246            ._addClass( newWrappers, "ui-menu-item-wrapper" );
5247
5248        // Add aria-disabled attribute to any disabled menu item
5249        items.filter( ".ui-state-disabled" ).attr( "aria-disabled", "true" );
5250
5251        // If the active item has been removed, blur the menu
5252        if ( this.active && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {
5253            this.blur();
5254        }
5255    },
5256
5257    _itemRole: function() {
5258        return {
5259            menu: "menuitem",
5260            listbox: "option"
5261        }[ this.options.role ];
5262    },
5263
5264    _setOption: function( key, value ) {
5265        if ( key === "icons" ) {
5266            var icons = this.element.find( ".ui-menu-icon" );
5267            this._removeClass( icons, null, this.options.icons.submenu )
5268                ._addClass( icons, null, value.submenu );
5269        }
5270        this._super( key, value );
5271    },
5272
5273    _setOptionDisabled: function( value ) {
5274        this._super( value );
5275
5276        this.element.attr( "aria-disabled", String( value ) );
5277        this._toggleClass( null, "ui-state-disabled", !!value );
5278    },
5279
5280    focus: function( event, item ) {
5281        var nested, focused, activeParent;
5282        this.blur( event, event && event.type === "focus" );
5283
5284        this._scrollIntoView( item );
5285
5286        this.active = item.first();
5287
5288        focused = this.active.children( ".ui-menu-item-wrapper" );
5289        this._addClass( focused, null, "ui-state-active" );
5290
5291        // Only update aria-activedescendant if there's a role
5292        // otherwise we assume focus is managed elsewhere
5293        if ( this.options.role ) {
5294            this.element.attr( "aria-activedescendant", focused.attr( "id" ) );
5295        }
5296
5297        // Highlight active parent menu item, if any
5298        activeParent = this.active
5299            .parent()
5300                .closest( ".ui-menu-item" )
5301                    .children( ".ui-menu-item-wrapper" );
5302        this._addClass( activeParent, null, "ui-state-active" );
5303
5304        if ( event && event.type === "keydown" ) {
5305            this._close();
5306        } else {
5307            this.timer = this._delay( function() {
5308                this._close();
5309            }, this.delay );
5310        }
5311
5312        nested = item.children( ".ui-menu" );
5313        if ( nested.length && event && ( /^mouse/.test( event.type ) ) ) {
5314            this._startOpening( nested );
5315        }
5316        this.activeMenu = item.parent();
5317
5318        this._trigger( "focus", event, { item: item } );
5319    },
5320
5321    _scrollIntoView: function( item ) {
5322        var borderTop, paddingTop, offset, scroll, elementHeight, itemHeight;
5323        if ( this._hasScroll() ) {
5324            borderTop = parseFloat( $.css( this.activeMenu[ 0 ], "borderTopWidth" ) ) || 0;
5325            paddingTop = parseFloat( $.css( this.activeMenu[ 0 ], "paddingTop" ) ) || 0;
5326            offset = item.offset().top - this.activeMenu.offset().top - borderTop - paddingTop;
5327            scroll = this.activeMenu.scrollTop();
5328            elementHeight = this.activeMenu.height();
5329            itemHeight = item.outerHeight();
5330
5331            if ( offset < 0 ) {
5332                this.activeMenu.scrollTop( scroll + offset );
5333            } else if ( offset + itemHeight > elementHeight ) {
5334                this.activeMenu.scrollTop( scroll + offset - elementHeight + itemHeight );
5335            }
5336        }
5337    },
5338
5339    blur: function( event, fromFocus ) {
5340        if ( !fromFocus ) {
5341            clearTimeout( this.timer );
5342        }
5343
5344        if ( !this.active ) {
5345            return;
5346        }
5347
5348        this._removeClass( this.active.children( ".ui-menu-item-wrapper" ),
5349            null, "ui-state-active" );
5350
5351        this._trigger( "blur", event, { item: this.active } );
5352        this.active = null;
5353    },
5354
5355    _startOpening: function( submenu ) {
5356        clearTimeout( this.timer );
5357
5358        // Don't open if already open fixes a Firefox bug that caused a .5 pixel
5359        // shift in the submenu position when mousing over the caret icon
5360        if ( submenu.attr( "aria-hidden" ) !== "true" ) {
5361            return;
5362        }
5363
5364        this.timer = this._delay( function() {
5365            this._close();
5366            this._open( submenu );
5367        }, this.delay );
5368    },
5369
5370    _open: function( submenu ) {
5371        var position = $.extend( {
5372            of: this.active
5373        }, this.options.position );
5374
5375        clearTimeout( this.timer );
5376        this.element.find( ".ui-menu" ).not( submenu.parents( ".ui-menu" ) )
5377            .hide()
5378            .attr( "aria-hidden", "true" );
5379
5380        submenu
5381            .show()
5382            .removeAttr( "aria-hidden" )
5383            .attr( "aria-expanded", "true" )
5384            .position( position );
5385    },
5386
5387    collapseAll: function( event, all ) {
5388        clearTimeout( this.timer );
5389        this.timer = this._delay( function() {
5390
5391            // If we were passed an event, look for the submenu that c
vendor: 7,781 bytes, lines 5391-5640
5391ontains the event
5392            var currentMenu = all ? this.element :
5393                $( event && event.target ).closest( this.element.find( ".ui-menu" ) );
5394
5395            // If we found no valid submenu ancestor, use the main menu to close all
5396            // sub menus anyway
5397            if ( !currentMenu.length ) {
5398                currentMenu = this.element;
5399            }
5400
5401            this._close( currentMenu );
5402
5403            this.blur( event );
5404
5405            // Work around active item staying active after menu is blurred
5406            this._removeClass( currentMenu.find( ".ui-state-active" ), null, "ui-state-active" );
5407
5408            this.activeMenu = currentMenu;
5409        }, this.delay );
5410    },
5411
5412    // With no arguments, closes the currently active menu - if nothing is active
5413    // it closes all menus.  If passed an argument, it will search for menus BELOW
5414    _close: function( startMenu ) {
5415        if ( !startMenu ) {
5416            startMenu = this.active ? this.active.parent() : this.element;
5417        }
5418
5419        startMenu.find( ".ui-menu" )
5420            .hide()
5421            .attr( "aria-hidden", "true" )
5422            .attr( "aria-expanded", "false" );
5423    },
5424
5425    _closeOnDocumentClick: function( event ) {
5426        return !$( event.target ).closest( ".ui-menu" ).length;
5427    },
5428
5429    _isDivider: function( item ) {
5430
5431        // Match hyphen, em dash, en dash
5432        return !/[^\-\u2014\u2013\s]/.test( item.text() );
5433    },
5434
5435    collapse: function( event ) {
5436        var newItem = this.active &&
5437            this.active.parent().closest( ".ui-menu-item", this.element );
5438        if ( newItem && newItem.length ) {
5439            this._close();
5440            this.focus( event, newItem );
5441        }
5442    },
5443
5444    expand: function( event ) {
5445        var newItem = this.active &&
5446            this.active
5447                .children( ".ui-menu " )
5448                    .find( this.options.items )
5449                        .first();
5450
5451        if ( newItem && newItem.length ) {
5452            this._open( newItem.parent() );
5453
5454            // Delay so Firefox will not hide activedescendant change in expanding submenu from AT
5455            this._delay( function() {
5456                this.focus( event, newItem );
5457            } );
5458        }
5459    },
5460
5461    next: function( event ) {
5462        this._move( "next", "first", event );
5463    },
5464
5465    previous: function( event ) {
5466        this._move( "prev", "last", event );
5467    },
5468
5469    isFirstItem: function() {
5470        return this.active && !this.active.prevAll( ".ui-menu-item" ).length;
5471    },
5472
5473    isLastItem: function() {
5474        return this.active && !this.active.nextAll( ".ui-menu-item" ).length;
5475    },
5476
5477    _move: function( direction, filter, event ) {
5478        var next;
5479        if ( this.active ) {
5480            if ( direction === "first" || direction === "last" ) {
5481                next = this.active
5482                    [ direction === "first" ? "prevAll" : "nextAll" ]( ".ui-menu-item" )
5483                    .eq( -1 );
5484            } else {
5485                next = this.active
5486                    [ direction + "All" ]( ".ui-menu-item" )
5487                    .eq( 0 );
5488            }
5489        }
5490        if ( !next || !next.length || !this.active ) {
5491            next = this.activeMenu.find( this.options.items )[ filter ]();
5492        }
5493
5494        this.focus( event, next );
5495    },
5496
5497    nextPage: function( event ) {
5498        var item, base, height;
5499
5500        if ( !this.active ) {
5501            this.next( event );
5502            return;
5503        }
5504        if ( this.isLastItem() ) {
5505            return;
5506        }
5507        if ( this._hasScroll() ) {
5508            base = this.active.offset().top;
5509            height = this.element.height();
5510            this.active.nextAll( ".ui-menu-item" ).each( function() {
5511                item = $( this );
5512                return item.offset().top - base - height < 0;
5513            } );
5514
5515            this.focus( event, item );
5516        } else {
5517            this.focus( event, this.activeMenu.find( this.options.items )
5518                [ !this.active ? "first" : "last" ]() );
5519        }
5520    },
5521
5522    previousPage: function( event ) {
5523        var item, base, height;
5524        if ( !this.active ) {
5525            this.next( event );
5526            return;
5527        }
5528        if ( this.isFirstItem() ) {
5529            return;
5530        }
5531        if ( this._hasScroll() ) {
5532            base = this.active.offset().top;
5533            height = this.element.height();
5534            this.active.prevAll( ".ui-menu-item" ).each( function() {
5535                item = $( this );
5536                return item.offset().top - base + height > 0;
5537            } );
5538
5539            this.focus( event, item );
5540        } else {
5541            this.focus( event, this.activeMenu.find( this.options.items ).first() );
5542        }
5543    },
5544
5545    _hasScroll: function() {
5546        return this.element.outerHeight() < this.element.prop( "scrollHeight" );
5547    },
5548
5549    select: function( event ) {
5550
5551        // TODO: It should never be possible to not have an active item at this
5552        // point, but the tests don't trigger mouseenter before click.
5553        this.active = this.active || $( event.target ).closest( ".ui-menu-item" );
5554        var ui = { item: this.active };
5555        if ( !this.active.has( ".ui-menu" ).length ) {
5556            this.collapseAll( event, true );
5557        }
5558        this._trigger( "select", event, ui );
5559    },
5560
5561    _filterMenuItems: function( character ) {
5562        var escapedCharacter = character.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" ),
5563            regex = new RegExp( "^" + escapedCharacter, "i" );
5564
5565        return this.activeMenu
5566            .find( this.options.items )
5567
5568                // Only match on items, not dividers or other content (#10571)
5569                .filter( ".ui-menu-item" )
5570                    .filter( function() {
5571                        return regex.test(
5572                            $.trim( $( this ).children( ".ui-menu-item-wrapper" ).text() ) );
5573                    } );
5574    }
5575} );
5576
5577
5578/*!
5579 * jQuery UI Autocomplete 1.12.1
5580 * http://jqueryui.com
5581 *
5582 * Copyright jQuery Foundation and other contributors
5583 * Released under the MIT license.
5584 * http://jquery.org/license
5585 */
5586
5587//>>label: Autocomplete
5588//>>group: Widgets
5589//>>description: Lists suggested words as the user is typing.
5590//>>docs: http://api.jqueryui.com/autocomplete/
5591//>>demos: http://jqueryui.com/autocomplete/
5592//>>css.structure: ../../themes/base/core.css
5593//>>css.structure: ../../themes/base/autocomplete.css
5594//>>css.theme: ../../themes/base/theme.css
5595
5596
5597
5598$.widget( "ui.autocomplete", {
5599    version: "1.12.1",
5600    defaultElement: "<input>",
5601    options: {
5602        appendTo: null,
5603        autoFocus: false,
5604        delay: 300,
5605        minLength: 1,
5606        position: {
5607            my: "left top",
5608            at: "left bottom",
5609            collision: "none"
5610        },
5611        source: null,
5612
5613        // Callbacks
5614        change: null,
5615        close: null,
5616        focus: null,
5617        open: null,
5618        response: null,
5619        search: null,
5620        select: null
5621    },
5622
5623    requestIndex: 0,
5624    pending: 0,
5625
5626    _create: function() {
5627
5628        // Some browsers only repeat keydown events, not keypress events,
5629        // so we use the suppressKeyPress flag to determine if we've already
5630        // handled the keydown event. #7269
5631        // Unfortunately the code for & in keypress is the same as the up arrow,
5632        // so we use the suppressKeyPressRepeat flag to avoid handling keypress
5633        // events when we know the keydown event was used to modify the
5634        // search term. #7799
5635        var suppressKeyPress, suppressKeyPressRepeat, suppressInput,
5636            nodeName = this.element[ 0 ].nodeName.toLowerCase(),
5637            isTextarea = nodeName === "textarea",
5638            isInput = nodeName === "input";
5639
5640        // Textareas are always multi-line
vendor: 4,488 bytes, lines 5641-5751
5641        // Inputs are always single-line, even if inside a contentEditable element
5642        // IE also treats inputs as contentEditable
5643        // All other element types are determined by whether or not they're contentEditable
5644        this.isMultiLine = isTextarea || !isInput && this._isContentEditable( this.element );
5645
5646        this.valueMethod = this.element[ isTextarea || isInput ? "val" : "text" ];
5647        this.isNewMenu = true;
5648
5649        this._addClass( "ui-autocomplete-input" );
5650        this.element.attr( "autocomplete", "off" );
5651
5652        this._on( this.element, {
5653            keydown: function( event ) {
5654                if ( this.element.prop( "readOnly" ) ) {
5655                    suppressKeyPress = true;
5656                    suppressInput = true;
5657                    suppressKeyPressRepeat = true;
5658                    return;
5659                }
5660
5661                suppressKeyPress = false;
5662                suppressInput = false;
5663                suppressKeyPressRepeat = false;
5664                var keyCode = $.ui.keyCode;
5665                switch ( event.keyCode ) {
5666                case keyCode.PAGE_UP:
5667                    suppressKeyPress = true;
5668                    this._move( "previousPage", event );
5669                    break;
5670                case keyCode.PAGE_DOWN:
5671                    suppressKeyPress = true;
5672                    this._move( "nextPage", event );
5673                    break;
5674                case keyCode.UP:
5675                    suppressKeyPress = true;
5676                    this._keyEvent( "previous", event );
5677                    break;
5678                case keyCode.DOWN:
5679                    suppressKeyPress = true;
5680                    this._keyEvent( "next", event );
5681                    break;
5682                case keyCode.ENTER:
5683
5684                    // when menu is open and has focus
5685                    if ( this.menu.active ) {
5686
5687                        // #6055 - Opera still allows the keypress to occur
5688                        // which causes forms to submit
5689                        suppressKeyPress = true;
5690                        event.preventDefault();
5691                        this.menu.select( event );
5692                    }
5693                    break;
5694                case keyCode.TAB:
5695                    if ( this.menu.active ) {
5696                        this.menu.select( event );
5697                    }
5698                    break;
5699                case keyCode.ESCAPE:
5700                    if ( this.menu.element.is( ":visible" ) ) {
5701                        if ( !this.isMultiLine ) {
5702                            this._value( this.term );
5703                        }
5704                        this.close( event );
5705
5706                        // Different browsers have different default behavior for escape
5707                        // Single press can mean undo or clear
5708                        // Double press in IE means clear the whole form
5709                        event.preventDefault();
5710                    }
5711                    break;
5712                default:
5713                    suppressKeyPressRepeat = true;
5714
5715                    // search timeout should be triggered before the input value is changed
5716                    this._searchTimeout( event );
5717                    break;
5718                }
5719            },
5720            keypress: function( event ) {
5721                if ( suppressKeyPress ) {
5722                    suppressKeyPress = false;
5723                    if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
5724                        event.preventDefault();
5725                    }
5726                    return;
5727                }
5728                if ( suppressKeyPressRepeat ) {
5729                    return;
5730                }
5731
5732                // Replicate some key handlers to allow them to repeat in Firefox and Opera
5733                var keyCode = $.ui.keyCode;
5734                switch ( event.keyCode ) {
5735                case keyCode.PAGE_UP:
5736                    this._move( "previousPage", event );
5737                    break;
5738                case keyCode.PAGE_DOWN:
5739                    this._move( "nextPage", event );
5740                    break;
5741                case keyCode.UP:
5742                    this._keyEvent( "previous", event );
5743                    break;
5744                case keyCode.DOWN:
5745                    this._keyEvent( "next", event );
5746                    break;
5747                }
5748            },
5749            input: function( event ) {
5750                if ( suppressInput ) {
5751                    suppressInput = false;
vendor: 37,670 bytes, lines 5752-6884
5752                    event.preventDefault();
5753                    return;
5754                }
5755                this._searchTimeout( event );
5756            },
5757            focus: function() {
5758                this.selectedItem = null;
5759                this.previous = this._value();
5760            },
5761            blur: function( event ) {
5762                if ( this.cancelBlur ) {
5763                    delete this.cancelBlur;
5764                    return;
5765                }
5766
5767                clearTimeout( this.searching );
5768                this.close( event );
5769                this._change( event );
5770            }
5771        } );
5772
5773        this._initSource();
5774        this.menu = $( "<ul>" )
5775            .appendTo( this._appendTo() )
5776            .menu( {
5777
5778                // disable ARIA support, the live region takes care of that
5779                role: null
5780            } )
5781            .hide()
5782            .menu( "instance" );
5783
5784        this._addClass( this.menu.element, "ui-autocomplete", "ui-front" );
5785        this._on( this.menu.element, {
5786            mousedown: function( event ) {
5787
5788                // prevent moving focus out of the text field
5789                event.preventDefault();
5790
5791                // IE doesn't prevent moving focus even with event.preventDefault()
5792                // so we set a flag to know when we should ignore the blur event
5793                this.cancelBlur = true;
5794                this._delay( function() {
5795                    delete this.cancelBlur;
5796
5797                    // Support: IE 8 only
5798                    // Right clicking a menu item or selecting text from the menu items will
5799                    // result in focus moving out of the input. However, we've already received
5800                    // and ignored the blur event because of the cancelBlur flag set above. So
5801                    // we restore focus to ensure that the menu closes properly based on the user's
5802                    // next actions.
5803                    if ( this.element[ 0 ] !== $.ui.safeActiveElement( this.document[ 0 ] ) ) {
5804                        this.element.trigger( "focus" );
5805                    }
5806                } );
5807            },
5808            menufocus: function( event, ui ) {
5809                var label, item;
5810
5811                // support: Firefox
5812                // Prevent accidental activation of menu items in Firefox (#7024 #9118)
5813                if ( this.isNewMenu ) {
5814                    this.isNewMenu = false;
5815                    if ( event.originalEvent && /^mouse/.test( event.originalEvent.type ) ) {
5816                        this.menu.blur();
5817
5818                        this.document.one( "mousemove", function() {
5819                            $( event.target ).trigger( event.originalEvent );
5820                        } );
5821
5822                        return;
5823                    }
5824                }
5825
5826                item = ui.item.data( "ui-autocomplete-item" );
5827                if ( false !== this._trigger( "focus", event, { item: item } ) ) {
5828
5829                    // use value to match what will end up in the input, if it was a key event
5830                    if ( event.originalEvent && /^key/.test( event.originalEvent.type ) ) {
5831                        this._value( item.value );
5832                    }
5833                }
5834
5835                // Announce the value in the liveRegion
5836                label = ui.item.attr( "aria-label" ) || item.value;
5837                if ( label && $.trim( label ).length ) {
5838                    this.liveRegion.children().hide();
5839                    $( "<div>" ).text( label ).appendTo( this.liveRegion );
5840                }
5841            },
5842            menuselect: function( event, ui ) {
5843                var item = ui.item.data( "ui-autocomplete-item" ),
5844                    previous = this.previous;
5845
5846                // Only trigger when focus was lost (click on menu)
5847                if ( this.element[ 0 ] !== $.ui.safeActiveElement( this.document[ 0 ] ) ) {
5848                    this.element.trigger( "focus" );
5849                    this.previous = previous;
5850
5851                    // #6109 - IE triggers two focus events and the second
5852                    // is asynchronous, so we need to reset the previous
5853                    // term synchronously and asynchronously :-(
5854                    this._delay( function() {
5855                        this.previous = previous;
5856                        this.selectedItem = item;
5857                    } );
5858                }
5859
5860                if ( false !== this._trigger( "select", event, { item: item } ) ) {
5861                    this._value( item.value );
5862                }
5863
5864                // reset the term after the select event
5865                // this allows custom select handling to work properly
5866                this.term = this._value();
5867
5868                this.close( event );
5869                this.selectedItem = item;
5870            }
5871        } );
5872
5873        this.liveRegion = $( "<div>", {
5874            role: "status",
5875            "aria-live": "assertive",
5876            "aria-relevant": "additions"
5877        } )
5878            .appendTo( this.document[ 0 ].body );
5879
5880        this._addClass( this.liveRegion, null, "ui-helper-hidden-accessible" );
5881
5882        // Turning off autocomplete prevents the browser from remembering the
5883        // value when navigating through history, so we re-enable autocomplete
5884        // if the page is unloaded before the widget is destroyed. #7790
5885        this._on( this.window, {
5886            beforeunload: function() {
5887                this.element.removeAttr( "autocomplete" );
5888            }
5889        } );
5890    },
5891
5892    _destroy: function() {
5893        clearTimeout( this.searching );
5894        this.element.removeAttr( "autocomplete" );
5895        this.menu.element.remove();
5896        this.liveRegion.remove();
5897    },
5898
5899    _setOption: function( key, value ) {
5900        this._super( key, value );
5901        if ( key === "source" ) {
5902            this._initSource();
5903        }
5904        if ( key === "appendTo" ) {
5905            this.menu.element.appendTo( this._appendTo() );
5906        }
5907        if ( key === "disabled" && value && this.xhr ) {
5908            this.xhr.abort();
5909        }
5910    },
5911
5912    _isEventTargetInWidget: function( event ) {
5913        var menuElement = this.menu.element[ 0 ];
5914
5915        return event.target === this.element[ 0 ] ||
5916            event.target === menuElement ||
5917            $.contains( menuElement, event.target );
5918    },
5919
5920    _closeOnClickOutside: function( event ) {
5921        if ( !this._isEventTargetInWidget( event ) ) {
5922            this.close();
5923        }
5924    },
5925
5926    _appendTo: function() {
5927        var element = this.options.appendTo;
5928
5929        if ( element ) {
5930            element = element.jquery || element.nodeType ?
5931                $( element ) :
5932                this.document.find( element ).eq( 0 );
5933        }
5934
5935        if ( !element || !element[ 0 ] ) {
5936            element = this.element.closest( ".ui-front, dialog" );
5937        }
5938
5939        if ( !element.length ) {
5940            element = this.document[ 0 ].body;
5941        }
5942
5943        return element;
5944    },
5945
5946    _initSource: function() {
5947        var array, url,
5948            that = this;
5949        if ( $.isArray( this.options.source ) ) {
5950            array = this.options.source;
5951            this.source = function( request, response ) {
5952                response( $.ui.autocomplete.filter( array, request.term ) );
5953            };
5954        } else if ( typeof this.options.source === "string" ) {
5955            url = this.options.source;
5956            this.source = function( request, response ) {
5957                if ( that.xhr ) {
5958                    that.xhr.abort();
5959                }
5960                that.xhr = $.ajax( {
5961                    url: url,
5962                    data: request,
5963                    dataType: "json",
5964                    success: function( data ) {
5965                        response( data );
5966                    },
5967                    error: function() {
5968                        response( [] );
5969                    }
5970                } );
5971            };
5972        } else {
5973            this.source = this.options.source;
5974        }
5975    },
5976
5977    _searchTimeout: function( event ) {
5978        clearTimeout( this.searching );
5979        this.searching = this._delay( function() {
5980
5981            // Search if the value has changed, or if the user retypes the same value (see #7434)
5982            var equalValues = this.term === this._value(),
5983                menuVisible = this.menu.element.is( ":visible" ),
5984                modifierKey = event.altKey || event.ctrlKey || event.metaKey || event.shiftKey;
5985
5986            if ( !equalValues || ( equalValues && !menuVisible && !modifierKey ) ) {
5987                this.selectedItem = null;
5988                this.search( null, event );
5989            }
5990        }, this.options.delay );
5991    },
5992
5993    search: function( value, event ) {
5994        value = value != null ? value : this._value();
5995
5996        // Always save the actual value, not the one passed as an argument
5997        this.term = this._value();
5998
5999        if ( value.length < this.options.minLength ) {
6000            return this.close( event );
6001        }
6002
6003        if ( this._trigger( "search", event ) === false ) {
6004            return;
6005        }
6006
6007        return this._search( value );
6008    },
6009
6010    _search: function( value ) {
6011        this.pending++;
6012        this._addClass( "ui-autocomplete-loading" );
6013        this.cancelSearch = false;
6014
6015        this.source( { term: value }, this._response() );
6016    },
6017
6018    _response: function() {
6019        var index = ++this.requestIndex;
6020
6021        return $.proxy( function( content ) {
6022            if ( index === this.requestIndex ) {
6023                this.__response( content );
6024            }
6025
6026            this.pending--;
6027            if ( !this.pending ) {
6028                this._removeClass( "ui-autocomplete-loading" );
6029            }
6030        }, this );
6031    },
6032
6033    __response: function( content ) {
6034        if ( content ) {
6035            content = this._normalize( content );
6036        }
6037        this._trigger( "response", null, { content: content } );
6038        if ( !this.options.disabled && content && content.length && !this.cancelSearch ) {
6039            this._suggest( content );
6040            this._trigger( "open" );
6041        } else {
6042
6043            // use ._close() instead of .close() so we don't cancel future searches
6044            this._close();
6045        }
6046    },
6047
6048    close: function( event ) {
6049        this.cancelSearch = true;
6050        this._close( event );
6051    },
6052
6053    _close: function( event ) {
6054
6055        // Remove the handler that closes the menu on outside clicks
6056        this._off( this.document, "mousedown" );
6057
6058        if ( this.menu.element.is( ":visible" ) ) {
6059            this.menu.element.hide();
6060            this.menu.blur();
6061            this.isNewMenu = true;
6062            this._trigger( "close", event );
6063        }
6064    },
6065
6066    _change: function( event ) {
6067        if ( this.previous !== this._value() ) {
6068            this._trigger( "change", event, { item: this.selectedItem } );
6069        }
6070    },
6071
6072    _normalize: function( items ) {
6073
6074        // assume all items have the right format when the first item is complete
6075        if ( items.length && items[ 0 ].label && items[ 0 ].value ) {
6076            return items;
6077        }
6078        return $.map( items, function( item ) {
6079            if ( typeof item === "string" ) {
6080                return {
6081                    label: item,
6082                    value: item
6083                };
6084            }
6085            return $.extend( {}, item, {
6086                label: item.label || item.value,
6087                value: item.value || item.label
6088            } );
6089        } );
6090    },
6091
6092    _suggest: function( items ) {
6093        var ul = this.menu.element.empty();
6094        this._renderMenu( ul, items );
6095        this.isNewMenu = true;
6096        this.menu.refresh();
6097
6098        // Size and position menu
6099        ul.show();
6100        this._resizeMenu();
6101        ul.position( $.extend( {
6102            of: this.element
6103        }, this.options.position ) );
6104
6105        if ( this.options.autoFocus ) {
6106            this.menu.next();
6107        }
6108
6109        // Listen for interactions outside of the widget (#6642)
6110        this._on( this.document, {
6111            mousedown: "_closeOnClickOutside"
6112        } );
6113    },
6114
6115    _resizeMenu: function() {
6116        var ul = this.menu.element;
6117        ul.outerWidth( Math.max(
6118
6119            // Firefox wraps long text (possibly a rounding bug)
6120            // so we add 1px to avoid the wrapping (#7513)
6121            ul.width( "" ).outerWidth() + 1,
6122            this.element.outerWidth()
6123        ) );
6124    },
6125
6126    _renderMenu: function( ul, items ) {
6127        var that = this;
6128        $.each( items, function( index, item ) {
6129            that._renderItemData( ul, item );
6130        } );
6131    },
6132
6133    _renderItemData: function( ul, item ) {
6134        return this._renderItem( ul, item ).data( "ui-autocomplete-item", item );
6135    },
6136
6137    _renderItem: function( ul, item ) {
6138        return $( "<li>" )
6139            .append( $( "<div>" ).text( item.label ) )
6140            .appendTo( ul );
6141    },
6142
6143    _move: function( direction, event ) {
6144        if ( !this.menu.element.is( ":visible" ) ) {
6145            this.search( null, event );
6146            return;
6147        }
6148        if ( this.menu.isFirstItem() && /^previous/.test( direction ) ||
6149                this.menu.isLastItem() && /^next/.test( direction ) ) {
6150
6151            if ( !this.isMultiLine ) {
6152                this._value( this.term );
6153            }
6154
6155            this.menu.blur();
6156            return;
6157        }
6158        this.menu[ direction ]( event );
6159    },
6160
6161    widget: function() {
6162        return this.menu.element;
6163    },
6164
6165    _value: function() {
6166        return this.valueMethod.apply( this.element, arguments );
6167    },
6168
6169    _keyEvent: function( keyEvent, event ) {
6170        if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
6171            this._move( keyEvent, event );
6172
6173            // Prevents moving cursor to beginning/end of the text field in some browsers
6174            event.preventDefault();
6175        }
6176    },
6177
6178    // Support: Chrome <=50
6179    // We should be able to just use this.element.prop( "isContentEditable" )
6180    // but hidden elements always report false in Chrome.
6181    // https://code.google.com/p/chromium/issues/detail?id=313082
6182    _isContentEditable: function( element ) {
6183        if ( !element.length ) {
6184            return false;
6185        }
6186
6187        var editable = element.prop( "contentEditable" );
6188
6189        if ( editable === "inherit" ) {
6190          return this._isContentEditable( element.parent() );
6191        }
6192
6193        return editable === "true";
6194    }
6195} );
6196
6197$.extend( $.ui.autocomplete, {
6198    escapeRegex: function( value ) {
6199        return value.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" );
6200    },
6201    filter: function( array, term ) {
6202        var matcher = new RegExp( $.ui.autocomplete.escapeRegex( term ), "i" );
6203        return $.grep( array, function( value ) {
6204            return matcher.test( value.label || value.value || value );
6205        } );
6206    }
6207} );
6208
6209// Live region extension, adding a `messages` option
6210// NOTE: This is an experimental API. We are still investigating
6211// a full solution for string manipulation and internationalization.
6212$.widget( "ui.autocomplete", $.ui.autocomplete, {
6213    options: {
6214        messages: {
6215            noResults: "No search results.",
6216            results: function( amount ) {
6217                return amount + ( amount > 1 ? " results are" : " result is" ) +
6218                    " available, use up and down arrow keys to navigate.";
6219            }
6220        }
6221    },
6222
6223    __response: function( content ) {
6224        var message;
6225        this._superApply( arguments );
6226        if ( this.options.disabled || this.cancelSearch ) {
6227            return;
6228        }
6229        if ( content && content.length ) {
6230            message = this.options.messages.results( content.length );
6231        } else {
6232            message = this.options.messages.noResults;
6233        }
6234        this.liveRegion.children().hide();
6235        $( "<div>" ).text( message ).appendTo( this.liveRegion );
6236    }
6237} );
6238
6239var widgetsAutocomplete = $.ui.autocomplete;
6240
6241
6242/*!
6243 * jQuery UI Controlgroup 1.12.1
6244 * http://jqueryui.com
6245 *
6246 * Copyright jQuery Foundation and other contributors
6247 * Released under the MIT license.
6248 * http://jquery.org/license
6249 */
6250
6251//>>label: Controlgroup
6252//>>group: Widgets
6253//>>description: Visually groups form control widgets
6254//>>docs: http://api.jqueryui.com/controlgroup/
6255//>>demos: http://jqueryui.com/controlgroup/
6256//>>css.structure: ../../themes/base/core.css
6257//>>css.structure: ../../themes/base/controlgroup.css
6258//>>css.theme: ../../themes/base/theme.css
6259
6260
6261var controlgroupCornerRegex = /ui-corner-([a-z]){2,6}/g;
6262
6263var widgetsControlgroup = $.widget( "ui.controlgroup", {
6264    version: "1.12.1",
6265    defaultElement: "<div>",
6266    options: {
6267        direction: "horizontal",
6268        disabled: null,
6269        onlyVisible: true,
6270        items: {
6271            "button": "input[type=button], input[type=submit], input[type=reset], button, a",
6272            "controlgroupLabel": ".ui-controlgroup-label",
6273            "checkboxradio": "input[type='checkbox'], input[type='radio']",
6274            "selectmenu": "select",
6275            "spinner": ".ui-spinner-input"
6276        }
6277    },
6278
6279    _create: function() {
6280        this._enhance();
6281    },
6282
6283    // To support the enhanced option in jQuery Mobile, we isolate DOM manipulation
6284    _enhance: function() {
6285        this.element.attr( "role", "toolbar" );
6286        this.refresh();
6287    },
6288
6289    _destroy: function() {
6290        this._callChildMethod( "destroy" );
6291        this.childWidgets.removeData( "ui-controlgroup-data" );
6292        this.element.removeAttr( "role" );
6293        if ( this.options.items.controlgroupLabel ) {
6294            this.element
6295                .find( this.options.items.controlgroupLabel )
6296                .find( ".ui-controlgroup-label-contents" )
6297                .contents().unwrap();
6298        }
6299    },
6300
6301    _initWidgets: function() {
6302        var that = this,
6303            childWidgets = [];
6304
6305        // First we iterate over each of the items options
6306        $.each( this.options.items, function( widget, selector ) {
6307            var labels;
6308            var options = {};
6309
6310            // Make sure the widget has a selector set
6311            if ( !selector ) {
6312                return;
6313            }
6314
6315            if ( widget === "controlgroupLabel" ) {
6316                labels = that.element.find( selector );
6317                labels.each( function() {
6318                    var element = $( this );
6319
6320                    if ( element.children( ".ui-controlgroup-label-contents" ).length ) {
6321                        return;
6322                    }
6323                    element.contents()
6324                        .wrapAll( "<span class='ui-controlgroup-label-contents'></span>" );
6325                } );
6326                that._addClass( labels, null, "ui-widget ui-widget-content ui-state-default" );
6327                childWidgets = childWidgets.concat( labels.get() );
6328                return;
6329            }
6330
6331            // Make sure the widget actually exists
6332            if ( !$.fn[ widget ] ) {
6333                return;
6334            }
6335
6336            // We assume everything is in the middle to start because we can't determine
6337            // first / last elements until all enhancments are done.
6338            if ( that[ "_" + widget + "Options" ] ) {
6339                options = that[ "_" + widget + "Options" ]( "middle" );
6340            } else {
6341                options = { classes: {} };
6342            }
6343
6344            // Find instances of this widget inside controlgroup and init them
6345            that.element
6346                .find( selector )
6347                .each( function() {
6348                    var element = $( this );
6349                    var instance = element[ widget ]( "instance" );
6350
6351                    // We need to clone the default options for this type of widget to avoid
6352                    // polluting the variable options which has a wider scope than a single widget.
6353                    var instanceOptions = $.widget.extend( {}, options );
6354
6355                    // If the button is the child of a spinner ignore it
6356                    // TODO: Find a more generic solution
6357                    if ( widget === "button" && element.parent( ".ui-spinner" ).length ) {
6358                        return;
6359                    }
6360
6361                    // Create the widget if it doesn't exist
6362                    if ( !instance ) {
6363                        instance = element[ widget ]()[ widget ]( "instance" );
6364                    }
6365                    if ( instance ) {
6366                        instanceOptions.classes =
6367                            that._resolveClassesValues( instanceOptions.classes, instance );
6368                    }
6369                    element[ widget ]( instanceOptions );
6370
6371                    // Store an instance of the controlgroup to be able to reference
6372                    // from the outermost element for changing options and refresh
6373                    var widgetElement = element[ widget ]( "widget" );
6374                    $.data( widgetElement[ 0 ], "ui-controlgroup-data",
6375                        instance ? instance : element[ widget ]( "instance" ) );
6376
6377                    childWidgets.push( widgetElement[ 0 ] );
6378                } );
6379        } );
6380
6381        this.childWidgets = $( $.unique( childWidgets ) );
6382        this._addClass( this.childWidgets, "ui-controlgroup-item" );
6383    },
6384
6385    _callChildMethod: function( method ) {
6386        this.childWidgets.each( function() {
6387            var element = $( this ),
6388                data = element.data( "ui-controlgroup-data" );
6389            if ( data && data[ method ] ) {
6390                data[ method ]();
6391            }
6392        } );
6393    },
6394
6395    _updateCornerClass: function( element, position ) {
6396        var remove = "ui-corner-top ui-corner-bottom ui-corner-left ui-corner-right ui-corner-all";
6397        var add = this._buildSimpleOptions( position, "label" ).classes.label;
6398
6399        this._removeClass( element, null, remove );
6400        this._addClass( element, null, add );
6401    },
6402
6403    _buildSimpleOptions: function( position, key ) {
6404        var direction = this.options.direction === "vertical";
6405        var result = {
6406            classes: {}
6407        };
6408        result.classes[ key ] = {
6409            "middle": "",
6410            "first": "ui-corner-" + ( direction ? "top" : "left" ),
6411            "last": "ui-corner-" + ( direction ? "bottom" : "right" ),
6412            "only": "ui-corner-all"
6413        }[ position ];
6414
6415        return result;
6416    },
6417
6418    _spinnerOptions: function( position ) {
6419        var options = this._buildSimpleOptions( position, "ui-spinner" );
6420
6421        options.classes[ "ui-spinner-up" ] = "";
6422        options.classes[ "ui-spinner-down" ] = "";
6423
6424        return options;
6425    },
6426
6427    _buttonOptions: function( position ) {
6428        return this._buildSimpleOptions( position, "ui-button" );
6429    },
6430
6431    _checkboxradioOptions: function( position ) {
6432        return this._buildSimpleOptions( position, "ui-checkboxradio-label" );
6433    },
6434
6435    _selectmenuOptions: function( position ) {
6436        var direction = this.options.direction === "vertical";
6437        return {
6438            width: direction ? "auto" : false,
6439            classes: {
6440                middle: {
6441                    "ui-selectmenu-button-open": "",
6442                    "ui-selectmenu-button-closed": ""
6443                },
6444                first: {
6445                    "ui-selectmenu-button-open": "ui-corner-" + ( direction ? "top" : "tl" ),
6446                    "ui-selectmenu-button-closed": "ui-corner-" + ( direction ? "top" : "left" )
6447                },
6448                last: {
6449                    "ui-selectmenu-button-open": direction ? "" : "ui-corner-tr",
6450                    "ui-selectmenu-button-closed": "ui-corner-" + ( direction ? "bottom" : "right" )
6451                },
6452                only: {
6453                    "ui-selectmenu-button-open": "ui-corner-top",
6454                    "ui-selectmenu-button-closed": "ui-corner-all"
6455                }
6456
6457            }[ position ]
6458        };
6459    },
6460
6461    _resolveClassesValues: function( classes, instance ) {
6462        var result = {};
6463        $.each( classes, function( key ) {
6464            var current = instance.options.classes[ key ] || "";
6465            current = $.trim( current.replace( controlgroupCornerRegex, "" ) );
6466            result[ key ] = ( current + " " + classes[ key ] ).replace( /\s+/g, " " );
6467        } );
6468        return result;
6469    },
6470
6471    _setOption: function( key, value ) {
6472        if ( key === "direction" ) {
6473            this._removeClass( "ui-controlgroup-" + this.options.direction );
6474        }
6475
6476        this._super( key, value );
6477        if ( key === "disabled" ) {
6478            this._callChildMethod( value ? "disable" : "enable" );
6479            return;
6480        }
6481
6482        this.refresh();
6483    },
6484
6485    refresh: function() {
6486        var children,
6487            that = this;
6488
6489        this._addClass( "ui-controlgroup ui-controlgroup-" + this.options.direction );
6490
6491        if ( this.options.direction === "horizontal" ) {
6492            this._addClass( null, "ui-helper-clearfix" );
6493        }
6494        this._initWidgets();
6495
6496        children = this.childWidgets;
6497
6498        // We filter here because we need to track all childWidgets not just the visible ones
6499        if ( this.options.onlyVisible ) {
6500            children = children.filter( ":visible" );
6501        }
6502
6503        if ( children.length ) {
6504
6505            // We do this last because we need to make sure all enhancment is done
6506            // before determining first and last
6507            $.each( [ "first", "last" ], function( index, value ) {
6508                var instance = children[ value ]().data( "ui-controlgroup-data" );
6509
6510                if ( instance && that[ "_" + instance.widgetName + "Options" ] ) {
6511                    var options = that[ "_" + instance.widgetName + "Options" ](
6512                        children.length === 1 ? "only" : value
6513                    );
6514                    options.classes = that._resolveClassesValues( options.classes, instance );
6515                    instance.element[ instance.widgetName ]( options );
6516                } else {
6517                    that._updateCornerClass( children[ value ](), value );
6518                }
6519            } );
6520
6521            // Finally call the refresh method on each of the child widgets.
6522            this._callChildMethod( "refresh" );
6523        }
6524    }
6525} );
6526
6527/*!
6528 * jQuery UI Checkboxradio 1.12.1
6529 * http://jqueryui.com
6530 *
6531 * Copyright jQuery Foundation and other contributors
6532 * Released under the MIT license.
6533 * http://jquery.org/license
6534 */
6535
6536//>>label: Checkboxradio
6537//>>group: Widgets
6538//>>description: Enhances a form with multiple themeable checkboxes or radio buttons.
6539//>>docs: http://api.jqueryui.com/checkboxradio/
6540//>>demos: http://jqueryui.com/checkboxradio/
6541//>>css.structure: ../../themes/base/core.css
6542//>>css.structure: ../../themes/base/button.css
6543//>>css.structure: ../../themes/base/checkboxradio.css
6544//>>css.theme: ../../themes/base/theme.css
6545
6546
6547
6548$.widget( "ui.checkboxradio", [ $.ui.formResetMixin, {
6549    version: "1.12.1",
6550    options: {
6551        disabled: null,
6552        label: null,
6553        icon: true,
6554        classes: {
6555            "ui-checkboxradio-label": "ui-corner-all",
6556            "ui-checkboxradio-icon": "ui-corner-all"
6557        }
6558    },
6559
6560    _getCreateOptions: function() {
6561        var disabled, labels;
6562        var that = this;
6563        var options = this._super() || {};
6564
6565        // We read the type here, because it makes more sense to throw a element type error first,
6566        // rather then the error for lack of a label. Often if its the wrong type, it
6567        // won't have a label (e.g. calling on a div, btn, etc)
6568        this._readType();
6569
6570        labels = this.element.labels();
6571
6572        // If there are multiple labels, use the last one
6573        this.label = $( labels[ labels.length - 1 ] );
6574        if ( !this.label.length ) {
6575            $.error( "No label found for checkboxradio widget" );
6576        }
6577
6578        this.originalLabel = "";
6579
6580        // We need to get the label text but this may also need to make sure it does not contain the
6581        // input itself.
6582        this.label.contents().not( this.element[ 0 ] ).each( function() {
6583
6584            // The label contents could be text, html, or a mix. We concat each element to get a
6585            // string representation of the label, without the input as part of it.
6586            that.originalLabel += this.nodeType === 3 ? $( this ).text() : this.outerHTML;
6587        } );
6588
6589        // Set the label option if we found label text
6590        if ( this.originalLabel ) {
6591            options.label = this.originalLabel;
6592        }
6593
6594        disabled = this.element[ 0 ].disabled;
6595        if ( disabled != null ) {
6596            options.disabled = disabled;
6597        }
6598        return options;
6599    },
6600
6601    _create: function() {
6602        var checked = this.element[ 0 ].checked;
6603
6604        this._bindFormResetHandler();
6605
6606        if ( this.options.disabled == null ) {
6607            this.options.disabled = this.element[ 0 ].disabled;
6608        }
6609
6610        this._setOption( "disabled", this.options.disabled );
6611        this._addClass( "ui-checkboxradio", "ui-helper-hidden-accessible" );
6612        this._addClass( this.label, "ui-checkboxradio-label", "ui-button ui-widget" );
6613
6614        if ( this.type === "radio" ) {
6615            this._addClass( this.label, "ui-checkboxradio-radio-label" );
6616        }
6617
6618        if ( this.options.label && this.options.label !== this.originalLabel ) {
6619            this._updateLabel();
6620        } else if ( this.originalLabel ) {
6621            this.options.label = this.originalLabel;
6622        }
6623
6624        this._enhance();
6625
6626        if ( checked ) {
6627            this._addClass( this.label, "ui-checkboxradio-checked", "ui-state-active" );
6628            if ( this.icon ) {
6629                this._addClass( this.icon, null, "ui-state-hover" );
6630            }
6631        }
6632
6633        this._on( {
6634            change: "_toggleClasses",
6635            focus: function() {
6636                this._addClass( this.label, null, "ui-state-focus ui-visual-focus" );
6637            },
6638            blur: function() {
6639                this._removeClass( this.label, null, "ui-state-focus ui-visual-focus" );
6640            }
6641        } );
6642    },
6643
6644    _readType: function() {
6645        var nodeName = this.element[ 0 ].nodeName.toLowerCase();
6646        this.type = this.element[ 0 ].type;
6647        if ( nodeName !== "input" || !/radio|checkbox/.test( this.type ) ) {
6648            $.error( "Can't create checkboxradio on element.nodeName=" + nodeName +
6649                " and element.type=" + this.type );
6650        }
6651    },
6652
6653    // Support jQuery Mobile enhanced option
6654    _enhance: function() {
6655        this._updateIcon( this.element[ 0 ].checked );
6656    },
6657
6658    widget: function() {
6659        return this.label;
6660    },
6661
6662    _getRadioGroup: function() {
6663        var group;
6664        var name = this.element[ 0 ].name;
6665        var nameSelector = "input[name='" + $.ui.escapeSelector( name ) + "']";
6666
6667        if ( !name ) {
6668            return $( [] );
6669        }
6670
6671        if ( this.form.length ) {
6672            group = $( this.form[ 0 ].elements ).filter( nameSelector );
6673        } else {
6674
6675            // Not inside a form, check all inputs that also are not inside a form
6676            group = $( nameSelector ).filter( function() {
6677                return $( this ).form().length === 0;
6678            } );
6679        }
6680
6681        return group.not( this.element );
6682    },
6683
6684    _toggleClasses: function() {
6685        var checked = this.element[ 0 ].checked;
6686        this._toggleClass( this.label, "ui-checkboxradio-checked", "ui-state-active", checked );
6687
6688        if ( this.options.icon && this.type === "checkbox" ) {
6689            this._toggleClass( this.icon, null, "ui-icon-check ui-state-checked", checked )
6690                ._toggleClass( this.icon, null, "ui-icon-blank", !checked );
6691        }
6692
6693        if ( this.type === "radio" ) {
6694            this._getRadioGroup()
6695                .each( function() {
6696                    var instance = $( this ).checkboxradio( "instance" );
6697
6698                    if ( instance ) {
6699                        instance._removeClass( instance.label,
6700                            "ui-checkboxradio-checked", "ui-state-active" );
6701                    }
6702                } );
6703        }
6704    },
6705
6706    _destroy: function() {
6707        this._unbindFormResetHandler();
6708
6709        if ( this.icon ) {
6710            this.icon.remove();
6711            this.iconSpace.remove();
6712        }
6713    },
6714
6715    _setOption: function( key, value ) {
6716
6717        // We don't allow the value to be set to nothing
6718        if ( key === "label" && !value ) {
6719            return;
6720        }
6721
6722        this._super( key, value );
6723
6724        if ( key === "disabled" ) {
6725            this._toggleClass( this.label, null, "ui-state-disabled", value );
6726            this.element[ 0 ].disabled = value;
6727
6728            // Don't refresh when setting disabled
6729            return;
6730        }
6731        this.refresh();
6732    },
6733
6734    _updateIcon: function( checked ) {
6735        var toAdd = "ui-icon ui-icon-background ";
6736
6737        if ( this.options.icon ) {
6738            if ( !this.icon ) {
6739                this.icon = $( "<span>" );
6740                this.iconSpace = $( "<span> </span>" );
6741                this._addClass( this.iconSpace, "ui-checkboxradio-icon-space" );
6742            }
6743
6744            if ( this.type === "checkbox" ) {
6745                toAdd += checked ? "ui-icon-check ui-state-checked" : "ui-icon-blank";
6746                this._removeClass( this.icon, null, checked ? "ui-icon-blank" : "ui-icon-check" );
6747            } else {
6748                toAdd += "ui-icon-blank";
6749            }
6750            this._addClass( this.icon, "ui-checkboxradio-icon", toAdd );
6751            if ( !checked ) {
6752                this._removeClass( this.icon, null, "ui-icon-check ui-state-checked" );
6753            }
6754            this.icon.prependTo( this.label ).after( this.iconSpace );
6755        } else if ( this.icon !== undefined ) {
6756            this.icon.remove();
6757            this.iconSpace.remove();
6758            delete this.icon;
6759        }
6760    },
6761
6762    _updateLabel: function() {
6763
6764        // Remove the contents of the label ( minus the icon, icon space, and input )
6765        var contents = this.label.contents().not( this.element[ 0 ] );
6766        if ( this.icon ) {
6767            contents = contents.not( this.icon[ 0 ] );
6768        }
6769        if ( this.iconSpace ) {
6770            contents = contents.not( this.iconSpace[ 0 ] );
6771        }
6772        contents.remove();
6773
6774        this.label.append( this.options.label );
6775    },
6776
6777    refresh: function() {
6778        var checked = this.element[ 0 ].checked,
6779            isDisabled = this.element[ 0 ].disabled;
6780
6781        this._updateIcon( checked );
6782        this._toggleClass( this.label, "ui-checkboxradio-checked", "ui-state-active", checked );
6783        if ( this.options.label !== null ) {
6784            this._updateLabel();
6785        }
6786
6787        if ( isDisabled !== this.options.disabled ) {
6788            this._setOptions( { "disabled": isDisabled } );
6789        }
6790    }
6791
6792} ] );
6793
6794var widgetsCheckboxradio = $.ui.checkboxradio;
6795
6796
6797/*!
6798 * jQuery UI Button 1.12.1
6799 * http://jqueryui.com
6800 *
6801 * Copyright jQuery Foundation and other contributors
6802 * Released under the MIT license.
6803 * http://jquery.org/license
6804 */
6805
6806//>>label: Button
6807//>>group: Widgets
6808//>>description: Enhances a form with themeable buttons.
6809//>>docs: http://api.jqueryui.com/button/
6810//>>demos: http://jqueryui.com/button/
6811//>>css.structure: ../../themes/base/core.css
6812//>>css.structure: ../../themes/base/button.css
6813//>>css.theme: ../../themes/base/theme.css
6814
6815
6816
6817$.widget( "ui.button", {
6818    version: "1.12.1",
6819    defaultElement: "<button>",
6820    options: {
6821        classes: {
6822            "ui-button": "ui-corner-all"
6823        },
6824        disabled: null,
6825        icon: null,
6826        iconPosition: "beginning",
6827        label: null,
6828        showLabel: true
6829    },
6830
6831    _getCreateOptions: function() {
6832        var disabled,
6833
6834            // This is to support cases like in jQuery Mobile where the base widget does have
6835            // an implementation of _getCreateOptions
6836            options = this._super() || {};
6837
6838        this.isInput = this.element.is( "input" );
6839
6840        disabled = this.element[ 0 ].disabled;
6841        if ( disabled != null ) {
6842            options.disabled = disabled;
6843        }
6844
6845        this.originalLabel = this.isInput ? this.element.val() : this.element.html();
6846        if ( this.originalLabel ) {
6847            options.label = this.originalLabel;
6848        }
6849
6850        return options;
6851    },
6852
6853    _create: function() {
6854        if ( !this.option.showLabel & !this.options.icon ) {
6855            this.options.showLabel = true;
6856        }
6857
6858        // We have to check the option again here even though we did in _getCreateOptions,
6859        // because null may have been passed on init which would override what was set in
6860        // _getCreateOptions
6861        if ( this.options.disabled == null ) {
6862            this.options.disabled = this.element[ 0 ].disabled || false;
6863        }
6864
6865        this.hasTitle = !!this.element.attr( "title" );
6866
6867        // Check to see if the label needs to be set or if its already correct
6868        if ( this.options.label && this.options.label !== this.originalLabel ) {
6869            if ( this.isInput ) {
6870                this.element.val( this.options.label );
6871            } else {
6872                this.element.html( this.options.label );
6873            }
6874        }
6875        this._addClass( "ui-button", "ui-widget" );
6876        this._setOption( "disabled", this.options.disabled );
6877        this._enhance();
6878
6879        if ( this.element.is( "a" ) ) {
6880            this._on( {
6881                "keyup": function( event ) {
6882                    if ( event.keyCode === $.ui.keyCode.SPACE ) {
6883                        event.preventDefault();
6884
vendor: 4,644 bytes, lines 6885-7026
6885                        // Support: PhantomJS <= 1.9, IE 8 Only
6886                        // If a native click is available use it so we actually cause navigation
6887                        // otherwise just trigger a click event
6888                        if ( this.element[ 0 ].click ) {
6889                            this.element[ 0 ].click();
6890                        } else {
6891                            this.element.trigger( "click" );
6892                        }
6893                    }
6894                }
6895            } );
6896        }
6897    },
6898
6899    _enhance: function() {
6900        if ( !this.element.is( "button" ) ) {
6901            this.element.attr( "role", "button" );
6902        }
6903
6904        if ( this.options.icon ) {
6905            this._updateIcon( "icon", this.options.icon );
6906            this._updateTooltip();
6907        }
6908    },
6909
6910    _updateTooltip: function() {
6911        this.title = this.element.attr( "title" );
6912
6913        if ( !this.options.showLabel && !this.title ) {
6914            this.element.attr( "title", this.options.label );
6915        }
6916    },
6917
6918    _updateIcon: function( option, value ) {
6919        var icon = option !== "iconPosition",
6920            position = icon ? this.options.iconPosition : value,
6921            displayBlock = position === "top" || position === "bottom";
6922
6923        // Create icon
6924        if ( !this.icon ) {
6925            this.icon = $( "<span>" );
6926
6927            this._addClass( this.icon, "ui-button-icon", "ui-icon" );
6928
6929            if ( !this.options.showLabel ) {
6930                this._addClass( "ui-button-icon-only" );
6931            }
6932        } else if ( icon ) {
6933
6934            // If we are updating the icon remove the old icon class
6935            this._removeClass( this.icon, null, this.options.icon );
6936        }
6937
6938        // If we are updating the icon add the new icon class
6939        if ( icon ) {
6940            this._addClass( this.icon, null, value );
6941        }
6942
6943        this._attachIcon( position );
6944
6945        // If the icon is on top or bottom we need to add the ui-widget-icon-block class and remove
6946        // the iconSpace if there is one.
6947        if ( displayBlock ) {
6948            this._addClass( this.icon, null, "ui-widget-icon-block" );
6949            if ( this.iconSpace ) {
6950                this.iconSpace.remove();
6951            }
6952        } else {
6953
6954            // Position is beginning or end so remove the ui-widget-icon-block class and add the
6955            // space if it does not exist
6956            if ( !this.iconSpace ) {
6957                this.iconSpace = $( "<span> </span>" );
6958                this._addClass( this.iconSpace, "ui-button-icon-space" );
6959            }
6960            this._removeClass( this.icon, null, "ui-wiget-icon-block" );
6961            this._attachIconSpace( position );
6962        }
6963    },
6964
6965    _destroy: function() {
6966        this.element.removeAttr( "role" );
6967
6968        if ( this.icon ) {
6969            this.icon.remove();
6970        }
6971        if ( this.iconSpace ) {
6972            this.iconSpace.remove();
6973        }
6974        if ( !this.hasTitle ) {
6975            this.element.removeAttr( "title" );
6976        }
6977    },
6978
6979    _attachIconSpace: function( iconPosition ) {
6980        this.icon[ /^(?:end|bottom)/.test( iconPosition ) ? "before" : "after" ]( this.iconSpace );
6981    },
6982
6983    _attachIcon: function( iconPosition ) {
6984        this.element[ /^(?:end|bottom)/.test( iconPosition ) ? "append" : "prepend" ]( this.icon );
6985    },
6986
6987    _setOptions: function( options ) {
6988        var newShowLabel = options.showLabel === undefined ?
6989                this.options.showLabel :
6990                options.showLabel,
6991            newIcon = options.icon === undefined ? this.options.icon : options.icon;
6992
6993        if ( !newShowLabel && !newIcon ) {
6994            options.showLabel = true;
6995        }
6996        this._super( options );
6997    },
6998
6999    _setOption: function( key, value ) {
7000        if ( key === "icon" ) {
7001            if ( value ) {
7002                this._updateIcon( key, value );
7003            } else if ( this.icon ) {
7004                this.icon.remove();
7005                if ( this.iconSpace ) {
7006                    this.iconSpace.remove();
7007                }
7008            }
7009        }
7010
7011        if ( key === "iconPosition" ) {
7012            this._updateIcon( key, value );
7013        }
7014
7015        // Make sure we can't end up with a button that has neither text nor icon
7016        if ( key === "showLabel" ) {
7017                this._toggleClass( "ui-button-icon-only", null, !value );
7018                this._updateTooltip();
7019        }
7020
7021        if ( key === "label" ) {
7022            if ( this.isInput ) {
7023                this.element.val( value );
7024            } else {
7025
7026                // If there is an icon, append it, else nothing then append the value
vendor: 9,619 bytes, lines 7027-7254
7027                // this avoids removal of the icon when setting label text
7028                this.element.html( value );
7029                if ( this.icon ) {
7030                    this._attachIcon( this.options.iconPosition );
7031                    this._attachIconSpace( this.options.iconPosition );
7032                }
7033            }
7034        }
7035
7036        this._super( key, value );
7037
7038        if ( key === "disabled" ) {
7039            this._toggleClass( null, "ui-state-disabled", value );
7040            this.element[ 0 ].disabled = value;
7041            if ( value ) {
7042                this.element.blur();
7043            }
7044        }
7045    },
7046
7047    refresh: function() {
7048
7049        // Make sure to only check disabled if its an element that supports this otherwise
7050        // check for the disabled class to determine state
7051        var isDisabled = this.element.is( "input, button" ) ?
7052            this.element[ 0 ].disabled : this.element.hasClass( "ui-button-disabled" );
7053
7054        if ( isDisabled !== this.options.disabled ) {
7055            this._setOptions( { disabled: isDisabled } );
7056        }
7057
7058        this._updateTooltip();
7059    }
7060} );
7061
7062// DEPRECATED
7063if ( $.uiBackCompat !== false ) {
7064
7065    // Text and Icons options
7066    $.widget( "ui.button", $.ui.button, {
7067        options: {
7068            text: true,
7069            icons: {
7070                primary: null,
7071                secondary: null
7072            }
7073        },
7074
7075        _create: function() {
7076            if ( this.options.showLabel && !this.options.text ) {
7077                this.options.showLabel = this.options.text;
7078            }
7079            if ( !this.options.showLabel && this.options.text ) {
7080                this.options.text = this.options.showLabel;
7081            }
7082            if ( !this.options.icon && ( this.options.icons.primary ||
7083                    this.options.icons.secondary ) ) {
7084                if ( this.options.icons.primary ) {
7085                    this.options.icon = this.options.icons.primary;
7086                } else {
7087                    this.options.icon = this.options.icons.secondary;
7088                    this.options.iconPosition = "end";
7089                }
7090            } else if ( this.options.icon ) {
7091                this.options.icons.primary = this.options.icon;
7092            }
7093            this._super();
7094        },
7095
7096        _setOption: function( key, value ) {
7097            if ( key === "text" ) {
7098                this._super( "showLabel", value );
7099                return;
7100            }
7101            if ( key === "showLabel" ) {
7102                this.options.text = value;
7103            }
7104            if ( key === "icon" ) {
7105                this.options.icons.primary = value;
7106            }
7107            if ( key === "icons" ) {
7108                if ( value.primary ) {
7109                    this._super( "icon", value.primary );
7110                    this._super( "iconPosition", "beginning" );
7111                } else if ( value.secondary ) {
7112                    this._super( "icon", value.secondary );
7113                    this._super( "iconPosition", "end" );
7114                }
7115            }
7116            this._superApply( arguments );
7117        }
7118    } );
7119
7120    $.fn.button = ( function( orig ) {
7121        return function() {
7122            if ( !this.length || ( this.length && this[ 0 ].tagName !== "INPUT" ) ||
7123                    ( this.length && this[ 0 ].tagName === "INPUT" && (
7124                        this.attr( "type" ) !== "checkbox" && this.attr( "type" ) !== "radio"
7125                    ) ) ) {
7126                return orig.apply( this, arguments );
7127            }
7128            if ( !$.ui.checkboxradio ) {
7129                $.error( "Checkboxradio widget missing" );
7130            }
7131            if ( arguments.length === 0 ) {
7132                return this.checkboxradio( {
7133                    "icon": false
7134                } );
7135            }
7136            return this.checkboxradio.apply( this, arguments );
7137        };
7138    } )( $.fn.button );
7139
7140    $.fn.buttonset = function() {
7141        if ( !$.ui.controlgroup ) {
7142            $.error( "Controlgroup widget missing" );
7143        }
7144        if ( arguments[ 0 ] === "option" && arguments[ 1 ] === "items" && arguments[ 2 ] ) {
7145            return this.controlgroup.apply( this,
7146                [ arguments[ 0 ], "items.button", arguments[ 2 ] ] );
7147        }
7148        if ( arguments[ 0 ] === "option" && arguments[ 1 ] === "items" ) {
7149            return this.controlgroup.apply( this, [ arguments[ 0 ], "items.button" ] );
7150        }
7151        if ( typeof arguments[ 0 ] === "object" && arguments[ 0 ].items ) {
7152            arguments[ 0 ].items = {
7153                button: arguments[ 0 ].items
7154            };
7155        }
7156        return this.controlgroup.apply( this, arguments );
7157    };
7158}
7159
7160var widgetsButton = $.ui.button;
7161
7162
7163// jscs:disable maximumLineLength
7164/* jscs:disable requireCamelCaseOrUpperCaseIdentifiers */
7165/*!
7166 * jQuery UI Datepicker 1.12.1
7167 * http://jqueryui.com
7168 *
7169 * Copyright jQuery Foundation and other contributors
7170 * Released under the MIT license.
7171 * http://jquery.org/license
7172 */
7173
7174//>>label: Datepicker
7175//>>group: Widgets
7176//>>description: Displays a calendar from an input or inline for selecting dates.
7177//>>docs: http://api.jqueryui.com/datepicker/
7178//>>demos: http://jqueryui.com/datepicker/
7179//>>css.structure: ../../themes/base/core.css
7180//>>css.structure: ../../themes/base/datepicker.css
7181//>>css.theme: ../../themes/base/theme.css
7182
7183
7184
7185$.extend( $.ui, { datepicker: { version: "1.12.1" } } );
7186
7187var datepicker_instActive;
7188
7189function datepicker_getZindex( elem ) {
7190    var position, value;
7191    while ( elem.length && elem[ 0 ] !== document ) {
7192
7193        // Ignore z-index if position is set to a value where z-index is ignored by the browser
7194        // This makes behavior of this function consistent across browsers
7195        // WebKit always returns auto if the element is positioned
7196        position = elem.css( "position" );
7197        if ( position === "absolute" || position === "relative" || position === "fixed" ) {
7198
7199            // IE returns 0 when zIndex is not specified
7200            // other browsers return a string
7201            // we ignore the case of nested elements with an explicit value of 0
7202            // <div style="z-index: -10;"><div style="z-index: 0;"></div></div>
7203            value = parseInt( elem.css( "zIndex" ), 10 );
7204            if ( !isNaN( value ) && value !== 0 ) {
7205                return value;
7206            }
7207        }
7208        elem = elem.parent();
7209    }
7210
7211    return 0;
7212}
7213/* Date picker manager.
7214   Use the singleton instance of this class, $.datepicker, to interact with the date picker.
7215   Settings for (groups of) date pickers are maintained in an instance object,
7216   allowing multiple different settings on the same page. */
7217
7218function Datepicker() {
7219    this._curInst = null; // The current instance in use
7220    this._keyEvent = false; // If the last event was a key event
7221    this._disabledInputs = []; // List of date picker inputs that have been disabled
7222    this._datepickerShowing = false; // True if the popup picker is showing , false if not
7223    this._inDialog = false; // True if showing within a "dialog", false if not
7224    this._mainDivId = "ui-datepicker-div"; // The ID of the main datepicker division
7225    this._inlineClass = "ui-datepicker-inline"; // The name of the inline marker class
7226    this._appendClass = "ui-datepicker-append"; // The name of the append marker class
7227    this._triggerClass = "ui-datepicker-trigger"; // The name of the trigger marker class
7228    this._dialogClass = "ui-datepicker-dialog"; // The name of the dialog marker class
7229    this._disableClass = "ui-datepicker-disabled"; // The name of the disabled covering marker class
7230    this._unselectableClass = "ui-datepicker-unselectable"; // The name of the unselectable cell marker class
7231    this._currentClass = "ui-datepicker-current-day"; // The name of the current day marker class
7232    this._dayOverClass = "ui-datepicker-days-cell-over"; // The name of the day hover marker class
7233    this.regional = []; // Available regional settings, indexed by language code
7234    this.regional[ "" ] = { // Default regional settings
7235        closeText: "Done", // Display text for close link
7236        prevText: "Prev", // Display text for previous month link
7237        nextText: "Next", // Display text for next month link
7238        currentText: "Today", // Display text for current month link
7239        monthNames: [ "January","February","March","April","May","June",
7240            "July","August","September","October","November","December" ], // Names of months for drop-down and formatting
7241        monthNamesShort: [ "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" ], // For formatting
7242        dayNames: [ "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday" ], // For formatting
7243        dayNamesShort: [ "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" ], // For formatting
7244        dayNamesMin: [ "Su","Mo","Tu","We","Th","Fr","Sa" ], // Column headings for days starting at Sunday
7245        weekHeader: "Wk", // Column header for week of the year
7246        dateFormat: "mm/dd/yy", // See format options on parseDate
7247        firstDay: 0, // The first day of the week, Sun = 0, Mon = 1, ...
7248        isRTL: false, // True if right-to-left language, false if left-to-right
7249        showMonthAfterYear: false, // True if the year select precedes month, false for month then year
7250        yearSuffix: "" // Additional text to append to the year in the month headers
7251    };
7252    this._defaults = { // Global defaults for all the date picker instances
7253        showOn: "focus", // "focus" for popup on focus,
7254            // "button" for trigger button, or "both" for either
vendor: 6,409 bytes, lines 7255-7363
7255        showAnim: "fadeIn", // Name of jQuery animation for popup
7256        showOptions: {}, // Options for enhanced animations
7257        defaultDate: null, // Used when field is blank: actual date,
7258            // +/-number for offset from today, null for today
7259        appendText: "", // Display text following the input box, e.g. showing the format
7260        buttonText: "...", // Text for trigger button
7261        buttonImage: "", // URL for trigger button image
7262        buttonImageOnly: false, // True if the image appears alone, false if it appears on a button
7263        hideIfNoPrevNext: false, // True to hide next/previous month links
7264            // if not applicable, false to just disable them
7265        navigationAsDateFormat: false, // True if date formatting applied to prev/today/next links
7266        gotoCurrent: false, // True if today link goes back to current selection instead
7267        changeMonth: false, // True if month can be selected directly, false if only prev/next
7268        changeYear: false, // True if year can be selected directly, false if only prev/next
7269        yearRange: "c-10:c+10", // Range of years to display in drop-down,
7270            // either relative to today's year (-nn:+nn), relative to currently displayed year
7271            // (c-nn:c+nn), absolute (nnnn:nnnn), or a combination of the above (nnnn:-n)
7272        showOtherMonths: false, // True to show dates in other months, false to leave blank
7273        selectOtherMonths: false, // True to allow selection of dates in other months, false for unselectable
7274        showWeek: false, // True to show week of the year, false to not show it
7275        calculateWeek: this.iso8601Week, // How to calculate the week of the year,
7276            // takes a Date and returns the number of the week for it
7277        shortYearCutoff: "+10", // Short year values < this are in the current century,
7278            // > this are in the previous century,
7279            // string value starting with "+" for current year + value
7280        minDate: null, // The earliest selectable date, or null for no limit
7281        maxDate: null, // The latest selectable date, or null for no limit
7282        duration: "fast", // Duration of display/closure
7283        beforeShowDay: null, // Function that takes a date and returns an array with
7284            // [0] = true if selectable, false if not, [1] = custom CSS class name(s) or "",
7285            // [2] = cell title (optional), e.g. $.datepicker.noWeekends
7286        beforeShow: null, // Function that takes an input field and
7287            // returns a set of custom settings for the date picker
7288        onSelect: null, // Define a callback function when a date is selected
7289        onChangeMonthYear: null, // Define a callback function when the month or year is changed
7290        onClose: null, // Define a callback function when the datepicker is closed
7291        numberOfMonths: 1, // Number of months to show at a time
7292        showCurrentAtPos: 0, // The position in multipe months at which to show the current month (starting at 0)
7293        stepMonths: 1, // Number of months to step back/forward
7294        stepBigMonths: 12, // Number of months to step back/forward for the big links
7295        altField: "", // Selector for an alternate field to store selected dates into
7296        altFormat: "", // The date format to use for the alternate field
7297        constrainInput: true, // The input is constrained by the current date format
7298        showButtonPanel: false, // True to show button panel, false to not show it
7299        autoSize: false, // True to size the input for the date format, false to leave as is
7300        disabled: false // The initial disabled state
7301    };
7302    $.extend( this._defaults, this.regional[ "" ] );
7303    this.regional.en = $.extend( true, {}, this.regional[ "" ] );
7304    this.regional[ "en-US" ] = $.extend( true, {}, this.regional.en );
7305    this.dpDiv = datepicker_bindHover( $( "<div id='" + this._mainDivId + "' class='ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>" ) );
7306}
7307
7308$.extend( Datepicker.prototype, {
7309    /* Class name added to elements to indicate already configured with a date picker. */
7310    markerClassName: "hasDatepicker",
7311
7312    //Keep track of the maximum number of rows displayed (see #7043)
7313    maxRows: 4,
7314
7315    // TODO rename to "widget" when switching to widget factory
7316    _widgetDatepicker: function() {
7317        return this.dpDiv;
7318    },
7319
7320    /* Override the default settings for all instances of the date picker.
7321     * @param  settings  object - the new settings to use as defaults (anonymous object)
7322     * @return the manager object
7323     */
7324    setDefaults: function( settings ) {
7325        datepicker_extendRemove( this._defaults, settings || {} );
7326        return this;
7327    },
7328
7329    /* Attach the date picker to a jQuery selection.
7330     * @param  target   element - the target input field or division or span
7331     * @param  settings  object - the new settings to use for this date picker instance (anonymous)
7332     */
7333    _attachDatepicker: function( target, settings ) {
7334        var nodeName, inline, inst;
7335        nodeName = target.nodeName.toLowerCase();
7336        inline = ( nodeName === "div" || nodeName === "span" );
7337        if ( !target.id ) {
7338            this.uuid += 1;
7339            target.id = "dp" + this.uuid;
7340        }
7341        inst = this._newInst( $( target ), inline );
7342        inst.settings = $.extend( {}, settings || {} );
7343        if ( nodeName === "input" ) {
7344            this._connectDatepicker( target, inst );
7345        } else if ( inline ) {
7346            this._inlineDatepicker( target, inst );
7347        }
7348    },
7349
7350    /* Create a new instance object. */
7351    _newInst: function( target, inline ) {
7352        var id = target[ 0 ].id.replace( /([^A-Za-z0-9_\-])/g, "\\\\$1" ); // escape jQuery meta chars
7353        return { id: id, input: target, // associated target
7354            selectedDay: 0, selectedMonth: 0, selectedYear: 0, // current selection
7355            drawMonth: 0, drawYear: 0, // month being drawn
7356            inline: inline, // is datepicker inline or not
7357            dpDiv: ( !inline ? this.dpDiv : // presentation div
7358            datepicker_bindHover( $( "<div class='" + this._inlineClass + " ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>" ) ) ) };
7359    },
7360
7361    /* Attach the date picker to an input field. */
7362    _connectDatepicker: function( target, inst ) {
7363        var input = $( target );
vendor: 4,815 bytes, lines 7364-7474
7364        inst.append = $( [] );
7365        inst.trigger = $( [] );
7366        if ( input.hasClass( this.markerClassName ) ) {
7367            return;
7368        }
7369        this._attachments( input, inst );
7370        input.addClass( this.markerClassName ).on( "keydown", this._doKeyDown ).
7371            on( "keypress", this._doKeyPress ).on( "keyup", this._doKeyUp );
7372        this._autoSize( inst );
7373        $.data( target, "datepicker", inst );
7374
7375        //If disabled option is true, disable the datepicker once it has been attached to the input (see ticket #5665)
7376        if ( inst.settings.disabled ) {
7377            this._disableDatepicker( target );
7378        }
7379    },
7380
7381    /* Make attachments based on settings. */
7382    _attachments: function( input, inst ) {
7383        var showOn, buttonText, buttonImage,
7384            appendText = this._get( inst, "appendText" ),
7385            isRTL = this._get( inst, "isRTL" );
7386
7387        if ( inst.append ) {
7388            inst.append.remove();
7389        }
7390        if ( appendText ) {
7391            inst.append = $( "<span class='" + this._appendClass + "'>" + appendText + "</span>" );
7392            input[ isRTL ? "before" : "after" ]( inst.append );
7393        }
7394
7395        input.off( "focus", this._showDatepicker );
7396
7397        if ( inst.trigger ) {
7398            inst.trigger.remove();
7399        }
7400
7401        showOn = this._get( inst, "showOn" );
7402        if ( showOn === "focus" || showOn === "both" ) { // pop-up date picker when in the marked field
7403            input.on( "focus", this._showDatepicker );
7404        }
7405        if ( showOn === "button" || showOn === "both" ) { // pop-up date picker when button clicked
7406            buttonText = this._get( inst, "buttonText" );
7407            buttonImage = this._get( inst, "buttonImage" );
7408            inst.trigger = $( this._get( inst, "buttonImageOnly" ) ?
7409                $( "<img/>" ).addClass( this._triggerClass ).
7410                    attr( { src: buttonImage, alt: buttonText, title: buttonText } ) :
7411                $( "<button type='button'></button>" ).addClass( this._triggerClass ).
7412                    html( !buttonImage ? buttonText : $( "<img/>" ).attr(
7413                    { src:buttonImage, alt:buttonText, title:buttonText } ) ) );
7414            input[ isRTL ? "before" : "after" ]( inst.trigger );
7415            inst.trigger.on( "click", function() {
7416                if ( $.datepicker._datepickerShowing && $.datepicker._lastInput === input[ 0 ] ) {
7417                    $.datepicker._hideDatepicker();
7418                } else if ( $.datepicker._datepickerShowing && $.datepicker._lastInput !== input[ 0 ] ) {
7419                    $.datepicker._hideDatepicker();
7420                    $.datepicker._showDatepicker( input[ 0 ] );
7421                } else {
7422                    $.datepicker._showDatepicker( input[ 0 ] );
7423                }
7424                return false;
7425            } );
7426        }
7427    },
7428
7429    /* Apply the maximum length for the date format. */
7430    _autoSize: function( inst ) {
7431        if ( this._get( inst, "autoSize" ) && !inst.inline ) {
7432            var findMax, max, maxI, i,
7433                date = new Date( 2009, 12 - 1, 20 ), // Ensure double digits
7434                dateFormat = this._get( inst, "dateFormat" );
7435
7436            if ( dateFormat.match( /[DM]/ ) ) {
7437                findMax = function( names ) {
7438                    max = 0;
7439                    maxI = 0;
7440                    for ( i = 0; i < names.length; i++ ) {
7441                        if ( names[ i ].length > max ) {
7442                            max = names[ i ].length;
7443                            maxI = i;
7444                        }
7445                    }
7446                    return maxI;
7447                };
7448                date.setMonth( findMax( this._get( inst, ( dateFormat.match( /MM/ ) ?
7449                    "monthNames" : "monthNamesShort" ) ) ) );
7450                date.setDate( findMax( this._get( inst, ( dateFormat.match( /DD/ ) ?
7451                    "dayNames" : "dayNamesShort" ) ) ) + 20 - date.getDay() );
7452            }
7453            inst.input.attr( "size", this._formatDate( inst, date ).length );
7454        }
7455    },
7456
7457    /* Attach an inline date picker to a div. */
7458    _inlineDatepicker: function( target, inst ) {
7459        var divSpan = $( target );
7460        if ( divSpan.hasClass( this.markerClassName ) ) {
7461            return;
7462        }
7463        divSpan.addClass( this.markerClassName ).append( inst.dpDiv );
7464        $.data( target, "datepicker", inst );
7465        this._setDate( inst, this._getDefaultDate( inst ), true );
7466        this._updateDatepicker( inst );
7467        this._updateAlternate( inst );
7468
7469        //If disabled option is true, disable the datepicker before showing it (see ticket #5665)
7470        if ( inst.settings.disabled ) {
7471            this._disableDatepicker( target );
7472        }
7473
7474        // Set display:block in place of inst.dpDiv.show() which w
vendor: 3,334 bytes, lines 7474-7545
7474on't work on disconnected elements
7475        // http://bugs.jqueryui.com/ticket/7552 - A Datepicker created on a detached div has zero height
7476        inst.dpDiv.css( "display", "block" );
7477    },
7478
7479    /* Pop-up the date picker in a "dialog" box.
7480     * @param  input element - ignored
7481     * @param  date string or Date - the initial date to display
7482     * @param  onSelect  function - the function to call when a date is selected
7483     * @param  settings  object - update the dialog date picker instance's settings (anonymous object)
7484     * @param  pos int[2] - coordinates for the dialog's position within the screen or
7485     *                  event - with x/y coordinates or
7486     *                  leave empty for default (screen centre)
7487     * @return the manager object
7488     */
7489    _dialogDatepicker: function( input, date, onSelect, settings, pos ) {
7490        var id, browserWidth, browserHeight, scrollX, scrollY,
7491            inst = this._dialogInst; // internal instance
7492
7493        if ( !inst ) {
7494            this.uuid += 1;
7495            id = "dp" + this.uuid;
7496            this._dialogInput = $( "<input type='text' id='" + id +
7497                "' style='position: absolute; top: -100px; width: 0px;'/>" );
7498            this._dialogInput.on( "keydown", this._doKeyDown );
7499            $( "body" ).append( this._dialogInput );
7500            inst = this._dialogInst = this._newInst( this._dialogInput, false );
7501            inst.settings = {};
7502            $.data( this._dialogInput[ 0 ], "datepicker", inst );
7503        }
7504        datepicker_extendRemove( inst.settings, settings || {} );
7505        date = ( date && date.constructor === Date ? this._formatDate( inst, date ) : date );
7506        this._dialogInput.val( date );
7507
7508        this._pos = ( pos ? ( pos.length ? pos : [ pos.pageX, pos.pageY ] ) : null );
7509        if ( !this._pos ) {
7510            browserWidth = document.documentElement.clientWidth;
7511            browserHeight = document.documentElement.clientHeight;
7512            scrollX = document.documentElement.scrollLeft || document.body.scrollLeft;
7513            scrollY = document.documentElement.scrollTop || document.body.scrollTop;
7514            this._pos = // should use actual width/height below
7515                [ ( browserWidth / 2 ) - 100 + scrollX, ( browserHeight / 2 ) - 150 + scrollY ];
7516        }
7517
7518        // Move input on screen for focus, but hidden behind dialog
7519        this._dialogInput.css( "left", ( this._pos[ 0 ] + 20 ) + "px" ).css( "top", this._pos[ 1 ] + "px" );
7520        inst.settings.onSelect = onSelect;
7521        this._inDialog = true;
7522        this.dpDiv.addClass( this._dialogClass );
7523        this._showDatepicker( this._dialogInput[ 0 ] );
7524        if ( $.blockUI ) {
7525            $.blockUI( this.dpDiv );
7526        }
7527        $.data( this._dialogInput[ 0 ], "datepicker", inst );
7528        return this;
7529    },
7530
7531    /* Detach a datepicker from its control.
7532     * @param  target   element - the target input field or division or span
7533     */
7534    _destroyDatepicker: function( target ) {
7535        var nodeName,
7536            $target = $( target ),
7537            inst = $.data( target, "datepicker" );
7538
7539        if ( !$target.hasClass( this.markerClassName ) ) {
7540            return;
7541        }
7542
7543        nodeName = target.nodeName.toLowerCase();
7544        $.removeData( target, "datepicker" );
7545        if ( nodeName === "input" ) {
vendor: 4,286 bytes, lines 7546-7651
7546            inst.append.remove();
7547            inst.trigger.remove();
7548            $target.removeClass( this.markerClassName ).
7549                off( "focus", this._showDatepicker ).
7550                off( "keydown", this._doKeyDown ).
7551                off( "keypress", this._doKeyPress ).
7552                off( "keyup", this._doKeyUp );
7553        } else if ( nodeName === "div" || nodeName === "span" ) {
7554            $target.removeClass( this.markerClassName ).empty();
7555        }
7556
7557        if ( datepicker_instActive === inst ) {
7558            datepicker_instActive = null;
7559        }
7560    },
7561
7562    /* Enable the date picker to a jQuery selection.
7563     * @param  target   element - the target input field or division or span
7564     */
7565    _enableDatepicker: function( target ) {
7566        var nodeName, inline,
7567            $target = $( target ),
7568            inst = $.data( target, "datepicker" );
7569
7570        if ( !$target.hasClass( this.markerClassName ) ) {
7571            return;
7572        }
7573
7574        nodeName = target.nodeName.toLowerCase();
7575        if ( nodeName === "input" ) {
7576            target.disabled = false;
7577            inst.trigger.filter( "button" ).
7578                each( function() { this.disabled = false; } ).end().
7579                filter( "img" ).css( { opacity: "1.0", cursor: "" } );
7580        } else if ( nodeName === "div" || nodeName === "span" ) {
7581            inline = $target.children( "." + this._inlineClass );
7582            inline.children().removeClass( "ui-state-disabled" );
7583            inline.find( "select.ui-datepicker-month, select.ui-datepicker-year" ).
7584                prop( "disabled", false );
7585        }
7586        this._disabledInputs = $.map( this._disabledInputs,
7587            function( value ) { return ( value === target ? null : value ); } ); // delete entry
7588    },
7589
7590    /* Disable the date picker to a jQuery selection.
7591     * @param  target   element - the target input field or division or span
7592     */
7593    _disableDatepicker: function( target ) {
7594        var nodeName, inline,
7595            $target = $( target ),
7596            inst = $.data( target, "datepicker" );
7597
7598        if ( !$target.hasClass( this.markerClassName ) ) {
7599            return;
7600        }
7601
7602        nodeName = target.nodeName.toLowerCase();
7603        if ( nodeName === "input" ) {
7604            target.disabled = true;
7605            inst.trigger.filter( "button" ).
7606                each( function() { this.disabled = true; } ).end().
7607                filter( "img" ).css( { opacity: "0.5", cursor: "default" } );
7608        } else if ( nodeName === "div" || nodeName === "span" ) {
7609            inline = $target.children( "." + this._inlineClass );
7610            inline.children().addClass( "ui-state-disabled" );
7611            inline.find( "select.ui-datepicker-month, select.ui-datepicker-year" ).
7612                prop( "disabled", true );
7613        }
7614        this._disabledInputs = $.map( this._disabledInputs,
7615            function( value ) { return ( value === target ? null : value ); } ); // delete entry
7616        this._disabledInputs[ this._disabledInputs.length ] = target;
7617    },
7618
7619    /* Is the first field in a jQuery collection disabled as a datepicker?
7620     * @param  target   element - the target input field or division or span
7621     * @return boolean - true if disabled, false if enabled
7622     */
7623    _isDisabledDatepicker: function( target ) {
7624        if ( !target ) {
7625            return false;
7626        }
7627        for ( var i = 0; i < this._disabledInputs.length; i++ ) {
7628            if ( this._disabledInputs[ i ] === target ) {
7629                return true;
7630            }
7631        }
7632        return false;
7633    },
7634
7635    /* Retrieve the instance data for the target control.
7636     * @param  target  element - the target input field or division or span
7637     * @return  object - the associated instance data
7638     * @throws  error if a jQuery problem getting data
7639     */
7640    _getInst: function( target ) {
7641        try {
7642            return $.data( target, "datepicker" );
7643        }
7644        catch ( err ) {
7645            throw "Missing instance data for this datepicker";
7646        }
7647    },
7648
7649    /* Update or retrieve the settings for a date picker attached to an input field or division.
7650     * @param  target  element - the target input field or division or span
7651     * @param  name object - the new settings to update or
vendor: 14,230 bytes, lines 7652-7982
7652     *              string - the name of the setting to change or retrieve,
7653     *              when retrieving also "all" for all instance settings or
7654     *              "defaults" for all global defaults
7655     * @param  value   any - the new value for the setting
7656     *              (omit if above is an object or to retrieve a value)
7657     */
7658    _optionDatepicker: function( target, name, value ) {
7659        var settings, date, minDate, maxDate,
7660            inst = this._getInst( target );
7661
7662        if ( arguments.length === 2 && typeof name === "string" ) {
7663            return ( name === "defaults" ? $.extend( {}, $.datepicker._defaults ) :
7664                ( inst ? ( name === "all" ? $.extend( {}, inst.settings ) :
7665                this._get( inst, name ) ) : null ) );
7666        }
7667
7668        settings = name || {};
7669        if ( typeof name === "string" ) {
7670            settings = {};
7671            settings[ name ] = value;
7672        }
7673
7674        if ( inst ) {
7675            if ( this._curInst === inst ) {
7676                this._hideDatepicker();
7677            }
7678
7679            date = this._getDateDatepicker( target, true );
7680            minDate = this._getMinMaxDate( inst, "min" );
7681            maxDate = this._getMinMaxDate( inst, "max" );
7682            datepicker_extendRemove( inst.settings, settings );
7683
7684            // reformat the old minDate/maxDate values if dateFormat changes and a new minDate/maxDate isn't provided
7685            if ( minDate !== null && settings.dateFormat !== undefined && settings.minDate === undefined ) {
7686                inst.settings.minDate = this._formatDate( inst, minDate );
7687            }
7688            if ( maxDate !== null && settings.dateFormat !== undefined && settings.maxDate === undefined ) {
7689                inst.settings.maxDate = this._formatDate( inst, maxDate );
7690            }
7691            if ( "disabled" in settings ) {
7692                if ( settings.disabled ) {
7693                    this._disableDatepicker( target );
7694                } else {
7695                    this._enableDatepicker( target );
7696                }
7697            }
7698            this._attachments( $( target ), inst );
7699            this._autoSize( inst );
7700            this._setDate( inst, date );
7701            this._updateAlternate( inst );
7702            this._updateDatepicker( inst );
7703        }
7704    },
7705
7706    // Change method deprecated
7707    _changeDatepicker: function( target, name, value ) {
7708        this._optionDatepicker( target, name, value );
7709    },
7710
7711    /* Redraw the date picker attached to an input field or division.
7712     * @param  target  element - the target input field or division or span
7713     */
7714    _refreshDatepicker: function( target ) {
7715        var inst = this._getInst( target );
7716        if ( inst ) {
7717            this._updateDatepicker( inst );
7718        }
7719    },
7720
7721    /* Set the dates for a jQuery selection.
7722     * @param  target element - the target input field or division or span
7723     * @param  date Date - the new date
7724     */
7725    _setDateDatepicker: function( target, date ) {
7726        var inst = this._getInst( target );
7727        if ( inst ) {
7728            this._setDate( inst, date );
7729            this._updateDatepicker( inst );
7730            this._updateAlternate( inst );
7731        }
7732    },
7733
7734    /* Get the date(s) for the first entry in a jQuery selection.
7735     * @param  target element - the target input field or division or span
7736     * @param  noDefault boolean - true if no default date is to be used
7737     * @return Date - the current date
7738     */
7739    _getDateDatepicker: function( target, noDefault ) {
7740        var inst = this._getInst( target );
7741        if ( inst && !inst.inline ) {
7742            this._setDateFromField( inst, noDefault );
7743        }
7744        return ( inst ? this._getDate( inst ) : null );
7745    },
7746
7747    /* Handle keystrokes. */
7748    _doKeyDown: function( event ) {
7749        var onSelect, dateStr, sel,
7750            inst = $.datepicker._getInst( event.target ),
7751            handled = true,
7752            isRTL = inst.dpDiv.is( ".ui-datepicker-rtl" );
7753
7754        inst._keyEvent = true;
7755        if ( $.datepicker._datepickerShowing ) {
7756            switch ( event.keyCode ) {
7757                case 9: $.datepicker._hideDatepicker();
7758                        handled = false;
7759                        break; // hide on tab out
7760                case 13: sel = $( "td." + $.datepicker._dayOverClass + ":not(." +
7761                                    $.datepicker._currentClass + ")", inst.dpDiv );
7762                        if ( sel[ 0 ] ) {
7763                            $.datepicker._selectDay( event.target, inst.selectedMonth, inst.selectedYear, sel[ 0 ] );
7764                        }
7765
7766                        onSelect = $.datepicker._get( inst, "onSelect" );
7767                        if ( onSelect ) {
7768                            dateStr = $.datepicker._formatDate( inst );
7769
7770                            // Trigger custom callback
7771                            onSelect.apply( ( inst.input ? inst.input[ 0 ] : null ), [ dateStr, inst ] );
7772                        } else {
7773                            $.datepicker._hideDatepicker();
7774                        }
7775
7776                        return false; // don't submit the form
7777                case 27: $.datepicker._hideDatepicker();
7778                        break; // hide on escape
7779                case 33: $.datepicker._adjustDate( event.target, ( event.ctrlKey ?
7780                            -$.datepicker._get( inst, "stepBigMonths" ) :
7781                            -$.datepicker._get( inst, "stepMonths" ) ), "M" );
7782                        break; // previous month/year on page up/+ ctrl
7783                case 34: $.datepicker._adjustDate( event.target, ( event.ctrlKey ?
7784                            +$.datepicker._get( inst, "stepBigMonths" ) :
7785                            +$.datepicker._get( inst, "stepMonths" ) ), "M" );
7786                        break; // next month/year on page down/+ ctrl
7787                case 35: if ( event.ctrlKey || event.metaKey ) {
7788                            $.datepicker._clearDate( event.target );
7789                        }
7790                        handled = event.ctrlKey || event.metaKey;
7791                        break; // clear on ctrl or command +end
7792                case 36: if ( event.ctrlKey || event.metaKey ) {
7793                            $.datepicker._gotoToday( event.target );
7794                        }
7795                        handled = event.ctrlKey || event.metaKey;
7796                        break; // current on ctrl or command +home
7797                case 37: if ( event.ctrlKey || event.metaKey ) {
7798                            $.datepicker._adjustDate( event.target, ( isRTL ? +1 : -1 ), "D" );
7799                        }
7800                        handled = event.ctrlKey || event.metaKey;
7801
7802                        // -1 day on ctrl or command +left
7803                        if ( event.originalEvent.altKey ) {
7804                            $.datepicker._adjustDate( event.target, ( event.ctrlKey ?
7805                                -$.datepicker._get( inst, "stepBigMonths" ) :
7806                                -$.datepicker._get( inst, "stepMonths" ) ), "M" );
7807                        }
7808
7809                        // next month/year on alt +left on Mac
7810                        break;
7811                case 38: if ( event.ctrlKey || event.metaKey ) {
7812                            $.datepicker._adjustDate( event.target, -7, "D" );
7813                        }
7814                        handled = event.ctrlKey || event.metaKey;
7815                        break; // -1 week on ctrl or command +up
7816                case 39: if ( event.ctrlKey || event.metaKey ) {
7817                            $.datepicker._adjustDate( event.target, ( isRTL ? -1 : +1 ), "D" );
7818                        }
7819                        handled = event.ctrlKey || event.metaKey;
7820
7821                        // +1 day on ctrl or command +right
7822                        if ( event.originalEvent.altKey ) {
7823                            $.datepicker._adjustDate( event.target, ( event.ctrlKey ?
7824                                +$.datepicker._get( inst, "stepBigMonths" ) :
7825                                +$.datepicker._get( inst, "stepMonths" ) ), "M" );
7826                        }
7827
7828                        // next month/year on alt +right
7829                        break;
7830                case 40: if ( event.ctrlKey || event.metaKey ) {
7831                            $.datepicker._adjustDate( event.target, +7, "D" );
7832                        }
7833                        handled = event.ctrlKey || event.metaKey;
7834                        break; // +1 week on ctrl or command +down
7835                default: handled = false;
7836            }
7837        } else if ( event.keyCode === 36 && event.ctrlKey ) { // display the date picker on ctrl+home
7838            $.datepicker._showDatepicker( this );
7839        } else {
7840            handled = false;
7841        }
7842
7843        if ( handled ) {
7844            event.preventDefault();
7845            event.stopPropagation();
7846        }
7847    },
7848
7849    /* Filter entered characters - based on date format. */
7850    _doKeyPress: function( event ) {
7851        var chars, chr,
7852            inst = $.datepicker._getInst( event.target );
7853
7854        if ( $.datepicker._get( inst, "constrainInput" ) ) {
7855            chars = $.datepicker._possibleChars( $.datepicker._get( inst, "dateFormat" ) );
7856            chr = String.fromCharCode( event.charCode == null ? event.keyCode : event.charCode );
7857            return event.ctrlKey || event.metaKey || ( chr < " " || !chars || chars.indexOf( chr ) > -1 );
7858        }
7859    },
7860
7861    /* Synchronise manual entry and field/alternate field. */
7862    _doKeyUp: function( event ) {
7863        var date,
7864            inst = $.datepicker._getInst( event.target );
7865
7866        if ( inst.input.val() !== inst.lastVal ) {
7867            try {
7868                date = $.datepicker.parseDate( $.datepicker._get( inst, "dateFormat" ),
7869                    ( inst.input ? inst.input.val() : null ),
7870                    $.datepicker._getFormatConfig( inst ) );
7871
7872                if ( date ) { // only if valid
7873                    $.datepicker._setDateFromField( inst );
7874                    $.datepicker._updateAlternate( inst );
7875                    $.datepicker._updateDatepicker( inst );
7876                }
7877            }
7878            catch ( err ) {
7879            }
7880        }
7881        return true;
7882    },
7883
7884    /* Pop-up the date picker for a given input field.
7885     * If false returned from beforeShow event handler do not show.
7886     * @param  input  element - the input field attached to the date picker or
7887     *                  event - if triggered by focus
7888     */
7889    _showDatepicker: function( input ) {
7890        input = input.target || input;
7891        if ( input.nodeName.toLowerCase() !== "input" ) { // find from button/image trigger
7892            input = $( "input", input.parentNode )[ 0 ];
7893        }
7894
7895        if ( $.datepicker._isDisabledDatepicker( input ) || $.datepicker._lastInput === input ) { // already here
7896            return;
7897        }
7898
7899        var inst, beforeShow, beforeShowSettings, isFixed,
7900            offset, showAnim, duration;
7901
7902        inst = $.datepicker._getInst( input );
7903        if ( $.datepicker._curInst && $.datepicker._curInst !== inst ) {
7904            $.datepicker._curInst.dpDiv.stop( true, true );
7905            if ( inst && $.datepicker._datepickerShowing ) {
7906                $.datepicker._hideDatepicker( $.datepicker._curInst.input[ 0 ] );
7907            }
7908        }
7909
7910        beforeShow = $.datepicker._get( inst, "beforeShow" );
7911        beforeShowSettings = beforeShow ? beforeShow.apply( input, [ input, inst ] ) : {};
7912        if ( beforeShowSettings === false ) {
7913            return;
7914        }
7915        datepicker_extendRemove( inst.settings, beforeShowSettings );
7916
7917        inst.lastVal = null;
7918        $.datepicker._lastInput = input;
7919        $.datepicker._setDateFromField( inst );
7920
7921        if ( $.datepicker._inDialog ) { // hide cursor
7922            input.value = "";
7923        }
7924        if ( !$.datepicker._pos ) { // position below input
7925            $.datepicker._pos = $.datepicker._findPos( input );
7926            $.datepicker._pos[ 1 ] += input.offsetHeight; // add the height
7927        }
7928
7929        isFixed = false;
7930        $( input ).parents().each( function() {
7931            isFixed |= $( this ).css( "position" ) === "fixed";
7932            return !isFixed;
7933        } );
7934
7935        offset = { left: $.datepicker._pos[ 0 ], top: $.datepicker._pos[ 1 ] };
7936        $.datepicker._pos = null;
7937
7938        //to avoid flashes on Firefox
7939        inst.dpDiv.empty();
7940
7941        // determine sizing offscreen
7942        inst.dpDiv.css( { position: "absolute", display: "block", top: "-1000px" } );
7943        $.datepicker._updateDatepicker( inst );
7944
7945        // fix width for dynamic number of date pickers
7946        // and adjust position before showing
7947        offset = $.datepicker._checkOffset( inst, offset, isFixed );
7948        inst.dpDiv.css( { position: ( $.datepicker._inDialog && $.blockUI ?
7949            "static" : ( isFixed ? "fixed" : "absolute" ) ), display: "none",
7950            left: offset.left + "px", top: offset.top + "px" } );
7951
7952        if ( !inst.inline ) {
7953            showAnim = $.datepicker._get( inst, "showAnim" );
7954            duration = $.datepicker._get( inst, "duration" );
7955            inst.dpDiv.css( "z-index", datepicker_getZindex( $( input ) ) + 1 );
7956            $.datepicker._datepickerShowing = true;
7957
7958            if ( $.effects && $.effects.effect[ showAnim ] ) {
7959                inst.dpDiv.show( showAnim, $.datepicker._get( inst, "showOptions" ), duration );
7960            } else {
7961                inst.dpDiv[ showAnim || "show" ]( showAnim ? duration : null );
7962            }
7963
7964            if ( $.datepicker._shouldFocusInput( inst ) ) {
7965                inst.input.trigger( "focus" );
7966            }
7967
7968            $.datepicker._curInst = inst;
7969        }
7970    },
7971
7972    /* Generate the date picker content. */
7973    _updateDatepicker: function( inst ) {
7974        this.maxRows = 4; //Reset the max number of rows being displayed (see #7043)
7975        datepicker_instActive = inst; // for delegate hover events
7976        inst.dpDiv.empty().append( this._generateHTML( inst ) );
7977        this._attachHandlers( inst );
7978
7979        var origyearshtml,
7980            numMonths = this._getNumberOfMonths( inst ),
7981            cols = numMonths[ 1 ],
7982            width = 17,
vendor: 4,815 bytes, lines 7983-8088
7983            activeCell = inst.dpDiv.find( "." + this._dayOverClass + " a" );
7984
7985        if ( activeCell.length > 0 ) {
7986            datepicker_handleMouseover.apply( activeCell.get( 0 ) );
7987        }
7988
7989        inst.dpDiv.removeClass( "ui-datepicker-multi-2 ui-datepicker-multi-3 ui-datepicker-multi-4" ).width( "" );
7990        if ( cols > 1 ) {
7991            inst.dpDiv.addClass( "ui-datepicker-multi-" + cols ).css( "width", ( width * cols ) + "em" );
7992        }
7993        inst.dpDiv[ ( numMonths[ 0 ] !== 1 || numMonths[ 1 ] !== 1 ? "add" : "remove" ) +
7994            "Class" ]( "ui-datepicker-multi" );
7995        inst.dpDiv[ ( this._get( inst, "isRTL" ) ? "add" : "remove" ) +
7996            "Class" ]( "ui-datepicker-rtl" );
7997
7998        if ( inst === $.datepicker._curInst && $.datepicker._datepickerShowing && $.datepicker._shouldFocusInput( inst ) ) {
7999            inst.input.trigger( "focus" );
8000        }
8001
8002        // Deffered render of the years select (to avoid flashes on Firefox)
8003        if ( inst.yearshtml ) {
8004            origyearshtml = inst.yearshtml;
8005            setTimeout( function() {
8006
8007                //assure that inst.yearshtml didn't change.
8008                if ( origyearshtml === inst.yearshtml && inst.yearshtml ) {
8009                    inst.dpDiv.find( "select.ui-datepicker-year:first" ).replaceWith( inst.yearshtml );
8010                }
8011                origyearshtml = inst.yearshtml = null;
8012            }, 0 );
8013        }
8014    },
8015
8016    // #6694 - don't focus the input if it's already focused
8017    // this breaks the change event in IE
8018    // Support: IE and jQuery <1.9
8019    _shouldFocusInput: function( inst ) {
8020        return inst.input && inst.input.is( ":visible" ) && !inst.input.is( ":disabled" ) && !inst.input.is( ":focus" );
8021    },
8022
8023    /* Check positioning to remain on screen. */
8024    _checkOffset: function( inst, offset, isFixed ) {
8025        var dpWidth = inst.dpDiv.outerWidth(),
8026            dpHeight = inst.dpDiv.outerHeight(),
8027            inputWidth = inst.input ? inst.input.outerWidth() : 0,
8028            inputHeight = inst.input ? inst.input.outerHeight() : 0,
8029            viewWidth = document.documentElement.clientWidth + ( isFixed ? 0 : $( document ).scrollLeft() ),
8030            viewHeight = document.documentElement.clientHeight + ( isFixed ? 0 : $( document ).scrollTop() );
8031
8032        offset.left -= ( this._get( inst, "isRTL" ) ? ( dpWidth - inputWidth ) : 0 );
8033        offset.left -= ( isFixed && offset.left === inst.input.offset().left ) ? $( document ).scrollLeft() : 0;
8034        offset.top -= ( isFixed && offset.top === ( inst.input.offset().top + inputHeight ) ) ? $( document ).scrollTop() : 0;
8035
8036        // Now check if datepicker is showing outside window viewport - move to a better place if so.
8037        offset.left -= Math.min( offset.left, ( offset.left + dpWidth > viewWidth && viewWidth > dpWidth ) ?
8038            Math.abs( offset.left + dpWidth - viewWidth ) : 0 );
8039        offset.top -= Math.min( offset.top, ( offset.top + dpHeight > viewHeight && viewHeight > dpHeight ) ?
8040            Math.abs( dpHeight + inputHeight ) : 0 );
8041
8042        return offset;
8043    },
8044
8045    /* Find an object's position on the screen. */
8046    _findPos: function( obj ) {
8047        var position,
8048            inst = this._getInst( obj ),
8049            isRTL = this._get( inst, "isRTL" );
8050
8051        while ( obj && ( obj.type === "hidden" || obj.nodeType !== 1 || $.expr.filters.hidden( obj ) ) ) {
8052            obj = obj[ isRTL ? "previousSibling" : "nextSibling" ];
8053        }
8054
8055        position = $( obj ).offset();
8056        return [ position.left, position.top ];
8057    },
8058
8059    /* Hide the date picker from view.
8060     * @param  input  element - the input field attached to the date picker
8061     */
8062    _hideDatepicker: function( input ) {
8063        var showAnim, duration, postProcess, onClose,
8064            inst = this._curInst;
8065
8066        if ( !inst || ( input && inst !== $.data( input, "datepicker" ) ) ) {
8067            return;
8068        }
8069
8070        if ( this._datepickerShowing ) {
8071            showAnim = this._get( inst, "showAnim" );
8072            duration = this._get( inst, "duration" );
8073            postProcess = function() {
8074                $.datepicker._tidyDialog( inst );
8075            };
8076
8077            // DEPRECATED: after BC for 1.8.x $.effects[ showAnim ] is not needed
8078            if ( $.effects && ( $.effects.effect[ showAnim ] || $.effects[ showAnim ] ) ) {
8079                inst.dpDiv.hide( showAnim, $.datepicker._get( inst, "showOptions" ), duration, postProcess );
8080            } else {
8081                inst.dpDiv[ ( showAnim === "slideDown" ? "slideUp" :
8082                    ( showAnim === "fadeIn" ? "fadeOut" : "hide" ) ) ]( ( showAnim ? duration : null ), postProcess );
8083            }
8084
8085            if ( !showAnim ) {
8086                postProcess();
8087            }
8088            this._datepickerShowing = false;
vendor: 9,760 bytes, lines 8089-8329
8089
8090            onClose = this._get( inst, "onClose" );
8091            if ( onClose ) {
8092                onClose.apply( ( inst.input ? inst.input[ 0 ] : null ), [ ( inst.input ? inst.input.val() : "" ), inst ] );
8093            }
8094
8095            this._lastInput = null;
8096            if ( this._inDialog ) {
8097                this._dialogInput.css( { position: "absolute", left: "0", top: "-100px" } );
8098                if ( $.blockUI ) {
8099                    $.unblockUI();
8100                    $( "body" ).append( this.dpDiv );
8101                }
8102            }
8103            this._inDialog = false;
8104        }
8105    },
8106
8107    /* Tidy up after a dialog display. */
8108    _tidyDialog: function( inst ) {
8109        inst.dpDiv.removeClass( this._dialogClass ).off( ".ui-datepicker-calendar" );
8110    },
8111
8112    /* Close date picker if clicked elsewhere. */
8113    _checkExternalClick: function( event ) {
8114        if ( !$.datepicker._curInst ) {
8115            return;
8116        }
8117
8118        var $target = $( event.target ),
8119            inst = $.datepicker._getInst( $target[ 0 ] );
8120
8121        if ( ( ( $target[ 0 ].id !== $.datepicker._mainDivId &&
8122                $target.parents( "#" + $.datepicker._mainDivId ).length === 0 &&
8123                !$target.hasClass( $.datepicker.markerClassName ) &&
8124                !$target.closest( "." + $.datepicker._triggerClass ).length &&
8125                $.datepicker._datepickerShowing && !( $.datepicker._inDialog && $.blockUI ) ) ) ||
8126            ( $target.hasClass( $.datepicker.markerClassName ) && $.datepicker._curInst !== inst ) ) {
8127                $.datepicker._hideDatepicker();
8128        }
8129    },
8130
8131    /* Adjust one of the date sub-fields. */
8132    _adjustDate: function( id, offset, period ) {
8133        var target = $( id ),
8134            inst = this._getInst( target[ 0 ] );
8135
8136        if ( this._isDisabledDatepicker( target[ 0 ] ) ) {
8137            return;
8138        }
8139        this._adjustInstDate( inst, offset +
8140            ( period === "M" ? this._get( inst, "showCurrentAtPos" ) : 0 ), // undo positioning
8141            period );
8142        this._updateDatepicker( inst );
8143    },
8144
8145    /* Action for current link. */
8146    _gotoToday: function( id ) {
8147        var date,
8148            target = $( id ),
8149            inst = this._getInst( target[ 0 ] );
8150
8151        if ( this._get( inst, "gotoCurrent" ) && inst.currentDay ) {
8152            inst.selectedDay = inst.currentDay;
8153            inst.drawMonth = inst.selectedMonth = inst.currentMonth;
8154            inst.drawYear = inst.selectedYear = inst.currentYear;
8155        } else {
8156            date = new Date();
8157            inst.selectedDay = date.getDate();
8158            inst.drawMonth = inst.selectedMonth = date.getMonth();
8159            inst.drawYear = inst.selectedYear = date.getFullYear();
8160        }
8161        this._notifyChange( inst );
8162        this._adjustDate( target );
8163    },
8164
8165    /* Action for selecting a new month/year. */
8166    _selectMonthYear: function( id, select, period ) {
8167        var target = $( id ),
8168            inst = this._getInst( target[ 0 ] );
8169
8170        inst[ "selected" + ( period === "M" ? "Month" : "Year" ) ] =
8171        inst[ "draw" + ( period === "M" ? "Month" : "Year" ) ] =
8172            parseInt( select.options[ select.selectedIndex ].value, 10 );
8173
8174        this._notifyChange( inst );
8175        this._adjustDate( target );
8176    },
8177
8178    /* Action for selecting a day. */
8179    _selectDay: function( id, month, year, td ) {
8180        var inst,
8181            target = $( id );
8182
8183        if ( $( td ).hasClass( this._unselectableClass ) || this._isDisabledDatepicker( target[ 0 ] ) ) {
8184            return;
8185        }
8186
8187        inst = this._getInst( target[ 0 ] );
8188        inst.selectedDay = inst.currentDay = $( "a", td ).html();
8189        inst.selectedMonth = inst.currentMonth = month;
8190        inst.selectedYear = inst.currentYear = year;
8191        this._selectDate( id, this._formatDate( inst,
8192            inst.currentDay, inst.currentMonth, inst.currentYear ) );
8193    },
8194
8195    /* Erase the input field and hide the date picker. */
8196    _clearDate: function( id ) {
8197        var target = $( id );
8198        this._selectDate( target, "" );
8199    },
8200
8201    /* Update the input field with the selected date. */
8202    _selectDate: function( id, dateStr ) {
8203        var onSelect,
8204            target = $( id ),
8205            inst = this._getInst( target[ 0 ] );
8206
8207        dateStr = ( dateStr != null ? dateStr : this._formatDate( inst ) );
8208        if ( inst.input ) {
8209            inst.input.val( dateStr );
8210        }
8211        this._updateAlternate( inst );
8212
8213        onSelect = this._get( inst, "onSelect" );
8214        if ( onSelect ) {
8215            onSelect.apply( ( inst.input ? inst.input[ 0 ] : null ), [ dateStr, inst ] );  // trigger custom callback
8216        } else if ( inst.input ) {
8217            inst.input.trigger( "change" ); // fire the change event
8218        }
8219
8220        if ( inst.inline ) {
8221            this._updateDatepicker( inst );
8222        } else {
8223            this._hideDatepicker();
8224            this._lastInput = inst.input[ 0 ];
8225            if ( typeof( inst.input[ 0 ] ) !== "object" ) {
8226                inst.input.trigger( "focus" ); // restore focus
8227            }
8228            this._lastInput = null;
8229        }
8230    },
8231
8232    /* Update any alternate field to synchronise with the main field. */
8233    _updateAlternate: function( inst ) {
8234        var altFormat, date, dateStr,
8235            altField = this._get( inst, "altField" );
8236
8237        if ( altField ) { // update alternate field too
8238            altFormat = this._get( inst, "altFormat" ) || this._get( inst, "dateFormat" );
8239            date = this._getDate( inst );
8240            dateStr = this.formatDate( altFormat, date, this._getFormatConfig( inst ) );
8241            $( altField ).val( dateStr );
8242        }
8243    },
8244
8245    /* Set as beforeShowDay function to prevent selection of weekends.
8246     * @param  date  Date - the date to customise
8247     * @return [boolean, string] - is this date selectable?, what is its CSS class?
8248     */
8249    noWeekends: function( date ) {
8250        var day = date.getDay();
8251        return [ ( day > 0 && day < 6 ), "" ];
8252    },
8253
8254    /* Set as calculateWeek to determine the week of the year based on the ISO 8601 definition.
8255     * @param  date  Date - the date to get the week for
8256     * @return  number - the number of the week within the year that contains this date
8257     */
8258    iso8601Week: function( date ) {
8259        var time,
8260            checkDate = new Date( date.getTime() );
8261
8262        // Find Thursday of this week starting on Monday
8263        checkDate.setDate( checkDate.getDate() + 4 - ( checkDate.getDay() || 7 ) );
8264
8265        time = checkDate.getTime();
8266        checkDate.setMonth( 0 ); // Compare with Jan 1
8267        checkDate.setDate( 1 );
8268        return Math.floor( Math.round( ( time - checkDate ) / 86400000 ) / 7 ) + 1;
8269    },
8270
8271    /* Parse a string value into a date object.
8272     * See formatDate below for the possible formats.
8273     *
8274     * @param  format string - the expected format of the date
8275     * @param  value string - the date in the above format
8276     * @param  settings Object - attributes include:
8277     *                  shortYearCutoff  number - the cutoff year for determining the century (optional)
8278     *                  dayNamesShort   string[7] - abbreviated names of the days from Sunday (optional)
8279     *                  dayNames        string[7] - names of the days from Sunday (optional)
8280     *                  monthNamesShort string[12] - abbreviated names of the months (optional)
8281     *                  monthNames      string[12] - names of the months (optional)
8282     * @return  Date - the extracted date value or null if value is blank
8283     */
8284    parseDate: function( format, value, settings ) {
8285        if ( format == null || value == null ) {
8286            throw "Invalid arguments";
8287        }
8288
8289        value = ( typeof value === "object" ? value.toString() : value + "" );
8290        if ( value === "" ) {
8291            return null;
8292        }
8293
8294        var iFormat, dim, extra,
8295            iValue = 0,
8296            shortYearCutoffTemp = ( settings ? settings.shortYearCutoff : null ) || this._defaults.shortYearCutoff,
8297            shortYearCutoff = ( typeof shortYearCutoffTemp !== "string" ? shortYearCutoffTemp :
8298                new Date().getFullYear() % 100 + parseInt( shortYearCutoffTemp, 10 ) ),
8299            dayNamesShort = ( settings ? settings.dayNamesShort : null ) || this._defaults.dayNamesShort,
8300            dayNames = ( settings ? settings.dayNames : null ) || this._defaults.dayNames,
8301            monthNamesShort = ( settings ? settings.monthNamesShort : null ) || this._defaults.monthNamesShort,
8302            monthNames = ( settings ? settings.monthNames : null ) || this._defaults.monthNames,
8303            year = -1,
8304            month = -1,
8305            day = -1,
8306            doy = -1,
8307            literal = false,
8308            date,
8309
8310            // Check whether a format character is doubled
8311            lookAhead = function( match ) {
8312                var matches = ( iFormat + 1 < format.length && format.charAt( iFormat + 1 ) === match );
8313                if ( matches ) {
8314                    iFormat++;
8315                }
8316                return matches;
8317            },
8318
8319            // Extract a number from the string value
8320            getNumber = function( match ) {
8321                var isDoubled = lookAhead( match ),
8322                    size = ( match === "@" ? 14 : ( match === "!" ? 20 :
8323                    ( match === "y" && isDoubled ? 4 : ( match === "o" ? 3 : 2 ) ) ) ),
8324                    minSize = ( match === "y" ? size : 1 ),
8325                    digits = new RegExp( "^\\d{" + minSize + "," + size + "}" ),
8326                    num = value.substring( iValue ).match( digits );
8327                if ( !num ) {
8328                    throw "Missing number at position " + iValue;
8329                }
vendor: 18,717 bytes, lines 8330-8790
8330                iValue += num[ 0 ].length;
8331                return parseInt( num[ 0 ], 10 );
8332            },
8333
8334            // Extract a name from the string value and convert to an index
8335            getName = function( match, shortNames, longNames ) {
8336                var index = -1,
8337                    names = $.map( lookAhead( match ) ? longNames : shortNames, function( v, k ) {
8338                        return [ [ k, v ] ];
8339                    } ).sort( function( a, b ) {
8340                        return -( a[ 1 ].length - b[ 1 ].length );
8341                    } );
8342
8343                $.each( names, function( i, pair ) {
8344                    var name = pair[ 1 ];
8345                    if ( value.substr( iValue, name.length ).toLowerCase() === name.toLowerCase() ) {
8346                        index = pair[ 0 ];
8347                        iValue += name.length;
8348                        return false;
8349                    }
8350                } );
8351                if ( index !== -1 ) {
8352                    return index + 1;
8353                } else {
8354                    throw "Unknown name at position " + iValue;
8355                }
8356            },
8357
8358            // Confirm that a literal character matches the string value
8359            checkLiteral = function() {
8360                if ( value.charAt( iValue ) !== format.charAt( iFormat ) ) {
8361                    throw "Unexpected literal at position " + iValue;
8362                }
8363                iValue++;
8364            };
8365
8366        for ( iFormat = 0; iFormat < format.length; iFormat++ ) {
8367            if ( literal ) {
8368                if ( format.charAt( iFormat ) === "'" && !lookAhead( "'" ) ) {
8369                    literal = false;
8370                } else {
8371                    checkLiteral();
8372                }
8373            } else {
8374                switch ( format.charAt( iFormat ) ) {
8375                    case "d":
8376                        day = getNumber( "d" );
8377                        break;
8378                    case "D":
8379                        getName( "D", dayNamesShort, dayNames );
8380                        break;
8381                    case "o":
8382                        doy = getNumber( "o" );
8383                        break;
8384                    case "m":
8385                        month = getNumber( "m" );
8386                        break;
8387                    case "M":
8388                        month = getName( "M", monthNamesShort, monthNames );
8389                        break;
8390                    case "y":
8391                        year = getNumber( "y" );
8392                        break;
8393                    case "@":
8394                        date = new Date( getNumber( "@" ) );
8395                        year = date.getFullYear();
8396                        month = date.getMonth() + 1;
8397                        day = date.getDate();
8398                        break;
8399                    case "!":
8400                        date = new Date( ( getNumber( "!" ) - this._ticksTo1970 ) / 10000 );
8401                        year = date.getFullYear();
8402                        month = date.getMonth() + 1;
8403                        day = date.getDate();
8404                        break;
8405                    case "'":
8406                        if ( lookAhead( "'" ) ) {
8407                            checkLiteral();
8408                        } else {
8409                            literal = true;
8410                        }
8411                        break;
8412                    default:
8413                        checkLiteral();
8414                }
8415            }
8416        }
8417
8418        if ( iValue < value.length ) {
8419            extra = value.substr( iValue );
8420            if ( !/^\s+/.test( extra ) ) {
8421                throw "Extra/unparsed characters found in date: " + extra;
8422            }
8423        }
8424
8425        if ( year === -1 ) {
8426            year = new Date().getFullYear();
8427        } else if ( year < 100 ) {
8428            year += new Date().getFullYear() - new Date().getFullYear() % 100 +
8429                ( year <= shortYearCutoff ? 0 : -100 );
8430        }
8431
8432        if ( doy > -1 ) {
8433            month = 1;
8434            day = doy;
8435            do {
8436                dim = this._getDaysInMonth( year, month - 1 );
8437                if ( day <= dim ) {
8438                    break;
8439                }
8440                month++;
8441                day -= dim;
8442            } while ( true );
8443        }
8444
8445        date = this._daylightSavingAdjust( new Date( year, month - 1, day ) );
8446        if ( date.getFullYear() !== year || date.getMonth() + 1 !== month || date.getDate() !== day ) {
8447            throw "Invalid date"; // E.g. 31/02/00
8448        }
8449        return date;
8450    },
8451
8452    /* Standard date formats. */
8453    ATOM: "yy-mm-dd", // RFC 3339 (ISO 8601)
8454    COOKIE: "D, dd M yy",
8455    ISO_8601: "yy-mm-dd",
8456    RFC_822: "D, d M y",
8457    RFC_850: "DD, dd-M-y",
8458    RFC_1036: "D, d M y",
8459    RFC_1123: "D, d M yy",
8460    RFC_2822: "D, d M yy",
8461    RSS: "D, d M y", // RFC 822
8462    TICKS: "!",
8463    TIMESTAMP: "@",
8464    W3C: "yy-mm-dd", // ISO 8601
8465
8466    _ticksTo1970: ( ( ( 1970 - 1 ) * 365 + Math.floor( 1970 / 4 ) - Math.floor( 1970 / 100 ) +
8467        Math.floor( 1970 / 400 ) ) * 24 * 60 * 60 * 10000000 ),
8468
8469    /* Format a date object into a string value.
8470     * The format can be combinations of the following:
8471     * d  - day of month (no leading zero)
8472     * dd - day of month (two digit)
8473     * o  - day of year (no leading zeros)
8474     * oo - day of year (three digit)
8475     * D  - day name short
8476     * DD - day name long
8477     * m  - month of year (no leading zero)
8478     * mm - month of year (two digit)
8479     * M  - month name short
8480     * MM - month name long
8481     * y  - year (two digit)
8482     * yy - year (four digit)
8483     * @ - Unix timestamp (ms since 01/01/1970)
8484     * ! - Windows ticks (100ns since 01/01/0001)
8485     * "..." - literal text
8486     * '' - single quote
8487     *
8488     * @param  format string - the desired format of the date
8489     * @param  date Date - the date value to format
8490     * @param  settings Object - attributes include:
8491     *                  dayNamesShort   string[7] - abbreviated names of the days from Sunday (optional)
8492     *                  dayNames        string[7] - names of the days from Sunday (optional)
8493     *                  monthNamesShort string[12] - abbreviated names of the months (optional)
8494     *                  monthNames      string[12] - names of the months (optional)
8495     * @return  string - the date in the above format
8496     */
8497    formatDate: function( format, date, settings ) {
8498        if ( !date ) {
8499            return "";
8500        }
8501
8502        var iFormat,
8503            dayNamesShort = ( settings ? settings.dayNamesShort : null ) || this._defaults.dayNamesShort,
8504            dayNames = ( settings ? settings.dayNames : null ) || this._defaults.dayNames,
8505            monthNamesShort = ( settings ? settings.monthNamesShort : null ) || this._defaults.monthNamesShort,
8506            monthNames = ( settings ? settings.monthNames : null ) || this._defaults.monthNames,
8507
8508            // Check whether a format character is doubled
8509            lookAhead = function( match ) {
8510                var matches = ( iFormat + 1 < format.length && format.charAt( iFormat + 1 ) === match );
8511                if ( matches ) {
8512                    iFormat++;
8513                }
8514                return matches;
8515            },
8516
8517            // Format a number, with leading zero if necessary
8518            formatNumber = function( match, value, len ) {
8519                var num = "" + value;
8520                if ( lookAhead( match ) ) {
8521                    while ( num.length < len ) {
8522                        num = "0" + num;
8523                    }
8524                }
8525                return num;
8526            },
8527
8528            // Format a name, short or long as requested
8529            formatName = function( match, value, shortNames, longNames ) {
8530                return ( lookAhead( match ) ? longNames[ value ] : shortNames[ value ] );
8531            },
8532            output = "",
8533            literal = false;
8534
8535        if ( date ) {
8536            for ( iFormat = 0; iFormat < format.length; iFormat++ ) {
8537                if ( literal ) {
8538                    if ( format.charAt( iFormat ) === "'" && !lookAhead( "'" ) ) {
8539                        literal = false;
8540                    } else {
8541                        output += format.charAt( iFormat );
8542                    }
8543                } else {
8544                    switch ( format.charAt( iFormat ) ) {
8545                        case "d":
8546                            output += formatNumber( "d", date.getDate(), 2 );
8547                            break;
8548                        case "D":
8549                            output += formatName( "D", date.getDay(), dayNamesShort, dayNames );
8550                            break;
8551                        case "o":
8552                            output += formatNumber( "o",
8553                                Math.round( ( new Date( date.getFullYear(), date.getMonth(), date.getDate() ).getTime() - new Date( date.getFullYear(), 0, 0 ).getTime() ) / 86400000 ), 3 );
8554                            break;
8555                        case "m":
8556                            output += formatNumber( "m", date.getMonth() + 1, 2 );
8557                            break;
8558                        case "M":
8559                            output += formatName( "M", date.getMonth(), monthNamesShort, monthNames );
8560                            break;
8561                        case "y":
8562                            output += ( lookAhead( "y" ) ? date.getFullYear() :
8563                                ( date.getFullYear() % 100 < 10 ? "0" : "" ) + date.getFullYear() % 100 );
8564                            break;
8565                        case "@":
8566                            output += date.getTime();
8567                            break;
8568                        case "!":
8569                            output += date.getTime() * 10000 + this._ticksTo1970;
8570                            break;
8571                        case "'":
8572                            if ( lookAhead( "'" ) ) {
8573                                output += "'";
8574                            } else {
8575                                literal = true;
8576                            }
8577                            break;
8578                        default:
8579                            output += format.charAt( iFormat );
8580                    }
8581                }
8582            }
8583        }
8584        return output;
8585    },
8586
8587    /* Extract all possible characters from the date format. */
8588    _possibleChars: function( format ) {
8589        var iFormat,
8590            chars = "",
8591            literal = false,
8592
8593            // Check whether a format character is doubled
8594            lookAhead = function( match ) {
8595                var matches = ( iFormat + 1 < format.length && format.charAt( iFormat + 1 ) === match );
8596                if ( matches ) {
8597                    iFormat++;
8598                }
8599                return matches;
8600            };
8601
8602        for ( iFormat = 0; iFormat < format.length; iFormat++ ) {
8603            if ( literal ) {
8604                if ( format.charAt( iFormat ) === "'" && !lookAhead( "'" ) ) {
8605                    literal = false;
8606                } else {
8607                    chars += format.charAt( iFormat );
8608                }
8609            } else {
8610                switch ( format.charAt( iFormat ) ) {
8611                    case "d": case "m": case "y": case "@":
8612                        chars += "0123456789";
8613                        break;
8614                    case "D": case "M":
8615                        return null; // Accept anything
8616                    case "'":
8617                        if ( lookAhead( "'" ) ) {
8618                            chars += "'";
8619                        } else {
8620                            literal = true;
8621                        }
8622                        break;
8623                    default:
8624                        chars += format.charAt( iFormat );
8625                }
8626            }
8627        }
8628        return chars;
8629    },
8630
8631    /* Get a setting value, defaulting if necessary. */
8632    _get: function( inst, name ) {
8633        return inst.settings[ name ] !== undefined ?
8634            inst.settings[ name ] : this._defaults[ name ];
8635    },
8636
8637    /* Parse existing date and initialise date picker. */
8638    _setDateFromField: function( inst, noDefault ) {
8639        if ( inst.input.val() === inst.lastVal ) {
8640            return;
8641        }
8642
8643        var dateFormat = this._get( inst, "dateFormat" ),
8644            dates = inst.lastVal = inst.input ? inst.input.val() : null,
8645            defaultDate = this._getDefaultDate( inst ),
8646            date = defaultDate,
8647            settings = this._getFormatConfig( inst );
8648
8649        try {
8650            date = this.parseDate( dateFormat, dates, settings ) || defaultDate;
8651        } catch ( event ) {
8652            dates = ( noDefault ? "" : dates );
8653        }
8654        inst.selectedDay = date.getDate();
8655        inst.drawMonth = inst.selectedMonth = date.getMonth();
8656        inst.drawYear = inst.selectedYear = date.getFullYear();
8657        inst.currentDay = ( dates ? date.getDate() : 0 );
8658        inst.currentMonth = ( dates ? date.getMonth() : 0 );
8659        inst.currentYear = ( dates ? date.getFullYear() : 0 );
8660        this._adjustInstDate( inst );
8661    },
8662
8663    /* Retrieve the default date shown on opening. */
8664    _getDefaultDate: function( inst ) {
8665        return this._restrictMinMax( inst,
8666            this._determineDate( inst, this._get( inst, "defaultDate" ), new Date() ) );
8667    },
8668
8669    /* A date may be specified as an exact value or a relative one. */
8670    _determineDate: function( inst, date, defaultDate ) {
8671        var offsetNumeric = function( offset ) {
8672                var date = new Date();
8673                date.setDate( date.getDate() + offset );
8674                return date;
8675            },
8676            offsetString = function( offset ) {
8677                try {
8678                    return $.datepicker.parseDate( $.datepicker._get( inst, "dateFormat" ),
8679                        offset, $.datepicker._getFormatConfig( inst ) );
8680                }
8681                catch ( e ) {
8682
8683                    // Ignore
8684                }
8685
8686                var date = ( offset.toLowerCase().match( /^c/ ) ?
8687                    $.datepicker._getDate( inst ) : null ) || new Date(),
8688                    year = date.getFullYear(),
8689                    month = date.getMonth(),
8690                    day = date.getDate(),
8691                    pattern = /([+\-]?[0-9]+)\s*(d|D|w|W|m|M|y|Y)?/g,
8692                    matches = pattern.exec( offset );
8693
8694                while ( matches ) {
8695                    switch ( matches[ 2 ] || "d" ) {
8696                        case "d" : case "D" :
8697                            day += parseInt( matches[ 1 ], 10 ); break;
8698                        case "w" : case "W" :
8699                            day += parseInt( matches[ 1 ], 10 ) * 7; break;
8700                        case "m" : case "M" :
8701                            month += parseInt( matches[ 1 ], 10 );
8702                            day = Math.min( day, $.datepicker._getDaysInMonth( year, month ) );
8703                            break;
8704                        case "y": case "Y" :
8705                            year += parseInt( matches[ 1 ], 10 );
8706                            day = Math.min( day, $.datepicker._getDaysInMonth( year, month ) );
8707                            break;
8708                    }
8709                    matches = pattern.exec( offset );
8710                }
8711                return new Date( year, month, day );
8712            },
8713            newDate = ( date == null || date === "" ? defaultDate : ( typeof date === "string" ? offsetString( date ) :
8714                ( typeof date === "number" ? ( isNaN( date ) ? defaultDate : offsetNumeric( date ) ) : new Date( date.getTime() ) ) ) );
8715
8716        newDate = ( newDate && newDate.toString() === "Invalid Date" ? defaultDate : newDate );
8717        if ( newDate ) {
8718            newDate.setHours( 0 );
8719            newDate.setMinutes( 0 );
8720            newDate.setSeconds( 0 );
8721            newDate.setMilliseconds( 0 );
8722        }
8723        return this._daylightSavingAdjust( newDate );
8724    },
8725
8726    /* Handle switch to/from daylight saving.
8727     * Hours may be non-zero on daylight saving cut-over:
8728     * > 12 when midnight changeover, but then cannot generate
8729     * midnight datetime, so jump to 1AM, otherwise reset.
8730     * @param  date  (Date) the date to check
8731     * @return  (Date) the corrected date
8732     */
8733    _daylightSavingAdjust: function( date ) {
8734        if ( !date ) {
8735            return null;
8736        }
8737        date.setHours( date.getHours() > 12 ? date.getHours() + 2 : 0 );
8738        return date;
8739    },
8740
8741    /* Set the date(s) directly. */
8742    _setDate: function( inst, date, noChange ) {
8743        var clear = !date,
8744            origMonth = inst.selectedMonth,
8745            origYear = inst.selectedYear,
8746            newDate = this._restrictMinMax( inst, this._determineDate( inst, date, new Date() ) );
8747
8748        inst.selectedDay = inst.currentDay = newDate.getDate();
8749        inst.drawMonth = inst.selectedMonth = inst.currentMonth = newDate.getMonth();
8750        inst.drawYear = inst.selectedYear = inst.currentYear = newDate.getFullYear();
8751        if ( ( origMonth !== inst.selectedMonth || origYear !== inst.selectedYear ) && !noChange ) {
8752            this._notifyChange( inst );
8753        }
8754        this._adjustInstDate( inst );
8755        if ( inst.input ) {
8756            inst.input.val( clear ? "" : this._formatDate( inst ) );
8757        }
8758    },
8759
8760    /* Retrieve the date(s) directly. */
8761    _getDate: function( inst ) {
8762        var startDate = ( !inst.currentYear || ( inst.input && inst.input.val() === "" ) ? null :
8763            this._daylightSavingAdjust( new Date(
8764            inst.currentYear, inst.currentMonth, inst.currentDay ) ) );
8765            return startDate;
8766    },
8767
8768    /* Attach the onxxx handlers.  These are declared statically so
8769     * they work with static code transformers like Caja.
8770     */
8771    _attachHandlers: function( inst ) {
8772        var stepMonths = this._get( inst, "stepMonths" ),
8773            id = "#" + inst.id.replace( /\\\\/g, "\\" );
8774        inst.dpDiv.find( "[data-handler]" ).map( function() {
8775            var handler = {
8776                prev: function() {
8777                    $.datepicker._adjustDate( id, -stepMonths, "M" );
8778                },
8779                next: function() {
8780                    $.datepicker._adjustDate( id, +stepMonths, "M" );
8781                },
8782                hide: function() {
8783                    $.datepicker._hideDatepicker();
8784                },
8785                today: function() {
8786                    $.datepicker._gotoToday( id );
8787                },
8788                selectDay: function() {
8789                    $.datepicker._selectDay( id, +this.getAttribute( "data-month" ), +this.getAttribute( "data-year" ), this );
8790                    return false;
vendor: 6,856 bytes, lines 8791-8907
8791                },
8792                selectMonth: function() {
8793                    $.datepicker._selectMonthYear( id, this, "M" );
8794                    return false;
8795                },
8796                selectYear: function() {
8797                    $.datepicker._selectMonthYear( id, this, "Y" );
8798                    return false;
8799                }
8800            };
8801            $( this ).on( this.getAttribute( "data-event" ), handler[ this.getAttribute( "data-handler" ) ] );
8802        } );
8803    },
8804
8805    /* Generate the HTML for the current state of the date picker. */
8806    _generateHTML: function( inst ) {
8807        var maxDraw, prevText, prev, nextText, next, currentText, gotoDate,
8808            controls, buttonPanel, firstDay, showWeek, dayNames, dayNamesMin,
8809            monthNames, monthNamesShort, beforeShowDay, showOtherMonths,
8810            selectOtherMonths, defaultDate, html, dow, row, group, col, selectedDate,
8811            cornerClass, calender, thead, day, daysInMonth, leadDays, curRows, numRows,
8812            printDate, dRow, tbody, daySettings, otherMonth, unselectable,
8813            tempDate = new Date(),
8814            today = this._daylightSavingAdjust(
8815                new Date( tempDate.getFullYear(), tempDate.getMonth(), tempDate.getDate() ) ), // clear time
8816            isRTL = this._get( inst, "isRTL" ),
8817            showButtonPanel = this._get( inst, "showButtonPanel" ),
8818            hideIfNoPrevNext = this._get( inst, "hideIfNoPrevNext" ),
8819            navigationAsDateFormat = this._get( inst, "navigationAsDateFormat" ),
8820            numMonths = this._getNumberOfMonths( inst ),
8821            showCurrentAtPos = this._get( inst, "showCurrentAtPos" ),
8822            stepMonths = this._get( inst, "stepMonths" ),
8823            isMultiMonth = ( numMonths[ 0 ] !== 1 || numMonths[ 1 ] !== 1 ),
8824            currentDate = this._daylightSavingAdjust( ( !inst.currentDay ? new Date( 9999, 9, 9 ) :
8825                new Date( inst.currentYear, inst.currentMonth, inst.currentDay ) ) ),
8826            minDate = this._getMinMaxDate( inst, "min" ),
8827            maxDate = this._getMinMaxDate( inst, "max" ),
8828            drawMonth = inst.drawMonth - showCurrentAtPos,
8829            drawYear = inst.drawYear;
8830
8831        if ( drawMonth < 0 ) {
8832            drawMonth += 12;
8833            drawYear--;
8834        }
8835        if ( maxDate ) {
8836            maxDraw = this._daylightSavingAdjust( new Date( maxDate.getFullYear(),
8837                maxDate.getMonth() - ( numMonths[ 0 ] * numMonths[ 1 ] ) + 1, maxDate.getDate() ) );
8838            maxDraw = ( minDate && maxDraw < minDate ? minDate : maxDraw );
8839            while ( this._daylightSavingAdjust( new Date( drawYear, drawMonth, 1 ) ) > maxDraw ) {
8840                drawMonth--;
8841                if ( drawMonth < 0 ) {
8842                    drawMonth = 11;
8843                    drawYear--;
8844                }
8845            }
8846        }
8847        inst.drawMonth = drawMonth;
8848        inst.drawYear = drawYear;
8849
8850        prevText = this._get( inst, "prevText" );
8851        prevText = ( !navigationAsDateFormat ? prevText : this.formatDate( prevText,
8852            this._daylightSavingAdjust( new Date( drawYear, drawMonth - stepMonths, 1 ) ),
8853            this._getFormatConfig( inst ) ) );
8854
8855        prev = ( this._canAdjustMonth( inst, -1, drawYear, drawMonth ) ?
8856            "<a class='ui-datepicker-prev ui-corner-all' data-handler='prev' data-event='click'" +
8857            " title='" + prevText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w" ) + "'>" + prevText + "</span></a>" :
8858            ( hideIfNoPrevNext ? "" : "<a class='ui-datepicker-prev ui-corner-all ui-state-disabled' title='" + prevText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w" ) + "'>" + prevText + "</span></a>" ) );
8859
8860        nextText = this._get( inst, "nextText" );
8861        nextText = ( !navigationAsDateFormat ? nextText : this.formatDate( nextText,
8862            this._daylightSavingAdjust( new Date( drawYear, drawMonth + stepMonths, 1 ) ),
8863            this._getFormatConfig( inst ) ) );
8864
8865        next = ( this._canAdjustMonth( inst, +1, drawYear, drawMonth ) ?
8866            "<a class='ui-datepicker-next ui-corner-all' data-handler='next' data-event='click'" +
8867            " title='" + nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e" ) + "'>" + nextText + "</span></a>" :
8868            ( hideIfNoPrevNext ? "" : "<a class='ui-datepicker-next ui-corner-all ui-state-disabled' title='" + nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e" ) + "'>" + nextText + "</span></a>" ) );
8869
8870        currentText = this._get( inst, "currentText" );
8871        gotoDate = ( this._get( inst, "gotoCurrent" ) && inst.currentDay ? currentDate : today );
8872        currentText = ( !navigationAsDateFormat ? currentText :
8873            this.formatDate( currentText, gotoDate, this._getFormatConfig( inst ) ) );
8874
8875        controls = ( !inst.inline ? "<button type='button' class='ui-datepicker-close ui-state-default ui-priority-primary ui-corner-all' data-handler='hide' data-event='click'>" +
8876            this._get( inst, "closeText" ) + "</button>" : "" );
8877
8878        buttonPanel = ( showButtonPanel ) ? "<div class='ui-datepicker-buttonpane ui-widget-content'>" + ( isRTL ? controls : "" ) +
8879            ( this._isInRange( inst, gotoDate ) ? "<button type='button' class='ui-datepicker-current ui-state-default ui-priority-secondary ui-corner-all' data-handler='today' data-event='click'" +
8880            ">" + currentText + "</button>" : "" ) + ( isRTL ? "" : controls ) + "</div>" : "";
8881
8882        firstDay = parseInt( this._get( inst, "firstDay" ), 10 );
8883        firstDay = ( isNaN( firstDay ) ? 0 : firstDay );
8884
8885        showWeek = this._get( inst, "showWeek" );
8886        dayNames = this._get( inst, "dayNames" );
8887        dayNamesMin = this._get( inst, "dayNamesMin" );
8888        monthNames = this._get( inst, "monthNames" );
8889        monthNamesShort = this._get( inst, "monthNamesShort" );
8890        beforeShowDay = this._get( inst, "beforeShowDay" );
8891        showOtherMonths = this._get( inst, "showOtherMonths" );
8892        selectOtherMonths = this._get( inst, "selectOtherMonths" );
8893        defaultDate = this._getDefaultDate( inst );
8894        html = "";
8895
8896        for ( row = 0; row < numMonths[ 0 ]; row++ ) {
8897            group = "";
8898            this.maxRows = 4;
8899            for ( col = 0; col < numMonths[ 1 ]; col++ ) {
8900                selectedDate = this._daylightSavingAdjust( new Date( drawYear, drawMonth, inst.selectedDay ) );
8901                cornerClass = " ui-corner-all";
8902                calender = "";
8903                if ( isMultiMonth ) {
8904                    calender += "<div class='ui-datepicker-group";
8905                    if ( numMonths[ 1 ] > 1 ) {
8906                        switch ( col ) {
8907                            case 0: calender += " ui-datepicker-group-first";
vendor: 6,473 bytes, lines 8908-8986
8908                                cornerClass = " ui-corner-" + ( isRTL ? "right" : "left" ); break;
8909                            case numMonths[ 1 ] - 1: calender += " ui-datepicker-group-last";
8910                                cornerClass = " ui-corner-" + ( isRTL ? "left" : "right" ); break;
8911                            default: calender += " ui-datepicker-group-middle"; cornerClass = ""; break;
8912                        }
8913                    }
8914                    calender += "'>";
8915                }
8916                calender += "<div class='ui-datepicker-header ui-widget-header ui-helper-clearfix" + cornerClass + "'>" +
8917                    ( /all|left/.test( cornerClass ) && row === 0 ? ( isRTL ? next : prev ) : "" ) +
8918                    ( /all|right/.test( cornerClass ) && row === 0 ? ( isRTL ? prev : next ) : "" ) +
8919                    this._generateMonthYearHeader( inst, drawMonth, drawYear, minDate, maxDate,
8920                    row > 0 || col > 0, monthNames, monthNamesShort ) + // draw month headers
8921                    "</div><table class='ui-datepicker-calendar'><thead>" +
8922                    "<tr>";
8923                thead = ( showWeek ? "<th class='ui-datepicker-week-col'>" + this._get( inst, "weekHeader" ) + "</th>" : "" );
8924                for ( dow = 0; dow < 7; dow++ ) { // days of the week
8925                    day = ( dow + firstDay ) % 7;
8926                    thead += "<th scope='col'" + ( ( dow + firstDay + 6 ) % 7 >= 5 ? " class='ui-datepicker-week-end'" : "" ) + ">" +
8927                        "<span title='" + dayNames[ day ] + "'>" + dayNamesMin[ day ] + "</span></th>";
8928                }
8929                calender += thead + "</tr></thead><tbody>";
8930                daysInMonth = this._getDaysInMonth( drawYear, drawMonth );
8931                if ( drawYear === inst.selectedYear && drawMonth === inst.selectedMonth ) {
8932                    inst.selectedDay = Math.min( inst.selectedDay, daysInMonth );
8933                }
8934                leadDays = ( this._getFirstDayOfMonth( drawYear, drawMonth ) - firstDay + 7 ) % 7;
8935                curRows = Math.ceil( ( leadDays + daysInMonth ) / 7 ); // calculate the number of rows to generate
8936                numRows = ( isMultiMonth ? this.maxRows > curRows ? this.maxRows : curRows : curRows ); //If multiple months, use the higher number of rows (see #7043)
8937                this.maxRows = numRows;
8938                printDate = this._daylightSavingAdjust( new Date( drawYear, drawMonth, 1 - leadDays ) );
8939                for ( dRow = 0; dRow < numRows; dRow++ ) { // create date picker rows
8940                    calender += "<tr>";
8941                    tbody = ( !showWeek ? "" : "<td class='ui-datepicker-week-col'>" +
8942                        this._get( inst, "calculateWeek" )( printDate ) + "</td>" );
8943                    for ( dow = 0; dow < 7; dow++ ) { // create date picker days
8944                        daySettings = ( beforeShowDay ?
8945                            beforeShowDay.apply( ( inst.input ? inst.input[ 0 ] : null ), [ printDate ] ) : [ true, "" ] );
8946                        otherMonth = ( printDate.getMonth() !== drawMonth );
8947                        unselectable = ( otherMonth && !selectOtherMonths ) || !daySettings[ 0 ] ||
8948                            ( minDate && printDate < minDate ) || ( maxDate && printDate > maxDate );
8949                        tbody += "<td class='" +
8950                            ( ( dow + firstDay + 6 ) % 7 >= 5 ? " ui-datepicker-week-end" : "" ) + // highlight weekends
8951                            ( otherMonth ? " ui-datepicker-other-month" : "" ) + // highlight days from other months
8952                            ( ( printDate.getTime() === selectedDate.getTime() && drawMonth === inst.selectedMonth && inst._keyEvent ) || // user pressed key
8953                            ( defaultDate.getTime() === printDate.getTime() && defaultDate.getTime() === selectedDate.getTime() ) ?
8954
8955                            // or defaultDate is current printedDate and defaultDate is selectedDate
8956                            " " + this._dayOverClass : "" ) + // highlight selected day
8957                            ( unselectable ? " " + this._unselectableClass + " ui-state-disabled" : "" ) +  // highlight unselectable days
8958                            ( otherMonth && !showOtherMonths ? "" : " " + daySettings[ 1 ] + // highlight custom dates
8959                            ( printDate.getTime() === currentDate.getTime() ? " " + this._currentClass : "" ) + // highlight selected day
8960                            ( printDate.getTime() === today.getTime() ? " ui-datepicker-today" : "" ) ) + "'" + // highlight today (if different)
8961                            ( ( !otherMonth || showOtherMonths ) && daySettings[ 2 ] ? " title='" + daySettings[ 2 ].replace( /'/g, "&#39;" ) + "'" : "" ) + // cell title
8962                            ( unselectable ? "" : " data-handler='selectDay' data-event='click' data-month='" + printDate.getMonth() + "' data-year='" + printDate.getFullYear() + "'" ) + ">" + // actions
8963                            ( otherMonth && !showOtherMonths ? "&#xa0;" : // display for other months
8964                            ( unselectable ? "<span class='ui-state-default'>" + printDate.getDate() + "</span>" : "<a class='ui-state-default" +
8965                            ( printDate.getTime() === today.getTime() ? " ui-state-highlight" : "" ) +
8966                            ( printDate.getTime() === currentDate.getTime() ? " ui-state-active" : "" ) + // highlight selected day
8967                            ( otherMonth ? " ui-priority-secondary" : "" ) + // distinguish dates from other months
8968                            "' href='#'>" + printDate.getDate() + "</a>" ) ) + "</td>"; // display selectable date
8969                        printDate.setDate( printDate.getDate() + 1 );
8970                        printDate = this._daylightSavingAdjust( printDate );
8971                    }
8972                    calender += tbody + "</tr>";
8973                }
8974                drawMonth++;
8975                if ( drawMonth > 11 ) {
8976                    drawMonth = 0;
8977                    drawYear++;
8978                }
8979                calender += "</tbody></table>" + ( isMultiMonth ? "</div>" +
8980                            ( ( numMonths[ 0 ] > 0 && col === numMonths[ 1 ] - 1 ) ? "<div class='ui-datepicker-row-break'></div>" : "" ) : "" );
8981                group += calender;
8982            }
8983            html += group;
8984        }
8985        html += buttonPanel;
8986        inst._keyEvent = false;
vendor: 4,547 bytes, lines 8987-9081
8987        return html;
8988    },
8989
8990    /* Generate the month and year header. */
8991    _generateMonthYearHeader: function( inst, drawMonth, drawYear, minDate, maxDate,
8992            secondary, monthNames, monthNamesShort ) {
8993
8994        var inMinYear, inMaxYear, month, years, thisYear, determineYear, year, endYear,
8995            changeMonth = this._get( inst, "changeMonth" ),
8996            changeYear = this._get( inst, "changeYear" ),
8997            showMonthAfterYear = this._get( inst, "showMonthAfterYear" ),
8998            html = "<div class='ui-datepicker-title'>",
8999            monthHtml = "";
9000
9001        // Month selection
9002        if ( secondary || !changeMonth ) {
9003            monthHtml += "<span class='ui-datepicker-month'>" + monthNames[ drawMonth ] + "</span>";
9004        } else {
9005            inMinYear = ( minDate && minDate.getFullYear() === drawYear );
9006            inMaxYear = ( maxDate && maxDate.getFullYear() === drawYear );
9007            monthHtml += "<select class='ui-datepicker-month' data-handler='selectMonth' data-event='change'>";
9008            for ( month = 0; month < 12; month++ ) {
9009                if ( ( !inMinYear || month >= minDate.getMonth() ) && ( !inMaxYear || month <= maxDate.getMonth() ) ) {
9010                    monthHtml += "<option value='" + month + "'" +
9011                        ( month === drawMonth ? " selected='selected'" : "" ) +
9012                        ">" + monthNamesShort[ month ] + "</option>";
9013                }
9014            }
9015            monthHtml += "</select>";
9016        }
9017
9018        if ( !showMonthAfterYear ) {
9019            html += monthHtml + ( secondary || !( changeMonth && changeYear ) ? "&#xa0;" : "" );
9020        }
9021
9022        // Year selection
9023        if ( !inst.yearshtml ) {
9024            inst.yearshtml = "";
9025            if ( secondary || !changeYear ) {
9026                html += "<span class='ui-datepicker-year'>" + drawYear + "</span>";
9027            } else {
9028
9029                // determine range of years to display
9030                years = this._get( inst, "yearRange" ).split( ":" );
9031                thisYear = new Date().getFullYear();
9032                determineYear = function( value ) {
9033                    var year = ( value.match( /c[+\-].*/ ) ? drawYear + parseInt( value.substring( 1 ), 10 ) :
9034                        ( value.match( /[+\-].*/ ) ? thisYear + parseInt( value, 10 ) :
9035                        parseInt( value, 10 ) ) );
9036                    return ( isNaN( year ) ? thisYear : year );
9037                };
9038                year = determineYear( years[ 0 ] );
9039                endYear = Math.max( year, determineYear( years[ 1 ] || "" ) );
9040                year = ( minDate ? Math.max( year, minDate.getFullYear() ) : year );
9041                endYear = ( maxDate ? Math.min( endYear, maxDate.getFullYear() ) : endYear );
9042                inst.yearshtml += "<select class='ui-datepicker-year' data-handler='selectYear' data-event='change'>";
9043                for ( ; year <= endYear; year++ ) {
9044                    inst.yearshtml += "<option value='" + year + "'" +
9045                        ( year === drawYear ? " selected='selected'" : "" ) +
9046                        ">" + year + "</option>";
9047                }
9048                inst.yearshtml += "</select>";
9049
9050                html += inst.yearshtml;
9051                inst.yearshtml = null;
9052            }
9053        }
9054
9055        html += this._get( inst, "yearSuffix" );
9056        if ( showMonthAfterYear ) {
9057            html += ( secondary || !( changeMonth && changeYear ) ? "&#xa0;" : "" ) + monthHtml;
9058        }
9059        html += "</div>"; // Close datepicker_header
9060        return html;
9061    },
9062
9063    /* Adjust one of the date sub-fields. */
9064    _adjustInstDate: function( inst, offset, period ) {
9065        var year = inst.selectedYear + ( period === "Y" ? offset : 0 ),
9066            month = inst.selectedMonth + ( period === "M" ? offset : 0 ),
9067            day = Math.min( inst.selectedDay, this._getDaysInMonth( year, month ) ) + ( period === "D" ? offset : 0 ),
9068            date = this._restrictMinMax( inst, this._daylightSavingAdjust( new Date( year, month, day ) ) );
9069
9070        inst.selectedDay = date.getDate();
9071        inst.drawMonth = inst.selectedMonth = date.getMonth();
9072        inst.drawYear = inst.selectedYear = date.getFullYear();
9073        if ( period === "M" || period === "Y" ) {
9074            this._notifyChange( inst );
9075        }
9076    },
9077
9078    /* Ensure a date is within any min/max bounds. */
9079    _restrictMinMax: function( inst, date ) {
9080        var minDate = this._getMinMaxDate( inst, "min" ),
9081            maxDate = this._getMinMaxDate( inst, "max" ),
vendor: 27,372 bytes, lines 9082-9894
9082            newDate = ( minDate && date < minDate ? minDate : date );
9083        return ( maxDate && newDate > maxDate ? maxDate : newDate );
9084    },
9085
9086    /* Notify change of month/year. */
9087    _notifyChange: function( inst ) {
9088        var onChange = this._get( inst, "onChangeMonthYear" );
9089        if ( onChange ) {
9090            onChange.apply( ( inst.input ? inst.input[ 0 ] : null ),
9091                [ inst.selectedYear, inst.selectedMonth + 1, inst ] );
9092        }
9093    },
9094
9095    /* Determine the number of months to show. */
9096    _getNumberOfMonths: function( inst ) {
9097        var numMonths = this._get( inst, "numberOfMonths" );
9098        return ( numMonths == null ? [ 1, 1 ] : ( typeof numMonths === "number" ? [ 1, numMonths ] : numMonths ) );
9099    },
9100
9101    /* Determine the current maximum date - ensure no time components are set. */
9102    _getMinMaxDate: function( inst, minMax ) {
9103        return this._determineDate( inst, this._get( inst, minMax + "Date" ), null );
9104    },
9105
9106    /* Find the number of days in a given month. */
9107    _getDaysInMonth: function( year, month ) {
9108        return 32 - this._daylightSavingAdjust( new Date( year, month, 32 ) ).getDate();
9109    },
9110
9111    /* Find the day of the week of the first of a month. */
9112    _getFirstDayOfMonth: function( year, month ) {
9113        return new Date( year, month, 1 ).getDay();
9114    },
9115
9116    /* Determines if we should allow a "next/prev" month display change. */
9117    _canAdjustMonth: function( inst, offset, curYear, curMonth ) {
9118        var numMonths = this._getNumberOfMonths( inst ),
9119            date = this._daylightSavingAdjust( new Date( curYear,
9120            curMonth + ( offset < 0 ? offset : numMonths[ 0 ] * numMonths[ 1 ] ), 1 ) );
9121
9122        if ( offset < 0 ) {
9123            date.setDate( this._getDaysInMonth( date.getFullYear(), date.getMonth() ) );
9124        }
9125        return this._isInRange( inst, date );
9126    },
9127
9128    /* Is the given date in the accepted range? */
9129    _isInRange: function( inst, date ) {
9130        var yearSplit, currentYear,
9131            minDate = this._getMinMaxDate( inst, "min" ),
9132            maxDate = this._getMinMaxDate( inst, "max" ),
9133            minYear = null,
9134            maxYear = null,
9135            years = this._get( inst, "yearRange" );
9136            if ( years ) {
9137                yearSplit = years.split( ":" );
9138                currentYear = new Date().getFullYear();
9139                minYear = parseInt( yearSplit[ 0 ], 10 );
9140                maxYear = parseInt( yearSplit[ 1 ], 10 );
9141                if ( yearSplit[ 0 ].match( /[+\-].*/ ) ) {
9142                    minYear += currentYear;
9143                }
9144                if ( yearSplit[ 1 ].match( /[+\-].*/ ) ) {
9145                    maxYear += currentYear;
9146                }
9147            }
9148
9149        return ( ( !minDate || date.getTime() >= minDate.getTime() ) &&
9150            ( !maxDate || date.getTime() <= maxDate.getTime() ) &&
9151            ( !minYear || date.getFullYear() >= minYear ) &&
9152            ( !maxYear || date.getFullYear() <= maxYear ) );
9153    },
9154
9155    /* Provide the configuration settings for formatting/parsing. */
9156    _getFormatConfig: function( inst ) {
9157        var shortYearCutoff = this._get( inst, "shortYearCutoff" );
9158        shortYearCutoff = ( typeof shortYearCutoff !== "string" ? shortYearCutoff :
9159            new Date().getFullYear() % 100 + parseInt( shortYearCutoff, 10 ) );
9160        return { shortYearCutoff: shortYearCutoff,
9161            dayNamesShort: this._get( inst, "dayNamesShort" ), dayNames: this._get( inst, "dayNames" ),
9162            monthNamesShort: this._get( inst, "monthNamesShort" ), monthNames: this._get( inst, "monthNames" ) };
9163    },
9164
9165    /* Format the given date for display. */
9166    _formatDate: function( inst, day, month, year ) {
9167        if ( !day ) {
9168            inst.currentDay = inst.selectedDay;
9169            inst.currentMonth = inst.selectedMonth;
9170            inst.currentYear = inst.selectedYear;
9171        }
9172        var date = ( day ? ( typeof day === "object" ? day :
9173            this._daylightSavingAdjust( new Date( year, month, day ) ) ) :
9174            this._daylightSavingAdjust( new Date( inst.currentYear, inst.currentMonth, inst.currentDay ) ) );
9175        return this.formatDate( this._get( inst, "dateFormat" ), date, this._getFormatConfig( inst ) );
9176    }
9177} );
9178
9179/*
9180 * Bind hover events for datepicker elements.
9181 * Done via delegate so the binding only occurs once in the lifetime of the parent div.
9182 * Global datepicker_instActive, set by _updateDatepicker allows the handlers to find their way back to the active picker.
9183 */
9184function datepicker_bindHover( dpDiv ) {
9185    var selector = "button, .ui-datepicker-prev, .ui-datepicker-next, .ui-datepicker-calendar td a";
9186    return dpDiv.on( "mouseout", selector, function() {
9187            $( this ).removeClass( "ui-state-hover" );
9188            if ( this.className.indexOf( "ui-datepicker-prev" ) !== -1 ) {
9189                $( this ).removeClass( "ui-datepicker-prev-hover" );
9190            }
9191            if ( this.className.indexOf( "ui-datepicker-next" ) !== -1 ) {
9192                $( this ).removeClass( "ui-datepicker-next-hover" );
9193            }
9194        } )
9195        .on( "mouseover", selector, datepicker_handleMouseover );
9196}
9197
9198function datepicker_handleMouseover() {
9199    if ( !$.datepicker._isDisabledDatepicker( datepicker_instActive.inline ? datepicker_instActive.dpDiv.parent()[ 0 ] : datepicker_instActive.input[ 0 ] ) ) {
9200        $( this ).parents( ".ui-datepicker-calendar" ).find( "a" ).removeClass( "ui-state-hover" );
9201        $( this ).addClass( "ui-state-hover" );
9202        if ( this.className.indexOf( "ui-datepicker-prev" ) !== -1 ) {
9203            $( this ).addClass( "ui-datepicker-prev-hover" );
9204        }
9205        if ( this.className.indexOf( "ui-datepicker-next" ) !== -1 ) {
9206            $( this ).addClass( "ui-datepicker-next-hover" );
9207        }
9208    }
9209}
9210
9211/* jQuery extend now ignores nulls! */
9212function datepicker_extendRemove( target, props ) {
9213    $.extend( target, props );
9214    for ( var name in props ) {
9215        if ( props[ name ] == null ) {
9216            target[ name ] = props[ name ];
9217        }
9218    }
9219    return target;
9220}
9221
9222/* Invoke the datepicker functionality.
9223   @param  options  string - a command, optionally followed by additional parameters or
9224                    Object - settings for attaching new datepicker functionality
9225   @return  jQuery object */
9226$.fn.datepicker = function( options ) {
9227
9228    /* Verify an empty collection wasn't passed - Fixes #6976 */
9229    if ( !this.length ) {
9230        return this;
9231    }
9232
9233    /* Initialise the date picker. */
9234    if ( !$.datepicker.initialized ) {
9235        $( document ).on( "mousedown", $.datepicker._checkExternalClick );
9236        $.datepicker.initialized = true;
9237    }
9238
9239    /* Append datepicker main container to body if not exist. */
9240    if ( $( "#" + $.datepicker._mainDivId ).length === 0 ) {
9241        $( "body" ).append( $.datepicker.dpDiv );
9242    }
9243
9244    var otherArgs = Array.prototype.slice.call( arguments, 1 );
9245    if ( typeof options === "string" && ( options === "isDisabled" || options === "getDate" || options === "widget" ) ) {
9246        return $.datepicker[ "_" + options + "Datepicker" ].
9247            apply( $.datepicker, [ this[ 0 ] ].concat( otherArgs ) );
9248    }
9249    if ( options === "option" && arguments.length === 2 && typeof arguments[ 1 ] === "string" ) {
9250        return $.datepicker[ "_" + options + "Datepicker" ].
9251            apply( $.datepicker, [ this[ 0 ] ].concat( otherArgs ) );
9252    }
9253    return this.each( function() {
9254        typeof options === "string" ?
9255            $.datepicker[ "_" + options + "Datepicker" ].
9256                apply( $.datepicker, [ this ].concat( otherArgs ) ) :
9257            $.datepicker._attachDatepicker( this, options );
9258    } );
9259};
9260
9261$.datepicker = new Datepicker(); // singleton instance
9262$.datepicker.initialized = false;
9263$.datepicker.uuid = new Date().getTime();
9264$.datepicker.version = "1.12.1";
9265
9266var widgetsDatepicker = $.datepicker;
9267
9268
9269
9270
9271// This file is deprecated
9272var ie = $.ui.ie = !!/msie [\w.]+/.exec( navigator.userAgent.toLowerCase() );
9273
9274/*!
9275 * jQuery UI Mouse 1.12.1
9276 * http://jqueryui.com
9277 *
9278 * Copyright jQuery Foundation and other contributors
9279 * Released under the MIT license.
9280 * http://jquery.org/license
9281 */
9282
9283//>>label: Mouse
9284//>>group: Widgets
9285//>>description: Abstracts mouse-based interactions to assist in creating certain widgets.
9286//>>docs: http://api.jqueryui.com/mouse/
9287
9288
9289
9290var mouseHandled = false;
9291$( document ).on( "mouseup", function() {
9292    mouseHandled = false;
9293} );
9294
9295var widgetsMouse = $.widget( "ui.mouse", {
9296    version: "1.12.1",
9297    options: {
9298        cancel: "input, textarea, button, select, option",
9299        distance: 1,
9300        delay: 0
9301    },
9302    _mouseInit: function() {
9303        var that = this;
9304
9305        this.element
9306            .on( "mousedown." + this.widgetName, function( event ) {
9307                return that._mouseDown( event );
9308            } )
9309            .on( "click." + this.widgetName, function( event ) {
9310                if ( true === $.data( event.target, that.widgetName + ".preventClickEvent" ) ) {
9311                    $.removeData( event.target, that.widgetName + ".preventClickEvent" );
9312                    event.stopImmediatePropagation();
9313                    return false;
9314                }
9315            } );
9316
9317        this.started = false;
9318    },
9319
9320    // TODO: make sure destroying one instance of mouse doesn't mess with
9321    // other instances of mouse
9322    _mouseDestroy: function() {
9323        this.element.off( "." + this.widgetName );
9324        if ( this._mouseMoveDelegate ) {
9325            this.document
9326                .off( "mousemove." + this.widgetName, this._mouseMoveDelegate )
9327                .off( "mouseup." + this.widgetName, this._mouseUpDelegate );
9328        }
9329    },
9330
9331    _mouseDown: function( event ) {
9332
9333        // don't let more than one widget handle mouseStart
9334        if ( mouseHandled ) {
9335            return;
9336        }
9337
9338        this._mouseMoved = false;
9339
9340        // We may have missed mouseup (out of window)
9341        ( this._mouseStarted && this._mouseUp( event ) );
9342
9343        this._mouseDownEvent = event;
9344
9345        var that = this,
9346            btnIsLeft = ( event.which === 1 ),
9347
9348            // event.target.nodeName works around a bug in IE 8 with
9349            // disabled inputs (#7620)
9350            elIsCancel = ( typeof this.options.cancel === "string" && event.target.nodeName ?
9351                $( event.target ).closest( this.options.cancel ).length : false );
9352        if ( !btnIsLeft || elIsCancel || !this._mouseCapture( event ) ) {
9353            return true;
9354        }
9355
9356        this.mouseDelayMet = !this.options.delay;
9357        if ( !this.mouseDelayMet ) {
9358            this._mouseDelayTimer = setTimeout( function() {
9359                that.mouseDelayMet = true;
9360            }, this.options.delay );
9361        }
9362
9363        if ( this._mouseDistanceMet( event ) && this._mouseDelayMet( event ) ) {
9364            this._mouseStarted = ( this._mouseStart( event ) !== false );
9365            if ( !this._mouseStarted ) {
9366                event.preventDefault();
9367                return true;
9368            }
9369        }
9370
9371        // Click event may never have fired (Gecko & Opera)
9372        if ( true === $.data( event.target, this.widgetName + ".preventClickEvent" ) ) {
9373            $.removeData( event.target, this.widgetName + ".preventClickEvent" );
9374        }
9375
9376        // These delegates are required to keep context
9377        this._mouseMoveDelegate = function( event ) {
9378            return that._mouseMove( event );
9379        };
9380        this._mouseUpDelegate = function( event ) {
9381            return that._mouseUp( event );
9382        };
9383
9384        this.document
9385            .on( "mousemove." + this.widgetName, this._mouseMoveDelegate )
9386            .on( "mouseup." + this.widgetName, this._mouseUpDelegate );
9387
9388        event.preventDefault();
9389
9390        mouseHandled = true;
9391        return true;
9392    },
9393
9394    _mouseMove: function( event ) {
9395
9396        // Only check for mouseups outside the document if you've moved inside the document
9397        // at least once. This prevents the firing of mouseup in the case of IE<9, which will
9398        // fire a mousemove event if content is placed under the cursor. See #7778
9399        // Support: IE <9
9400        if ( this._mouseMoved ) {
9401
9402            // IE mouseup check - mouseup happened when mouse was out of window
9403            if ( $.ui.ie && ( !document.documentMode || document.documentMode < 9 ) &&
9404                    !event.button ) {
9405                return this._mouseUp( event );
9406
9407            // Iframe mouseup check - mouseup occurred in another document
9408            } else if ( !event.which ) {
9409
9410                // Support: Safari <=8 - 9
9411                // Safari sets which to 0 if you press any of the following keys
9412                // during a drag (#14461)
9413                if ( event.originalEvent.altKey || event.originalEvent.ctrlKey ||
9414                        event.originalEvent.metaKey || event.originalEvent.shiftKey ) {
9415                    this.ignoreMissingWhich = true;
9416                } else if ( !this.ignoreMissingWhich ) {
9417                    return this._mouseUp( event );
9418                }
9419            }
9420        }
9421
9422        if ( event.which || event.button ) {
9423            this._mouseMoved = true;
9424        }
9425
9426        if ( this._mouseStarted ) {
9427            this._mouseDrag( event );
9428            return event.preventDefault();
9429        }
9430
9431        if ( this._mouseDistanceMet( event ) && this._mouseDelayMet( event ) ) {
9432            this._mouseStarted =
9433                ( this._mouseStart( this._mouseDownEvent, event ) !== false );
9434            ( this._mouseStarted ? this._mouseDrag( event ) : this._mouseUp( event ) );
9435        }
9436
9437        return !this._mouseStarted;
9438    },
9439
9440    _mouseUp: function( event ) {
9441        this.document
9442            .off( "mousemove." + this.widgetName, this._mouseMoveDelegate )
9443            .off( "mouseup." + this.widgetName, this._mouseUpDelegate );
9444
9445        if ( this._mouseStarted ) {
9446            this._mouseStarted = false;
9447
9448            if ( event.target === this._mouseDownEvent.target ) {
9449                $.data( event.target, this.widgetName + ".preventClickEvent", true );
9450            }
9451
9452            this._mouseStop( event );
9453        }
9454
9455        if ( this._mouseDelayTimer ) {
9456            clearTimeout( this._mouseDelayTimer );
9457            delete this._mouseDelayTimer;
9458        }
9459
9460        this.ignoreMissingWhich = false;
9461        mouseHandled = false;
9462        event.preventDefault();
9463    },
9464
9465    _mouseDistanceMet: function( event ) {
9466        return ( Math.max(
9467                Math.abs( this._mouseDownEvent.pageX - event.pageX ),
9468                Math.abs( this._mouseDownEvent.pageY - event.pageY )
9469            ) >= this.options.distance
9470        );
9471    },
9472
9473    _mouseDelayMet: function( /* event */ ) {
9474        return this.mouseDelayMet;
9475    },
9476
9477    // These are placeholder methods, to be overriden by extending plugin
9478    _mouseStart: function( /* event */ ) {},
9479    _mouseDrag: function( /* event */ ) {},
9480    _mouseStop: function( /* event */ ) {},
9481    _mouseCapture: function( /* event */ ) { return true; }
9482} );
9483
9484
9485
9486
9487// $.ui.plugin is deprecated. Use $.widget() extensions instead.
9488var plugin = $.ui.plugin = {
9489    add: function( module, option, set ) {
9490        var i,
9491            proto = $.ui[ module ].prototype;
9492        for ( i in set ) {
9493            proto.plugins[ i ] = proto.plugins[ i ] || [];
9494            proto.plugins[ i ].push( [ option, set[ i ] ] );
9495        }
9496    },
9497    call: function( instance, name, args, allowDisconnected ) {
9498        var i,
9499            set = instance.plugins[ name ];
9500
9501        if ( !set ) {
9502            return;
9503        }
9504
9505        if ( !allowDisconnected && ( !instance.element[ 0 ].parentNode ||
9506                instance.element[ 0 ].parentNode.nodeType === 11 ) ) {
9507            return;
9508        }
9509
9510        for ( i = 0; i < set.length; i++ ) {
9511            if ( instance.options[ set[ i ][ 0 ] ] ) {
9512                set[ i ][ 1 ].apply( instance.element, args );
9513            }
9514        }
9515    }
9516};
9517
9518
9519
9520var safeBlur = $.ui.safeBlur = function( element ) {
9521
9522    // Support: IE9 - 10 only
9523    // If the <body> is blurred, IE will switch windows, see #9420
9524    if ( element && element.nodeName.toLowerCase() !== "body" ) {
9525        $( element ).trigger( "blur" );
9526    }
9527};
9528
9529
9530/*!
9531 * jQuery UI Draggable 1.12.1
9532 * http://jqueryui.com
9533 *
9534 * Copyright jQuery Foundation and other contributors
9535 * Released under the MIT license.
9536 * http://jquery.org/license
9537 */
9538
9539//>>label: Draggable
9540//>>group: Interactions
9541//>>description: Enables dragging functionality for any element.
9542//>>docs: http://api.jqueryui.com/draggable/
9543//>>demos: http://jqueryui.com/draggable/
9544//>>css.structure: ../../themes/base/draggable.css
9545
9546
9547
9548$.widget( "ui.draggable", $.ui.mouse, {
9549    version: "1.12.1",
9550    widgetEventPrefix: "drag",
9551    options: {
9552        addClasses: true,
9553        appendTo: "parent",
9554        axis: false,
9555        connectToSortable: false,
9556        containment: false,
9557        cursor: "auto",
9558        cursorAt: false,
9559        grid: false,
9560        handle: false,
9561        helper: "original",
9562        iframeFix: false,
9563        opacity: false,
9564        refreshPositions: false,
9565        revert: false,
9566        revertDuration: 500,
9567        scope: "default",
9568        scroll: true,
9569        scrollSensitivity: 20,
9570        scrollSpeed: 20,
9571        snap: false,
9572        snapMode: "both",
9573        snapTolerance: 20,
9574        stack: false,
9575        zIndex: false,
9576
9577        // Callbacks
9578        drag: null,
9579        start: null,
9580        stop: null
9581    },
9582    _create: function() {
9583
9584        if ( this.options.helper === "original" ) {
9585            this._setPositionRelative();
9586        }
9587        if ( this.options.addClasses ) {
9588            this._addClass( "ui-draggable" );
9589        }
9590        this._setHandleClassName();
9591
9592        this._mouseInit();
9593    },
9594
9595    _setOption: function( key, value ) {
9596        this._super( key, value );
9597        if ( key === "handle" ) {
9598            this._removeHandleClassName();
9599            this._setHandleClassName();
9600        }
9601    },
9602
9603    _destroy: function() {
9604        if ( ( this.helper || this.element ).is( ".ui-draggable-dragging" ) ) {
9605            this.destroyOnClear = true;
9606            return;
9607        }
9608        this._removeHandleClassName();
9609        this._mouseDestroy();
9610    },
9611
9612    _mouseCapture: function( event ) {
9613        var o = this.options;
9614
9615        // Among others, prevent a drag on a resizable-handle
9616        if ( this.helper || o.disabled ||
9617                $( event.target ).closest( ".ui-resizable-handle" ).length > 0 ) {
9618            return false;
9619        }
9620
9621        //Quit if we're not on a valid handle
9622        this.handle = this._getHandle( event );
9623        if ( !this.handle ) {
9624            return false;
9625        }
9626
9627        this._blurActiveElement( event );
9628
9629        this._blockFrames( o.iframeFix === true ? "iframe" : o.iframeFix );
9630
9631        return true;
9632
9633    },
9634
9635    _blockFrames: function( selector ) {
9636        this.iframeBlocks = this.document.find( selector ).map( function() {
9637            var iframe = $( this );
9638
9639            return $( "<div>" )
9640                .css( "position", "absolute" )
9641                .appendTo( iframe.parent() )
9642                .outerWidth( iframe.outerWidth() )
9643                .outerHeight( iframe.outerHeight() )
9644                .offset( iframe.offset() )[ 0 ];
9645        } );
9646    },
9647
9648    _unblockFrames: function() {
9649        if ( this.iframeBlocks ) {
9650            this.iframeBlocks.remove();
9651            delete this.iframeBlocks;
9652        }
9653    },
9654
9655    _blurActiveElement: function( event ) {
9656        var activeElement = $.ui.safeActiveElement( this.document[ 0 ] ),
9657            target = $( event.target );
9658
9659        // Don't blur if the event occurred on an element that is within
9660        // the currently focused element
9661        // See #10527, #12472
9662        if ( target.closest( activeElement ).length ) {
9663            return;
9664        }
9665
9666        // Blur any element that currently has focus, see #4261
9667        $.ui.safeBlur( activeElement );
9668    },
9669
9670    _mouseStart: function( event ) {
9671
9672        var o = this.options;
9673
9674        //Create and append the visible helper
9675        this.helper = this._createHelper( event );
9676
9677        this._addClass( this.helper, "ui-draggable-dragging" );
9678
9679        //Cache the helper size
9680        this._cacheHelperProportions();
9681
9682        //If ddmanager is used for droppables, set the global draggable
9683        if ( $.ui.ddmanager ) {
9684            $.ui.ddmanager.current = this;
9685        }
9686
9687        /*
9688         * - Position generation -
9689         * This block generates everything position related - it's the core of draggables.
9690         */
9691
9692        //Cache the margins of the original element
9693        this._cacheMargins();
9694
9695        //Store the helper's css position
9696        this.cssPosition = this.helper.css( "position" );
9697        this.scrollParent = this.helper.scrollParent( true );
9698        this.offsetParent = this.helper.offsetParent();
9699        this.hasFixedAncestor = this.helper.parents().filter( function() {
9700                return $( this ).css( "position" ) === "fixed";
9701            } ).length > 0;
9702
9703        //The element's absolute position on the page minus margins
9704        this.positionAbs = this.element.offset();
9705        this._refreshOffsets( event );
9706
9707        //Generate the original position
9708        this.originalPosition = this.position = this._generatePosition( event, false );
9709        this.originalPageX = event.pageX;
9710        this.originalPageY = event.pageY;
9711
9712        //Adjust the mouse offset relative to the helper if "cursorAt" is supplied
9713        ( o.cursorAt && this._adjustOffsetFromHelper( o.cursorAt ) );
9714
9715        //Set a containment if given in the options
9716        this._setContainment();
9717
9718        //Trigger event + callbacks
9719        if ( this._trigger( "start", event ) === false ) {
9720            this._clear();
9721            return false;
9722        }
9723
9724        //Recache the helper size
9725        this._cacheHelperProportions();
9726
9727        //Prepare the droppable offsets
9728        if ( $.ui.ddmanager && !o.dropBehaviour ) {
9729            $.ui.ddmanager.prepareOffsets( this, event );
9730        }
9731
9732        // Execute the drag once - this causes the helper not to be visible before getting its
9733        // correct position
9734        this._mouseDrag( event, true );
9735
9736        // If the ddmanager is used for droppables, inform the manager that dragging has started
9737        // (see #5003)
9738        if ( $.ui.ddmanager ) {
9739            $.ui.ddmanager.dragStart( this, event );
9740        }
9741
9742        return true;
9743    },
9744
9745    _refreshOffsets: function( event ) {
9746        this.offset = {
9747            top: this.positionAbs.top - this.margins.top,
9748            left: this.positionAbs.left - this.margins.left,
9749            scroll: false,
9750            parent: this._getParentOffset(),
9751            relative: this._getRelativeOffset()
9752        };
9753
9754        this.offset.click = {
9755            left: event.pageX - this.offset.left,
9756            top: event.pageY - this.offset.top
9757        };
9758    },
9759
9760    _mouseDrag: function( event, noPropagation ) {
9761
9762        // reset any necessary cached properties (see #5009)
9763        if ( this.hasFixedAncestor ) {
9764            this.offset.parent = this._getParentOffset();
9765        }
9766
9767        //Compute the helpers position
9768        this.position = this._generatePosition( event, true );
9769        this.positionAbs = this._convertPositionTo( "absolute" );
9770
9771        //Call plugins and callbacks and use the resulting position if something is returned
9772        if ( !noPropagation ) {
9773            var ui = this._uiHash();
9774            if ( this._trigger( "drag", event, ui ) === false ) {
9775                this._mouseUp( new $.Event( "mouseup", event ) );
9776                return false;
9777            }
9778            this.position = ui.position;
9779        }
9780
9781        this.helper[ 0 ].style.left = this.position.left + "px";
9782        this.helper[ 0 ].style.top = this.position.top + "px";
9783
9784        if ( $.ui.ddmanager ) {
9785            $.ui.ddmanager.drag( this, event );
9786        }
9787
9788        return false;
9789    },
9790
9791    _mouseStop: function( event ) {
9792
9793        //If we are using droppables, inform the manager about the drop
9794        var that = this,
9795            dropped = false;
9796        if ( $.ui.ddmanager && !this.options.dropBehaviour ) {
9797            dropped = $.ui.ddmanager.drop( this, event );
9798        }
9799
9800        //if a drop comes from outside (a sortable)
9801        if ( this.dropped ) {
9802            dropped = this.dropped;
9803            this.dropped = false;
9804        }
9805
9806        if ( ( this.options.revert === "invalid" && !dropped ) ||
9807                ( this.options.revert === "valid" && dropped ) ||
9808                this.options.revert === true || ( $.isFunction( this.options.revert ) &&
9809                this.options.revert.call( this.element, dropped ) )
9810        ) {
9811            $( this.helper ).animate(
9812                this.originalPosition,
9813                parseInt( this.options.revertDuration, 10 ),
9814                function() {
9815                    if ( that._trigger( "stop", event ) !== false ) {
9816                        that._clear();
9817                    }
9818                }
9819            );
9820        } else {
9821            if ( this._trigger( "stop", event ) !== false ) {
9822                this._clear();
9823            }
9824        }
9825
9826        return false;
9827    },
9828
9829    _mouseUp: function( event ) {
9830        this._unblockFrames();
9831
9832        // If the ddmanager is used for droppables, inform the manager that dragging has stopped
9833        // (see #5003)
9834        if ( $.ui.ddmanager ) {
9835            $.ui.ddmanager.dragStop( this, event );
9836        }
9837
9838        // Only need to focus if the event occurred on the draggable itself, see #10527
9839        if ( this.handleElement.is( event.target ) ) {
9840
9841            // The interaction is over; whether or not the click resulted in a drag,
9842            // focus the element
9843            this.element.trigger( "focus" );
9844        }
9845
9846        return $.ui.mouse.prototype._mouseUp.call( this, event );
9847    },
9848
9849    cancel: function() {
9850
9851        if ( this.helper.is( ".ui-draggable-dragging" ) ) {
9852            this._mouseUp( new $.Event( "mouseup", { target: this.element[ 0 ] } ) );
9853        } else {
9854            this._clear();
9855        }
9856
9857        return this;
9858
9859    },
9860
9861    _getHandle: function( event ) {
9862        return this.options.handle ?
9863            !!$( event.target ).closest( this.element.find( this.options.handle ) ).length :
9864            true;
9865    },
9866
9867    _setHandleClassName: function() {
9868        this.handleElement = this.options.handle ?
9869            this.element.find( this.options.handle ) : this.element;
9870        this._addClass( this.handleElement, "ui-draggable-handle" );
9871    },
9872
9873    _removeHandleClassName: function() {
9874        this._removeClass( this.handleElement, "ui-draggable-handle" );
9875    },
9876
9877    _createHelper: function( event ) {
9878
9879        var o = this.options,
9880            helperIsFunction = $.isFunction( o.helper ),
9881            helper = helperIsFunction ?
9882                $( o.helper.apply( this.element[ 0 ], [ event ] ) ) :
9883                ( o.helper === "clone" ?
9884                    this.element.clone().removeAttr( "id" ) :
9885                    this.element );
9886
9887        if ( !helper.parents( "body" ).length ) {
9888            helper.appendTo( ( o.appendTo === "parent" ?
9889                this.element[ 0 ].parentNode :
9890                o.appendTo ) );
9891        }
9892
9893        // Http://bugs.jqueryui.com/ticket/9446
9894        // a helper function can return the original element
vendor: 21,960 bytes, lines 9895-10453
9895        // which wouldn't have been set to relative in _create
9896        if ( helperIsFunction && helper[ 0 ] === this.element[ 0 ] ) {
9897            this._setPositionRelative();
9898        }
9899
9900        if ( helper[ 0 ] !== this.element[ 0 ] &&
9901                !( /(fixed|absolute)/ ).test( helper.css( "position" ) ) ) {
9902            helper.css( "position", "absolute" );
9903        }
9904
9905        return helper;
9906
9907    },
9908
9909    _setPositionRelative: function() {
9910        if ( !( /^(?:r|a|f)/ ).test( this.element.css( "position" ) ) ) {
9911            this.element[ 0 ].style.position = "relative";
9912        }
9913    },
9914
9915    _adjustOffsetFromHelper: function( obj ) {
9916        if ( typeof obj === "string" ) {
9917            obj = obj.split( " " );
9918        }
9919        if ( $.isArray( obj ) ) {
9920            obj = { left: +obj[ 0 ], top: +obj[ 1 ] || 0 };
9921        }
9922        if ( "left" in obj ) {
9923            this.offset.click.left = obj.left + this.margins.left;
9924        }
9925        if ( "right" in obj ) {
9926            this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
9927        }
9928        if ( "top" in obj ) {
9929            this.offset.click.top = obj.top + this.margins.top;
9930        }
9931        if ( "bottom" in obj ) {
9932            this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
9933        }
9934    },
9935
9936    _isRootNode: function( element ) {
9937        return ( /(html|body)/i ).test( element.tagName ) || element === this.document[ 0 ];
9938    },
9939
9940    _getParentOffset: function() {
9941
9942        //Get the offsetParent and cache its position
9943        var po = this.offsetParent.offset(),
9944            document = this.document[ 0 ];
9945
9946        // This is a special case where we need to modify a offset calculated on start, since the
9947        // following happened:
9948        // 1. The position of the helper is absolute, so it's position is calculated based on the
9949        // next positioned parent
9950        // 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't
9951        // the document, which means that the scroll is included in the initial calculation of the
9952        // offset of the parent, and never recalculated upon drag
9953        if ( this.cssPosition === "absolute" && this.scrollParent[ 0 ] !== document &&
9954                $.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) {
9955            po.left += this.scrollParent.scrollLeft();
9956            po.top += this.scrollParent.scrollTop();
9957        }
9958
9959        if ( this._isRootNode( this.offsetParent[ 0 ] ) ) {
9960            po = { top: 0, left: 0 };
9961        }
9962
9963        return {
9964            top: po.top + ( parseInt( this.offsetParent.css( "borderTopWidth" ), 10 ) || 0 ),
9965            left: po.left + ( parseInt( this.offsetParent.css( "borderLeftWidth" ), 10 ) || 0 )
9966        };
9967
9968    },
9969
9970    _getRelativeOffset: function() {
9971        if ( this.cssPosition !== "relative" ) {
9972            return { top: 0, left: 0 };
9973        }
9974
9975        var p = this.element.position(),
9976            scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );
9977
9978        return {
9979            top: p.top - ( parseInt( this.helper.css( "top" ), 10 ) || 0 ) +
9980                ( !scrollIsRootNode ? this.scrollParent.scrollTop() : 0 ),
9981            left: p.left - ( parseInt( this.helper.css( "left" ), 10 ) || 0 ) +
9982                ( !scrollIsRootNode ? this.scrollParent.scrollLeft() : 0 )
9983        };
9984
9985    },
9986
9987    _cacheMargins: function() {
9988        this.margins = {
9989            left: ( parseInt( this.element.css( "marginLeft" ), 10 ) || 0 ),
9990            top: ( parseInt( this.element.css( "marginTop" ), 10 ) || 0 ),
9991            right: ( parseInt( this.element.css( "marginRight" ), 10 ) || 0 ),
9992            bottom: ( parseInt( this.element.css( "marginBottom" ), 10 ) || 0 )
9993        };
9994    },
9995
9996    _cacheHelperProportions: function() {
9997        this.helperProportions = {
9998            width: this.helper.outerWidth(),
9999            height: this.helper.outerHeight()
10000        };
10001    },
10002
10003    _setContainment: function() {
10004
10005        var isUserScrollable, c, ce,
10006            o = this.options,
10007            document = this.document[ 0 ];
10008
10009        this.relativeContainer = null;
10010
10011        if ( !o.containment ) {
10012            this.containment = null;
10013            return;
10014        }
10015
10016        if ( o.containment === "window" ) {
10017            this.containment = [
10018                $( window ).scrollLeft() - this.offset.relative.left - this.offset.parent.left,
10019                $( window ).scrollTop() - this.offset.relative.top - this.offset.parent.top,
10020                $( window ).scrollLeft() + $( window ).width() -
10021                    this.helperProportions.width - this.margins.left,
10022                $( window ).scrollTop() +
10023                    ( $( window ).height() || document.body.parentNode.scrollHeight ) -
10024                    this.helperProportions.height - this.margins.top
10025            ];
10026            return;
10027        }
10028
10029        if ( o.containment === "document" ) {
10030            this.containment = [
10031                0,
10032                0,
10033                $( document ).width() - this.helperProportions.width - this.margins.left,
10034                ( $( document ).height() || document.body.parentNode.scrollHeight ) -
10035                    this.helperProportions.height - this.margins.top
10036            ];
10037            return;
10038        }
10039
10040        if ( o.containment.constructor === Array ) {
10041            this.containment = o.containment;
10042            return;
10043        }
10044
10045        if ( o.containment === "parent" ) {
10046            o.containment = this.helper[ 0 ].parentNode;
10047        }
10048
10049        c = $( o.containment );
10050        ce = c[ 0 ];
10051
10052        if ( !ce ) {
10053            return;
10054        }
10055
10056        isUserScrollable = /(scroll|auto)/.test( c.css( "overflow" ) );
10057
10058        this.containment = [
10059            ( parseInt( c.css( "borderLeftWidth" ), 10 ) || 0 ) +
10060                ( parseInt( c.css( "paddingLeft" ), 10 ) || 0 ),
10061            ( parseInt( c.css( "borderTopWidth" ), 10 ) || 0 ) +
10062                ( parseInt( c.css( "paddingTop" ), 10 ) || 0 ),
10063            ( isUserScrollable ? Math.max( ce.scrollWidth, ce.offsetWidth ) : ce.offsetWidth ) -
10064                ( parseInt( c.css( "borderRightWidth" ), 10 ) || 0 ) -
10065                ( parseInt( c.css( "paddingRight" ), 10 ) || 0 ) -
10066                this.helperProportions.width -
10067                this.margins.left -
10068                this.margins.right,
10069            ( isUserScrollable ? Math.max( ce.scrollHeight, ce.offsetHeight ) : ce.offsetHeight ) -
10070                ( parseInt( c.css( "borderBottomWidth" ), 10 ) || 0 ) -
10071                ( parseInt( c.css( "paddingBottom" ), 10 ) || 0 ) -
10072                this.helperProportions.height -
10073                this.margins.top -
10074                this.margins.bottom
10075        ];
10076        this.relativeContainer = c;
10077    },
10078
10079    _convertPositionTo: function( d, pos ) {
10080
10081        if ( !pos ) {
10082            pos = this.position;
10083        }
10084
10085        var mod = d === "absolute" ? 1 : -1,
10086            scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );
10087
10088        return {
10089            top: (
10090
10091                // The absolute mouse position
10092                pos.top +
10093
10094                // Only for relative positioned nodes: Relative offset from element to offset parent
10095                this.offset.relative.top * mod +
10096
10097                // The offsetParent's offset without borders (offset + border)
10098                this.offset.parent.top * mod -
10099                ( ( this.cssPosition === "fixed" ?
10100                    -this.offset.scroll.top :
10101                    ( scrollIsRootNode ? 0 : this.offset.scroll.top ) ) * mod )
10102            ),
10103            left: (
10104
10105                // The absolute mouse position
10106                pos.left +
10107
10108                // Only for relative positioned nodes: Relative offset from element to offset parent
10109                this.offset.relative.left * mod +
10110
10111                // The offsetParent's offset without borders (offset + border)
10112                this.offset.parent.left * mod   -
10113                ( ( this.cssPosition === "fixed" ?
10114                    -this.offset.scroll.left :
10115                    ( scrollIsRootNode ? 0 : this.offset.scroll.left ) ) * mod )
10116            )
10117        };
10118
10119    },
10120
10121    _generatePosition: function( event, constrainPosition ) {
10122
10123        var containment, co, top, left,
10124            o = this.options,
10125            scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] ),
10126            pageX = event.pageX,
10127            pageY = event.pageY;
10128
10129        // Cache the scroll
10130        if ( !scrollIsRootNode || !this.offset.scroll ) {
10131            this.offset.scroll = {
10132                top: this.scrollParent.scrollTop(),
10133                left: this.scrollParent.scrollLeft()
10134            };
10135        }
10136
10137        /*
10138         * - Position constraining -
10139         * Constrain the position to a mix of grid, containment.
10140         */
10141
10142        // If we are not dragging yet, we won't check for options
10143        if ( constrainPosition ) {
10144            if ( this.containment ) {
10145                if ( this.relativeContainer ) {
10146                    co = this.relativeContainer.offset();
10147                    containment = [
10148                        this.containment[ 0 ] + co.left,
10149                        this.containment[ 1 ] + co.top,
10150                        this.containment[ 2 ] + co.left,
10151                        this.containment[ 3 ] + co.top
10152                    ];
10153                } else {
10154                    containment = this.containment;
10155                }
10156
10157                if ( event.pageX - this.offset.click.left < containment[ 0 ] ) {
10158                    pageX = containment[ 0 ] + this.offset.click.left;
10159                }
10160                if ( event.pageY - this.offset.click.top < containment[ 1 ] ) {
10161                    pageY = containment[ 1 ] + this.offset.click.top;
10162                }
10163                if ( event.pageX - this.offset.click.left > containment[ 2 ] ) {
10164                    pageX = containment[ 2 ] + this.offset.click.left;
10165                }
10166                if ( event.pageY - this.offset.click.top > containment[ 3 ] ) {
10167                    pageY = containment[ 3 ] + this.offset.click.top;
10168                }
10169            }
10170
10171            if ( o.grid ) {
10172
10173                //Check for grid elements set to 0 to prevent divide by 0 error causing invalid
10174                // argument errors in IE (see ticket #6950)
10175                top = o.grid[ 1 ] ? this.originalPageY + Math.round( ( pageY -
10176                    this.originalPageY ) / o.grid[ 1 ] ) * o.grid[ 1 ] : this.originalPageY;
10177                pageY = containment ? ( ( top - this.offset.click.top >= containment[ 1 ] ||
10178                    top - this.offset.click.top > containment[ 3 ] ) ?
10179                        top :
10180                        ( ( top - this.offset.click.top >= containment[ 1 ] ) ?
10181                            top - o.grid[ 1 ] : top + o.grid[ 1 ] ) ) : top;
10182
10183                left = o.grid[ 0 ] ? this.originalPageX +
10184                    Math.round( ( pageX - this.originalPageX ) / o.grid[ 0 ] ) * o.grid[ 0 ] :
10185                    this.originalPageX;
10186                pageX = containment ? ( ( left - this.offset.click.left >= containment[ 0 ] ||
10187                    left - this.offset.click.left > containment[ 2 ] ) ?
10188                        left :
10189                        ( ( left - this.offset.click.left >= containment[ 0 ] ) ?
10190                            left - o.grid[ 0 ] : left + o.grid[ 0 ] ) ) : left;
10191            }
10192
10193            if ( o.axis === "y" ) {
10194                pageX = this.originalPageX;
10195            }
10196
10197            if ( o.axis === "x" ) {
10198                pageY = this.originalPageY;
10199            }
10200        }
10201
10202        return {
10203            top: (
10204
10205                // The absolute mouse position
10206                pageY -
10207
10208                // Click offset (relative to the element)
10209                this.offset.click.top -
10210
10211                // Only for relative positioned nodes: Relative offset from element to offset parent
10212                this.offset.relative.top -
10213
10214                // The offsetParent's offset without borders (offset + border)
10215                this.offset.parent.top +
10216                ( this.cssPosition === "fixed" ?
10217                    -this.offset.scroll.top :
10218                    ( scrollIsRootNode ? 0 : this.offset.scroll.top ) )
10219            ),
10220            left: (
10221
10222                // The absolute mouse position
10223                pageX -
10224
10225                // Click offset (relative to the element)
10226                this.offset.click.left -
10227
10228                // Only for relative positioned nodes: Relative offset from element to offset parent
10229                this.offset.relative.left -
10230
10231                // The offsetParent's offset without borders (offset + border)
10232                this.offset.parent.left +
10233                ( this.cssPosition === "fixed" ?
10234                    -this.offset.scroll.left :
10235                    ( scrollIsRootNode ? 0 : this.offset.scroll.left ) )
10236            )
10237        };
10238
10239    },
10240
10241    _clear: function() {
10242        this._removeClass( this.helper, "ui-draggable-dragging" );
10243        if ( this.helper[ 0 ] !== this.element[ 0 ] && !this.cancelHelperRemoval ) {
10244            this.helper.remove();
10245        }
10246        this.helper = null;
10247        this.cancelHelperRemoval = false;
10248        if ( this.destroyOnClear ) {
10249            this.destroy();
10250        }
10251    },
10252
10253    // From now on bulk stuff - mainly helpers
10254
10255    _trigger: function( type, event, ui ) {
10256        ui = ui || this._uiHash();
10257        $.ui.plugin.call( this, type, [ event, ui, this ], true );
10258
10259        // Absolute position and offset (see #6884 ) have to be recalculated after plugins
10260        if ( /^(drag|start|stop)/.test( type ) ) {
10261            this.positionAbs = this._convertPositionTo( "absolute" );
10262            ui.offset = this.positionAbs;
10263        }
10264        return $.Widget.prototype._trigger.call( this, type, event, ui );
10265    },
10266
10267    plugins: {},
10268
10269    _uiHash: function() {
10270        return {
10271            helper: this.helper,
10272            position: this.position,
10273            originalPosition: this.originalPosition,
10274            offset: this.positionAbs
10275        };
10276    }
10277
10278} );
10279
10280$.ui.plugin.add( "draggable", "connectToSortable", {
10281    start: function( event, ui, draggable ) {
10282        var uiSortable = $.extend( {}, ui, {
10283            item: draggable.element
10284        } );
10285
10286        draggable.sortables = [];
10287        $( draggable.options.connectToSortable ).each( function() {
10288            var sortable = $( this ).sortable( "instance" );
10289
10290            if ( sortable && !sortable.options.disabled ) {
10291                draggable.sortables.push( sortable );
10292
10293                // RefreshPositions is called at drag start to refresh the containerCache
10294                // which is used in drag. This ensures it's initialized and synchronized
10295                // with any changes that might have happened on the page since initialization.
10296                sortable.refreshPositions();
10297                sortable._trigger( "activate", event, uiSortable );
10298            }
10299        } );
10300    },
10301    stop: function( event, ui, draggable ) {
10302        var uiSortable = $.extend( {}, ui, {
10303            item: draggable.element
10304        } );
10305
10306        draggable.cancelHelperRemoval = false;
10307
10308        $.each( draggable.sortables, function() {
10309            var sortable = this;
10310
10311            if ( sortable.isOver ) {
10312                sortable.isOver = 0;
10313
10314                // Allow this sortable to handle removing the helper
10315                draggable.cancelHelperRemoval = true;
10316                sortable.cancelHelperRemoval = false;
10317
10318                // Use _storedCSS To restore properties in the sortable,
10319                // as this also handles revert (#9675) since the draggable
10320                // may have modified them in unexpected ways (#8809)
10321                sortable._storedCSS = {
10322                    position: sortable.placeholder.css( "position" ),
10323                    top: sortable.placeholder.css( "top" ),
10324                    left: sortable.placeholder.css( "left" )
10325                };
10326
10327                sortable._mouseStop( event );
10328
10329                // Once drag has ended, the sortable should return to using
10330                // its original helper, not the shared helper from draggable
10331                sortable.options.helper = sortable.options._helper;
10332            } else {
10333
10334                // Prevent this Sortable from removing the helper.
10335                // However, don't set the draggable to remove the helper
10336                // either as another connected Sortable may yet handle the removal.
10337                sortable.cancelHelperRemoval = true;
10338
10339                sortable._trigger( "deactivate", event, uiSortable );
10340            }
10341        } );
10342    },
10343    drag: function( event, ui, draggable ) {
10344        $.each( draggable.sortables, function() {
10345            var innermostIntersecting = false,
10346                sortable = this;
10347
10348            // Copy over variables that sortable's _intersectsWith uses
10349            sortable.positionAbs = draggable.positionAbs;
10350            sortable.helperProportions = draggable.helperProportions;
10351            sortable.offset.click = draggable.offset.click;
10352
10353            if ( sortable._intersectsWith( sortable.containerCache ) ) {
10354                innermostIntersecting = true;
10355
10356                $.each( draggable.sortables, function() {
10357
10358                    // Copy over variables that sortable's _intersectsWith uses
10359                    this.positionAbs = draggable.positionAbs;
10360                    this.helperProportions = draggable.helperProportions;
10361                    this.offset.click = draggable.offset.click;
10362
10363                    if ( this !== sortable &&
10364                            this._intersectsWith( this.containerCache ) &&
10365                            $.contains( sortable.element[ 0 ], this.element[ 0 ] ) ) {
10366                        innermostIntersecting = false;
10367                    }
10368
10369                    return innermostIntersecting;
10370                } );
10371            }
10372
10373            if ( innermostIntersecting ) {
10374
10375                // If it intersects, we use a little isOver variable and set it once,
10376                // so that the move-in stuff gets fired only once.
10377                if ( !sortable.isOver ) {
10378                    sortable.isOver = 1;
10379
10380                    // Store draggable's parent in case we need to reappend to it later.
10381                    draggable._parent = ui.helper.parent();
10382
10383                    sortable.currentItem = ui.helper
10384                        .appendTo( sortable.element )
10385                        .data( "ui-sortable-item", true );
10386
10387                    // Store helper option to later restore it
10388                    sortable.options._helper = sortable.options.helper;
10389
10390                    sortable.options.helper = function() {
10391                        return ui.helper[ 0 ];
10392                    };
10393
10394                    // Fire the start events of the sortable with our passed browser event,
10395                    // and our own helper (so it doesn't create a new one)
10396                    event.target = sortable.currentItem[ 0 ];
10397                    sortable._mouseCapture( event, true );
10398                    sortable._mouseStart( event, true, true );
10399
10400                    // Because the browser event is way off the new appended portlet,
10401                    // modify necessary variables to reflect the changes
10402                    sortable.offset.click.top = draggable.offset.click.top;
10403                    sortable.offset.click.left = draggable.offset.click.left;
10404                    sortable.offset.parent.left -= draggable.offset.parent.left -
10405                        sortable.offset.parent.left;
10406                    sortable.offset.parent.top -= draggable.offset.parent.top -
10407                        sortable.offset.parent.top;
10408
10409                    draggable._trigger( "toSortable", event );
10410
10411                    // Inform draggable that the helper is in a valid drop zone,
10412                    // used solely in the revert option to handle "valid/invalid".
10413                    draggable.dropped = sortable.element;
10414
10415                    // Need to refreshPositions of all sortables in the case that
10416                    // adding to one sortable changes the location of the other sortables (#9675)
10417                    $.each( draggable.sortables, function() {
10418                        this.refreshPositions();
10419                    } );
10420
10421                    // Hack so receive/update callbacks work (mostly)
10422                    draggable.currentItem = draggable.element;
10423                    sortable.fromOutside = draggable;
10424                }
10425
10426                if ( sortable.currentItem ) {
10427                    sortable._mouseDrag( event );
10428
10429                    // Copy the sortable's position because the draggable's can potentially reflect
10430                    // a relative position, while sortable is always absolute, which the dragged
10431                    // element has now become. (#8809)
10432                    ui.position = sortable.position;
10433                }
10434            } else {
10435
10436                // If it doesn't intersect with the sortable, and it intersected before,
10437                // we fake the drag stop of the sortable, but make sure it doesn't remove
10438                // the helper by using cancelHelperRemoval.
10439                if ( sortable.isOver ) {
10440
10441                    sortable.isOver = 0;
10442                    sortable.cancelHelperRemoval = true;
10443
10444                    // Calling sortable's mouseStop would trigger a revert,
10445                    // so revert must be temporarily false until after mouseStop is called.
10446                    sortable.options._revert = sortable.options.revert;
10447                    sortable.options.revert = false;
10448
10449                    sortable._trigger( "out", event, sortable._uiHash( sortable ) );
10450                    sortable._mouseStop( event, true );
10451
10452                    // Restore sortable behaviors that were modfied
10453                    // when the draggable entered the sortable area (#9481)
vendor: 7,054 bytes, lines 10454-10635
10454                    sortable.options.revert = sortable.options._revert;
10455                    sortable.options.helper = sortable.options._helper;
10456
10457                    if ( sortable.placeholder ) {
10458                        sortable.placeholder.remove();
10459                    }
10460
10461                    // Restore and recalculate the draggable's offset considering the sortable
10462                    // may have modified them in unexpected ways. (#8809, #10669)
10463                    ui.helper.appendTo( draggable._parent );
10464                    draggable._refreshOffsets( event );
10465                    ui.position = draggable._generatePosition( event, true );
10466
10467                    draggable._trigger( "fromSortable", event );
10468
10469                    // Inform draggable that the helper is no longer in a valid drop zone
10470                    draggable.dropped = false;
10471
10472                    // Need to refreshPositions of all sortables just in case removing
10473                    // from one sortable changes the location of other sortables (#9675)
10474                    $.each( draggable.sortables, function() {
10475                        this.refreshPositions();
10476                    } );
10477                }
10478            }
10479        } );
10480    }
10481} );
10482
10483$.ui.plugin.add( "draggable", "cursor", {
10484    start: function( event, ui, instance ) {
10485        var t = $( "body" ),
10486            o = instance.options;
10487
10488        if ( t.css( "cursor" ) ) {
10489            o._cursor = t.css( "cursor" );
10490        }
10491        t.css( "cursor", o.cursor );
10492    },
10493    stop: function( event, ui, instance ) {
10494        var o = instance.options;
10495        if ( o._cursor ) {
10496            $( "body" ).css( "cursor", o._cursor );
10497        }
10498    }
10499} );
10500
10501$.ui.plugin.add( "draggable", "opacity", {
10502    start: function( event, ui, instance ) {
10503        var t = $( ui.helper ),
10504            o = instance.options;
10505        if ( t.css( "opacity" ) ) {
10506            o._opacity = t.css( "opacity" );
10507        }
10508        t.css( "opacity", o.opacity );
10509    },
10510    stop: function( event, ui, instance ) {
10511        var o = instance.options;
10512        if ( o._opacity ) {
10513            $( ui.helper ).css( "opacity", o._opacity );
10514        }
10515    }
10516} );
10517
10518$.ui.plugin.add( "draggable", "scroll", {
10519    start: function( event, ui, i ) {
10520        if ( !i.scrollParentNotHidden ) {
10521            i.scrollParentNotHidden = i.helper.scrollParent( false );
10522        }
10523
10524        if ( i.scrollParentNotHidden[ 0 ] !== i.document[ 0 ] &&
10525                i.scrollParentNotHidden[ 0 ].tagName !== "HTML" ) {
10526            i.overflowOffset = i.scrollParentNotHidden.offset();
10527        }
10528    },
10529    drag: function( event, ui, i  ) {
10530
10531        var o = i.options,
10532            scrolled = false,
10533            scrollParent = i.scrollParentNotHidden[ 0 ],
10534            document = i.document[ 0 ];
10535
10536        if ( scrollParent !== document && scrollParent.tagName !== "HTML" ) {
10537            if ( !o.axis || o.axis !== "x" ) {
10538                if ( ( i.overflowOffset.top + scrollParent.offsetHeight ) - event.pageY <
10539                        o.scrollSensitivity ) {
10540                    scrollParent.scrollTop = scrolled = scrollParent.scrollTop + o.scrollSpeed;
10541                } else if ( event.pageY - i.overflowOffset.top < o.scrollSensitivity ) {
10542                    scrollParent.scrollTop = scrolled = scrollParent.scrollTop - o.scrollSpeed;
10543                }
10544            }
10545
10546            if ( !o.axis || o.axis !== "y" ) {
10547                if ( ( i.overflowOffset.left + scrollParent.offsetWidth ) - event.pageX <
10548                        o.scrollSensitivity ) {
10549                    scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft + o.scrollSpeed;
10550                } else if ( event.pageX - i.overflowOffset.left < o.scrollSensitivity ) {
10551                    scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft - o.scrollSpeed;
10552                }
10553            }
10554
10555        } else {
10556
10557            if ( !o.axis || o.axis !== "x" ) {
10558                if ( event.pageY - $( document ).scrollTop() < o.scrollSensitivity ) {
10559                    scrolled = $( document ).scrollTop( $( document ).scrollTop() - o.scrollSpeed );
10560                } else if ( $( window ).height() - ( event.pageY - $( document ).scrollTop() ) <
10561                        o.scrollSensitivity ) {
10562                    scrolled = $( document ).scrollTop( $( document ).scrollTop() + o.scrollSpeed );
10563                }
10564            }
10565
10566            if ( !o.axis || o.axis !== "y" ) {
10567                if ( event.pageX - $( document ).scrollLeft() < o.scrollSensitivity ) {
10568                    scrolled = $( document ).scrollLeft(
10569                        $( document ).scrollLeft() - o.scrollSpeed
10570                    );
10571                } else if ( $( window ).width() - ( event.pageX - $( document ).scrollLeft() ) <
10572                        o.scrollSensitivity ) {
10573                    scrolled = $( document ).scrollLeft(
10574                        $( document ).scrollLeft() + o.scrollSpeed
10575                    );
10576                }
10577            }
10578
10579        }
10580
10581        if ( scrolled !== false && $.ui.ddmanager && !o.dropBehaviour ) {
10582            $.ui.ddmanager.prepareOffsets( i, event );
10583        }
10584
10585    }
10586} );
10587
10588$.ui.plugin.add( "draggable", "snap", {
10589    start: function( event, ui, i ) {
10590
10591        var o = i.options;
10592
10593        i.snapElements = [];
10594
10595        $( o.snap.constructor !== String ? ( o.snap.items || ":data(ui-draggable)" ) : o.snap )
10596            .each( function() {
10597                var $t = $( this ),
10598                    $o = $t.offset();
10599                if ( this !== i.element[ 0 ] ) {
10600                    i.snapElements.push( {
10601                        item: this,
10602                        width: $t.outerWidth(), height: $t.outerHeight(),
10603                        top: $o.top, left: $o.left
10604                    } );
10605                }
10606            } );
10607
10608    },
10609    drag: function( event, ui, inst ) {
10610
10611        var ts, bs, ls, rs, l, r, t, b, i, first,
10612            o = inst.options,
10613            d = o.snapTolerance,
10614            x1 = ui.offset.left, x2 = x1 + inst.helperProportions.width,
10615            y1 = ui.offset.top, y2 = y1 + inst.helperProportions.height;
10616
10617        for ( i = inst.snapElements.length - 1; i >= 0; i-- ) {
10618
10619            l = inst.snapElements[ i ].left - inst.margins.left;
10620            r = l + inst.snapElements[ i ].width;
10621            t = inst.snapElements[ i ].top - inst.margins.top;
10622            b = t + inst.snapElements[ i ].height;
10623
10624            if ( x2 < l - d || x1 > r + d || y2 < t - d || y1 > b + d ||
10625                    !$.contains( inst.snapElements[ i ].item.ownerDocument,
10626                    inst.snapElements[ i ].item ) ) {
10627                if ( inst.snapElements[ i ].snapping ) {
10628                    ( inst.options.snap.release &&
10629                        inst.options.snap.release.call(
10630                            inst.element,
10631                            event,
10632                            $.extend( inst._uiHash(), { snapItem: inst.snapElements[ i ].item } )
10633                        ) );
10634                }
10635                inst.snapElements[ i ].snapping = false;
vendor: 12,807 bytes, lines 10636-11041
10636                continue;
10637            }
10638
10639            if ( o.snapMode !== "inner" ) {
10640                ts = Math.abs( t - y2 ) <= d;
10641                bs = Math.abs( b - y1 ) <= d;
10642                ls = Math.abs( l - x2 ) <= d;
10643                rs = Math.abs( r - x1 ) <= d;
10644                if ( ts ) {
10645                    ui.position.top = inst._convertPositionTo( "relative", {
10646                        top: t - inst.helperProportions.height,
10647                        left: 0
10648                    } ).top;
10649                }
10650                if ( bs ) {
10651                    ui.position.top = inst._convertPositionTo( "relative", {
10652                        top: b,
10653                        left: 0
10654                    } ).top;
10655                }
10656                if ( ls ) {
10657                    ui.position.left = inst._convertPositionTo( "relative", {
10658                        top: 0,
10659                        left: l - inst.helperProportions.width
10660                    } ).left;
10661                }
10662                if ( rs ) {
10663                    ui.position.left = inst._convertPositionTo( "relative", {
10664                        top: 0,
10665                        left: r
10666                    } ).left;
10667                }
10668            }
10669
10670            first = ( ts || bs || ls || rs );
10671
10672            if ( o.snapMode !== "outer" ) {
10673                ts = Math.abs( t - y1 ) <= d;
10674                bs = Math.abs( b - y2 ) <= d;
10675                ls = Math.abs( l - x1 ) <= d;
10676                rs = Math.abs( r - x2 ) <= d;
10677                if ( ts ) {
10678                    ui.position.top = inst._convertPositionTo( "relative", {
10679                        top: t,
10680                        left: 0
10681                    } ).top;
10682                }
10683                if ( bs ) {
10684                    ui.position.top = inst._convertPositionTo( "relative", {
10685                        top: b - inst.helperProportions.height,
10686                        left: 0
10687                    } ).top;
10688                }
10689                if ( ls ) {
10690                    ui.position.left = inst._convertPositionTo( "relative", {
10691                        top: 0,
10692                        left: l
10693                    } ).left;
10694                }
10695                if ( rs ) {
10696                    ui.position.left = inst._convertPositionTo( "relative", {
10697                        top: 0,
10698                        left: r - inst.helperProportions.width
10699                    } ).left;
10700                }
10701            }
10702
10703            if ( !inst.snapElements[ i ].snapping && ( ts || bs || ls || rs || first ) ) {
10704                ( inst.options.snap.snap &&
10705                    inst.options.snap.snap.call(
10706                        inst.element,
10707                        event,
10708                        $.extend( inst._uiHash(), {
10709                            snapItem: inst.snapElements[ i ].item
10710                        } ) ) );
10711            }
10712            inst.snapElements[ i ].snapping = ( ts || bs || ls || rs || first );
10713
10714        }
10715
10716    }
10717} );
10718
10719$.ui.plugin.add( "draggable", "stack", {
10720    start: function( event, ui, instance ) {
10721        var min,
10722            o = instance.options,
10723            group = $.makeArray( $( o.stack ) ).sort( function( a, b ) {
10724                return ( parseInt( $( a ).css( "zIndex" ), 10 ) || 0 ) -
10725                    ( parseInt( $( b ).css( "zIndex" ), 10 ) || 0 );
10726            } );
10727
10728        if ( !group.length ) { return; }
10729
10730        min = parseInt( $( group[ 0 ] ).css( "zIndex" ), 10 ) || 0;
10731        $( group ).each( function( i ) {
10732            $( this ).css( "zIndex", min + i );
10733        } );
10734        this.css( "zIndex", ( min + group.length ) );
10735    }
10736} );
10737
10738$.ui.plugin.add( "draggable", "zIndex", {
10739    start: function( event, ui, instance ) {
10740        var t = $( ui.helper ),
10741            o = instance.options;
10742
10743        if ( t.css( "zIndex" ) ) {
10744            o._zIndex = t.css( "zIndex" );
10745        }
10746        t.css( "zIndex", o.zIndex );
10747    },
10748    stop: function( event, ui, instance ) {
10749        var o = instance.options;
10750
10751        if ( o._zIndex ) {
10752            $( ui.helper ).css( "zIndex", o._zIndex );
10753        }
10754    }
10755} );
10756
10757var widgetsDraggable = $.ui.draggable;
10758
10759
10760/*!
10761 * jQuery UI Resizable 1.12.1
10762 * http://jqueryui.com
10763 *
10764 * Copyright jQuery Foundation and other contributors
10765 * Released under the MIT license.
10766 * http://jquery.org/license
10767 */
10768
10769//>>label: Resizable
10770//>>group: Interactions
10771//>>description: Enables resize functionality for any element.
10772//>>docs: http://api.jqueryui.com/resizable/
10773//>>demos: http://jqueryui.com/resizable/
10774//>>css.structure: ../../themes/base/core.css
10775//>>css.structure: ../../themes/base/resizable.css
10776//>>css.theme: ../../themes/base/theme.css
10777
10778
10779
10780$.widget( "ui.resizable", $.ui.mouse, {
10781    version: "1.12.1",
10782    widgetEventPrefix: "resize",
10783    options: {
10784        alsoResize: false,
10785        animate: false,
10786        animateDuration: "slow",
10787        animateEasing: "swing",
10788        aspectRatio: false,
10789        autoHide: false,
10790        classes: {
10791            "ui-resizable-se": "ui-icon ui-icon-gripsmall-diagonal-se"
10792        },
10793        containment: false,
10794        ghost: false,
10795        grid: false,
10796        handles: "e,s,se",
10797        helper: false,
10798        maxHeight: null,
10799        maxWidth: null,
10800        minHeight: 10,
10801        minWidth: 10,
10802
10803        // See #7960
10804        zIndex: 90,
10805
10806        // Callbacks
10807        resize: null,
10808        start: null,
10809        stop: null
10810    },
10811
10812    _num: function( value ) {
10813        return parseFloat( value ) || 0;
10814    },
10815
10816    _isNumber: function( value ) {
10817        return !isNaN( parseFloat( value ) );
10818    },
10819
10820    _hasScroll: function( el, a ) {
10821
10822        if ( $( el ).css( "overflow" ) === "hidden" ) {
10823            return false;
10824        }
10825
10826        var scroll = ( a && a === "left" ) ? "scrollLeft" : "scrollTop",
10827            has = false;
10828
10829        if ( el[ scroll ] > 0 ) {
10830            return true;
10831        }
10832
10833        // TODO: determine which cases actually cause this to happen
10834        // if the element doesn't have the scroll set, see if it's possible to
10835        // set the scroll
10836        el[ scroll ] = 1;
10837        has = ( el[ scroll ] > 0 );
10838        el[ scroll ] = 0;
10839        return has;
10840    },
10841
10842    _create: function() {
10843
10844        var margins,
10845            o = this.options,
10846            that = this;
10847        this._addClass( "ui-resizable" );
10848
10849        $.extend( this, {
10850            _aspectRatio: !!( o.aspectRatio ),
10851            aspectRatio: o.aspectRatio,
10852            originalElement: this.element,
10853            _proportionallyResizeElements: [],
10854            _helper: o.helper || o.ghost || o.animate ? o.helper || "ui-resizable-helper" : null
10855        } );
10856
10857        // Wrap the element if it cannot hold child nodes
10858        if ( this.element[ 0 ].nodeName.match( /^(canvas|textarea|input|select|button|img)$/i ) ) {
10859
10860            this.element.wrap(
10861                $( "<div class='ui-wrapper' style='overflow: hidden;'></div>" ).css( {
10862                    position: this.element.css( "position" ),
10863                    width: this.element.outerWidth(),
10864                    height: this.element.outerHeight(),
10865                    top: this.element.css( "top" ),
10866                    left: this.element.css( "left" )
10867                } )
10868            );
10869
10870            this.element = this.element.parent().data(
10871                "ui-resizable", this.element.resizable( "instance" )
10872            );
10873
10874            this.elementIsWrapper = true;
10875
10876            margins = {
10877                marginTop: this.originalElement.css( "marginTop" ),
10878                marginRight: this.originalElement.css( "marginRight" ),
10879                marginBottom: this.originalElement.css( "marginBottom" ),
10880                marginLeft: this.originalElement.css( "marginLeft" )
10881            };
10882
10883            this.element.css( margins );
10884            this.originalElement.css( "margin", 0 );
10885
10886            // support: Safari
10887            // Prevent Safari textarea resize
10888            this.originalResizeStyle = this.originalElement.css( "resize" );
10889            this.originalElement.css( "resize", "none" );
10890
10891            this._proportionallyResizeElements.push( this.originalElement.css( {
10892                position: "static",
10893                zoom: 1,
10894                display: "block"
10895            } ) );
10896
10897            // Support: IE9
10898            // avoid IE jump (hard set the margin)
10899            this.originalElement.css( margins );
10900
10901            this._proportionallyResize();
10902        }
10903
10904        this._setupHandles();
10905
10906        if ( o.autoHide ) {
10907            $( this.element )
10908                .on( "mouseenter", function() {
10909                    if ( o.disabled ) {
10910                        return;
10911                    }
10912                    that._removeClass( "ui-resizable-autohide" );
10913                    that._handles.show();
10914                } )
10915                .on( "mouseleave", function() {
10916                    if ( o.disabled ) {
10917                        return;
10918                    }
10919                    if ( !that.resizing ) {
10920                        that._addClass( "ui-resizable-autohide" );
10921                        that._handles.hide();
10922                    }
10923                } );
10924        }
10925
10926        this._mouseInit();
10927    },
10928
10929    _destroy: function() {
10930
10931        this._mouseDestroy();
10932
10933        var wrapper,
10934            _destroy = function( exp ) {
10935                $( exp )
10936                    .removeData( "resizable" )
10937                    .removeData( "ui-resizable" )
10938                    .off( ".resizable" )
10939                    .find( ".ui-resizable-handle" )
10940                        .remove();
10941            };
10942
10943        // TODO: Unwrap at same DOM position
10944        if ( this.elementIsWrapper ) {
10945            _destroy( this.element );
10946            wrapper = this.element;
10947            this.originalElement.css( {
10948                position: wrapper.css( "position" ),
10949                width: wrapper.outerWidth(),
10950                height: wrapper.outerHeight(),
10951                top: wrapper.css( "top" ),
10952                left: wrapper.css( "left" )
10953            } ).insertAfter( wrapper );
10954            wrapper.remove();
10955        }
10956
10957        this.originalElement.css( "resize", this.originalResizeStyle );
10958        _destroy( this.originalElement );
10959
10960        return this;
10961    },
10962
10963    _setOption: function( key, value ) {
10964        this._super( key, value );
10965
10966        switch ( key ) {
10967        case "handles":
10968            this._removeHandles();
10969            this._setupHandles();
10970            break;
10971        default:
10972            break;
10973        }
10974    },
10975
10976    _setupHandles: function() {
10977        var o = this.options, handle, i, n, hname, axis, that = this;
10978        this.handles = o.handles ||
10979            ( !$( ".ui-resizable-handle", this.element ).length ?
10980                "e,s,se" : {
10981                    n: ".ui-resizable-n",
10982                    e: ".ui-resizable-e",
10983                    s: ".ui-resizable-s",
10984                    w: ".ui-resizable-w",
10985                    se: ".ui-resizable-se",
10986                    sw: ".ui-resizable-sw",
10987                    ne: ".ui-resizable-ne",
10988                    nw: ".ui-resizable-nw"
10989                } );
10990
10991        this._handles = $();
10992        if ( this.handles.constructor === String ) {
10993
10994            if ( this.handles === "all" ) {
10995                this.handles = "n,e,s,w,se,sw,ne,nw";
10996            }
10997
10998            n = this.handles.split( "," );
10999            this.handles = {};
11000
11001            for ( i = 0; i < n.length; i++ ) {
11002
11003                handle = $.trim( n[ i ] );
11004                hname = "ui-resizable-" + handle;
11005                axis = $( "<div>" );
11006                this._addClass( axis, "ui-resizable-handle " + hname );
11007
11008                axis.css( { zIndex: o.zIndex } );
11009
11010                this.handles[ handle ] = ".ui-resizable-" + handle;
11011                this.element.append( axis );
11012            }
11013
11014        }
11015
11016        this._renderAxis = function( target ) {
11017
11018            var i, axis, padPos, padWrapper;
11019
11020            target = target || this.element;
11021
11022            for ( i in this.handles ) {
11023
11024                if ( this.handles[ i ].constructor === String ) {
11025                    this.handles[ i ] = this.element.children( this.handles[ i ] ).first().show();
11026                } else if ( this.handles[ i ].jquery || this.handles[ i ].nodeType ) {
11027                    this.handles[ i ] = $( this.handles[ i ] );
11028                    this._on( this.handles[ i ], { "mousedown": that._mouseDown } );
11029                }
11030
11031                if ( this.elementIsWrapper &&
11032                        this.originalElement[ 0 ]
11033                            .nodeName
11034                            .match( /^(textarea|input|select|button)$/i ) ) {
11035                    axis = $( this.handles[ i ], this.element );
11036
11037                    padWrapper = /sw|ne|nw|se|n|s/.test( i ) ?
11038                        axis.outerHeight() :
11039                        axis.outerWidth();
11040
11041                    padPos = [ "padding",
vendor: 4,442 bytes, lines 11042-11191
11042                        /ne|nw|n/.test( i ) ? "Top" :
11043                        /se|sw|s/.test( i ) ? "Bottom" :
11044                        /^e$/.test( i ) ? "Right" : "Left" ].join( "" );
11045
11046                    target.css( padPos, padWrapper );
11047
11048                    this._proportionallyResize();
11049                }
11050
11051                this._handles = this._handles.add( this.handles[ i ] );
11052            }
11053        };
11054
11055        // TODO: make renderAxis a prototype function
11056        this._renderAxis( this.element );
11057
11058        this._handles = this._handles.add( this.element.find( ".ui-resizable-handle" ) );
11059        this._handles.disableSelection();
11060
11061        this._handles.on( "mouseover", function() {
11062            if ( !that.resizing ) {
11063                if ( this.className ) {
11064                    axis = this.className.match( /ui-resizable-(se|sw|ne|nw|n|e|s|w)/i );
11065                }
11066                that.axis = axis && axis[ 1 ] ? axis[ 1 ] : "se";
11067            }
11068        } );
11069
11070        if ( o.autoHide ) {
11071            this._handles.hide();
11072            this._addClass( "ui-resizable-autohide" );
11073        }
11074    },
11075
11076    _removeHandles: function() {
11077        this._handles.remove();
11078    },
11079
11080    _mouseCapture: function( event ) {
11081        var i, handle,
11082            capture = false;
11083
11084        for ( i in this.handles ) {
11085            handle = $( this.handles[ i ] )[ 0 ];
11086            if ( handle === event.target || $.contains( handle, event.target ) ) {
11087                capture = true;
11088            }
11089        }
11090
11091        return !this.options.disabled && capture;
11092    },
11093
11094    _mouseStart: function( event ) {
11095
11096        var curleft, curtop, cursor,
11097            o = this.options,
11098            el = this.element;
11099
11100        this.resizing = true;
11101
11102        this._renderProxy();
11103
11104        curleft = this._num( this.helper.css( "left" ) );
11105        curtop = this._num( this.helper.css( "top" ) );
11106
11107        if ( o.containment ) {
11108            curleft += $( o.containment ).scrollLeft() || 0;
11109            curtop += $( o.containment ).scrollTop() || 0;
11110        }
11111
11112        this.offset = this.helper.offset();
11113        this.position = { left: curleft, top: curtop };
11114
11115        this.size = this._helper ? {
11116                width: this.helper.width(),
11117                height: this.helper.height()
11118            } : {
11119                width: el.width(),
11120                height: el.height()
11121            };
11122
11123        this.originalSize = this._helper ? {
11124                width: el.outerWidth(),
11125                height: el.outerHeight()
11126            } : {
11127                width: el.width(),
11128                height: el.height()
11129            };
11130
11131        this.sizeDiff = {
11132            width: el.outerWidth() - el.width(),
11133            height: el.outerHeight() - el.height()
11134        };
11135
11136        this.originalPosition = { left: curleft, top: curtop };
11137        this.originalMousePosition = { left: event.pageX, top: event.pageY };
11138
11139        this.aspectRatio = ( typeof o.aspectRatio === "number" ) ?
11140            o.aspectRatio :
11141            ( ( this.originalSize.width / this.originalSize.height ) || 1 );
11142
11143        cursor = $( ".ui-resizable-" + this.axis ).css( "cursor" );
11144        $( "body" ).css( "cursor", cursor === "auto" ? this.axis + "-resize" : cursor );
11145
11146        this._addClass( "ui-resizable-resizing" );
11147        this._propagate( "start", event );
11148        return true;
11149    },
11150
11151    _mouseDrag: function( event ) {
11152
11153        var data, props,
11154            smp = this.originalMousePosition,
11155            a = this.axis,
11156            dx = ( event.pageX - smp.left ) || 0,
11157            dy = ( event.pageY - smp.top ) || 0,
11158            trigger = this._change[ a ];
11159
11160        this._updatePrevProperties();
11161
11162        if ( !trigger ) {
11163            return false;
11164        }
11165
11166        data = trigger.apply( this, [ event, dx, dy ] );
11167
11168        this._updateVirtualBoundaries( event.shiftKey );
11169        if ( this._aspectRatio || event.shiftKey ) {
11170            data = this._updateRatio( data, event );
11171        }
11172
11173        data = this._respectSize( data, event );
11174
11175        this._updateCache( data );
11176
11177        this._propagate( "resize", event );
11178
11179        props = this._applyChanges();
11180
11181        if ( !this._helper && this._proportionallyResizeElements.length ) {
11182            this._proportionallyResize();
11183        }
11184
11185        if ( !$.isEmptyObject( props ) ) {
11186            this._updatePrevProperties();
11187            this._trigger( "resize", event, this.ui() );
11188            this._applyChanges();
11189        }
11190
11191        return false;
vendor: 14,109 bytes, lines 11192-11627
11192    },
11193
11194    _mouseStop: function( event ) {
11195
11196        this.resizing = false;
11197        var pr, ista, soffseth, soffsetw, s, left, top,
11198            o = this.options, that = this;
11199
11200        if ( this._helper ) {
11201
11202            pr = this._proportionallyResizeElements;
11203            ista = pr.length && ( /textarea/i ).test( pr[ 0 ].nodeName );
11204            soffseth = ista && this._hasScroll( pr[ 0 ], "left" ) ? 0 : that.sizeDiff.height;
11205            soffsetw = ista ? 0 : that.sizeDiff.width;
11206
11207            s = {
11208                width: ( that.helper.width()  - soffsetw ),
11209                height: ( that.helper.height() - soffseth )
11210            };
11211            left = ( parseFloat( that.element.css( "left" ) ) +
11212                ( that.position.left - that.originalPosition.left ) ) || null;
11213            top = ( parseFloat( that.element.css( "top" ) ) +
11214                ( that.position.top - that.originalPosition.top ) ) || null;
11215
11216            if ( !o.animate ) {
11217                this.element.css( $.extend( s, { top: top, left: left } ) );
11218            }
11219
11220            that.helper.height( that.size.height );
11221            that.helper.width( that.size.width );
11222
11223            if ( this._helper && !o.animate ) {
11224                this._proportionallyResize();
11225            }
11226        }
11227
11228        $( "body" ).css( "cursor", "auto" );
11229
11230        this._removeClass( "ui-resizable-resizing" );
11231
11232        this._propagate( "stop", event );
11233
11234        if ( this._helper ) {
11235            this.helper.remove();
11236        }
11237
11238        return false;
11239
11240    },
11241
11242    _updatePrevProperties: function() {
11243        this.prevPosition = {
11244            top: this.position.top,
11245            left: this.position.left
11246        };
11247        this.prevSize = {
11248            width: this.size.width,
11249            height: this.size.height
11250        };
11251    },
11252
11253    _applyChanges: function() {
11254        var props = {};
11255
11256        if ( this.position.top !== this.prevPosition.top ) {
11257            props.top = this.position.top + "px";
11258        }
11259        if ( this.position.left !== this.prevPosition.left ) {
11260            props.left = this.position.left + "px";
11261        }
11262        if ( this.size.width !== this.prevSize.width ) {
11263            props.width = this.size.width + "px";
11264        }
11265        if ( this.size.height !== this.prevSize.height ) {
11266            props.height = this.size.height + "px";
11267        }
11268
11269        this.helper.css( props );
11270
11271        return props;
11272    },
11273
11274    _updateVirtualBoundaries: function( forceAspectRatio ) {
11275        var pMinWidth, pMaxWidth, pMinHeight, pMaxHeight, b,
11276            o = this.options;
11277
11278        b = {
11279            minWidth: this._isNumber( o.minWidth ) ? o.minWidth : 0,
11280            maxWidth: this._isNumber( o.maxWidth ) ? o.maxWidth : Infinity,
11281            minHeight: this._isNumber( o.minHeight ) ? o.minHeight : 0,
11282            maxHeight: this._isNumber( o.maxHeight ) ? o.maxHeight : Infinity
11283        };
11284
11285        if ( this._aspectRatio || forceAspectRatio ) {
11286            pMinWidth = b.minHeight * this.aspectRatio;
11287            pMinHeight = b.minWidth / this.aspectRatio;
11288            pMaxWidth = b.maxHeight * this.aspectRatio;
11289            pMaxHeight = b.maxWidth / this.aspectRatio;
11290
11291            if ( pMinWidth > b.minWidth ) {
11292                b.minWidth = pMinWidth;
11293            }
11294            if ( pMinHeight > b.minHeight ) {
11295                b.minHeight = pMinHeight;
11296            }
11297            if ( pMaxWidth < b.maxWidth ) {
11298                b.maxWidth = pMaxWidth;
11299            }
11300            if ( pMaxHeight < b.maxHeight ) {
11301                b.maxHeight = pMaxHeight;
11302            }
11303        }
11304        this._vBoundaries = b;
11305    },
11306
11307    _updateCache: function( data ) {
11308        this.offset = this.helper.offset();
11309        if ( this._isNumber( data.left ) ) {
11310            this.position.left = data.left;
11311        }
11312        if ( this._isNumber( data.top ) ) {
11313            this.position.top = data.top;
11314        }
11315        if ( this._isNumber( data.height ) ) {
11316            this.size.height = data.height;
11317        }
11318        if ( this._isNumber( data.width ) ) {
11319            this.size.width = data.width;
11320        }
11321    },
11322
11323    _updateRatio: function( data ) {
11324
11325        var cpos = this.position,
11326            csize = this.size,
11327            a = this.axis;
11328
11329        if ( this._isNumber( data.height ) ) {
11330            data.width = ( data.height * this.aspectRatio );
11331        } else if ( this._isNumber( data.width ) ) {
11332            data.height = ( data.width / this.aspectRatio );
11333        }
11334
11335        if ( a === "sw" ) {
11336            data.left = cpos.left + ( csize.width - data.width );
11337            data.top = null;
11338        }
11339        if ( a === "nw" ) {
11340            data.top = cpos.top + ( csize.height - data.height );
11341            data.left = cpos.left + ( csize.width - data.width );
11342        }
11343
11344        return data;
11345    },
11346
11347    _respectSize: function( data ) {
11348
11349        var o = this._vBoundaries,
11350            a = this.axis,
11351            ismaxw = this._isNumber( data.width ) && o.maxWidth && ( o.maxWidth < data.width ),
11352            ismaxh = this._isNumber( data.height ) && o.maxHeight && ( o.maxHeight < data.height ),
11353            isminw = this._isNumber( data.width ) && o.minWidth && ( o.minWidth > data.width ),
11354            isminh = this._isNumber( data.height ) && o.minHeight && ( o.minHeight > data.height ),
11355            dw = this.originalPosition.left + this.originalSize.width,
11356            dh = this.originalPosition.top + this.originalSize.height,
11357            cw = /sw|nw|w/.test( a ), ch = /nw|ne|n/.test( a );
11358        if ( isminw ) {
11359            data.width = o.minWidth;
11360        }
11361        if ( isminh ) {
11362            data.height = o.minHeight;
11363        }
11364        if ( ismaxw ) {
11365            data.width = o.maxWidth;
11366        }
11367        if ( ismaxh ) {
11368            data.height = o.maxHeight;
11369        }
11370
11371        if ( isminw && cw ) {
11372            data.left = dw - o.minWidth;
11373        }
11374        if ( ismaxw && cw ) {
11375            data.left = dw - o.maxWidth;
11376        }
11377        if ( isminh && ch ) {
11378            data.top = dh - o.minHeight;
11379        }
11380        if ( ismaxh && ch ) {
11381            data.top = dh - o.maxHeight;
11382        }
11383
11384        // Fixing jump error on top/left - bug #2330
11385        if ( !data.width && !data.height && !data.left && data.top ) {
11386            data.top = null;
11387        } else if ( !data.width && !data.height && !data.top && data.left ) {
11388            data.left = null;
11389        }
11390
11391        return data;
11392    },
11393
11394    _getPaddingPlusBorderDimensions: function( element ) {
11395        var i = 0,
11396            widths = [],
11397            borders = [
11398                element.css( "borderTopWidth" ),
11399                element.css( "borderRightWidth" ),
11400                element.css( "borderBottomWidth" ),
11401                element.css( "borderLeftWidth" )
11402            ],
11403            paddings = [
11404                element.css( "paddingTop" ),
11405                element.css( "paddingRight" ),
11406                element.css( "paddingBottom" ),
11407                element.css( "paddingLeft" )
11408            ];
11409
11410        for ( ; i < 4; i++ ) {
11411            widths[ i ] = ( parseFloat( borders[ i ] ) || 0 );
11412            widths[ i ] += ( parseFloat( paddings[ i ] ) || 0 );
11413        }
11414
11415        return {
11416            height: widths[ 0 ] + widths[ 2 ],
11417            width: widths[ 1 ] + widths[ 3 ]
11418        };
11419    },
11420
11421    _proportionallyResize: function() {
11422
11423        if ( !this._proportionallyResizeElements.length ) {
11424            return;
11425        }
11426
11427        var prel,
11428            i = 0,
11429            element = this.helper || this.element;
11430
11431        for ( ; i < this._proportionallyResizeElements.length; i++ ) {
11432
11433            prel = this._proportionallyResizeElements[ i ];
11434
11435            // TODO: Seems like a bug to cache this.outerDimensions
11436            // considering that we are in a loop.
11437            if ( !this.outerDimensions ) {
11438                this.outerDimensions = this._getPaddingPlusBorderDimensions( prel );
11439            }
11440
11441            prel.css( {
11442                height: ( element.height() - this.outerDimensions.height ) || 0,
11443                width: ( element.width() - this.outerDimensions.width ) || 0
11444            } );
11445
11446        }
11447
11448    },
11449
11450    _renderProxy: function() {
11451
11452        var el = this.element, o = this.options;
11453        this.elementOffset = el.offset();
11454
11455        if ( this._helper ) {
11456
11457            this.helper = this.helper || $( "<div style='overflow:hidden;'></div>" );
11458
11459            this._addClass( this.helper, this._helper );
11460            this.helper.css( {
11461                width: this.element.outerWidth(),
11462                height: this.element.outerHeight(),
11463                position: "absolute",
11464                left: this.elementOffset.left + "px",
11465                top: this.elementOffset.top + "px",
11466                zIndex: ++o.zIndex //TODO: Don't modify option
11467            } );
11468
11469            this.helper
11470                .appendTo( "body" )
11471                .disableSelection();
11472
11473        } else {
11474            this.helper = this.element;
11475        }
11476
11477    },
11478
11479    _change: {
11480        e: function( event, dx ) {
11481            return { width: this.originalSize.width + dx };
11482        },
11483        w: function( event, dx ) {
11484            var cs = this.originalSize, sp = this.originalPosition;
11485            return { left: sp.left + dx, width: cs.width - dx };
11486        },
11487        n: function( event, dx, dy ) {
11488            var cs = this.originalSize, sp = this.originalPosition;
11489            return { top: sp.top + dy, height: cs.height - dy };
11490        },
11491        s: function( event, dx, dy ) {
11492            return { height: this.originalSize.height + dy };
11493        },
11494        se: function( event, dx, dy ) {
11495            return $.extend( this._change.s.apply( this, arguments ),
11496                this._change.e.apply( this, [ event, dx, dy ] ) );
11497        },
11498        sw: function( event, dx, dy ) {
11499            return $.extend( this._change.s.apply( this, arguments ),
11500                this._change.w.apply( this, [ event, dx, dy ] ) );
11501        },
11502        ne: function( event, dx, dy ) {
11503            return $.extend( this._change.n.apply( this, arguments ),
11504                this._change.e.apply( this, [ event, dx, dy ] ) );
11505        },
11506        nw: function( event, dx, dy ) {
11507            return $.extend( this._change.n.apply( this, arguments ),
11508                this._change.w.apply( this, [ event, dx, dy ] ) );
11509        }
11510    },
11511
11512    _propagate: function( n, event ) {
11513        $.ui.plugin.call( this, n, [ event, this.ui() ] );
11514        ( n !== "resize" && this._trigger( n, event, this.ui() ) );
11515    },
11516
11517    plugins: {},
11518
11519    ui: function() {
11520        return {
11521            originalElement: this.originalElement,
11522            element: this.element,
11523            helper: this.helper,
11524            position: this.position,
11525            size: this.size,
11526            originalSize: this.originalSize,
11527            originalPosition: this.originalPosition
11528        };
11529    }
11530
11531} );
11532
11533/*
11534 * Resizable Extensions
11535 */
11536
11537$.ui.plugin.add( "resizable", "animate", {
11538
11539    stop: function( event ) {
11540        var that = $( this ).resizable( "instance" ),
11541            o = that.options,
11542            pr = that._proportionallyResizeElements,
11543            ista = pr.length && ( /textarea/i ).test( pr[ 0 ].nodeName ),
11544            soffseth = ista && that._hasScroll( pr[ 0 ], "left" ) ? 0 : that.sizeDiff.height,
11545            soffsetw = ista ? 0 : that.sizeDiff.width,
11546            style = {
11547                width: ( that.size.width - soffsetw ),
11548                height: ( that.size.height - soffseth )
11549            },
11550            left = ( parseFloat( that.element.css( "left" ) ) +
11551                ( that.position.left - that.originalPosition.left ) ) || null,
11552            top = ( parseFloat( that.element.css( "top" ) ) +
11553                ( that.position.top - that.originalPosition.top ) ) || null;
11554
11555        that.element.animate(
11556            $.extend( style, top && left ? { top: top, left: left } : {} ), {
11557                duration: o.animateDuration,
11558                easing: o.animateEasing,
11559                step: function() {
11560
11561                    var data = {
11562                        width: parseFloat( that.element.css( "width" ) ),
11563                        height: parseFloat( that.element.css( "height" ) ),
11564                        top: parseFloat( that.element.css( "top" ) ),
11565                        left: parseFloat( that.element.css( "left" ) )
11566                    };
11567
11568                    if ( pr && pr.length ) {
11569                        $( pr[ 0 ] ).css( { width: data.width, height: data.height } );
11570                    }
11571
11572                    // Propagating resize, and updating values for each animation step
11573                    that._updateCache( data );
11574                    that._propagate( "resize", event );
11575
11576                }
11577            }
11578        );
11579    }
11580
11581} );
11582
11583$.ui.plugin.add( "resizable", "containment", {
11584
11585    start: function() {
11586        var element, p, co, ch, cw, width, height,
11587            that = $( this ).resizable( "instance" ),
11588            o = that.options,
11589            el = that.element,
11590            oc = o.containment,
11591            ce = ( oc instanceof $ ) ?
11592                oc.get( 0 ) :
11593                ( /parent/.test( oc ) ) ? el.parent().get( 0 ) : oc;
11594
11595        if ( !ce ) {
11596            return;
11597        }
11598
11599        that.containerElement = $( ce );
11600
11601        if ( /document/.test( oc ) || oc === document ) {
11602            that.containerOffset = {
11603                left: 0,
11604                top: 0
11605            };
11606            that.containerPosition = {
11607                left: 0,
11608                top: 0
11609            };
11610
11611            that.parentData = {
11612                element: $( document ),
11613                left: 0,
11614                top: 0,
11615                width: $( document ).width(),
11616                height: $( document ).height() || document.body.parentNode.scrollHeight
11617            };
11618        } else {
11619            element = $( ce );
11620            p = [];
11621            $( [ "Top", "Right", "Left", "Bottom" ] ).each( function( i, name ) {
11622                p[ i ] = that._num( element.css( "padding" + name ) );
11623            } );
11624
11625            that.containerOffset = element.offset();
11626            that.containerPosition = element.position();
11627            that.containerSize = {
vendor: 4,272 bytes, lines 11628-11747
11628                height: ( element.innerHeight() - p[ 3 ] ),
11629                width: ( element.innerWidth() - p[ 1 ] )
11630            };
11631
11632            co = that.containerOffset;
11633            ch = that.containerSize.height;
11634            cw = that.containerSize.width;
11635            width = ( that._hasScroll ( ce, "left" ) ? ce.scrollWidth : cw );
11636            height = ( that._hasScroll ( ce ) ? ce.scrollHeight : ch ) ;
11637
11638            that.parentData = {
11639                element: ce,
11640                left: co.left,
11641                top: co.top,
11642                width: width,
11643                height: height
11644            };
11645        }
11646    },
11647
11648    resize: function( event ) {
11649        var woset, hoset, isParent, isOffsetRelative,
11650            that = $( this ).resizable( "instance" ),
11651            o = that.options,
11652            co = that.containerOffset,
11653            cp = that.position,
11654            pRatio = that._aspectRatio || event.shiftKey,
11655            cop = {
11656                top: 0,
11657                left: 0
11658            },
11659            ce = that.containerElement,
11660            continueResize = true;
11661
11662        if ( ce[ 0 ] !== document && ( /static/ ).test( ce.css( "position" ) ) ) {
11663            cop = co;
11664        }
11665
11666        if ( cp.left < ( that._helper ? co.left : 0 ) ) {
11667            that.size.width = that.size.width +
11668                ( that._helper ?
11669                    ( that.position.left - co.left ) :
11670                    ( that.position.left - cop.left ) );
11671
11672            if ( pRatio ) {
11673                that.size.height = that.size.width / that.aspectRatio;
11674                continueResize = false;
11675            }
11676            that.position.left = o.helper ? co.left : 0;
11677        }
11678
11679        if ( cp.top < ( that._helper ? co.top : 0 ) ) {
11680            that.size.height = that.size.height +
11681                ( that._helper ?
11682                    ( that.position.top - co.top ) :
11683                    that.position.top );
11684
11685            if ( pRatio ) {
11686                that.size.width = that.size.height * that.aspectRatio;
11687                continueResize = false;
11688            }
11689            that.position.top = that._helper ? co.top : 0;
11690        }
11691
11692        isParent = that.containerElement.get( 0 ) === that.element.parent().get( 0 );
11693        isOffsetRelative = /relative|absolute/.test( that.containerElement.css( "position" ) );
11694
11695        if ( isParent && isOffsetRelative ) {
11696            that.offset.left = that.parentData.left + that.position.left;
11697            that.offset.top = that.parentData.top + that.position.top;
11698        } else {
11699            that.offset.left = that.element.offset().left;
11700            that.offset.top = that.element.offset().top;
11701        }
11702
11703        woset = Math.abs( that.sizeDiff.width +
11704            ( that._helper ?
11705                that.offset.left - cop.left :
11706                ( that.offset.left - co.left ) ) );
11707
11708        hoset = Math.abs( that.sizeDiff.height +
11709            ( that._helper ?
11710                that.offset.top - cop.top :
11711                ( that.offset.top - co.top ) ) );
11712
11713        if ( woset + that.size.width >= that.parentData.width ) {
11714            that.size.width = that.parentData.width - woset;
11715            if ( pRatio ) {
11716                that.size.height = that.size.width / that.aspectRatio;
11717                continueResize = false;
11718            }
11719        }
11720
11721        if ( hoset + that.size.height >= that.parentData.height ) {
11722            that.size.height = that.parentData.height - hoset;
11723            if ( pRatio ) {
11724                that.size.width = that.size.height * that.aspectRatio;
11725                continueResize = false;
11726            }
11727        }
11728
11729        if ( !continueResize ) {
11730            that.position.left = that.prevPosition.left;
11731            that.position.top = that.prevPosition.top;
11732            that.size.width = that.prevSize.width;
11733            that.size.height = that.prevSize.height;
11734        }
11735    },
11736
11737    stop: function() {
11738        var that = $( this ).resizable( "instance" ),
11739            o = that.options,
11740            co = that.containerOffset,
11741            cop = that.containerPosition,
11742            ce = that.containerElement,
11743            helper = $( that.helper ),
11744            ho = helper.offset(),
11745            w = helper.outerWidth() - that.sizeDiff.width,
11746            h = helper.outerHeight() - that.sizeDiff.height;
11747
vendor: 6,483 bytes, lines 11748-11955
11748        if ( that._helper && !o.animate && ( /relative/ ).test( ce.css( "position" ) ) ) {
11749            $( this ).css( {
11750                left: ho.left - cop.left - co.left,
11751                width: w,
11752                height: h
11753            } );
11754        }
11755
11756        if ( that._helper && !o.animate && ( /static/ ).test( ce.css( "position" ) ) ) {
11757            $( this ).css( {
11758                left: ho.left - cop.left - co.left,
11759                width: w,
11760                height: h
11761            } );
11762        }
11763    }
11764} );
11765
11766$.ui.plugin.add( "resizable", "alsoResize", {
11767
11768    start: function() {
11769        var that = $( this ).resizable( "instance" ),
11770            o = that.options;
11771
11772        $( o.alsoResize ).each( function() {
11773            var el = $( this );
11774            el.data( "ui-resizable-alsoresize", {
11775                width: parseFloat( el.width() ), height: parseFloat( el.height() ),
11776                left: parseFloat( el.css( "left" ) ), top: parseFloat( el.css( "top" ) )
11777            } );
11778        } );
11779    },
11780
11781    resize: function( event, ui ) {
11782        var that = $( this ).resizable( "instance" ),
11783            o = that.options,
11784            os = that.originalSize,
11785            op = that.originalPosition,
11786            delta = {
11787                height: ( that.size.height - os.height ) || 0,
11788                width: ( that.size.width - os.width ) || 0,
11789                top: ( that.position.top - op.top ) || 0,
11790                left: ( that.position.left - op.left ) || 0
11791            };
11792
11793            $( o.alsoResize ).each( function() {
11794                var el = $( this ), start = $( this ).data( "ui-resizable-alsoresize" ), style = {},
11795                    css = el.parents( ui.originalElement[ 0 ] ).length ?
11796                            [ "width", "height" ] :
11797                            [ "width", "height", "top", "left" ];
11798
11799                $.each( css, function( i, prop ) {
11800                    var sum = ( start[ prop ] || 0 ) + ( delta[ prop ] || 0 );
11801                    if ( sum && sum >= 0 ) {
11802                        style[ prop ] = sum || null;
11803                    }
11804                } );
11805
11806                el.css( style );
11807            } );
11808    },
11809
11810    stop: function() {
11811        $( this ).removeData( "ui-resizable-alsoresize" );
11812    }
11813} );
11814
11815$.ui.plugin.add( "resizable", "ghost", {
11816
11817    start: function() {
11818
11819        var that = $( this ).resizable( "instance" ), cs = that.size;
11820
11821        that.ghost = that.originalElement.clone();
11822        that.ghost.css( {
11823            opacity: 0.25,
11824            display: "block",
11825            position: "relative",
11826            height: cs.height,
11827            width: cs.width,
11828            margin: 0,
11829            left: 0,
11830            top: 0
11831        } );
11832
11833        that._addClass( that.ghost, "ui-resizable-ghost" );
11834
11835        // DEPRECATED
11836        // TODO: remove after 1.12
11837        if ( $.uiBackCompat !== false && typeof that.options.ghost === "string" ) {
11838
11839            // Ghost option
11840            that.ghost.addClass( this.options.ghost );
11841        }
11842
11843        that.ghost.appendTo( that.helper );
11844
11845    },
11846
11847    resize: function() {
11848        var that = $( this ).resizable( "instance" );
11849        if ( that.ghost ) {
11850            that.ghost.css( {
11851                position: "relative",
11852                height: that.size.height,
11853                width: that.size.width
11854            } );
11855        }
11856    },
11857
11858    stop: function() {
11859        var that = $( this ).resizable( "instance" );
11860        if ( that.ghost && that.helper ) {
11861            that.helper.get( 0 ).removeChild( that.ghost.get( 0 ) );
11862        }
11863    }
11864
11865} );
11866
11867$.ui.plugin.add( "resizable", "grid", {
11868
11869    resize: function() {
11870        var outerDimensions,
11871            that = $( this ).resizable( "instance" ),
11872            o = that.options,
11873            cs = that.size,
11874            os = that.originalSize,
11875            op = that.originalPosition,
11876            a = that.axis,
11877            grid = typeof o.grid === "number" ? [ o.grid, o.grid ] : o.grid,
11878            gridX = ( grid[ 0 ] || 1 ),
11879            gridY = ( grid[ 1 ] || 1 ),
11880            ox = Math.round( ( cs.width - os.width ) / gridX ) * gridX,
11881            oy = Math.round( ( cs.height - os.height ) / gridY ) * gridY,
11882            newWidth = os.width + ox,
11883            newHeight = os.height + oy,
11884            isMaxWidth = o.maxWidth && ( o.maxWidth < newWidth ),
11885            isMaxHeight = o.maxHeight && ( o.maxHeight < newHeight ),
11886            isMinWidth = o.minWidth && ( o.minWidth > newWidth ),
11887            isMinHeight = o.minHeight && ( o.minHeight > newHeight );
11888
11889        o.grid = grid;
11890
11891        if ( isMinWidth ) {
11892            newWidth += gridX;
11893        }
11894        if ( isMinHeight ) {
11895            newHeight += gridY;
11896        }
11897        if ( isMaxWidth ) {
11898            newWidth -= gridX;
11899        }
11900        if ( isMaxHeight ) {
11901            newHeight -= gridY;
11902        }
11903
11904        if ( /^(se|s|e)$/.test( a ) ) {
11905            that.size.width = newWidth;
11906            that.size.height = newHeight;
11907        } else if ( /^(ne)$/.test( a ) ) {
11908            that.size.width = newWidth;
11909            that.size.height = newHeight;
11910            that.position.top = op.top - oy;
11911        } else if ( /^(sw)$/.test( a ) ) {
11912            that.size.width = newWidth;
11913            that.size.height = newHeight;
11914            that.position.left = op.left - ox;
11915        } else {
11916            if ( newHeight - gridY <= 0 || newWidth - gridX <= 0 ) {
11917                outerDimensions = that._getPaddingPlusBorderDimensions( this );
11918            }
11919
11920            if ( newHeight - gridY > 0 ) {
11921                that.size.height = newHeight;
11922                that.position.top = op.top - oy;
11923            } else {
11924                newHeight = gridY - outerDimensions.height;
11925                that.size.height = newHeight;
11926                that.position.top = op.top + os.height - newHeight;
11927            }
11928            if ( newWidth - gridX > 0 ) {
11929                that.size.width = newWidth;
11930                that.position.left = op.left - ox;
11931            } else {
11932                newWidth = gridX - outerDimensions.width;
11933                that.size.width = newWidth;
11934                that.position.left = op.left + os.width - newWidth;
11935            }
11936        }
11937    }
11938
11939} );
11940
11941var widgetsResizable = $.ui.resizable;
11942
11943
11944/*!
11945 * jQuery UI Dialog 1.12.1
11946 * http://jqueryui.com
11947 *
11948 * Copyright jQuery Foundation and other contributors
11949 * Released under the MIT license.
11950 * http://jquery.org/license
11951 */
11952
11953//>>label: Dialog
11954//>>group: Widgets
11955//>>description: Displays customizable dialog windows.
vendor: 3,834 bytes, lines 11956-12103
11956//>>docs: http://api.jqueryui.com/dialog/
11957//>>demos: http://jqueryui.com/dialog/
11958//>>css.structure: ../../themes/base/core.css
11959//>>css.structure: ../../themes/base/dialog.css
11960//>>css.theme: ../../themes/base/theme.css
11961
11962
11963
11964$.widget( "ui.dialog", {
11965    version: "1.12.1",
11966    options: {
11967        appendTo: "body",
11968        autoOpen: true,
11969        buttons: [],
11970        classes: {
11971            "ui-dialog": "ui-corner-all",
11972            "ui-dialog-titlebar": "ui-corner-all"
11973        },
11974        closeOnEscape: true,
11975        closeText: "Close",
11976        draggable: true,
11977        hide: null,
11978        height: "auto",
11979        maxHeight: null,
11980        maxWidth: null,
11981        minHeight: 150,
11982        minWidth: 150,
11983        modal: false,
11984        position: {
11985            my: "center",
11986            at: "center",
11987            of: window,
11988            collision: "fit",
11989
11990            // Ensure the titlebar is always visible
11991            using: function( pos ) {
11992                var topOffset = $( this ).css( pos ).offset().top;
11993                if ( topOffset < 0 ) {
11994                    $( this ).css( "top", pos.top - topOffset );
11995                }
11996            }
11997        },
11998        resizable: true,
11999        show: null,
12000        title: null,
12001        width: 300,
12002
12003        // Callbacks
12004        beforeClose: null,
12005        close: null,
12006        drag: null,
12007        dragStart: null,
12008        dragStop: null,
12009        focus: null,
12010        open: null,
12011        resize: null,
12012        resizeStart: null,
12013        resizeStop: null
12014    },
12015
12016    sizeRelatedOptions: {
12017        buttons: true,
12018        height: true,
12019        maxHeight: true,
12020        maxWidth: true,
12021        minHeight: true,
12022        minWidth: true,
12023        width: true
12024    },
12025
12026    resizableRelatedOptions: {
12027        maxHeight: true,
12028        maxWidth: true,
12029        minHeight: true,
12030        minWidth: true
12031    },
12032
12033    _create: function() {
12034        this.originalCss = {
12035            display: this.element[ 0 ].style.display,
12036            width: this.element[ 0 ].style.width,
12037            minHeight: this.element[ 0 ].style.minHeight,
12038            maxHeight: this.element[ 0 ].style.maxHeight,
12039            height: this.element[ 0 ].style.height
12040        };
12041        this.originalPosition = {
12042            parent: this.element.parent(),
12043            index: this.element.parent().children().index( this.element )
12044        };
12045        this.originalTitle = this.element.attr( "title" );
12046        if ( this.options.title == null && this.originalTitle != null ) {
12047            this.options.title = this.originalTitle;
12048        }
12049
12050        // Dialogs can't be disabled
12051        if ( this.options.disabled ) {
12052            this.options.disabled = false;
12053        }
12054
12055        this._createWrapper();
12056
12057        this.element
12058            .show()
12059            .removeAttr( "title" )
12060            .appendTo( this.uiDialog );
12061
12062        this._addClass( "ui-dialog-content", "ui-widget-content" );
12063
12064        this._createTitlebar();
12065        this._createButtonPane();
12066
12067        if ( this.options.draggable && $.fn.draggable ) {
12068            this._makeDraggable();
12069        }
12070        if ( this.options.resizable && $.fn.resizable ) {
12071            this._makeResizable();
12072        }
12073
12074        this._isOpen = false;
12075
12076        this._trackFocus();
12077    },
12078
12079    _init: function() {
12080        if ( this.options.autoOpen ) {
12081            this.open();
12082        }
12083    },
12084
12085    _appendTo: function() {
12086        var element = this.options.appendTo;
12087        if ( element && ( element.jquery || element.nodeType ) ) {
12088            return $( element );
12089        }
12090        return this.document.find( element || "body" ).eq( 0 );
12091    },
12092
12093    _destroy: function() {
12094        var next,
12095            originalPosition = this.originalPosition;
12096
12097        this._untrackInstance();
12098        this._destroyOverlay();
12099
12100        this.element
12101            .removeUniqueId()
12102            .css( this.originalCss )
12103
vendor: 37,682 bytes, lines 12104-13264
12104            // Without detaching first, the following becomes really slow
12105            .detach();
12106
12107        this.uiDialog.remove();
12108
12109        if ( this.originalTitle ) {
12110            this.element.attr( "title", this.originalTitle );
12111        }
12112
12113        next = originalPosition.parent.children().eq( originalPosition.index );
12114
12115        // Don't try to place the dialog next to itself (#8613)
12116        if ( next.length && next[ 0 ] !== this.element[ 0 ] ) {
12117            next.before( this.element );
12118        } else {
12119            originalPosition.parent.append( this.element );
12120        }
12121    },
12122
12123    widget: function() {
12124        return this.uiDialog;
12125    },
12126
12127    disable: $.noop,
12128    enable: $.noop,
12129
12130    close: function( event ) {
12131        var that = this;
12132
12133        if ( !this._isOpen || this._trigger( "beforeClose", event ) === false ) {
12134            return;
12135        }
12136
12137        this._isOpen = false;
12138        this._focusedElement = null;
12139        this._destroyOverlay();
12140        this._untrackInstance();
12141
12142        if ( !this.opener.filter( ":focusable" ).trigger( "focus" ).length ) {
12143
12144            // Hiding a focused element doesn't trigger blur in WebKit
12145            // so in case we have nothing to focus on, explicitly blur the active element
12146            // https://bugs.webkit.org/show_bug.cgi?id=47182
12147            $.ui.safeBlur( $.ui.safeActiveElement( this.document[ 0 ] ) );
12148        }
12149
12150        this._hide( this.uiDialog, this.options.hide, function() {
12151            that._trigger( "close", event );
12152        } );
12153    },
12154
12155    isOpen: function() {
12156        return this._isOpen;
12157    },
12158
12159    moveToTop: function() {
12160        this._moveToTop();
12161    },
12162
12163    _moveToTop: function( event, silent ) {
12164        var moved = false,
12165            zIndices = this.uiDialog.siblings( ".ui-front:visible" ).map( function() {
12166                return +$( this ).css( "z-index" );
12167            } ).get(),
12168            zIndexMax = Math.max.apply( null, zIndices );
12169
12170        if ( zIndexMax >= +this.uiDialog.css( "z-index" ) ) {
12171            this.uiDialog.css( "z-index", zIndexMax + 1 );
12172            moved = true;
12173        }
12174
12175        if ( moved && !silent ) {
12176            this._trigger( "focus", event );
12177        }
12178        return moved;
12179    },
12180
12181    open: function() {
12182        var that = this;
12183        if ( this._isOpen ) {
12184            if ( this._moveToTop() ) {
12185                this._focusTabbable();
12186            }
12187            return;
12188        }
12189
12190        this._isOpen = true;
12191        this.opener = $( $.ui.safeActiveElement( this.document[ 0 ] ) );
12192
12193        this._size();
12194        this._position();
12195        this._createOverlay();
12196        this._moveToTop( null, true );
12197
12198        // Ensure the overlay is moved to the top with the dialog, but only when
12199        // opening. The overlay shouldn't move after the dialog is open so that
12200        // modeless dialogs opened after the modal dialog stack properly.
12201        if ( this.overlay ) {
12202            this.overlay.css( "z-index", this.uiDialog.css( "z-index" ) - 1 );
12203        }
12204
12205        this._show( this.uiDialog, this.options.show, function() {
12206            that._focusTabbable();
12207            that._trigger( "focus" );
12208        } );
12209
12210        // Track the dialog immediately upon openening in case a focus event
12211        // somehow occurs outside of the dialog before an element inside the
12212        // dialog is focused (#10152)
12213        this._makeFocusTarget();
12214
12215        this._trigger( "open" );
12216    },
12217
12218    _focusTabbable: function() {
12219
12220        // Set focus to the first match:
12221        // 1. An element that was focused previously
12222        // 2. First element inside the dialog matching [autofocus]
12223        // 3. Tabbable element inside the content element
12224        // 4. Tabbable element inside the buttonpane
12225        // 5. The close button
12226        // 6. The dialog itself
12227        var hasFocus = this._focusedElement;
12228        if ( !hasFocus ) {
12229            hasFocus = this.element.find( "[autofocus]" );
12230        }
12231        if ( !hasFocus.length ) {
12232            hasFocus = this.element.find( ":tabbable" );
12233        }
12234        if ( !hasFocus.length ) {
12235            hasFocus = this.uiDialogButtonPane.find( ":tabbable" );
12236        }
12237        if ( !hasFocus.length ) {
12238            hasFocus = this.uiDialogTitlebarClose.filter( ":tabbable" );
12239        }
12240        if ( !hasFocus.length ) {
12241            hasFocus = this.uiDialog;
12242        }
12243        hasFocus.eq( 0 ).trigger( "focus" );
12244    },
12245
12246    _keepFocus: function( event ) {
12247        function checkFocus() {
12248            var activeElement = $.ui.safeActiveElement( this.document[ 0 ] ),
12249                isActive = this.uiDialog[ 0 ] === activeElement ||
12250                    $.contains( this.uiDialog[ 0 ], activeElement );
12251            if ( !isActive ) {
12252                this._focusTabbable();
12253            }
12254        }
12255        event.preventDefault();
12256        checkFocus.call( this );
12257
12258        // support: IE
12259        // IE <= 8 doesn't prevent moving focus even with event.preventDefault()
12260        // so we check again later
12261        this._delay( checkFocus );
12262    },
12263
12264    _createWrapper: function() {
12265        this.uiDialog = $( "<div>" )
12266            .hide()
12267            .attr( {
12268
12269                // Setting tabIndex makes the div focusable
12270                tabIndex: -1,
12271                role: "dialog"
12272            } )
12273            .appendTo( this._appendTo() );
12274
12275        this._addClass( this.uiDialog, "ui-dialog", "ui-widget ui-widget-content ui-front" );
12276        this._on( this.uiDialog, {
12277            keydown: function( event ) {
12278                if ( this.options.closeOnEscape && !event.isDefaultPrevented() && event.keyCode &&
12279                        event.keyCode === $.ui.keyCode.ESCAPE ) {
12280                    event.preventDefault();
12281                    this.close( event );
12282                    return;
12283                }
12284
12285                // Prevent tabbing out of dialogs
12286                if ( event.keyCode !== $.ui.keyCode.TAB || event.isDefaultPrevented() ) {
12287                    return;
12288                }
12289                var tabbables = this.uiDialog.find( ":tabbable" ),
12290                    first = tabbables.filter( ":first" ),
12291                    last = tabbables.filter( ":last" );
12292
12293                if ( ( event.target === last[ 0 ] || event.target === this.uiDialog[ 0 ] ) &&
12294                        !event.shiftKey ) {
12295                    this._delay( function() {
12296                        first.trigger( "focus" );
12297                    } );
12298                    event.preventDefault();
12299                } else if ( ( event.target === first[ 0 ] ||
12300                        event.target === this.uiDialog[ 0 ] ) && event.shiftKey ) {
12301                    this._delay( function() {
12302                        last.trigger( "focus" );
12303                    } );
12304                    event.preventDefault();
12305                }
12306            },
12307            mousedown: function( event ) {
12308                if ( this._moveToTop( event ) ) {
12309                    this._focusTabbable();
12310                }
12311            }
12312        } );
12313
12314        // We assume that any existing aria-describedby attribute means
12315        // that the dialog content is marked up properly
12316        // otherwise we brute force the content as the description
12317        if ( !this.element.find( "[aria-describedby]" ).length ) {
12318            this.uiDialog.attr( {
12319                "aria-describedby": this.element.uniqueId().attr( "id" )
12320            } );
12321        }
12322    },
12323
12324    _createTitlebar: function() {
12325        var uiDialogTitle;
12326
12327        this.uiDialogTitlebar = $( "<div>" );
12328        this._addClass( this.uiDialogTitlebar,
12329            "ui-dialog-titlebar", "ui-widget-header ui-helper-clearfix" );
12330        this._on( this.uiDialogTitlebar, {
12331            mousedown: function( event ) {
12332
12333                // Don't prevent click on close button (#8838)
12334                // Focusing a dialog that is partially scrolled out of view
12335                // causes the browser to scroll it into view, preventing the click event
12336                if ( !$( event.target ).closest( ".ui-dialog-titlebar-close" ) ) {
12337
12338                    // Dialog isn't getting focus when dragging (#8063)
12339                    this.uiDialog.trigger( "focus" );
12340                }
12341            }
12342        } );
12343
12344        // Support: IE
12345        // Use type="button" to prevent enter keypresses in textboxes from closing the
12346        // dialog in IE (#9312)
12347        this.uiDialogTitlebarClose = $( "<button type='button'></button>" )
12348            .button( {
12349                label: $( "<a>" ).text( this.options.closeText ).html(),
12350                icon: "ui-icon-closethick",
12351                showLabel: false
12352            } )
12353            .appendTo( this.uiDialogTitlebar );
12354
12355        this._addClass( this.uiDialogTitlebarClose, "ui-dialog-titlebar-close" );
12356        this._on( this.uiDialogTitlebarClose, {
12357            click: function( event ) {
12358                event.preventDefault();
12359                this.close( event );
12360            }
12361        } );
12362
12363        uiDialogTitle = $( "<span>" ).uniqueId().prependTo( this.uiDialogTitlebar );
12364        this._addClass( uiDialogTitle, "ui-dialog-title" );
12365        this._title( uiDialogTitle );
12366
12367        this.uiDialogTitlebar.prependTo( this.uiDialog );
12368
12369        this.uiDialog.attr( {
12370            "aria-labelledby": uiDialogTitle.attr( "id" )
12371        } );
12372    },
12373
12374    _title: function( title ) {
12375        if ( this.options.title ) {
12376            title.text( this.options.title );
12377        } else {
12378            title.html( "&#160;" );
12379        }
12380    },
12381
12382    _createButtonPane: function() {
12383        this.uiDialogButtonPane = $( "<div>" );
12384        this._addClass( this.uiDialogButtonPane, "ui-dialog-buttonpane",
12385            "ui-widget-content ui-helper-clearfix" );
12386
12387        this.uiButtonSet = $( "<div>" )
12388            .appendTo( this.uiDialogButtonPane );
12389        this._addClass( this.uiButtonSet, "ui-dialog-buttonset" );
12390
12391        this._createButtons();
12392    },
12393
12394    _createButtons: function() {
12395        var that = this,
12396            buttons = this.options.buttons;
12397
12398        // If we already have a button pane, remove it
12399        this.uiDialogButtonPane.remove();
12400        this.uiButtonSet.empty();
12401
12402        if ( $.isEmptyObject( buttons ) || ( $.isArray( buttons ) && !buttons.length ) ) {
12403            this._removeClass( this.uiDialog, "ui-dialog-buttons" );
12404            return;
12405        }
12406
12407        $.each( buttons, function( name, props ) {
12408            var click, buttonOptions;
12409            props = $.isFunction( props ) ?
12410                { click: props, text: name } :
12411                props;
12412
12413            // Default to a non-submitting button
12414            props = $.extend( { type: "button" }, props );
12415
12416            // Change the context for the click callback to be the main element
12417            click = props.click;
12418            buttonOptions = {
12419                icon: props.icon,
12420                iconPosition: props.iconPosition,
12421                showLabel: props.showLabel,
12422
12423                // Deprecated options
12424                icons: props.icons,
12425                text: props.text
12426            };
12427
12428            delete props.click;
12429            delete props.icon;
12430            delete props.iconPosition;
12431            delete props.showLabel;
12432
12433            // Deprecated options
12434            delete props.icons;
12435            if ( typeof props.text === "boolean" ) {
12436                delete props.text;
12437            }
12438
12439            $( "<button></button>", props )
12440                .button( buttonOptions )
12441                .appendTo( that.uiButtonSet )
12442                .on( "click", function() {
12443                    click.apply( that.element[ 0 ], arguments );
12444                } );
12445        } );
12446        this._addClass( this.uiDialog, "ui-dialog-buttons" );
12447        this.uiDialogButtonPane.appendTo( this.uiDialog );
12448    },
12449
12450    _makeDraggable: function() {
12451        var that = this,
12452            options = this.options;
12453
12454        function filteredUi( ui ) {
12455            return {
12456                position: ui.position,
12457                offset: ui.offset
12458            };
12459        }
12460
12461        this.uiDialog.draggable( {
12462            cancel: ".ui-dialog-content, .ui-dialog-titlebar-close",
12463            handle: ".ui-dialog-titlebar",
12464            containment: "document",
12465            start: function( event, ui ) {
12466                that._addClass( $( this ), "ui-dialog-dragging" );
12467                that._blockFrames();
12468                that._trigger( "dragStart", event, filteredUi( ui ) );
12469            },
12470            drag: function( event, ui ) {
12471                that._trigger( "drag", event, filteredUi( ui ) );
12472            },
12473            stop: function( event, ui ) {
12474                var left = ui.offset.left - that.document.scrollLeft(),
12475                    top = ui.offset.top - that.document.scrollTop();
12476
12477                options.position = {
12478                    my: "left top",
12479                    at: "left" + ( left >= 0 ? "+" : "" ) + left + " " +
12480                        "top" + ( top >= 0 ? "+" : "" ) + top,
12481                    of: that.window
12482                };
12483                that._removeClass( $( this ), "ui-dialog-dragging" );
12484                that._unblockFrames();
12485                that._trigger( "dragStop", event, filteredUi( ui ) );
12486            }
12487        } );
12488    },
12489
12490    _makeResizable: function() {
12491        var that = this,
12492            options = this.options,
12493            handles = options.resizable,
12494
12495            // .ui-resizable has position: relative defined in the stylesheet
12496            // but dialogs have to use absolute or fixed positioning
12497            position = this.uiDialog.css( "position" ),
12498            resizeHandles = typeof handles === "string" ?
12499                handles :
12500                "n,e,s,w,se,sw,ne,nw";
12501
12502        function filteredUi( ui ) {
12503            return {
12504                originalPosition: ui.originalPosition,
12505                originalSize: ui.originalSize,
12506                position: ui.position,
12507                size: ui.size
12508            };
12509        }
12510
12511        this.uiDialog.resizable( {
12512            cancel: ".ui-dialog-content",
12513            containment: "document",
12514            alsoResize: this.element,
12515            maxWidth: options.maxWidth,
12516            maxHeight: options.maxHeight,
12517            minWidth: options.minWidth,
12518            minHeight: this._minHeight(),
12519            handles: resizeHandles,
12520            start: function( event, ui ) {
12521                that._addClass( $( this ), "ui-dialog-resizing" );
12522                that._blockFrames();
12523                that._trigger( "resizeStart", event, filteredUi( ui ) );
12524            },
12525            resize: function( event, ui ) {
12526                that._trigger( "resize", event, filteredUi( ui ) );
12527            },
12528            stop: function( event, ui ) {
12529                var offset = that.uiDialog.offset(),
12530                    left = offset.left - that.document.scrollLeft(),
12531                    top = offset.top - that.document.scrollTop();
12532
12533                options.height = that.uiDialog.height();
12534                options.width = that.uiDialog.width();
12535                options.position = {
12536                    my: "left top",
12537                    at: "left" + ( left >= 0 ? "+" : "" ) + left + " " +
12538                        "top" + ( top >= 0 ? "+" : "" ) + top,
12539                    of: that.window
12540                };
12541                that._removeClass( $( this ), "ui-dialog-resizing" );
12542                that._unblockFrames();
12543                that._trigger( "resizeStop", event, filteredUi( ui ) );
12544            }
12545        } )
12546            .css( "position", position );
12547    },
12548
12549    _trackFocus: function() {
12550        this._on( this.widget(), {
12551            focusin: function( event ) {
12552                this._makeFocusTarget();
12553                this._focusedElement = $( event.target );
12554            }
12555        } );
12556    },
12557
12558    _makeFocusTarget: function() {
12559        this._untrackInstance();
12560        this._trackingInstances().unshift( this );
12561    },
12562
12563    _untrackInstance: function() {
12564        var instances = this._trackingInstances(),
12565            exists = $.inArray( this, instances );
12566        if ( exists !== -1 ) {
12567            instances.splice( exists, 1 );
12568        }
12569    },
12570
12571    _trackingInstances: function() {
12572        var instances = this.document.data( "ui-dialog-instances" );
12573        if ( !instances ) {
12574            instances = [];
12575            this.document.data( "ui-dialog-instances", instances );
12576        }
12577        return instances;
12578    },
12579
12580    _minHeight: function() {
12581        var options = this.options;
12582
12583        return options.height === "auto" ?
12584            options.minHeight :
12585            Math.min( options.minHeight, options.height );
12586    },
12587
12588    _position: function() {
12589
12590        // Need to show the dialog to get the actual offset in the position plugin
12591        var isVisible = this.uiDialog.is( ":visible" );
12592        if ( !isVisible ) {
12593            this.uiDialog.show();
12594        }
12595        this.uiDialog.position( this.options.position );
12596        if ( !isVisible ) {
12597            this.uiDialog.hide();
12598        }
12599    },
12600
12601    _setOptions: function( options ) {
12602        var that = this,
12603            resize = false,
12604            resizableOptions = {};
12605
12606        $.each( options, function( key, value ) {
12607            that._setOption( key, value );
12608
12609            if ( key in that.sizeRelatedOptions ) {
12610                resize = true;
12611            }
12612            if ( key in that.resizableRelatedOptions ) {
12613                resizableOptions[ key ] = value;
12614            }
12615        } );
12616
12617        if ( resize ) {
12618            this._size();
12619            this._position();
12620        }
12621        if ( this.uiDialog.is( ":data(ui-resizable)" ) ) {
12622            this.uiDialog.resizable( "option", resizableOptions );
12623        }
12624    },
12625
12626    _setOption: function( key, value ) {
12627        var isDraggable, isResizable,
12628            uiDialog = this.uiDialog;
12629
12630        if ( key === "disabled" ) {
12631            return;
12632        }
12633
12634        this._super( key, value );
12635
12636        if ( key === "appendTo" ) {
12637            this.uiDialog.appendTo( this._appendTo() );
12638        }
12639
12640        if ( key === "buttons" ) {
12641            this._createButtons();
12642        }
12643
12644        if ( key === "closeText" ) {
12645            this.uiDialogTitlebarClose.button( {
12646
12647                // Ensure that we always pass a string
12648                label: $( "<a>" ).text( "" + this.options.closeText ).html()
12649            } );
12650        }
12651
12652        if ( key === "draggable" ) {
12653            isDraggable = uiDialog.is( ":data(ui-draggable)" );
12654            if ( isDraggable && !value ) {
12655                uiDialog.draggable( "destroy" );
12656            }
12657
12658            if ( !isDraggable && value ) {
12659                this._makeDraggable();
12660            }
12661        }
12662
12663        if ( key === "position" ) {
12664            this._position();
12665        }
12666
12667        if ( key === "resizable" ) {
12668
12669            // currently resizable, becoming non-resizable
12670            isResizable = uiDialog.is( ":data(ui-resizable)" );
12671            if ( isResizable && !value ) {
12672                uiDialog.resizable( "destroy" );
12673            }
12674
12675            // Currently resizable, changing handles
12676            if ( isResizable && typeof value === "string" ) {
12677                uiDialog.resizable( "option", "handles", value );
12678            }
12679
12680            // Currently non-resizable, becoming resizable
12681            if ( !isResizable && value !== false ) {
12682                this._makeResizable();
12683            }
12684        }
12685
12686        if ( key === "title" ) {
12687            this._title( this.uiDialogTitlebar.find( ".ui-dialog-title" ) );
12688        }
12689    },
12690
12691    _size: function() {
12692
12693        // If the user has resized the dialog, the .ui-dialog and .ui-dialog-content
12694        // divs will both have width and height set, so we need to reset them
12695        var nonContentHeight, minContentHeight, maxContentHeight,
12696            options = this.options;
12697
12698        // Reset content sizing
12699        this.element.show().css( {
12700            width: "auto",
12701            minHeight: 0,
12702            maxHeight: "none",
12703            height: 0
12704        } );
12705
12706        if ( options.minWidth > options.width ) {
12707            options.width = options.minWidth;
12708        }
12709
12710        // Reset wrapper sizing
12711        // determine the height of all the non-content elements
12712        nonContentHeight = this.uiDialog.css( {
12713            height: "auto",
12714            width: options.width
12715        } )
12716            .outerHeight();
12717        minContentHeight = Math.max( 0, options.minHeight - nonContentHeight );
12718        maxContentHeight = typeof options.maxHeight === "number" ?
12719            Math.max( 0, options.maxHeight - nonContentHeight ) :
12720            "none";
12721
12722        if ( options.height === "auto" ) {
12723            this.element.css( {
12724                minHeight: minContentHeight,
12725                maxHeight: maxContentHeight,
12726                height: "auto"
12727            } );
12728        } else {
12729            this.element.height( Math.max( 0, options.height - nonContentHeight ) );
12730        }
12731
12732        if ( this.uiDialog.is( ":data(ui-resizable)" ) ) {
12733            this.uiDialog.resizable( "option", "minHeight", this._minHeight() );
12734        }
12735    },
12736
12737    _blockFrames: function() {
12738        this.iframeBlocks = this.document.find( "iframe" ).map( function() {
12739            var iframe = $( this );
12740
12741            return $( "<div>" )
12742                .css( {
12743                    position: "absolute",
12744                    width: iframe.outerWidth(),
12745                    height: iframe.outerHeight()
12746                } )
12747                .appendTo( iframe.parent() )
12748                .offset( iframe.offset() )[ 0 ];
12749        } );
12750    },
12751
12752    _unblockFrames: function() {
12753        if ( this.iframeBlocks ) {
12754            this.iframeBlocks.remove();
12755            delete this.iframeBlocks;
12756        }
12757    },
12758
12759    _allowInteraction: function( event ) {
12760        if ( $( event.target ).closest( ".ui-dialog" ).length ) {
12761            return true;
12762        }
12763
12764        // TODO: Remove hack when datepicker implements
12765        // the .ui-front logic (#8989)
12766        return !!$( event.target ).closest( ".ui-datepicker" ).length;
12767    },
12768
12769    _createOverlay: function() {
12770        if ( !this.options.modal ) {
12771            return;
12772        }
12773
12774        // We use a delay in case the overlay is created from an
12775        // event that we're going to be cancelling (#2804)
12776        var isOpening = true;
12777        this._delay( function() {
12778            isOpening = false;
12779        } );
12780
12781        if ( !this.document.data( "ui-dialog-overlays" ) ) {
12782
12783            // Prevent use of anchors and inputs
12784            // Using _on() for an event handler shared across many instances is
12785            // safe because the dialogs stack and must be closed in reverse order
12786            this._on( this.document, {
12787                focusin: function( event ) {
12788                    if ( isOpening ) {
12789                        return;
12790                    }
12791
12792                    if ( !this._allowInteraction( event ) ) {
12793                        event.preventDefault();
12794                        this._trackingInstances()[ 0 ]._focusTabbable();
12795                    }
12796                }
12797            } );
12798        }
12799
12800        this.overlay = $( "<div>" )
12801            .appendTo( this._appendTo() );
12802
12803        this._addClass( this.overlay, null, "ui-widget-overlay ui-front" );
12804        this._on( this.overlay, {
12805            mousedown: "_keepFocus"
12806        } );
12807        this.document.data( "ui-dialog-overlays",
12808            ( this.document.data( "ui-dialog-overlays" ) || 0 ) + 1 );
12809    },
12810
12811    _destroyOverlay: function() {
12812        if ( !this.options.modal ) {
12813            return;
12814        }
12815
12816        if ( this.overlay ) {
12817            var overlays = this.document.data( "ui-dialog-overlays" ) - 1;
12818
12819            if ( !overlays ) {
12820                this._off( this.document, "focusin" );
12821                this.document.removeData( "ui-dialog-overlays" );
12822            } else {
12823                this.document.data( "ui-dialog-overlays", overlays );
12824            }
12825
12826            this.overlay.remove();
12827            this.overlay = null;
12828        }
12829    }
12830} );
12831
12832// DEPRECATED
12833// TODO: switch return back to widget declaration at top of file when this is removed
12834if ( $.uiBackCompat !== false ) {
12835
12836    // Backcompat for dialogClass option
12837    $.widget( "ui.dialog", $.ui.dialog, {
12838        options: {
12839            dialogClass: ""
12840        },
12841        _createWrapper: function() {
12842            this._super();
12843            this.uiDialog.addClass( this.options.dialogClass );
12844        },
12845        _setOption: function( key, value ) {
12846            if ( key === "dialogClass" ) {
12847                this.uiDialog
12848                    .removeClass( this.options.dialogClass )
12849                    .addClass( value );
12850            }
12851            this._superApply( arguments );
12852        }
12853    } );
12854}
12855
12856var widgetsDialog = $.ui.dialog;
12857
12858
12859/*!
12860 * jQuery UI Droppable 1.12.1
12861 * http://jqueryui.com
12862 *
12863 * Copyright jQuery Foundation and other contributors
12864 * Released under the MIT license.
12865 * http://jquery.org/license
12866 */
12867
12868//>>label: Droppable
12869//>>group: Interactions
12870//>>description: Enables drop targets for draggable elements.
12871//>>docs: http://api.jqueryui.com/droppable/
12872//>>demos: http://jqueryui.com/droppable/
12873
12874
12875
12876$.widget( "ui.droppable", {
12877    version: "1.12.1",
12878    widgetEventPrefix: "drop",
12879    options: {
12880        accept: "*",
12881        addClasses: true,
12882        greedy: false,
12883        scope: "default",
12884        tolerance: "intersect",
12885
12886        // Callbacks
12887        activate: null,
12888        deactivate: null,
12889        drop: null,
12890        out: null,
12891        over: null
12892    },
12893    _create: function() {
12894
12895        var proportions,
12896            o = this.options,
12897            accept = o.accept;
12898
12899        this.isover = false;
12900        this.isout = true;
12901
12902        this.accept = $.isFunction( accept ) ? accept : function( d ) {
12903            return d.is( accept );
12904        };
12905
12906        this.proportions = function( /* valueToWrite */ ) {
12907            if ( arguments.length ) {
12908
12909                // Store the droppable's proportions
12910                proportions = arguments[ 0 ];
12911            } else {
12912
12913                // Retrieve or derive the droppable's proportions
12914                return proportions ?
12915                    proportions :
12916                    proportions = {
12917                        width: this.element[ 0 ].offsetWidth,
12918                        height: this.element[ 0 ].offsetHeight
12919                    };
12920            }
12921        };
12922
12923        this._addToManager( o.scope );
12924
12925        o.addClasses && this._addClass( "ui-droppable" );
12926
12927    },
12928
12929    _addToManager: function( scope ) {
12930
12931        // Add the reference and positions to the manager
12932        $.ui.ddmanager.droppables[ scope ] = $.ui.ddmanager.droppables[ scope ] || [];
12933        $.ui.ddmanager.droppables[ scope ].push( this );
12934    },
12935
12936    _splice: function( drop ) {
12937        var i = 0;
12938        for ( ; i < drop.length; i++ ) {
12939            if ( drop[ i ] === this ) {
12940                drop.splice( i, 1 );
12941            }
12942        }
12943    },
12944
12945    _destroy: function() {
12946        var drop = $.ui.ddmanager.droppables[ this.options.scope ];
12947
12948        this._splice( drop );
12949    },
12950
12951    _setOption: function( key, value ) {
12952
12953        if ( key === "accept" ) {
12954            this.accept = $.isFunction( value ) ? value : function( d ) {
12955                return d.is( value );
12956            };
12957        } else if ( key === "scope" ) {
12958            var drop = $.ui.ddmanager.droppables[ this.options.scope ];
12959
12960            this._splice( drop );
12961            this._addToManager( value );
12962        }
12963
12964        this._super( key, value );
12965    },
12966
12967    _activate: function( event ) {
12968        var draggable = $.ui.ddmanager.current;
12969
12970        this._addActiveClass();
12971        if ( draggable ) {
12972            this._trigger( "activate", event, this.ui( draggable ) );
12973        }
12974    },
12975
12976    _deactivate: function( event ) {
12977        var draggable = $.ui.ddmanager.current;
12978
12979        this._removeActiveClass();
12980        if ( draggable ) {
12981            this._trigger( "deactivate", event, this.ui( draggable ) );
12982        }
12983    },
12984
12985    _over: function( event ) {
12986
12987        var draggable = $.ui.ddmanager.current;
12988
12989        // Bail if draggable and droppable are same element
12990        if ( !draggable || ( draggable.currentItem ||
12991                draggable.element )[ 0 ] === this.element[ 0 ] ) {
12992            return;
12993        }
12994
12995        if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem ||
12996                draggable.element ) ) ) {
12997            this._addHoverClass();
12998            this._trigger( "over", event, this.ui( draggable ) );
12999        }
13000
13001    },
13002
13003    _out: function( event ) {
13004
13005        var draggable = $.ui.ddmanager.current;
13006
13007        // Bail if draggable and droppable are same element
13008        if ( !draggable || ( draggable.currentItem ||
13009                draggable.element )[ 0 ] === this.element[ 0 ] ) {
13010            return;
13011        }
13012
13013        if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem ||
13014                draggable.element ) ) ) {
13015            this._removeHoverClass();
13016            this._trigger( "out", event, this.ui( draggable ) );
13017        }
13018
13019    },
13020
13021    _drop: function( event, custom ) {
13022
13023        var draggable = custom || $.ui.ddmanager.current,
13024            childrenIntersection = false;
13025
13026        // Bail if draggable and droppable are same element
13027        if ( !draggable || ( draggable.currentItem ||
13028                draggable.element )[ 0 ] === this.element[ 0 ] ) {
13029            return false;
13030        }
13031
13032        this.element
13033            .find( ":data(ui-droppable)" )
13034            .not( ".ui-draggable-dragging" )
13035            .each( function() {
13036                var inst = $( this ).droppable( "instance" );
13037                if (
13038                    inst.options.greedy &&
13039                    !inst.options.disabled &&
13040                    inst.options.scope === draggable.options.scope &&
13041                    inst.accept.call(
13042                        inst.element[ 0 ], ( draggable.currentItem || draggable.element )
13043                    ) &&
13044                    intersect(
13045                        draggable,
13046                        $.extend( inst, { offset: inst.element.offset() } ),
13047                        inst.options.tolerance, event
13048                    )
13049                ) {
13050                    childrenIntersection = true;
13051                    return false; }
13052            } );
13053        if ( childrenIntersection ) {
13054            return false;
13055        }
13056
13057        if ( this.accept.call( this.element[ 0 ],
13058                ( draggable.currentItem || draggable.element ) ) ) {
13059            this._removeActiveClass();
13060            this._removeHoverClass();
13061
13062            this._trigger( "drop", event, this.ui( draggable ) );
13063            return this.element;
13064        }
13065
13066        return false;
13067
13068    },
13069
13070    ui: function( c ) {
13071        return {
13072            draggable: ( c.currentItem || c.element ),
13073            helper: c.helper,
13074            position: c.position,
13075            offset: c.positionAbs
13076        };
13077    },
13078
13079    // Extension points just to make backcompat sane and avoid duplicating logic
13080    // TODO: Remove in 1.13 along with call to it below
13081    _addHoverClass: function() {
13082        this._addClass( "ui-droppable-hover" );
13083    },
13084
13085    _removeHoverClass: function() {
13086        this._removeClass( "ui-droppable-hover" );
13087    },
13088
13089    _addActiveClass: function() {
13090        this._addClass( "ui-droppable-active" );
13091    },
13092
13093    _removeActiveClass: function() {
13094        this._removeClass( "ui-droppable-active" );
13095    }
13096} );
13097
13098var intersect = $.ui.intersect = ( function() {
13099    function isOverAxis( x, reference, size ) {
13100        return ( x >= reference ) && ( x < ( reference + size ) );
13101    }
13102
13103    return function( draggable, droppable, toleranceMode, event ) {
13104
13105        if ( !droppable.offset ) {
13106            return false;
13107        }
13108
13109        var x1 = ( draggable.positionAbs ||
13110                draggable.position.absolute ).left + draggable.margins.left,
13111            y1 = ( draggable.positionAbs ||
13112                draggable.position.absolute ).top + draggable.margins.top,
13113            x2 = x1 + draggable.helperProportions.width,
13114            y2 = y1 + draggable.helperProportions.height,
13115            l = droppable.offset.left,
13116            t = droppable.offset.top,
13117            r = l + droppable.proportions().width,
13118            b = t + droppable.proportions().height;
13119
13120        switch ( toleranceMode ) {
13121        case "fit":
13122            return ( l <= x1 && x2 <= r && t <= y1 && y2 <= b );
13123        case "intersect":
13124            return ( l < x1 + ( draggable.helperProportions.width / 2 ) && // Right Half
13125                x2 - ( draggable.helperProportions.width / 2 ) < r && // Left Half
13126                t < y1 + ( draggable.helperProportions.height / 2 ) && // Bottom Half
13127                y2 - ( draggable.helperProportions.height / 2 ) < b ); // Top Half
13128        case "pointer":
13129            return isOverAxis( event.pageY, t, droppable.proportions().height ) &&
13130                isOverAxis( event.pageX, l, droppable.proportions().width );
13131        case "touch":
13132            return (
13133                ( y1 >= t && y1 <= b ) || // Top edge touching
13134                ( y2 >= t && y2 <= b ) || // Bottom edge touching
13135                ( y1 < t && y2 > b ) // Surrounded vertically
13136            ) && (
13137                ( x1 >= l && x1 <= r ) || // Left edge touching
13138                ( x2 >= l && x2 <= r ) || // Right edge touching
13139                ( x1 < l && x2 > r ) // Surrounded horizontally
13140            );
13141        default:
13142            return false;
13143        }
13144    };
13145} )();
13146
13147/*
13148    This manager tracks offsets of draggables and droppables
13149*/
13150$.ui.ddmanager = {
13151    current: null,
13152    droppables: { "default": [] },
13153    prepareOffsets: function( t, event ) {
13154
13155        var i, j,
13156            m = $.ui.ddmanager.droppables[ t.options.scope ] || [],
13157            type = event ? event.type : null, // workaround for #2317
13158            list = ( t.currentItem || t.element ).find( ":data(ui-droppable)" ).addBack();
13159
13160        droppablesLoop: for ( i = 0; i < m.length; i++ ) {
13161
13162            // No disabled and non-accepted
13163            if ( m[ i ].options.disabled || ( t && !m[ i ].accept.call( m[ i ].element[ 0 ],
13164                    ( t.currentItem || t.element ) ) ) ) {
13165                continue;
13166            }
13167
13168            // Filter out elements in the current dragged item
13169            for ( j = 0; j < list.length; j++ ) {
13170                if ( list[ j ] === m[ i ].element[ 0 ] ) {
13171                    m[ i ].proportions().height = 0;
13172                    continue droppablesLoop;
13173                }
13174            }
13175
13176            m[ i ].visible = m[ i ].element.css( "display" ) !== "none";
13177            if ( !m[ i ].visible ) {
13178                continue;
13179            }
13180
13181            // Activate the droppable if used directly from draggables
13182            if ( type === "mousedown" ) {
13183                m[ i ]._activate.call( m[ i ], event );
13184            }
13185
13186            m[ i ].offset = m[ i ].element.offset();
13187            m[ i ].proportions( {
13188                width: m[ i ].element[ 0 ].offsetWidth,
13189                height: m[ i ].element[ 0 ].offsetHeight
13190            } );
13191
13192        }
13193
13194    },
13195    drop: function( draggable, event ) {
13196
13197        var dropped = false;
13198
13199        // Create a copy of the droppables in case the list changes during the drop (#9116)
13200        $.each( ( $.ui.ddmanager.droppables[ draggable.options.scope ] || [] ).slice(), function() {
13201
13202            if ( !this.options ) {
13203                return;
13204            }
13205            if ( !this.options.disabled && this.visible &&
13206                    intersect( draggable, this, this.options.tolerance, event ) ) {
13207                dropped = this._drop.call( this, event ) || dropped;
13208            }
13209
13210            if ( !this.options.disabled && this.visible && this.accept.call( this.element[ 0 ],
13211                    ( draggable.currentItem || draggable.element ) ) ) {
13212                this.isout = true;
13213                this.isover = false;
13214                this._deactivate.call( this, event );
13215            }
13216
13217        } );
13218        return dropped;
13219
13220    },
13221    dragStart: function( draggable, event ) {
13222
13223        // Listen for scrolling so that if the dragging causes scrolling the position of the
13224        // droppables can be recalculated (see #5003)
13225        draggable.element.parentsUntil( "body" ).on( "scroll.droppable", function() {
13226            if ( !draggable.options.refreshPositions ) {
13227                $.ui.ddmanager.prepareOffsets( draggable, event );
13228            }
13229        } );
13230    },
13231    drag: function( draggable, event ) {
13232
13233        // If you have a highly dynamic page, you might try this option. It renders positions
13234        // every time you move the mouse.
13235        if ( draggable.options.refreshPositions ) {
13236            $.ui.ddmanager.prepareOffsets( draggable, event );
13237        }
13238
13239        // Run through all droppables and check their positions based on specific tolerance options
13240        $.each( $.ui.ddmanager.droppables[ draggable.options.scope ] || [], function() {
13241
13242            if ( this.options.disabled || this.greedyChild || !this.visible ) {
13243                return;
13244            }
13245
13246            var parentInstance, scope, parent,
13247                intersects = intersect( draggable, this, this.options.tolerance, event ),
13248                c = !intersects && this.isover ?
13249                    "isout" :
13250                    ( intersects && !this.isover ? "isover" : null );
13251            if ( !c ) {
13252                return;
13253            }
13254
13255            if ( this.options.greedy ) {
13256
13257                // find droppable parents with same scope
13258                scope = this.options.scope;
13259                parent = this.element.parents( ":data(ui-droppable)" ).filter( function() {
13260                    return $( this ).droppable( "instance" ).options.scope === scope;
13261                } );
13262
13263                if ( parent.length ) {
13264                    parentInstance = $( parent[ 0 ] ).droppable( "instance" );
vendor: 4,707 bytes, lines 13265-13420
13265                    parentInstance.greedyChild = ( c === "isover" );
13266                }
13267            }
13268
13269            // We just moved into a greedy child
13270            if ( parentInstance && c === "isover" ) {
13271                parentInstance.isover = false;
13272                parentInstance.isout = true;
13273                parentInstance._out.call( parentInstance, event );
13274            }
13275
13276            this[ c ] = true;
13277            this[ c === "isout" ? "isover" : "isout" ] = false;
13278            this[ c === "isover" ? "_over" : "_out" ].call( this, event );
13279
13280            // We just moved out of a greedy child
13281            if ( parentInstance && c === "isout" ) {
13282                parentInstance.isout = false;
13283                parentInstance.isover = true;
13284                parentInstance._over.call( parentInstance, event );
13285            }
13286        } );
13287
13288    },
13289    dragStop: function( draggable, event ) {
13290        draggable.element.parentsUntil( "body" ).off( "scroll.droppable" );
13291
13292        // Call prepareOffsets one final time since IE does not fire return scroll events when
13293        // overflow was caused by drag (see #5003)
13294        if ( !draggable.options.refreshPositions ) {
13295            $.ui.ddmanager.prepareOffsets( draggable, event );
13296        }
13297    }
13298};
13299
13300// DEPRECATED
13301// TODO: switch return back to widget declaration at top of file when this is removed
13302if ( $.uiBackCompat !== false ) {
13303
13304    // Backcompat for activeClass and hoverClass options
13305    $.widget( "ui.droppable", $.ui.droppable, {
13306        options: {
13307            hoverClass: false,
13308            activeClass: false
13309        },
13310        _addActiveClass: function() {
13311            this._super();
13312            if ( this.options.activeClass ) {
13313                this.element.addClass( this.options.activeClass );
13314            }
13315        },
13316        _removeActiveClass: function() {
13317            this._super();
13318            if ( this.options.activeClass ) {
13319                this.element.removeClass( this.options.activeClass );
13320            }
13321        },
13322        _addHoverClass: function() {
13323            this._super();
13324            if ( this.options.hoverClass ) {
13325                this.element.addClass( this.options.hoverClass );
13326            }
13327        },
13328        _removeHoverClass: function() {
13329            this._super();
13330            if ( this.options.hoverClass ) {
13331                this.element.removeClass( this.options.hoverClass );
13332            }
13333        }
13334    } );
13335}
13336
13337var widgetsDroppable = $.ui.droppable;
13338
13339
13340/*!
13341 * jQuery UI Progressbar 1.12.1
13342 * http://jqueryui.com
13343 *
13344 * Copyright jQuery Foundation and other contributors
13345 * Released under the MIT license.
13346 * http://jquery.org/license
13347 */
13348
13349//>>label: Progressbar
13350//>>group: Widgets
13351// jscs:disable maximumLineLength
13352//>>description: Displays a status indicator for loading state, standard percentage, and other progress indicators.
13353// jscs:enable maximumLineLength
13354//>>docs: http://api.jqueryui.com/progressbar/
13355//>>demos: http://jqueryui.com/progressbar/
13356//>>css.structure: ../../themes/base/core.css
13357//>>css.structure: ../../themes/base/progressbar.css
13358//>>css.theme: ../../themes/base/theme.css
13359
13360
13361
13362var widgetsProgressbar = $.widget( "ui.progressbar", {
13363    version: "1.12.1",
13364    options: {
13365        classes: {
13366            "ui-progressbar": "ui-corner-all",
13367            "ui-progressbar-value": "ui-corner-left",
13368            "ui-progressbar-complete": "ui-corner-right"
13369        },
13370        max: 100,
13371        value: 0,
13372
13373        change: null,
13374        complete: null
13375    },
13376
13377    min: 0,
13378
13379    _create: function() {
13380
13381        // Constrain initial value
13382        this.oldValue = this.options.value = this._constrainedValue();
13383
13384        this.element.attr( {
13385
13386            // Only set static values; aria-valuenow and aria-valuemax are
13387            // set inside _refreshValue()
13388            role: "progressbar",
13389            "aria-valuemin": this.min
13390        } );
13391        this._addClass( "ui-progressbar", "ui-widget ui-widget-content" );
13392
13393        this.valueDiv = $( "<div>" ).appendTo( this.element );
13394        this._addClass( this.valueDiv, "ui-progressbar-value", "ui-widget-header" );
13395        this._refreshValue();
13396    },
13397
13398    _destroy: function() {
13399        this.element.removeAttr( "role aria-valuemin aria-valuemax aria-valuenow" );
13400
13401        this.valueDiv.remove();
13402    },
13403
13404    value: function( newValue ) {
13405        if ( newValue === undefined ) {
13406            return this.options.value;
13407        }
13408
13409        this.options.value = this._constrainedValue( newValue );
13410        this._refreshValue();
13411    },
13412
13413    _constrainedValue: function( newValue ) {
13414        if ( newValue === undefined ) {
13415            newValue = this.options.value;
13416        }
13417
13418        this.indeterminate = newValue === false;
13419
13420        // Sanitize value
vendor: 14,427 bytes, lines 13421-13861
13421        if ( typeof newValue !== "number" ) {
13422            newValue = 0;
13423        }
13424
13425        return this.indeterminate ? false :
13426            Math.min( this.options.max, Math.max( this.min, newValue ) );
13427    },
13428
13429    _setOptions: function( options ) {
13430
13431        // Ensure "value" option is set after other values (like max)
13432        var value = options.value;
13433        delete options.value;
13434
13435        this._super( options );
13436
13437        this.options.value = this._constrainedValue( value );
13438        this._refreshValue();
13439    },
13440
13441    _setOption: function( key, value ) {
13442        if ( key === "max" ) {
13443
13444            // Don't allow a max less than min
13445            value = Math.max( this.min, value );
13446        }
13447        this._super( key, value );
13448    },
13449
13450    _setOptionDisabled: function( value ) {
13451        this._super( value );
13452
13453        this.element.attr( "aria-disabled", value );
13454        this._toggleClass( null, "ui-state-disabled", !!value );
13455    },
13456
13457    _percentage: function() {
13458        return this.indeterminate ?
13459            100 :
13460            100 * ( this.options.value - this.min ) / ( this.options.max - this.min );
13461    },
13462
13463    _refreshValue: function() {
13464        var value = this.options.value,
13465            percentage = this._percentage();
13466
13467        this.valueDiv
13468            .toggle( this.indeterminate || value > this.min )
13469            .width( percentage.toFixed( 0 ) + "%" );
13470
13471        this
13472            ._toggleClass( this.valueDiv, "ui-progressbar-complete", null,
13473                value === this.options.max )
13474            ._toggleClass( "ui-progressbar-indeterminate", null, this.indeterminate );
13475
13476        if ( this.indeterminate ) {
13477            this.element.removeAttr( "aria-valuenow" );
13478            if ( !this.overlayDiv ) {
13479                this.overlayDiv = $( "<div>" ).appendTo( this.valueDiv );
13480                this._addClass( this.overlayDiv, "ui-progressbar-overlay" );
13481            }
13482        } else {
13483            this.element.attr( {
13484                "aria-valuemax": this.options.max,
13485                "aria-valuenow": value
13486            } );
13487            if ( this.overlayDiv ) {
13488                this.overlayDiv.remove();
13489                this.overlayDiv = null;
13490            }
13491        }
13492
13493        if ( this.oldValue !== value ) {
13494            this.oldValue = value;
13495            this._trigger( "change" );
13496        }
13497        if ( value === this.options.max ) {
13498            this._trigger( "complete" );
13499        }
13500    }
13501} );
13502
13503
13504/*!
13505 * jQuery UI Selectable 1.12.1
13506 * http://jqueryui.com
13507 *
13508 * Copyright jQuery Foundation and other contributors
13509 * Released under the MIT license.
13510 * http://jquery.org/license
13511 */
13512
13513//>>label: Selectable
13514//>>group: Interactions
13515//>>description: Allows groups of elements to be selected with the mouse.
13516//>>docs: http://api.jqueryui.com/selectable/
13517//>>demos: http://jqueryui.com/selectable/
13518//>>css.structure: ../../themes/base/selectable.css
13519
13520
13521
13522var widgetsSelectable = $.widget( "ui.selectable", $.ui.mouse, {
13523    version: "1.12.1",
13524    options: {
13525        appendTo: "body",
13526        autoRefresh: true,
13527        distance: 0,
13528        filter: "*",
13529        tolerance: "touch",
13530
13531        // Callbacks
13532        selected: null,
13533        selecting: null,
13534        start: null,
13535        stop: null,
13536        unselected: null,
13537        unselecting: null
13538    },
13539    _create: function() {
13540        var that = this;
13541
13542        this._addClass( "ui-selectable" );
13543
13544        this.dragged = false;
13545
13546        // Cache selectee children based on filter
13547        this.refresh = function() {
13548            that.elementPos = $( that.element[ 0 ] ).offset();
13549            that.selectees = $( that.options.filter, that.element[ 0 ] );
13550            that._addClass( that.selectees, "ui-selectee" );
13551            that.selectees.each( function() {
13552                var $this = $( this ),
13553                    selecteeOffset = $this.offset(),
13554                    pos = {
13555                        left: selecteeOffset.left - that.elementPos.left,
13556                        top: selecteeOffset.top - that.elementPos.top
13557                    };
13558                $.data( this, "selectable-item", {
13559                    element: this,
13560                    $element: $this,
13561                    left: pos.left,
13562                    top: pos.top,
13563                    right: pos.left + $this.outerWidth(),
13564                    bottom: pos.top + $this.outerHeight(),
13565                    startselected: false,
13566                    selected: $this.hasClass( "ui-selected" ),
13567                    selecting: $this.hasClass( "ui-selecting" ),
13568                    unselecting: $this.hasClass( "ui-unselecting" )
13569                } );
13570            } );
13571        };
13572        this.refresh();
13573
13574        this._mouseInit();
13575
13576        this.helper = $( "<div>" );
13577        this._addClass( this.helper, "ui-selectable-helper" );
13578    },
13579
13580    _destroy: function() {
13581        this.selectees.removeData( "selectable-item" );
13582        this._mouseDestroy();
13583    },
13584
13585    _mouseStart: function( event ) {
13586        var that = this,
13587            options = this.options;
13588
13589        this.opos = [ event.pageX, event.pageY ];
13590        this.elementPos = $( this.element[ 0 ] ).offset();
13591
13592        if ( this.options.disabled ) {
13593            return;
13594        }
13595
13596        this.selectees = $( options.filter, this.element[ 0 ] );
13597
13598        this._trigger( "start", event );
13599
13600        $( options.appendTo ).append( this.helper );
13601
13602        // position helper (lasso)
13603        this.helper.css( {
13604            "left": event.pageX,
13605            "top": event.pageY,
13606            "width": 0,
13607            "height": 0
13608        } );
13609
13610        if ( options.autoRefresh ) {
13611            this.refresh();
13612        }
13613
13614        this.selectees.filter( ".ui-selected" ).each( function() {
13615            var selectee = $.data( this, "selectable-item" );
13616            selectee.startselected = true;
13617            if ( !event.metaKey && !event.ctrlKey ) {
13618                that._removeClass( selectee.$element, "ui-selected" );
13619                selectee.selected = false;
13620                that._addClass( selectee.$element, "ui-unselecting" );
13621                selectee.unselecting = true;
13622
13623                // selectable UNSELECTING callback
13624                that._trigger( "unselecting", event, {
13625                    unselecting: selectee.element
13626                } );
13627            }
13628        } );
13629
13630        $( event.target ).parents().addBack().each( function() {
13631            var doSelect,
13632                selectee = $.data( this, "selectable-item" );
13633            if ( selectee ) {
13634                doSelect = ( !event.metaKey && !event.ctrlKey ) ||
13635                    !selectee.$element.hasClass( "ui-selected" );
13636                that._removeClass( selectee.$element, doSelect ? "ui-unselecting" : "ui-selected" )
13637                    ._addClass( selectee.$element, doSelect ? "ui-selecting" : "ui-unselecting" );
13638                selectee.unselecting = !doSelect;
13639                selectee.selecting = doSelect;
13640                selectee.selected = doSelect;
13641
13642                // selectable (UN)SELECTING callback
13643                if ( doSelect ) {
13644                    that._trigger( "selecting", event, {
13645                        selecting: selectee.element
13646                    } );
13647                } else {
13648                    that._trigger( "unselecting", event, {
13649                        unselecting: selectee.element
13650                    } );
13651                }
13652                return false;
13653            }
13654        } );
13655
13656    },
13657
13658    _mouseDrag: function( event ) {
13659
13660        this.dragged = true;
13661
13662        if ( this.options.disabled ) {
13663            return;
13664        }
13665
13666        var tmp,
13667            that = this,
13668            options = this.options,
13669            x1 = this.opos[ 0 ],
13670            y1 = this.opos[ 1 ],
13671            x2 = event.pageX,
13672            y2 = event.pageY;
13673
13674        if ( x1 > x2 ) { tmp = x2; x2 = x1; x1 = tmp; }
13675        if ( y1 > y2 ) { tmp = y2; y2 = y1; y1 = tmp; }
13676        this.helper.css( { left: x1, top: y1, width: x2 - x1, height: y2 - y1 } );
13677
13678        this.selectees.each( function() {
13679            var selectee = $.data( this, "selectable-item" ),
13680                hit = false,
13681                offset = {};
13682
13683            //prevent helper from being selected if appendTo: selectable
13684            if ( !selectee || selectee.element === that.element[ 0 ] ) {
13685                return;
13686            }
13687
13688            offset.left   = selectee.left   + that.elementPos.left;
13689            offset.right  = selectee.right  + that.elementPos.left;
13690            offset.top    = selectee.top    + that.elementPos.top;
13691            offset.bottom = selectee.bottom + that.elementPos.top;
13692
13693            if ( options.tolerance === "touch" ) {
13694                hit = ( !( offset.left > x2 || offset.right < x1 || offset.top > y2 ||
13695                    offset.bottom < y1 ) );
13696            } else if ( options.tolerance === "fit" ) {
13697                hit = ( offset.left > x1 && offset.right < x2 && offset.top > y1 &&
13698                    offset.bottom < y2 );
13699            }
13700
13701            if ( hit ) {
13702
13703                // SELECT
13704                if ( selectee.selected ) {
13705                    that._removeClass( selectee.$element, "ui-selected" );
13706                    selectee.selected = false;
13707                }
13708                if ( selectee.unselecting ) {
13709                    that._removeClass( selectee.$element, "ui-unselecting" );
13710                    selectee.unselecting = false;
13711                }
13712                if ( !selectee.selecting ) {
13713                    that._addClass( selectee.$element, "ui-selecting" );
13714                    selectee.selecting = true;
13715
13716                    // selectable SELECTING callback
13717                    that._trigger( "selecting", event, {
13718                        selecting: selectee.element
13719                    } );
13720                }
13721            } else {
13722
13723                // UNSELECT
13724                if ( selectee.selecting ) {
13725                    if ( ( event.metaKey || event.ctrlKey ) && selectee.startselected ) {
13726                        that._removeClass( selectee.$element, "ui-selecting" );
13727                        selectee.selecting = false;
13728                        that._addClass( selectee.$element, "ui-selected" );
13729                        selectee.selected = true;
13730                    } else {
13731                        that._removeClass( selectee.$element, "ui-selecting" );
13732                        selectee.selecting = false;
13733                        if ( selectee.startselected ) {
13734                            that._addClass( selectee.$element, "ui-unselecting" );
13735                            selectee.unselecting = true;
13736                        }
13737
13738                        // selectable UNSELECTING callback
13739                        that._trigger( "unselecting", event, {
13740                            unselecting: selectee.element
13741                        } );
13742                    }
13743                }
13744                if ( selectee.selected ) {
13745                    if ( !event.metaKey && !event.ctrlKey && !selectee.startselected ) {
13746                        that._removeClass( selectee.$element, "ui-selected" );
13747                        selectee.selected = false;
13748
13749                        that._addClass( selectee.$element, "ui-unselecting" );
13750                        selectee.unselecting = true;
13751
13752                        // selectable UNSELECTING callback
13753                        that._trigger( "unselecting", event, {
13754                            unselecting: selectee.element
13755                        } );
13756                    }
13757                }
13758            }
13759        } );
13760
13761        return false;
13762    },
13763
13764    _mouseStop: function( event ) {
13765        var that = this;
13766
13767        this.dragged = false;
13768
13769        $( ".ui-unselecting", this.element[ 0 ] ).each( function() {
13770            var selectee = $.data( this, "selectable-item" );
13771            that._removeClass( selectee.$element, "ui-unselecting" );
13772            selectee.unselecting = false;
13773            selectee.startselected = false;
13774            that._trigger( "unselected", event, {
13775                unselected: selectee.element
13776            } );
13777        } );
13778        $( ".ui-selecting", this.element[ 0 ] ).each( function() {
13779            var selectee = $.data( this, "selectable-item" );
13780            that._removeClass( selectee.$element, "ui-selecting" )
13781                ._addClass( selectee.$element, "ui-selected" );
13782            selectee.selecting = false;
13783            selectee.selected = true;
13784            selectee.startselected = true;
13785            that._trigger( "selected", event, {
13786                selected: selectee.element
13787            } );
13788        } );
13789        this._trigger( "stop", event );
13790
13791        this.helper.remove();
13792
13793        return false;
13794    }
13795
13796} );
13797
13798
13799/*!
13800 * jQuery UI Selectmenu 1.12.1
13801 * http://jqueryui.com
13802 *
13803 * Copyright jQuery Foundation and other contributors
13804 * Released under the MIT license.
13805 * http://jquery.org/license
13806 */
13807
13808//>>label: Selectmenu
13809//>>group: Widgets
13810// jscs:disable maximumLineLength
13811//>>description: Duplicates and extends the functionality of a native HTML select element, allowing it to be customizable in behavior and appearance far beyond the limitations of a native select.
13812// jscs:enable maximumLineLength
13813//>>docs: http://api.jqueryui.com/selectmenu/
13814//>>demos: http://jqueryui.com/selectmenu/
13815//>>css.structure: ../../themes/base/core.css
13816//>>css.structure: ../../themes/base/selectmenu.css, ../../themes/base/button.css
13817//>>css.theme: ../../themes/base/theme.css
13818
13819
13820
13821var widgetsSelectmenu = $.widget( "ui.selectmenu", [ $.ui.formResetMixin, {
13822    version: "1.12.1",
13823    defaultElement: "<select>",
13824    options: {
13825        appendTo: null,
13826        classes: {
13827            "ui-selectmenu-button-open": "ui-corner-top",
13828            "ui-selectmenu-button-closed": "ui-corner-all"
13829        },
13830        disabled: null,
13831        icons: {
13832            button: "ui-icon-triangle-1-s"
13833        },
13834        position: {
13835            my: "left top",
13836            at: "left bottom",
13837            collision: "none"
13838        },
13839        width: false,
13840
13841        // Callbacks
13842        change: null,
13843        close: null,
13844        focus: null,
13845        open: null,
13846        select: null
13847    },
13848
13849    _create: function() {
13850        var selectmenuId = this.element.uniqueId().attr( "id" );
13851        this.ids = {
13852            element: selectmenuId,
13853            button: selectmenuId + "-button",
13854            menu: selectmenuId + "-menu"
13855        };
13856
13857        this._drawButton();
13858        this._drawMenu();
13859        this._bindFormResetHandler();
13860
13861        this._rendered = false;
vendor: 4,177 bytes, lines 13862-13981
13862        this.menuItems = $();
13863    },
13864
13865    _drawButton: function() {
13866        var icon,
13867            that = this,
13868            item = this._parseOption(
13869                this.element.find( "option:selected" ),
13870                this.element[ 0 ].selectedIndex
13871            );
13872
13873        // Associate existing label with the new button
13874        this.labels = this.element.labels().attr( "for", this.ids.button );
13875        this._on( this.labels, {
13876            click: function( event ) {
13877                this.button.focus();
13878                event.preventDefault();
13879            }
13880        } );
13881
13882        // Hide original select element
13883        this.element.hide();
13884
13885        // Create button
13886        this.button = $( "<span>", {
13887            tabindex: this.options.disabled ? -1 : 0,
13888            id: this.ids.button,
13889            role: "combobox",
13890            "aria-expanded": "false",
13891            "aria-autocomplete": "list",
13892            "aria-owns": this.ids.menu,
13893            "aria-haspopup": "true",
13894            title: this.element.attr( "title" )
13895        } )
13896            .insertAfter( this.element );
13897
13898        this._addClass( this.button, "ui-selectmenu-button ui-selectmenu-button-closed",
13899            "ui-button ui-widget" );
13900
13901        icon = $( "<span>" ).appendTo( this.button );
13902        this._addClass( icon, "ui-selectmenu-icon", "ui-icon " + this.options.icons.button );
13903        this.buttonItem = this._renderButtonItem( item )
13904            .appendTo( this.button );
13905
13906        if ( this.options.width !== false ) {
13907            this._resizeButton();
13908        }
13909
13910        this._on( this.button, this._buttonEvents );
13911        this.button.one( "focusin", function() {
13912
13913            // Delay rendering the menu items until the button receives focus.
13914            // The menu may have already been rendered via a programmatic open.
13915            if ( !that._rendered ) {
13916                that._refreshMenu();
13917            }
13918        } );
13919    },
13920
13921    _drawMenu: function() {
13922        var that = this;
13923
13924        // Create menu
13925        this.menu = $( "<ul>", {
13926            "aria-hidden": "true",
13927            "aria-labelledby": this.ids.button,
13928            id: this.ids.menu
13929        } );
13930
13931        // Wrap menu
13932        this.menuWrap = $( "<div>" ).append( this.menu );
13933        this._addClass( this.menuWrap, "ui-selectmenu-menu", "ui-front" );
13934        this.menuWrap.appendTo( this._appendTo() );
13935
13936        // Initialize menu widget
13937        this.menuInstance = this.menu
13938            .menu( {
13939                classes: {
13940                    "ui-menu": "ui-corner-bottom"
13941                },
13942                role: "listbox",
13943                select: function( event, ui ) {
13944                    event.preventDefault();
13945
13946                    // Support: IE8
13947                    // If the item was selected via a click, the text selection
13948                    // will be destroyed in IE
13949                    that._setSelection();
13950
13951                    that._select( ui.item.data( "ui-selectmenu-item" ), event );
13952                },
13953                focus: function( event, ui ) {
13954                    var item = ui.item.data( "ui-selectmenu-item" );
13955
13956                    // Prevent inital focus from firing and check if its a newly focused item
13957                    if ( that.focusIndex != null && item.index !== that.focusIndex ) {
13958                        that._trigger( "focus", event, { item: item } );
13959                        if ( !that.isOpen ) {
13960                            that._select( item, event );
13961                        }
13962                    }
13963                    that.focusIndex = item.index;
13964
13965                    that.button.attr( "aria-activedescendant",
13966                        that.menuItems.eq( item.index ).attr( "id" ) );
13967                }
13968            } )
13969            .menu( "instance" );
13970
13971        // Don't close the menu on mouseleave
13972        this.menuInstance._off( this.menu, "mouseleave" );
13973
13974        // Cancel the menu's collapseAll on document click
13975        this.menuInstance._closeOnDocumentClick = function() {
13976            return false;
13977        };
13978
13979        // Selects often contain empty items, but never contain dividers
13980        this.menuInstance._isDivider = function() {
13981            return false;
vendor: 7,044 bytes, lines 13982-14240
13982        };
13983    },
13984
13985    refresh: function() {
13986        this._refreshMenu();
13987        this.buttonItem.replaceWith(
13988            this.buttonItem = this._renderButtonItem(
13989
13990                // Fall back to an empty object in case there are no options
13991                this._getSelectedItem().data( "ui-selectmenu-item" ) || {}
13992            )
13993        );
13994        if ( this.options.width === null ) {
13995            this._resizeButton();
13996        }
13997    },
13998
13999    _refreshMenu: function() {
14000        var item,
14001            options = this.element.find( "option" );
14002
14003        this.menu.empty();
14004
14005        this._parseOptions( options );
14006        this._renderMenu( this.menu, this.items );
14007
14008        this.menuInstance.refresh();
14009        this.menuItems = this.menu.find( "li" )
14010            .not( ".ui-selectmenu-optgroup" )
14011                .find( ".ui-menu-item-wrapper" );
14012
14013        this._rendered = true;
14014
14015        if ( !options.length ) {
14016            return;
14017        }
14018
14019        item = this._getSelectedItem();
14020
14021        // Update the menu to have the correct item focused
14022        this.menuInstance.focus( null, item );
14023        this._setAria( item.data( "ui-selectmenu-item" ) );
14024
14025        // Set disabled state
14026        this._setOption( "disabled", this.element.prop( "disabled" ) );
14027    },
14028
14029    open: function( event ) {
14030        if ( this.options.disabled ) {
14031            return;
14032        }
14033
14034        // If this is the first time the menu is being opened, render the items
14035        if ( !this._rendered ) {
14036            this._refreshMenu();
14037        } else {
14038
14039            // Menu clears focus on close, reset focus to selected item
14040            this._removeClass( this.menu.find( ".ui-state-active" ), null, "ui-state-active" );
14041            this.menuInstance.focus( null, this._getSelectedItem() );
14042        }
14043
14044        // If there are no options, don't open the menu
14045        if ( !this.menuItems.length ) {
14046            return;
14047        }
14048
14049        this.isOpen = true;
14050        this._toggleAttr();
14051        this._resizeMenu();
14052        this._position();
14053
14054        this._on( this.document, this._documentClick );
14055
14056        this._trigger( "open", event );
14057    },
14058
14059    _position: function() {
14060        this.menuWrap.position( $.extend( { of: this.button }, this.options.position ) );
14061    },
14062
14063    close: function( event ) {
14064        if ( !this.isOpen ) {
14065            return;
14066        }
14067
14068        this.isOpen = false;
14069        this._toggleAttr();
14070
14071        this.range = null;
14072        this._off( this.document );
14073
14074        this._trigger( "close", event );
14075    },
14076
14077    widget: function() {
14078        return this.button;
14079    },
14080
14081    menuWidget: function() {
14082        return this.menu;
14083    },
14084
14085    _renderButtonItem: function( item ) {
14086        var buttonItem = $( "<span>" );
14087
14088        this._setText( buttonItem, item.label );
14089        this._addClass( buttonItem, "ui-selectmenu-text" );
14090
14091        return buttonItem;
14092    },
14093
14094    _renderMenu: function( ul, items ) {
14095        var that = this,
14096            currentOptgroup = "";
14097
14098        $.each( items, function( index, item ) {
14099            var li;
14100
14101            if ( item.optgroup !== currentOptgroup ) {
14102                li = $( "<li>", {
14103                    text: item.optgroup
14104                } );
14105                that._addClass( li, "ui-selectmenu-optgroup", "ui-menu-divider" +
14106                    ( item.element.parent( "optgroup" ).prop( "disabled" ) ?
14107                        " ui-state-disabled" :
14108                        "" ) );
14109
14110                li.appendTo( ul );
14111
14112                currentOptgroup = item.optgroup;
14113            }
14114
14115            that._renderItemData( ul, item );
14116        } );
14117    },
14118
14119    _renderItemData: function( ul, item ) {
14120        return this._renderItem( ul, item ).data( "ui-selectmenu-item", item );
14121    },
14122
14123    _renderItem: function( ul, item ) {
14124        var li = $( "<li>" ),
14125            wrapper = $( "<div>", {
14126                title: item.element.attr( "title" )
14127            } );
14128
14129        if ( item.disabled ) {
14130            this._addClass( li, null, "ui-state-disabled" );
14131        }
14132        this._setText( wrapper, item.label );
14133
14134        return li.append( wrapper ).appendTo( ul );
14135    },
14136
14137    _setText: function( element, value ) {
14138        if ( value ) {
14139            element.text( value );
14140        } else {
14141            element.html( "&#160;" );
14142        }
14143    },
14144
14145    _move: function( direction, event ) {
14146        var item, next,
14147            filter = ".ui-menu-item";
14148
14149        if ( this.isOpen ) {
14150            item = this.menuItems.eq( this.focusIndex ).parent( "li" );
14151        } else {
14152            item = this.menuItems.eq( this.element[ 0 ].selectedIndex ).parent( "li" );
14153            filter += ":not(.ui-state-disabled)";
14154        }
14155
14156        if ( direction === "first" || direction === "last" ) {
14157            next = item[ direction === "first" ? "prevAll" : "nextAll" ]( filter ).eq( -1 );
14158        } else {
14159            next = item[ direction + "All" ]( filter ).eq( 0 );
14160        }
14161
14162        if ( next.length ) {
14163            this.menuInstance.focus( event, next );
14164        }
14165    },
14166
14167    _getSelectedItem: function() {
14168        return this.menuItems.eq( this.element[ 0 ].selectedIndex ).parent( "li" );
14169    },
14170
14171    _toggle: function( event ) {
14172        this[ this.isOpen ? "close" : "open" ]( event );
14173    },
14174
14175    _setSelection: function() {
14176        var selection;
14177
14178        if ( !this.range ) {
14179            return;
14180        }
14181
14182        if ( window.getSelection ) {
14183            selection = window.getSelection();
14184            selection.removeAllRanges();
14185            selection.addRange( this.range );
14186
14187        // Support: IE8
14188        } else {
14189            this.range.select();
14190        }
14191
14192        // Support: IE
14193        // Setting the text selection kills the button focus in IE, but
14194        // restoring the focus doesn't kill the selection.
14195        this.button.focus();
14196    },
14197
14198    _documentClick: {
14199        mousedown: function( event ) {
14200            if ( !this.isOpen ) {
14201                return;
14202            }
14203
14204            if ( !$( event.target ).closest( ".ui-selectmenu-menu, #" +
14205                    $.ui.escapeSelector( this.ids.button ) ).length ) {
14206                this.close( event );
14207            }
14208        }
14209    },
14210
14211    _buttonEvents: {
14212
14213        // Prevent text selection from being reset when interacting with the selectmenu (#10144)
14214        mousedown: function() {
14215            var selection;
14216
14217            if ( window.getSelection ) {
14218                selection = window.getSelection();
14219                if ( selection.rangeCount ) {
14220                    this.range = selection.getRangeAt( 0 );
14221                }
14222
14223            // Support: IE8
14224            } else {
14225                this.range = document.selection.createRange();
14226            }
14227        },
14228
14229        click: function( event ) {
14230            this._setSelection();
14231            this._toggle( event );
14232        },
14233
14234        keydown: function( event ) {
14235            var preventDefault = true;
14236            switch ( event.keyCode ) {
14237            case $.ui.keyCode.TAB:
14238            case $.ui.keyCode.ESCAPE:
14239                this.close( event );
14240                preventDefault = false;
vendor: 1,493 bytes, lines 14241-14284
14241                break;
14242            case $.ui.keyCode.ENTER:
14243                if ( this.isOpen ) {
14244                    this._selectFocusedItem( event );
14245                }
14246                break;
14247            case $.ui.keyCode.UP:
14248                if ( event.altKey ) {
14249                    this._toggle( event );
14250                } else {
14251                    this._move( "prev", event );
14252                }
14253                break;
14254            case $.ui.keyCode.DOWN:
14255                if ( event.altKey ) {
14256                    this._toggle( event );
14257                } else {
14258                    this._move( "next", event );
14259                }
14260                break;
14261            case $.ui.keyCode.SPACE:
14262                if ( this.isOpen ) {
14263                    this._selectFocusedItem( event );
14264                } else {
14265                    this._toggle( event );
14266                }
14267                break;
14268            case $.ui.keyCode.LEFT:
14269                this._move( "prev", event );
14270                break;
14271            case $.ui.keyCode.RIGHT:
14272                this._move( "next", event );
14273                break;
14274            case $.ui.keyCode.HOME:
14275            case $.ui.keyCode.PAGE_UP:
14276                this._move( "first", event );
14277                break;
14278            case $.ui.keyCode.END:
14279            case $.ui.keyCode.PAGE_DOWN:
14280                this._move( "last", event );
14281                break;
14282            default:
14283                this.menu.trigger( event );
14284                preventDefault = false;
vendor: 5,265 bytes, lines 14285-14464
14285            }
14286
14287            if ( preventDefault ) {
14288                event.preventDefault();
14289            }
14290        }
14291    },
14292
14293    _selectFocusedItem: function( event ) {
14294        var item = this.menuItems.eq( this.focusIndex ).parent( "li" );
14295        if ( !item.hasClass( "ui-state-disabled" ) ) {
14296            this._select( item.data( "ui-selectmenu-item" ), event );
14297        }
14298    },
14299
14300    _select: function( item, event ) {
14301        var oldIndex = this.element[ 0 ].selectedIndex;
14302
14303        // Change native select element
14304        this.element[ 0 ].selectedIndex = item.index;
14305        this.buttonItem.replaceWith( this.buttonItem = this._renderButtonItem( item ) );
14306        this._setAria( item );
14307        this._trigger( "select", event, { item: item } );
14308
14309        if ( item.index !== oldIndex ) {
14310            this._trigger( "change", event, { item: item } );
14311        }
14312
14313        this.close( event );
14314    },
14315
14316    _setAria: function( item ) {
14317        var id = this.menuItems.eq( item.index ).attr( "id" );
14318
14319        this.button.attr( {
14320            "aria-labelledby": id,
14321            "aria-activedescendant": id
14322        } );
14323        this.menu.attr( "aria-activedescendant", id );
14324    },
14325
14326    _setOption: function( key, value ) {
14327        if ( key === "icons" ) {
14328            var icon = this.button.find( "span.ui-icon" );
14329            this._removeClass( icon, null, this.options.icons.button )
14330                ._addClass( icon, null, value.button );
14331        }
14332
14333        this._super( key, value );
14334
14335        if ( key === "appendTo" ) {
14336            this.menuWrap.appendTo( this._appendTo() );
14337        }
14338
14339        if ( key === "width" ) {
14340            this._resizeButton();
14341        }
14342    },
14343
14344    _setOptionDisabled: function( value ) {
14345        this._super( value );
14346
14347        this.menuInstance.option( "disabled", value );
14348        this.button.attr( "aria-disabled", value );
14349        this._toggleClass( this.button, null, "ui-state-disabled", value );
14350
14351        this.element.prop( "disabled", value );
14352        if ( value ) {
14353            this.button.attr( "tabindex", -1 );
14354            this.close();
14355        } else {
14356            this.button.attr( "tabindex", 0 );
14357        }
14358    },
14359
14360    _appendTo: function() {
14361        var element = this.options.appendTo;
14362
14363        if ( element ) {
14364            element = element.jquery || element.nodeType ?
14365                $( element ) :
14366                this.document.find( element ).eq( 0 );
14367        }
14368
14369        if ( !element || !element[ 0 ] ) {
14370            element = this.element.closest( ".ui-front, dialog" );
14371        }
14372
14373        if ( !element.length ) {
14374            element = this.document[ 0 ].body;
14375        }
14376
14377        return element;
14378    },
14379
14380    _toggleAttr: function() {
14381        this.button.attr( "aria-expanded", this.isOpen );
14382
14383        // We can't use two _toggleClass() calls here, because we need to make sure
14384        // we always remove classes first and add them second, otherwise if both classes have the
14385        // same theme class, it will be removed after we add it.
14386        this._removeClass( this.button, "ui-selectmenu-button-" +
14387            ( this.isOpen ? "closed" : "open" ) )
14388            ._addClass( this.button, "ui-selectmenu-button-" +
14389                ( this.isOpen ? "open" : "closed" ) )
14390            ._toggleClass( this.menuWrap, "ui-selectmenu-open", null, this.isOpen );
14391
14392        this.menu.attr( "aria-hidden", !this.isOpen );
14393    },
14394
14395    _resizeButton: function() {
14396        var width = this.options.width;
14397
14398        // For `width: false`, just remove inline style and stop
14399        if ( width === false ) {
14400            this.button.css( "width", "" );
14401            return;
14402        }
14403
14404        // For `width: null`, match the width of the original element
14405        if ( width === null ) {
14406            width = this.element.show().outerWidth();
14407            this.element.hide();
14408        }
14409
14410        this.button.outerWidth( width );
14411    },
14412
14413    _resizeMenu: function() {
14414        this.menu.outerWidth( Math.max(
14415            this.button.outerWidth(),
14416
14417            // Support: IE10
14418            // IE10 wraps long text (possibly a rounding bug)
14419            // so we add 1px to avoid the wrapping
14420            this.menu.width( "" ).outerWidth() + 1
14421        ) );
14422    },
14423
14424    _getCreateOptions: function() {
14425        var options = this._super();
14426
14427        options.disabled = this.element.prop( "disabled" );
14428
14429        return options;
14430    },
14431
14432    _parseOptions: function( options ) {
14433        var that = this,
14434            data = [];
14435        options.each( function( index, item ) {
14436            data.push( that._parseOption( $( item ), index ) );
14437        } );
14438        this.items = data;
14439    },
14440
14441    _parseOption: function( option, index ) {
14442        var optgroup = option.parent( "optgroup" );
14443
14444        return {
14445            element: option,
14446            index: index,
14447            value: option.val(),
14448            label: option.text(),
14449            optgroup: optgroup.attr( "label" ) || "",
14450            disabled: optgroup.prop( "disabled" ) || option.prop( "disabled" )
14451        };
14452    },
14453
14454    _destroy: function() {
14455        this._unbindFormResetHandler();
14456        this.menuWrap.remove();
14457        this.button.remove();
14458        this.element.show();
14459        this.element.removeUniqueId();
14460        this.labels.attr( "for", this.ids.element );
14461    }
14462} ] );
14463
14464
vendor: 27,904 bytes, lines 14465-15328
14465/*!
14466 * jQuery UI Slider 1.12.1
14467 * http://jqueryui.com
14468 *
14469 * Copyright jQuery Foundation and other contributors
14470 * Released under the MIT license.
14471 * http://jquery.org/license
14472 */
14473
14474//>>label: Slider
14475//>>group: Widgets
14476//>>description: Displays a flexible slider with ranges and accessibility via keyboard.
14477//>>docs: http://api.jqueryui.com/slider/
14478//>>demos: http://jqueryui.com/slider/
14479//>>css.structure: ../../themes/base/core.css
14480//>>css.structure: ../../themes/base/slider.css
14481//>>css.theme: ../../themes/base/theme.css
14482
14483
14484
14485var widgetsSlider = $.widget( "ui.slider", $.ui.mouse, {
14486    version: "1.12.1",
14487    widgetEventPrefix: "slide",
14488
14489    options: {
14490        animate: false,
14491        classes: {
14492            "ui-slider": "ui-corner-all",
14493            "ui-slider-handle": "ui-corner-all",
14494
14495            // Note: ui-widget-header isn't the most fittingly semantic framework class for this
14496            // element, but worked best visually with a variety of themes
14497            "ui-slider-range": "ui-corner-all ui-widget-header"
14498        },
14499        distance: 0,
14500        max: 100,
14501        min: 0,
14502        orientation: "horizontal",
14503        range: false,
14504        step: 1,
14505        value: 0,
14506        values: null,
14507
14508        // Callbacks
14509        change: null,
14510        slide: null,
14511        start: null,
14512        stop: null
14513    },
14514
14515    // Number of pages in a slider
14516    // (how many times can you page up/down to go through the whole range)
14517    numPages: 5,
14518
14519    _create: function() {
14520        this._keySliding = false;
14521        this._mouseSliding = false;
14522        this._animateOff = true;
14523        this._handleIndex = null;
14524        this._detectOrientation();
14525        this._mouseInit();
14526        this._calculateNewMax();
14527
14528        this._addClass( "ui-slider ui-slider-" + this.orientation,
14529            "ui-widget ui-widget-content" );
14530
14531        this._refresh();
14532
14533        this._animateOff = false;
14534    },
14535
14536    _refresh: function() {
14537        this._createRange();
14538        this._createHandles();
14539        this._setupEvents();
14540        this._refreshValue();
14541    },
14542
14543    _createHandles: function() {
14544        var i, handleCount,
14545            options = this.options,
14546            existingHandles = this.element.find( ".ui-slider-handle" ),
14547            handle = "<span tabindex='0'></span>",
14548            handles = [];
14549
14550        handleCount = ( options.values && options.values.length ) || 1;
14551
14552        if ( existingHandles.length > handleCount ) {
14553            existingHandles.slice( handleCount ).remove();
14554            existingHandles = existingHandles.slice( 0, handleCount );
14555        }
14556
14557        for ( i = existingHandles.length; i < handleCount; i++ ) {
14558            handles.push( handle );
14559        }
14560
14561        this.handles = existingHandles.add( $( handles.join( "" ) ).appendTo( this.element ) );
14562
14563        this._addClass( this.handles, "ui-slider-handle", "ui-state-default" );
14564
14565        this.handle = this.handles.eq( 0 );
14566
14567        this.handles.each( function( i ) {
14568            $( this )
14569                .data( "ui-slider-handle-index", i )
14570                .attr( "tabIndex", 0 );
14571        } );
14572    },
14573
14574    _createRange: function() {
14575        var options = this.options;
14576
14577        if ( options.range ) {
14578            if ( options.range === true ) {
14579                if ( !options.values ) {
14580                    options.values = [ this._valueMin(), this._valueMin() ];
14581                } else if ( options.values.length && options.values.length !== 2 ) {
14582                    options.values = [ options.values[ 0 ], options.values[ 0 ] ];
14583                } else if ( $.isArray( options.values ) ) {
14584                    options.values = options.values.slice( 0 );
14585                }
14586            }
14587
14588            if ( !this.range || !this.range.length ) {
14589                this.range = $( "<div>" )
14590                    .appendTo( this.element );
14591
14592                this._addClass( this.range, "ui-slider-range" );
14593            } else {
14594                this._removeClass( this.range, "ui-slider-range-min ui-slider-range-max" );
14595
14596                // Handle range switching from true to min/max
14597                this.range.css( {
14598                    "left": "",
14599                    "bottom": ""
14600                } );
14601            }
14602            if ( options.range === "min" || options.range === "max" ) {
14603                this._addClass( this.range, "ui-slider-range-" + options.range );
14604            }
14605        } else {
14606            if ( this.range ) {
14607                this.range.remove();
14608            }
14609            this.range = null;
14610        }
14611    },
14612
14613    _setupEvents: function() {
14614        this._off( this.handles );
14615        this._on( this.handles, this._handleEvents );
14616        this._hoverable( this.handles );
14617        this._focusable( this.handles );
14618    },
14619
14620    _destroy: function() {
14621        this.handles.remove();
14622        if ( this.range ) {
14623            this.range.remove();
14624        }
14625
14626        this._mouseDestroy();
14627    },
14628
14629    _mouseCapture: function( event ) {
14630        var position, normValue, distance, closestHandle, index, allowed, offset, mouseOverHandle,
14631            that = this,
14632            o = this.options;
14633
14634        if ( o.disabled ) {
14635            return false;
14636        }
14637
14638        this.elementSize = {
14639            width: this.element.outerWidth(),
14640            height: this.element.outerHeight()
14641        };
14642        this.elementOffset = this.element.offset();
14643
14644        position = { x: event.pageX, y: event.pageY };
14645        normValue = this._normValueFromMouse( position );
14646        distance = this._valueMax() - this._valueMin() + 1;
14647        this.handles.each( function( i ) {
14648            var thisDistance = Math.abs( normValue - that.values( i ) );
14649            if ( ( distance > thisDistance ) ||
14650                ( distance === thisDistance &&
14651                    ( i === that._lastChangedValue || that.values( i ) === o.min ) ) ) {
14652                distance = thisDistance;
14653                closestHandle = $( this );
14654                index = i;
14655            }
14656        } );
14657
14658        allowed = this._start( event, index );
14659        if ( allowed === false ) {
14660            return false;
14661        }
14662        this._mouseSliding = true;
14663
14664        this._handleIndex = index;
14665
14666        this._addClass( closestHandle, null, "ui-state-active" );
14667        closestHandle.trigger( "focus" );
14668
14669        offset = closestHandle.offset();
14670        mouseOverHandle = !$( event.target ).parents().addBack().is( ".ui-slider-handle" );
14671        this._clickOffset = mouseOverHandle ? { left: 0, top: 0 } : {
14672            left: event.pageX - offset.left - ( closestHandle.width() / 2 ),
14673            top: event.pageY - offset.top -
14674                ( closestHandle.height() / 2 ) -
14675                ( parseInt( closestHandle.css( "borderTopWidth" ), 10 ) || 0 ) -
14676                ( parseInt( closestHandle.css( "borderBottomWidth" ), 10 ) || 0 ) +
14677                ( parseInt( closestHandle.css( "marginTop" ), 10 ) || 0 )
14678        };
14679
14680        if ( !this.handles.hasClass( "ui-state-hover" ) ) {
14681            this._slide( event, index, normValue );
14682        }
14683        this._animateOff = true;
14684        return true;
14685    },
14686
14687    _mouseStart: function() {
14688        return true;
14689    },
14690
14691    _mouseDrag: function( event ) {
14692        var position = { x: event.pageX, y: event.pageY },
14693            normValue = this._normValueFromMouse( position );
14694
14695        this._slide( event, this._handleIndex, normValue );
14696
14697        return false;
14698    },
14699
14700    _mouseStop: function( event ) {
14701        this._removeClass( this.handles, null, "ui-state-active" );
14702        this._mouseSliding = false;
14703
14704        this._stop( event, this._handleIndex );
14705        this._change( event, this._handleIndex );
14706
14707        this._handleIndex = null;
14708        this._clickOffset = null;
14709        this._animateOff = false;
14710
14711        return false;
14712    },
14713
14714    _detectOrientation: function() {
14715        this.orientation = ( this.options.orientation === "vertical" ) ? "vertical" : "horizontal";
14716    },
14717
14718    _normValueFromMouse: function( position ) {
14719        var pixelTotal,
14720            pixelMouse,
14721            percentMouse,
14722            valueTotal,
14723            valueMouse;
14724
14725        if ( this.orientation === "horizontal" ) {
14726            pixelTotal = this.elementSize.width;
14727            pixelMouse = position.x - this.elementOffset.left -
14728                ( this._clickOffset ? this._clickOffset.left : 0 );
14729        } else {
14730            pixelTotal = this.elementSize.height;
14731            pixelMouse = position.y - this.elementOffset.top -
14732                ( this._clickOffset ? this._clickOffset.top : 0 );
14733        }
14734
14735        percentMouse = ( pixelMouse / pixelTotal );
14736        if ( percentMouse > 1 ) {
14737            percentMouse = 1;
14738        }
14739        if ( percentMouse < 0 ) {
14740            percentMouse = 0;
14741        }
14742        if ( this.orientation === "vertical" ) {
14743            percentMouse = 1 - percentMouse;
14744        }
14745
14746        valueTotal = this._valueMax() - this._valueMin();
14747        valueMouse = this._valueMin() + percentMouse * valueTotal;
14748
14749        return this._trimAlignValue( valueMouse );
14750    },
14751
14752    _uiHash: function( index, value, values ) {
14753        var uiHash = {
14754            handle: this.handles[ index ],
14755            handleIndex: index,
14756            value: value !== undefined ? value : this.value()
14757        };
14758
14759        if ( this._hasMultipleValues() ) {
14760            uiHash.value = value !== undefined ? value : this.values( index );
14761            uiHash.values = values || this.values();
14762        }
14763
14764        return uiHash;
14765    },
14766
14767    _hasMultipleValues: function() {
14768        return this.options.values && this.options.values.length;
14769    },
14770
14771    _start: function( event, index ) {
14772        return this._trigger( "start", event, this._uiHash( index ) );
14773    },
14774
14775    _slide: function( event, index, newVal ) {
14776        var allowed, otherVal,
14777            currentValue = this.value(),
14778            newValues = this.values();
14779
14780        if ( this._hasMultipleValues() ) {
14781            otherVal = this.values( index ? 0 : 1 );
14782            currentValue = this.values( index );
14783
14784            if ( this.options.values.length === 2 && this.options.range === true ) {
14785                newVal =  index === 0 ? Math.min( otherVal, newVal ) : Math.max( otherVal, newVal );
14786            }
14787
14788            newValues[ index ] = newVal;
14789        }
14790
14791        if ( newVal === currentValue ) {
14792            return;
14793        }
14794
14795        allowed = this._trigger( "slide", event, this._uiHash( index, newVal, newValues ) );
14796
14797        // A slide can be canceled by returning false from the slide callback
14798        if ( allowed === false ) {
14799            return;
14800        }
14801
14802        if ( this._hasMultipleValues() ) {
14803            this.values( index, newVal );
14804        } else {
14805            this.value( newVal );
14806        }
14807    },
14808
14809    _stop: function( event, index ) {
14810        this._trigger( "stop", event, this._uiHash( index ) );
14811    },
14812
14813    _change: function( event, index ) {
14814        if ( !this._keySliding && !this._mouseSliding ) {
14815
14816            //store the last changed value index for reference when handles overlap
14817            this._lastChangedValue = index;
14818            this._trigger( "change", event, this._uiHash( index ) );
14819        }
14820    },
14821
14822    value: function( newValue ) {
14823        if ( arguments.length ) {
14824            this.options.value = this._trimAlignValue( newValue );
14825            this._refreshValue();
14826            this._change( null, 0 );
14827            return;
14828        }
14829
14830        return this._value();
14831    },
14832
14833    values: function( index, newValue ) {
14834        var vals,
14835            newValues,
14836            i;
14837
14838        if ( arguments.length > 1 ) {
14839            this.options.values[ index ] = this._trimAlignValue( newValue );
14840            this._refreshValue();
14841            this._change( null, index );
14842            return;
14843        }
14844
14845        if ( arguments.length ) {
14846            if ( $.isArray( arguments[ 0 ] ) ) {
14847                vals = this.options.values;
14848                newValues = arguments[ 0 ];
14849                for ( i = 0; i < vals.length; i += 1 ) {
14850                    vals[ i ] = this._trimAlignValue( newValues[ i ] );
14851                    this._change( null, i );
14852                }
14853                this._refreshValue();
14854            } else {
14855                if ( this._hasMultipleValues() ) {
14856                    return this._values( index );
14857                } else {
14858                    return this.value();
14859                }
14860            }
14861        } else {
14862            return this._values();
14863        }
14864    },
14865
14866    _setOption: function( key, value ) {
14867        var i,
14868            valsLength = 0;
14869
14870        if ( key === "range" && this.options.range === true ) {
14871            if ( value === "min" ) {
14872                this.options.value = this._values( 0 );
14873                this.options.values = null;
14874            } else if ( value === "max" ) {
14875                this.options.value = this._values( this.options.values.length - 1 );
14876                this.options.values = null;
14877            }
14878        }
14879
14880        if ( $.isArray( this.options.values ) ) {
14881            valsLength = this.options.values.length;
14882        }
14883
14884        this._super( key, value );
14885
14886        switch ( key ) {
14887            case "orientation":
14888                this._detectOrientation();
14889                this._removeClass( "ui-slider-horizontal ui-slider-vertical" )
14890                    ._addClass( "ui-slider-" + this.orientation );
14891                this._refreshValue();
14892                if ( this.options.range ) {
14893                    this._refreshRange( value );
14894                }
14895
14896                // Reset positioning from previous orientation
14897                this.handles.css( value === "horizontal" ? "bottom" : "left", "" );
14898                break;
14899            case "value":
14900                this._animateOff = true;
14901                this._refreshValue();
14902                this._change( null, 0 );
14903                this._animateOff = false;
14904                break;
14905            case "values":
14906                this._animateOff = true;
14907                this._refreshValue();
14908
14909                // Start from the last handle to prevent unreachable handles (#9046)
14910                for ( i = valsLength - 1; i >= 0; i-- ) {
14911                    this._change( null, i );
14912                }
14913                this._animateOff = false;
14914                break;
14915            case "step":
14916            case "min":
14917            case "max":
14918                this._animateOff = true;
14919                this._calculateNewMax();
14920                this._refreshValue();
14921                this._animateOff = false;
14922                break;
14923            case "range":
14924                this._animateOff = true;
14925                this._refresh();
14926                this._animateOff = false;
14927                break;
14928        }
14929    },
14930
14931    _setOptionDisabled: function( value ) {
14932        this._super( value );
14933
14934        this._toggleClass( null, "ui-state-disabled", !!value );
14935    },
14936
14937    //internal value getter
14938    // _value() returns value trimmed by min and max, aligned by step
14939    _value: function() {
14940        var val = this.options.value;
14941        val = this._trimAlignValue( val );
14942
14943        return val;
14944    },
14945
14946    //internal values getter
14947    // _values() returns array of values trimmed by min and max, aligned by step
14948    // _values( index ) returns single value trimmed by min and max, aligned by step
14949    _values: function( index ) {
14950        var val,
14951            vals,
14952            i;
14953
14954        if ( arguments.length ) {
14955            val = this.options.values[ index ];
14956            val = this._trimAlignValue( val );
14957
14958            return val;
14959        } else if ( this._hasMultipleValues() ) {
14960
14961            // .slice() creates a copy of the array
14962            // this copy gets trimmed by min and max and then returned
14963            vals = this.options.values.slice();
14964            for ( i = 0; i < vals.length; i += 1 ) {
14965                vals[ i ] = this._trimAlignValue( vals[ i ] );
14966            }
14967
14968            return vals;
14969        } else {
14970            return [];
14971        }
14972    },
14973
14974    // Returns the step-aligned value that val is closest to, between (inclusive) min and max
14975    _trimAlignValue: function( val ) {
14976        if ( val <= this._valueMin() ) {
14977            return this._valueMin();
14978        }
14979        if ( val >= this._valueMax() ) {
14980            return this._valueMax();
14981        }
14982        var step = ( this.options.step > 0 ) ? this.options.step : 1,
14983            valModStep = ( val - this._valueMin() ) % step,
14984            alignValue = val - valModStep;
14985
14986        if ( Math.abs( valModStep ) * 2 >= step ) {
14987            alignValue += ( valModStep > 0 ) ? step : ( -step );
14988        }
14989
14990        // Since JavaScript has problems with large floats, round
14991        // the final value to 5 digits after the decimal point (see #4124)
14992        return parseFloat( alignValue.toFixed( 5 ) );
14993    },
14994
14995    _calculateNewMax: function() {
14996        var max = this.options.max,
14997            min = this._valueMin(),
14998            step = this.options.step,
14999            aboveMin = Math.round( ( max - min ) / step ) * step;
15000        max = aboveMin + min;
15001        if ( max > this.options.max ) {
15002
15003            //If max is not divisible by step, rounding off may increase its value
15004            max -= step;
15005        }
15006        this.max = parseFloat( max.toFixed( this._precision() ) );
15007    },
15008
15009    _precision: function() {
15010        var precision = this._precisionOf( this.options.step );
15011        if ( this.options.min !== null ) {
15012            precision = Math.max( precision, this._precisionOf( this.options.min ) );
15013        }
15014        return precision;
15015    },
15016
15017    _precisionOf: function( num ) {
15018        var str = num.toString(),
15019            decimal = str.indexOf( "." );
15020        return decimal === -1 ? 0 : str.length - decimal - 1;
15021    },
15022
15023    _valueMin: function() {
15024        return this.options.min;
15025    },
15026
15027    _valueMax: function() {
15028        return this.max;
15029    },
15030
15031    _refreshRange: function( orientation ) {
15032        if ( orientation === "vertical" ) {
15033            this.range.css( { "width": "", "left": "" } );
15034        }
15035        if ( orientation === "horizontal" ) {
15036            this.range.css( { "height": "", "bottom": "" } );
15037        }
15038    },
15039
15040    _refreshValue: function() {
15041        var lastValPercent, valPercent, value, valueMin, valueMax,
15042            oRange = this.options.range,
15043            o = this.options,
15044            that = this,
15045            animate = ( !this._animateOff ) ? o.animate : false,
15046            _set = {};
15047
15048        if ( this._hasMultipleValues() ) {
15049            this.handles.each( function( i ) {
15050                valPercent = ( that.values( i ) - that._valueMin() ) / ( that._valueMax() -
15051                    that._valueMin() ) * 100;
15052                _set[ that.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
15053                $( this ).stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
15054                if ( that.options.range === true ) {
15055                    if ( that.orientation === "horizontal" ) {
15056                        if ( i === 0 ) {
15057                            that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
15058                                left: valPercent + "%"
15059                            }, o.animate );
15060                        }
15061                        if ( i === 1 ) {
15062                            that.range[ animate ? "animate" : "css" ]( {
15063                                width: ( valPercent - lastValPercent ) + "%"
15064                            }, {
15065                                queue: false,
15066                                duration: o.animate
15067                            } );
15068                        }
15069                    } else {
15070                        if ( i === 0 ) {
15071                            that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
15072                                bottom: ( valPercent ) + "%"
15073                            }, o.animate );
15074                        }
15075                        if ( i === 1 ) {
15076                            that.range[ animate ? "animate" : "css" ]( {
15077                                height: ( valPercent - lastValPercent ) + "%"
15078                            }, {
15079                                queue: false,
15080                                duration: o.animate
15081                            } );
15082                        }
15083                    }
15084                }
15085                lastValPercent = valPercent;
15086            } );
15087        } else {
15088            value = this.value();
15089            valueMin = this._valueMin();
15090            valueMax = this._valueMax();
15091            valPercent = ( valueMax !== valueMin ) ?
15092                    ( value - valueMin ) / ( valueMax - valueMin ) * 100 :
15093                    0;
15094            _set[ this.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
15095            this.handle.stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
15096
15097            if ( oRange === "min" && this.orientation === "horizontal" ) {
15098                this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
15099                    width: valPercent + "%"
15100                }, o.animate );
15101            }
15102            if ( oRange === "max" && this.orientation === "horizontal" ) {
15103                this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
15104                    width: ( 100 - valPercent ) + "%"
15105                }, o.animate );
15106            }
15107            if ( oRange === "min" && this.orientation === "vertical" ) {
15108                this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
15109                    height: valPercent + "%"
15110                }, o.animate );
15111            }
15112            if ( oRange === "max" && this.orientation === "vertical" ) {
15113                this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( {
15114                    height: ( 100 - valPercent ) + "%"
15115                }, o.animate );
15116            }
15117        }
15118    },
15119
15120    _handleEvents: {
15121        keydown: function( event ) {
15122            var allowed, curVal, newVal, step,
15123                index = $( event.target ).data( "ui-slider-handle-index" );
15124
15125            switch ( event.keyCode ) {
15126                case $.ui.keyCode.HOME:
15127                case $.ui.keyCode.END:
15128                case $.ui.keyCode.PAGE_UP:
15129                case $.ui.keyCode.PAGE_DOWN:
15130                case $.ui.keyCode.UP:
15131                case $.ui.keyCode.RIGHT:
15132                case $.ui.keyCode.DOWN:
15133                case $.ui.keyCode.LEFT:
15134                    event.preventDefault();
15135                    if ( !this._keySliding ) {
15136                        this._keySliding = true;
15137                        this._addClass( $( event.target ), null, "ui-state-active" );
15138                        allowed = this._start( event, index );
15139                        if ( allowed === false ) {
15140                            return;
15141                        }
15142                    }
15143                    break;
15144            }
15145
15146            step = this.options.step;
15147            if ( this._hasMultipleValues() ) {
15148                curVal = newVal = this.values( index );
15149            } else {
15150                curVal = newVal = this.value();
15151            }
15152
15153            switch ( event.keyCode ) {
15154                case $.ui.keyCode.HOME:
15155                    newVal = this._valueMin();
15156                    break;
15157                case $.ui.keyCode.END:
15158                    newVal = this._valueMax();
15159                    break;
15160                case $.ui.keyCode.PAGE_UP:
15161                    newVal = this._trimAlignValue(
15162                        curVal + ( ( this._valueMax() - this._valueMin() ) / this.numPages )
15163                    );
15164                    break;
15165                case $.ui.keyCode.PAGE_DOWN:
15166                    newVal = this._trimAlignValue(
15167                        curVal - ( ( this._valueMax() - this._valueMin() ) / this.numPages ) );
15168                    break;
15169                case $.ui.keyCode.UP:
15170                case $.ui.keyCode.RIGHT:
15171                    if ( curVal === this._valueMax() ) {
15172                        return;
15173                    }
15174                    newVal = this._trimAlignValue( curVal + step );
15175                    break;
15176                case $.ui.keyCode.DOWN:
15177                case $.ui.keyCode.LEFT:
15178                    if ( curVal === this._valueMin() ) {
15179                        return;
15180                    }
15181                    newVal = this._trimAlignValue( curVal - step );
15182                    break;
15183            }
15184
15185            this._slide( event, index, newVal );
15186        },
15187        keyup: function( event ) {
15188            var index = $( event.target ).data( "ui-slider-handle-index" );
15189
15190            if ( this._keySliding ) {
15191                this._keySliding = false;
15192                this._stop( event, index );
15193                this._change( event, index );
15194                this._removeClass( $( event.target ), null, "ui-state-active" );
15195            }
15196        }
15197    }
15198} );
15199
15200
15201/*!
15202 * jQuery UI Sortable 1.12.1
15203 * http://jqueryui.com
15204 *
15205 * Copyright jQuery Foundation and other contributors
15206 * Released under the MIT license.
15207 * http://jquery.org/license
15208 */
15209
15210//>>label: Sortable
15211//>>group: Interactions
15212//>>description: Enables items in a list to be sorted using the mouse.
15213//>>docs: http://api.jqueryui.com/sortable/
15214//>>demos: http://jqueryui.com/sortable/
15215//>>css.structure: ../../themes/base/sortable.css
15216
15217
15218
15219var widgetsSortable = $.widget( "ui.sortable", $.ui.mouse, {
15220    version: "1.12.1",
15221    widgetEventPrefix: "sort",
15222    ready: false,
15223    options: {
15224        appendTo: "parent",
15225        axis: false,
15226        connectWith: false,
15227        containment: false,
15228        cursor: "auto",
15229        cursorAt: false,
15230        dropOnEmpty: true,
15231        forcePlaceholderSize: false,
15232        forceHelperSize: false,
15233        grid: false,
15234        handle: false,
15235        helper: "original",
15236        items: "> *",
15237        opacity: false,
15238        placeholder: false,
15239        revert: false,
15240        scroll: true,
15241        scrollSensitivity: 20,
15242        scrollSpeed: 20,
15243        scope: "default",
15244        tolerance: "intersect",
15245        zIndex: 1000,
15246
15247        // Callbacks
15248        activate: null,
15249        beforeStop: null,
15250        change: null,
15251        deactivate: null,
15252        out: null,
15253        over: null,
15254        receive: null,
15255        remove: null,
15256        sort: null,
15257        start: null,
15258        stop: null,
15259        update: null
15260    },
15261
15262    _isOverAxis: function( x, reference, size ) {
15263        return ( x >= reference ) && ( x < ( reference + size ) );
15264    },
15265
15266    _isFloating: function( item ) {
15267        return ( /left|right/ ).test( item.css( "float" ) ) ||
15268            ( /inline|table-cell/ ).test( item.css( "display" ) );
15269    },
15270
15271    _create: function() {
15272        this.containerCache = {};
15273        this._addClass( "ui-sortable" );
15274
15275        //Get the items
15276        this.refresh();
15277
15278        //Let's determine the parent's offset
15279        this.offset = this.element.offset();
15280
15281        //Initialize mouse events for interaction
15282        this._mouseInit();
15283
15284        this._setHandleClassName();
15285
15286        //We're ready to go
15287        this.ready = true;
15288
15289    },
15290
15291    _setOption: function( key, value ) {
15292        this._super( key, value );
15293
15294        if ( key === "handle" ) {
15295            this._setHandleClassName();
15296        }
15297    },
15298
15299    _setHandleClassName: function() {
15300        var that = this;
15301        this._removeClass( this.element.find( ".ui-sortable-handle" ), "ui-sortable-handle" );
15302        $.each( this.items, function() {
15303            that._addClass(
15304                this.instance.options.handle ?
15305                    this.item.find( this.instance.options.handle ) :
15306                    this.item,
15307                "ui-sortable-handle"
15308            );
15309        } );
15310    },
15311
15312    _destroy: function() {
15313        this._mouseDestroy();
15314
15315        for ( var i = this.items.length - 1; i >= 0; i-- ) {
15316            this.items[ i ].item.removeData( this.widgetName + "-item" );
15317        }
15318
15319        return this;
15320    },
15321
15322    _mouseCapture: function( event, overrideHandle ) {
15323        var currentItem = null,
15324            validHandle = false,
15325            that = this;
15326
15327        if ( this.reverting ) {
15328            return false;
vendor: 4,146 bytes, lines 15329-15451
15329        }
15330
15331        if ( this.options.disabled || this.options.type === "static" ) {
15332            return false;
15333        }
15334
15335        //We have to refresh the items data once first
15336        this._refreshItems( event );
15337
15338        //Find out if the clicked node (or one of its parents) is a actual item in this.items
15339        $( event.target ).parents().each( function() {
15340            if ( $.data( this, that.widgetName + "-item" ) === that ) {
15341                currentItem = $( this );
15342                return false;
15343            }
15344        } );
15345        if ( $.data( event.target, that.widgetName + "-item" ) === that ) {
15346            currentItem = $( event.target );
15347        }
15348
15349        if ( !currentItem ) {
15350            return false;
15351        }
15352        if ( this.options.handle && !overrideHandle ) {
15353            $( this.options.handle, currentItem ).find( "*" ).addBack().each( function() {
15354                if ( this === event.target ) {
15355                    validHandle = true;
15356                }
15357            } );
15358            if ( !validHandle ) {
15359                return false;
15360            }
15361        }
15362
15363        this.currentItem = currentItem;
15364        this._removeCurrentsFromItems();
15365        return true;
15366
15367    },
15368
15369    _mouseStart: function( event, overrideHandle, noActivation ) {
15370
15371        var i, body,
15372            o = this.options;
15373
15374        this.currentContainer = this;
15375
15376        //We only need to call refreshPositions, because the refreshItems call has been moved to
15377        // mouseCapture
15378        this.refreshPositions();
15379
15380        //Create and append the visible helper
15381        this.helper = this._createHelper( event );
15382
15383        //Cache the helper size
15384        this._cacheHelperProportions();
15385
15386        /*
15387         * - Position generation -
15388         * This block generates everything position related - it's the core of draggables.
15389         */
15390
15391        //Cache the margins of the original element
15392        this._cacheMargins();
15393
15394        //Get the next scrolling parent
15395        this.scrollParent = this.helper.scrollParent();
15396
15397        //The element's absolute position on the page minus margins
15398        this.offset = this.currentItem.offset();
15399        this.offset = {
15400            top: this.offset.top - this.margins.top,
15401            left: this.offset.left - this.margins.left
15402        };
15403
15404        $.extend( this.offset, {
15405            click: { //Where the click happened, relative to the element
15406                left: event.pageX - this.offset.left,
15407                top: event.pageY - this.offset.top
15408            },
15409            parent: this._getParentOffset(),
15410
15411            // This is a relative to absolute position minus the actual position calculation -
15412            // only used for relative positioned helper
15413            relative: this._getRelativeOffset()
15414        } );
15415
15416        // Only after we got the offset, we can change the helper's position to absolute
15417        // TODO: Still need to figure out a way to make relative sorting possible
15418        this.helper.css( "position", "absolute" );
15419        this.cssPosition = this.helper.css( "position" );
15420
15421        //Generate the original position
15422        this.originalPosition = this._generatePosition( event );
15423        this.originalPageX = event.pageX;
15424        this.originalPageY = event.pageY;
15425
15426        //Adjust the mouse offset relative to the helper if "cursorAt" is supplied
15427        ( o.cursorAt && this._adjustOffsetFromHelper( o.cursorAt ) );
15428
15429        //Cache the former DOM position
15430        this.domPosition = {
15431            prev: this.currentItem.prev()[ 0 ],
15432            parent: this.currentItem.parent()[ 0 ]
15433        };
15434
15435        // If the helper is not the original, hide the original so it's not playing any role during
15436        // the drag, won't cause anything bad this way
15437        if ( this.helper[ 0 ] !== this.currentItem[ 0 ] ) {
15438            this.currentItem.hide();
15439        }
15440
15441        //Create the placeholder
15442        this._createPlaceholder();
15443
15444        //Set a containment if given in the options
15445        if ( o.containment ) {
15446            this._setContainment();
15447        }
15448
15449        if ( o.cursor && o.cursor !== "auto" ) { // cursor option
15450            body = this.document.find( "body" );
15451
vendor: 6,010 bytes, lines 15452-15604
15452            // Support: IE
15453            this.storedCursor = body.css( "cursor" );
15454            body.css( "cursor", o.cursor );
15455
15456            this.storedStylesheet =
15457                $( "<style>*{ cursor: " + o.cursor + " !important; }</style>" ).appendTo( body );
15458        }
15459
15460        if ( o.opacity ) { // opacity option
15461            if ( this.helper.css( "opacity" ) ) {
15462                this._storedOpacity = this.helper.css( "opacity" );
15463            }
15464            this.helper.css( "opacity", o.opacity );
15465        }
15466
15467        if ( o.zIndex ) { // zIndex option
15468            if ( this.helper.css( "zIndex" ) ) {
15469                this._storedZIndex = this.helper.css( "zIndex" );
15470            }
15471            this.helper.css( "zIndex", o.zIndex );
15472        }
15473
15474        //Prepare scrolling
15475        if ( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
15476                this.scrollParent[ 0 ].tagName !== "HTML" ) {
15477            this.overflowOffset = this.scrollParent.offset();
15478        }
15479
15480        //Call callbacks
15481        this._trigger( "start", event, this._uiHash() );
15482
15483        //Recache the helper size
15484        if ( !this._preserveHelperProportions ) {
15485            this._cacheHelperProportions();
15486        }
15487
15488        //Post "activate" events to possible containers
15489        if ( !noActivation ) {
15490            for ( i = this.containers.length - 1; i >= 0; i-- ) {
15491                this.containers[ i ]._trigger( "activate", event, this._uiHash( this ) );
15492            }
15493        }
15494
15495        //Prepare possible droppables
15496        if ( $.ui.ddmanager ) {
15497            $.ui.ddmanager.current = this;
15498        }
15499
15500        if ( $.ui.ddmanager && !o.dropBehaviour ) {
15501            $.ui.ddmanager.prepareOffsets( this, event );
15502        }
15503
15504        this.dragging = true;
15505
15506        this._addClass( this.helper, "ui-sortable-helper" );
15507
15508        // Execute the drag once - this causes the helper not to be visiblebefore getting its
15509        // correct position
15510        this._mouseDrag( event );
15511        return true;
15512
15513    },
15514
15515    _mouseDrag: function( event ) {
15516        var i, item, itemElement, intersection,
15517            o = this.options,
15518            scrolled = false;
15519
15520        //Compute the helpers position
15521        this.position = this._generatePosition( event );
15522        this.positionAbs = this._convertPositionTo( "absolute" );
15523
15524        if ( !this.lastPositionAbs ) {
15525            this.lastPositionAbs = this.positionAbs;
15526        }
15527
15528        //Do scrolling
15529        if ( this.options.scroll ) {
15530            if ( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
15531                    this.scrollParent[ 0 ].tagName !== "HTML" ) {
15532
15533                if ( ( this.overflowOffset.top + this.scrollParent[ 0 ].offsetHeight ) -
15534                        event.pageY < o.scrollSensitivity ) {
15535                    this.scrollParent[ 0 ].scrollTop =
15536                        scrolled = this.scrollParent[ 0 ].scrollTop + o.scrollSpeed;
15537                } else if ( event.pageY - this.overflowOffset.top < o.scrollSensitivity ) {
15538                    this.scrollParent[ 0 ].scrollTop =
15539                        scrolled = this.scrollParent[ 0 ].scrollTop - o.scrollSpeed;
15540                }
15541
15542                if ( ( this.overflowOffset.left + this.scrollParent[ 0 ].offsetWidth ) -
15543                        event.pageX < o.scrollSensitivity ) {
15544                    this.scrollParent[ 0 ].scrollLeft = scrolled =
15545                        this.scrollParent[ 0 ].scrollLeft + o.scrollSpeed;
15546                } else if ( event.pageX - this.overflowOffset.left < o.scrollSensitivity ) {
15547                    this.scrollParent[ 0 ].scrollLeft = scrolled =
15548                        this.scrollParent[ 0 ].scrollLeft - o.scrollSpeed;
15549                }
15550
15551            } else {
15552
15553                if ( event.pageY - this.document.scrollTop() < o.scrollSensitivity ) {
15554                    scrolled = this.document.scrollTop( this.document.scrollTop() - o.scrollSpeed );
15555                } else if ( this.window.height() - ( event.pageY - this.document.scrollTop() ) <
15556                        o.scrollSensitivity ) {
15557                    scrolled = this.document.scrollTop( this.document.scrollTop() + o.scrollSpeed );
15558                }
15559
15560                if ( event.pageX - this.document.scrollLeft() < o.scrollSensitivity ) {
15561                    scrolled = this.document.scrollLeft(
15562                        this.document.scrollLeft() - o.scrollSpeed
15563                    );
15564                } else if ( this.window.width() - ( event.pageX - this.document.scrollLeft() ) <
15565                        o.scrollSensitivity ) {
15566                    scrolled = this.document.scrollLeft(
15567                        this.document.scrollLeft() + o.scrollSpeed
15568                    );
15569                }
15570
15571            }
15572
15573            if ( scrolled !== false && $.ui.ddmanager && !o.dropBehaviour ) {
15574                $.ui.ddmanager.prepareOffsets( this, event );
15575            }
15576        }
15577
15578        //Regenerate the absolute position used for position checks
15579        this.positionAbs = this._convertPositionTo( "absolute" );
15580
15581        //Set the helper position
15582        if ( !this.options.axis || this.options.axis !== "y" ) {
15583            this.helper[ 0 ].style.left = this.position.left + "px";
15584        }
15585        if ( !this.options.axis || this.options.axis !== "x" ) {
15586            this.helper[ 0 ].style.top = this.position.top + "px";
15587        }
15588
15589        //Rearrange
15590        for ( i = this.items.length - 1; i >= 0; i-- ) {
15591
15592            //Cache variables and intersection, continue if no intersection
15593            item = this.items[ i ];
15594            itemElement = item.item[ 0 ];
15595            intersection = this._intersectsWithPointer( item );
15596            if ( !intersection ) {
15597                continue;
15598            }
15599
15600            // Only put the placeholder inside the current Container, skip all
15601            // items from other containers. This works because when moving
15602            // an item from one container to another the
15603            // currentContainer is switched before the placeholder is moved.
15604            //
vendor: 5,812 bytes, lines 15605-15784
15605            // Without this, moving items in "sub-sortables" can cause
15606            // the placeholder to jitter between the outer and inner container.
15607            if ( item.instance !== this.currentContainer ) {
15608                continue;
15609            }
15610
15611            // Cannot intersect with itself
15612            // no useless actions that have been done before
15613            // no action if the item moved is the parent of the item checked
15614            if ( itemElement !== this.currentItem[ 0 ] &&
15615                this.placeholder[ intersection === 1 ? "next" : "prev" ]()[ 0 ] !== itemElement &&
15616                !$.contains( this.placeholder[ 0 ], itemElement ) &&
15617                ( this.options.type === "semi-dynamic" ?
15618                    !$.contains( this.element[ 0 ], itemElement ) :
15619                    true
15620                )
15621            ) {
15622
15623                this.direction = intersection === 1 ? "down" : "up";
15624
15625                if ( this.options.tolerance === "pointer" || this._intersectsWithSides( item ) ) {
15626                    this._rearrange( event, item );
15627                } else {
15628                    break;
15629                }
15630
15631                this._trigger( "change", event, this._uiHash() );
15632                break;
15633            }
15634        }
15635
15636        //Post events to containers
15637        this._contactContainers( event );
15638
15639        //Interconnect with droppables
15640        if ( $.ui.ddmanager ) {
15641            $.ui.ddmanager.drag( this, event );
15642        }
15643
15644        //Call callbacks
15645        this._trigger( "sort", event, this._uiHash() );
15646
15647        this.lastPositionAbs = this.positionAbs;
15648        return false;
15649
15650    },
15651
15652    _mouseStop: function( event, noPropagation ) {
15653
15654        if ( !event ) {
15655            return;
15656        }
15657
15658        //If we are using droppables, inform the manager about the drop
15659        if ( $.ui.ddmanager && !this.options.dropBehaviour ) {
15660            $.ui.ddmanager.drop( this, event );
15661        }
15662
15663        if ( this.options.revert ) {
15664            var that = this,
15665                cur = this.placeholder.offset(),
15666                axis = this.options.axis,
15667                animation = {};
15668
15669            if ( !axis || axis === "x" ) {
15670                animation.left = cur.left - this.offset.parent.left - this.margins.left +
15671                    ( this.offsetParent[ 0 ] === this.document[ 0 ].body ?
15672                        0 :
15673                        this.offsetParent[ 0 ].scrollLeft
15674                    );
15675            }
15676            if ( !axis || axis === "y" ) {
15677                animation.top = cur.top - this.offset.parent.top - this.margins.top +
15678                    ( this.offsetParent[ 0 ] === this.document[ 0 ].body ?
15679                        0 :
15680                        this.offsetParent[ 0 ].scrollTop
15681                    );
15682            }
15683            this.reverting = true;
15684            $( this.helper ).animate(
15685                animation,
15686                parseInt( this.options.revert, 10 ) || 500,
15687                function() {
15688                    that._clear( event );
15689                }
15690            );
15691        } else {
15692            this._clear( event, noPropagation );
15693        }
15694
15695        return false;
15696
15697    },
15698
15699    cancel: function() {
15700
15701        if ( this.dragging ) {
15702
15703            this._mouseUp( new $.Event( "mouseup", { target: null } ) );
15704
15705            if ( this.options.helper === "original" ) {
15706                this.currentItem.css( this._storedCSS );
15707                this._removeClass( this.currentItem, "ui-sortable-helper" );
15708            } else {
15709                this.currentItem.show();
15710            }
15711
15712            //Post deactivating events to containers
15713            for ( var i = this.containers.length - 1; i >= 0; i-- ) {
15714                this.containers[ i ]._trigger( "deactivate", null, this._uiHash( this ) );
15715                if ( this.containers[ i ].containerCache.over ) {
15716                    this.containers[ i ]._trigger( "out", null, this._uiHash( this ) );
15717                    this.containers[ i ].containerCache.over = 0;
15718                }
15719            }
15720
15721        }
15722
15723        if ( this.placeholder ) {
15724
15725            //$(this.placeholder[0]).remove(); would have been the jQuery way - unfortunately,
15726            // it unbinds ALL events from the original node!
15727            if ( this.placeholder[ 0 ].parentNode ) {
15728                this.placeholder[ 0 ].parentNode.removeChild( this.placeholder[ 0 ] );
15729            }
15730            if ( this.options.helper !== "original" && this.helper &&
15731                    this.helper[ 0 ].parentNode ) {
15732                this.helper.remove();
15733            }
15734
15735            $.extend( this, {
15736                helper: null,
15737                dragging: false,
15738                reverting: false,
15739                _noFinalSort: null
15740            } );
15741
15742            if ( this.domPosition.prev ) {
15743                $( this.domPosition.prev ).after( this.currentItem );
15744            } else {
15745                $( this.domPosition.parent ).prepend( this.currentItem );
15746            }
15747        }
15748
15749        return this;
15750
15751    },
15752
15753    serialize: function( o ) {
15754
15755        var items = this._getItemsAsjQuery( o && o.connected ),
15756            str = [];
15757        o = o || {};
15758
15759        $( items ).each( function() {
15760            var res = ( $( o.item || this ).attr( o.attribute || "id" ) || "" )
15761                .match( o.expression || ( /(.+)[\-=_](.+)/ ) );
15762            if ( res ) {
15763                str.push(
15764                    ( o.key || res[ 1 ] + "[]" ) +
15765                    "=" + ( o.key && o.expression ? res[ 1 ] : res[ 2 ] ) );
15766            }
15767        } );
15768
15769        if ( !str.length && o.key ) {
15770            str.push( o.key + "=" );
15771        }
15772
15773        return str.join( "&" );
15774
15775    },
15776
15777    toArray: function( o ) {
15778
15779        var items = this._getItemsAsjQuery( o && o.connected ),
15780            ret = [];
15781
15782        o = o || {};
15783
15784        items.each( function() {
vendor: 11,876 bytes, lines 15785-16091
15785            ret.push( $( o.item || this ).attr( o.attribute || "id" ) || "" );
15786        } );
15787        return ret;
15788
15789    },
15790
15791    /* Be careful with the following core functions */
15792    _intersectsWith: function( item ) {
15793
15794        var x1 = this.positionAbs.left,
15795            x2 = x1 + this.helperProportions.width,
15796            y1 = this.positionAbs.top,
15797            y2 = y1 + this.helperProportions.height,
15798            l = item.left,
15799            r = l + item.width,
15800            t = item.top,
15801            b = t + item.height,
15802            dyClick = this.offset.click.top,
15803            dxClick = this.offset.click.left,
15804            isOverElementHeight = ( this.options.axis === "x" ) || ( ( y1 + dyClick ) > t &&
15805                ( y1 + dyClick ) < b ),
15806            isOverElementWidth = ( this.options.axis === "y" ) || ( ( x1 + dxClick ) > l &&
15807                ( x1 + dxClick ) < r ),
15808            isOverElement = isOverElementHeight && isOverElementWidth;
15809
15810        if ( this.options.tolerance === "pointer" ||
15811            this.options.forcePointerForContainers ||
15812            ( this.options.tolerance !== "pointer" &&
15813                this.helperProportions[ this.floating ? "width" : "height" ] >
15814                item[ this.floating ? "width" : "height" ] )
15815        ) {
15816            return isOverElement;
15817        } else {
15818
15819            return ( l < x1 + ( this.helperProportions.width / 2 ) && // Right Half
15820                x2 - ( this.helperProportions.width / 2 ) < r && // Left Half
15821                t < y1 + ( this.helperProportions.height / 2 ) && // Bottom Half
15822                y2 - ( this.helperProportions.height / 2 ) < b ); // Top Half
15823
15824        }
15825    },
15826
15827    _intersectsWithPointer: function( item ) {
15828        var verticalDirection, horizontalDirection,
15829            isOverElementHeight = ( this.options.axis === "x" ) ||
15830                this._isOverAxis(
15831                    this.positionAbs.top + this.offset.click.top, item.top, item.height ),
15832            isOverElementWidth = ( this.options.axis === "y" ) ||
15833                this._isOverAxis(
15834                    this.positionAbs.left + this.offset.click.left, item.left, item.width ),
15835            isOverElement = isOverElementHeight && isOverElementWidth;
15836
15837        if ( !isOverElement ) {
15838            return false;
15839        }
15840
15841        verticalDirection = this._getDragVerticalDirection();
15842        horizontalDirection = this._getDragHorizontalDirection();
15843
15844        return this.floating ?
15845            ( ( horizontalDirection === "right" || verticalDirection === "down" ) ? 2 : 1 )
15846            : ( verticalDirection && ( verticalDirection === "down" ? 2 : 1 ) );
15847
15848    },
15849
15850    _intersectsWithSides: function( item ) {
15851
15852        var isOverBottomHalf = this._isOverAxis( this.positionAbs.top +
15853                this.offset.click.top, item.top + ( item.height / 2 ), item.height ),
15854            isOverRightHalf = this._isOverAxis( this.positionAbs.left +
15855                this.offset.click.left, item.left + ( item.width / 2 ), item.width ),
15856            verticalDirection = this._getDragVerticalDirection(),
15857            horizontalDirection = this._getDragHorizontalDirection();
15858
15859        if ( this.floating && horizontalDirection ) {
15860            return ( ( horizontalDirection === "right" && isOverRightHalf ) ||
15861                ( horizontalDirection === "left" && !isOverRightHalf ) );
15862        } else {
15863            return verticalDirection && ( ( verticalDirection === "down" && isOverBottomHalf ) ||
15864                ( verticalDirection === "up" && !isOverBottomHalf ) );
15865        }
15866
15867    },
15868
15869    _getDragVerticalDirection: function() {
15870        var delta = this.positionAbs.top - this.lastPositionAbs.top;
15871        return delta !== 0 && ( delta > 0 ? "down" : "up" );
15872    },
15873
15874    _getDragHorizontalDirection: function() {
15875        var delta = this.positionAbs.left - this.lastPositionAbs.left;
15876        return delta !== 0 && ( delta > 0 ? "right" : "left" );
15877    },
15878
15879    refresh: function( event ) {
15880        this._refreshItems( event );
15881        this._setHandleClassName();
15882        this.refreshPositions();
15883        return this;
15884    },
15885
15886    _connectWith: function() {
15887        var options = this.options;
15888        return options.connectWith.constructor === String ?
15889            [ options.connectWith ] :
15890            options.connectWith;
15891    },
15892
15893    _getItemsAsjQuery: function( connected ) {
15894
15895        var i, j, cur, inst,
15896            items = [],
15897            queries = [],
15898            connectWith = this._connectWith();
15899
15900        if ( connectWith && connected ) {
15901            for ( i = connectWith.length - 1; i >= 0; i-- ) {
15902                cur = $( connectWith[ i ], this.document[ 0 ] );
15903                for ( j = cur.length - 1; j >= 0; j-- ) {
15904                    inst = $.data( cur[ j ], this.widgetFullName );
15905                    if ( inst && inst !== this && !inst.options.disabled ) {
15906                        queries.push( [ $.isFunction( inst.options.items ) ?
15907                            inst.options.items.call( inst.element ) :
15908                            $( inst.options.items, inst.element )
15909                                .not( ".ui-sortable-helper" )
15910                                .not( ".ui-sortable-placeholder" ), inst ] );
15911                    }
15912                }
15913            }
15914        }
15915
15916        queries.push( [ $.isFunction( this.options.items ) ?
15917            this.options.items
15918                .call( this.element, null, { options: this.options, item: this.currentItem } ) :
15919            $( this.options.items, this.element )
15920                .not( ".ui-sortable-helper" )
15921                .not( ".ui-sortable-placeholder" ), this ] );
15922
15923        function addItems() {
15924            items.push( this );
15925        }
15926        for ( i = queries.length - 1; i >= 0; i-- ) {
15927            queries[ i ][ 0 ].each( addItems );
15928        }
15929
15930        return $( items );
15931
15932    },
15933
15934    _removeCurrentsFromItems: function() {
15935
15936        var list = this.currentItem.find( ":data(" + this.widgetName + "-item)" );
15937
15938        this.items = $.grep( this.items, function( item ) {
15939            for ( var j = 0; j < list.length; j++ ) {
15940                if ( list[ j ] === item.item[ 0 ] ) {
15941                    return false;
15942                }
15943            }
15944            return true;
15945        } );
15946
15947    },
15948
15949    _refreshItems: function( event ) {
15950
15951        this.items = [];
15952        this.containers = [ this ];
15953
15954        var i, j, cur, inst, targetData, _queries, item, queriesLength,
15955            items = this.items,
15956            queries = [ [ $.isFunction( this.options.items ) ?
15957                this.options.items.call( this.element[ 0 ], event, { item: this.currentItem } ) :
15958                $( this.options.items, this.element ), this ] ],
15959            connectWith = this._connectWith();
15960
15961        //Shouldn't be run the first time through due to massive slow-down
15962        if ( connectWith && this.ready ) {
15963            for ( i = connectWith.length - 1; i >= 0; i-- ) {
15964                cur = $( connectWith[ i ], this.document[ 0 ] );
15965                for ( j = cur.length - 1; j >= 0; j-- ) {
15966                    inst = $.data( cur[ j ], this.widgetFullName );
15967                    if ( inst && inst !== this && !inst.options.disabled ) {
15968                        queries.push( [ $.isFunction( inst.options.items ) ?
15969                            inst.options.items
15970                                .call( inst.element[ 0 ], event, { item: this.currentItem } ) :
15971                            $( inst.options.items, inst.element ), inst ] );
15972                        this.containers.push( inst );
15973                    }
15974                }
15975            }
15976        }
15977
15978        for ( i = queries.length - 1; i >= 0; i-- ) {
15979            targetData = queries[ i ][ 1 ];
15980            _queries = queries[ i ][ 0 ];
15981
15982            for ( j = 0, queriesLength = _queries.length; j < queriesLength; j++ ) {
15983                item = $( _queries[ j ] );
15984
15985                // Data for target checking (mouse manager)
15986                item.data( this.widgetName + "-item", targetData );
15987
15988                items.push( {
15989                    item: item,
15990                    instance: targetData,
15991                    width: 0, height: 0,
15992                    left: 0, top: 0
15993                } );
15994            }
15995        }
15996
15997    },
15998
15999    refreshPositions: function( fast ) {
16000
16001        // Determine whether items are being displayed horizontally
16002        this.floating = this.items.length ?
16003            this.options.axis === "x" || this._isFloating( this.items[ 0 ].item ) :
16004            false;
16005
16006        //This has to be redone because due to the item being moved out/into the offsetParent,
16007        // the offsetParent's position will change
16008        if ( this.offsetParent && this.helper ) {
16009            this.offset.parent = this._getParentOffset();
16010        }
16011
16012        var i, item, t, p;
16013
16014        for ( i = this.items.length - 1; i >= 0; i-- ) {
16015            item = this.items[ i ];
16016
16017            //We ignore calculating positions of all connected containers when we're not over them
16018            if ( item.instance !== this.currentContainer && this.currentContainer &&
16019                    item.item[ 0 ] !== this.currentItem[ 0 ] ) {
16020                continue;
16021            }
16022
16023            t = this.options.toleranceElement ?
16024                $( this.options.toleranceElement, item.item ) :
16025                item.item;
16026
16027            if ( !fast ) {
16028                item.width = t.outerWidth();
16029                item.height = t.outerHeight();
16030            }
16031
16032            p = t.offset();
16033            item.left = p.left;
16034            item.top = p.top;
16035        }
16036
16037        if ( this.options.custom && this.options.custom.refreshContainers ) {
16038            this.options.custom.refreshContainers.call( this );
16039        } else {
16040            for ( i = this.containers.length - 1; i >= 0; i-- ) {
16041                p = this.containers[ i ].element.offset();
16042                this.containers[ i ].containerCache.left = p.left;
16043                this.containers[ i ].containerCache.top = p.top;
16044                this.containers[ i ].containerCache.width =
16045                    this.containers[ i ].element.outerWidth();
16046                this.containers[ i ].containerCache.height =
16047                    this.containers[ i ].element.outerHeight();
16048            }
16049        }
16050
16051        return this;
16052    },
16053
16054    _createPlaceholder: function( that ) {
16055        that = that || this;
16056        var className,
16057            o = that.options;
16058
16059        if ( !o.placeholder || o.placeholder.constructor === String ) {
16060            className = o.placeholder;
16061            o.placeholder = {
16062                element: function() {
16063
16064                    var nodeName = that.currentItem[ 0 ].nodeName.toLowerCase(),
16065                        element = $( "<" + nodeName + ">", that.document[ 0 ] );
16066
16067                        that._addClass( element, "ui-sortable-placeholder",
16068                                className || that.currentItem[ 0 ].className )
16069                            ._removeClass( element, "ui-sortable-helper" );
16070
16071                    if ( nodeName === "tbody" ) {
16072                        that._createTrPlaceholder(
16073                            that.currentItem.find( "tr" ).eq( 0 ),
16074                            $( "<tr>", that.document[ 0 ] ).appendTo( element )
16075                        );
16076                    } else if ( nodeName === "tr" ) {
16077                        that._createTrPlaceholder( that.currentItem, element );
16078                    } else if ( nodeName === "img" ) {
16079                        element.attr( "src", that.currentItem.attr( "src" ) );
16080                    }
16081
16082                    if ( !className ) {
16083                        element.css( "visibility", "hidden" );
16084                    }
16085
16086                    return element;
16087                },
16088                update: function( container, p ) {
16089
16090                    // 1. If a className is set as 'placeholder option, we don't force sizes -
16091                    // the class is responsible for that
vendor: 4,822 bytes, lines 16092-16208
16092                    // 2. The option 'forcePlaceholderSize can be enabled to force it even if a
16093                    // class name is specified
16094                    if ( className && !o.forcePlaceholderSize ) {
16095                        return;
16096                    }
16097
16098                    //If the element doesn't have a actual height by itself (without styles coming
16099                    // from a stylesheet), it receives the inline height from the dragged item
16100                    if ( !p.height() ) {
16101                        p.height(
16102                            that.currentItem.innerHeight() -
16103                            parseInt( that.currentItem.css( "paddingTop" ) || 0, 10 ) -
16104                            parseInt( that.currentItem.css( "paddingBottom" ) || 0, 10 ) );
16105                    }
16106                    if ( !p.width() ) {
16107                        p.width(
16108                            that.currentItem.innerWidth() -
16109                            parseInt( that.currentItem.css( "paddingLeft" ) || 0, 10 ) -
16110                            parseInt( that.currentItem.css( "paddingRight" ) || 0, 10 ) );
16111                    }
16112                }
16113            };
16114        }
16115
16116        //Create the placeholder
16117        that.placeholder = $( o.placeholder.element.call( that.element, that.currentItem ) );
16118
16119        //Append it after the actual current item
16120        that.currentItem.after( that.placeholder );
16121
16122        //Update the size of the placeholder (TODO: Logic to fuzzy, see line 316/317)
16123        o.placeholder.update( that, that.placeholder );
16124
16125    },
16126
16127    _createTrPlaceholder: function( sourceTr, targetTr ) {
16128        var that = this;
16129
16130        sourceTr.children().each( function() {
16131            $( "<td>&#160;</td>", that.document[ 0 ] )
16132                .attr( "colspan", $( this ).attr( "colspan" ) || 1 )
16133                .appendTo( targetTr );
16134        } );
16135    },
16136
16137    _contactContainers: function( event ) {
16138        var i, j, dist, itemWithLeastDistance, posProperty, sizeProperty, cur, nearBottom,
16139            floating, axis,
16140            innermostContainer = null,
16141            innermostIndex = null;
16142
16143        // Get innermost container that intersects with item
16144        for ( i = this.containers.length - 1; i >= 0; i-- ) {
16145
16146            // Never consider a container that's located within the item itself
16147            if ( $.contains( this.currentItem[ 0 ], this.containers[ i ].element[ 0 ] ) ) {
16148                continue;
16149            }
16150
16151            if ( this._intersectsWith( this.containers[ i ].containerCache ) ) {
16152
16153                // If we've already found a container and it's more "inner" than this, then continue
16154                if ( innermostContainer &&
16155                        $.contains(
16156                            this.containers[ i ].element[ 0 ],
16157                            innermostContainer.element[ 0 ] ) ) {
16158                    continue;
16159                }
16160
16161                innermostContainer = this.containers[ i ];
16162                innermostIndex = i;
16163
16164            } else {
16165
16166                // container doesn't intersect. trigger "out" event if necessary
16167                if ( this.containers[ i ].containerCache.over ) {
16168                    this.containers[ i ]._trigger( "out", event, this._uiHash( this ) );
16169                    this.containers[ i ].containerCache.over = 0;
16170                }
16171            }
16172
16173        }
16174
16175        // If no intersecting containers found, return
16176        if ( !innermostContainer ) {
16177            return;
16178        }
16179
16180        // Move the item into the container if it's not there already
16181        if ( this.containers.length === 1 ) {
16182            if ( !this.containers[ innermostIndex ].containerCache.over ) {
16183                this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash( this ) );
16184                this.containers[ innermostIndex ].containerCache.over = 1;
16185            }
16186        } else {
16187
16188            // When entering a new container, we will find the item with the least distance and
16189            // append our item near it
16190            dist = 10000;
16191            itemWithLeastDistance = null;
16192            floating = innermostContainer.floating || this._isFloating( this.currentItem );
16193            posProperty = floating ? "left" : "top";
16194            sizeProperty = floating ? "width" : "height";
16195            axis = floating ? "pageX" : "pageY";
16196
16197            for ( j = this.items.length - 1; j >= 0; j-- ) {
16198                if ( !$.contains(
16199                        this.containers[ innermostIndex ].element[ 0 ], this.items[ j ].item[ 0 ] )
16200                ) {
16201                    continue;
16202                }
16203                if ( this.items[ j ].item[ 0 ] === this.currentItem[ 0 ] ) {
16204                    continue;
16205                }
16206
16207                cur = this.items[ j ].item.offset()[ posProperty ];
16208                nearBottom = false;
vendor: 7,939 bytes, lines 16209-16400
16209                if ( event[ axis ] - cur > this.items[ j ][ sizeProperty ] / 2 ) {
16210                    nearBottom = true;
16211                }
16212
16213                if ( Math.abs( event[ axis ] - cur ) < dist ) {
16214                    dist = Math.abs( event[ axis ] - cur );
16215                    itemWithLeastDistance = this.items[ j ];
16216                    this.direction = nearBottom ? "up" : "down";
16217                }
16218            }
16219
16220            //Check if dropOnEmpty is enabled
16221            if ( !itemWithLeastDistance && !this.options.dropOnEmpty ) {
16222                return;
16223            }
16224
16225            if ( this.currentContainer === this.containers[ innermostIndex ] ) {
16226                if ( !this.currentContainer.containerCache.over ) {
16227                    this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash() );
16228                    this.currentContainer.containerCache.over = 1;
16229                }
16230                return;
16231            }
16232
16233            itemWithLeastDistance ?
16234                this._rearrange( event, itemWithLeastDistance, null, true ) :
16235                this._rearrange( event, null, this.containers[ innermostIndex ].element, true );
16236            this._trigger( "change", event, this._uiHash() );
16237            this.containers[ innermostIndex ]._trigger( "change", event, this._uiHash( this ) );
16238            this.currentContainer = this.containers[ innermostIndex ];
16239
16240            //Update the placeholder
16241            this.options.placeholder.update( this.currentContainer, this.placeholder );
16242
16243            this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash( this ) );
16244            this.containers[ innermostIndex ].containerCache.over = 1;
16245        }
16246
16247    },
16248
16249    _createHelper: function( event ) {
16250
16251        var o = this.options,
16252            helper = $.isFunction( o.helper ) ?
16253                $( o.helper.apply( this.element[ 0 ], [ event, this.currentItem ] ) ) :
16254                ( o.helper === "clone" ? this.currentItem.clone() : this.currentItem );
16255
16256        //Add the helper to the DOM if that didn't happen already
16257        if ( !helper.parents( "body" ).length ) {
16258            $( o.appendTo !== "parent" ?
16259                o.appendTo :
16260                this.currentItem[ 0 ].parentNode )[ 0 ].appendChild( helper[ 0 ] );
16261        }
16262
16263        if ( helper[ 0 ] === this.currentItem[ 0 ] ) {
16264            this._storedCSS = {
16265                width: this.currentItem[ 0 ].style.width,
16266                height: this.currentItem[ 0 ].style.height,
16267                position: this.currentItem.css( "position" ),
16268                top: this.currentItem.css( "top" ),
16269                left: this.currentItem.css( "left" )
16270            };
16271        }
16272
16273        if ( !helper[ 0 ].style.width || o.forceHelperSize ) {
16274            helper.width( this.currentItem.width() );
16275        }
16276        if ( !helper[ 0 ].style.height || o.forceHelperSize ) {
16277            helper.height( this.currentItem.height() );
16278        }
16279
16280        return helper;
16281
16282    },
16283
16284    _adjustOffsetFromHelper: function( obj ) {
16285        if ( typeof obj === "string" ) {
16286            obj = obj.split( " " );
16287        }
16288        if ( $.isArray( obj ) ) {
16289            obj = { left: +obj[ 0 ], top: +obj[ 1 ] || 0 };
16290        }
16291        if ( "left" in obj ) {
16292            this.offset.click.left = obj.left + this.margins.left;
16293        }
16294        if ( "right" in obj ) {
16295            this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
16296        }
16297        if ( "top" in obj ) {
16298            this.offset.click.top = obj.top + this.margins.top;
16299        }
16300        if ( "bottom" in obj ) {
16301            this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
16302        }
16303    },
16304
16305    _getParentOffset: function() {
16306
16307        //Get the offsetParent and cache its position
16308        this.offsetParent = this.helper.offsetParent();
16309        var po = this.offsetParent.offset();
16310
16311        // This is a special case where we need to modify a offset calculated on start, since the
16312        // following happened:
16313        // 1. The position of the helper is absolute, so it's position is calculated based on the
16314        // next positioned parent
16315        // 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't
16316        // the document, which means that the scroll is included in the initial calculation of the
16317        // offset of the parent, and never recalculated upon drag
16318        if ( this.cssPosition === "absolute" && this.scrollParent[ 0 ] !== this.document[ 0 ] &&
16319                $.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) {
16320            po.left += this.scrollParent.scrollLeft();
16321            po.top += this.scrollParent.scrollTop();
16322        }
16323
16324        // This needs to be actually done for all browsers, since pageX/pageY includes this
16325        // information with an ugly IE fix
16326        if ( this.offsetParent[ 0 ] === this.document[ 0 ].body ||
16327                ( this.offsetParent[ 0 ].tagName &&
16328                this.offsetParent[ 0 ].tagName.toLowerCase() === "html" && $.ui.ie ) ) {
16329            po = { top: 0, left: 0 };
16330        }
16331
16332        return {
16333            top: po.top + ( parseInt( this.offsetParent.css( "borderTopWidth" ), 10 ) || 0 ),
16334            left: po.left + ( parseInt( this.offsetParent.css( "borderLeftWidth" ), 10 ) || 0 )
16335        };
16336
16337    },
16338
16339    _getRelativeOffset: function() {
16340
16341        if ( this.cssPosition === "relative" ) {
16342            var p = this.currentItem.position();
16343            return {
16344                top: p.top - ( parseInt( this.helper.css( "top" ), 10 ) || 0 ) +
16345                    this.scrollParent.scrollTop(),
16346                left: p.left - ( parseInt( this.helper.css( "left" ), 10 ) || 0 ) +
16347                    this.scrollParent.scrollLeft()
16348            };
16349        } else {
16350            return { top: 0, left: 0 };
16351        }
16352
16353    },
16354
16355    _cacheMargins: function() {
16356        this.margins = {
16357            left: ( parseInt( this.currentItem.css( "marginLeft" ), 10 ) || 0 ),
16358            top: ( parseInt( this.currentItem.css( "marginTop" ), 10 ) || 0 )
16359        };
16360    },
16361
16362    _cacheHelperProportions: function() {
16363        this.helperProportions = {
16364            width: this.helper.outerWidth(),
16365            height: this.helper.outerHeight()
16366        };
16367    },
16368
16369    _setContainment: function() {
16370
16371        var ce, co, over,
16372            o = this.options;
16373        if ( o.containment === "parent" ) {
16374            o.containment = this.helper[ 0 ].parentNode;
16375        }
16376        if ( o.containment === "document" || o.containment === "window" ) {
16377            this.containment = [
16378                0 - this.offset.relative.left - this.offset.parent.left,
16379                0 - this.offset.relative.top - this.offset.parent.top,
16380                o.containment === "document" ?
16381                    this.document.width() :
16382                    this.window.width() - this.helperProportions.width - this.margins.left,
16383                ( o.containment === "document" ?
16384                    ( this.document.height() || document.body.parentNode.scrollHeight ) :
16385                    this.window.height() || this.document[ 0 ].body.parentNode.scrollHeight
16386                ) - this.helperProportions.height - this.margins.top
16387            ];
16388        }
16389
16390        if ( !( /^(document|window|parent)$/ ).test( o.containment ) ) {
16391            ce = $( o.containment )[ 0 ];
16392            co = $( o.containment ).offset();
16393            over = ( $( ce ).css( "overflow" ) !== "hidden" );
16394
16395            this.containment = [
16396                co.left + ( parseInt( $( ce ).css( "borderLeftWidth" ), 10 ) || 0 ) +
16397                    ( parseInt( $( ce ).css( "paddingLeft" ), 10 ) || 0 ) - this.margins.left,
16398                co.top + ( parseInt( $( ce ).css( "borderTopWidth" ), 10 ) || 0 ) +
16399                    ( parseInt( $( ce ).css( "paddingTop" ), 10 ) || 0 ) - this.margins.top,
16400                co.left + ( over ? Math.max( ce.scrollWidth, ce.offsetWidth ) 
vendor: 8,049 bytes, lines 16400-16593
16400: ce.offsetWidth ) -
16401                    ( parseInt( $( ce ).css( "borderLeftWidth" ), 10 ) || 0 ) -
16402                    ( parseInt( $( ce ).css( "paddingRight" ), 10 ) || 0 ) -
16403                    this.helperProportions.width - this.margins.left,
16404                co.top + ( over ? Math.max( ce.scrollHeight, ce.offsetHeight ) : ce.offsetHeight ) -
16405                    ( parseInt( $( ce ).css( "borderTopWidth" ), 10 ) || 0 ) -
16406                    ( parseInt( $( ce ).css( "paddingBottom" ), 10 ) || 0 ) -
16407                    this.helperProportions.height - this.margins.top
16408            ];
16409        }
16410
16411    },
16412
16413    _convertPositionTo: function( d, pos ) {
16414
16415        if ( !pos ) {
16416            pos = this.position;
16417        }
16418        var mod = d === "absolute" ? 1 : -1,
16419            scroll = this.cssPosition === "absolute" &&
16420                !( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
16421                $.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) ?
16422                    this.offsetParent :
16423                    this.scrollParent,
16424            scrollIsRootNode = ( /(html|body)/i ).test( scroll[ 0 ].tagName );
16425
16426        return {
16427            top: (
16428
16429                // The absolute mouse position
16430                pos.top +
16431
16432                // Only for relative positioned nodes: Relative offset from element to offset parent
16433                this.offset.relative.top * mod +
16434
16435                // The offsetParent's offset without borders (offset + border)
16436                this.offset.parent.top * mod -
16437                ( ( this.cssPosition === "fixed" ?
16438                    -this.scrollParent.scrollTop() :
16439                    ( scrollIsRootNode ? 0 : scroll.scrollTop() ) ) * mod )
16440            ),
16441            left: (
16442
16443                // The absolute mouse position
16444                pos.left +
16445
16446                // Only for relative positioned nodes: Relative offset from element to offset parent
16447                this.offset.relative.left * mod +
16448
16449                // The offsetParent's offset without borders (offset + border)
16450                this.offset.parent.left * mod   -
16451                ( ( this.cssPosition === "fixed" ?
16452                    -this.scrollParent.scrollLeft() : scrollIsRootNode ? 0 :
16453                    scroll.scrollLeft() ) * mod )
16454            )
16455        };
16456
16457    },
16458
16459    _generatePosition: function( event ) {
16460
16461        var top, left,
16462            o = this.options,
16463            pageX = event.pageX,
16464            pageY = event.pageY,
16465            scroll = this.cssPosition === "absolute" &&
16466                !( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
16467                $.contains( this.scrollParent[ 0 ], this.offsetParent[ 0 ] ) ) ?
16468                    this.offsetParent :
16469                    this.scrollParent,
16470                scrollIsRootNode = ( /(html|body)/i ).test( scroll[ 0 ].tagName );
16471
16472        // This is another very weird special case that only happens for relative elements:
16473        // 1. If the css position is relative
16474        // 2. and the scroll parent is the document or similar to the offset parent
16475        // we have to refresh the relative offset during the scroll so there are no jumps
16476        if ( this.cssPosition === "relative" && !( this.scrollParent[ 0 ] !== this.document[ 0 ] &&
16477                this.scrollParent[ 0 ] !== this.offsetParent[ 0 ] ) ) {
16478            this.offset.relative = this._getRelativeOffset();
16479        }
16480
16481        /*
16482         * - Position constraining -
16483         * Constrain the position to a mix of grid, containment.
16484         */
16485
16486        if ( this.originalPosition ) { //If we are not dragging yet, we won't check for options
16487
16488            if ( this.containment ) {
16489                if ( event.pageX - this.offset.click.left < this.containment[ 0 ] ) {
16490                    pageX = this.containment[ 0 ] + this.offset.click.left;
16491                }
16492                if ( event.pageY - this.offset.click.top < this.containment[ 1 ] ) {
16493                    pageY = this.containment[ 1 ] + this.offset.click.top;
16494                }
16495                if ( event.pageX - this.offset.click.left > this.containment[ 2 ] ) {
16496                    pageX = this.containment[ 2 ] + this.offset.click.left;
16497                }
16498                if ( event.pageY - this.offset.click.top > this.containment[ 3 ] ) {
16499                    pageY = this.containment[ 3 ] + this.offset.click.top;
16500                }
16501            }
16502
16503            if ( o.grid ) {
16504                top = this.originalPageY + Math.round( ( pageY - this.originalPageY ) /
16505                    o.grid[ 1 ] ) * o.grid[ 1 ];
16506                pageY = this.containment ?
16507                    ( ( top - this.offset.click.top >= this.containment[ 1 ] &&
16508                        top - this.offset.click.top <= this.containment[ 3 ] ) ?
16509                            top :
16510                            ( ( top - this.offset.click.top >= this.containment[ 1 ] ) ?
16511                                top - o.grid[ 1 ] : top + o.grid[ 1 ] ) ) :
16512                                top;
16513
16514                left = this.originalPageX + Math.round( ( pageX - this.originalPageX ) /
16515                    o.grid[ 0 ] ) * o.grid[ 0 ];
16516                pageX = this.containment ?
16517                    ( ( left - this.offset.click.left >= this.containment[ 0 ] &&
16518                        left - this.offset.click.left <= this.containment[ 2 ] ) ?
16519                            left :
16520                            ( ( left - this.offset.click.left >= this.containment[ 0 ] ) ?
16521                                left - o.grid[ 0 ] : left + o.grid[ 0 ] ) ) :
16522                                left;
16523            }
16524
16525        }
16526
16527        return {
16528            top: (
16529
16530                // The absolute mouse position
16531                pageY -
16532
16533                // Click offset (relative to the element)
16534                this.offset.click.top -
16535
16536                // Only for relative positioned nodes: Relative offset from element to offset parent
16537                this.offset.relative.top -
16538
16539                // The offsetParent's offset without borders (offset + border)
16540                this.offset.parent.top +
16541                ( ( this.cssPosition === "fixed" ?
16542                    -this.scrollParent.scrollTop() :
16543                    ( scrollIsRootNode ? 0 : scroll.scrollTop() ) ) )
16544            ),
16545            left: (
16546
16547                // The absolute mouse position
16548                pageX -
16549
16550                // Click offset (relative to the element)
16551                this.offset.click.left -
16552
16553                // Only for relative positioned nodes: Relative offset from element to offset parent
16554                this.offset.relative.left -
16555
16556                // The offsetParent's offset without borders (offset + border)
16557                this.offset.parent.left +
16558                ( ( this.cssPosition === "fixed" ?
16559                    -this.scrollParent.scrollLeft() :
16560                    scrollIsRootNode ? 0 : scroll.scrollLeft() ) )
16561            )
16562        };
16563
16564    },
16565
16566    _rearrange: function( event, i, a, hardRefresh ) {
16567
16568        a ? a[ 0 ].appendChild( this.placeholder[ 0 ] ) :
16569            i.item[ 0 ].parentNode.insertBefore( this.placeholder[ 0 ],
16570                ( this.direction === "down" ? i.item[ 0 ] : i.item[ 0 ].nextSibling ) );
16571
16572        //Various things done here to improve the performance:
16573        // 1. we create a setTimeout, that calls refreshPositions
16574        // 2. on the instance, we have a counter variable, that get's higher after every append
16575        // 3. on the local scope, we copy the counter variable, and check in the timeout,
16576        // if it's still the same
16577        // 4. this lets only the last addition to the timeout stack through
16578        this.counter = this.counter ? ++this.counter : 1;
16579        var counter = this.counter;
16580
16581        this._delay( function() {
16582            if ( counter === this.counter ) {
16583
16584                //Precompute after each DOM insertion, NOT on mousemove
16585                this.refreshPositions( !hardRefresh );
16586            }
16587        } );
16588
16589    },
16590
16591    _clear: function( event, noPropagation ) {
16592
16593        this.reverting = false;
vendor: 14,486 bytes, lines 16594-17017
16594
16595        // We delay all events that have to be triggered to after the point where the placeholder
16596        // has been removed and everything else normalized again
16597        var i,
16598            delayedTriggers = [];
16599
16600        // We first have to update the dom position of the actual currentItem
16601        // Note: don't do it if the current item is already removed (by a user), or it gets
16602        // reappended (see #4088)
16603        if ( !this._noFinalSort && this.currentItem.parent().length ) {
16604            this.placeholder.before( this.currentItem );
16605        }
16606        this._noFinalSort = null;
16607
16608        if ( this.helper[ 0 ] === this.currentItem[ 0 ] ) {
16609            for ( i in this._storedCSS ) {
16610                if ( this._storedCSS[ i ] === "auto" || this._storedCSS[ i ] === "static" ) {
16611                    this._storedCSS[ i ] = "";
16612                }
16613            }
16614            this.currentItem.css( this._storedCSS );
16615            this._removeClass( this.currentItem, "ui-sortable-helper" );
16616        } else {
16617            this.currentItem.show();
16618        }
16619
16620        if ( this.fromOutside && !noPropagation ) {
16621            delayedTriggers.push( function( event ) {
16622                this._trigger( "receive", event, this._uiHash( this.fromOutside ) );
16623            } );
16624        }
16625        if ( ( this.fromOutside ||
16626                this.domPosition.prev !==
16627                this.currentItem.prev().not( ".ui-sortable-helper" )[ 0 ] ||
16628                this.domPosition.parent !== this.currentItem.parent()[ 0 ] ) && !noPropagation ) {
16629
16630            // Trigger update callback if the DOM position has changed
16631            delayedTriggers.push( function( event ) {
16632                this._trigger( "update", event, this._uiHash() );
16633            } );
16634        }
16635
16636        // Check if the items Container has Changed and trigger appropriate
16637        // events.
16638        if ( this !== this.currentContainer ) {
16639            if ( !noPropagation ) {
16640                delayedTriggers.push( function( event ) {
16641                    this._trigger( "remove", event, this._uiHash() );
16642                } );
16643                delayedTriggers.push( ( function( c ) {
16644                    return function( event ) {
16645                        c._trigger( "receive", event, this._uiHash( this ) );
16646                    };
16647                } ).call( this, this.currentContainer ) );
16648                delayedTriggers.push( ( function( c ) {
16649                    return function( event ) {
16650                        c._trigger( "update", event, this._uiHash( this ) );
16651                    };
16652                } ).call( this, this.currentContainer ) );
16653            }
16654        }
16655
16656        //Post events to containers
16657        function delayEvent( type, instance, container ) {
16658            return function( event ) {
16659                container._trigger( type, event, instance._uiHash( instance ) );
16660            };
16661        }
16662        for ( i = this.containers.length - 1; i >= 0; i-- ) {
16663            if ( !noPropagation ) {
16664                delayedTriggers.push( delayEvent( "deactivate", this, this.containers[ i ] ) );
16665            }
16666            if ( this.containers[ i ].containerCache.over ) {
16667                delayedTriggers.push( delayEvent( "out", this, this.containers[ i ] ) );
16668                this.containers[ i ].containerCache.over = 0;
16669            }
16670        }
16671
16672        //Do what was originally in plugins
16673        if ( this.storedCursor ) {
16674            this.document.find( "body" ).css( "cursor", this.storedCursor );
16675            this.storedStylesheet.remove();
16676        }
16677        if ( this._storedOpacity ) {
16678            this.helper.css( "opacity", this._storedOpacity );
16679        }
16680        if ( this._storedZIndex ) {
16681            this.helper.css( "zIndex", this._storedZIndex === "auto" ? "" : this._storedZIndex );
16682        }
16683
16684        this.dragging = false;
16685
16686        if ( !noPropagation ) {
16687            this._trigger( "beforeStop", event, this._uiHash() );
16688        }
16689
16690        //$(this.placeholder[0]).remove(); would have been the jQuery way - unfortunately,
16691        // it unbinds ALL events from the original node!
16692        this.placeholder[ 0 ].parentNode.removeChild( this.placeholder[ 0 ] );
16693
16694        if ( !this.cancelHelperRemoval ) {
16695            if ( this.helper[ 0 ] !== this.currentItem[ 0 ] ) {
16696                this.helper.remove();
16697            }
16698            this.helper = null;
16699        }
16700
16701        if ( !noPropagation ) {
16702            for ( i = 0; i < delayedTriggers.length; i++ ) {
16703
16704                // Trigger all delayed events
16705                delayedTriggers[ i ].call( this, event );
16706            }
16707            this._trigger( "stop", event, this._uiHash() );
16708        }
16709
16710        this.fromOutside = false;
16711        return !this.cancelHelperRemoval;
16712
16713    },
16714
16715    _trigger: function() {
16716        if ( $.Widget.prototype._trigger.apply( this, arguments ) === false ) {
16717            this.cancel();
16718        }
16719    },
16720
16721    _uiHash: function( _inst ) {
16722        var inst = _inst || this;
16723        return {
16724            helper: inst.helper,
16725            placeholder: inst.placeholder || $( [] ),
16726            position: inst.position,
16727            originalPosition: inst.originalPosition,
16728            offset: inst.positionAbs,
16729            item: inst.currentItem,
16730            sender: _inst ? _inst.element : null
16731        };
16732    }
16733
16734} );
16735
16736
16737/*!
16738 * jQuery UI Spinner 1.12.1
16739 * http://jqueryui.com
16740 *
16741 * Copyright jQuery Foundation and other contributors
16742 * Released under the MIT license.
16743 * http://jquery.org/license
16744 */
16745
16746//>>label: Spinner
16747//>>group: Widgets
16748//>>description: Displays buttons to easily input numbers via the keyboard or mouse.
16749//>>docs: http://api.jqueryui.com/spinner/
16750//>>demos: http://jqueryui.com/spinner/
16751//>>css.structure: ../../themes/base/core.css
16752//>>css.structure: ../../themes/base/spinner.css
16753//>>css.theme: ../../themes/base/theme.css
16754
16755
16756
16757function spinnerModifer( fn ) {
16758    return function() {
16759        var previous = this.element.val();
16760        fn.apply( this, arguments );
16761        this._refresh();
16762        if ( previous !== this.element.val() ) {
16763            this._trigger( "change" );
16764        }
16765    };
16766}
16767
16768$.widget( "ui.spinner", {
16769    version: "1.12.1",
16770    defaultElement: "<input>",
16771    widgetEventPrefix: "spin",
16772    options: {
16773        classes: {
16774            "ui-spinner": "ui-corner-all",
16775            "ui-spinner-down": "ui-corner-br",
16776            "ui-spinner-up": "ui-corner-tr"
16777        },
16778        culture: null,
16779        icons: {
16780            down: "ui-icon-triangle-1-s",
16781            up: "ui-icon-triangle-1-n"
16782        },
16783        incremental: true,
16784        max: null,
16785        min: null,
16786        numberFormat: null,
16787        page: 10,
16788        step: 1,
16789
16790        change: null,
16791        spin: null,
16792        start: null,
16793        stop: null
16794    },
16795
16796    _create: function() {
16797
16798        // handle string values that need to be parsed
16799        this._setOption( "max", this.options.max );
16800        this._setOption( "min", this.options.min );
16801        this._setOption( "step", this.options.step );
16802
16803        // Only format if there is a value, prevents the field from being marked
16804        // as invalid in Firefox, see #9573.
16805        if ( this.value() !== "" ) {
16806
16807            // Format the value, but don't constrain.
16808            this._value( this.element.val(), true );
16809        }
16810
16811        this._draw();
16812        this._on( this._events );
16813        this._refresh();
16814
16815        // Turning off autocomplete prevents the browser from remembering the
16816        // value when navigating through history, so we re-enable autocomplete
16817        // if the page is unloaded before the widget is destroyed. #7790
16818        this._on( this.window, {
16819            beforeunload: function() {
16820                this.element.removeAttr( "autocomplete" );
16821            }
16822        } );
16823    },
16824
16825    _getCreateOptions: function() {
16826        var options = this._super();
16827        var element = this.element;
16828
16829        $.each( [ "min", "max", "step" ], function( i, option ) {
16830            var value = element.attr( option );
16831            if ( value != null && value.length ) {
16832                options[ option ] = value;
16833            }
16834        } );
16835
16836        return options;
16837    },
16838
16839    _events: {
16840        keydown: function( event ) {
16841            if ( this._start( event ) && this._keydown( event ) ) {
16842                event.preventDefault();
16843            }
16844        },
16845        keyup: "_stop",
16846        focus: function() {
16847            this.previous = this.element.val();
16848        },
16849        blur: function( event ) {
16850            if ( this.cancelBlur ) {
16851                delete this.cancelBlur;
16852                return;
16853            }
16854
16855            this._stop();
16856            this._refresh();
16857            if ( this.previous !== this.element.val() ) {
16858                this._trigger( "change", event );
16859            }
16860        },
16861        mousewheel: function( event, delta ) {
16862            if ( !delta ) {
16863                return;
16864            }
16865            if ( !this.spinning && !this._start( event ) ) {
16866                return false;
16867            }
16868
16869            this._spin( ( delta > 0 ? 1 : -1 ) * this.options.step, event );
16870            clearTimeout( this.mousewheelTimer );
16871            this.mousewheelTimer = this._delay( function() {
16872                if ( this.spinning ) {
16873                    this._stop( event );
16874                }
16875            }, 100 );
16876            event.preventDefault();
16877        },
16878        "mousedown .ui-spinner-button": function( event ) {
16879            var previous;
16880
16881            // We never want the buttons to have focus; whenever the user is
16882            // interacting with the spinner, the focus should be on the input.
16883            // If the input is focused then this.previous is properly set from
16884            // when the input first received focus. If the input is not focused
16885            // then we need to set this.previous based on the value before spinning.
16886            previous = this.element[ 0 ] === $.ui.safeActiveElement( this.document[ 0 ] ) ?
16887                this.previous : this.element.val();
16888            function checkFocus() {
16889                var isActive = this.element[ 0 ] === $.ui.safeActiveElement( this.document[ 0 ] );
16890                if ( !isActive ) {
16891                    this.element.trigger( "focus" );
16892                    this.previous = previous;
16893
16894                    // support: IE
16895                    // IE sets focus asynchronously, so we need to check if focus
16896                    // moved off of the input because the user clicked on the button.
16897                    this._delay( function() {
16898                        this.previous = previous;
16899                    } );
16900                }
16901            }
16902
16903            // Ensure focus is on (or stays on) the text field
16904            event.preventDefault();
16905            checkFocus.call( this );
16906
16907            // Support: IE
16908            // IE doesn't prevent moving focus even with event.preventDefault()
16909            // so we set a flag to know when we should ignore the blur event
16910            // and check (again) if focus moved off of the input.
16911            this.cancelBlur = true;
16912            this._delay( function() {
16913                delete this.cancelBlur;
16914                checkFocus.call( this );
16915            } );
16916
16917            if ( this._start( event ) === false ) {
16918                return;
16919            }
16920
16921            this._repeat( null, $( event.currentTarget )
16922                .hasClass( "ui-spinner-up" ) ? 1 : -1, event );
16923        },
16924        "mouseup .ui-spinner-button": "_stop",
16925        "mouseenter .ui-spinner-button": function( event ) {
16926
16927            // button will add ui-state-active if mouse was down while mouseleave and kept down
16928            if ( !$( event.currentTarget ).hasClass( "ui-state-active" ) ) {
16929                return;
16930            }
16931
16932            if ( this._start( event ) === false ) {
16933                return false;
16934            }
16935            this._repeat( null, $( event.currentTarget )
16936                .hasClass( "ui-spinner-up" ) ? 1 : -1, event );
16937        },
16938
16939        // TODO: do we really want to consider this a stop?
16940        // shouldn't we just stop the repeater and wait until mouseup before
16941        // we trigger the stop event?
16942        "mouseleave .ui-spinner-button": "_stop"
16943    },
16944
16945    // Support mobile enhanced option and make backcompat more sane
16946    _enhance: function() {
16947        this.uiSpinner = this.element
16948            .attr( "autocomplete", "off" )
16949            .wrap( "<span>" )
16950            .parent()
16951
16952                // Add buttons
16953                .append(
16954                    "<a></a><a></a>"
16955                );
16956    },
16957
16958    _draw: function() {
16959        this._enhance();
16960
16961        this._addClass( this.uiSpinner, "ui-spinner", "ui-widget ui-widget-content" );
16962        this._addClass( "ui-spinner-input" );
16963
16964        this.element.attr( "role", "spinbutton" );
16965
16966        // Button bindings
16967        this.buttons = this.uiSpinner.children( "a" )
16968            .attr( "tabIndex", -1 )
16969            .attr( "aria-hidden", true )
16970            .button( {
16971                classes: {
16972                    "ui-button": ""
16973                }
16974            } );
16975
16976        // TODO: Right now button does not support classes this is already updated in button PR
16977        this._removeClass( this.buttons, "ui-corner-all" );
16978
16979        this._addClass( this.buttons.first(), "ui-spinner-button ui-spinner-up" );
16980        this._addClass( this.buttons.last(), "ui-spinner-button ui-spinner-down" );
16981        this.buttons.first().button( {
16982            "icon": this.options.icons.up,
16983            "showLabel": false
16984        } );
16985        this.buttons.last().button( {
16986            "icon": this.options.icons.down,
16987            "showLabel": false
16988        } );
16989
16990        // IE 6 doesn't understand height: 50% for the buttons
16991        // unless the wrapper has an explicit height
16992        if ( this.buttons.height() > Math.ceil( this.uiSpinner.height() * 0.5 ) &&
16993                this.uiSpinner.height() > 0 ) {
16994            this.uiSpinner.height( this.uiSpinner.height() );
16995        }
16996    },
16997
16998    _keydown: function( event ) {
16999        var options = this.options,
17000            keyCode = $.ui.keyCode;
17001
17002        switch ( event.keyCode ) {
17003        case keyCode.UP:
17004            this._repeat( null, 1, event );
17005            return true;
17006        case keyCode.DOWN:
17007            this._repeat( null, -1, event );
17008            return true;
17009        case keyCode.PAGE_UP:
17010            this._repeat( null, options.page, event );
17011            return true;
17012        case keyCode.PAGE_DOWN:
17013            this._repeat( null, -options.page, event );
17014            return true;
17015        }
17016
17017        return false;
vendor: 5,200 bytes, lines 17018-17193
17018    },
17019
17020    _start: function( event ) {
17021        if ( !this.spinning && this._trigger( "start", event ) === false ) {
17022            return false;
17023        }
17024
17025        if ( !this.counter ) {
17026            this.counter = 1;
17027        }
17028        this.spinning = true;
17029        return true;
17030    },
17031
17032    _repeat: function( i, steps, event ) {
17033        i = i || 500;
17034
17035        clearTimeout( this.timer );
17036        this.timer = this._delay( function() {
17037            this._repeat( 40, steps, event );
17038        }, i );
17039
17040        this._spin( steps * this.options.step, event );
17041    },
17042
17043    _spin: function( step, event ) {
17044        var value = this.value() || 0;
17045
17046        if ( !this.counter ) {
17047            this.counter = 1;
17048        }
17049
17050        value = this._adjustValue( value + step * this._increment( this.counter ) );
17051
17052        if ( !this.spinning || this._trigger( "spin", event, { value: value } ) !== false ) {
17053            this._value( value );
17054            this.counter++;
17055        }
17056    },
17057
17058    _increment: function( i ) {
17059        var incremental = this.options.incremental;
17060
17061        if ( incremental ) {
17062            return $.isFunction( incremental ) ?
17063                incremental( i ) :
17064                Math.floor( i * i * i / 50000 - i * i / 500 + 17 * i / 200 + 1 );
17065        }
17066
17067        return 1;
17068    },
17069
17070    _precision: function() {
17071        var precision = this._precisionOf( this.options.step );
17072        if ( this.options.min !== null ) {
17073            precision = Math.max( precision, this._precisionOf( this.options.min ) );
17074        }
17075        return precision;
17076    },
17077
17078    _precisionOf: function( num ) {
17079        var str = num.toString(),
17080            decimal = str.indexOf( "." );
17081        return decimal === -1 ? 0 : str.length - decimal - 1;
17082    },
17083
17084    _adjustValue: function( value ) {
17085        var base, aboveMin,
17086            options = this.options;
17087
17088        // Make sure we're at a valid step
17089        // - find out where we are relative to the base (min or 0)
17090        base = options.min !== null ? options.min : 0;
17091        aboveMin = value - base;
17092
17093        // - round to the nearest step
17094        aboveMin = Math.round( aboveMin / options.step ) * options.step;
17095
17096        // - rounding is based on 0, so adjust back to our base
17097        value = base + aboveMin;
17098
17099        // Fix precision from bad JS floating point math
17100        value = parseFloat( value.toFixed( this._precision() ) );
17101
17102        // Clamp the value
17103        if ( options.max !== null && value > options.max ) {
17104            return options.max;
17105        }
17106        if ( options.min !== null && value < options.min ) {
17107            return options.min;
17108        }
17109
17110        return value;
17111    },
17112
17113    _stop: function( event ) {
17114        if ( !this.spinning ) {
17115            return;
17116        }
17117
17118        clearTimeout( this.timer );
17119        clearTimeout( this.mousewheelTimer );
17120        this.counter = 0;
17121        this.spinning = false;
17122        this._trigger( "stop", event );
17123    },
17124
17125    _setOption: function( key, value ) {
17126        var prevValue, first, last;
17127
17128        if ( key === "culture" || key === "numberFormat" ) {
17129            prevValue = this._parse( this.element.val() );
17130            this.options[ key ] = value;
17131            this.element.val( this._format( prevValue ) );
17132            return;
17133        }
17134
17135        if ( key === "max" || key === "min" || key === "step" ) {
17136            if ( typeof value === "string" ) {
17137                value = this._parse( value );
17138            }
17139        }
17140        if ( key === "icons" ) {
17141            first = this.buttons.first().find( ".ui-icon" );
17142            this._removeClass( first, null, this.options.icons.up );
17143            this._addClass( first, null, value.up );
17144            last = this.buttons.last().find( ".ui-icon" );
17145            this._removeClass( last, null, this.options.icons.down );
17146            this._addClass( last, null, value.down );
17147        }
17148
17149        this._super( key, value );
17150    },
17151
17152    _setOptionDisabled: function( value ) {
17153        this._super( value );
17154
17155        this._toggleClass( this.uiSpinner, null, "ui-state-disabled", !!value );
17156        this.element.prop( "disabled", !!value );
17157        this.buttons.button( value ? "disable" : "enable" );
17158    },
17159
17160    _setOptions: spinnerModifer( function( options ) {
17161        this._super( options );
17162    } ),
17163
17164    _parse: function( val ) {
17165        if ( typeof val === "string" && val !== "" ) {
17166            val = window.Globalize && this.options.numberFormat ?
17167                Globalize.parseFloat( val, 10, this.options.culture ) : +val;
17168        }
17169        return val === "" || isNaN( val ) ? null : val;
17170    },
17171
17172    _format: function( value ) {
17173        if ( value === "" ) {
17174            return "";
17175        }
17176        return window.Globalize && this.options.numberFormat ?
17177            Globalize.format( value, this.options.numberFormat, this.options.culture ) :
17178            value;
17179    },
17180
17181    _refresh: function() {
17182        this.element.attr( {
17183            "aria-valuemin": this.options.min,
17184            "aria-valuemax": this.options.max,
17185
17186            // TODO: what should we do with values that can't be parsed?
17187            "aria-valuenow": this._parse( this.element.val() )
17188        } );
17189    },
17190
17191    isValid: function() {
17192        var value = this.value();
17193
vendor: 12,443 bytes, lines 17194-17608
17194        // Null is invalid
17195        if ( value === null ) {
17196            return false;
17197        }
17198
17199        // If value gets adjusted, it's invalid
17200        return value === this._adjustValue( value );
17201    },
17202
17203    // Update the value without triggering change
17204    _value: function( value, allowAny ) {
17205        var parsed;
17206        if ( value !== "" ) {
17207            parsed = this._parse( value );
17208            if ( parsed !== null ) {
17209                if ( !allowAny ) {
17210                    parsed = this._adjustValue( parsed );
17211                }
17212                value = this._format( parsed );
17213            }
17214        }
17215        this.element.val( value );
17216        this._refresh();
17217    },
17218
17219    _destroy: function() {
17220        this.element
17221            .prop( "disabled", false )
17222            .removeAttr( "autocomplete role aria-valuemin aria-valuemax aria-valuenow" );
17223
17224        this.uiSpinner.replaceWith( this.element );
17225    },
17226
17227    stepUp: spinnerModifer( function( steps ) {
17228        this._stepUp( steps );
17229    } ),
17230    _stepUp: function( steps ) {
17231        if ( this._start() ) {
17232            this._spin( ( steps || 1 ) * this.options.step );
17233            this._stop();
17234        }
17235    },
17236
17237    stepDown: spinnerModifer( function( steps ) {
17238        this._stepDown( steps );
17239    } ),
17240    _stepDown: function( steps ) {
17241        if ( this._start() ) {
17242            this._spin( ( steps || 1 ) * -this.options.step );
17243            this._stop();
17244        }
17245    },
17246
17247    pageUp: spinnerModifer( function( pages ) {
17248        this._stepUp( ( pages || 1 ) * this.options.page );
17249    } ),
17250
17251    pageDown: spinnerModifer( function( pages ) {
17252        this._stepDown( ( pages || 1 ) * this.options.page );
17253    } ),
17254
17255    value: function( newVal ) {
17256        if ( !arguments.length ) {
17257            return this._parse( this.element.val() );
17258        }
17259        spinnerModifer( this._value ).call( this, newVal );
17260    },
17261
17262    widget: function() {
17263        return this.uiSpinner;
17264    }
17265} );
17266
17267// DEPRECATED
17268// TODO: switch return back to widget declaration at top of file when this is removed
17269if ( $.uiBackCompat !== false ) {
17270
17271    // Backcompat for spinner html extension points
17272    $.widget( "ui.spinner", $.ui.spinner, {
17273        _enhance: function() {
17274            this.uiSpinner = this.element
17275                .attr( "autocomplete", "off" )
17276                .wrap( this._uiSpinnerHtml() )
17277                .parent()
17278
17279                    // Add buttons
17280                    .append( this._buttonHtml() );
17281        },
17282        _uiSpinnerHtml: function() {
17283            return "<span>";
17284        },
17285
17286        _buttonHtml: function() {
17287            return "<a></a><a></a>";
17288        }
17289    } );
17290}
17291
17292var widgetsSpinner = $.ui.spinner;
17293
17294
17295/*!
17296 * jQuery UI Tabs 1.12.1
17297 * http://jqueryui.com
17298 *
17299 * Copyright jQuery Foundation and other contributors
17300 * Released under the MIT license.
17301 * http://jquery.org/license
17302 */
17303
17304//>>label: Tabs
17305//>>group: Widgets
17306//>>description: Transforms a set of container elements into a tab structure.
17307//>>docs: http://api.jqueryui.com/tabs/
17308//>>demos: http://jqueryui.com/tabs/
17309//>>css.structure: ../../themes/base/core.css
17310//>>css.structure: ../../themes/base/tabs.css
17311//>>css.theme: ../../themes/base/theme.css
17312
17313
17314
17315$.widget( "ui.tabs", {
17316    version: "1.12.1",
17317    delay: 300,
17318    options: {
17319        active: null,
17320        classes: {
17321            "ui-tabs": "ui-corner-all",
17322            "ui-tabs-nav": "ui-corner-all",
17323            "ui-tabs-panel": "ui-corner-bottom",
17324            "ui-tabs-tab": "ui-corner-top"
17325        },
17326        collapsible: false,
17327        event: "click",
17328        heightStyle: "content",
17329        hide: null,
17330        show: null,
17331
17332        // Callbacks
17333        activate: null,
17334        beforeActivate: null,
17335        beforeLoad: null,
17336        load: null
17337    },
17338
17339    _isLocal: ( function() {
17340        var rhash = /#.*$/;
17341
17342        return function( anchor ) {
17343            var anchorUrl, locationUrl;
17344
17345            anchorUrl = anchor.href.replace( rhash, "" );
17346            locationUrl = location.href.replace( rhash, "" );
17347
17348            // Decoding may throw an error if the URL isn't UTF-8 (#9518)
17349            try {
17350                anchorUrl = decodeURIComponent( anchorUrl );
17351            } catch ( error ) {}
17352            try {
17353                locationUrl = decodeURIComponent( locationUrl );
17354            } catch ( error ) {}
17355
17356            return anchor.hash.length > 1 && anchorUrl === locationUrl;
17357        };
17358    } )(),
17359
17360    _create: function() {
17361        var that = this,
17362            options = this.options;
17363
17364        this.running = false;
17365
17366        this._addClass( "ui-tabs", "ui-widget ui-widget-content" );
17367        this._toggleClass( "ui-tabs-collapsible", null, options.collapsible );
17368
17369        this._processTabs();
17370        options.active = this._initialActive();
17371
17372        // Take disabling tabs via class attribute from HTML
17373        // into account and update option properly.
17374        if ( $.isArray( options.disabled ) ) {
17375            options.disabled = $.unique( options.disabled.concat(
17376                $.map( this.tabs.filter( ".ui-state-disabled" ), function( li ) {
17377                    return that.tabs.index( li );
17378                } )
17379            ) ).sort();
17380        }
17381
17382        // Check for length avoids error when initializing empty list
17383        if ( this.options.active !== false && this.anchors.length ) {
17384            this.active = this._findActive( options.active );
17385        } else {
17386            this.active = $();
17387        }
17388
17389        this._refresh();
17390
17391        if ( this.active.length ) {
17392            this.load( options.active );
17393        }
17394    },
17395
17396    _initialActive: function() {
17397        var active = this.options.active,
17398            collapsible = this.options.collapsible,
17399            locationHash = location.hash.substring( 1 );
17400
17401        if ( active === null ) {
17402
17403            // check the fragment identifier in the URL
17404            if ( locationHash ) {
17405                this.tabs.each( function( i, tab ) {
17406                    if ( $( tab ).attr( "aria-controls" ) === locationHash ) {
17407                        active = i;
17408                        return false;
17409                    }
17410                } );
17411            }
17412
17413            // Check for a tab marked active via a class
17414            if ( active === null ) {
17415                active = this.tabs.index( this.tabs.filter( ".ui-tabs-active" ) );
17416            }
17417
17418            // No active tab, set to false
17419            if ( active === null || active === -1 ) {
17420                active = this.tabs.length ? 0 : false;
17421            }
17422        }
17423
17424        // Handle numbers: negative, out of range
17425        if ( active !== false ) {
17426            active = this.tabs.index( this.tabs.eq( active ) );
17427            if ( active === -1 ) {
17428                active = collapsible ? false : 0;
17429            }
17430        }
17431
17432        // Don't allow collapsible: false and active: false
17433        if ( !collapsible && active === false && this.anchors.length ) {
17434            active = 0;
17435        }
17436
17437        return active;
17438    },
17439
17440    _getCreateEventData: function() {
17441        return {
17442            tab: this.active,
17443            panel: !this.active.length ? $() : this._getPanelForTab( this.active )
17444        };
17445    },
17446
17447    _tabKeydown: function( event ) {
17448        var focusedTab = $( $.ui.safeActiveElement( this.document[ 0 ] ) ).closest( "li" ),
17449            selectedIndex = this.tabs.index( focusedTab ),
17450            goingForward = true;
17451
17452        if ( this._handlePageNav( event ) ) {
17453            return;
17454        }
17455
17456        switch ( event.keyCode ) {
17457        case $.ui.keyCode.RIGHT:
17458        case $.ui.keyCode.DOWN:
17459            selectedIndex++;
17460            break;
17461        case $.ui.keyCode.UP:
17462        case $.ui.keyCode.LEFT:
17463            goingForward = false;
17464            selectedIndex--;
17465            break;
17466        case $.ui.keyCode.END:
17467            selectedIndex = this.anchors.length - 1;
17468            break;
17469        case $.ui.keyCode.HOME:
17470            selectedIndex = 0;
17471            break;
17472        case $.ui.keyCode.SPACE:
17473
17474            // Activate only, no collapsing
17475            event.preventDefault();
17476            clearTimeout( this.activating );
17477            this._activate( selectedIndex );
17478            return;
17479        case $.ui.keyCode.ENTER:
17480
17481            // Toggle (cancel delayed activation, allow collapsing)
17482            event.preventDefault();
17483            clearTimeout( this.activating );
17484
17485            // Determine if we should collapse or activate
17486            this._activate( selectedIndex === this.options.active ? false : selectedIndex );
17487            return;
17488        default:
17489            return;
17490        }
17491
17492        // Focus the appropriate tab, based on which key was pressed
17493        event.preventDefault();
17494        clearTimeout( this.activating );
17495        selectedIndex = this._focusNextTab( selectedIndex, goingForward );
17496
17497        // Navigating with control/command key will prevent automatic activation
17498        if ( !event.ctrlKey && !event.metaKey ) {
17499
17500            // Update aria-selected immediately so that AT think the tab is already selected.
17501            // Otherwise AT may confuse the user by stating that they need to activate the tab,
17502            // but the tab will already be activated by the time the announcement finishes.
17503            focusedTab.attr( "aria-selected", "false" );
17504            this.tabs.eq( selectedIndex ).attr( "aria-selected", "true" );
17505
17506            this.activating = this._delay( function() {
17507                this.option( "active", selectedIndex );
17508            }, this.delay );
17509        }
17510    },
17511
17512    _panelKeydown: function( event ) {
17513        if ( this._handlePageNav( event ) ) {
17514            return;
17515        }
17516
17517        // Ctrl+up moves focus to the current tab
17518        if ( event.ctrlKey && event.keyCode === $.ui.keyCode.UP ) {
17519            event.preventDefault();
17520            this.active.trigger( "focus" );
17521        }
17522    },
17523
17524    // Alt+page up/down moves focus to the previous/next tab (and activates)
17525    _handlePageNav: function( event ) {
17526        if ( event.altKey && event.keyCode === $.ui.keyCode.PAGE_UP ) {
17527            this._activate( this._focusNextTab( this.options.active - 1, false ) );
17528            return true;
17529        }
17530        if ( event.altKey && event.keyCode === $.ui.keyCode.PAGE_DOWN ) {
17531            this._activate( this._focusNextTab( this.options.active + 1, true ) );
17532            return true;
17533        }
17534    },
17535
17536    _findNextTab: function( index, goingForward ) {
17537        var lastTabIndex = this.tabs.length - 1;
17538
17539        function constrain() {
17540            if ( index > lastTabIndex ) {
17541                index = 0;
17542            }
17543            if ( index < 0 ) {
17544                index = lastTabIndex;
17545            }
17546            return index;
17547        }
17548
17549        while ( $.inArray( constrain(), this.options.disabled ) !== -1 ) {
17550            index = goingForward ? index + 1 : index - 1;
17551        }
17552
17553        return index;
17554    },
17555
17556    _focusNextTab: function( index, goingForward ) {
17557        index = this._findNextTab( index, goingForward );
17558        this.tabs.eq( index ).trigger( "focus" );
17559        return index;
17560    },
17561
17562    _setOption: function( key, value ) {
17563        if ( key === "active" ) {
17564
17565            // _activate() will handle invalid values and update this.options
17566            this._activate( value );
17567            return;
17568        }
17569
17570        this._super( key, value );
17571
17572        if ( key === "collapsible" ) {
17573            this._toggleClass( "ui-tabs-collapsible", null, value );
17574
17575            // Setting collapsible: false while collapsed; open first panel
17576            if ( !value && this.options.active === false ) {
17577                this._activate( 0 );
17578            }
17579        }
17580
17581        if ( key === "event" ) {
17582            this._setupEvents( value );
17583        }
17584
17585        if ( key === "heightStyle" ) {
17586            this._setupHeightStyle( value );
17587        }
17588    },
17589
17590    _sanitizeSelector: function( hash ) {
17591        return hash ? hash.replace( /[!"$%&'()*+,.\/:;<=>?@\[\]\^`{|}~]/g, "\\$&" ) : "";
17592    },
17593
17594    refresh: function() {
17595        var options = this.options,
17596            lis = this.tablist.children( ":has(a[href])" );
17597
17598        // Get disabled tabs from class attribute from HTML
17599        // this will get converted to a boolean if needed in _refresh()
17600        options.disabled = $.map( lis.filter( ".ui-state-disabled" ), function( tab ) {
17601            return lis.index( tab );
17602        } );
17603
17604        this._processTabs();
17605
17606        // Was collapsed or no tabs
17607        if ( options.active === false || !this.anchors.length ) {
17608            options.active = false;
vendor: 4,909 bytes, lines 17609-17746
17609            this.active = $();
17610
17611        // was active, but active tab is gone
17612        } else if ( this.active.length && !$.contains( this.tablist[ 0 ], this.active[ 0 ] ) ) {
17613
17614            // all remaining tabs are disabled
17615            if ( this.tabs.length === options.disabled.length ) {
17616                options.active = false;
17617                this.active = $();
17618
17619            // activate previous tab
17620            } else {
17621                this._activate( this._findNextTab( Math.max( 0, options.active - 1 ), false ) );
17622            }
17623
17624        // was active, active tab still exists
17625        } else {
17626
17627            // make sure active index is correct
17628            options.active = this.tabs.index( this.active );
17629        }
17630
17631        this._refresh();
17632    },
17633
17634    _refresh: function() {
17635        this._setOptionDisabled( this.options.disabled );
17636        this._setupEvents( this.options.event );
17637        this._setupHeightStyle( this.options.heightStyle );
17638
17639        this.tabs.not( this.active ).attr( {
17640            "aria-selected": "false",
17641            "aria-expanded": "false",
17642            tabIndex: -1
17643        } );
17644        this.panels.not( this._getPanelForTab( this.active ) )
17645            .hide()
17646            .attr( {
17647                "aria-hidden": "true"
17648            } );
17649
17650        // Make sure one tab is in the tab order
17651        if ( !this.active.length ) {
17652            this.tabs.eq( 0 ).attr( "tabIndex", 0 );
17653        } else {
17654            this.active
17655                .attr( {
17656                    "aria-selected": "true",
17657                    "aria-expanded": "true",
17658                    tabIndex: 0
17659                } );
17660            this._addClass( this.active, "ui-tabs-active", "ui-state-active" );
17661            this._getPanelForTab( this.active )
17662                .show()
17663                .attr( {
17664                    "aria-hidden": "false"
17665                } );
17666        }
17667    },
17668
17669    _processTabs: function() {
17670        var that = this,
17671            prevTabs = this.tabs,
17672            prevAnchors = this.anchors,
17673            prevPanels = this.panels;
17674
17675        this.tablist = this._getList().attr( "role", "tablist" );
17676        this._addClass( this.tablist, "ui-tabs-nav",
17677            "ui-helper-reset ui-helper-clearfix ui-widget-header" );
17678
17679        // Prevent users from focusing disabled tabs via click
17680        this.tablist
17681            .on( "mousedown" + this.eventNamespace, "> li", function( event ) {
17682                if ( $( this ).is( ".ui-state-disabled" ) ) {
17683                    event.preventDefault();
17684                }
17685            } )
17686
17687            // Support: IE <9
17688            // Preventing the default action in mousedown doesn't prevent IE
17689            // from focusing the element, so if the anchor gets focused, blur.
17690            // We don't have to worry about focusing the previously focused
17691            // element since clicking on a non-focusable element should focus
17692            // the body anyway.
17693            .on( "focus" + this.eventNamespace, ".ui-tabs-anchor", function() {
17694                if ( $( this ).closest( "li" ).is( ".ui-state-disabled" ) ) {
17695                    this.blur();
17696                }
17697            } );
17698
17699        this.tabs = this.tablist.find( "> li:has(a[href])" )
17700            .attr( {
17701                role: "tab",
17702                tabIndex: -1
17703            } );
17704        this._addClass( this.tabs, "ui-tabs-tab", "ui-state-default" );
17705
17706        this.anchors = this.tabs.map( function() {
17707            return $( "a", this )[ 0 ];
17708        } )
17709            .attr( {
17710                role: "presentation",
17711                tabIndex: -1
17712            } );
17713        this._addClass( this.anchors, "ui-tabs-anchor" );
17714
17715        this.panels = $();
17716
17717        this.anchors.each( function( i, anchor ) {
17718            var selector, panel, panelId,
17719                anchorId = $( anchor ).uniqueId().attr( "id" ),
17720                tab = $( anchor ).closest( "li" ),
17721                originalAriaControls = tab.attr( "aria-controls" );
17722
17723            // Inline tab
17724            if ( that._isLocal( anchor ) ) {
17725                selector = anchor.hash;
17726                panelId = selector.substring( 1 );
17727                panel = that.element.find( that._sanitizeSelector( selector ) );
17728
17729            // remote tab
17730            } else {
17731
17732                // If the tab doesn't already have aria-controls,
17733                // generate an id by using a throw-away element
17734                panelId = tab.attr( "aria-controls" ) || $( {} ).uniqueId()[ 0 ].id;
17735                selector = "#" + panelId;
17736                panel = that.element.find( selector );
17737                if ( !panel.length ) {
17738                    panel = that._createPanel( panelId );
17739                    panel.insertAfter( that.panels[ i - 1 ] || that.tablist );
17740                }
17741                panel.attr( "aria-live", "polite" );
17742            }
17743
17744            if ( panel.length ) {
17745                that.panels = that.panels.add( panel );
17746            }
vendor: 4,315 bytes, lines 17747-17872
17747            if ( originalAriaControls ) {
17748                tab.data( "ui-tabs-aria-controls", originalAriaControls );
17749            }
17750            tab.attr( {
17751                "aria-controls": panelId,
17752                "aria-labelledby": anchorId
17753            } );
17754            panel.attr( "aria-labelledby", anchorId );
17755        } );
17756
17757        this.panels.attr( "role", "tabpanel" );
17758        this._addClass( this.panels, "ui-tabs-panel", "ui-widget-content" );
17759
17760        // Avoid memory leaks (#10056)
17761        if ( prevTabs ) {
17762            this._off( prevTabs.not( this.tabs ) );
17763            this._off( prevAnchors.not( this.anchors ) );
17764            this._off( prevPanels.not( this.panels ) );
17765        }
17766    },
17767
17768    // Allow overriding how to find the list for rare usage scenarios (#7715)
17769    _getList: function() {
17770        return this.tablist || this.element.find( "ol, ul" ).eq( 0 );
17771    },
17772
17773    _createPanel: function( id ) {
17774        return $( "<div>" )
17775            .attr( "id", id )
17776            .data( "ui-tabs-destroy", true );
17777    },
17778
17779    _setOptionDisabled: function( disabled ) {
17780        var currentItem, li, i;
17781
17782        if ( $.isArray( disabled ) ) {
17783            if ( !disabled.length ) {
17784                disabled = false;
17785            } else if ( disabled.length === this.anchors.length ) {
17786                disabled = true;
17787            }
17788        }
17789
17790        // Disable tabs
17791        for ( i = 0; ( li = this.tabs[ i ] ); i++ ) {
17792            currentItem = $( li );
17793            if ( disabled === true || $.inArray( i, disabled ) !== -1 ) {
17794                currentItem.attr( "aria-disabled", "true" );
17795                this._addClass( currentItem, null, "ui-state-disabled" );
17796            } else {
17797                currentItem.removeAttr( "aria-disabled" );
17798                this._removeClass( currentItem, null, "ui-state-disabled" );
17799            }
17800        }
17801
17802        this.options.disabled = disabled;
17803
17804        this._toggleClass( this.widget(), this.widgetFullName + "-disabled", null,
17805            disabled === true );
17806    },
17807
17808    _setupEvents: function( event ) {
17809        var events = {};
17810        if ( event ) {
17811            $.each( event.split( " " ), function( index, eventName ) {
17812                events[ eventName ] = "_eventHandler";
17813            } );
17814        }
17815
17816        this._off( this.anchors.add( this.tabs ).add( this.panels ) );
17817
17818        // Always prevent the default action, even when disabled
17819        this._on( true, this.anchors, {
17820            click: function( event ) {
17821                event.preventDefault();
17822            }
17823        } );
17824        this._on( this.anchors, events );
17825        this._on( this.tabs, { keydown: "_tabKeydown" } );
17826        this._on( this.panels, { keydown: "_panelKeydown" } );
17827
17828        this._focusable( this.tabs );
17829        this._hoverable( this.tabs );
17830    },
17831
17832    _setupHeightStyle: function( heightStyle ) {
17833        var maxHeight,
17834            parent = this.element.parent();
17835
17836        if ( heightStyle === "fill" ) {
17837            maxHeight = parent.height();
17838            maxHeight -= this.element.outerHeight() - this.element.height();
17839
17840            this.element.siblings( ":visible" ).each( function() {
17841                var elem = $( this ),
17842                    position = elem.css( "position" );
17843
17844                if ( position === "absolute" || position === "fixed" ) {
17845                    return;
17846                }
17847                maxHeight -= elem.outerHeight( true );
17848            } );
17849
17850            this.element.children().not( this.panels ).each( function() {
17851                maxHeight -= $( this ).outerHeight( true );
17852            } );
17853
17854            this.panels.each( function() {
17855                $( this ).height( Math.max( 0, maxHeight -
17856                    $( this ).innerHeight() + $( this ).height() ) );
17857            } )
17858                .css( "overflow", "auto" );
17859        } else if ( heightStyle === "auto" ) {
17860            maxHeight = 0;
17861            this.panels.each( function() {
17862                maxHeight = Math.max( maxHeight, $( this ).height( "" ).height() );
17863            } ).height( maxHeight );
17864        }
17865    },
17866
17867    _eventHandler: function( event ) {
17868        var options = this.options,
17869            active = this.active,
17870            anchor = $( event.currentTarget ),
17871            tab = anchor.closest( "li" ),
17872            clickedIsActive = tab[ 0 ] === active[ 0 ],
vendor: 23,456 bytes, lines 17873-18578
17873            collapsing = clickedIsActive && options.collapsible,
17874            toShow = collapsing ? $() : this._getPanelForTab( tab ),
17875            toHide = !active.length ? $() : this._getPanelForTab( active ),
17876            eventData = {
17877                oldTab: active,
17878                oldPanel: toHide,
17879                newTab: collapsing ? $() : tab,
17880                newPanel: toShow
17881            };
17882
17883        event.preventDefault();
17884
17885        if ( tab.hasClass( "ui-state-disabled" ) ||
17886
17887                // tab is already loading
17888                tab.hasClass( "ui-tabs-loading" ) ||
17889
17890                // can't switch durning an animation
17891                this.running ||
17892
17893                // click on active header, but not collapsible
17894                ( clickedIsActive && !options.collapsible ) ||
17895
17896                // allow canceling activation
17897                ( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
17898            return;
17899        }
17900
17901        options.active = collapsing ? false : this.tabs.index( tab );
17902
17903        this.active = clickedIsActive ? $() : tab;
17904        if ( this.xhr ) {
17905            this.xhr.abort();
17906        }
17907
17908        if ( !toHide.length && !toShow.length ) {
17909            $.error( "jQuery UI Tabs: Mismatching fragment identifier." );
17910        }
17911
17912        if ( toShow.length ) {
17913            this.load( this.tabs.index( tab ), event );
17914        }
17915        this._toggle( event, eventData );
17916    },
17917
17918    // Handles show/hide for selecting tabs
17919    _toggle: function( event, eventData ) {
17920        var that = this,
17921            toShow = eventData.newPanel,
17922            toHide = eventData.oldPanel;
17923
17924        this.running = true;
17925
17926        function complete() {
17927            that.running = false;
17928            that._trigger( "activate", event, eventData );
17929        }
17930
17931        function show() {
17932            that._addClass( eventData.newTab.closest( "li" ), "ui-tabs-active", "ui-state-active" );
17933
17934            if ( toShow.length && that.options.show ) {
17935                that._show( toShow, that.options.show, complete );
17936            } else {
17937                toShow.show();
17938                complete();
17939            }
17940        }
17941
17942        // Start out by hiding, then showing, then completing
17943        if ( toHide.length && this.options.hide ) {
17944            this._hide( toHide, this.options.hide, function() {
17945                that._removeClass( eventData.oldTab.closest( "li" ),
17946                    "ui-tabs-active", "ui-state-active" );
17947                show();
17948            } );
17949        } else {
17950            this._removeClass( eventData.oldTab.closest( "li" ),
17951                "ui-tabs-active", "ui-state-active" );
17952            toHide.hide();
17953            show();
17954        }
17955
17956        toHide.attr( "aria-hidden", "true" );
17957        eventData.oldTab.attr( {
17958            "aria-selected": "false",
17959            "aria-expanded": "false"
17960        } );
17961
17962        // If we're switching tabs, remove the old tab from the tab order.
17963        // If we're opening from collapsed state, remove the previous tab from the tab order.
17964        // If we're collapsing, then keep the collapsing tab in the tab order.
17965        if ( toShow.length && toHide.length ) {
17966            eventData.oldTab.attr( "tabIndex", -1 );
17967        } else if ( toShow.length ) {
17968            this.tabs.filter( function() {
17969                return $( this ).attr( "tabIndex" ) === 0;
17970            } )
17971                .attr( "tabIndex", -1 );
17972        }
17973
17974        toShow.attr( "aria-hidden", "false" );
17975        eventData.newTab.attr( {
17976            "aria-selected": "true",
17977            "aria-expanded": "true",
17978            tabIndex: 0
17979        } );
17980    },
17981
17982    _activate: function( index ) {
17983        var anchor,
17984            active = this._findActive( index );
17985
17986        // Trying to activate the already active panel
17987        if ( active[ 0 ] === this.active[ 0 ] ) {
17988            return;
17989        }
17990
17991        // Trying to collapse, simulate a click on the current active header
17992        if ( !active.length ) {
17993            active = this.active;
17994        }
17995
17996        anchor = active.find( ".ui-tabs-anchor" )[ 0 ];
17997        this._eventHandler( {
17998            target: anchor,
17999            currentTarget: anchor,
18000            preventDefault: $.noop
18001        } );
18002    },
18003
18004    _findActive: function( index ) {
18005        return index === false ? $() : this.tabs.eq( index );
18006    },
18007
18008    _getIndex: function( index ) {
18009
18010        // meta-function to give users option to provide a href string instead of a numerical index.
18011        if ( typeof index === "string" ) {
18012            index = this.anchors.index( this.anchors.filter( "[href$='" +
18013                $.ui.escapeSelector( index ) + "']" ) );
18014        }
18015
18016        return index;
18017    },
18018
18019    _destroy: function() {
18020        if ( this.xhr ) {
18021            this.xhr.abort();
18022        }
18023
18024        this.tablist
18025            .removeAttr( "role" )
18026            .off( this.eventNamespace );
18027
18028        this.anchors
18029            .removeAttr( "role tabIndex" )
18030            .removeUniqueId();
18031
18032        this.tabs.add( this.panels ).each( function() {
18033            if ( $.data( this, "ui-tabs-destroy" ) ) {
18034                $( this ).remove();
18035            } else {
18036                $( this ).removeAttr( "role tabIndex " +
18037                    "aria-live aria-busy aria-selected aria-labelledby aria-hidden aria-expanded" );
18038            }
18039        } );
18040
18041        this.tabs.each( function() {
18042            var li = $( this ),
18043                prev = li.data( "ui-tabs-aria-controls" );
18044            if ( prev ) {
18045                li
18046                    .attr( "aria-controls", prev )
18047                    .removeData( "ui-tabs-aria-controls" );
18048            } else {
18049                li.removeAttr( "aria-controls" );
18050            }
18051        } );
18052
18053        this.panels.show();
18054
18055        if ( this.options.heightStyle !== "content" ) {
18056            this.panels.css( "height", "" );
18057        }
18058    },
18059
18060    enable: function( index ) {
18061        var disabled = this.options.disabled;
18062        if ( disabled === false ) {
18063            return;
18064        }
18065
18066        if ( index === undefined ) {
18067            disabled = false;
18068        } else {
18069            index = this._getIndex( index );
18070            if ( $.isArray( disabled ) ) {
18071                disabled = $.map( disabled, function( num ) {
18072                    return num !== index ? num : null;
18073                } );
18074            } else {
18075                disabled = $.map( this.tabs, function( li, num ) {
18076                    return num !== index ? num : null;
18077                } );
18078            }
18079        }
18080        this._setOptionDisabled( disabled );
18081    },
18082
18083    disable: function( index ) {
18084        var disabled = this.options.disabled;
18085        if ( disabled === true ) {
18086            return;
18087        }
18088
18089        if ( index === undefined ) {
18090            disabled = true;
18091        } else {
18092            index = this._getIndex( index );
18093            if ( $.inArray( index, disabled ) !== -1 ) {
18094                return;
18095            }
18096            if ( $.isArray( disabled ) ) {
18097                disabled = $.merge( [ index ], disabled ).sort();
18098            } else {
18099                disabled = [ index ];
18100            }
18101        }
18102        this._setOptionDisabled( disabled );
18103    },
18104
18105    load: function( index, event ) {
18106        index = this._getIndex( index );
18107        var that = this,
18108            tab = this.tabs.eq( index ),
18109            anchor = tab.find( ".ui-tabs-anchor" ),
18110            panel = this._getPanelForTab( tab ),
18111            eventData = {
18112                tab: tab,
18113                panel: panel
18114            },
18115            complete = function( jqXHR, status ) {
18116                if ( status === "abort" ) {
18117                    that.panels.stop( false, true );
18118                }
18119
18120                that._removeClass( tab, "ui-tabs-loading" );
18121                panel.removeAttr( "aria-busy" );
18122
18123                if ( jqXHR === that.xhr ) {
18124                    delete that.xhr;
18125                }
18126            };
18127
18128        // Not remote
18129        if ( this._isLocal( anchor[ 0 ] ) ) {
18130            return;
18131        }
18132
18133        this.xhr = $.ajax( this._ajaxSettings( anchor, event, eventData ) );
18134
18135        // Support: jQuery <1.8
18136        // jQuery <1.8 returns false if the request is canceled in beforeSend,
18137        // but as of 1.8, $.ajax() always returns a jqXHR object.
18138        if ( this.xhr && this.xhr.statusText !== "canceled" ) {
18139            this._addClass( tab, "ui-tabs-loading" );
18140            panel.attr( "aria-busy", "true" );
18141
18142            this.xhr
18143                .done( function( response, status, jqXHR ) {
18144
18145                    // support: jQuery <1.8
18146                    // http://bugs.jquery.com/ticket/11778
18147                    setTimeout( function() {
18148                        panel.html( response );
18149                        that._trigger( "load", event, eventData );
18150
18151                        complete( jqXHR, status );
18152                    }, 1 );
18153                } )
18154                .fail( function( jqXHR, status ) {
18155
18156                    // support: jQuery <1.8
18157                    // http://bugs.jquery.com/ticket/11778
18158                    setTimeout( function() {
18159                        complete( jqXHR, status );
18160                    }, 1 );
18161                } );
18162        }
18163    },
18164
18165    _ajaxSettings: function( anchor, event, eventData ) {
18166        var that = this;
18167        return {
18168
18169            // Support: IE <11 only
18170            // Strip any hash that exists to prevent errors with the Ajax request
18171            url: anchor.attr( "href" ).replace( /#.*$/, "" ),
18172            beforeSend: function( jqXHR, settings ) {
18173                return that._trigger( "beforeLoad", event,
18174                    $.extend( { jqXHR: jqXHR, ajaxSettings: settings }, eventData ) );
18175            }
18176        };
18177    },
18178
18179    _getPanelForTab: function( tab ) {
18180        var id = $( tab ).attr( "aria-controls" );
18181        return this.element.find( this._sanitizeSelector( "#" + id ) );
18182    }
18183} );
18184
18185// DEPRECATED
18186// TODO: Switch return back to widget declaration at top of file when this is removed
18187if ( $.uiBackCompat !== false ) {
18188
18189    // Backcompat for ui-tab class (now ui-tabs-tab)
18190    $.widget( "ui.tabs", $.ui.tabs, {
18191        _processTabs: function() {
18192            this._superApply( arguments );
18193            this._addClass( this.tabs, "ui-tab" );
18194        }
18195    } );
18196}
18197
18198var widgetsTabs = $.ui.tabs;
18199
18200
18201/*!
18202 * jQuery UI Tooltip 1.12.1
18203 * http://jqueryui.com
18204 *
18205 * Copyright jQuery Foundation and other contributors
18206 * Released under the MIT license.
18207 * http://jquery.org/license
18208 */
18209
18210//>>label: Tooltip
18211//>>group: Widgets
18212//>>description: Shows additional information for any element on hover or focus.
18213//>>docs: http://api.jqueryui.com/tooltip/
18214//>>demos: http://jqueryui.com/tooltip/
18215//>>css.structure: ../../themes/base/core.css
18216//>>css.structure: ../../themes/base/tooltip.css
18217//>>css.theme: ../../themes/base/theme.css
18218
18219
18220
18221$.widget( "ui.tooltip", {
18222    version: "1.12.1",
18223    options: {
18224        classes: {
18225            "ui-tooltip": "ui-corner-all ui-widget-shadow"
18226        },
18227        content: function() {
18228
18229            // support: IE<9, Opera in jQuery <1.7
18230            // .text() can't accept undefined, so coerce to a string
18231            var title = $( this ).attr( "title" ) || "";
18232
18233            // Escape title, since we're going from an attribute to raw HTML
18234            return $( "<a>" ).text( title ).html();
18235        },
18236        hide: true,
18237
18238        // Disabled elements have inconsistent behavior across browsers (#8661)
18239        items: "[title]:not([disabled])",
18240        position: {
18241            my: "left top+15",
18242            at: "left bottom",
18243            collision: "flipfit flip"
18244        },
18245        show: true,
18246        track: false,
18247
18248        // Callbacks
18249        close: null,
18250        open: null
18251    },
18252
18253    _addDescribedBy: function( elem, id ) {
18254        var describedby = ( elem.attr( "aria-describedby" ) || "" ).split( /\s+/ );
18255        describedby.push( id );
18256        elem
18257            .data( "ui-tooltip-id", id )
18258            .attr( "aria-describedby", $.trim( describedby.join( " " ) ) );
18259    },
18260
18261    _removeDescribedBy: function( elem ) {
18262        var id = elem.data( "ui-tooltip-id" ),
18263            describedby = ( elem.attr( "aria-describedby" ) || "" ).split( /\s+/ ),
18264            index = $.inArray( id, describedby );
18265
18266        if ( index !== -1 ) {
18267            describedby.splice( index, 1 );
18268        }
18269
18270        elem.removeData( "ui-tooltip-id" );
18271        describedby = $.trim( describedby.join( " " ) );
18272        if ( describedby ) {
18273            elem.attr( "aria-describedby", describedby );
18274        } else {
18275            elem.removeAttr( "aria-describedby" );
18276        }
18277    },
18278
18279    _create: function() {
18280        this._on( {
18281            mouseover: "open",
18282            focusin: "open"
18283        } );
18284
18285        // IDs of generated tooltips, needed for destroy
18286        this.tooltips = {};
18287
18288        // IDs of parent tooltips where we removed the title attribute
18289        this.parents = {};
18290
18291        // Append the aria-live region so tooltips announce correctly
18292        this.liveRegion = $( "<div>" )
18293            .attr( {
18294                role: "log",
18295                "aria-live": "assertive",
18296                "aria-relevant": "additions"
18297            } )
18298            .appendTo( this.document[ 0 ].body );
18299        this._addClass( this.liveRegion, null, "ui-helper-hidden-accessible" );
18300
18301        this.disabledTitles = $( [] );
18302    },
18303
18304    _setOption: function( key, value ) {
18305        var that = this;
18306
18307        this._super( key, value );
18308
18309        if ( key === "content" ) {
18310            $.each( this.tooltips, function( id, tooltipData ) {
18311                that._updateContent( tooltipData.element );
18312            } );
18313        }
18314    },
18315
18316    _setOptionDisabled: function( value ) {
18317        this[ value ? "_disable" : "_enable" ]();
18318    },
18319
18320    _disable: function() {
18321        var that = this;
18322
18323        // Close open tooltips
18324        $.each( this.tooltips, function( id, tooltipData ) {
18325            var event = $.Event( "blur" );
18326            event.target = event.currentTarget = tooltipData.element[ 0 ];
18327            that.close( event, true );
18328        } );
18329
18330        // Remove title attributes to prevent native tooltips
18331        this.disabledTitles = this.disabledTitles.add(
18332            this.element.find( this.options.items ).addBack()
18333                .filter( function() {
18334                    var element = $( this );
18335                    if ( element.is( "[title]" ) ) {
18336                        return element
18337                            .data( "ui-tooltip-title", element.attr( "title" ) )
18338                            .removeAttr( "title" );
18339                    }
18340                } )
18341        );
18342    },
18343
18344    _enable: function() {
18345
18346        // restore title attributes
18347        this.disabledTitles.each( function() {
18348            var element = $( this );
18349            if ( element.data( "ui-tooltip-title" ) ) {
18350                element.attr( "title", element.data( "ui-tooltip-title" ) );
18351            }
18352        } );
18353        this.disabledTitles = $( [] );
18354    },
18355
18356    open: function( event ) {
18357        var that = this,
18358            target = $( event ? event.target : this.element )
18359
18360                // we need closest here due to mouseover bubbling,
18361                // but always pointing at the same event target
18362                .closest( this.options.items );
18363
18364        // No element to show a tooltip for or the tooltip is already open
18365        if ( !target.length || target.data( "ui-tooltip-id" ) ) {
18366            return;
18367        }
18368
18369        if ( target.attr( "title" ) ) {
18370            target.data( "ui-tooltip-title", target.attr( "title" ) );
18371        }
18372
18373        target.data( "ui-tooltip-open", true );
18374
18375        // Kill parent tooltips, custom or native, for hover
18376        if ( event && event.type === "mouseover" ) {
18377            target.parents().each( function() {
18378                var parent = $( this ),
18379                    blurEvent;
18380                if ( parent.data( "ui-tooltip-open" ) ) {
18381                    blurEvent = $.Event( "blur" );
18382                    blurEvent.target = blurEvent.currentTarget = this;
18383                    that.close( blurEvent, true );
18384                }
18385                if ( parent.attr( "title" ) ) {
18386                    parent.uniqueId();
18387                    that.parents[ this.id ] = {
18388                        element: this,
18389                        title: parent.attr( "title" )
18390                    };
18391                    parent.attr( "title", "" );
18392                }
18393            } );
18394        }
18395
18396        this._registerCloseHandlers( event, target );
18397        this._updateContent( target, event );
18398    },
18399
18400    _updateContent: function( target, event ) {
18401        var content,
18402            contentOption = this.options.content,
18403            that = this,
18404            eventType = event ? event.type : null;
18405
18406        if ( typeof contentOption === "string" || contentOption.nodeType ||
18407                contentOption.jquery ) {
18408            return this._open( event, target, contentOption );
18409        }
18410
18411        content = contentOption.call( target[ 0 ], function( response ) {
18412
18413            // IE may instantly serve a cached response for ajax requests
18414            // delay this call to _open so the other call to _open runs first
18415            that._delay( function() {
18416
18417                // Ignore async response if tooltip was closed already
18418                if ( !target.data( "ui-tooltip-open" ) ) {
18419                    return;
18420                }
18421
18422                // JQuery creates a special event for focusin when it doesn't
18423                // exist natively. To improve performance, the native event
18424                // object is reused and the type is changed. Therefore, we can't
18425                // rely on the type being correct after the event finished
18426                // bubbling, so we set it back to the previous value. (#8740)
18427                if ( event ) {
18428                    event.type = eventType;
18429                }
18430                this._open( event, target, response );
18431            } );
18432        } );
18433        if ( content ) {
18434            this._open( event, target, content );
18435        }
18436    },
18437
18438    _open: function( event, target, content ) {
18439        var tooltipData, tooltip, delayedShow, a11yContent,
18440            positionOption = $.extend( {}, this.options.position );
18441
18442        if ( !content ) {
18443            return;
18444        }
18445
18446        // Content can be updated multiple times. If the tooltip already
18447        // exists, then just update the content and bail.
18448        tooltipData = this._find( target );
18449        if ( tooltipData ) {
18450            tooltipData.tooltip.find( ".ui-tooltip-content" ).html( content );
18451            return;
18452        }
18453
18454        // If we have a title, clear it to prevent the native tooltip
18455        // we have to check first to avoid defining a title if none exists
18456        // (we don't want to cause an element to start matching [title])
18457        //
18458        // We use removeAttr only for key events, to allow IE to export the correct
18459        // accessible attributes. For mouse events, set to empty string to avoid
18460        // native tooltip showing up (happens only when removing inside mouseover).
18461        if ( target.is( "[title]" ) ) {
18462            if ( event && event.type === "mouseover" ) {
18463                target.attr( "title", "" );
18464            } else {
18465                target.removeAttr( "title" );
18466            }
18467        }
18468
18469        tooltipData = this._tooltip( target );
18470        tooltip = tooltipData.tooltip;
18471        this._addDescribedBy( target, tooltip.attr( "id" ) );
18472        tooltip.find( ".ui-tooltip-content" ).html( content );
18473
18474        // Support: Voiceover on OS X, JAWS on IE <= 9
18475        // JAWS announces deletions even when aria-relevant="additions"
18476        // Voiceover will sometimes re-read the entire log region's contents from the beginning
18477        this.liveRegion.children().hide();
18478        a11yContent = $( "<div>" ).html( tooltip.find( ".ui-tooltip-content" ).html() );
18479        a11yContent.removeAttr( "name" ).find( "[name]" ).removeAttr( "name" );
18480        a11yContent.removeAttr( "id" ).find( "[id]" ).removeAttr( "id" );
18481        a11yContent.appendTo( this.liveRegion );
18482
18483        function position( event ) {
18484            positionOption.of = event;
18485            if ( tooltip.is( ":hidden" ) ) {
18486                return;
18487            }
18488            tooltip.position( positionOption );
18489        }
18490        if ( this.options.track && event && /^mouse/.test( event.type ) ) {
18491            this._on( this.document, {
18492                mousemove: position
18493            } );
18494
18495            // trigger once to override element-relative positioning
18496            position( event );
18497        } else {
18498            tooltip.position( $.extend( {
18499                of: target
18500            }, this.options.position ) );
18501        }
18502
18503        tooltip.hide();
18504
18505        this._show( tooltip, this.options.show );
18506
18507        // Handle tracking tooltips that are shown with a delay (#8644). As soon
18508        // as the tooltip is visible, position the tooltip using the most recent
18509        // event.
18510        // Adds the check to add the timers only when both delay and track options are set (#14682)
18511        if ( this.options.track && this.options.show && this.options.show.delay ) {
18512            delayedShow = this.delayedShow = setInterval( function() {
18513                if ( tooltip.is( ":visible" ) ) {
18514                    position( positionOption.of );
18515                    clearInterval( delayedShow );
18516                }
18517            }, $.fx.interval );
18518        }
18519
18520        this._trigger( "open", event, { tooltip: tooltip } );
18521    },
18522
18523    _registerCloseHandlers: function( event, target ) {
18524        var events = {
18525            keyup: function( event ) {
18526                if ( event.keyCode === $.ui.keyCode.ESCAPE ) {
18527                    var fakeEvent = $.Event( event );
18528                    fakeEvent.currentTarget = target[ 0 ];
18529                    this.close( fakeEvent, true );
18530                }
18531            }
18532        };
18533
18534        // Only bind remove handler for delegated targets. Non-delegated
18535        // tooltips will handle this in destroy.
18536        if ( target[ 0 ] !== this.element[ 0 ] ) {
18537            events.remove = function() {
18538                this._removeTooltip( this._find( target ).tooltip );
18539            };
18540        }
18541
18542        if ( !event || event.type === "mouseover" ) {
18543            events.mouseleave = "close";
18544        }
18545        if ( !event || event.type === "focusin" ) {
18546            events.focusout = "close";
18547        }
18548        this._on( true, target, events );
18549    },
18550
18551    close: function( event ) {
18552        var tooltip,
18553            that = this,
18554            target = $( event ? event.currentTarget : this.element ),
18555            tooltipData = this._find( target );
18556
18557        // The tooltip may already be closed
18558        if ( !tooltipData ) {
18559
18560            // We set ui-tooltip-open immediately upon open (in open()), but only set the
18561            // additional data once there's actually content to show (in _open()). So even if the
18562            // tooltip doesn't have full data, we always remove ui-tooltip-open in case we're in
18563            // the period between open() and _open().
18564            target.removeData( "ui-tooltip-open" );
18565            return;
18566        }
18567
18568        tooltip = tooltipData.tooltip;
18569
18570        // Disabling closes the tooltip, so we need to track when we're closing
18571        // to avoid an infinite loop in case the tooltip becomes disabled on close
18572        if ( tooltipData.closing ) {
18573            return;
18574        }
18575
18576        // Clear the interval for delayed tracking tooltips
18577        clearInterval( this.delayedShow );
18578
vendor: 3,916 bytes, lines 18579-18706
18579        // Only set title if we had one before (see comment in _open())
18580        // If the title attribute has changed since open(), don't restore
18581        if ( target.data( "ui-tooltip-title" ) && !target.attr( "title" ) ) {
18582            target.attr( "title", target.data( "ui-tooltip-title" ) );
18583        }
18584
18585        this._removeDescribedBy( target );
18586
18587        tooltipData.hiding = true;
18588        tooltip.stop( true );
18589        this._hide( tooltip, this.options.hide, function() {
18590            that._removeTooltip( $( this ) );
18591        } );
18592
18593        target.removeData( "ui-tooltip-open" );
18594        this._off( target, "mouseleave focusout keyup" );
18595
18596        // Remove 'remove' binding only on delegated targets
18597        if ( target[ 0 ] !== this.element[ 0 ] ) {
18598            this._off( target, "remove" );
18599        }
18600        this._off( this.document, "mousemove" );
18601
18602        if ( event && event.type === "mouseleave" ) {
18603            $.each( this.parents, function( id, parent ) {
18604                $( parent.element ).attr( "title", parent.title );
18605                delete that.parents[ id ];
18606            } );
18607        }
18608
18609        tooltipData.closing = true;
18610        this._trigger( "close", event, { tooltip: tooltip } );
18611        if ( !tooltipData.hiding ) {
18612            tooltipData.closing = false;
18613        }
18614    },
18615
18616    _tooltip: function( element ) {
18617        var tooltip = $( "<div>" ).attr( "role", "tooltip" ),
18618            content = $( "<div>" ).appendTo( tooltip ),
18619            id = tooltip.uniqueId().attr( "id" );
18620
18621        this._addClass( content, "ui-tooltip-content" );
18622        this._addClass( tooltip, "ui-tooltip", "ui-widget ui-widget-content" );
18623
18624        tooltip.appendTo( this._appendTo( element ) );
18625
18626        return this.tooltips[ id ] = {
18627            element: element,
18628            tooltip: tooltip
18629        };
18630    },
18631
18632    _find: function( target ) {
18633        var id = target.data( "ui-tooltip-id" );
18634        return id ? this.tooltips[ id ] : null;
18635    },
18636
18637    _removeTooltip: function( tooltip ) {
18638        tooltip.remove();
18639        delete this.tooltips[ tooltip.attr( "id" ) ];
18640    },
18641
18642    _appendTo: function( target ) {
18643        var element = target.closest( ".ui-front, dialog" );
18644
18645        if ( !element.length ) {
18646            element = this.document[ 0 ].body;
18647        }
18648
18649        return element;
18650    },
18651
18652    _destroy: function() {
18653        var that = this;
18654
18655        // Close open tooltips
18656        $.each( this.tooltips, function( id, tooltipData ) {
18657
18658            // Delegate to close method to handle common cleanup
18659            var event = $.Event( "blur" ),
18660                element = tooltipData.element;
18661            event.target = event.currentTarget = element[ 0 ];
18662            that.close( event, true );
18663
18664            // Remove immediately; destroying an open tooltip doesn't use the
18665            // hide animation
18666            $( "#" + id ).remove();
18667
18668            // Restore the title
18669            if ( element.data( "ui-tooltip-title" ) ) {
18670
18671                // If the title attribute has changed since open(), don't restore
18672                if ( !element.attr( "title" ) ) {
18673                    element.attr( "title", element.data( "ui-tooltip-title" ) );
18674                }
18675                element.removeData( "ui-tooltip-title" );
18676            }
18677        } );
18678        this.liveRegion.remove();
18679    }
18680} );
18681
18682// DEPRECATED
18683// TODO: Switch return back to widget declaration at top of file when this is removed
18684if ( $.uiBackCompat !== false ) {
18685
18686    // Backcompat for tooltipClass option
18687    $.widget( "ui.tooltip", $.ui.tooltip, {
18688        options: {
18689            tooltipClass: null
18690        },
18691        _tooltip: function() {
18692            var tooltipData = this._superApply( arguments );
18693            if ( this.options.tooltipClass ) {
18694                tooltipData.tooltip.addClass( this.options.tooltipClass );
18695            }
18696            return tooltipData;
18697        }
18698    } );
18699}
18700
18701var widgetsTooltip = $.ui.tooltip;
18702
18703
18704
18705
18706}));

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.