]> git.somenet.org - fsinf/pub/w2c.git/blob - jquery-ui.js
fix insert. Forgot to add a ", ?" when adding gruppenfotoerlaubnis.
[fsinf/pub/w2c.git] / jquery-ui.js
1 /*! jQuery UI - v1.11.4 - 2015-03-11
2 * http://jqueryui.com
3 * Includes: core.js, widget.js, mouse.js, position.js, accordion.js, autocomplete.js, button.js, datepicker.js, dialog.js, draggable.js, droppable.js, effect.js, effect-blind.js, effect-bounce.js, effect-clip.js, effect-drop.js, effect-explode.js, effect-fade.js, effect-fold.js, effect-highlight.js, effect-puff.js, effect-pulsate.js, effect-scale.js, effect-shake.js, effect-size.js, effect-slide.js, effect-transfer.js, menu.js, progressbar.js, resizable.js, selectable.js, selectmenu.js, slider.js, sortable.js, spinner.js, tabs.js, tooltip.js
4 * Copyright 2015 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  * jQuery UI Core 1.11.4
19  * http://jqueryui.com
20  *
21  * Copyright jQuery Foundation and other contributors
22  * Released under the MIT license.
23  * http://jquery.org/license
24  *
25  * http://api.jqueryui.com/category/ui-core/
26  */
27
28
29 // $.ui might exist from components with no dependencies, e.g., $.ui.position
30 $.ui = $.ui || {};
31
32 $.extend( $.ui, {
33         version: "1.11.4",
34
35         keyCode: {
36                 BACKSPACE: 8,
37                 COMMA: 188,
38                 DELETE: 46,
39                 DOWN: 40,
40                 END: 35,
41                 ENTER: 13,
42                 ESCAPE: 27,
43                 HOME: 36,
44                 LEFT: 37,
45                 PAGE_DOWN: 34,
46                 PAGE_UP: 33,
47                 PERIOD: 190,
48                 RIGHT: 39,
49                 SPACE: 32,
50                 TAB: 9,
51                 UP: 38
52         }
53 });
54
55 // plugins
56 $.fn.extend({
57         scrollParent: function( includeHidden ) {
58                 var position = this.css( "position" ),
59                         excludeStaticParent = position === "absolute",
60                         overflowRegex = includeHidden ? /(auto|scroll|hidden)/ : /(auto|scroll)/,
61                         scrollParent = this.parents().filter( function() {
62                                 var parent = $( this );
63                                 if ( excludeStaticParent && parent.css( "position" ) === "static" ) {
64                                         return false;
65                                 }
66                                 return overflowRegex.test( parent.css( "overflow" ) + parent.css( "overflow-y" ) + parent.css( "overflow-x" ) );
67                         }).eq( 0 );
68
69                 return position === "fixed" || !scrollParent.length ? $( this[ 0 ].ownerDocument || document ) : scrollParent;
70         },
71
72         uniqueId: (function() {
73                 var uuid = 0;
74
75                 return function() {
76                         return this.each(function() {
77                                 if ( !this.id ) {
78                                         this.id = "ui-id-" + ( ++uuid );
79                                 }
80                         });
81                 };
82         })(),
83
84         removeUniqueId: function() {
85                 return this.each(function() {
86                         if ( /^ui-id-\d+$/.test( this.id ) ) {
87                                 $( this ).removeAttr( "id" );
88                         }
89                 });
90         }
91 });
92
93 // selectors
94 function focusable( element, isTabIndexNotNaN ) {
95         var map, mapName, img,
96                 nodeName = element.nodeName.toLowerCase();
97         if ( "area" === nodeName ) {
98                 map = element.parentNode;
99                 mapName = map.name;
100                 if ( !element.href || !mapName || map.nodeName.toLowerCase() !== "map" ) {
101                         return false;
102                 }
103                 img = $( "img[usemap='#" + mapName + "']" )[ 0 ];
104                 return !!img && visible( img );
105         }
106         return ( /^(input|select|textarea|button|object)$/.test( nodeName ) ?
107                 !element.disabled :
108                 "a" === nodeName ?
109                         element.href || isTabIndexNotNaN :
110                         isTabIndexNotNaN) &&
111                 // the element and all of its ancestors must be visible
112                 visible( element );
113 }
114
115 function visible( element ) {
116         return $.expr.filters.visible( element ) &&
117                 !$( element ).parents().addBack().filter(function() {
118                         return $.css( this, "visibility" ) === "hidden";
119                 }).length;
120 }
121
122 $.extend( $.expr[ ":" ], {
123         data: $.expr.createPseudo ?
124                 $.expr.createPseudo(function( dataName ) {
125                         return function( elem ) {
126                                 return !!$.data( elem, dataName );
127                         };
128                 }) :
129                 // support: jQuery <1.8
130                 function( elem, i, match ) {
131                         return !!$.data( elem, match[ 3 ] );
132                 },
133
134         focusable: function( element ) {
135                 return focusable( element, !isNaN( $.attr( element, "tabindex" ) ) );
136         },
137
138         tabbable: function( element ) {
139                 var tabIndex = $.attr( element, "tabindex" ),
140                         isTabIndexNaN = isNaN( tabIndex );
141                 return ( isTabIndexNaN || tabIndex >= 0 ) && focusable( element, !isTabIndexNaN );
142         }
143 });
144
145 // support: jQuery <1.8
146 if ( !$( "<a>" ).outerWidth( 1 ).jquery ) {
147         $.each( [ "Width", "Height" ], function( i, name ) {
148                 var side = name === "Width" ? [ "Left", "Right" ] : [ "Top", "Bottom" ],
149                         type = name.toLowerCase(),
150                         orig = {
151                                 innerWidth: $.fn.innerWidth,
152                                 innerHeight: $.fn.innerHeight,
153                                 outerWidth: $.fn.outerWidth,
154                                 outerHeight: $.fn.outerHeight
155                         };
156
157                 function reduce( elem, size, border, margin ) {
158                         $.each( side, function() {
159                                 size -= parseFloat( $.css( elem, "padding" + this ) ) || 0;
160                                 if ( border ) {
161                                         size -= parseFloat( $.css( elem, "border" + this + "Width" ) ) || 0;
162                                 }
163                                 if ( margin ) {
164                                         size -= parseFloat( $.css( elem, "margin" + this ) ) || 0;
165                                 }
166                         });
167                         return size;
168                 }
169
170                 $.fn[ "inner" + name ] = function( size ) {
171                         if ( size === undefined ) {
172                                 return orig[ "inner" + name ].call( this );
173                         }
174
175                         return this.each(function() {
176                                 $( this ).css( type, reduce( this, size ) + "px" );
177                         });
178                 };
179
180                 $.fn[ "outer" + name] = function( size, margin ) {
181                         if ( typeof size !== "number" ) {
182                                 return orig[ "outer" + name ].call( this, size );
183                         }
184
185                         return this.each(function() {
186                                 $( this).css( type, reduce( this, size, true, margin ) + "px" );
187                         });
188                 };
189         });
190 }
191
192 // support: jQuery <1.8
193 if ( !$.fn.addBack ) {
194         $.fn.addBack = function( selector ) {
195                 return this.add( selector == null ?
196                         this.prevObject : this.prevObject.filter( selector )
197                 );
198         };
199 }
200
201 // support: jQuery 1.6.1, 1.6.2 (http://bugs.jquery.com/ticket/9413)
202 if ( $( "<a>" ).data( "a-b", "a" ).removeData( "a-b" ).data( "a-b" ) ) {
203         $.fn.removeData = (function( removeData ) {
204                 return function( key ) {
205                         if ( arguments.length ) {
206                                 return removeData.call( this, $.camelCase( key ) );
207                         } else {
208                                 return removeData.call( this );
209                         }
210                 };
211         })( $.fn.removeData );
212 }
213
214 // deprecated
215 $.ui.ie = !!/msie [\w.]+/.exec( navigator.userAgent.toLowerCase() );
216
217 $.fn.extend({
218         focus: (function( orig ) {
219                 return function( delay, fn ) {
220                         return typeof delay === "number" ?
221                                 this.each(function() {
222                                         var elem = this;
223                                         setTimeout(function() {
224                                                 $( elem ).focus();
225                                                 if ( fn ) {
226                                                         fn.call( elem );
227                                                 }
228                                         }, delay );
229                                 }) :
230                                 orig.apply( this, arguments );
231                 };
232         })( $.fn.focus ),
233
234         disableSelection: (function() {
235                 var eventType = "onselectstart" in document.createElement( "div" ) ?
236                         "selectstart" :
237                         "mousedown";
238
239                 return function() {
240                         return this.bind( eventType + ".ui-disableSelection", function( event ) {
241                                 event.preventDefault();
242                         });
243                 };
244         })(),
245
246         enableSelection: function() {
247                 return this.unbind( ".ui-disableSelection" );
248         },
249
250         zIndex: function( zIndex ) {
251                 if ( zIndex !== undefined ) {
252                         return this.css( "zIndex", zIndex );
253                 }
254
255                 if ( this.length ) {
256                         var elem = $( this[ 0 ] ), position, value;
257                         while ( elem.length && elem[ 0 ] !== document ) {
258                                 // Ignore z-index if position is set to a value where z-index is ignored by the browser
259                                 // This makes behavior of this function consistent across browsers
260                                 // WebKit always returns auto if the element is positioned
261                                 position = elem.css( "position" );
262                                 if ( position === "absolute" || position === "relative" || position === "fixed" ) {
263                                         // IE returns 0 when zIndex is not specified
264                                         // other browsers return a string
265                                         // we ignore the case of nested elements with an explicit value of 0
266                                         // <div style="z-index: -10;"><div style="z-index: 0;"></div></div>
267                                         value = parseInt( elem.css( "zIndex" ), 10 );
268                                         if ( !isNaN( value ) && value !== 0 ) {
269                                                 return value;
270                                         }
271                                 }
272                                 elem = elem.parent();
273                         }
274                 }
275
276                 return 0;
277         }
278 });
279
280 // $.ui.plugin is deprecated. Use $.widget() extensions instead.
281 $.ui.plugin = {
282         add: function( module, option, set ) {
283                 var i,
284                         proto = $.ui[ module ].prototype;
285                 for ( i in set ) {
286                         proto.plugins[ i ] = proto.plugins[ i ] || [];
287                         proto.plugins[ i ].push( [ option, set[ i ] ] );
288                 }
289         },
290         call: function( instance, name, args, allowDisconnected ) {
291                 var i,
292                         set = instance.plugins[ name ];
293
294                 if ( !set ) {
295                         return;
296                 }
297
298                 if ( !allowDisconnected && ( !instance.element[ 0 ].parentNode || instance.element[ 0 ].parentNode.nodeType === 11 ) ) {
299                         return;
300                 }
301
302                 for ( i = 0; i < set.length; i++ ) {
303                         if ( instance.options[ set[ i ][ 0 ] ] ) {
304                                 set[ i ][ 1 ].apply( instance.element, args );
305                         }
306                 }
307         }
308 };
309
310
311 /*!
312  * jQuery UI Widget 1.11.4
313  * http://jqueryui.com
314  *
315  * Copyright jQuery Foundation and other contributors
316  * Released under the MIT license.
317  * http://jquery.org/license
318  *
319  * http://api.jqueryui.com/jQuery.widget/
320  */
321
322
323 var widget_uuid = 0,
324         widget_slice = Array.prototype.slice;
325
326 $.cleanData = (function( orig ) {
327         return function( elems ) {
328                 var events, elem, i;
329                 for ( i = 0; (elem = elems[i]) != null; i++ ) {
330                         try {
331
332                                 // Only trigger remove when necessary to save time
333                                 events = $._data( elem, "events" );
334                                 if ( events && events.remove ) {
335                                         $( elem ).triggerHandler( "remove" );
336                                 }
337
338                         // http://bugs.jquery.com/ticket/8235
339                         } catch ( e ) {}
340                 }
341                 orig( elems );
342         };
343 })( $.cleanData );
344
345 $.widget = function( name, base, prototype ) {
346         var fullName, existingConstructor, constructor, basePrototype,
347                 // proxiedPrototype allows the provided prototype to remain unmodified
348                 // so that it can be used as a mixin for multiple widgets (#8876)
349                 proxiedPrototype = {},
350                 namespace = name.split( "." )[ 0 ];
351
352         name = name.split( "." )[ 1 ];
353         fullName = namespace + "-" + name;
354
355         if ( !prototype ) {
356                 prototype = base;
357                 base = $.Widget;
358         }
359
360         // create selector for plugin
361         $.expr[ ":" ][ fullName.toLowerCase() ] = function( elem ) {
362                 return !!$.data( elem, fullName );
363         };
364
365         $[ namespace ] = $[ namespace ] || {};
366         existingConstructor = $[ namespace ][ name ];
367         constructor = $[ namespace ][ name ] = function( options, element ) {
368                 // allow instantiation without "new" keyword
369                 if ( !this._createWidget ) {
370                         return new constructor( options, element );
371                 }
372
373                 // allow instantiation without initializing for simple inheritance
374                 // must use "new" keyword (the code above always passes args)
375                 if ( arguments.length ) {
376                         this._createWidget( options, element );
377                 }
378         };
379         // extend with the existing constructor to carry over any static properties
380         $.extend( constructor, existingConstructor, {
381                 version: prototype.version,
382                 // copy the object used to create the prototype in case we need to
383                 // redefine the widget later
384                 _proto: $.extend( {}, prototype ),
385                 // track widgets that inherit from this widget in case this widget is
386                 // redefined after a widget inherits from it
387                 _childConstructors: []
388         });
389
390         basePrototype = new base();
391         // we need to make the options hash a property directly on the new instance
392         // otherwise we'll modify the options hash on the prototype that we're
393         // inheriting from
394         basePrototype.options = $.widget.extend( {}, basePrototype.options );
395         $.each( prototype, function( prop, value ) {
396                 if ( !$.isFunction( value ) ) {
397                         proxiedPrototype[ prop ] = value;
398                         return;
399                 }
400                 proxiedPrototype[ prop ] = (function() {
401                         var _super = function() {
402                                         return base.prototype[ prop ].apply( this, arguments );
403                                 },
404                                 _superApply = function( args ) {
405                                         return base.prototype[ prop ].apply( this, args );
406                                 };
407                         return function() {
408                                 var __super = this._super,
409                                         __superApply = this._superApply,
410                                         returnValue;
411
412                                 this._super = _super;
413                                 this._superApply = _superApply;
414
415                                 returnValue = value.apply( this, arguments );
416
417                                 this._super = __super;
418                                 this._superApply = __superApply;
419
420                                 return returnValue;
421                         };
422                 })();
423         });
424         constructor.prototype = $.widget.extend( basePrototype, {
425                 // TODO: remove support for widgetEventPrefix
426                 // always use the name + a colon as the prefix, e.g., draggable:start
427                 // don't prefix for widgets that aren't DOM-based
428                 widgetEventPrefix: existingConstructor ? (basePrototype.widgetEventPrefix || name) : name
429         }, proxiedPrototype, {
430                 constructor: constructor,
431                 namespace: namespace,
432                 widgetName: name,
433                 widgetFullName: fullName
434         });
435
436         // If this widget is being redefined then we need to find all widgets that
437         // are inheriting from it and redefine all of them so that they inherit from
438         // the new version of this widget. We're essentially trying to replace one
439         // level in the prototype chain.
440         if ( existingConstructor ) {
441                 $.each( existingConstructor._childConstructors, function( i, child ) {
442                         var childPrototype = child.prototype;
443
444                         // redefine the child widget using the same prototype that was
445                         // originally used, but inherit from the new version of the base
446                         $.widget( childPrototype.namespace + "." + childPrototype.widgetName, constructor, child._proto );
447                 });
448                 // remove the list of existing child constructors from the old constructor
449                 // so the old child constructors can be garbage collected
450                 delete existingConstructor._childConstructors;
451         } else {
452                 base._childConstructors.push( constructor );
453         }
454
455         $.widget.bridge( name, constructor );
456
457         return constructor;
458 };
459
460 $.widget.extend = function( target ) {
461         var input = widget_slice.call( arguments, 1 ),
462                 inputIndex = 0,
463                 inputLength = input.length,
464                 key,
465                 value;
466         for ( ; inputIndex < inputLength; inputIndex++ ) {
467                 for ( key in input[ inputIndex ] ) {
468                         value = input[ inputIndex ][ key ];
469                         if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {
470                                 // Clone objects
471                                 if ( $.isPlainObject( value ) ) {
472                                         target[ key ] = $.isPlainObject( target[ key ] ) ?
473                                                 $.widget.extend( {}, target[ key ], value ) :
474                                                 // Don't extend strings, arrays, etc. with objects
475                                                 $.widget.extend( {}, value );
476                                 // Copy everything else by reference
477                                 } else {
478                                         target[ key ] = value;
479                                 }
480                         }
481                 }
482         }
483         return target;
484 };
485
486 $.widget.bridge = function( name, object ) {
487         var fullName = object.prototype.widgetFullName || name;
488         $.fn[ name ] = function( options ) {
489                 var isMethodCall = typeof options === "string",
490                         args = widget_slice.call( arguments, 1 ),
491                         returnValue = this;
492
493                 if ( isMethodCall ) {
494                         this.each(function() {
495                                 var methodValue,
496                                         instance = $.data( this, fullName );
497                                 if ( options === "instance" ) {
498                                         returnValue = instance;
499                                         return false;
500                                 }
501                                 if ( !instance ) {
502                                         return $.error( "cannot call methods on " + name + " prior to initialization; " +
503                                                 "attempted to call method '" + options + "'" );
504                                 }
505                                 if ( !$.isFunction( instance[options] ) || options.charAt( 0 ) === "_" ) {
506                                         return $.error( "no such method '" + options + "' for " + name + " widget instance" );
507                                 }
508                                 methodValue = instance[ options ].apply( instance, args );
509                                 if ( methodValue !== instance && methodValue !== undefined ) {
510                                         returnValue = methodValue && methodValue.jquery ?
511                                                 returnValue.pushStack( methodValue.get() ) :
512                                                 methodValue;
513                                         return false;
514                                 }
515                         });
516                 } else {
517
518                         // Allow multiple hashes to be passed on init
519                         if ( args.length ) {
520                                 options = $.widget.extend.apply( null, [ options ].concat(args) );
521                         }
522
523                         this.each(function() {
524                                 var instance = $.data( this, fullName );
525                                 if ( instance ) {
526                                         instance.option( options || {} );
527                                         if ( instance._init ) {
528                                                 instance._init();
529                                         }
530                                 } else {
531                                         $.data( this, fullName, new object( options, this ) );
532                                 }
533                         });
534                 }
535
536                 return returnValue;
537         };
538 };
539
540 $.Widget = function( /* options, element */ ) {};
541 $.Widget._childConstructors = [];
542
543 $.Widget.prototype = {
544         widgetName: "widget",
545         widgetEventPrefix: "",
546         defaultElement: "<div>",
547         options: {
548                 disabled: false,
549
550                 // callbacks
551                 create: null
552         },
553         _createWidget: function( options, element ) {
554                 element = $( element || this.defaultElement || this )[ 0 ];
555                 this.element = $( element );
556                 this.uuid = widget_uuid++;
557                 this.eventNamespace = "." + this.widgetName + this.uuid;
558
559                 this.bindings = $();
560                 this.hoverable = $();
561                 this.focusable = $();
562
563                 if ( element !== this ) {
564                         $.data( element, this.widgetFullName, this );
565                         this._on( true, this.element, {
566                                 remove: function( event ) {
567                                         if ( event.target === element ) {
568                                                 this.destroy();
569                                         }
570                                 }
571                         });
572                         this.document = $( element.style ?
573                                 // element within the document
574                                 element.ownerDocument :
575                                 // element is window or document
576                                 element.document || element );
577                         this.window = $( this.document[0].defaultView || this.document[0].parentWindow );
578                 }
579
580                 this.options = $.widget.extend( {},
581                         this.options,
582                         this._getCreateOptions(),
583                         options );
584
585                 this._create();
586                 this._trigger( "create", null, this._getCreateEventData() );
587                 this._init();
588         },
589         _getCreateOptions: $.noop,
590         _getCreateEventData: $.noop,
591         _create: $.noop,
592         _init: $.noop,
593
594         destroy: function() {
595                 this._destroy();
596                 // we can probably remove the unbind calls in 2.0
597                 // all event bindings should go through this._on()
598                 this.element
599                         .unbind( this.eventNamespace )
600                         .removeData( this.widgetFullName )
601                         // support: jquery <1.6.3
602                         // http://bugs.jquery.com/ticket/9413
603                         .removeData( $.camelCase( this.widgetFullName ) );
604                 this.widget()
605                         .unbind( this.eventNamespace )
606                         .removeAttr( "aria-disabled" )
607                         .removeClass(
608                                 this.widgetFullName + "-disabled " +
609                                 "ui-state-disabled" );
610
611                 // clean up events and states
612                 this.bindings.unbind( this.eventNamespace );
613                 this.hoverable.removeClass( "ui-state-hover" );
614                 this.focusable.removeClass( "ui-state-focus" );
615         },
616         _destroy: $.noop,
617
618         widget: function() {
619                 return this.element;
620         },
621
622         option: function( key, value ) {
623                 var options = key,
624                         parts,
625                         curOption,
626                         i;
627
628                 if ( arguments.length === 0 ) {
629                         // don't return a reference to the internal hash
630                         return $.widget.extend( {}, this.options );
631                 }
632
633                 if ( typeof key === "string" ) {
634                         // handle nested keys, e.g., "foo.bar" => { foo: { bar: ___ } }
635                         options = {};
636                         parts = key.split( "." );
637                         key = parts.shift();
638                         if ( parts.length ) {
639                                 curOption = options[ key ] = $.widget.extend( {}, this.options[ key ] );
640                                 for ( i = 0; i < parts.length - 1; i++ ) {
641                                         curOption[ parts[ i ] ] = curOption[ parts[ i ] ] || {};
642                                         curOption = curOption[ parts[ i ] ];
643                                 }
644                                 key = parts.pop();
645                                 if ( arguments.length === 1 ) {
646                                         return curOption[ key ] === undefined ? null : curOption[ key ];
647                                 }
648                                 curOption[ key ] = value;
649                         } else {
650                                 if ( arguments.length === 1 ) {
651                                         return this.options[ key ] === undefined ? null : this.options[ key ];
652                                 }
653                                 options[ key ] = value;
654                         }
655                 }
656
657                 this._setOptions( options );
658
659                 return this;
660         },
661         _setOptions: function( options ) {
662                 var key;
663
664                 for ( key in options ) {
665                         this._setOption( key, options[ key ] );
666                 }
667
668                 return this;
669         },
670         _setOption: function( key, value ) {
671                 this.options[ key ] = value;
672
673                 if ( key === "disabled" ) {
674                         this.widget()
675                                 .toggleClass( this.widgetFullName + "-disabled", !!value );
676
677                         // If the widget is becoming disabled, then nothing is interactive
678                         if ( value ) {
679                                 this.hoverable.removeClass( "ui-state-hover" );
680                                 this.focusable.removeClass( "ui-state-focus" );
681                         }
682                 }
683
684                 return this;
685         },
686
687         enable: function() {
688                 return this._setOptions({ disabled: false });
689         },
690         disable: function() {
691                 return this._setOptions({ disabled: true });
692         },
693
694         _on: function( suppressDisabledCheck, element, handlers ) {
695                 var delegateElement,
696                         instance = this;
697
698                 // no suppressDisabledCheck flag, shuffle arguments
699                 if ( typeof suppressDisabledCheck !== "boolean" ) {
700                         handlers = element;
701                         element = suppressDisabledCheck;
702                         suppressDisabledCheck = false;
703                 }
704
705                 // no element argument, shuffle and use this.element
706                 if ( !handlers ) {
707                         handlers = element;
708                         element = this.element;
709                         delegateElement = this.widget();
710                 } else {
711                         element = delegateElement = $( element );
712                         this.bindings = this.bindings.add( element );
713                 }
714
715                 $.each( handlers, function( event, handler ) {
716                         function handlerProxy() {
717                                 // allow widgets to customize the disabled handling
718                                 // - disabled as an array instead of boolean
719                                 // - disabled class as method for disabling individual parts
720                                 if ( !suppressDisabledCheck &&
721                                                 ( instance.options.disabled === true ||
722                                                         $( this ).hasClass( "ui-state-disabled" ) ) ) {
723                                         return;
724                                 }
725                                 return ( typeof handler === "string" ? instance[ handler ] : handler )
726                                         .apply( instance, arguments );
727                         }
728
729                         // copy the guid so direct unbinding works
730                         if ( typeof handler !== "string" ) {
731                                 handlerProxy.guid = handler.guid =
732                                         handler.guid || handlerProxy.guid || $.guid++;
733                         }
734
735                         var match = event.match( /^([\w:-]*)\s*(.*)$/ ),
736                                 eventName = match[1] + instance.eventNamespace,
737                                 selector = match[2];
738                         if ( selector ) {
739                                 delegateElement.delegate( selector, eventName, handlerProxy );
740                         } else {
741                                 element.bind( eventName, handlerProxy );
742                         }
743                 });
744         },
745
746         _off: function( element, eventName ) {
747                 eventName = (eventName || "").split( " " ).join( this.eventNamespace + " " ) +
748                         this.eventNamespace;
749                 element.unbind( eventName ).undelegate( eventName );
750
751                 // Clear the stack to avoid memory leaks (#10056)
752                 this.bindings = $( this.bindings.not( element ).get() );
753                 this.focusable = $( this.focusable.not( element ).get() );
754                 this.hoverable = $( this.hoverable.not( element ).get() );
755         },
756
757         _delay: function( handler, delay ) {
758                 function handlerProxy() {
759                         return ( typeof handler === "string" ? instance[ handler ] : handler )
760                                 .apply( instance, arguments );
761                 }
762                 var instance = this;
763                 return setTimeout( handlerProxy, delay || 0 );
764         },
765
766         _hoverable: function( element ) {
767                 this.hoverable = this.hoverable.add( element );
768                 this._on( element, {
769                         mouseenter: function( event ) {
770                                 $( event.currentTarget ).addClass( "ui-state-hover" );
771                         },
772                         mouseleave: function( event ) {
773                                 $( event.currentTarget ).removeClass( "ui-state-hover" );
774                         }
775                 });
776         },
777
778         _focusable: function( element ) {
779                 this.focusable = this.focusable.add( element );
780                 this._on( element, {
781                         focusin: function( event ) {
782                                 $( event.currentTarget ).addClass( "ui-state-focus" );
783                         },
784                         focusout: function( event ) {
785                                 $( event.currentTarget ).removeClass( "ui-state-focus" );
786                         }
787                 });
788         },
789
790         _trigger: function( type, event, data ) {
791                 var prop, orig,
792                         callback = this.options[ type ];
793
794                 data = data || {};
795                 event = $.Event( event );
796                 event.type = ( type === this.widgetEventPrefix ?
797                         type :
798                         this.widgetEventPrefix + type ).toLowerCase();
799                 // the original event may come from any element
800                 // so we need to reset the target on the new event
801                 event.target = this.element[ 0 ];
802
803                 // copy original event properties over to the new event
804                 orig = event.originalEvent;
805                 if ( orig ) {
806                         for ( prop in orig ) {
807                                 if ( !( prop in event ) ) {
808                                         event[ prop ] = orig[ prop ];
809                                 }
810                         }
811                 }
812
813                 this.element.trigger( event, data );
814                 return !( $.isFunction( callback ) &&
815                         callback.apply( this.element[0], [ event ].concat( data ) ) === false ||
816                         event.isDefaultPrevented() );
817         }
818 };
819
820 $.each( { show: "fadeIn", hide: "fadeOut" }, function( method, defaultEffect ) {
821         $.Widget.prototype[ "_" + method ] = function( element, options, callback ) {
822                 if ( typeof options === "string" ) {
823                         options = { effect: options };
824                 }
825                 var hasOptions,
826                         effectName = !options ?
827                                 method :
828                                 options === true || typeof options === "number" ?
829                                         defaultEffect :
830                                         options.effect || defaultEffect;
831                 options = options || {};
832                 if ( typeof options === "number" ) {
833                         options = { duration: options };
834                 }
835                 hasOptions = !$.isEmptyObject( options );
836                 options.complete = callback;
837                 if ( options.delay ) {
838                         element.delay( options.delay );
839                 }
840                 if ( hasOptions && $.effects && $.effects.effect[ effectName ] ) {
841                         element[ method ]( options );
842                 } else if ( effectName !== method && element[ effectName ] ) {
843                         element[ effectName ]( options.duration, options.easing, callback );
844                 } else {
845                         element.queue(function( next ) {
846                                 $( this )[ method ]();
847                                 if ( callback ) {
848                                         callback.call( element[ 0 ] );
849                                 }
850                                 next();
851                         });
852                 }
853         };
854 });
855
856 var widget = $.widget;
857
858
859 /*!
860  * jQuery UI Mouse 1.11.4
861  * http://jqueryui.com
862  *
863  * Copyright jQuery Foundation and other contributors
864  * Released under the MIT license.
865  * http://jquery.org/license
866  *
867  * http://api.jqueryui.com/mouse/
868  */
869
870
871 var mouseHandled = false;
872 $( document ).mouseup( function() {
873         mouseHandled = false;
874 });
875
876 var mouse = $.widget("ui.mouse", {
877         version: "1.11.4",
878         options: {
879                 cancel: "input,textarea,button,select,option",
880                 distance: 1,
881                 delay: 0
882         },
883         _mouseInit: function() {
884                 var that = this;
885
886                 this.element
887                         .bind("mousedown." + this.widgetName, function(event) {
888                                 return that._mouseDown(event);
889                         })
890                         .bind("click." + this.widgetName, function(event) {
891                                 if (true === $.data(event.target, that.widgetName + ".preventClickEvent")) {
892                                         $.removeData(event.target, that.widgetName + ".preventClickEvent");
893                                         event.stopImmediatePropagation();
894                                         return false;
895                                 }
896                         });
897
898                 this.started = false;
899         },
900
901         // TODO: make sure destroying one instance of mouse doesn't mess with
902         // other instances of mouse
903         _mouseDestroy: function() {
904                 this.element.unbind("." + this.widgetName);
905                 if ( this._mouseMoveDelegate ) {
906                         this.document
907                                 .unbind("mousemove." + this.widgetName, this._mouseMoveDelegate)
908                                 .unbind("mouseup." + this.widgetName, this._mouseUpDelegate);
909                 }
910         },
911
912         _mouseDown: function(event) {
913                 // don't let more than one widget handle mouseStart
914                 if ( mouseHandled ) {
915                         return;
916                 }
917
918                 this._mouseMoved = false;
919
920                 // we may have missed mouseup (out of window)
921                 (this._mouseStarted && this._mouseUp(event));
922
923                 this._mouseDownEvent = event;
924
925                 var that = this,
926                         btnIsLeft = (event.which === 1),
927                         // event.target.nodeName works around a bug in IE 8 with
928                         // disabled inputs (#7620)
929                         elIsCancel = (typeof this.options.cancel === "string" && event.target.nodeName ? $(event.target).closest(this.options.cancel).length : false);
930                 if (!btnIsLeft || elIsCancel || !this._mouseCapture(event)) {
931                         return true;
932                 }
933
934                 this.mouseDelayMet = !this.options.delay;
935                 if (!this.mouseDelayMet) {
936                         this._mouseDelayTimer = setTimeout(function() {
937                                 that.mouseDelayMet = true;
938                         }, this.options.delay);
939                 }
940
941                 if (this._mouseDistanceMet(event) && this._mouseDelayMet(event)) {
942                         this._mouseStarted = (this._mouseStart(event) !== false);
943                         if (!this._mouseStarted) {
944                                 event.preventDefault();
945                                 return true;
946                         }
947                 }
948
949                 // Click event may never have fired (Gecko & Opera)
950                 if (true === $.data(event.target, this.widgetName + ".preventClickEvent")) {
951                         $.removeData(event.target, this.widgetName + ".preventClickEvent");
952                 }
953
954                 // these delegates are required to keep context
955                 this._mouseMoveDelegate = function(event) {
956                         return that._mouseMove(event);
957                 };
958                 this._mouseUpDelegate = function(event) {
959                         return that._mouseUp(event);
960                 };
961
962                 this.document
963                         .bind( "mousemove." + this.widgetName, this._mouseMoveDelegate )
964                         .bind( "mouseup." + this.widgetName, this._mouseUpDelegate );
965
966                 event.preventDefault();
967
968                 mouseHandled = true;
969                 return true;
970         },
971
972         _mouseMove: function(event) {
973                 // Only check for mouseups outside the document if you've moved inside the document
974                 // at least once. This prevents the firing of mouseup in the case of IE<9, which will
975                 // fire a mousemove event if content is placed under the cursor. See #7778
976                 // Support: IE <9
977                 if ( this._mouseMoved ) {
978                         // IE mouseup check - mouseup happened when mouse was out of window
979                         if ($.ui.ie && ( !document.documentMode || document.documentMode < 9 ) && !event.button) {
980                                 return this._mouseUp(event);
981
982                         // Iframe mouseup check - mouseup occurred in another document
983                         } else if ( !event.which ) {
984                                 return this._mouseUp( event );
985                         }
986                 }
987
988                 if ( event.which || event.button ) {
989                         this._mouseMoved = true;
990                 }
991
992                 if (this._mouseStarted) {
993                         this._mouseDrag(event);
994                         return event.preventDefault();
995                 }
996
997                 if (this._mouseDistanceMet(event) && this._mouseDelayMet(event)) {
998                         this._mouseStarted =
999                                 (this._mouseStart(this._mouseDownEvent, event) !== false);
1000                         (this._mouseStarted ? this._mouseDrag(event) : this._mouseUp(event));
1001                 }
1002
1003                 return !this._mouseStarted;
1004         },
1005
1006         _mouseUp: function(event) {
1007                 this.document
1008                         .unbind( "mousemove." + this.widgetName, this._mouseMoveDelegate )
1009                         .unbind( "mouseup." + this.widgetName, this._mouseUpDelegate );
1010
1011                 if (this._mouseStarted) {
1012                         this._mouseStarted = false;
1013
1014                         if (event.target === this._mouseDownEvent.target) {
1015                                 $.data(event.target, this.widgetName + ".preventClickEvent", true);
1016                         }
1017
1018                         this._mouseStop(event);
1019                 }
1020
1021                 mouseHandled = false;
1022                 return false;
1023         },
1024
1025         _mouseDistanceMet: function(event) {
1026                 return (Math.max(
1027                                 Math.abs(this._mouseDownEvent.pageX - event.pageX),
1028                                 Math.abs(this._mouseDownEvent.pageY - event.pageY)
1029                         ) >= this.options.distance
1030                 );
1031         },
1032
1033         _mouseDelayMet: function(/* event */) {
1034                 return this.mouseDelayMet;
1035         },
1036
1037         // These are placeholder methods, to be overriden by extending plugin
1038         _mouseStart: function(/* event */) {},
1039         _mouseDrag: function(/* event */) {},
1040         _mouseStop: function(/* event */) {},
1041         _mouseCapture: function(/* event */) { return true; }
1042 });
1043
1044
1045 /*!
1046  * jQuery UI Position 1.11.4
1047  * http://jqueryui.com
1048  *
1049  * Copyright jQuery Foundation and other contributors
1050  * Released under the MIT license.
1051  * http://jquery.org/license
1052  *
1053  * http://api.jqueryui.com/position/
1054  */
1055
1056 (function() {
1057
1058 $.ui = $.ui || {};
1059
1060 var cachedScrollbarWidth, supportsOffsetFractions,
1061         max = Math.max,
1062         abs = Math.abs,
1063         round = Math.round,
1064         rhorizontal = /left|center|right/,
1065         rvertical = /top|center|bottom/,
1066         roffset = /[\+\-]\d+(\.[\d]+)?%?/,
1067         rposition = /^\w+/,
1068         rpercent = /%$/,
1069         _position = $.fn.position;
1070
1071 function getOffsets( offsets, width, height ) {
1072         return [
1073                 parseFloat( offsets[ 0 ] ) * ( rpercent.test( offsets[ 0 ] ) ? width / 100 : 1 ),
1074                 parseFloat( offsets[ 1 ] ) * ( rpercent.test( offsets[ 1 ] ) ? height / 100 : 1 )
1075         ];
1076 }
1077
1078 function parseCss( element, property ) {
1079         return parseInt( $.css( element, property ), 10 ) || 0;
1080 }
1081
1082 function getDimensions( elem ) {
1083         var raw = elem[0];
1084         if ( raw.nodeType === 9 ) {
1085                 return {
1086                         width: elem.width(),
1087                         height: elem.height(),
1088                         offset: { top: 0, left: 0 }
1089                 };
1090         }
1091         if ( $.isWindow( raw ) ) {
1092                 return {
1093                         width: elem.width(),
1094                         height: elem.height(),
1095                         offset: { top: elem.scrollTop(), left: elem.scrollLeft() }
1096                 };
1097         }
1098         if ( raw.preventDefault ) {
1099                 return {
1100                         width: 0,
1101                         height: 0,
1102                         offset: { top: raw.pageY, left: raw.pageX }
1103                 };
1104         }
1105         return {
1106                 width: elem.outerWidth(),
1107                 height: elem.outerHeight(),
1108                 offset: elem.offset()
1109         };
1110 }
1111
1112 $.position = {
1113         scrollbarWidth: function() {
1114                 if ( cachedScrollbarWidth !== undefined ) {
1115                         return cachedScrollbarWidth;
1116                 }
1117                 var w1, w2,
1118                         div = $( "<div style='display:block;position:absolute;width:50px;height:50px;overflow:hidden;'><div style='height:100px;width:auto;'></div></div>" ),
1119                         innerDiv = div.children()[0];
1120
1121                 $( "body" ).append( div );
1122                 w1 = innerDiv.offsetWidth;
1123                 div.css( "overflow", "scroll" );
1124
1125                 w2 = innerDiv.offsetWidth;
1126
1127                 if ( w1 === w2 ) {
1128                         w2 = div[0].clientWidth;
1129                 }
1130
1131                 div.remove();
1132
1133                 return (cachedScrollbarWidth = w1 - w2);
1134         },
1135         getScrollInfo: function( within ) {
1136                 var overflowX = within.isWindow || within.isDocument ? "" :
1137                                 within.element.css( "overflow-x" ),
1138                         overflowY = within.isWindow || within.isDocument ? "" :
1139                                 within.element.css( "overflow-y" ),
1140                         hasOverflowX = overflowX === "scroll" ||
1141                                 ( overflowX === "auto" && within.width < within.element[0].scrollWidth ),
1142                         hasOverflowY = overflowY === "scroll" ||
1143                                 ( overflowY === "auto" && within.height < within.element[0].scrollHeight );
1144                 return {
1145                         width: hasOverflowY ? $.position.scrollbarWidth() : 0,
1146                         height: hasOverflowX ? $.position.scrollbarWidth() : 0
1147                 };
1148         },
1149         getWithinInfo: function( element ) {
1150                 var withinElement = $( element || window ),
1151                         isWindow = $.isWindow( withinElement[0] ),
1152                         isDocument = !!withinElement[ 0 ] && withinElement[ 0 ].nodeType === 9;
1153                 return {
1154                         element: withinElement,
1155                         isWindow: isWindow,
1156                         isDocument: isDocument,
1157                         offset: withinElement.offset() || { left: 0, top: 0 },
1158                         scrollLeft: withinElement.scrollLeft(),
1159                         scrollTop: withinElement.scrollTop(),
1160
1161                         // support: jQuery 1.6.x
1162                         // jQuery 1.6 doesn't support .outerWidth/Height() on documents or windows
1163                         width: isWindow || isDocument ? withinElement.width() : withinElement.outerWidth(),
1164                         height: isWindow || isDocument ? withinElement.height() : withinElement.outerHeight()
1165                 };
1166         }
1167 };
1168
1169 $.fn.position = function( options ) {
1170         if ( !options || !options.of ) {
1171                 return _position.apply( this, arguments );
1172         }
1173
1174         // make a copy, we don't want to modify arguments
1175         options = $.extend( {}, options );
1176
1177         var atOffset, targetWidth, targetHeight, targetOffset, basePosition, dimensions,
1178                 target = $( options.of ),
1179                 within = $.position.getWithinInfo( options.within ),
1180                 scrollInfo = $.position.getScrollInfo( within ),
1181                 collision = ( options.collision || "flip" ).split( " " ),
1182                 offsets = {};
1183
1184         dimensions = getDimensions( target );
1185         if ( target[0].preventDefault ) {
1186                 // force left top to allow flipping
1187                 options.at = "left top";
1188         }
1189         targetWidth = dimensions.width;
1190         targetHeight = dimensions.height;
1191         targetOffset = dimensions.offset;
1192         // clone to reuse original targetOffset later
1193         basePosition = $.extend( {}, targetOffset );
1194
1195         // force my and at to have valid horizontal and vertical positions
1196         // if a value is missing or invalid, it will be converted to center
1197         $.each( [ "my", "at" ], function() {
1198                 var pos = ( options[ this ] || "" ).split( " " ),
1199                         horizontalOffset,
1200                         verticalOffset;
1201
1202                 if ( pos.length === 1) {
1203                         pos = rhorizontal.test( pos[ 0 ] ) ?
1204                                 pos.concat( [ "center" ] ) :
1205                                 rvertical.test( pos[ 0 ] ) ?
1206                                         [ "center" ].concat( pos ) :
1207                                         [ "center", "center" ];
1208                 }
1209                 pos[ 0 ] = rhorizontal.test( pos[ 0 ] ) ? pos[ 0 ] : "center";
1210                 pos[ 1 ] = rvertical.test( pos[ 1 ] ) ? pos[ 1 ] : "center";
1211
1212                 // calculate offsets
1213                 horizontalOffset = roffset.exec( pos[ 0 ] );
1214                 verticalOffset = roffset.exec( pos[ 1 ] );
1215                 offsets[ this ] = [
1216                         horizontalOffset ? horizontalOffset[ 0 ] : 0,
1217                         verticalOffset ? verticalOffset[ 0 ] : 0
1218                 ];
1219
1220                 // reduce to just the positions without the offsets
1221                 options[ this ] = [
1222                         rposition.exec( pos[ 0 ] )[ 0 ],
1223                         rposition.exec( pos[ 1 ] )[ 0 ]
1224                 ];
1225         });
1226
1227         // normalize collision option
1228         if ( collision.length === 1 ) {
1229                 collision[ 1 ] = collision[ 0 ];
1230         }
1231
1232         if ( options.at[ 0 ] === "right" ) {
1233                 basePosition.left += targetWidth;
1234         } else if ( options.at[ 0 ] === "center" ) {
1235                 basePosition.left += targetWidth / 2;
1236         }
1237
1238         if ( options.at[ 1 ] === "bottom" ) {
1239                 basePosition.top += targetHeight;
1240         } else if ( options.at[ 1 ] === "center" ) {
1241                 basePosition.top += targetHeight / 2;
1242         }
1243
1244         atOffset = getOffsets( offsets.at, targetWidth, targetHeight );
1245         basePosition.left += atOffset[ 0 ];
1246         basePosition.top += atOffset[ 1 ];
1247
1248         return this.each(function() {
1249                 var collisionPosition, using,
1250                         elem = $( this ),
1251                         elemWidth = elem.outerWidth(),
1252                         elemHeight = elem.outerHeight(),
1253                         marginLeft = parseCss( this, "marginLeft" ),
1254                         marginTop = parseCss( this, "marginTop" ),
1255                         collisionWidth = elemWidth + marginLeft + parseCss( this, "marginRight" ) + scrollInfo.width,
1256                         collisionHeight = elemHeight + marginTop + parseCss( this, "marginBottom" ) + scrollInfo.height,
1257                         position = $.extend( {}, basePosition ),
1258                         myOffset = getOffsets( offsets.my, elem.outerWidth(), elem.outerHeight() );
1259
1260                 if ( options.my[ 0 ] === "right" ) {
1261                         position.left -= elemWidth;
1262                 } else if ( options.my[ 0 ] === "center" ) {
1263                         position.left -= elemWidth / 2;
1264                 }
1265
1266                 if ( options.my[ 1 ] === "bottom" ) {
1267                         position.top -= elemHeight;
1268                 } else if ( options.my[ 1 ] === "center" ) {
1269                         position.top -= elemHeight / 2;
1270                 }
1271
1272                 position.left += myOffset[ 0 ];
1273                 position.top += myOffset[ 1 ];
1274
1275                 // if the browser doesn't support fractions, then round for consistent results
1276                 if ( !supportsOffsetFractions ) {
1277                         position.left = round( position.left );
1278                         position.top = round( position.top );
1279                 }
1280
1281                 collisionPosition = {
1282                         marginLeft: marginLeft,
1283                         marginTop: marginTop
1284                 };
1285
1286                 $.each( [ "left", "top" ], function( i, dir ) {
1287                         if ( $.ui.position[ collision[ i ] ] ) {
1288                                 $.ui.position[ collision[ i ] ][ dir ]( position, {
1289                                         targetWidth: targetWidth,
1290                                         targetHeight: targetHeight,
1291                                         elemWidth: elemWidth,
1292                                         elemHeight: elemHeight,
1293                                         collisionPosition: collisionPosition,
1294                                         collisionWidth: collisionWidth,
1295                                         collisionHeight: collisionHeight,
1296                                         offset: [ atOffset[ 0 ] + myOffset[ 0 ], atOffset [ 1 ] + myOffset[ 1 ] ],
1297                                         my: options.my,
1298                                         at: options.at,
1299                                         within: within,
1300                                         elem: elem
1301                                 });
1302                         }
1303                 });
1304
1305                 if ( options.using ) {
1306                         // adds feedback as second argument to using callback, if present
1307                         using = function( props ) {
1308                                 var left = targetOffset.left - position.left,
1309                                         right = left + targetWidth - elemWidth,
1310                                         top = targetOffset.top - position.top,
1311                                         bottom = top + targetHeight - elemHeight,
1312                                         feedback = {
1313                                                 target: {
1314                                                         element: target,
1315                                                         left: targetOffset.left,
1316                                                         top: targetOffset.top,
1317                                                         width: targetWidth,
1318                                                         height: targetHeight
1319                                                 },
1320                                                 element: {
1321                                                         element: elem,
1322                                                         left: position.left,
1323                                                         top: position.top,
1324                                                         width: elemWidth,
1325                                                         height: elemHeight
1326                                                 },
1327                                                 horizontal: right < 0 ? "left" : left > 0 ? "right" : "center",
1328                                                 vertical: bottom < 0 ? "top" : top > 0 ? "bottom" : "middle"
1329                                         };
1330                                 if ( targetWidth < elemWidth && abs( left + right ) < targetWidth ) {
1331                                         feedback.horizontal = "center";
1332                                 }
1333                                 if ( targetHeight < elemHeight && abs( top + bottom ) < targetHeight ) {
1334                                         feedback.vertical = "middle";
1335                                 }
1336                                 if ( max( abs( left ), abs( right ) ) > max( abs( top ), abs( bottom ) ) ) {
1337                                         feedback.important = "horizontal";
1338                                 } else {
1339                                         feedback.important = "vertical";
1340                                 }
1341                                 options.using.call( this, props, feedback );
1342                         };
1343                 }
1344
1345                 elem.offset( $.extend( position, { using: using } ) );
1346         });
1347 };
1348
1349 $.ui.position = {
1350         fit: {
1351                 left: function( position, data ) {
1352                         var within = data.within,
1353                                 withinOffset = within.isWindow ? within.scrollLeft : within.offset.left,
1354                                 outerWidth = within.width,
1355                                 collisionPosLeft = position.left - data.collisionPosition.marginLeft,
1356                                 overLeft = withinOffset - collisionPosLeft,
1357                                 overRight = collisionPosLeft + data.collisionWidth - outerWidth - withinOffset,
1358                                 newOverRight;
1359
1360                         // element is wider than within
1361                         if ( data.collisionWidth > outerWidth ) {
1362                                 // element is initially over the left side of within
1363                                 if ( overLeft > 0 && overRight <= 0 ) {
1364                                         newOverRight = position.left + overLeft + data.collisionWidth - outerWidth - withinOffset;
1365                                         position.left += overLeft - newOverRight;
1366                                 // element is initially over right side of within
1367                                 } else if ( overRight > 0 && overLeft <= 0 ) {
1368                                         position.left = withinOffset;
1369                                 // element is initially over both left and right sides of within
1370                                 } else {
1371                                         if ( overLeft > overRight ) {
1372                                                 position.left = withinOffset + outerWidth - data.collisionWidth;
1373                                         } else {
1374                                                 position.left = withinOffset;
1375                                         }
1376                                 }
1377                         // too far left -> align with left edge
1378                         } else if ( overLeft > 0 ) {
1379                                 position.left += overLeft;
1380                         // too far right -> align with right edge
1381                         } else if ( overRight > 0 ) {
1382                                 position.left -= overRight;
1383                         // adjust based on position and margin
1384                         } else {
1385                                 position.left = max( position.left - collisionPosLeft, position.left );
1386                         }
1387                 },
1388                 top: function( position, data ) {
1389                         var within = data.within,
1390                                 withinOffset = within.isWindow ? within.scrollTop : within.offset.top,
1391                                 outerHeight = data.within.height,
1392                                 collisionPosTop = position.top - data.collisionPosition.marginTop,
1393                                 overTop = withinOffset - collisionPosTop,
1394                                 overBottom = collisionPosTop + data.collisionHeight - outerHeight - withinOffset,
1395                                 newOverBottom;
1396
1397                         // element is taller than within
1398                         if ( data.collisionHeight > outerHeight ) {
1399                                 // element is initially over the top of within
1400                                 if ( overTop > 0 && overBottom <= 0 ) {
1401                                         newOverBottom = position.top + overTop + data.collisionHeight - outerHeight - withinOffset;
1402                                         position.top += overTop - newOverBottom;
1403                                 // element is initially over bottom of within
1404                                 } else if ( overBottom > 0 && overTop <= 0 ) {
1405                                         position.top = withinOffset;
1406                                 // element is initially over both top and bottom of within
1407                                 } else {
1408                                         if ( overTop > overBottom ) {
1409                                                 position.top = withinOffset + outerHeight - data.collisionHeight;
1410                                         } else {
1411                                                 position.top = withinOffset;
1412                                         }
1413                                 }
1414                         // too far up -> align with top
1415                         } else if ( overTop > 0 ) {
1416                                 position.top += overTop;
1417                         // too far down -> align with bottom edge
1418                         } else if ( overBottom > 0 ) {
1419                                 position.top -= overBottom;
1420                         // adjust based on position and margin
1421                         } else {
1422                                 position.top = max( position.top - collisionPosTop, position.top );
1423                         }
1424                 }
1425         },
1426         flip: {
1427                 left: function( position, data ) {
1428                         var within = data.within,
1429                                 withinOffset = within.offset.left + within.scrollLeft,
1430                                 outerWidth = within.width,
1431                                 offsetLeft = within.isWindow ? within.scrollLeft : within.offset.left,
1432                                 collisionPosLeft = position.left - data.collisionPosition.marginLeft,
1433                                 overLeft = collisionPosLeft - offsetLeft,
1434                                 overRight = collisionPosLeft + data.collisionWidth - outerWidth - offsetLeft,
1435                                 myOffset = data.my[ 0 ] === "left" ?
1436                                         -data.elemWidth :
1437                                         data.my[ 0 ] === "right" ?
1438                                                 data.elemWidth :
1439                                                 0,
1440                                 atOffset = data.at[ 0 ] === "left" ?
1441                                         data.targetWidth :
1442                                         data.at[ 0 ] === "right" ?
1443                                                 -data.targetWidth :
1444                                                 0,
1445                                 offset = -2 * data.offset[ 0 ],
1446                                 newOverRight,
1447                                 newOverLeft;
1448
1449                         if ( overLeft < 0 ) {
1450                                 newOverRight = position.left + myOffset + atOffset + offset + data.collisionWidth - outerWidth - withinOffset;
1451                                 if ( newOverRight < 0 || newOverRight < abs( overLeft ) ) {
1452                                         position.left += myOffset + atOffset + offset;
1453                                 }
1454                         } else if ( overRight > 0 ) {
1455                                 newOverLeft = position.left - data.collisionPosition.marginLeft + myOffset + atOffset + offset - offsetLeft;
1456                                 if ( newOverLeft > 0 || abs( newOverLeft ) < overRight ) {
1457                                         position.left += myOffset + atOffset + offset;
1458                                 }
1459                         }
1460                 },
1461                 top: function( position, data ) {
1462                         var within = data.within,
1463                                 withinOffset = within.offset.top + within.scrollTop,
1464                                 outerHeight = within.height,
1465                                 offsetTop = within.isWindow ? within.scrollTop : within.offset.top,
1466                                 collisionPosTop = position.top - data.collisionPosition.marginTop,
1467                                 overTop = collisionPosTop - offsetTop,
1468                                 overBottom = collisionPosTop + data.collisionHeight - outerHeight - offsetTop,
1469                                 top = data.my[ 1 ] === "top",
1470                                 myOffset = top ?
1471                                         -data.elemHeight :
1472                                         data.my[ 1 ] === "bottom" ?
1473                                                 data.elemHeight :
1474                                                 0,
1475                                 atOffset = data.at[ 1 ] === "top" ?
1476                                         data.targetHeight :
1477                                         data.at[ 1 ] === "bottom" ?
1478                                                 -data.targetHeight :
1479                                                 0,
1480                                 offset = -2 * data.offset[ 1 ],
1481                                 newOverTop,
1482                                 newOverBottom;
1483                         if ( overTop < 0 ) {
1484                                 newOverBottom = position.top + myOffset + atOffset + offset + data.collisionHeight - outerHeight - withinOffset;
1485                                 if ( newOverBottom < 0 || newOverBottom < abs( overTop ) ) {
1486                                         position.top += myOffset + atOffset + offset;
1487                                 }
1488                         } else if ( overBottom > 0 ) {
1489                                 newOverTop = position.top - data.collisionPosition.marginTop + myOffset + atOffset + offset - offsetTop;
1490                                 if ( newOverTop > 0 || abs( newOverTop ) < overBottom ) {
1491                                         position.top += myOffset + atOffset + offset;
1492                                 }
1493                         }
1494                 }
1495         },
1496         flipfit: {
1497                 left: function() {
1498                         $.ui.position.flip.left.apply( this, arguments );
1499                         $.ui.position.fit.left.apply( this, arguments );
1500                 },
1501                 top: function() {
1502                         $.ui.position.flip.top.apply( this, arguments );
1503                         $.ui.position.fit.top.apply( this, arguments );
1504                 }
1505         }
1506 };
1507
1508 // fraction support test
1509 (function() {
1510         var testElement, testElementParent, testElementStyle, offsetLeft, i,
1511                 body = document.getElementsByTagName( "body" )[ 0 ],
1512                 div = document.createElement( "div" );
1513
1514         //Create a "fake body" for testing based on method used in jQuery.support
1515         testElement = document.createElement( body ? "div" : "body" );
1516         testElementStyle = {
1517                 visibility: "hidden",
1518                 width: 0,
1519                 height: 0,
1520                 border: 0,
1521                 margin: 0,
1522                 background: "none"
1523         };
1524         if ( body ) {
1525                 $.extend( testElementStyle, {
1526                         position: "absolute",
1527                         left: "-1000px",
1528                         top: "-1000px"
1529                 });
1530         }
1531         for ( i in testElementStyle ) {
1532                 testElement.style[ i ] = testElementStyle[ i ];
1533         }
1534         testElement.appendChild( div );
1535         testElementParent = body || document.documentElement;
1536         testElementParent.insertBefore( testElement, testElementParent.firstChild );
1537
1538         div.style.cssText = "position: absolute; left: 10.7432222px;";
1539
1540         offsetLeft = $( div ).offset().left;
1541         supportsOffsetFractions = offsetLeft > 10 && offsetLeft < 11;
1542
1543         testElement.innerHTML = "";
1544         testElementParent.removeChild( testElement );
1545 })();
1546
1547 })();
1548
1549 var position = $.ui.position;
1550
1551
1552 /*!
1553  * jQuery UI Accordion 1.11.4
1554  * http://jqueryui.com
1555  *
1556  * Copyright jQuery Foundation and other contributors
1557  * Released under the MIT license.
1558  * http://jquery.org/license
1559  *
1560  * http://api.jqueryui.com/accordion/
1561  */
1562
1563
1564 var accordion = $.widget( "ui.accordion", {
1565         version: "1.11.4",
1566         options: {
1567                 active: 0,
1568                 animate: {},
1569                 collapsible: false,
1570                 event: "click",
1571                 header: "> li > :first-child,> :not(li):even",
1572                 heightStyle: "auto",
1573                 icons: {
1574                         activeHeader: "ui-icon-triangle-1-s",
1575                         header: "ui-icon-triangle-1-e"
1576                 },
1577
1578                 // callbacks
1579                 activate: null,
1580                 beforeActivate: null
1581         },
1582
1583         hideProps: {
1584                 borderTopWidth: "hide",
1585                 borderBottomWidth: "hide",
1586                 paddingTop: "hide",
1587                 paddingBottom: "hide",
1588                 height: "hide"
1589         },
1590
1591         showProps: {
1592                 borderTopWidth: "show",
1593                 borderBottomWidth: "show",
1594                 paddingTop: "show",
1595                 paddingBottom: "show",
1596                 height: "show"
1597         },
1598
1599         _create: function() {
1600                 var options = this.options;
1601                 this.prevShow = this.prevHide = $();
1602                 this.element.addClass( "ui-accordion ui-widget ui-helper-reset" )
1603                         // ARIA
1604                         .attr( "role", "tablist" );
1605
1606                 // don't allow collapsible: false and active: false / null
1607                 if ( !options.collapsible && (options.active === false || options.active == null) ) {
1608                         options.active = 0;
1609                 }
1610
1611                 this._processPanels();
1612                 // handle negative values
1613                 if ( options.active < 0 ) {
1614                         options.active += this.headers.length;
1615                 }
1616                 this._refresh();
1617         },
1618
1619         _getCreateEventData: function() {
1620                 return {
1621                         header: this.active,
1622                         panel: !this.active.length ? $() : this.active.next()
1623                 };
1624         },
1625
1626         _createIcons: function() {
1627                 var icons = this.options.icons;
1628                 if ( icons ) {
1629                         $( "<span>" )
1630                                 .addClass( "ui-accordion-header-icon ui-icon " + icons.header )
1631                                 .prependTo( this.headers );
1632                         this.active.children( ".ui-accordion-header-icon" )
1633                                 .removeClass( icons.header )
1634                                 .addClass( icons.activeHeader );
1635                         this.headers.addClass( "ui-accordion-icons" );
1636                 }
1637         },
1638
1639         _destroyIcons: function() {
1640                 this.headers
1641                         .removeClass( "ui-accordion-icons" )
1642                         .children( ".ui-accordion-header-icon" )
1643                                 .remove();
1644         },
1645
1646         _destroy: function() {
1647                 var contents;
1648
1649                 // clean up main element
1650                 this.element
1651                         .removeClass( "ui-accordion ui-widget ui-helper-reset" )
1652                         .removeAttr( "role" );
1653
1654                 // clean up headers
1655                 this.headers
1656                         .removeClass( "ui-accordion-header ui-accordion-header-active ui-state-default " +
1657                                 "ui-corner-all ui-state-active ui-state-disabled ui-corner-top" )
1658                         .removeAttr( "role" )
1659                         .removeAttr( "aria-expanded" )
1660                         .removeAttr( "aria-selected" )
1661                         .removeAttr( "aria-controls" )
1662                         .removeAttr( "tabIndex" )
1663                         .removeUniqueId();
1664
1665                 this._destroyIcons();
1666
1667                 // clean up content panels
1668                 contents = this.headers.next()
1669                         .removeClass( "ui-helper-reset ui-widget-content ui-corner-bottom " +
1670                                 "ui-accordion-content ui-accordion-content-active ui-state-disabled" )
1671                         .css( "display", "" )
1672                         .removeAttr( "role" )
1673                         .removeAttr( "aria-hidden" )
1674                         .removeAttr( "aria-labelledby" )
1675                         .removeUniqueId();
1676
1677                 if ( this.options.heightStyle !== "content" ) {
1678                         contents.css( "height", "" );
1679                 }
1680         },
1681
1682         _setOption: function( key, value ) {
1683                 if ( key === "active" ) {
1684                         // _activate() will handle invalid values and update this.options
1685                         this._activate( value );
1686                         return;
1687                 }
1688
1689                 if ( key === "event" ) {
1690                         if ( this.options.event ) {
1691                                 this._off( this.headers, this.options.event );
1692                         }
1693                         this._setupEvents( value );
1694                 }
1695
1696                 this._super( key, value );
1697
1698                 // setting collapsible: false while collapsed; open first panel
1699                 if ( key === "collapsible" && !value && this.options.active === false ) {
1700                         this._activate( 0 );
1701                 }
1702
1703                 if ( key === "icons" ) {
1704                         this._destroyIcons();
1705                         if ( value ) {
1706                                 this._createIcons();
1707                         }
1708                 }
1709
1710                 // #5332 - opacity doesn't cascade to positioned elements in IE
1711                 // so we need to add the disabled class to the headers and panels
1712                 if ( key === "disabled" ) {
1713                         this.element
1714                                 .toggleClass( "ui-state-disabled", !!value )
1715                                 .attr( "aria-disabled", value );
1716                         this.headers.add( this.headers.next() )
1717                                 .toggleClass( "ui-state-disabled", !!value );
1718                 }
1719         },
1720
1721         _keydown: function( event ) {
1722                 if ( event.altKey || event.ctrlKey ) {
1723                         return;
1724                 }
1725
1726                 var keyCode = $.ui.keyCode,
1727                         length = this.headers.length,
1728                         currentIndex = this.headers.index( event.target ),
1729                         toFocus = false;
1730
1731                 switch ( event.keyCode ) {
1732                         case keyCode.RIGHT:
1733                         case keyCode.DOWN:
1734                                 toFocus = this.headers[ ( currentIndex + 1 ) % length ];
1735                                 break;
1736                         case keyCode.LEFT:
1737                         case keyCode.UP:
1738                                 toFocus = this.headers[ ( currentIndex - 1 + length ) % length ];
1739                                 break;
1740                         case keyCode.SPACE:
1741                         case keyCode.ENTER:
1742                                 this._eventHandler( event );
1743                                 break;
1744                         case keyCode.HOME:
1745                                 toFocus = this.headers[ 0 ];
1746                                 break;
1747                         case keyCode.END:
1748                                 toFocus = this.headers[ length - 1 ];
1749                                 break;
1750                 }
1751
1752                 if ( toFocus ) {
1753                         $( event.target ).attr( "tabIndex", -1 );
1754                         $( toFocus ).attr( "tabIndex", 0 );
1755                         toFocus.focus();
1756                         event.preventDefault();
1757                 }
1758         },
1759
1760         _panelKeyDown: function( event ) {
1761                 if ( event.keyCode === $.ui.keyCode.UP && event.ctrlKey ) {
1762                         $( event.currentTarget ).prev().focus();
1763                 }
1764         },
1765
1766         refresh: function() {
1767                 var options = this.options;
1768                 this._processPanels();
1769
1770                 // was collapsed or no panel
1771                 if ( ( options.active === false && options.collapsible === true ) || !this.headers.length ) {
1772                         options.active = false;
1773                         this.active = $();
1774                 // active false only when collapsible is true
1775                 } else if ( options.active === false ) {
1776                         this._activate( 0 );
1777                 // was active, but active panel is gone
1778                 } else if ( this.active.length && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {
1779                         // all remaining panel are disabled
1780                         if ( this.headers.length === this.headers.find(".ui-state-disabled").length ) {
1781                                 options.active = false;
1782                                 this.active = $();
1783                         // activate previous panel
1784                         } else {
1785                                 this._activate( Math.max( 0, options.active - 1 ) );
1786                         }
1787                 // was active, active panel still exists
1788                 } else {
1789                         // make sure active index is correct
1790                         options.active = this.headers.index( this.active );
1791                 }
1792
1793                 this._destroyIcons();
1794
1795                 this._refresh();
1796         },
1797
1798         _processPanels: function() {
1799                 var prevHeaders = this.headers,
1800                         prevPanels = this.panels;
1801
1802                 this.headers = this.element.find( this.options.header )
1803                         .addClass( "ui-accordion-header ui-state-default ui-corner-all" );
1804
1805                 this.panels = this.headers.next()
1806                         .addClass( "ui-accordion-content ui-helper-reset ui-widget-content ui-corner-bottom" )
1807                         .filter( ":not(.ui-accordion-content-active)" )
1808                         .hide();
1809
1810                 // Avoid memory leaks (#10056)
1811                 if ( prevPanels ) {
1812                         this._off( prevHeaders.not( this.headers ) );
1813                         this._off( prevPanels.not( this.panels ) );
1814                 }
1815         },
1816
1817         _refresh: function() {
1818                 var maxHeight,
1819                         options = this.options,
1820                         heightStyle = options.heightStyle,
1821                         parent = this.element.parent();
1822
1823                 this.active = this._findActive( options.active )
1824                         .addClass( "ui-accordion-header-active ui-state-active ui-corner-top" )
1825                         .removeClass( "ui-corner-all" );
1826                 this.active.next()
1827                         .addClass( "ui-accordion-content-active" )
1828                         .show();
1829
1830                 this.headers
1831                         .attr( "role", "tab" )
1832                         .each(function() {
1833                                 var header = $( this ),
1834                                         headerId = header.uniqueId().attr( "id" ),
1835                                         panel = header.next(),
1836                                         panelId = panel.uniqueId().attr( "id" );
1837                                 header.attr( "aria-controls", panelId );
1838                                 panel.attr( "aria-labelledby", headerId );
1839                         })
1840                         .next()
1841                                 .attr( "role", "tabpanel" );
1842
1843                 this.headers
1844                         .not( this.active )
1845                         .attr({
1846                                 "aria-selected": "false",
1847                                 "aria-expanded": "false",
1848                                 tabIndex: -1
1849                         })
1850                         .next()
1851                                 .attr({
1852                                         "aria-hidden": "true"
1853                                 })
1854                                 .hide();
1855
1856                 // make sure at least one header is in the tab order
1857                 if ( !this.active.length ) {
1858                         this.headers.eq( 0 ).attr( "tabIndex", 0 );
1859                 } else {
1860                         this.active.attr({
1861                                 "aria-selected": "true",
1862                                 "aria-expanded": "true",
1863                                 tabIndex: 0
1864                         })
1865                         .next()
1866                                 .attr({
1867                                         "aria-hidden": "false"
1868                                 });
1869                 }
1870
1871                 this._createIcons();
1872
1873                 this._setupEvents( options.event );
1874
1875                 if ( heightStyle === "fill" ) {
1876                         maxHeight = parent.height();
1877                         this.element.siblings( ":visible" ).each(function() {
1878                                 var elem = $( this ),
1879                                         position = elem.css( "position" );
1880
1881                                 if ( position === "absolute" || position === "fixed" ) {
1882                                         return;
1883                                 }
1884                                 maxHeight -= elem.outerHeight( true );
1885                         });
1886
1887                         this.headers.each(function() {
1888                                 maxHeight -= $( this ).outerHeight( true );
1889                         });
1890
1891                         this.headers.next()
1892                                 .each(function() {
1893                                         $( this ).height( Math.max( 0, maxHeight -
1894                                                 $( this ).innerHeight() + $( this ).height() ) );
1895                                 })
1896                                 .css( "overflow", "auto" );
1897                 } else if ( heightStyle === "auto" ) {
1898                         maxHeight = 0;
1899                         this.headers.next()
1900                                 .each(function() {
1901                                         maxHeight = Math.max( maxHeight, $( this ).css( "height", "" ).height() );
1902                                 })
1903                                 .height( maxHeight );
1904                 }
1905         },
1906
1907         _activate: function( index ) {
1908                 var active = this._findActive( index )[ 0 ];
1909
1910                 // trying to activate the already active panel
1911                 if ( active === this.active[ 0 ] ) {
1912                         return;
1913                 }
1914
1915                 // trying to collapse, simulate a click on the currently active header
1916                 active = active || this.active[ 0 ];
1917
1918                 this._eventHandler({
1919                         target: active,
1920                         currentTarget: active,
1921                         preventDefault: $.noop
1922                 });
1923         },
1924
1925         _findActive: function( selector ) {
1926                 return typeof selector === "number" ? this.headers.eq( selector ) : $();
1927         },
1928
1929         _setupEvents: function( event ) {
1930                 var events = {
1931                         keydown: "_keydown"
1932                 };
1933                 if ( event ) {
1934                         $.each( event.split( " " ), function( index, eventName ) {
1935                                 events[ eventName ] = "_eventHandler";
1936                         });
1937                 }
1938
1939                 this._off( this.headers.add( this.headers.next() ) );
1940                 this._on( this.headers, events );
1941                 this._on( this.headers.next(), { keydown: "_panelKeyDown" });
1942                 this._hoverable( this.headers );
1943                 this._focusable( this.headers );
1944         },
1945
1946         _eventHandler: function( event ) {
1947                 var options = this.options,
1948                         active = this.active,
1949                         clicked = $( event.currentTarget ),
1950                         clickedIsActive = clicked[ 0 ] === active[ 0 ],
1951                         collapsing = clickedIsActive && options.collapsible,
1952                         toShow = collapsing ? $() : clicked.next(),
1953                         toHide = active.next(),
1954                         eventData = {
1955                                 oldHeader: active,
1956                                 oldPanel: toHide,
1957                                 newHeader: collapsing ? $() : clicked,
1958                                 newPanel: toShow
1959                         };
1960
1961                 event.preventDefault();
1962
1963                 if (
1964                                 // click on active header, but not collapsible
1965                                 ( clickedIsActive && !options.collapsible ) ||
1966                                 // allow canceling activation
1967                                 ( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
1968                         return;
1969                 }
1970
1971                 options.active = collapsing ? false : this.headers.index( clicked );
1972
1973                 // when the call to ._toggle() comes after the class changes
1974                 // it causes a very odd bug in IE 8 (see #6720)
1975                 this.active = clickedIsActive ? $() : clicked;
1976                 this._toggle( eventData );
1977
1978                 // switch classes
1979                 // corner classes on the previously active header stay after the animation
1980                 active.removeClass( "ui-accordion-header-active ui-state-active" );
1981                 if ( options.icons ) {
1982                         active.children( ".ui-accordion-header-icon" )
1983                                 .removeClass( options.icons.activeHeader )
1984                                 .addClass( options.icons.header );
1985                 }
1986
1987                 if ( !clickedIsActive ) {
1988                         clicked
1989                                 .removeClass( "ui-corner-all" )
1990                                 .addClass( "ui-accordion-header-active ui-state-active ui-corner-top" );
1991                         if ( options.icons ) {
1992                                 clicked.children( ".ui-accordion-header-icon" )
1993                                         .removeClass( options.icons.header )
1994                                         .addClass( options.icons.activeHeader );
1995                         }
1996
1997                         clicked
1998                                 .next()
1999                                 .addClass( "ui-accordion-content-active" );
2000                 }
2001         },
2002
2003         _toggle: function( data ) {
2004                 var toShow = data.newPanel,
2005                         toHide = this.prevShow.length ? this.prevShow : data.oldPanel;
2006
2007                 // handle activating a panel during the animation for another activation
2008                 this.prevShow.add( this.prevHide ).stop( true, true );
2009                 this.prevShow = toShow;
2010                 this.prevHide = toHide;
2011
2012                 if ( this.options.animate ) {
2013                         this._animate( toShow, toHide, data );
2014                 } else {
2015                         toHide.hide();
2016                         toShow.show();
2017                         this._toggleComplete( data );
2018                 }
2019
2020                 toHide.attr({
2021                         "aria-hidden": "true"
2022                 });
2023                 toHide.prev().attr({
2024                         "aria-selected": "false",
2025                         "aria-expanded": "false"
2026                 });
2027                 // if we're switching panels, remove the old header from the tab order
2028                 // if we're opening from collapsed state, remove the previous header from the tab order
2029                 // if we're collapsing, then keep the collapsing header in the tab order
2030                 if ( toShow.length && toHide.length ) {
2031                         toHide.prev().attr({
2032                                 "tabIndex": -1,
2033                                 "aria-expanded": "false"
2034                         });
2035                 } else if ( toShow.length ) {
2036                         this.headers.filter(function() {
2037                                 return parseInt( $( this ).attr( "tabIndex" ), 10 ) === 0;
2038                         })
2039                         .attr( "tabIndex", -1 );
2040                 }
2041
2042                 toShow
2043                         .attr( "aria-hidden", "false" )
2044                         .prev()
2045                                 .attr({
2046                                         "aria-selected": "true",
2047                                         "aria-expanded": "true",
2048                                         tabIndex: 0
2049                                 });
2050         },
2051
2052         _animate: function( toShow, toHide, data ) {
2053                 var total, easing, duration,
2054                         that = this,
2055                         adjust = 0,
2056                         boxSizing = toShow.css( "box-sizing" ),
2057                         down = toShow.length &&
2058                                 ( !toHide.length || ( toShow.index() < toHide.index() ) ),
2059                         animate = this.options.animate || {},
2060                         options = down && animate.down || animate,
2061                         complete = function() {
2062                                 that._toggleComplete( data );
2063                         };
2064
2065                 if ( typeof options === "number" ) {
2066                         duration = options;
2067                 }
2068                 if ( typeof options === "string" ) {
2069                         easing = options;
2070                 }
2071                 // fall back from options to animation in case of partial down settings
2072                 easing = easing || options.easing || animate.easing;
2073                 duration = duration || options.duration || animate.duration;
2074
2075                 if ( !toHide.length ) {
2076                         return toShow.animate( this.showProps, duration, easing, complete );
2077                 }
2078                 if ( !toShow.length ) {
2079                         return toHide.animate( this.hideProps, duration, easing, complete );
2080                 }
2081
2082                 total = toShow.show().outerHeight();
2083                 toHide.animate( this.hideProps, {
2084                         duration: duration,
2085                         easing: easing,
2086                         step: function( now, fx ) {
2087                                 fx.now = Math.round( now );
2088                         }
2089                 });
2090                 toShow
2091                         .hide()
2092                         .animate( this.showProps, {
2093                                 duration: duration,
2094                                 easing: easing,
2095                                 complete: complete,
2096                                 step: function( now, fx ) {
2097                                         fx.now = Math.round( now );
2098                                         if ( fx.prop !== "height" ) {
2099                                                 if ( boxSizing === "content-box" ) {
2100                                                         adjust += fx.now;
2101                                                 }
2102                                         } else if ( that.options.heightStyle !== "content" ) {
2103                                                 fx.now = Math.round( total - toHide.outerHeight() - adjust );
2104                                                 adjust = 0;
2105                                         }
2106                                 }
2107                         });
2108         },
2109
2110         _toggleComplete: function( data ) {
2111                 var toHide = data.oldPanel;
2112
2113                 toHide
2114                         .removeClass( "ui-accordion-content-active" )
2115                         .prev()
2116                                 .removeClass( "ui-corner-top" )
2117                                 .addClass( "ui-corner-all" );
2118
2119                 // Work around for rendering bug in IE (#5421)
2120                 if ( toHide.length ) {
2121                         toHide.parent()[ 0 ].className = toHide.parent()[ 0 ].className;
2122                 }
2123                 this._trigger( "activate", null, data );
2124         }
2125 });
2126
2127
2128 /*!
2129  * jQuery UI Menu 1.11.4
2130  * http://jqueryui.com
2131  *
2132  * Copyright jQuery Foundation and other contributors
2133  * Released under the MIT license.
2134  * http://jquery.org/license
2135  *
2136  * http://api.jqueryui.com/menu/
2137  */
2138
2139
2140 var menu = $.widget( "ui.menu", {
2141         version: "1.11.4",
2142         defaultElement: "<ul>",
2143         delay: 300,
2144         options: {
2145                 icons: {
2146                         submenu: "ui-icon-carat-1-e"
2147                 },
2148                 items: "> *",
2149                 menus: "ul",
2150                 position: {
2151                         my: "left-1 top",
2152                         at: "right top"
2153                 },
2154                 role: "menu",
2155
2156                 // callbacks
2157                 blur: null,
2158                 focus: null,
2159                 select: null
2160         },
2161
2162         _create: function() {
2163                 this.activeMenu = this.element;
2164
2165                 // Flag used to prevent firing of the click handler
2166                 // as the event bubbles up through nested menus
2167                 this.mouseHandled = false;
2168                 this.element
2169                         .uniqueId()
2170                         .addClass( "ui-menu ui-widget ui-widget-content" )
2171                         .toggleClass( "ui-menu-icons", !!this.element.find( ".ui-icon" ).length )
2172                         .attr({
2173                                 role: this.options.role,
2174                                 tabIndex: 0
2175                         });
2176
2177                 if ( this.options.disabled ) {
2178                         this.element
2179                                 .addClass( "ui-state-disabled" )
2180                                 .attr( "aria-disabled", "true" );
2181                 }
2182
2183                 this._on({
2184                         // Prevent focus from sticking to links inside menu after clicking
2185                         // them (focus should always stay on UL during navigation).
2186                         "mousedown .ui-menu-item": function( event ) {
2187                                 event.preventDefault();
2188                         },
2189                         "click .ui-menu-item": function( event ) {
2190                                 var target = $( event.target );
2191                                 if ( !this.mouseHandled && target.not( ".ui-state-disabled" ).length ) {
2192                                         this.select( event );
2193
2194                                         // Only set the mouseHandled flag if the event will bubble, see #9469.
2195                                         if ( !event.isPropagationStopped() ) {
2196                                                 this.mouseHandled = true;
2197                                         }
2198
2199                                         // Open submenu on click
2200                                         if ( target.has( ".ui-menu" ).length ) {
2201                                                 this.expand( event );
2202                                         } else if ( !this.element.is( ":focus" ) && $( this.document[ 0 ].activeElement ).closest( ".ui-menu" ).length ) {
2203
2204                                                 // Redirect focus to the menu
2205                                                 this.element.trigger( "focus", [ true ] );
2206
2207                                                 // If the active item is on the top level, let it stay active.
2208                                                 // Otherwise, blur the active item since it is no longer visible.
2209                                                 if ( this.active && this.active.parents( ".ui-menu" ).length === 1 ) {
2210                                                         clearTimeout( this.timer );
2211                                                 }
2212                                         }
2213                                 }
2214                         },
2215                         "mouseenter .ui-menu-item": function( event ) {
2216                                 // Ignore mouse events while typeahead is active, see #10458.
2217                                 // Prevents focusing the wrong item when typeahead causes a scroll while the mouse
2218                                 // is over an item in the menu
2219                                 if ( this.previousFilter ) {
2220                                         return;
2221                                 }
2222                                 var target = $( event.currentTarget );
2223                                 // Remove ui-state-active class from siblings of the newly focused menu item
2224                                 // to avoid a jump caused by adjacent elements both having a class with a border
2225                                 target.siblings( ".ui-state-active" ).removeClass( "ui-state-active" );
2226                                 this.focus( event, target );
2227                         },
2228                         mouseleave: "collapseAll",
2229                         "mouseleave .ui-menu": "collapseAll",
2230                         focus: function( event, keepActiveItem ) {
2231                                 // If there's already an active item, keep it active
2232                                 // If not, activate the first item
2233                                 var item = this.active || this.element.find( this.options.items ).eq( 0 );
2234
2235                                 if ( !keepActiveItem ) {
2236                                         this.focus( event, item );
2237                                 }
2238                         },
2239                         blur: function( event ) {
2240                                 this._delay(function() {
2241                                         if ( !$.contains( this.element[0], this.document[0].activeElement ) ) {
2242                                                 this.collapseAll( event );
2243                                         }
2244                                 });
2245                         },
2246                         keydown: "_keydown"
2247                 });
2248
2249                 this.refresh();
2250
2251                 // Clicks outside of a menu collapse any open menus
2252                 this._on( this.document, {
2253                         click: function( event ) {
2254                                 if ( this._closeOnDocumentClick( event ) ) {
2255                                         this.collapseAll( event );
2256                                 }
2257
2258                                 // Reset the mouseHandled flag
2259                                 this.mouseHandled = false;
2260                         }
2261                 });
2262         },
2263
2264         _destroy: function() {
2265                 // Destroy (sub)menus
2266                 this.element
2267                         .removeAttr( "aria-activedescendant" )
2268                         .find( ".ui-menu" ).addBack()
2269                                 .removeClass( "ui-menu ui-widget ui-widget-content ui-menu-icons ui-front" )
2270                                 .removeAttr( "role" )
2271                                 .removeAttr( "tabIndex" )
2272                                 .removeAttr( "aria-labelledby" )
2273                                 .removeAttr( "aria-expanded" )
2274                                 .removeAttr( "aria-hidden" )
2275                                 .removeAttr( "aria-disabled" )
2276                                 .removeUniqueId()
2277                                 .show();
2278
2279                 // Destroy menu items
2280                 this.element.find( ".ui-menu-item" )
2281                         .removeClass( "ui-menu-item" )
2282                         .removeAttr( "role" )
2283                         .removeAttr( "aria-disabled" )
2284                         .removeUniqueId()
2285                         .removeClass( "ui-state-hover" )
2286                         .removeAttr( "tabIndex" )
2287                         .removeAttr( "role" )
2288                         .removeAttr( "aria-haspopup" )
2289                         .children().each( function() {
2290                                 var elem = $( this );
2291                                 if ( elem.data( "ui-menu-submenu-carat" ) ) {
2292                                         elem.remove();
2293                                 }
2294                         });
2295
2296                 // Destroy menu dividers
2297                 this.element.find( ".ui-menu-divider" ).removeClass( "ui-menu-divider ui-widget-content" );
2298         },
2299
2300         _keydown: function( event ) {
2301                 var match, prev, character, skip,
2302                         preventDefault = true;
2303
2304                 switch ( event.keyCode ) {
2305                 case $.ui.keyCode.PAGE_UP:
2306                         this.previousPage( event );
2307                         break;
2308                 case $.ui.keyCode.PAGE_DOWN:
2309                         this.nextPage( event );
2310                         break;
2311                 case $.ui.keyCode.HOME:
2312                         this._move( "first", "first", event );
2313                         break;
2314                 case $.ui.keyCode.END:
2315                         this._move( "last", "last", event );
2316                         break;
2317                 case $.ui.keyCode.UP:
2318                         this.previous( event );
2319                         break;
2320                 case $.ui.keyCode.DOWN:
2321                         this.next( event );
2322                         break;
2323                 case $.ui.keyCode.LEFT:
2324                         this.collapse( event );
2325                         break;
2326                 case $.ui.keyCode.RIGHT:
2327                         if ( this.active && !this.active.is( ".ui-state-disabled" ) ) {
2328                                 this.expand( event );
2329                         }
2330                         break;
2331                 case $.ui.keyCode.ENTER:
2332                 case $.ui.keyCode.SPACE:
2333                         this._activate( event );
2334                         break;
2335                 case $.ui.keyCode.ESCAPE:
2336                         this.collapse( event );
2337                         break;
2338                 default:
2339                         preventDefault = false;
2340                         prev = this.previousFilter || "";
2341                         character = String.fromCharCode( event.keyCode );
2342                         skip = false;
2343
2344                         clearTimeout( this.filterTimer );
2345
2346                         if ( character === prev ) {
2347                                 skip = true;
2348                         } else {
2349                                 character = prev + character;
2350                         }
2351
2352                         match = this._filterMenuItems( character );
2353                         match = skip && match.index( this.active.next() ) !== -1 ?
2354                                 this.active.nextAll( ".ui-menu-item" ) :
2355                                 match;
2356
2357                         // If no matches on the current filter, reset to the last character pressed
2358                         // to move down the menu to the first item that starts with that character
2359                         if ( !match.length ) {
2360                                 character = String.fromCharCode( event.keyCode );
2361                                 match = this._filterMenuItems( character );
2362                         }
2363
2364                         if ( match.length ) {
2365                                 this.focus( event, match );
2366                                 this.previousFilter = character;
2367                                 this.filterTimer = this._delay(function() {
2368                                         delete this.previousFilter;
2369                                 }, 1000 );
2370                         } else {
2371                                 delete this.previousFilter;
2372                         }
2373                 }
2374
2375                 if ( preventDefault ) {
2376                         event.preventDefault();
2377                 }
2378         },
2379
2380         _activate: function( event ) {
2381                 if ( !this.active.is( ".ui-state-disabled" ) ) {
2382                         if ( this.active.is( "[aria-haspopup='true']" ) ) {
2383                                 this.expand( event );
2384                         } else {
2385                                 this.select( event );
2386                         }
2387                 }
2388         },
2389
2390         refresh: function() {
2391                 var menus, items,
2392                         that = this,
2393                         icon = this.options.icons.submenu,
2394                         submenus = this.element.find( this.options.menus );
2395
2396                 this.element.toggleClass( "ui-menu-icons", !!this.element.find( ".ui-icon" ).length );
2397
2398                 // Initialize nested menus
2399                 submenus.filter( ":not(.ui-menu)" )
2400                         .addClass( "ui-menu ui-widget ui-widget-content ui-front" )
2401                         .hide()
2402                         .attr({
2403                                 role: this.options.role,
2404                                 "aria-hidden": "true",
2405                                 "aria-expanded": "false"
2406                         })
2407                         .each(function() {
2408                                 var menu = $( this ),
2409                                         item = menu.parent(),
2410                                         submenuCarat = $( "<span>" )
2411                                                 .addClass( "ui-menu-icon ui-icon " + icon )
2412                                                 .data( "ui-menu-submenu-carat", true );
2413
2414                                 item
2415                                         .attr( "aria-haspopup", "true" )
2416                                         .prepend( submenuCarat );
2417                                 menu.attr( "aria-labelledby", item.attr( "id" ) );
2418                         });
2419
2420                 menus = submenus.add( this.element );
2421                 items = menus.find( this.options.items );
2422
2423                 // Initialize menu-items containing spaces and/or dashes only as dividers
2424                 items.not( ".ui-menu-item" ).each(function() {
2425                         var item = $( this );
2426                         if ( that._isDivider( item ) ) {
2427                                 item.addClass( "ui-widget-content ui-menu-divider" );
2428                         }
2429                 });
2430
2431                 // Don't refresh list items that are already adapted
2432                 items.not( ".ui-menu-item, .ui-menu-divider" )
2433                         .addClass( "ui-menu-item" )
2434                         .uniqueId()
2435                         .attr({
2436                                 tabIndex: -1,
2437                                 role: this._itemRole()
2438                         });
2439
2440                 // Add aria-disabled attribute to any disabled menu item
2441                 items.filter( ".ui-state-disabled" ).attr( "aria-disabled", "true" );
2442
2443                 // If the active item has been removed, blur the menu
2444                 if ( this.active && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) {
2445                         this.blur();
2446                 }
2447         },
2448
2449         _itemRole: function() {
2450                 return {
2451                         menu: "menuitem",
2452                         listbox: "option"
2453                 }[ this.options.role ];
2454         },
2455
2456         _setOption: function( key, value ) {
2457                 if ( key === "icons" ) {
2458                         this.element.find( ".ui-menu-icon" )
2459                                 .removeClass( this.options.icons.submenu )
2460                                 .addClass( value.submenu );
2461                 }
2462                 if ( key === "disabled" ) {
2463                         this.element
2464                                 .toggleClass( "ui-state-disabled", !!value )
2465                                 .attr( "aria-disabled", value );
2466                 }
2467                 this._super( key, value );
2468         },
2469
2470         focus: function( event, item ) {
2471                 var nested, focused;
2472                 this.blur( event, event && event.type === "focus" );
2473
2474                 this._scrollIntoView( item );
2475
2476                 this.active = item.first();
2477                 focused = this.active.addClass( "ui-state-focus" ).removeClass( "ui-state-active" );
2478                 // Only update aria-activedescendant if there's a role
2479                 // otherwise we assume focus is managed elsewhere
2480                 if ( this.options.role ) {
2481                         this.element.attr( "aria-activedescendant", focused.attr( "id" ) );
2482                 }
2483
2484                 // Highlight active parent menu item, if any
2485                 this.active
2486                         .parent()
2487                         .closest( ".ui-menu-item" )
2488                         .addClass( "ui-state-active" );
2489
2490                 if ( event && event.type === "keydown" ) {
2491                         this._close();
2492                 } else {
2493                         this.timer = this._delay(function() {
2494                                 this._close();
2495                         }, this.delay );
2496                 }
2497
2498                 nested = item.children( ".ui-menu" );
2499                 if ( nested.length && event && ( /^mouse/.test( event.type ) ) ) {
2500                         this._startOpening(nested);
2501                 }
2502                 this.activeMenu = item.parent();
2503
2504                 this._trigger( "focus", event, { item: item } );
2505         },
2506
2507         _scrollIntoView: function( item ) {
2508                 var borderTop, paddingTop, offset, scroll, elementHeight, itemHeight;
2509                 if ( this._hasScroll() ) {
2510                         borderTop = parseFloat( $.css( this.activeMenu[0], "borderTopWidth" ) ) || 0;
2511                         paddingTop = parseFloat( $.css( this.activeMenu[0], "paddingTop" ) ) || 0;
2512                         offset = item.offset().top - this.activeMenu.offset().top - borderTop - paddingTop;
2513                         scroll = this.activeMenu.scrollTop();
2514                         elementHeight = this.activeMenu.height();
2515                         itemHeight = item.outerHeight();
2516
2517                         if ( offset < 0 ) {
2518                                 this.activeMenu.scrollTop( scroll + offset );
2519                         } else if ( offset + itemHeight > elementHeight ) {
2520                                 this.activeMenu.scrollTop( scroll + offset - elementHeight + itemHeight );
2521                         }
2522                 }
2523         },
2524
2525         blur: function( event, fromFocus ) {
2526                 if ( !fromFocus ) {
2527                         clearTimeout( this.timer );
2528                 }
2529
2530                 if ( !this.active ) {
2531                         return;
2532                 }
2533
2534                 this.active.removeClass( "ui-state-focus" );
2535                 this.active = null;
2536
2537                 this._trigger( "blur", event, { item: this.active } );
2538         },
2539
2540         _startOpening: function( submenu ) {
2541                 clearTimeout( this.timer );
2542
2543                 // Don't open if already open fixes a Firefox bug that caused a .5 pixel
2544                 // shift in the submenu position when mousing over the carat icon
2545                 if ( submenu.attr( "aria-hidden" ) !== "true" ) {
2546                         return;
2547                 }
2548
2549                 this.timer = this._delay(function() {
2550                         this._close();
2551                         this._open( submenu );
2552                 }, this.delay );
2553         },
2554
2555         _open: function( submenu ) {
2556                 var position = $.extend({
2557                         of: this.active
2558                 }, this.options.position );
2559
2560                 clearTimeout( this.timer );
2561                 this.element.find( ".ui-menu" ).not( submenu.parents( ".ui-menu" ) )
2562                         .hide()
2563                         .attr( "aria-hidden", "true" );
2564
2565                 submenu
2566                         .show()
2567                         .removeAttr( "aria-hidden" )
2568                         .attr( "aria-expanded", "true" )
2569                         .position( position );
2570         },
2571
2572         collapseAll: function( event, all ) {
2573                 clearTimeout( this.timer );
2574                 this.timer = this._delay(function() {
2575                         // If we were passed an event, look for the submenu that contains the event
2576                         var currentMenu = all ? this.element :
2577                                 $( event && event.target ).closest( this.element.find( ".ui-menu" ) );
2578
2579                         // If we found no valid submenu ancestor, use the main menu to close all sub menus anyway
2580                         if ( !currentMenu.length ) {
2581                                 currentMenu = this.element;
2582                         }
2583
2584                         this._close( currentMenu );
2585
2586                         this.blur( event );
2587                         this.activeMenu = currentMenu;
2588                 }, this.delay );
2589         },
2590
2591         // With no arguments, closes the currently active menu - if nothing is active
2592         // it closes all menus.  If passed an argument, it will search for menus BELOW
2593         _close: function( startMenu ) {
2594                 if ( !startMenu ) {
2595                         startMenu = this.active ? this.active.parent() : this.element;
2596                 }
2597
2598                 startMenu
2599                         .find( ".ui-menu" )
2600                                 .hide()
2601                                 .attr( "aria-hidden", "true" )
2602                                 .attr( "aria-expanded", "false" )
2603                         .end()
2604                         .find( ".ui-state-active" ).not( ".ui-state-focus" )
2605                                 .removeClass( "ui-state-active" );
2606         },
2607
2608         _closeOnDocumentClick: function( event ) {
2609                 return !$( event.target ).closest( ".ui-menu" ).length;
2610         },
2611
2612         _isDivider: function( item ) {
2613
2614                 // Match hyphen, em dash, en dash
2615                 return !/[^\-\u2014\u2013\s]/.test( item.text() );
2616         },
2617
2618         collapse: function( event ) {
2619                 var newItem = this.active &&
2620                         this.active.parent().closest( ".ui-menu-item", this.element );
2621                 if ( newItem && newItem.length ) {
2622                         this._close();
2623                         this.focus( event, newItem );
2624                 }
2625         },
2626
2627         expand: function( event ) {
2628                 var newItem = this.active &&
2629                         this.active
2630                                 .children( ".ui-menu " )
2631                                 .find( this.options.items )
2632                                 .first();
2633
2634                 if ( newItem && newItem.length ) {
2635                         this._open( newItem.parent() );
2636
2637                         // Delay so Firefox will not hide activedescendant change in expanding submenu from AT
2638                         this._delay(function() {
2639                                 this.focus( event, newItem );
2640                         });
2641                 }
2642         },
2643
2644         next: function( event ) {
2645                 this._move( "next", "first", event );
2646         },
2647
2648         previous: function( event ) {
2649                 this._move( "prev", "last", event );
2650         },
2651
2652         isFirstItem: function() {
2653                 return this.active && !this.active.prevAll( ".ui-menu-item" ).length;
2654         },
2655
2656         isLastItem: function() {
2657                 return this.active && !this.active.nextAll( ".ui-menu-item" ).length;
2658         },
2659
2660         _move: function( direction, filter, event ) {
2661                 var next;
2662                 if ( this.active ) {
2663                         if ( direction === "first" || direction === "last" ) {
2664                                 next = this.active
2665                                         [ direction === "first" ? "prevAll" : "nextAll" ]( ".ui-menu-item" )
2666                                         .eq( -1 );
2667                         } else {
2668                                 next = this.active
2669                                         [ direction + "All" ]( ".ui-menu-item" )
2670                                         .eq( 0 );
2671                         }
2672                 }
2673                 if ( !next || !next.length || !this.active ) {
2674                         next = this.activeMenu.find( this.options.items )[ filter ]();
2675                 }
2676
2677                 this.focus( event, next );
2678         },
2679
2680         nextPage: function( event ) {
2681                 var item, base, height;
2682
2683                 if ( !this.active ) {
2684                         this.next( event );
2685                         return;
2686                 }
2687                 if ( this.isLastItem() ) {
2688                         return;
2689                 }
2690                 if ( this._hasScroll() ) {
2691                         base = this.active.offset().top;
2692                         height = this.element.height();
2693                         this.active.nextAll( ".ui-menu-item" ).each(function() {
2694                                 item = $( this );
2695                                 return item.offset().top - base - height < 0;
2696                         });
2697
2698                         this.focus( event, item );
2699                 } else {
2700                         this.focus( event, this.activeMenu.find( this.options.items )
2701                                 [ !this.active ? "first" : "last" ]() );
2702                 }
2703         },
2704
2705         previousPage: function( event ) {
2706                 var item, base, height;
2707                 if ( !this.active ) {
2708                         this.next( event );
2709                         return;
2710                 }
2711                 if ( this.isFirstItem() ) {
2712                         return;
2713                 }
2714                 if ( this._hasScroll() ) {
2715                         base = this.active.offset().top;
2716                         height = this.element.height();
2717                         this.active.prevAll( ".ui-menu-item" ).each(function() {
2718                                 item = $( this );
2719                                 return item.offset().top - base + height > 0;
2720                         });
2721
2722                         this.focus( event, item );
2723                 } else {
2724                         this.focus( event, this.activeMenu.find( this.options.items ).first() );
2725                 }
2726         },
2727
2728         _hasScroll: function() {
2729                 return this.element.outerHeight() < this.element.prop( "scrollHeight" );
2730         },
2731
2732         select: function( event ) {
2733                 // TODO: It should never be possible to not have an active item at this
2734                 // point, but the tests don't trigger mouseenter before click.
2735                 this.active = this.active || $( event.target ).closest( ".ui-menu-item" );
2736                 var ui = { item: this.active };
2737                 if ( !this.active.has( ".ui-menu" ).length ) {
2738                         this.collapseAll( event, true );
2739                 }
2740                 this._trigger( "select", event, ui );
2741         },
2742
2743         _filterMenuItems: function(character) {
2744                 var escapedCharacter = character.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" ),
2745                         regex = new RegExp( "^" + escapedCharacter, "i" );
2746
2747                 return this.activeMenu
2748                         .find( this.options.items )
2749
2750                         // Only match on items, not dividers or other content (#10571)
2751                         .filter( ".ui-menu-item" )
2752                         .filter(function() {
2753                                 return regex.test( $.trim( $( this ).text() ) );
2754                         });
2755         }
2756 });
2757
2758
2759 /*!
2760  * jQuery UI Autocomplete 1.11.4
2761  * http://jqueryui.com
2762  *
2763  * Copyright jQuery Foundation and other contributors
2764  * Released under the MIT license.
2765  * http://jquery.org/license
2766  *
2767  * http://api.jqueryui.com/autocomplete/
2768  */
2769
2770
2771 $.widget( "ui.autocomplete", {
2772         version: "1.11.4",
2773         defaultElement: "<input>",
2774         options: {
2775                 appendTo: null,
2776                 autoFocus: false,
2777                 delay: 300,
2778                 minLength: 1,
2779                 position: {
2780                         my: "left top",
2781                         at: "left bottom",
2782                         collision: "none"
2783                 },
2784                 source: null,
2785
2786                 // callbacks
2787                 change: null,
2788                 close: null,
2789                 focus: null,
2790                 open: null,
2791                 response: null,
2792                 search: null,
2793                 select: null
2794         },
2795
2796         requestIndex: 0,
2797         pending: 0,
2798
2799         _create: function() {
2800                 // Some browsers only repeat keydown events, not keypress events,
2801                 // so we use the suppressKeyPress flag to determine if we've already
2802                 // handled the keydown event. #7269
2803                 // Unfortunately the code for & in keypress is the same as the up arrow,
2804                 // so we use the suppressKeyPressRepeat flag to avoid handling keypress
2805                 // events when we know the keydown event was used to modify the
2806                 // search term. #7799
2807                 var suppressKeyPress, suppressKeyPressRepeat, suppressInput,
2808                         nodeName = this.element[ 0 ].nodeName.toLowerCase(),
2809                         isTextarea = nodeName === "textarea",
2810                         isInput = nodeName === "input";
2811
2812                 this.isMultiLine =
2813                         // Textareas are always multi-line
2814                         isTextarea ? true :
2815                         // Inputs are always single-line, even if inside a contentEditable element
2816                         // IE also treats inputs as contentEditable
2817                         isInput ? false :
2818                         // All other element types are determined by whether or not they're contentEditable
2819                         this.element.prop( "isContentEditable" );
2820
2821                 this.valueMethod = this.element[ isTextarea || isInput ? "val" : "text" ];
2822                 this.isNewMenu = true;
2823
2824                 this.element
2825                         .addClass( "ui-autocomplete-input" )
2826                         .attr( "autocomplete", "off" );
2827
2828                 this._on( this.element, {
2829                         keydown: function( event ) {
2830                                 if ( this.element.prop( "readOnly" ) ) {
2831                                         suppressKeyPress = true;
2832                                         suppressInput = true;
2833                                         suppressKeyPressRepeat = true;
2834                                         return;
2835                                 }
2836
2837                                 suppressKeyPress = false;
2838                                 suppressInput = false;
2839                                 suppressKeyPressRepeat = false;
2840                                 var keyCode = $.ui.keyCode;
2841                                 switch ( event.keyCode ) {
2842                                 case keyCode.PAGE_UP:
2843                                         suppressKeyPress = true;
2844                                         this._move( "previousPage", event );
2845                                         break;
2846                                 case keyCode.PAGE_DOWN:
2847                                         suppressKeyPress = true;
2848                                         this._move( "nextPage", event );
2849                                         break;
2850                                 case keyCode.UP:
2851                                         suppressKeyPress = true;
2852                                         this._keyEvent( "previous", event );
2853                                         break;
2854                                 case keyCode.DOWN:
2855                                         suppressKeyPress = true;
2856                                         this._keyEvent( "next", event );
2857                                         break;
2858                                 case keyCode.ENTER:
2859                                         // when menu is open and has focus
2860                                         if ( this.menu.active ) {
2861                                                 // #6055 - Opera still allows the keypress to occur
2862                                                 // which causes forms to submit
2863                                                 suppressKeyPress = true;
2864                                                 event.preventDefault();
2865                                                 this.menu.select( event );
2866                                         }
2867                                         break;
2868                                 case keyCode.TAB:
2869                                         if ( this.menu.active ) {
2870                                                 this.menu.select( event );
2871                                         }
2872                                         break;
2873                                 case keyCode.ESCAPE:
2874                                         if ( this.menu.element.is( ":visible" ) ) {
2875                                                 if ( !this.isMultiLine ) {
2876                                                         this._value( this.term );
2877                                                 }
2878                                                 this.close( event );
2879                                                 // Different browsers have different default behavior for escape
2880                                                 // Single press can mean undo or clear
2881                                                 // Double press in IE means clear the whole form
2882                                                 event.preventDefault();
2883                                         }
2884                                         break;
2885                                 default:
2886                                         suppressKeyPressRepeat = true;
2887                                         // search timeout should be triggered before the input value is changed
2888                                         this._searchTimeout( event );
2889                                         break;
2890                                 }
2891                         },
2892                         keypress: function( event ) {
2893                                 if ( suppressKeyPress ) {
2894                                         suppressKeyPress = false;
2895                                         if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
2896                                                 event.preventDefault();
2897                                         }
2898                                         return;
2899                                 }
2900                                 if ( suppressKeyPressRepeat ) {
2901                                         return;
2902                                 }
2903
2904                                 // replicate some key handlers to allow them to repeat in Firefox and Opera
2905                                 var keyCode = $.ui.keyCode;
2906                                 switch ( event.keyCode ) {
2907                                 case keyCode.PAGE_UP:
2908                                         this._move( "previousPage", event );
2909                                         break;
2910                                 case keyCode.PAGE_DOWN:
2911                                         this._move( "nextPage", event );
2912                                         break;
2913                                 case keyCode.UP:
2914                                         this._keyEvent( "previous", event );
2915                                         break;
2916                                 case keyCode.DOWN:
2917                                         this._keyEvent( "next", event );
2918                                         break;
2919                                 }
2920                         },
2921                         input: function( event ) {
2922                                 if ( suppressInput ) {
2923                                         suppressInput = false;
2924                                         event.preventDefault();
2925                                         return;
2926                                 }
2927                                 this._searchTimeout( event );
2928                         },
2929                         focus: function() {
2930                                 this.selectedItem = null;
2931                                 this.previous = this._value();
2932                         },
2933                         blur: function( event ) {
2934                                 if ( this.cancelBlur ) {
2935                                         delete this.cancelBlur;
2936                                         return;
2937                                 }
2938
2939                                 clearTimeout( this.searching );
2940                                 this.close( event );
2941                                 this._change( event );
2942                         }
2943                 });
2944
2945                 this._initSource();
2946                 this.menu = $( "<ul>" )
2947                         .addClass( "ui-autocomplete ui-front" )
2948                         .appendTo( this._appendTo() )
2949                         .menu({
2950                                 // disable ARIA support, the live region takes care of that
2951                                 role: null
2952                         })
2953                         .hide()
2954                         .menu( "instance" );
2955
2956                 this._on( this.menu.element, {
2957                         mousedown: function( event ) {
2958                                 // prevent moving focus out of the text field
2959                                 event.preventDefault();
2960
2961                                 // IE doesn't prevent moving focus even with event.preventDefault()
2962                                 // so we set a flag to know when we should ignore the blur event
2963                                 this.cancelBlur = true;
2964                                 this._delay(function() {
2965                                         delete this.cancelBlur;
2966                                 });
2967
2968                                 // clicking on the scrollbar causes focus to shift to the body
2969                                 // but we can't detect a mouseup or a click immediately afterward
2970                                 // so we have to track the next mousedown and close the menu if
2971                                 // the user clicks somewhere outside of the autocomplete
2972                                 var menuElement = this.menu.element[ 0 ];
2973                                 if ( !$( event.target ).closest( ".ui-menu-item" ).length ) {
2974                                         this._delay(function() {
2975                                                 var that = this;
2976                                                 this.document.one( "mousedown", function( event ) {
2977                                                         if ( event.target !== that.element[ 0 ] &&
2978                                                                         event.target !== menuElement &&
2979                                                                         !$.contains( menuElement, event.target ) ) {
2980                                                                 that.close();
2981                                                         }
2982                                                 });
2983                                         });
2984                                 }
2985                         },
2986                         menufocus: function( event, ui ) {
2987                                 var label, item;
2988                                 // support: Firefox
2989                                 // Prevent accidental activation of menu items in Firefox (#7024 #9118)
2990                                 if ( this.isNewMenu ) {
2991                                         this.isNewMenu = false;
2992                                         if ( event.originalEvent && /^mouse/.test( event.originalEvent.type ) ) {
2993                                                 this.menu.blur();
2994
2995                                                 this.document.one( "mousemove", function() {
2996                                                         $( event.target ).trigger( event.originalEvent );
2997                                                 });
2998
2999                                                 return;
3000                                         }
3001                                 }
3002
3003                                 item = ui.item.data( "ui-autocomplete-item" );
3004                                 if ( false !== this._trigger( "focus", event, { item: item } ) ) {
3005                                         // use value to match what will end up in the input, if it was a key event
3006                                         if ( event.originalEvent && /^key/.test( event.originalEvent.type ) ) {
3007                                                 this._value( item.value );
3008                                         }
3009                                 }
3010
3011                                 // Announce the value in the liveRegion
3012                                 label = ui.item.attr( "aria-label" ) || item.value;
3013                                 if ( label && $.trim( label ).length ) {
3014                                         this.liveRegion.children().hide();
3015                                         $( "<div>" ).text( label ).appendTo( this.liveRegion );
3016                                 }
3017                         },
3018                         menuselect: function( event, ui ) {
3019                                 var item = ui.item.data( "ui-autocomplete-item" ),
3020                                         previous = this.previous;
3021
3022                                 // only trigger when focus was lost (click on menu)
3023                                 if ( this.element[ 0 ] !== this.document[ 0 ].activeElement ) {
3024                                         this.element.focus();
3025                                         this.previous = previous;
3026                                         // #6109 - IE triggers two focus events and the second
3027                                         // is asynchronous, so we need to reset the previous
3028                                         // term synchronously and asynchronously :-(
3029                                         this._delay(function() {
3030                                                 this.previous = previous;
3031                                                 this.selectedItem = item;
3032                                         });
3033                                 }
3034
3035                                 if ( false !== this._trigger( "select", event, { item: item } ) ) {
3036                                         this._value( item.value );
3037                                 }
3038                                 // reset the term after the select event
3039                                 // this allows custom select handling to work properly
3040                                 this.term = this._value();
3041
3042                                 this.close( event );
3043                                 this.selectedItem = item;
3044                         }
3045                 });
3046
3047                 this.liveRegion = $( "<span>", {
3048                                 role: "status",
3049                                 "aria-live": "assertive",
3050                                 "aria-relevant": "additions"
3051                         })
3052                         .addClass( "ui-helper-hidden-accessible" )
3053                         .appendTo( this.document[ 0 ].body );
3054
3055                 // turning off autocomplete prevents the browser from remembering the
3056                 // value when navigating through history, so we re-enable autocomplete
3057                 // if the page is unloaded before the widget is destroyed. #7790
3058                 this._on( this.window, {
3059                         beforeunload: function() {
3060                                 this.element.removeAttr( "autocomplete" );
3061                         }
3062                 });
3063         },
3064
3065         _destroy: function() {
3066                 clearTimeout( this.searching );
3067                 this.element
3068                         .removeClass( "ui-autocomplete-input" )
3069                         .removeAttr( "autocomplete" );
3070                 this.menu.element.remove();
3071                 this.liveRegion.remove();
3072         },
3073
3074         _setOption: function( key, value ) {
3075                 this._super( key, value );
3076                 if ( key === "source" ) {
3077                         this._initSource();
3078                 }
3079                 if ( key === "appendTo" ) {
3080                         this.menu.element.appendTo( this._appendTo() );
3081                 }
3082                 if ( key === "disabled" && value && this.xhr ) {
3083                         this.xhr.abort();
3084                 }
3085         },
3086
3087         _appendTo: function() {
3088                 var element = this.options.appendTo;
3089
3090                 if ( element ) {
3091                         element = element.jquery || element.nodeType ?
3092                                 $( element ) :
3093                                 this.document.find( element ).eq( 0 );
3094                 }
3095
3096                 if ( !element || !element[ 0 ] ) {
3097                         element = this.element.closest( ".ui-front" );
3098                 }
3099
3100                 if ( !element.length ) {
3101                         element = this.document[ 0 ].body;
3102                 }
3103
3104                 return element;
3105         },
3106
3107         _initSource: function() {
3108                 var array, url,
3109                         that = this;
3110                 if ( $.isArray( this.options.source ) ) {
3111                         array = this.options.source;
3112                         this.source = function( request, response ) {
3113                                 response( $.ui.autocomplete.filter( array, request.term ) );
3114                         };
3115                 } else if ( typeof this.options.source === "string" ) {
3116                         url = this.options.source;
3117                         this.source = function( request, response ) {
3118                                 if ( that.xhr ) {
3119                                         that.xhr.abort();
3120                                 }
3121                                 that.xhr = $.ajax({
3122                                         url: url,
3123                                         data: request,
3124                                         dataType: "json",
3125                                         success: function( data ) {
3126                                                 response( data );
3127                                         },
3128                                         error: function() {
3129                                                 response([]);
3130                                         }
3131                                 });
3132                         };
3133                 } else {
3134                         this.source = this.options.source;
3135                 }
3136         },
3137
3138         _searchTimeout: function( event ) {
3139                 clearTimeout( this.searching );
3140                 this.searching = this._delay(function() {
3141
3142                         // Search if the value has changed, or if the user retypes the same value (see #7434)
3143                         var equalValues = this.term === this._value(),
3144                                 menuVisible = this.menu.element.is( ":visible" ),
3145                                 modifierKey = event.altKey || event.ctrlKey || event.metaKey || event.shiftKey;
3146
3147                         if ( !equalValues || ( equalValues && !menuVisible && !modifierKey ) ) {
3148                                 this.selectedItem = null;
3149                                 this.search( null, event );
3150                         }
3151                 }, this.options.delay );
3152         },
3153
3154         search: function( value, event ) {
3155                 value = value != null ? value : this._value();
3156
3157                 // always save the actual value, not the one passed as an argument
3158                 this.term = this._value();
3159
3160                 if ( value.length < this.options.minLength ) {
3161                         return this.close( event );
3162                 }
3163
3164                 if ( this._trigger( "search", event ) === false ) {
3165                         return;
3166                 }
3167
3168                 return this._search( value );
3169         },
3170
3171         _search: function( value ) {
3172                 this.pending++;
3173                 this.element.addClass( "ui-autocomplete-loading" );
3174                 this.cancelSearch = false;
3175
3176                 this.source( { term: value }, this._response() );
3177         },
3178
3179         _response: function() {
3180                 var index = ++this.requestIndex;
3181
3182                 return $.proxy(function( content ) {
3183                         if ( index === this.requestIndex ) {
3184                                 this.__response( content );
3185                         }
3186
3187                         this.pending--;
3188                         if ( !this.pending ) {
3189                                 this.element.removeClass( "ui-autocomplete-loading" );
3190                         }
3191                 }, this );
3192         },
3193
3194         __response: function( content ) {
3195                 if ( content ) {
3196                         content = this._normalize( content );
3197                 }
3198                 this._trigger( "response", null, { content: content } );
3199                 if ( !this.options.disabled && content && content.length && !this.cancelSearch ) {
3200                         this._suggest( content );
3201                         this._trigger( "open" );
3202                 } else {
3203                         // use ._close() instead of .close() so we don't cancel future searches
3204                         this._close();
3205                 }
3206         },
3207
3208         close: function( event ) {
3209                 this.cancelSearch = true;
3210                 this._close( event );
3211         },
3212
3213         _close: function( event ) {
3214                 if ( this.menu.element.is( ":visible" ) ) {
3215                         this.menu.element.hide();
3216                         this.menu.blur();
3217                         this.isNewMenu = true;
3218                         this._trigger( "close", event );
3219                 }
3220         },
3221
3222         _change: function( event ) {
3223                 if ( this.previous !== this._value() ) {
3224                         this._trigger( "change", event, { item: this.selectedItem } );
3225                 }
3226         },
3227
3228         _normalize: function( items ) {
3229                 // assume all items have the right format when the first item is complete
3230                 if ( items.length && items[ 0 ].label && items[ 0 ].value ) {
3231                         return items;
3232                 }
3233                 return $.map( items, function( item ) {
3234                         if ( typeof item === "string" ) {
3235                                 return {
3236                                         label: item,
3237                                         value: item
3238                                 };
3239                         }
3240                         return $.extend( {}, item, {
3241                                 label: item.label || item.value,
3242                                 value: item.value || item.label
3243                         });
3244                 });
3245         },
3246
3247         _suggest: function( items ) {
3248                 var ul = this.menu.element.empty();
3249                 this._renderMenu( ul, items );
3250                 this.isNewMenu = true;
3251                 this.menu.refresh();
3252
3253                 // size and position menu
3254                 ul.show();
3255                 this._resizeMenu();
3256                 ul.position( $.extend({
3257                         of: this.element
3258                 }, this.options.position ) );
3259
3260                 if ( this.options.autoFocus ) {
3261                         this.menu.next();
3262                 }
3263         },
3264
3265         _resizeMenu: function() {
3266                 var ul = this.menu.element;
3267                 ul.outerWidth( Math.max(
3268                         // Firefox wraps long text (possibly a rounding bug)
3269                         // so we add 1px to avoid the wrapping (#7513)
3270                         ul.width( "" ).outerWidth() + 1,
3271                         this.element.outerWidth()
3272                 ) );
3273         },
3274
3275         _renderMenu: function( ul, items ) {
3276                 var that = this;
3277                 $.each( items, function( index, item ) {
3278                         that._renderItemData( ul, item );
3279                 });
3280         },
3281
3282         _renderItemData: function( ul, item ) {
3283                 return this._renderItem( ul, item ).data( "ui-autocomplete-item", item );
3284         },
3285
3286         _renderItem: function( ul, item ) {
3287                 return $( "<li>" ).text( item.label ).appendTo( ul );
3288         },
3289
3290         _move: function( direction, event ) {
3291                 if ( !this.menu.element.is( ":visible" ) ) {
3292                         this.search( null, event );
3293                         return;
3294                 }
3295                 if ( this.menu.isFirstItem() && /^previous/.test( direction ) ||
3296                                 this.menu.isLastItem() && /^next/.test( direction ) ) {
3297
3298                         if ( !this.isMultiLine ) {
3299                                 this._value( this.term );
3300                         }
3301
3302                         this.menu.blur();
3303                         return;
3304                 }
3305                 this.menu[ direction ]( event );
3306         },
3307
3308         widget: function() {
3309                 return this.menu.element;
3310         },
3311
3312         _value: function() {
3313                 return this.valueMethod.apply( this.element, arguments );
3314         },
3315
3316         _keyEvent: function( keyEvent, event ) {
3317                 if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) {
3318                         this._move( keyEvent, event );
3319
3320                         // prevents moving cursor to beginning/end of the text field in some browsers
3321                         event.preventDefault();
3322                 }
3323         }
3324 });
3325
3326 $.extend( $.ui.autocomplete, {
3327         escapeRegex: function( value ) {
3328                 return value.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" );
3329         },
3330         filter: function( array, term ) {
3331                 var matcher = new RegExp( $.ui.autocomplete.escapeRegex( term ), "i" );
3332                 return $.grep( array, function( value ) {
3333                         return matcher.test( value.label || value.value || value );
3334                 });
3335         }
3336 });
3337
3338 // live region extension, adding a `messages` option
3339 // NOTE: This is an experimental API. We are still investigating
3340 // a full solution for string manipulation and internationalization.
3341 $.widget( "ui.autocomplete", $.ui.autocomplete, {
3342         options: {
3343                 messages: {
3344                         noResults: "No search results.",
3345                         results: function( amount ) {
3346                                 return amount + ( amount > 1 ? " results are" : " result is" ) +
3347                                         " available, use up and down arrow keys to navigate.";
3348                         }
3349                 }
3350         },
3351
3352         __response: function( content ) {
3353                 var message;
3354                 this._superApply( arguments );
3355                 if ( this.options.disabled || this.cancelSearch ) {
3356                         return;
3357                 }
3358                 if ( content && content.length ) {
3359                         message = this.options.messages.results( content.length );
3360                 } else {
3361                         message = this.options.messages.noResults;
3362                 }
3363                 this.liveRegion.children().hide();
3364                 $( "<div>" ).text( message ).appendTo( this.liveRegion );
3365         }
3366 });
3367
3368 var autocomplete = $.ui.autocomplete;
3369
3370
3371 /*!
3372  * jQuery UI Button 1.11.4
3373  * http://jqueryui.com
3374  *
3375  * Copyright jQuery Foundation and other contributors
3376  * Released under the MIT license.
3377  * http://jquery.org/license
3378  *
3379  * http://api.jqueryui.com/button/
3380  */
3381
3382
3383 var lastActive,
3384         baseClasses = "ui-button ui-widget ui-state-default ui-corner-all",
3385         typeClasses = "ui-button-icons-only ui-button-icon-only ui-button-text-icons ui-button-text-icon-primary ui-button-text-icon-secondary ui-button-text-only",
3386         formResetHandler = function() {
3387                 var form = $( this );
3388                 setTimeout(function() {
3389                         form.find( ":ui-button" ).button( "refresh" );
3390                 }, 1 );
3391         },
3392         radioGroup = function( radio ) {
3393                 var name = radio.name,
3394                         form = radio.form,
3395                         radios = $( [] );
3396                 if ( name ) {
3397                         name = name.replace( /'/g, "\\'" );
3398                         if ( form ) {
3399                                 radios = $( form ).find( "[name='" + name + "'][type=radio]" );
3400                         } else {
3401                                 radios = $( "[name='" + name + "'][type=radio]", radio.ownerDocument )
3402                                         .filter(function() {
3403                                                 return !this.form;
3404                                         });
3405                         }
3406                 }
3407                 return radios;
3408         };
3409
3410 $.widget( "ui.button", {
3411         version: "1.11.4",
3412         defaultElement: "<button>",
3413         options: {
3414                 disabled: null,
3415                 text: true,
3416                 label: null,
3417                 icons: {
3418                         primary: null,
3419                         secondary: null
3420                 }
3421         },
3422         _create: function() {
3423                 this.element.closest( "form" )
3424                         .unbind( "reset" + this.eventNamespace )
3425                         .bind( "reset" + this.eventNamespace, formResetHandler );
3426
3427                 if ( typeof this.options.disabled !== "boolean" ) {
3428                         this.options.disabled = !!this.element.prop( "disabled" );
3429                 } else {
3430                         this.element.prop( "disabled", this.options.disabled );
3431                 }
3432
3433                 this._determineButtonType();
3434                 this.hasTitle = !!this.buttonElement.attr( "title" );
3435
3436                 var that = this,
3437                         options = this.options,
3438                         toggleButton = this.type === "checkbox" || this.type === "radio",
3439                         activeClass = !toggleButton ? "ui-state-active" : "";
3440
3441                 if ( options.label === null ) {
3442                         options.label = (this.type === "input" ? this.buttonElement.val() : this.buttonElement.html());
3443                 }
3444
3445                 this._hoverable( this.buttonElement );
3446
3447                 this.buttonElement
3448                         .addClass( baseClasses )
3449                         .attr( "role", "button" )
3450                         .bind( "mouseenter" + this.eventNamespace, function() {
3451                                 if ( options.disabled ) {
3452                                         return;
3453                                 }
3454                                 if ( this === lastActive ) {
3455                                         $( this ).addClass( "ui-state-active" );
3456                                 }
3457                         })
3458                         .bind( "mouseleave" + this.eventNamespace, function() {
3459                                 if ( options.disabled ) {
3460                                         return;
3461                                 }
3462                                 $( this ).removeClass( activeClass );
3463                         })
3464                         .bind( "click" + this.eventNamespace, function( event ) {
3465                                 if ( options.disabled ) {
3466                                         event.preventDefault();
3467                                         event.stopImmediatePropagation();
3468                                 }
3469                         });
3470
3471                 // Can't use _focusable() because the element that receives focus
3472                 // and the element that gets the ui-state-focus class are different
3473                 this._on({
3474                         focus: function() {
3475                                 this.buttonElement.addClass( "ui-state-focus" );
3476                         },
3477                         blur: function() {
3478                                 this.buttonElement.removeClass( "ui-state-focus" );
3479                         }
3480                 });
3481
3482                 if ( toggleButton ) {
3483                         this.element.bind( "change" + this.eventNamespace, function() {
3484                                 that.refresh();
3485                         });
3486                 }
3487
3488                 if ( this.type === "checkbox" ) {
3489                         this.buttonElement.bind( "click" + this.eventNamespace, function() {
3490                                 if ( options.disabled ) {
3491                                         return false;
3492                                 }
3493                         });
3494                 } else if ( this.type === "radio" ) {
3495                         this.buttonElement.bind( "click" + this.eventNamespace, function() {
3496                                 if ( options.disabled ) {
3497                                         return false;
3498                                 }
3499                                 $( this ).addClass( "ui-state-active" );
3500                                 that.buttonElement.attr( "aria-pressed", "true" );
3501
3502                                 var radio = that.element[ 0 ];
3503                                 radioGroup( radio )
3504                                         .not( radio )
3505                                         .map(function() {
3506                                                 return $( this ).button( "widget" )[ 0 ];
3507                                         })
3508                                         .removeClass( "ui-state-active" )
3509                                         .attr( "aria-pressed", "false" );
3510                         });
3511                 } else {
3512                         this.buttonElement
3513                                 .bind( "mousedown" + this.eventNamespace, function() {
3514                                         if ( options.disabled ) {
3515                                                 return false;
3516                                         }
3517                                         $( this ).addClass( "ui-state-active" );
3518                                         lastActive = this;
3519                                         that.document.one( "mouseup", function() {
3520                                                 lastActive = null;
3521                                         });
3522                                 })
3523                                 .bind( "mouseup" + this.eventNamespace, function() {
3524                                         if ( options.disabled ) {
3525                                                 return false;
3526                                         }
3527                                         $( this ).removeClass( "ui-state-active" );
3528                                 })
3529                                 .bind( "keydown" + this.eventNamespace, function(event) {
3530                                         if ( options.disabled ) {
3531                                                 return false;
3532                                         }
3533                                         if ( event.keyCode === $.ui.keyCode.SPACE || event.keyCode === $.ui.keyCode.ENTER ) {
3534                                                 $( this ).addClass( "ui-state-active" );
3535                                         }
3536                                 })
3537                                 // see #8559, we bind to blur here in case the button element loses
3538                                 // focus between keydown and keyup, it would be left in an "active" state
3539                                 .bind( "keyup" + this.eventNamespace + " blur" + this.eventNamespace, function() {
3540                                         $( this ).removeClass( "ui-state-active" );
3541                                 });
3542
3543                         if ( this.buttonElement.is("a") ) {
3544                                 this.buttonElement.keyup(function(event) {
3545                                         if ( event.keyCode === $.ui.keyCode.SPACE ) {
3546                                                 // TODO pass through original event correctly (just as 2nd argument doesn't work)
3547                                                 $( this ).click();
3548                                         }
3549                                 });
3550                         }
3551                 }
3552
3553                 this._setOption( "disabled", options.disabled );
3554                 this._resetButton();
3555         },
3556
3557         _determineButtonType: function() {
3558                 var ancestor, labelSelector, checked;
3559
3560                 if ( this.element.is("[type=checkbox]") ) {
3561                         this.type = "checkbox";
3562                 } else if ( this.element.is("[type=radio]") ) {
3563                         this.type = "radio";
3564                 } else if ( this.element.is("input") ) {
3565                         this.type = "input";
3566                 } else {
3567                         this.type = "button";
3568                 }
3569
3570                 if ( this.type === "checkbox" || this.type === "radio" ) {
3571                         // we don't search against the document in case the element
3572                         // is disconnected from the DOM
3573                         ancestor = this.element.parents().last();
3574                         labelSelector = "label[for='" + this.element.attr("id") + "']";
3575                         this.buttonElement = ancestor.find( labelSelector );
3576                         if ( !this.buttonElement.length ) {
3577                                 ancestor = ancestor.length ? ancestor.siblings() : this.element.siblings();
3578                                 this.buttonElement = ancestor.filter( labelSelector );
3579                                 if ( !this.buttonElement.length ) {
3580                                         this.buttonElement = ancestor.find( labelSelector );
3581                                 }
3582                         }
3583                         this.element.addClass( "ui-helper-hidden-accessible" );
3584
3585                         checked = this.element.is( ":checked" );
3586                         if ( checked ) {
3587                                 this.buttonElement.addClass( "ui-state-active" );
3588                         }
3589                         this.buttonElement.prop( "aria-pressed", checked );
3590                 } else {
3591                         this.buttonElement = this.element;
3592                 }
3593         },
3594
3595         widget: function() {
3596                 return this.buttonElement;
3597         },
3598
3599         _destroy: function() {
3600                 this.element
3601                         .removeClass( "ui-helper-hidden-accessible" );
3602                 this.buttonElement
3603                         .removeClass( baseClasses + " ui-state-active " + typeClasses )
3604                         .removeAttr( "role" )
3605                         .removeAttr( "aria-pressed" )
3606                         .html( this.buttonElement.find(".ui-button-text").html() );
3607
3608                 if ( !this.hasTitle ) {
3609                         this.buttonElement.removeAttr( "title" );
3610                 }
3611         },
3612
3613         _setOption: function( key, value ) {
3614                 this._super( key, value );
3615                 if ( key === "disabled" ) {
3616                         this.widget().toggleClass( "ui-state-disabled", !!value );
3617                         this.element.prop( "disabled", !!value );
3618                         if ( value ) {
3619                                 if ( this.type === "checkbox" || this.type === "radio" ) {
3620                                         this.buttonElement.removeClass( "ui-state-focus" );
3621                                 } else {
3622                                         this.buttonElement.removeClass( "ui-state-focus ui-state-active" );
3623                                 }
3624                         }
3625                         return;
3626                 }
3627                 this._resetButton();
3628         },
3629
3630         refresh: function() {
3631                 //See #8237 & #8828
3632                 var isDisabled = this.element.is( "input, button" ) ? this.element.is( ":disabled" ) : this.element.hasClass( "ui-button-disabled" );
3633
3634                 if ( isDisabled !== this.options.disabled ) {
3635                         this._setOption( "disabled", isDisabled );
3636                 }
3637                 if ( this.type === "radio" ) {
3638                         radioGroup( this.element[0] ).each(function() {
3639                                 if ( $( this ).is( ":checked" ) ) {
3640                                         $( this ).button( "widget" )
3641                                                 .addClass( "ui-state-active" )
3642                                                 .attr( "aria-pressed", "true" );
3643                                 } else {
3644                                         $( this ).button( "widget" )
3645                                                 .removeClass( "ui-state-active" )
3646                                                 .attr( "aria-pressed", "false" );
3647                                 }
3648                         });
3649                 } else if ( this.type === "checkbox" ) {
3650                         if ( this.element.is( ":checked" ) ) {
3651                                 this.buttonElement
3652                                         .addClass( "ui-state-active" )
3653                                         .attr( "aria-pressed", "true" );
3654                         } else {
3655                                 this.buttonElement
3656                                         .removeClass( "ui-state-active" )
3657                                         .attr( "aria-pressed", "false" );
3658                         }
3659                 }
3660         },
3661
3662         _resetButton: function() {
3663                 if ( this.type === "input" ) {
3664                         if ( this.options.label ) {
3665                                 this.element.val( this.options.label );
3666                         }
3667                         return;
3668                 }
3669                 var buttonElement = this.buttonElement.removeClass( typeClasses ),
3670                         buttonText = $( "<span></span>", this.document[0] )
3671                                 .addClass( "ui-button-text" )
3672                                 .html( this.options.label )
3673                                 .appendTo( buttonElement.empty() )
3674                                 .text(),
3675                         icons = this.options.icons,
3676                         multipleIcons = icons.primary && icons.secondary,
3677                         buttonClasses = [];
3678
3679                 if ( icons.primary || icons.secondary ) {
3680                         if ( this.options.text ) {
3681                                 buttonClasses.push( "ui-button-text-icon" + ( multipleIcons ? "s" : ( icons.primary ? "-primary" : "-secondary" ) ) );
3682                         }
3683
3684                         if ( icons.primary ) {
3685                                 buttonElement.prepend( "<span class='ui-button-icon-primary ui-icon " + icons.primary + "'></span>" );
3686                         }
3687
3688                         if ( icons.secondary ) {
3689                                 buttonElement.append( "<span class='ui-button-icon-secondary ui-icon " + icons.secondary + "'></span>" );
3690                         }
3691
3692                         if ( !this.options.text ) {
3693                                 buttonClasses.push( multipleIcons ? "ui-button-icons-only" : "ui-button-icon-only" );
3694
3695                                 if ( !this.hasTitle ) {
3696                                         buttonElement.attr( "title", $.trim( buttonText ) );
3697                                 }
3698                         }
3699                 } else {
3700                         buttonClasses.push( "ui-button-text-only" );
3701                 }
3702                 buttonElement.addClass( buttonClasses.join( " " ) );
3703         }
3704 });
3705
3706 $.widget( "ui.buttonset", {
3707         version: "1.11.4",
3708         options: {
3709                 items: "button, input[type=button], input[type=submit], input[type=reset], input[type=checkbox], input[type=radio], a, :data(ui-button)"
3710         },
3711
3712         _create: function() {
3713                 this.element.addClass( "ui-buttonset" );
3714         },
3715
3716         _init: function() {
3717                 this.refresh();
3718         },
3719
3720         _setOption: function( key, value ) {
3721                 if ( key === "disabled" ) {
3722                         this.buttons.button( "option", key, value );
3723                 }
3724
3725                 this._super( key, value );
3726         },
3727
3728         refresh: function() {
3729                 var rtl = this.element.css( "direction" ) === "rtl",
3730                         allButtons = this.element.find( this.options.items ),
3731                         existingButtons = allButtons.filter( ":ui-button" );
3732
3733                 // Initialize new buttons
3734                 allButtons.not( ":ui-button" ).button();
3735
3736                 // Refresh existing buttons
3737                 existingButtons.button( "refresh" );
3738
3739                 this.buttons = allButtons
3740                         .map(function() {
3741                                 return $( this ).button( "widget" )[ 0 ];
3742                         })
3743                                 .removeClass( "ui-corner-all ui-corner-left ui-corner-right" )
3744                                 .filter( ":first" )
3745                                         .addClass( rtl ? "ui-corner-right" : "ui-corner-left" )
3746                                 .end()
3747                                 .filter( ":last" )
3748                                         .addClass( rtl ? "ui-corner-left" : "ui-corner-right" )
3749                                 .end()
3750                         .end();
3751         },
3752
3753         _destroy: function() {
3754                 this.element.removeClass( "ui-buttonset" );
3755                 this.buttons
3756                         .map(function() {
3757                                 return $( this ).button( "widget" )[ 0 ];
3758                         })
3759                                 .removeClass( "ui-corner-left ui-corner-right" )
3760                         .end()
3761                         .button( "destroy" );
3762         }
3763 });
3764
3765 var button = $.ui.button;
3766
3767
3768 /*!
3769  * jQuery UI Datepicker 1.11.4
3770  * http://jqueryui.com
3771  *
3772  * Copyright jQuery Foundation and other contributors
3773  * Released under the MIT license.
3774  * http://jquery.org/license
3775  *
3776  * http://api.jqueryui.com/datepicker/
3777  */
3778
3779
3780 $.extend($.ui, { datepicker: { version: "1.11.4" } });
3781
3782 var datepicker_instActive;
3783
3784 function datepicker_getZindex( elem ) {
3785         var position, value;
3786         while ( elem.length && elem[ 0 ] !== document ) {
3787                 // Ignore z-index if position is set to a value where z-index is ignored by the browser
3788                 // This makes behavior of this function consistent across browsers
3789                 // WebKit always returns auto if the element is positioned
3790                 position = elem.css( "position" );
3791                 if ( position === "absolute" || position === "relative" || position === "fixed" ) {
3792                         // IE returns 0 when zIndex is not specified
3793                         // other browsers return a string
3794                         // we ignore the case of nested elements with an explicit value of 0
3795                         // <div style="z-index: -10;"><div style="z-index: 0;"></div></div>
3796                         value = parseInt( elem.css( "zIndex" ), 10 );
3797                         if ( !isNaN( value ) && value !== 0 ) {
3798                                 return value;
3799                         }
3800                 }
3801                 elem = elem.parent();
3802         }
3803
3804         return 0;
3805 }
3806 /* Date picker manager.
3807    Use the singleton instance of this class, $.datepicker, to interact with the date picker.
3808    Settings for (groups of) date pickers are maintained in an instance object,
3809    allowing multiple different settings on the same page. */
3810
3811 function Datepicker() {
3812         this._curInst = null; // The current instance in use
3813         this._keyEvent = false; // If the last event was a key event
3814         this._disabledInputs = []; // List of date picker inputs that have been disabled
3815         this._datepickerShowing = false; // True if the popup picker is showing , false if not
3816         this._inDialog = false; // True if showing within a "dialog", false if not
3817         this._mainDivId = "ui-datepicker-div"; // The ID of the main datepicker division
3818         this._inlineClass = "ui-datepicker-inline"; // The name of the inline marker class
3819         this._appendClass = "ui-datepicker-append"; // The name of the append marker class
3820         this._triggerClass = "ui-datepicker-trigger"; // The name of the trigger marker class
3821         this._dialogClass = "ui-datepicker-dialog"; // The name of the dialog marker class
3822         this._disableClass = "ui-datepicker-disabled"; // The name of the disabled covering marker class
3823         this._unselectableClass = "ui-datepicker-unselectable"; // The name of the unselectable cell marker class
3824         this._currentClass = "ui-datepicker-current-day"; // The name of the current day marker class
3825         this._dayOverClass = "ui-datepicker-days-cell-over"; // The name of the day hover marker class
3826         this.regional = []; // Available regional settings, indexed by language code
3827         this.regional[""] = { // Default regional settings
3828                 closeText: "Done", // Display text for close link
3829                 prevText: "Prev", // Display text for previous month link
3830                 nextText: "Next", // Display text for next month link
3831                 currentText: "Today", // Display text for current month link
3832                 monthNames: ["January","February","March","April","May","June",
3833                         "July","August","September","October","November","December"], // Names of months for drop-down and formatting
3834                 monthNamesShort: ["Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"], // For formatting
3835                 dayNames: ["Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"], // For formatting
3836                 dayNamesShort: ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"], // For formatting
3837                 dayNamesMin: ["Su","Mo","Tu","We","Th","Fr","Sa"], // Column headings for days starting at Sunday
3838                 weekHeader: "Wk", // Column header for week of the year
3839                 dateFormat: "mm/dd/yy", // See format options on parseDate
3840                 firstDay: 0, // The first day of the week, Sun = 0, Mon = 1, ...
3841                 isRTL: false, // True if right-to-left language, false if left-to-right
3842                 showMonthAfterYear: false, // True if the year select precedes month, false for month then year
3843                 yearSuffix: "" // Additional text to append to the year in the month headers
3844         };
3845         this._defaults = { // Global defaults for all the date picker instances
3846                 showOn: "focus", // "focus" for popup on focus,
3847                         // "button" for trigger button, or "both" for either
3848                 showAnim: "fadeIn", // Name of jQuery animation for popup
3849                 showOptions: {}, // Options for enhanced animations
3850                 defaultDate: null, // Used when field is blank: actual date,
3851                         // +/-number for offset from today, null for today
3852                 appendText: "", // Display text following the input box, e.g. showing the format
3853                 buttonText: "...", // Text for trigger button
3854                 buttonImage: "", // URL for trigger button image
3855                 buttonImageOnly: false, // True if the image appears alone, false if it appears on a button
3856                 hideIfNoPrevNext: false, // True to hide next/previous month links
3857                         // if not applicable, false to just disable them
3858                 navigationAsDateFormat: false, // True if date formatting applied to prev/today/next links
3859                 gotoCurrent: false, // True if today link goes back to current selection instead
3860                 changeMonth: false, // True if month can be selected directly, false if only prev/next
3861                 changeYear: false, // True if year can be selected directly, false if only prev/next
3862                 yearRange: "c-10:c+10", // Range of years to display in drop-down,
3863                         // either relative to today's year (-nn:+nn), relative to currently displayed year
3864                         // (c-nn:c+nn), absolute (nnnn:nnnn), or a combination of the above (nnnn:-n)
3865                 showOtherMonths: false, // True to show dates in other months, false to leave blank
3866                 selectOtherMonths: false, // True to allow selection of dates in other months, false for unselectable
3867                 showWeek: false, // True to show week of the year, false to not show it
3868                 calculateWeek: this.iso8601Week, // How to calculate the week of the year,
3869                         // takes a Date and returns the number of the week for it
3870                 shortYearCutoff: "+10", // Short year values < this are in the current century,
3871                         // > this are in the previous century,
3872                         // string value starting with "+" for current year + value
3873                 minDate: null, // The earliest selectable date, or null for no limit
3874                 maxDate: null, // The latest selectable date, or null for no limit
3875                 duration: "fast", // Duration of display/closure
3876                 beforeShowDay: null, // Function that takes a date and returns an array with
3877                         // [0] = true if selectable, false if not, [1] = custom CSS class name(s) or "",
3878                         // [2] = cell title (optional), e.g. $.datepicker.noWeekends
3879                 beforeShow: null, // Function that takes an input field and
3880                         // returns a set of custom settings for the date picker
3881                 onSelect: null, // Define a callback function when a date is selected
3882                 onChangeMonthYear: null, // Define a callback function when the month or year is changed
3883                 onClose: null, // Define a callback function when the datepicker is closed
3884                 numberOfMonths: 1, // Number of months to show at a time
3885                 showCurrentAtPos: 0, // The position in multipe months at which to show the current month (starting at 0)
3886                 stepMonths: 1, // Number of months to step back/forward
3887                 stepBigMonths: 12, // Number of months to step back/forward for the big links
3888                 altField: "", // Selector for an alternate field to store selected dates into
3889                 altFormat: "", // The date format to use for the alternate field
3890                 constrainInput: true, // The input is constrained by the current date format
3891                 showButtonPanel: false, // True to show button panel, false to not show it
3892                 autoSize: false, // True to size the input for the date format, false to leave as is
3893                 disabled: false // The initial disabled state
3894         };
3895         $.extend(this._defaults, this.regional[""]);
3896         this.regional.en = $.extend( true, {}, this.regional[ "" ]);
3897         this.regional[ "en-US" ] = $.extend( true, {}, this.regional.en );
3898         this.dpDiv = datepicker_bindHover($("<div id='" + this._mainDivId + "' class='ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>"));
3899 }
3900
3901 $.extend(Datepicker.prototype, {
3902         /* Class name added to elements to indicate already configured with a date picker. */
3903         markerClassName: "hasDatepicker",
3904
3905         //Keep track of the maximum number of rows displayed (see #7043)
3906         maxRows: 4,
3907
3908         // TODO rename to "widget" when switching to widget factory
3909         _widgetDatepicker: function() {
3910                 return this.dpDiv;
3911         },
3912
3913         /* Override the default settings for all instances of the date picker.
3914          * @param  settings  object - the new settings to use as defaults (anonymous object)
3915          * @return the manager object
3916          */
3917         setDefaults: function(settings) {
3918                 datepicker_extendRemove(this._defaults, settings || {});
3919                 return this;
3920         },
3921
3922         /* Attach the date picker to a jQuery selection.
3923          * @param  target       element - the target input field or division or span
3924          * @param  settings  object - the new settings to use for this date picker instance (anonymous)
3925          */
3926         _attachDatepicker: function(target, settings) {
3927                 var nodeName, inline, inst;
3928                 nodeName = target.nodeName.toLowerCase();
3929                 inline = (nodeName === "div" || nodeName === "span");
3930                 if (!target.id) {
3931                         this.uuid += 1;
3932                         target.id = "dp" + this.uuid;
3933                 }
3934                 inst = this._newInst($(target), inline);
3935                 inst.settings = $.extend({}, settings || {});
3936                 if (nodeName === "input") {
3937                         this._connectDatepicker(target, inst);
3938                 } else if (inline) {
3939                         this._inlineDatepicker(target, inst);
3940                 }
3941         },
3942
3943         /* Create a new instance object. */
3944         _newInst: function(target, inline) {
3945                 var id = target[0].id.replace(/([^A-Za-z0-9_\-])/g, "\\\\$1"); // escape jQuery meta chars
3946                 return {id: id, input: target, // associated target
3947                         selectedDay: 0, selectedMonth: 0, selectedYear: 0, // current selection
3948                         drawMonth: 0, drawYear: 0, // month being drawn
3949                         inline: inline, // is datepicker inline or not
3950                         dpDiv: (!inline ? this.dpDiv : // presentation div
3951                         datepicker_bindHover($("<div class='" + this._inlineClass + " ui-datepicker ui-widget ui-widget-content ui-helper-clearfix ui-corner-all'></div>")))};
3952         },
3953
3954         /* Attach the date picker to an input field. */
3955         _connectDatepicker: function(target, inst) {
3956                 var input = $(target);
3957                 inst.append = $([]);
3958                 inst.trigger = $([]);
3959                 if (input.hasClass(this.markerClassName)) {
3960                         return;
3961                 }
3962                 this._attachments(input, inst);
3963                 input.addClass(this.markerClassName).keydown(this._doKeyDown).
3964                         keypress(this._doKeyPress).keyup(this._doKeyUp);
3965                 this._autoSize(inst);
3966                 $.data(target, "datepicker", inst);
3967                 //If disabled option is true, disable the datepicker once it has been attached to the input (see ticket #5665)
3968                 if( inst.settings.disabled ) {
3969                         this._disableDatepicker( target );
3970                 }
3971         },
3972
3973         /* Make attachments based on settings. */
3974         _attachments: function(input, inst) {
3975                 var showOn, buttonText, buttonImage,
3976                         appendText = this._get(inst, "appendText"),
3977                         isRTL = this._get(inst, "isRTL");
3978
3979                 if (inst.append) {
3980                         inst.append.remove();
3981                 }
3982                 if (appendText) {
3983                         inst.append = $("<span class='" + this._appendClass + "'>" + appendText + "</span>");
3984                         input[isRTL ? "before" : "after"](inst.append);
3985                 }
3986
3987                 input.unbind("focus", this._showDatepicker);
3988
3989                 if (inst.trigger) {
3990                         inst.trigger.remove();
3991                 }
3992
3993                 showOn = this._get(inst, "showOn");
3994                 if (showOn === "focus" || showOn === "both") { // pop-up date picker when in the marked field
3995                         input.focus(this._showDatepicker);
3996                 }
3997                 if (showOn === "button" || showOn === "both") { // pop-up date picker when button clicked
3998                         buttonText = this._get(inst, "buttonText");
3999                         buttonImage = this._get(inst, "buttonImage");
4000                         inst.trigger = $(this._get(inst, "buttonImageOnly") ?
4001                                 $("<img/>").addClass(this._triggerClass).
4002                                         attr({ src: buttonImage, alt: buttonText, title: buttonText }) :
4003                                 $("<button type='button'></button>").addClass(this._triggerClass).
4004                                         html(!buttonImage ? buttonText : $("<img/>").attr(
4005                                         { src:buttonImage, alt:buttonText, title:buttonText })));
4006                         input[isRTL ? "before" : "after"](inst.trigger);
4007                         inst.trigger.click(function() {
4008                                 if ($.datepicker._datepickerShowing && $.datepicker._lastInput === input[0]) {
4009                                         $.datepicker._hideDatepicker();
4010                                 } else if ($.datepicker._datepickerShowing && $.datepicker._lastInput !== input[0]) {
4011                                         $.datepicker._hideDatepicker();
4012                                         $.datepicker._showDatepicker(input[0]);
4013                                 } else {
4014                                         $.datepicker._showDatepicker(input[0]);
4015                                 }
4016                                 return false;
4017                         });
4018                 }
4019         },
4020
4021         /* Apply the maximum length for the date format. */
4022         _autoSize: function(inst) {
4023                 if (this._get(inst, "autoSize") && !inst.inline) {
4024                         var findMax, max, maxI, i,
4025                                 date = new Date(2009, 12 - 1, 20), // Ensure double digits
4026                                 dateFormat = this._get(inst, "dateFormat");
4027
4028                         if (dateFormat.match(/[DM]/)) {
4029                                 findMax = function(names) {
4030                                         max = 0;
4031                                         maxI = 0;
4032                                         for (i = 0; i < names.length; i++) {
4033                                                 if (names[i].length > max) {
4034                                                         max = names[i].length;
4035                                                         maxI = i;
4036                                                 }
4037                                         }
4038                                         return maxI;
4039                                 };
4040                                 date.setMonth(findMax(this._get(inst, (dateFormat.match(/MM/) ?
4041                                         "monthNames" : "monthNamesShort"))));
4042                                 date.setDate(findMax(this._get(inst, (dateFormat.match(/DD/) ?
4043                                         "dayNames" : "dayNamesShort"))) + 20 - date.getDay());
4044                         }
4045                         inst.input.attr("size", this._formatDate(inst, date).length);
4046                 }
4047         },
4048
4049         /* Attach an inline date picker to a div. */
4050         _inlineDatepicker: function(target, inst) {
4051                 var divSpan = $(target);
4052                 if (divSpan.hasClass(this.markerClassName)) {
4053                         return;
4054                 }
4055                 divSpan.addClass(this.markerClassName).append(inst.dpDiv);
4056                 $.data(target, "datepicker", inst);
4057                 this._setDate(inst, this._getDefaultDate(inst), true);
4058                 this._updateDatepicker(inst);
4059                 this._updateAlternate(inst);
4060                 //If disabled option is true, disable the datepicker before showing it (see ticket #5665)
4061                 if( inst.settings.disabled ) {
4062                         this._disableDatepicker( target );
4063                 }
4064                 // Set display:block in place of inst.dpDiv.show() which won't work on disconnected elements
4065                 // http://bugs.jqueryui.com/ticket/7552 - A Datepicker created on a detached div has zero height
4066                 inst.dpDiv.css( "display", "block" );
4067         },
4068
4069         /* Pop-up the date picker in a "dialog" box.
4070          * @param  input element - ignored
4071          * @param  date string or Date - the initial date to display
4072          * @param  onSelect  function - the function to call when a date is selected
4073          * @param  settings  object - update the dialog date picker instance's settings (anonymous object)
4074          * @param  pos int[2] - coordinates for the dialog's position within the screen or
4075          *                                      event - with x/y coordinates or
4076          *                                      leave empty for default (screen centre)
4077          * @return the manager object
4078          */
4079         _dialogDatepicker: function(input, date, onSelect, settings, pos) {
4080                 var id, browserWidth, browserHeight, scrollX, scrollY,
4081                         inst = this._dialogInst; // internal instance
4082
4083                 if (!inst) {
4084                         this.uuid += 1;
4085                         id = "dp" + this.uuid;
4086                         this._dialogInput = $("<input type='text' id='" + id +
4087                                 "' style='position: absolute; top: -100px; width: 0px;'/>");
4088                         this._dialogInput.keydown(this._doKeyDown);
4089                         $("body").append(this._dialogInput);
4090                         inst = this._dialogInst = this._newInst(this._dialogInput, false);
4091                         inst.settings = {};
4092                         $.data(this._dialogInput[0], "datepicker", inst);
4093                 }
4094                 datepicker_extendRemove(inst.settings, settings || {});
4095                 date = (date && date.constructor === Date ? this._formatDate(inst, date) : date);
4096                 this._dialogInput.val(date);
4097
4098                 this._pos = (pos ? (pos.length ? pos : [pos.pageX, pos.pageY]) : null);
4099                 if (!this._pos) {
4100                         browserWidth = document.documentElement.clientWidth;
4101                         browserHeight = document.documentElement.clientHeight;
4102                         scrollX = document.documentElement.scrollLeft || document.body.scrollLeft;
4103                         scrollY = document.documentElement.scrollTop || document.body.scrollTop;
4104                         this._pos = // should use actual width/height below
4105                                 [(browserWidth / 2) - 100 + scrollX, (browserHeight / 2) - 150 + scrollY];
4106                 }
4107
4108                 // move input on screen for focus, but hidden behind dialog
4109                 this._dialogInput.css("left", (this._pos[0] + 20) + "px").css("top", this._pos[1] + "px");
4110                 inst.settings.onSelect = onSelect;
4111                 this._inDialog = true;
4112                 this.dpDiv.addClass(this._dialogClass);
4113                 this._showDatepicker(this._dialogInput[0]);
4114                 if ($.blockUI) {
4115                         $.blockUI(this.dpDiv);
4116                 }
4117                 $.data(this._dialogInput[0], "datepicker", inst);
4118                 return this;
4119         },
4120
4121         /* Detach a datepicker from its control.
4122          * @param  target       element - the target input field or division or span
4123          */
4124         _destroyDatepicker: function(target) {
4125                 var nodeName,
4126                         $target = $(target),
4127                         inst = $.data(target, "datepicker");
4128
4129                 if (!$target.hasClass(this.markerClassName)) {
4130                         return;
4131                 }
4132
4133                 nodeName = target.nodeName.toLowerCase();
4134                 $.removeData(target, "datepicker");
4135                 if (nodeName === "input") {
4136                         inst.append.remove();
4137                         inst.trigger.remove();
4138                         $target.removeClass(this.markerClassName).
4139                                 unbind("focus", this._showDatepicker).
4140                                 unbind("keydown", this._doKeyDown).
4141                                 unbind("keypress", this._doKeyPress).
4142                                 unbind("keyup", this._doKeyUp);
4143                 } else if (nodeName === "div" || nodeName === "span") {
4144                         $target.removeClass(this.markerClassName).empty();
4145                 }
4146
4147                 if ( datepicker_instActive === inst ) {
4148                         datepicker_instActive = null;
4149                 }
4150         },
4151
4152         /* Enable the date picker to a jQuery selection.
4153          * @param  target       element - the target input field or division or span
4154          */
4155         _enableDatepicker: function(target) {
4156                 var nodeName, inline,
4157                         $target = $(target),
4158                         inst = $.data(target, "datepicker");
4159
4160                 if (!$target.hasClass(this.markerClassName)) {
4161                         return;
4162                 }
4163
4164                 nodeName = target.nodeName.toLowerCase();
4165                 if (nodeName === "input") {
4166                         target.disabled = false;
4167                         inst.trigger.filter("button").
4168                                 each(function() { this.disabled = false; }).end().
4169                                 filter("img").css({opacity: "1.0", cursor: ""});
4170                 } else if (nodeName === "div" || nodeName === "span") {
4171                         inline = $target.children("." + this._inlineClass);
4172                         inline.children().removeClass("ui-state-disabled");
4173                         inline.find("select.ui-datepicker-month, select.ui-datepicker-year").
4174                                 prop("disabled", false);
4175                 }
4176                 this._disabledInputs = $.map(this._disabledInputs,
4177                         function(value) { return (value === target ? null : value); }); // delete entry
4178         },
4179
4180         /* Disable the date picker to a jQuery selection.
4181          * @param  target       element - the target input field or division or span
4182          */
4183         _disableDatepicker: function(target) {
4184                 var nodeName, inline,
4185                         $target = $(target),
4186                         inst = $.data(target, "datepicker");
4187
4188                 if (!$target.hasClass(this.markerClassName)) {
4189                         return;
4190                 }
4191
4192                 nodeName = target.nodeName.toLowerCase();
4193                 if (nodeName === "input") {
4194                         target.disabled = true;
4195                         inst.trigger.filter("button").
4196                                 each(function() { this.disabled = true; }).end().
4197                                 filter("img").css({opacity: "0.5", cursor: "default"});
4198                 } else if (nodeName === "div" || nodeName === "span") {
4199                         inline = $target.children("." + this._inlineClass);
4200                         inline.children().addClass("ui-state-disabled");
4201                         inline.find("select.ui-datepicker-month, select.ui-datepicker-year").
4202                                 prop("disabled", true);
4203                 }
4204                 this._disabledInputs = $.map(this._disabledInputs,
4205                         function(value) { return (value === target ? null : value); }); // delete entry
4206                 this._disabledInputs[this._disabledInputs.length] = target;
4207         },
4208
4209         /* Is the first field in a jQuery collection disabled as a datepicker?
4210          * @param  target       element - the target input field or division or span
4211          * @return boolean - true if disabled, false if enabled
4212          */
4213         _isDisabledDatepicker: function(target) {
4214                 if (!target) {
4215                         return false;
4216                 }
4217                 for (var i = 0; i < this._disabledInputs.length; i++) {
4218                         if (this._disabledInputs[i] === target) {
4219                                 return true;
4220                         }
4221                 }
4222                 return false;
4223         },
4224
4225         /* Retrieve the instance data for the target control.
4226          * @param  target  element - the target input field or division or span
4227          * @return  object - the associated instance data
4228          * @throws  error if a jQuery problem getting data
4229          */
4230         _getInst: function(target) {
4231                 try {
4232                         return $.data(target, "datepicker");
4233                 }
4234                 catch (err) {
4235                         throw "Missing instance data for this datepicker";
4236                 }
4237         },
4238
4239         /* Update or retrieve the settings for a date picker attached to an input field or division.
4240          * @param  target  element - the target input field or division or span
4241          * @param  name object - the new settings to update or
4242          *                              string - the name of the setting to change or retrieve,
4243          *                              when retrieving also "all" for all instance settings or
4244          *                              "defaults" for all global defaults
4245          * @param  value   any - the new value for the setting
4246          *                              (omit if above is an object or to retrieve a value)
4247          */
4248         _optionDatepicker: function(target, name, value) {
4249                 var settings, date, minDate, maxDate,
4250                         inst = this._getInst(target);
4251
4252                 if (arguments.length === 2 && typeof name === "string") {
4253                         return (name === "defaults" ? $.extend({}, $.datepicker._defaults) :
4254                                 (inst ? (name === "all" ? $.extend({}, inst.settings) :
4255                                 this._get(inst, name)) : null));
4256                 }
4257
4258                 settings = name || {};
4259                 if (typeof name === "string") {
4260                         settings = {};
4261                         settings[name] = value;
4262                 }
4263
4264                 if (inst) {
4265                         if (this._curInst === inst) {
4266                                 this._hideDatepicker();
4267                         }
4268
4269                         date = this._getDateDatepicker(target, true);
4270                         minDate = this._getMinMaxDate(inst, "min");
4271                         maxDate = this._getMinMaxDate(inst, "max");
4272                         datepicker_extendRemove(inst.settings, settings);
4273                         // reformat the old minDate/maxDate values if dateFormat changes and a new minDate/maxDate isn't provided
4274                         if (minDate !== null && settings.dateFormat !== undefined && settings.minDate === undefined) {
4275                                 inst.settings.minDate = this._formatDate(inst, minDate);
4276                         }
4277                         if (maxDate !== null && settings.dateFormat !== undefined && settings.maxDate === undefined) {
4278                                 inst.settings.maxDate = this._formatDate(inst, maxDate);
4279                         }
4280                         if ( "disabled" in settings ) {
4281                                 if ( settings.disabled ) {
4282                                         this._disableDatepicker(target);
4283                                 } else {
4284                                         this._enableDatepicker(target);
4285                                 }
4286                         }
4287                         this._attachments($(target), inst);
4288                         this._autoSize(inst);
4289                         this._setDate(inst, date);
4290                         this._updateAlternate(inst);
4291                         this._updateDatepicker(inst);
4292                 }
4293         },
4294
4295         // change method deprecated
4296         _changeDatepicker: function(target, name, value) {
4297                 this._optionDatepicker(target, name, value);
4298         },
4299
4300         /* Redraw the date picker attached to an input field or division.
4301          * @param  target  element - the target input field or division or span
4302          */
4303         _refreshDatepicker: function(target) {
4304                 var inst = this._getInst(target);
4305                 if (inst) {
4306                         this._updateDatepicker(inst);
4307                 }
4308         },
4309
4310         /* Set the dates for a jQuery selection.
4311          * @param  target element - the target input field or division or span
4312          * @param  date Date - the new date
4313          */
4314         _setDateDatepicker: function(target, date) {
4315                 var inst = this._getInst(target);
4316                 if (inst) {
4317                         this._setDate(inst, date);
4318                         this._updateDatepicker(inst);
4319                         this._updateAlternate(inst);
4320                 }
4321         },
4322
4323         /* Get the date(s) for the first entry in a jQuery selection.
4324          * @param  target element - the target input field or division or span
4325          * @param  noDefault boolean - true if no default date is to be used
4326          * @return Date - the current date
4327          */
4328         _getDateDatepicker: function(target, noDefault) {
4329                 var inst = this._getInst(target);
4330                 if (inst && !inst.inline) {
4331                         this._setDateFromField(inst, noDefault);
4332                 }
4333                 return (inst ? this._getDate(inst) : null);
4334         },
4335
4336         /* Handle keystrokes. */
4337         _doKeyDown: function(event) {
4338                 var onSelect, dateStr, sel,
4339                         inst = $.datepicker._getInst(event.target),
4340                         handled = true,
4341                         isRTL = inst.dpDiv.is(".ui-datepicker-rtl");
4342
4343                 inst._keyEvent = true;
4344                 if ($.datepicker._datepickerShowing) {
4345                         switch (event.keyCode) {
4346                                 case 9: $.datepicker._hideDatepicker();
4347                                                 handled = false;
4348                                                 break; // hide on tab out
4349                                 case 13: sel = $("td." + $.datepicker._dayOverClass + ":not(." +
4350                                                                         $.datepicker._currentClass + ")", inst.dpDiv);
4351                                                 if (sel[0]) {
4352                                                         $.datepicker._selectDay(event.target, inst.selectedMonth, inst.selectedYear, sel[0]);
4353                                                 }
4354
4355                                                 onSelect = $.datepicker._get(inst, "onSelect");
4356                                                 if (onSelect) {
4357                                                         dateStr = $.datepicker._formatDate(inst);
4358
4359                                                         // trigger custom callback
4360                                                         onSelect.apply((inst.input ? inst.input[0] : null), [dateStr, inst]);
4361                                                 } else {
4362                                                         $.datepicker._hideDatepicker();
4363                                                 }
4364
4365                                                 return false; // don't submit the form
4366                                 case 27: $.datepicker._hideDatepicker();
4367                                                 break; // hide on escape
4368                                 case 33: $.datepicker._adjustDate(event.target, (event.ctrlKey ?
4369                                                         -$.datepicker._get(inst, "stepBigMonths") :
4370                                                         -$.datepicker._get(inst, "stepMonths")), "M");
4371                                                 break; // previous month/year on page up/+ ctrl
4372                                 case 34: $.datepicker._adjustDate(event.target, (event.ctrlKey ?
4373                                                         +$.datepicker._get(inst, "stepBigMonths") :
4374                                                         +$.datepicker._get(inst, "stepMonths")), "M");
4375                                                 break; // next month/year on page down/+ ctrl
4376                                 case 35: if (event.ctrlKey || event.metaKey) {
4377                                                         $.datepicker._clearDate(event.target);
4378                                                 }
4379                                                 handled = event.ctrlKey || event.metaKey;
4380                                                 break; // clear on ctrl or command +end
4381                                 case 36: if (event.ctrlKey || event.metaKey) {
4382                                                         $.datepicker._gotoToday(event.target);
4383                                                 }
4384                                                 handled = event.ctrlKey || event.metaKey;
4385                                                 break; // current on ctrl or command +home
4386                                 case 37: if (event.ctrlKey || event.metaKey) {
4387                                                         $.datepicker._adjustDate(event.target, (isRTL ? +1 : -1), "D");
4388                                                 }
4389                                                 handled = event.ctrlKey || event.metaKey;
4390                                                 // -1 day on ctrl or command +left
4391                                                 if (event.originalEvent.altKey) {
4392                                                         $.datepicker._adjustDate(event.target, (event.ctrlKey ?
4393                                                                 -$.datepicker._get(inst, "stepBigMonths") :
4394                                                                 -$.datepicker._get(inst, "stepMonths")), "M");
4395                                                 }
4396                                                 // next month/year on alt +left on Mac
4397                                                 break;
4398                                 case 38: if (event.ctrlKey || event.metaKey) {
4399                                                         $.datepicker._adjustDate(event.target, -7, "D");
4400                                                 }
4401                                                 handled = event.ctrlKey || event.metaKey;
4402                                                 break; // -1 week on ctrl or command +up
4403                                 case 39: if (event.ctrlKey || event.metaKey) {
4404                                                         $.datepicker._adjustDate(event.target, (isRTL ? -1 : +1), "D");
4405                                                 }
4406                                                 handled = event.ctrlKey || event.metaKey;
4407                                                 // +1 day on ctrl or command +right
4408                                                 if (event.originalEvent.altKey) {
4409                                                         $.datepicker._adjustDate(event.target, (event.ctrlKey ?
4410                                                                 +$.datepicker._get(inst, "stepBigMonths") :
4411                                                                 +$.datepicker._get(inst, "stepMonths")), "M");
4412                                                 }
4413                                                 // next month/year on alt +right
4414                                                 break;
4415                                 case 40: if (event.ctrlKey || event.metaKey) {
4416                                                         $.datepicker._adjustDate(event.target, +7, "D");
4417                                                 }
4418                                                 handled = event.ctrlKey || event.metaKey;
4419                                                 break; // +1 week on ctrl or command +down
4420                                 default: handled = false;
4421                         }
4422                 } else if (event.keyCode === 36 && event.ctrlKey) { // display the date picker on ctrl+home
4423                         $.datepicker._showDatepicker(this);
4424                 } else {
4425                         handled = false;
4426                 }
4427
4428                 if (handled) {
4429                         event.preventDefault();
4430                         event.stopPropagation();
4431                 }
4432         },
4433
4434         /* Filter entered characters - based on date format. */
4435         _doKeyPress: function(event) {
4436                 var chars, chr,
4437                         inst = $.datepicker._getInst(event.target);
4438
4439                 if ($.datepicker._get(inst, "constrainInput")) {
4440                         chars = $.datepicker._possibleChars($.datepicker._get(inst, "dateFormat"));
4441                         chr = String.fromCharCode(event.charCode == null ? event.keyCode : event.charCode);
4442                         return event.ctrlKey || event.metaKey || (chr < " " || !chars || chars.indexOf(chr) > -1);
4443                 }
4444         },
4445
4446         /* Synchronise manual entry and field/alternate field. */
4447         _doKeyUp: function(event) {
4448                 var date,
4449                         inst = $.datepicker._getInst(event.target);
4450
4451                 if (inst.input.val() !== inst.lastVal) {
4452                         try {
4453                                 date = $.datepicker.parseDate($.datepicker._get(inst, "dateFormat"),
4454                                         (inst.input ? inst.input.val() : null),
4455                                         $.datepicker._getFormatConfig(inst));
4456
4457                                 if (date) { // only if valid
4458                                         $.datepicker._setDateFromField(inst);
4459                                         $.datepicker._updateAlternate(inst);
4460                                         $.datepicker._updateDatepicker(inst);
4461                                 }
4462                         }
4463                         catch (err) {
4464                         }
4465                 }
4466                 return true;
4467         },
4468
4469         /* Pop-up the date picker for a given input field.
4470          * If false returned from beforeShow event handler do not show.
4471          * @param  input  element - the input field attached to the date picker or
4472          *                                      event - if triggered by focus
4473          */
4474         _showDatepicker: function(input) {
4475                 input = input.target || input;
4476                 if (input.nodeName.toLowerCase() !== "input") { // find from button/image trigger
4477                         input = $("input", input.parentNode)[0];
4478                 }
4479
4480                 if ($.datepicker._isDisabledDatepicker(input) || $.datepicker._lastInput === input) { // already here
4481                         return;
4482                 }
4483
4484                 var inst, beforeShow, beforeShowSettings, isFixed,
4485                         offset, showAnim, duration;
4486
4487                 inst = $.datepicker._getInst(input);
4488                 if ($.datepicker._curInst && $.datepicker._curInst !== inst) {
4489                         $.datepicker._curInst.dpDiv.stop(true, true);
4490                         if ( inst && $.datepicker._datepickerShowing ) {
4491                                 $.datepicker._hideDatepicker( $.datepicker._curInst.input[0] );
4492                         }
4493                 }
4494
4495                 beforeShow = $.datepicker._get(inst, "beforeShow");
4496                 beforeShowSettings = beforeShow ? beforeShow.apply(input, [input, inst]) : {};
4497                 if(beforeShowSettings === false){
4498                         return;
4499                 }
4500                 datepicker_extendRemove(inst.settings, beforeShowSettings);
4501
4502                 inst.lastVal = null;
4503                 $.datepicker._lastInput = input;
4504                 $.datepicker._setDateFromField(inst);
4505
4506                 if ($.datepicker._inDialog) { // hide cursor
4507                         input.value = "";
4508                 }
4509                 if (!$.datepicker._pos) { // position below input
4510                         $.datepicker._pos = $.datepicker._findPos(input);
4511                         $.datepicker._pos[1] += input.offsetHeight; // add the height
4512                 }
4513
4514                 isFixed = false;
4515                 $(input).parents().each(function() {
4516                         isFixed |= $(this).css("position") === "fixed";
4517                         return !isFixed;
4518                 });
4519
4520                 offset = {left: $.datepicker._pos[0], top: $.datepicker._pos[1]};
4521                 $.datepicker._pos = null;
4522                 //to avoid flashes on Firefox
4523                 inst.dpDiv.empty();
4524                 // determine sizing offscreen
4525                 inst.dpDiv.css({position: "absolute", display: "block", top: "-1000px"});
4526                 $.datepicker._updateDatepicker(inst);
4527                 // fix width for dynamic number of date pickers
4528                 // and adjust position before showing
4529                 offset = $.datepicker._checkOffset(inst, offset, isFixed);
4530                 inst.dpDiv.css({position: ($.datepicker._inDialog && $.blockUI ?
4531                         "static" : (isFixed ? "fixed" : "absolute")), display: "none",
4532                         left: offset.left + "px", top: offset.top + "px"});
4533
4534                 if (!inst.inline) {
4535                         showAnim = $.datepicker._get(inst, "showAnim");
4536                         duration = $.datepicker._get(inst, "duration");
4537                         inst.dpDiv.css( "z-index", datepicker_getZindex( $( input ) ) + 1 );
4538                         $.datepicker._datepickerShowing = true;
4539
4540                         if ( $.effects && $.effects.effect[ showAnim ] ) {
4541                                 inst.dpDiv.show(showAnim, $.datepicker._get(inst, "showOptions"), duration);
4542                         } else {
4543                                 inst.dpDiv[showAnim || "show"](showAnim ? duration : null);
4544                         }
4545
4546                         if ( $.datepicker._shouldFocusInput( inst ) ) {
4547                                 inst.input.focus();
4548                         }
4549
4550                         $.datepicker._curInst = inst;
4551                 }
4552         },
4553
4554         /* Generate the date picker content. */
4555         _updateDatepicker: function(inst) {
4556                 this.maxRows = 4; //Reset the max number of rows being displayed (see #7043)
4557                 datepicker_instActive = inst; // for delegate hover events
4558                 inst.dpDiv.empty().append(this._generateHTML(inst));
4559                 this._attachHandlers(inst);
4560
4561                 var origyearshtml,
4562                         numMonths = this._getNumberOfMonths(inst),
4563                         cols = numMonths[1],
4564                         width = 17,
4565                         activeCell = inst.dpDiv.find( "." + this._dayOverClass + " a" );
4566
4567                 if ( activeCell.length > 0 ) {
4568                         datepicker_handleMouseover.apply( activeCell.get( 0 ) );
4569                 }
4570
4571                 inst.dpDiv.removeClass("ui-datepicker-multi-2 ui-datepicker-multi-3 ui-datepicker-multi-4").width("");
4572                 if (cols > 1) {
4573                         inst.dpDiv.addClass("ui-datepicker-multi-" + cols).css("width", (width * cols) + "em");
4574                 }
4575                 inst.dpDiv[(numMonths[0] !== 1 || numMonths[1] !== 1 ? "add" : "remove") +
4576                         "Class"]("ui-datepicker-multi");
4577                 inst.dpDiv[(this._get(inst, "isRTL") ? "add" : "remove") +
4578                         "Class"]("ui-datepicker-rtl");
4579
4580                 if (inst === $.datepicker._curInst && $.datepicker._datepickerShowing && $.datepicker._shouldFocusInput( inst ) ) {
4581                         inst.input.focus();
4582                 }
4583
4584                 // deffered render of the years select (to avoid flashes on Firefox)
4585                 if( inst.yearshtml ){
4586                         origyearshtml = inst.yearshtml;
4587                         setTimeout(function(){
4588                                 //assure that inst.yearshtml didn't change.
4589                                 if( origyearshtml === inst.yearshtml && inst.yearshtml ){
4590                                         inst.dpDiv.find("select.ui-datepicker-year:first").replaceWith(inst.yearshtml);
4591                                 }
4592                                 origyearshtml = inst.yearshtml = null;
4593                         }, 0);
4594                 }
4595         },
4596
4597         // #6694 - don't focus the input if it's already focused
4598         // this breaks the change event in IE
4599         // Support: IE and jQuery <1.9
4600         _shouldFocusInput: function( inst ) {
4601                 return inst.input && inst.input.is( ":visible" ) && !inst.input.is( ":disabled" ) && !inst.input.is( ":focus" );
4602         },
4603
4604         /* Check positioning to remain on screen. */
4605         _checkOffset: function(inst, offset, isFixed) {
4606                 var dpWidth = inst.dpDiv.outerWidth(),
4607                         dpHeight = inst.dpDiv.outerHeight(),
4608                         inputWidth = inst.input ? inst.input.outerWidth() : 0,
4609                         inputHeight = inst.input ? inst.input.outerHeight() : 0,
4610                         viewWidth = document.documentElement.clientWidth + (isFixed ? 0 : $(document).scrollLeft()),
4611                         viewHeight = document.documentElement.clientHeight + (isFixed ? 0 : $(document).scrollTop());
4612
4613                 offset.left -= (this._get(inst, "isRTL") ? (dpWidth - inputWidth) : 0);
4614                 offset.left -= (isFixed && offset.left === inst.input.offset().left) ? $(document).scrollLeft() : 0;
4615                 offset.top -= (isFixed && offset.top === (inst.input.offset().top + inputHeight)) ? $(document).scrollTop() : 0;
4616
4617                 // now check if datepicker is showing outside window viewport - move to a better place if so.
4618                 offset.left -= Math.min(offset.left, (offset.left + dpWidth > viewWidth && viewWidth > dpWidth) ?
4619                         Math.abs(offset.left + dpWidth - viewWidth) : 0);
4620                 offset.top -= Math.min(offset.top, (offset.top + dpHeight > viewHeight && viewHeight > dpHeight) ?
4621                         Math.abs(dpHeight + inputHeight) : 0);
4622
4623                 return offset;
4624         },
4625
4626         /* Find an object's position on the screen. */
4627         _findPos: function(obj) {
4628                 var position,
4629                         inst = this._getInst(obj),
4630                         isRTL = this._get(inst, "isRTL");
4631
4632                 while (obj && (obj.type === "hidden" || obj.nodeType !== 1 || $.expr.filters.hidden(obj))) {
4633                         obj = obj[isRTL ? "previousSibling" : "nextSibling"];
4634                 }
4635
4636                 position = $(obj).offset();
4637                 return [position.left, position.top];
4638         },
4639
4640         /* Hide the date picker from view.
4641          * @param  input  element - the input field attached to the date picker
4642          */
4643         _hideDatepicker: function(input) {
4644                 var showAnim, duration, postProcess, onClose,
4645                         inst = this._curInst;
4646
4647                 if (!inst || (input && inst !== $.data(input, "datepicker"))) {
4648                         return;
4649                 }
4650
4651                 if (this._datepickerShowing) {
4652                         showAnim = this._get(inst, "showAnim");
4653                         duration = this._get(inst, "duration");
4654                         postProcess = function() {
4655                                 $.datepicker._tidyDialog(inst);
4656                         };
4657
4658                         // DEPRECATED: after BC for 1.8.x $.effects[ showAnim ] is not needed
4659                         if ( $.effects && ( $.effects.effect[ showAnim ] || $.effects[ showAnim ] ) ) {
4660                                 inst.dpDiv.hide(showAnim, $.datepicker._get(inst, "showOptions"), duration, postProcess);
4661                         } else {
4662                                 inst.dpDiv[(showAnim === "slideDown" ? "slideUp" :
4663                                         (showAnim === "fadeIn" ? "fadeOut" : "hide"))]((showAnim ? duration : null), postProcess);
4664                         }
4665
4666                         if (!showAnim) {
4667                                 postProcess();
4668                         }
4669                         this._datepickerShowing = false;
4670
4671                         onClose = this._get(inst, "onClose");
4672                         if (onClose) {
4673                                 onClose.apply((inst.input ? inst.input[0] : null), [(inst.input ? inst.input.val() : ""), inst]);
4674                         }
4675
4676                         this._lastInput = null;
4677                         if (this._inDialog) {
4678                                 this._dialogInput.css({ position: "absolute", left: "0", top: "-100px" });
4679                                 if ($.blockUI) {
4680                                         $.unblockUI();
4681                                         $("body").append(this.dpDiv);
4682                                 }
4683                         }
4684                         this._inDialog = false;
4685                 }
4686         },
4687
4688         /* Tidy up after a dialog display. */
4689         _tidyDialog: function(inst) {
4690                 inst.dpDiv.removeClass(this._dialogClass).unbind(".ui-datepicker-calendar");
4691         },
4692
4693         /* Close date picker if clicked elsewhere. */
4694         _checkExternalClick: function(event) {
4695                 if (!$.datepicker._curInst) {
4696                         return;
4697                 }
4698
4699                 var $target = $(event.target),
4700                         inst = $.datepicker._getInst($target[0]);
4701
4702                 if ( ( ( $target[0].id !== $.datepicker._mainDivId &&
4703                                 $target.parents("#" + $.datepicker._mainDivId).length === 0 &&
4704                                 !$target.hasClass($.datepicker.markerClassName) &&
4705                                 !$target.closest("." + $.datepicker._triggerClass).length &&
4706                                 $.datepicker._datepickerShowing && !($.datepicker._inDialog && $.blockUI) ) ) ||
4707                         ( $target.hasClass($.datepicker.markerClassName) && $.datepicker._curInst !== inst ) ) {
4708                                 $.datepicker._hideDatepicker();
4709                 }
4710         },
4711
4712         /* Adjust one of the date sub-fields. */
4713         _adjustDate: function(id, offset, period) {
4714                 var target = $(id),
4715                         inst = this._getInst(target[0]);
4716
4717                 if (this._isDisabledDatepicker(target[0])) {
4718                         return;
4719                 }
4720                 this._adjustInstDate(inst, offset +
4721                         (period === "M" ? this._get(inst, "showCurrentAtPos") : 0), // undo positioning
4722                         period);
4723                 this._updateDatepicker(inst);
4724         },
4725
4726         /* Action for current link. */
4727         _gotoToday: function(id) {
4728                 var date,
4729                         target = $(id),
4730                         inst = this._getInst(target[0]);
4731
4732                 if (this._get(inst, "gotoCurrent") && inst.currentDay) {
4733                         inst.selectedDay = inst.currentDay;
4734                         inst.drawMonth = inst.selectedMonth = inst.currentMonth;
4735                         inst.drawYear = inst.selectedYear = inst.currentYear;
4736                 } else {
4737                         date = new Date();
4738                         inst.selectedDay = date.getDate();
4739                         inst.drawMonth = inst.selectedMonth = date.getMonth();
4740                         inst.drawYear = inst.selectedYear = date.getFullYear();
4741                 }
4742                 this._notifyChange(inst);
4743                 this._adjustDate(target);
4744         },
4745
4746         /* Action for selecting a new month/year. */
4747         _selectMonthYear: function(id, select, period) {
4748                 var target = $(id),
4749                         inst = this._getInst(target[0]);
4750
4751                 inst["selected" + (period === "M" ? "Month" : "Year")] =
4752                 inst["draw" + (period === "M" ? "Month" : "Year")] =
4753                         parseInt(select.options[select.selectedIndex].value,10);
4754
4755                 this._notifyChange(inst);
4756                 this._adjustDate(target);
4757         },
4758
4759         /* Action for selecting a day. */
4760         _selectDay: function(id, month, year, td) {
4761                 var inst,
4762                         target = $(id);
4763
4764                 if ($(td).hasClass(this._unselectableClass) || this._isDisabledDatepicker(target[0])) {
4765                         return;
4766                 }
4767
4768                 inst = this._getInst(target[0]);
4769                 inst.selectedDay = inst.currentDay = $("a", td).html();
4770                 inst.selectedMonth = inst.currentMonth = month;
4771                 inst.selectedYear = inst.currentYear = year;
4772                 this._selectDate(id, this._formatDate(inst,
4773                         inst.currentDay, inst.currentMonth, inst.currentYear));
4774         },
4775
4776         /* Erase the input field and hide the date picker. */
4777         _clearDate: function(id) {
4778                 var target = $(id);
4779                 this._selectDate(target, "");
4780         },
4781
4782         /* Update the input field with the selected date. */
4783         _selectDate: function(id, dateStr) {
4784                 var onSelect,
4785                         target = $(id),
4786                         inst = this._getInst(target[0]);
4787
4788                 dateStr = (dateStr != null ? dateStr : this._formatDate(inst));
4789                 if (inst.input) {
4790                         inst.input.val(dateStr);
4791                 }
4792                 this._updateAlternate(inst);
4793
4794                 onSelect = this._get(inst, "onSelect");
4795                 if (onSelect) {
4796                         onSelect.apply((inst.input ? inst.input[0] : null), [dateStr, inst]);  // trigger custom callback
4797                 } else if (inst.input) {
4798                         inst.input.trigger("change"); // fire the change event
4799                 }
4800
4801                 if (inst.inline){
4802                         this._updateDatepicker(inst);
4803                 } else {
4804                         this._hideDatepicker();
4805                         this._lastInput = inst.input[0];
4806                         if (typeof(inst.input[0]) !== "object") {
4807                                 inst.input.focus(); // restore focus
4808                         }
4809                         this._lastInput = null;
4810                 }
4811         },
4812
4813         /* Update any alternate field to synchronise with the main field. */
4814         _updateAlternate: function(inst) {
4815                 var altFormat, date, dateStr,
4816                         altField = this._get(inst, "altField");
4817
4818                 if (altField) { // update alternate field too
4819                         altFormat = this._get(inst, "altFormat") || this._get(inst, "dateFormat");
4820                         date = this._getDate(inst);
4821                         dateStr = this.formatDate(altFormat, date, this._getFormatConfig(inst));
4822                         $(altField).each(function() { $(this).val(dateStr); });
4823                 }
4824         },
4825
4826         /* Set as beforeShowDay function to prevent selection of weekends.
4827          * @param  date  Date - the date to customise
4828          * @return [boolean, string] - is this date selectable?, what is its CSS class?
4829          */
4830         noWeekends: function(date) {
4831                 var day = date.getDay();
4832                 return [(day > 0 && day < 6), ""];
4833         },
4834
4835         /* Set as calculateWeek to determine the week of the year based on the ISO 8601 definition.
4836          * @param  date  Date - the date to get the week for
4837          * @return  number - the number of the week within the year that contains this date
4838          */
4839         iso8601Week: function(date) {
4840                 var time,
4841                         checkDate = new Date(date.getTime());
4842
4843                 // Find Thursday of this week starting on Monday
4844                 checkDate.setDate(checkDate.getDate() + 4 - (checkDate.getDay() || 7));
4845
4846                 time = checkDate.getTime();
4847                 checkDate.setMonth(0); // Compare with Jan 1
4848                 checkDate.setDate(1);
4849                 return Math.floor(Math.round((time - checkDate) / 86400000) / 7) + 1;
4850         },
4851
4852         /* Parse a string value into a date object.
4853          * See formatDate below for the possible formats.
4854          *
4855          * @param  format string - the expected format of the date
4856          * @param  value string - the date in the above format
4857          * @param  settings Object - attributes include:
4858          *                                      shortYearCutoff  number - the cutoff year for determining the century (optional)
4859          *                                      dayNamesShort   string[7] - abbreviated names of the days from Sunday (optional)
4860          *                                      dayNames                string[7] - names of the days from Sunday (optional)
4861          *                                      monthNamesShort string[12] - abbreviated names of the months (optional)
4862          *                                      monthNames              string[12] - names of the months (optional)
4863          * @return  Date - the extracted date value or null if value is blank
4864          */
4865         parseDate: function (format, value, settings) {
4866                 if (format == null || value == null) {
4867                         throw "Invalid arguments";
4868                 }
4869
4870                 value = (typeof value === "object" ? value.toString() : value + "");
4871                 if (value === "") {
4872                         return null;
4873                 }
4874
4875                 var iFormat, dim, extra,
4876                         iValue = 0,
4877                         shortYearCutoffTemp = (settings ? settings.shortYearCutoff : null) || this._defaults.shortYearCutoff,
4878                         shortYearCutoff = (typeof shortYearCutoffTemp !== "string" ? shortYearCutoffTemp :
4879                                 new Date().getFullYear() % 100 + parseInt(shortYearCutoffTemp, 10)),
4880                         dayNamesShort = (settings ? settings.dayNamesShort : null) || this._defaults.dayNamesShort,
4881                         dayNames = (settings ? settings.dayNames : null) || this._defaults.dayNames,
4882                         monthNamesShort = (settings ? settings.monthNamesShort : null) || this._defaults.monthNamesShort,
4883                         monthNames = (settings ? settings.monthNames : null) || this._defaults.monthNames,
4884                         year = -1,
4885                         month = -1,
4886                         day = -1,
4887                         doy = -1,
4888                         literal = false,
4889                         date,
4890                         // Check whether a format character is doubled
4891                         lookAhead = function(match) {
4892                                 var matches = (iFormat + 1 < format.length && format.charAt(iFormat + 1) === match);
4893                                 if (matches) {
4894                                         iFormat++;
4895                                 }
4896                                 return matches;
4897                         },
4898                         // Extract a number from the string value
4899                         getNumber = function(match) {
4900                                 var isDoubled = lookAhead(match),
4901                                         size = (match === "@" ? 14 : (match === "!" ? 20 :
4902                                         (match === "y" && isDoubled ? 4 : (match === "o" ? 3 : 2)))),
4903                                         minSize = (match === "y" ? size : 1),
4904                                         digits = new RegExp("^\\d{" + minSize + "," + size + "}"),
4905                                         num = value.substring(iValue).match(digits);
4906                                 if (!num) {
4907                                         throw "Missing number at position " + iValue;
4908                                 }
4909                                 iValue += num[0].length;
4910                                 return parseInt(num[0], 10);
4911                         },
4912                         // Extract a name from the string value and convert to an index
4913                         getName = function(match, shortNames, longNames) {
4914                                 var index = -1,
4915                                         names = $.map(lookAhead(match) ? longNames : shortNames, function (v, k) {
4916                                                 return [ [k, v] ];
4917                                         }).sort(function (a, b) {
4918                                                 return -(a[1].length - b[1].length);
4919                                         });
4920
4921                                 $.each(names, function (i, pair) {
4922                                         var name = pair[1];
4923                                         if (value.substr(iValue, name.length).toLowerCase() === name.toLowerCase()) {
4924                                                 index = pair[0];
4925                                                 iValue += name.length;
4926                                                 return false;
4927                                         }
4928                                 });
4929                                 if (index !== -1) {
4930                                         return index + 1;
4931                                 } else {
4932                                         throw "Unknown name at position " + iValue;
4933                                 }
4934                         },
4935                         // Confirm that a literal character matches the string value
4936                         checkLiteral = function() {
4937                                 if (value.charAt(iValue) !== format.charAt(iFormat)) {
4938                                         throw "Unexpected literal at position " + iValue;
4939                                 }
4940                                 iValue++;
4941                         };
4942
4943                 for (iFormat = 0; iFormat < format.length; iFormat++) {
4944                         if (literal) {
4945                                 if (format.charAt(iFormat) === "'" && !lookAhead("'")) {
4946                                         literal = false;
4947                                 } else {
4948                                         checkLiteral();
4949                                 }
4950                         } else {
4951                                 switch (format.charAt(iFormat)) {
4952                                         case "d":
4953                                                 day = getNumber("d");
4954                                                 break;
4955                                         case "D":
4956                                                 getName("D", dayNamesShort, dayNames);
4957                                                 break;
4958                                         case "o":
4959                                                 doy = getNumber("o");
4960                                                 break;
4961                                         case "m":
4962                                                 month = getNumber("m");
4963                                                 break;
4964                                         case "M":
4965                                                 month = getName("M", monthNamesShort, monthNames);
4966                                                 break;
4967                                         case "y":
4968                                                 year = getNumber("y");
4969                                                 break;
4970                                         case "@":
4971                                                 date = new Date(getNumber("@"));
4972                                                 year = date.getFullYear();
4973                                                 month = date.getMonth() + 1;
4974                                                 day = date.getDate();
4975                                                 break;
4976                                         case "!":
4977                                                 date = new Date((getNumber("!") - this._ticksTo1970) / 10000);
4978                                                 year = date.getFullYear();
4979                                                 month = date.getMonth() + 1;
4980                                                 day = date.getDate();
4981                                                 break;
4982                                         case "'":
4983                                                 if (lookAhead("'")){
4984                                                         checkLiteral();
4985                                                 } else {
4986                                                         literal = true;
4987                                                 }
4988                                                 break;
4989                                         default:
4990                                                 checkLiteral();
4991                                 }
4992                         }
4993                 }
4994
4995                 if (iValue < value.length){
4996                         extra = value.substr(iValue);
4997                         if (!/^\s+/.test(extra)) {
4998                                 throw "Extra/unparsed characters found in date: " + extra;
4999                         }
5000                 }
5001
5002                 if (year === -1) {
5003                         year = new Date().getFullYear();
5004                 } else if (year < 100) {
5005                         year += new Date().getFullYear() - new Date().getFullYear() % 100 +
5006                                 (year <= shortYearCutoff ? 0 : -100);
5007                 }
5008
5009                 if (doy > -1) {
5010                         month = 1;
5011                         day = doy;
5012                         do {
5013                                 dim = this._getDaysInMonth(year, month - 1);
5014                                 if (day <= dim) {
5015                                         break;
5016                                 }
5017                                 month++;
5018                                 day -= dim;
5019                         } while (true);
5020                 }
5021
5022                 date = this._daylightSavingAdjust(new Date(year, month - 1, day));
5023                 if (date.getFullYear() !== year || date.getMonth() + 1 !== month || date.getDate() !== day) {
5024                         throw "Invalid date"; // E.g. 31/02/00
5025                 }
5026                 return date;
5027         },
5028
5029         /* Standard date formats. */
5030         ATOM: "yy-mm-dd", // RFC 3339 (ISO 8601)
5031         COOKIE: "D, dd M yy",
5032         ISO_8601: "yy-mm-dd",
5033         RFC_822: "D, d M y",
5034         RFC_850: "DD, dd-M-y",
5035         RFC_1036: "D, d M y",
5036         RFC_1123: "D, d M yy",
5037         RFC_2822: "D, d M yy",
5038         RSS: "D, d M y", // RFC 822
5039         TICKS: "!",
5040         TIMESTAMP: "@",
5041         W3C: "yy-mm-dd", // ISO 8601
5042
5043         _ticksTo1970: (((1970 - 1) * 365 + Math.floor(1970 / 4) - Math.floor(1970 / 100) +
5044                 Math.floor(1970 / 400)) * 24 * 60 * 60 * 10000000),
5045
5046         /* Format a date object into a string value.
5047          * The format can be combinations of the following:
5048          * d  - day of month (no leading zero)
5049          * dd - day of month (two digit)
5050          * o  - day of year (no leading zeros)
5051          * oo - day of year (three digit)
5052          * D  - day name short
5053          * DD - day name long
5054          * m  - month of year (no leading zero)
5055          * mm - month of year (two digit)
5056          * M  - month name short
5057          * MM - month name long
5058          * y  - year (two digit)
5059          * yy - year (four digit)
5060          * @ - Unix timestamp (ms since 01/01/1970)
5061          * ! - Windows ticks (100ns since 01/01/0001)
5062          * "..." - literal text
5063          * '' - single quote
5064          *
5065          * @param  format string - the desired format of the date
5066          * @param  date Date - the date value to format
5067          * @param  settings Object - attributes include:
5068          *                                      dayNamesShort   string[7] - abbreviated names of the days from Sunday (optional)
5069          *                                      dayNames                string[7] - names of the days from Sunday (optional)
5070          *                                      monthNamesShort string[12] - abbreviated names of the months (optional)
5071          *                                      monthNames              string[12] - names of the months (optional)
5072          * @return  string - the date in the above format
5073          */
5074         formatDate: function (format, date, settings) {
5075                 if (!date) {
5076                         return "";
5077                 }
5078
5079                 var iFormat,
5080                         dayNamesShort = (settings ? settings.dayNamesShort : null) || this._defaults.dayNamesShort,
5081                         dayNames = (settings ? settings.dayNames : null) || this._defaults.dayNames,
5082                         monthNamesShort = (settings ? settings.monthNamesShort : null) || this._defaults.monthNamesShort,
5083                         monthNames = (settings ? settings.monthNames : null) || this._defaults.monthNames,
5084                         // Check whether a format character is doubled
5085                         lookAhead = function(match) {
5086                                 var matches = (iFormat + 1 < format.length && format.charAt(iFormat + 1) === match);
5087                                 if (matches) {
5088                                         iFormat++;
5089                                 }
5090                                 return matches;
5091                         },
5092                         // Format a number, with leading zero if necessary
5093                         formatNumber = function(match, value, len) {
5094                                 var num = "" + value;
5095                                 if (lookAhead(match)) {
5096                                         while (num.length < len) {
5097                                                 num = "0" + num;
5098                                         }
5099                                 }
5100                                 return num;
5101                         },
5102                         // Format a name, short or long as requested
5103                         formatName = function(match, value, shortNames, longNames) {
5104                                 return (lookAhead(match) ? longNames[value] : shortNames[value]);
5105                         },
5106                         output = "",
5107                         literal = false;
5108
5109                 if (date) {
5110                         for (iFormat = 0; iFormat < format.length; iFormat++) {
5111                                 if (literal) {
5112                                         if (format.charAt(iFormat) === "'" && !lookAhead("'")) {
5113                                                 literal = false;
5114                                         } else {
5115                                                 output += format.charAt(iFormat);
5116                                         }
5117                                 } else {
5118                                         switch (format.charAt(iFormat)) {
5119                                                 case "d":
5120                                                         output += formatNumber("d", date.getDate(), 2);
5121                                                         break;
5122                                                 case "D":
5123                                                         output += formatName("D", date.getDay(), dayNamesShort, dayNames);
5124                                                         break;
5125                                                 case "o":
5126                                                         output += formatNumber("o",
5127                                                                 Math.round((new Date(date.getFullYear(), date.getMonth(), date.getDate()).getTime() - new Date(date.getFullYear(), 0, 0).getTime()) / 86400000), 3);
5128                                                         break;
5129                                                 case "m":
5130                                                         output += formatNumber("m", date.getMonth() + 1, 2);
5131                                                         break;
5132                                                 case "M":
5133                                                         output += formatName("M", date.getMonth(), monthNamesShort, monthNames);
5134                                                         break;
5135                                                 case "y":
5136                                                         output += (lookAhead("y") ? date.getFullYear() :
5137                                                                 (date.getYear() % 100 < 10 ? "0" : "") + date.getYear() % 100);
5138                                                         break;
5139                                                 case "@":
5140                                                         output += date.getTime();
5141                                                         break;
5142                                                 case "!":
5143                                                         output += date.getTime() * 10000 + this._ticksTo1970;
5144                                                         break;
5145                                                 case "'":
5146                                                         if (lookAhead("'")) {
5147                                                                 output += "'";
5148                                                         } else {
5149                                                                 literal = true;
5150                                                         }
5151                                                         break;
5152                                                 default:
5153                                                         output += format.charAt(iFormat);
5154                                         }
5155                                 }
5156                         }
5157                 }
5158                 return output;
5159         },
5160
5161         /* Extract all possible characters from the date format. */
5162         _possibleChars: function (format) {
5163                 var iFormat,
5164                         chars = "",
5165                         literal = false,
5166                         // Check whether a format character is doubled
5167                         lookAhead = function(match) {
5168                                 var matches = (iFormat + 1 < format.length && format.charAt(iFormat + 1) === match);
5169                                 if (matches) {
5170                                         iFormat++;
5171                                 }
5172                                 return matches;
5173                         };
5174
5175                 for (iFormat = 0; iFormat < format.length; iFormat++) {
5176                         if (literal) {
5177                                 if (format.charAt(iFormat) === "'" && !lookAhead("'")) {
5178                                         literal = false;
5179                                 } else {
5180                                         chars += format.charAt(iFormat);
5181                                 }
5182                         } else {
5183                                 switch (format.charAt(iFormat)) {
5184                                         case "d": case "m": case "y": case "@":
5185                                                 chars += "0123456789";
5186                                                 break;
5187                                         case "D": case "M":
5188                                                 return null; // Accept anything
5189                                         case "'":
5190                                                 if (lookAhead("'")) {
5191                                                         chars += "'";
5192                                                 } else {
5193                                                         literal = true;
5194                                                 }
5195                                                 break;
5196                                         default:
5197                                                 chars += format.charAt(iFormat);
5198                                 }
5199                         }
5200                 }
5201                 return chars;
5202         },
5203
5204         /* Get a setting value, defaulting if necessary. */
5205         _get: function(inst, name) {
5206                 return inst.settings[name] !== undefined ?
5207                         inst.settings[name] : this._defaults[name];
5208         },
5209
5210         /* Parse existing date and initialise date picker. */
5211         _setDateFromField: function(inst, noDefault) {
5212                 if (inst.input.val() === inst.lastVal) {
5213                         return;
5214                 }
5215
5216                 var dateFormat = this._get(inst, "dateFormat"),
5217                         dates = inst.lastVal = inst.input ? inst.input.val() : null,
5218                         defaultDate = this._getDefaultDate(inst),
5219                         date = defaultDate,
5220                         settings = this._getFormatConfig(inst);
5221
5222                 try {
5223                         date = this.parseDate(dateFormat, dates, settings) || defaultDate;
5224                 } catch (event) {
5225                         dates = (noDefault ? "" : dates);
5226                 }
5227                 inst.selectedDay = date.getDate();
5228                 inst.drawMonth = inst.selectedMonth = date.getMonth();
5229                 inst.drawYear = inst.selectedYear = date.getFullYear();
5230                 inst.currentDay = (dates ? date.getDate() : 0);
5231                 inst.currentMonth = (dates ? date.getMonth() : 0);
5232                 inst.currentYear = (dates ? date.getFullYear() : 0);
5233                 this._adjustInstDate(inst);
5234         },
5235
5236         /* Retrieve the default date shown on opening. */
5237         _getDefaultDate: function(inst) {
5238                 return this._restrictMinMax(inst,
5239                         this._determineDate(inst, this._get(inst, "defaultDate"), new Date()));
5240         },
5241
5242         /* A date may be specified as an exact value or a relative one. */
5243         _determineDate: function(inst, date, defaultDate) {
5244                 var offsetNumeric = function(offset) {
5245                                 var date = new Date();
5246                                 date.setDate(date.getDate() + offset);
5247                                 return date;
5248                         },
5249                         offsetString = function(offset) {
5250                                 try {
5251                                         return $.datepicker.parseDate($.datepicker._get(inst, "dateFormat"),
5252                                                 offset, $.datepicker._getFormatConfig(inst));
5253                                 }
5254                                 catch (e) {
5255                                         // Ignore
5256                                 }
5257
5258                                 var date = (offset.toLowerCase().match(/^c/) ?
5259                                         $.datepicker._getDate(inst) : null) || new Date(),
5260                                         year = date.getFullYear(),
5261                                         month = date.getMonth(),
5262                                         day = date.getDate(),
5263                                         pattern = /([+\-]?[0-9]+)\s*(d|D|w|W|m|M|y|Y)?/g,
5264                                         matches = pattern.exec(offset);
5265
5266                                 while (matches) {
5267                                         switch (matches[2] || "d") {
5268                                                 case "d" : case "D" :
5269                                                         day += parseInt(matches[1],10); break;
5270                                                 case "w" : case "W" :
5271                                                         day += parseInt(matches[1],10) * 7; break;
5272                                                 case "m" : case "M" :
5273                                                         month += parseInt(matches[1],10);
5274                                                         day = Math.min(day, $.datepicker._getDaysInMonth(year, month));
5275                                                         break;
5276                                                 case "y": case "Y" :
5277                                                         year += parseInt(matches[1],10);
5278                                                         day = Math.min(day, $.datepicker._getDaysInMonth(year, month));
5279                                                         break;
5280                                         }
5281                                         matches = pattern.exec(offset);
5282                                 }
5283                                 return new Date(year, month, day);
5284                         },
5285                         newDate = (date == null || date === "" ? defaultDate : (typeof date === "string" ? offsetString(date) :
5286                                 (typeof date === "number" ? (isNaN(date) ? defaultDate : offsetNumeric(date)) : new Date(date.getTime()))));
5287
5288                 newDate = (newDate && newDate.toString() === "Invalid Date" ? defaultDate : newDate);
5289                 if (newDate) {
5290                         newDate.setHours(0);
5291                         newDate.setMinutes(0);
5292                         newDate.setSeconds(0);
5293                         newDate.setMilliseconds(0);
5294                 }
5295                 return this._daylightSavingAdjust(newDate);
5296         },
5297
5298         /* Handle switch to/from daylight saving.
5299          * Hours may be non-zero on daylight saving cut-over:
5300          * > 12 when midnight changeover, but then cannot generate
5301          * midnight datetime, so jump to 1AM, otherwise reset.
5302          * @param  date  (Date) the date to check
5303          * @return  (Date) the corrected date
5304          */
5305         _daylightSavingAdjust: function(date) {
5306                 if (!date) {
5307                         return null;
5308                 }
5309                 date.setHours(date.getHours() > 12 ? date.getHours() + 2 : 0);
5310                 return date;
5311         },
5312
5313         /* Set the date(s) directly. */
5314         _setDate: function(inst, date, noChange) {
5315                 var clear = !date,
5316                         origMonth = inst.selectedMonth,
5317                         origYear = inst.selectedYear,
5318                         newDate = this._restrictMinMax(inst, this._determineDate(inst, date, new Date()));
5319
5320                 inst.selectedDay = inst.currentDay = newDate.getDate();
5321                 inst.drawMonth = inst.selectedMonth = inst.currentMonth = newDate.getMonth();
5322                 inst.drawYear = inst.selectedYear = inst.currentYear = newDate.getFullYear();
5323                 if ((origMonth !== inst.selectedMonth || origYear !== inst.selectedYear) && !noChange) {
5324                         this._notifyChange(inst);
5325                 }
5326                 this._adjustInstDate(inst);
5327                 if (inst.input) {
5328                         inst.input.val(clear ? "" : this._formatDate(inst));
5329                 }
5330         },
5331
5332         /* Retrieve the date(s) directly. */
5333         _getDate: function(inst) {
5334                 var startDate = (!inst.currentYear || (inst.input && inst.input.val() === "") ? null :
5335                         this._daylightSavingAdjust(new Date(
5336                         inst.currentYear, inst.currentMonth, inst.currentDay)));
5337                         return startDate;
5338         },
5339
5340         /* Attach the onxxx handlers.  These are declared statically so
5341          * they work with static code transformers like Caja.
5342          */
5343         _attachHandlers: function(inst) {
5344                 var stepMonths = this._get(inst, "stepMonths"),
5345                         id = "#" + inst.id.replace( /\\\\/g, "\\" );
5346                 inst.dpDiv.find("[data-handler]").map(function () {
5347                         var handler = {
5348                                 prev: function () {
5349                                         $.datepicker._adjustDate(id, -stepMonths, "M");
5350                                 },
5351                                 next: function () {
5352                                         $.datepicker._adjustDate(id, +stepMonths, "M");
5353                                 },
5354                                 hide: function () {
5355                                         $.datepicker._hideDatepicker();
5356                                 },
5357                                 today: function () {
5358                                         $.datepicker._gotoToday(id);
5359                                 },
5360                                 selectDay: function () {
5361                                         $.datepicker._selectDay(id, +this.getAttribute("data-month"), +this.getAttribute("data-year"), this);
5362                                         return false;
5363                                 },
5364                                 selectMonth: function () {
5365                                         $.datepicker._selectMonthYear(id, this, "M");
5366                                         return false;
5367                                 },
5368                                 selectYear: function () {
5369                                         $.datepicker._selectMonthYear(id, this, "Y");
5370                                         return false;
5371                                 }
5372                         };
5373                         $(this).bind(this.getAttribute("data-event"), handler[this.getAttribute("data-handler")]);
5374                 });
5375         },
5376
5377         /* Generate the HTML for the current state of the date picker. */
5378         _generateHTML: function(inst) {
5379                 var maxDraw, prevText, prev, nextText, next, currentText, gotoDate,
5380                         controls, buttonPanel, firstDay, showWeek, dayNames, dayNamesMin,
5381                         monthNames, monthNamesShort, beforeShowDay, showOtherMonths,
5382                         selectOtherMonths, defaultDate, html, dow, row, group, col, selectedDate,
5383                         cornerClass, calender, thead, day, daysInMonth, leadDays, curRows, numRows,
5384                         printDate, dRow, tbody, daySettings, otherMonth, unselectable,
5385                         tempDate = new Date(),
5386                         today = this._daylightSavingAdjust(
5387                                 new Date(tempDate.getFullYear(), tempDate.getMonth(), tempDate.getDate())), // clear time
5388                         isRTL = this._get(inst, "isRTL"),
5389                         showButtonPanel = this._get(inst, "showButtonPanel"),
5390                         hideIfNoPrevNext = this._get(inst, "hideIfNoPrevNext"),
5391                         navigationAsDateFormat = this._get(inst, "navigationAsDateFormat"),
5392                         numMonths = this._getNumberOfMonths(inst),
5393                         showCurrentAtPos = this._get(inst, "showCurrentAtPos"),
5394                         stepMonths = this._get(inst, "stepMonths"),
5395                         isMultiMonth = (numMonths[0] !== 1 || numMonths[1] !== 1),
5396                         currentDate = this._daylightSavingAdjust((!inst.currentDay ? new Date(9999, 9, 9) :
5397                                 new Date(inst.currentYear, inst.currentMonth, inst.currentDay))),
5398                         minDate = this._getMinMaxDate(inst, "min"),
5399                         maxDate = this._getMinMaxDate(inst, "max"),
5400                         drawMonth = inst.drawMonth - showCurrentAtPos,
5401                         drawYear = inst.drawYear;
5402
5403                 if (drawMonth < 0) {
5404                         drawMonth += 12;
5405                         drawYear--;
5406                 }
5407                 if (maxDate) {
5408                         maxDraw = this._daylightSavingAdjust(new Date(maxDate.getFullYear(),
5409                                 maxDate.getMonth() - (numMonths[0] * numMonths[1]) + 1, maxDate.getDate()));
5410                         maxDraw = (minDate && maxDraw < minDate ? minDate : maxDraw);
5411                         while (this._daylightSavingAdjust(new Date(drawYear, drawMonth, 1)) > maxDraw) {
5412                                 drawMonth--;
5413                                 if (drawMonth < 0) {
5414                                         drawMonth = 11;
5415                                         drawYear--;
5416                                 }
5417                         }
5418                 }
5419                 inst.drawMonth = drawMonth;
5420                 inst.drawYear = drawYear;
5421
5422                 prevText = this._get(inst, "prevText");
5423                 prevText = (!navigationAsDateFormat ? prevText : this.formatDate(prevText,
5424                         this._daylightSavingAdjust(new Date(drawYear, drawMonth - stepMonths, 1)),
5425                         this._getFormatConfig(inst)));
5426
5427                 prev = (this._canAdjustMonth(inst, -1, drawYear, drawMonth) ?
5428                         "<a class='ui-datepicker-prev ui-corner-all' data-handler='prev' data-event='click'" +
5429                         " title='" + prevText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "e" : "w") + "'>" + prevText + "</span></a>" :
5430                         (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>"));
5431
5432                 nextText = this._get(inst, "nextText");
5433                 nextText = (!navigationAsDateFormat ? nextText : this.formatDate(nextText,
5434                         this._daylightSavingAdjust(new Date(drawYear, drawMonth + stepMonths, 1)),
5435                         this._getFormatConfig(inst)));
5436
5437                 next = (this._canAdjustMonth(inst, +1, drawYear, drawMonth) ?
5438                         "<a class='ui-datepicker-next ui-corner-all' data-handler='next' data-event='click'" +
5439                         " title='" + nextText + "'><span class='ui-icon ui-icon-circle-triangle-" + ( isRTL ? "w" : "e") + "'>" + nextText + "</span></a>" :
5440                         (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>"));
5441
5442                 currentText = this._get(inst, "currentText");
5443                 gotoDate = (this._get(inst, "gotoCurrent") && inst.currentDay ? currentDate : today);
5444                 currentText = (!navigationAsDateFormat ? currentText :
5445                         this.formatDate(currentText, gotoDate, this._getFormatConfig(inst)));
5446
5447                 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'>" +
5448                         this._get(inst, "closeText") + "</button>" : "");
5449
5450                 buttonPanel = (showButtonPanel) ? "<div class='ui-datepicker-buttonpane ui-widget-content'>" + (isRTL ? controls : "") +
5451                         (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'" +
5452                         ">" + currentText + "</button>" : "") + (isRTL ? "" : controls) + "</div>" : "";
5453
5454                 firstDay = parseInt(this._get(inst, "firstDay"),10);
5455                 firstDay = (isNaN(firstDay) ? 0 : firstDay);
5456
5457                 showWeek = this._get(inst, "showWeek");
5458                 dayNames = this._get(inst, "dayNames");
5459                 dayNamesMin = this._get(inst, "dayNamesMin");
5460                 monthNames = this._get(inst, "monthNames");
5461                 monthNamesShort = this._get(inst, "monthNamesShort");
5462                 beforeShowDay = this._get(inst, "beforeShowDay");
5463                 showOtherMonths = this._get(inst, "showOtherMonths");
5464                 selectOtherMonths = this._get(inst, "selectOtherMonths");
5465                 defaultDate = this._getDefaultDate(inst);
5466                 html = "";
5467                 dow;
5468                 for (row = 0; row < numMonths[0]; row++) {
5469                         group = "";
5470                         this.maxRows = 4;
5471                         for (col = 0; col < numMonths[1]; col++) {
5472                                 selectedDate = this._daylightSavingAdjust(new Date(drawYear, drawMonth, inst.selectedDay));
5473                                 cornerClass = " ui-corner-all";
5474                                 calender = "";
5475                                 if (isMultiMonth) {
5476                                         calender += "<div class='ui-datepicker-group";
5477                                         if (numMonths[1] > 1) {
5478                                                 switch (col) {
5479                                                         case 0: calender += " ui-datepicker-group-first";
5480                                                                 cornerClass = " ui-corner-" + (isRTL ? "right" : "left"); break;
5481                                                         case numMonths[1]-1: calender += " ui-datepicker-group-last";
5482                                                                 cornerClass = " ui-corner-" + (isRTL ? "left" : "right"); break;
5483                                                         default: calender += " ui-datepicker-group-middle"; cornerClass = ""; break;
5484                                                 }
5485                                         }
5486                                         calender += "'>";
5487                                 }
5488                                 calender += "<div class='ui-datepicker-header ui-widget-header ui-helper-clearfix" + cornerClass + "'>" +
5489                                         (/all|left/.test(cornerClass) && row === 0 ? (isRTL ? next : prev) : "") +
5490                                         (/all|right/.test(cornerClass) && row === 0 ? (isRTL ? prev : next) : "") +
5491                                         this._generateMonthYearHeader(inst, drawMonth, drawYear, minDate, maxDate,
5492                                         row > 0 || col > 0, monthNames, monthNamesShort) + // draw month headers
5493                                         "</div><table class='ui-datepicker-calendar'><thead>" +
5494                                         "<tr>";
5495                                 thead = (showWeek ? "<th class='ui-datepicker-week-col'>" + this._get(inst, "weekHeader") + "</th>" : "");
5496                                 for (dow = 0; dow < 7; dow++) { // days of the week
5497                                         day = (dow + firstDay) % 7;
5498                                         thead += "<th scope='col'" + ((dow + firstDay + 6) % 7 >= 5 ? " class='ui-datepicker-week-end'" : "") + ">" +
5499                                                 "<span title='" + dayNames[day] + "'>" + dayNamesMin[day] + "</span></th>";
5500                                 }
5501                                 calender += thead + "</tr></thead><tbody>";
5502                                 daysInMonth = this._getDaysInMonth(drawYear, drawMonth);
5503                                 if (drawYear === inst.selectedYear && drawMonth === inst.selectedMonth) {
5504                                         inst.selectedDay = Math.min(inst.selectedDay, daysInMonth);
5505                                 }
5506                                 leadDays = (this._getFirstDayOfMonth(drawYear, drawMonth) - firstDay + 7) % 7;
5507                                 curRows = Math.ceil((leadDays + daysInMonth) / 7); // calculate the number of rows to generate
5508                                 numRows = (isMultiMonth ? this.maxRows > curRows ? this.maxRows : curRows : curRows); //If multiple months, use the higher number of rows (see #7043)
5509                                 this.maxRows = numRows;
5510                                 printDate = this._daylightSavingAdjust(new Date(drawYear, drawMonth, 1 - leadDays));
5511                                 for (dRow = 0; dRow < numRows; dRow++) { // create date picker rows
5512                                         calender += "<tr>";
5513                                         tbody = (!showWeek ? "" : "<td class='ui-datepicker-week-col'>" +
5514                                                 this._get(inst, "calculateWeek")(printDate) + "</td>");
5515                                         for (dow = 0; dow < 7; dow++) { // create date picker days
5516                                                 daySettings = (beforeShowDay ?
5517                                                         beforeShowDay.apply((inst.input ? inst.input[0] : null), [printDate]) : [true, ""]);
5518                                                 otherMonth = (printDate.getMonth() !== drawMonth);
5519                                                 unselectable = (otherMonth && !selectOtherMonths) || !daySettings[0] ||
5520                                                         (minDate && printDate < minDate) || (maxDate && printDate > maxDate);
5521                                                 tbody += "<td class='" +
5522                                                         ((dow + firstDay + 6) % 7 >= 5 ? " ui-datepicker-week-end" : "") + // highlight weekends
5523                                                         (otherMonth ? " ui-datepicker-other-month" : "") + // highlight days from other months
5524                                                         ((printDate.getTime() === selectedDate.getTime() && drawMonth === inst.selectedMonth && inst._keyEvent) || // user pressed key
5525                                                         (defaultDate.getTime() === printDate.getTime() && defaultDate.getTime() === selectedDate.getTime()) ?
5526                                                         // or defaultDate is current printedDate and defaultDate is selectedDate
5527                                                         " " + this._dayOverClass : "") + // highlight selected day
5528                                                         (unselectable ? " " + this._unselectableClass + " ui-state-disabled": "") +  // highlight unselectable days
5529                                                         (otherMonth && !showOtherMonths ? "" : " " + daySettings[1] + // highlight custom dates
5530                                                         (printDate.getTime() === currentDate.getTime() ? " " + this._currentClass : "") + // highlight selected day
5531                                                         (printDate.getTime() === today.getTime() ? " ui-datepicker-today" : "")) + "'" + // highlight today (if different)
5532                                                         ((!otherMonth || showOtherMonths) && daySettings[2] ? " title='" + daySettings[2].replace(/'/g, "&#39;") + "'" : "") + // cell title
5533                                                         (unselectable ? "" : " data-handler='selectDay' data-event='click' data-month='" + printDate.getMonth() + "' data-year='" + printDate.getFullYear() + "'") + ">" + // actions
5534                                                         (otherMonth && !showOtherMonths ? "&#xa0;" : // display for other months
5535                                                         (unselectable ? "<span class='ui-state-default'>" + printDate.getDate() + "</span>" : "<a class='ui-state-default" +
5536                                                         (printDate.getTime() === today.getTime() ? " ui-state-highlight" : "") +
5537                                                         (printDate.getTime() === currentDate.getTime() ? " ui-state-active" : "") + // highlight selected day
5538                                                         (otherMonth ? " ui-priority-secondary" : "") + // distinguish dates from other months
5539                                                         "' href='#'>" + printDate.getDate() + "</a>")) + "</td>"; // display selectable date
5540                                                 printDate.setDate(printDate.getDate() + 1);
5541                                                 printDate = this._daylightSavingAdjust(printDate);
5542                                         }
5543                                         calender += tbody + "</tr>";
5544                                 }
5545                                 drawMonth++;
5546                                 if (drawMonth > 11) {
5547                                         drawMonth = 0;
5548                                         drawYear++;
5549                                 }
5550                                 calender += "</tbody></table>" + (isMultiMonth ? "</div>" +
5551                                                         ((numMonths[0] > 0 && col === numMonths[1]-1) ? "<div class='ui-datepicker-row-break'></div>" : "") : "");
5552                                 group += calender;
5553                         }
5554                         html += group;
5555                 }
5556                 html += buttonPanel;
5557                 inst._keyEvent = false;
5558                 return html;
5559         },
5560
5561         /* Generate the month and year header. */
5562         _generateMonthYearHeader: function(inst, drawMonth, drawYear, minDate, maxDate,
5563                         secondary, monthNames, monthNamesShort) {
5564
5565                 var inMinYear, inMaxYear, month, years, thisYear, determineYear, year, endYear,
5566                         changeMonth = this._get(inst, "changeMonth"),
5567                         changeYear = this._get(inst, "changeYear"),
5568                         showMonthAfterYear = this._get(inst, "showMonthAfterYear"),
5569                         html = "<div class='ui-datepicker-title'>",
5570                         monthHtml = "";
5571
5572                 // month selection
5573                 if (secondary || !changeMonth) {
5574                         monthHtml += "<span class='ui-datepicker-month'>" + monthNames[drawMonth] + "</span>";
5575                 } else {
5576                         inMinYear = (minDate && minDate.getFullYear() === drawYear);
5577                         inMaxYear = (maxDate && maxDate.getFullYear() === drawYear);
5578                         monthHtml += "<select class='ui-datepicker-month' data-handler='selectMonth' data-event='change'>";
5579                         for ( month = 0; month < 12; month++) {
5580                                 if ((!inMinYear || month >= minDate.getMonth()) && (!inMaxYear || month <= maxDate.getMonth())) {
5581                                         monthHtml += "<option value='" + month + "'" +
5582                                                 (month === drawMonth ? " selected='selected'" : "") +
5583                                                 ">" + monthNamesShort[month] + "</option>";
5584                                 }
5585                         }
5586                         monthHtml += "</select>";
5587                 }
5588
5589                 if (!showMonthAfterYear) {
5590                         html += monthHtml + (secondary || !(changeMonth && changeYear) ? "&#xa0;" : "");
5591                 }
5592
5593                 // year selection
5594                 if ( !inst.yearshtml ) {
5595                         inst.yearshtml = "";
5596                         if (secondary || !changeYear) {
5597                                 html += "<span class='ui-datepicker-year'>" + drawYear + "</span>";
5598                         } else {
5599                                 // determine range of years to display
5600                                 years = this._get(inst, "yearRange").split(":");
5601                                 thisYear = new Date().getFullYear();
5602                                 determineYear = function(value) {
5603                                         var year = (value.match(/c[+\-].*/) ? drawYear + parseInt(value.substring(1), 10) :
5604                                                 (value.match(/[+\-].*/) ? thisYear + parseInt(value, 10) :
5605                                                 parseInt(value, 10)));
5606                                         return (isNaN(year) ? thisYear : year);
5607                                 };
5608                                 year = determineYear(years[0]);
5609                                 endYear = Math.max(year, determineYear(years[1] || ""));
5610                                 year = (minDate ? Math.max(year, minDate.getFullYear()) : year);
5611                                 endYear = (maxDate ? Math.min(endYear, maxDate.getFullYear()) : endYear);
5612                                 inst.yearshtml += "<select class='ui-datepicker-year' data-handler='selectYear' data-event='change'>";
5613                                 for (; year <= endYear; year++) {
5614                                         inst.yearshtml += "<option value='" + year + "'" +
5615                                                 (year === drawYear ? " selected='selected'" : "") +
5616                                                 ">" + year + "</option>";
5617                                 }
5618                                 inst.yearshtml += "</select>";
5619
5620                                 html += inst.yearshtml;
5621                                 inst.yearshtml = null;
5622                         }
5623                 }
5624
5625                 html += this._get(inst, "yearSuffix");
5626                 if (showMonthAfterYear) {
5627                         html += (secondary || !(changeMonth && changeYear) ? "&#xa0;" : "") + monthHtml;
5628                 }
5629                 html += "</div>"; // Close datepicker_header
5630                 return html;
5631         },
5632
5633         /* Adjust one of the date sub-fields. */
5634         _adjustInstDate: function(inst, offset, period) {
5635                 var year = inst.drawYear + (period === "Y" ? offset : 0),
5636                         month = inst.drawMonth + (period === "M" ? offset : 0),
5637                         day = Math.min(inst.selectedDay, this._getDaysInMonth(year, month)) + (period === "D" ? offset : 0),
5638                         date = this._restrictMinMax(inst, this._daylightSavingAdjust(new Date(year, month, day)));
5639
5640                 inst.selectedDay = date.getDate();
5641                 inst.drawMonth = inst.selectedMonth = date.getMonth();
5642                 inst.drawYear = inst.selectedYear = date.getFullYear();
5643                 if (period === "M" || period === "Y") {
5644                         this._notifyChange(inst);
5645                 }
5646         },
5647
5648         /* Ensure a date is within any min/max bounds. */
5649         _restrictMinMax: function(inst, date) {
5650                 var minDate = this._getMinMaxDate(inst, "min"),
5651                         maxDate = this._getMinMaxDate(inst, "max"),
5652                         newDate = (minDate && date < minDate ? minDate : date);
5653                 return (maxDate && newDate > maxDate ? maxDate : newDate);
5654         },
5655
5656         /* Notify change of month/year. */
5657         _notifyChange: function(inst) {
5658                 var onChange = this._get(inst, "onChangeMonthYear");
5659                 if (onChange) {
5660                         onChange.apply((inst.input ? inst.input[0] : null),
5661                                 [inst.selectedYear, inst.selectedMonth + 1, inst]);
5662                 }
5663         },
5664
5665         /* Determine the number of months to show. */
5666         _getNumberOfMonths: function(inst) {
5667                 var numMonths = this._get(inst, "numberOfMonths");
5668                 return (numMonths == null ? [1, 1] : (typeof numMonths === "number" ? [1, numMonths] : numMonths));
5669         },
5670
5671         /* Determine the current maximum date - ensure no time components are set. */
5672         _getMinMaxDate: function(inst, minMax) {
5673                 return this._determineDate(inst, this._get(inst, minMax + "Date"), null);
5674         },
5675
5676         /* Find the number of days in a given month. */
5677         _getDaysInMonth: function(year, month) {
5678                 return 32 - this._daylightSavingAdjust(new Date(year, month, 32)).getDate();
5679         },
5680
5681         /* Find the day of the week of the first of a month. */
5682         _getFirstDayOfMonth: function(year, month) {
5683                 return new Date(year, month, 1).getDay();
5684         },
5685
5686         /* Determines if we should allow a "next/prev" month display change. */
5687         _canAdjustMonth: function(inst, offset, curYear, curMonth) {
5688                 var numMonths = this._getNumberOfMonths(inst),
5689                         date = this._daylightSavingAdjust(new Date(curYear,
5690                         curMonth + (offset < 0 ? offset : numMonths[0] * numMonths[1]), 1));
5691
5692                 if (offset < 0) {
5693                         date.setDate(this._getDaysInMonth(date.getFullYear(), date.getMonth()));
5694                 }
5695                 return this._isInRange(inst, date);
5696         },
5697
5698         /* Is the given date in the accepted range? */
5699         _isInRange: function(inst, date) {
5700                 var yearSplit, currentYear,
5701                         minDate = this._getMinMaxDate(inst, "min"),
5702                         maxDate = this._getMinMaxDate(inst, "max"),
5703                         minYear = null,
5704                         maxYear = null,
5705                         years = this._get(inst, "yearRange");
5706                         if (years){
5707                                 yearSplit = years.split(":");
5708                                 currentYear = new Date().getFullYear();
5709                                 minYear = parseInt(yearSplit[0], 10);
5710                                 maxYear = parseInt(yearSplit[1], 10);
5711                                 if ( yearSplit[0].match(/[+\-].*/) ) {
5712                                         minYear += currentYear;
5713                                 }
5714                                 if ( yearSplit[1].match(/[+\-].*/) ) {
5715                                         maxYear += currentYear;
5716                                 }
5717                         }
5718
5719                 return ((!minDate || date.getTime() >= minDate.getTime()) &&
5720                         (!maxDate || date.getTime() <= maxDate.getTime()) &&
5721                         (!minYear || date.getFullYear() >= minYear) &&
5722                         (!maxYear || date.getFullYear() <= maxYear));
5723         },
5724
5725         /* Provide the configuration settings for formatting/parsing. */
5726         _getFormatConfig: function(inst) {
5727                 var shortYearCutoff = this._get(inst, "shortYearCutoff");
5728                 shortYearCutoff = (typeof shortYearCutoff !== "string" ? shortYearCutoff :
5729                         new Date().getFullYear() % 100 + parseInt(shortYearCutoff, 10));
5730                 return {shortYearCutoff: shortYearCutoff,
5731                         dayNamesShort: this._get(inst, "dayNamesShort"), dayNames: this._get(inst, "dayNames"),
5732                         monthNamesShort: this._get(inst, "monthNamesShort"), monthNames: this._get(inst, "monthNames")};
5733         },
5734
5735         /* Format the given date for display. */
5736         _formatDate: function(inst, day, month, year) {
5737                 if (!day) {
5738                         inst.currentDay = inst.selectedDay;
5739                         inst.currentMonth = inst.selectedMonth;
5740                         inst.currentYear = inst.selectedYear;
5741                 }
5742                 var date = (day ? (typeof day === "object" ? day :
5743                         this._daylightSavingAdjust(new Date(year, month, day))) :
5744                         this._daylightSavingAdjust(new Date(inst.currentYear, inst.currentMonth, inst.currentDay)));
5745                 return this.formatDate(this._get(inst, "dateFormat"), date, this._getFormatConfig(inst));
5746         }
5747 });
5748
5749 /*
5750  * Bind hover events for datepicker elements.
5751  * Done via delegate so the binding only occurs once in the lifetime of the parent div.
5752  * Global datepicker_instActive, set by _updateDatepicker allows the handlers to find their way back to the active picker.
5753  */
5754 function datepicker_bindHover(dpDiv) {
5755         var selector = "button, .ui-datepicker-prev, .ui-datepicker-next, .ui-datepicker-calendar td a";
5756         return dpDiv.delegate(selector, "mouseout", function() {
5757                         $(this).removeClass("ui-state-hover");
5758                         if (this.className.indexOf("ui-datepicker-prev") !== -1) {
5759                                 $(this).removeClass("ui-datepicker-prev-hover");
5760                         }
5761                         if (this.className.indexOf("ui-datepicker-next") !== -1) {
5762                                 $(this).removeClass("ui-datepicker-next-hover");
5763                         }
5764                 })
5765                 .delegate( selector, "mouseover", datepicker_handleMouseover );
5766 }
5767
5768 function datepicker_handleMouseover() {
5769         if (!$.datepicker._isDisabledDatepicker( datepicker_instActive.inline? datepicker_instActive.dpDiv.parent()[0] : datepicker_instActive.input[0])) {
5770                 $(this).parents(".ui-datepicker-calendar").find("a").removeClass("ui-state-hover");
5771                 $(this).addClass("ui-state-hover");
5772                 if (this.className.indexOf("ui-datepicker-prev") !== -1) {
5773                         $(this).addClass("ui-datepicker-prev-hover");
5774                 }
5775                 if (this.className.indexOf("ui-datepicker-next") !== -1) {
5776                         $(this).addClass("ui-datepicker-next-hover");
5777                 }
5778         }
5779 }
5780
5781 /* jQuery extend now ignores nulls! */
5782 function datepicker_extendRemove(target, props) {
5783         $.extend(target, props);
5784         for (var name in props) {
5785                 if (props[name] == null) {
5786                         target[name] = props[name];
5787                 }
5788         }
5789         return target;
5790 }
5791
5792 /* Invoke the datepicker functionality.
5793    @param  options  string - a command, optionally followed by additional parameters or
5794                                         Object - settings for attaching new datepicker functionality
5795    @return  jQuery object */
5796 $.fn.datepicker = function(options){
5797
5798         /* Verify an empty collection wasn't passed - Fixes #6976 */
5799         if ( !this.length ) {
5800                 return this;
5801         }
5802
5803         /* Initialise the date picker. */
5804         if (!$.datepicker.initialized) {
5805                 $(document).mousedown($.datepicker._checkExternalClick);
5806                 $.datepicker.initialized = true;
5807         }
5808
5809         /* Append datepicker main container to body if not exist. */
5810         if ($("#"+$.datepicker._mainDivId).length === 0) {
5811                 $("body").append($.datepicker.dpDiv);
5812         }
5813
5814         var otherArgs = Array.prototype.slice.call(arguments, 1);
5815         if (typeof options === "string" && (options === "isDisabled" || options === "getDate" || options === "widget")) {
5816                 return $.datepicker["_" + options + "Datepicker"].
5817                         apply($.datepicker, [this[0]].concat(otherArgs));
5818         }
5819         if (options === "option" && arguments.length === 2 && typeof arguments[1] === "string") {
5820                 return $.datepicker["_" + options + "Datepicker"].
5821                         apply($.datepicker, [this[0]].concat(otherArgs));
5822         }
5823         return this.each(function() {
5824                 typeof options === "string" ?
5825                         $.datepicker["_" + options + "Datepicker"].
5826                                 apply($.datepicker, [this].concat(otherArgs)) :
5827                         $.datepicker._attachDatepicker(this, options);
5828         });
5829 };
5830
5831 $.datepicker = new Datepicker(); // singleton instance
5832 $.datepicker.initialized = false;
5833 $.datepicker.uuid = new Date().getTime();
5834 $.datepicker.version = "1.11.4";
5835
5836 var datepicker = $.datepicker;
5837
5838
5839 /*!
5840  * jQuery UI Draggable 1.11.4
5841  * http://jqueryui.com
5842  *
5843  * Copyright jQuery Foundation and other contributors
5844  * Released under the MIT license.
5845  * http://jquery.org/license
5846  *
5847  * http://api.jqueryui.com/draggable/
5848  */
5849
5850
5851 $.widget("ui.draggable", $.ui.mouse, {
5852         version: "1.11.4",
5853         widgetEventPrefix: "drag",
5854         options: {
5855                 addClasses: true,
5856                 appendTo: "parent",
5857                 axis: false,
5858                 connectToSortable: false,
5859                 containment: false,
5860                 cursor: "auto",
5861                 cursorAt: false,
5862                 grid: false,
5863                 handle: false,
5864                 helper: "original",
5865                 iframeFix: false,
5866                 opacity: false,
5867                 refreshPositions: false,
5868                 revert: false,
5869                 revertDuration: 500,
5870                 scope: "default",
5871                 scroll: true,
5872                 scrollSensitivity: 20,
5873                 scrollSpeed: 20,
5874                 snap: false,
5875                 snapMode: "both",
5876                 snapTolerance: 20,
5877                 stack: false,
5878                 zIndex: false,
5879
5880                 // callbacks
5881                 drag: null,
5882                 start: null,
5883                 stop: null
5884         },
5885         _create: function() {
5886
5887                 if ( this.options.helper === "original" ) {
5888                         this._setPositionRelative();
5889                 }
5890                 if (this.options.addClasses){
5891                         this.element.addClass("ui-draggable");
5892                 }
5893                 if (this.options.disabled){
5894                         this.element.addClass("ui-draggable-disabled");
5895                 }
5896                 this._setHandleClassName();
5897
5898                 this._mouseInit();
5899         },
5900
5901         _setOption: function( key, value ) {
5902                 this._super( key, value );
5903                 if ( key === "handle" ) {
5904                         this._removeHandleClassName();
5905                         this._setHandleClassName();
5906                 }
5907         },
5908
5909         _destroy: function() {
5910                 if ( ( this.helper || this.element ).is( ".ui-draggable-dragging" ) ) {
5911                         this.destroyOnClear = true;
5912                         return;
5913                 }
5914                 this.element.removeClass( "ui-draggable ui-draggable-dragging ui-draggable-disabled" );
5915                 this._removeHandleClassName();
5916                 this._mouseDestroy();
5917         },
5918
5919         _mouseCapture: function(event) {
5920                 var o = this.options;
5921
5922                 this._blurActiveElement( event );
5923
5924                 // among others, prevent a drag on a resizable-handle
5925                 if (this.helper || o.disabled || $(event.target).closest(".ui-resizable-handle").length > 0) {
5926                         return false;
5927                 }
5928
5929                 //Quit if we're not on a valid handle
5930                 this.handle = this._getHandle(event);
5931                 if (!this.handle) {
5932                         return false;
5933                 }
5934
5935                 this._blockFrames( o.iframeFix === true ? "iframe" : o.iframeFix );
5936
5937                 return true;
5938
5939         },
5940
5941         _blockFrames: function( selector ) {
5942                 this.iframeBlocks = this.document.find( selector ).map(function() {
5943                         var iframe = $( this );
5944
5945                         return $( "<div>" )
5946                                 .css( "position", "absolute" )
5947                                 .appendTo( iframe.parent() )
5948                                 .outerWidth( iframe.outerWidth() )
5949                                 .outerHeight( iframe.outerHeight() )
5950                                 .offset( iframe.offset() )[ 0 ];
5951                 });
5952         },
5953
5954         _unblockFrames: function() {
5955                 if ( this.iframeBlocks ) {
5956                         this.iframeBlocks.remove();
5957                         delete this.iframeBlocks;
5958                 }
5959         },
5960
5961         _blurActiveElement: function( event ) {
5962                 var document = this.document[ 0 ];
5963
5964                 // Only need to blur if the event occurred on the draggable itself, see #10527
5965                 if ( !this.handleElement.is( event.target ) ) {
5966                         return;
5967                 }
5968
5969                 // support: IE9
5970                 // IE9 throws an "Unspecified error" accessing document.activeElement from an <iframe>
5971                 try {
5972
5973                         // Support: IE9, IE10
5974                         // If the <body> is blurred, IE will switch windows, see #9520
5975                         if ( document.activeElement && document.activeElement.nodeName.toLowerCase() !== "body" ) {
5976
5977                                 // Blur any element that currently has focus, see #4261
5978                                 $( document.activeElement ).blur();
5979                         }
5980                 } catch ( error ) {}
5981         },
5982
5983         _mouseStart: function(event) {
5984
5985                 var o = this.options;
5986
5987                 //Create and append the visible helper
5988                 this.helper = this._createHelper(event);
5989
5990                 this.helper.addClass("ui-draggable-dragging");
5991
5992                 //Cache the helper size
5993                 this._cacheHelperProportions();
5994
5995                 //If ddmanager is used for droppables, set the global draggable
5996                 if ($.ui.ddmanager) {
5997                         $.ui.ddmanager.current = this;
5998                 }
5999
6000                 /*
6001                  * - Position generation -
6002                  * This block generates everything position related - it's the core of draggables.
6003                  */
6004
6005                 //Cache the margins of the original element
6006                 this._cacheMargins();
6007
6008                 //Store the helper's css position
6009                 this.cssPosition = this.helper.css( "position" );
6010                 this.scrollParent = this.helper.scrollParent( true );
6011                 this.offsetParent = this.helper.offsetParent();
6012                 this.hasFixedAncestor = this.helper.parents().filter(function() {
6013                                 return $( this ).css( "position" ) === "fixed";
6014                         }).length > 0;
6015
6016                 //The element's absolute position on the page minus margins
6017                 this.positionAbs = this.element.offset();
6018                 this._refreshOffsets( event );
6019
6020                 //Generate the original position
6021                 this.originalPosition = this.position = this._generatePosition( event, false );
6022                 this.originalPageX = event.pageX;
6023                 this.originalPageY = event.pageY;
6024
6025                 //Adjust the mouse offset relative to the helper if "cursorAt" is supplied
6026                 (o.cursorAt && this._adjustOffsetFromHelper(o.cursorAt));
6027
6028                 //Set a containment if given in the options
6029                 this._setContainment();
6030
6031                 //Trigger event + callbacks
6032                 if (this._trigger("start", event) === false) {
6033                         this._clear();
6034                         return false;
6035                 }
6036
6037                 //Recache the helper size
6038                 this._cacheHelperProportions();
6039
6040                 //Prepare the droppable offsets
6041                 if ($.ui.ddmanager && !o.dropBehaviour) {
6042                         $.ui.ddmanager.prepareOffsets(this, event);
6043                 }
6044
6045                 // Reset helper's right/bottom css if they're set and set explicit width/height instead
6046                 // as this prevents resizing of elements with right/bottom set (see #7772)
6047                 this._normalizeRightBottom();
6048
6049                 this._mouseDrag(event, true); //Execute the drag once - this causes the helper not to be visible before getting its correct position
6050
6051                 //If the ddmanager is used for droppables, inform the manager that dragging has started (see #5003)
6052                 if ( $.ui.ddmanager ) {
6053                         $.ui.ddmanager.dragStart(this, event);
6054                 }
6055
6056                 return true;
6057         },
6058
6059         _refreshOffsets: function( event ) {
6060                 this.offset = {
6061                         top: this.positionAbs.top - this.margins.top,
6062                         left: this.positionAbs.left - this.margins.left,
6063                         scroll: false,
6064                         parent: this._getParentOffset(),
6065                         relative: this._getRelativeOffset()
6066                 };
6067
6068                 this.offset.click = {
6069                         left: event.pageX - this.offset.left,
6070                         top: event.pageY - this.offset.top
6071                 };
6072         },
6073
6074         _mouseDrag: function(event, noPropagation) {
6075                 // reset any necessary cached properties (see #5009)
6076                 if ( this.hasFixedAncestor ) {
6077                         this.offset.parent = this._getParentOffset();
6078                 }
6079
6080                 //Compute the helpers position
6081                 this.position = this._generatePosition( event, true );
6082                 this.positionAbs = this._convertPositionTo("absolute");
6083
6084                 //Call plugins and callbacks and use the resulting position if something is returned
6085                 if (!noPropagation) {
6086                         var ui = this._uiHash();
6087                         if (this._trigger("drag", event, ui) === false) {
6088                                 this._mouseUp({});
6089                                 return false;
6090                         }
6091                         this.position = ui.position;
6092                 }
6093
6094                 this.helper[ 0 ].style.left = this.position.left + "px";
6095                 this.helper[ 0 ].style.top = this.position.top + "px";
6096
6097                 if ($.ui.ddmanager) {
6098                         $.ui.ddmanager.drag(this, event);
6099                 }
6100
6101                 return false;
6102         },
6103
6104         _mouseStop: function(event) {
6105
6106                 //If we are using droppables, inform the manager about the drop
6107                 var that = this,
6108                         dropped = false;
6109                 if ($.ui.ddmanager && !this.options.dropBehaviour) {
6110                         dropped = $.ui.ddmanager.drop(this, event);
6111                 }
6112
6113                 //if a drop comes from outside (a sortable)
6114                 if (this.dropped) {
6115                         dropped = this.dropped;
6116                         this.dropped = false;
6117                 }
6118
6119                 if ((this.options.revert === "invalid" && !dropped) || (this.options.revert === "valid" && dropped) || this.options.revert === true || ($.isFunction(this.options.revert) && this.options.revert.call(this.element, dropped))) {
6120                         $(this.helper).animate(this.originalPosition, parseInt(this.options.revertDuration, 10), function() {
6121                                 if (that._trigger("stop", event) !== false) {
6122                                         that._clear();
6123                                 }
6124                         });
6125                 } else {
6126                         if (this._trigger("stop", event) !== false) {
6127                                 this._clear();
6128                         }
6129                 }
6130
6131                 return false;
6132         },
6133
6134         _mouseUp: function( event ) {
6135                 this._unblockFrames();
6136
6137                 //If the ddmanager is used for droppables, inform the manager that dragging has stopped (see #5003)
6138                 if ( $.ui.ddmanager ) {
6139                         $.ui.ddmanager.dragStop(this, event);
6140                 }
6141
6142                 // Only need to focus if the event occurred on the draggable itself, see #10527
6143                 if ( this.handleElement.is( event.target ) ) {
6144                         // The interaction is over; whether or not the click resulted in a drag, focus the element
6145                         this.element.focus();
6146                 }
6147
6148                 return $.ui.mouse.prototype._mouseUp.call(this, event);
6149         },
6150
6151         cancel: function() {
6152
6153                 if (this.helper.is(".ui-draggable-dragging")) {
6154                         this._mouseUp({});
6155                 } else {
6156                         this._clear();
6157                 }
6158
6159                 return this;
6160
6161         },
6162
6163         _getHandle: function(event) {
6164                 return this.options.handle ?
6165                         !!$( event.target ).closest( this.element.find( this.options.handle ) ).length :
6166                         true;
6167         },
6168
6169         _setHandleClassName: function() {
6170                 this.handleElement = this.options.handle ?
6171                         this.element.find( this.options.handle ) : this.element;
6172                 this.handleElement.addClass( "ui-draggable-handle" );
6173         },
6174
6175         _removeHandleClassName: function() {
6176                 this.handleElement.removeClass( "ui-draggable-handle" );
6177         },
6178
6179         _createHelper: function(event) {
6180
6181                 var o = this.options,
6182                         helperIsFunction = $.isFunction( o.helper ),
6183                         helper = helperIsFunction ?
6184                                 $( o.helper.apply( this.element[ 0 ], [ event ] ) ) :
6185                                 ( o.helper === "clone" ?
6186                                         this.element.clone().removeAttr( "id" ) :
6187                                         this.element );
6188
6189                 if (!helper.parents("body").length) {
6190                         helper.appendTo((o.appendTo === "parent" ? this.element[0].parentNode : o.appendTo));
6191                 }
6192
6193                 // http://bugs.jqueryui.com/ticket/9446
6194                 // a helper function can return the original element
6195                 // which wouldn't have been set to relative in _create
6196                 if ( helperIsFunction && helper[ 0 ] === this.element[ 0 ] ) {
6197                         this._setPositionRelative();
6198                 }
6199
6200                 if (helper[0] !== this.element[0] && !(/(fixed|absolute)/).test(helper.css("position"))) {
6201                         helper.css("position", "absolute");
6202                 }
6203
6204                 return helper;
6205
6206         },
6207
6208         _setPositionRelative: function() {
6209                 if ( !( /^(?:r|a|f)/ ).test( this.element.css( "position" ) ) ) {
6210                         this.element[ 0 ].style.position = "relative";
6211                 }
6212         },
6213
6214         _adjustOffsetFromHelper: function(obj) {
6215                 if (typeof obj === "string") {
6216                         obj = obj.split(" ");
6217                 }
6218                 if ($.isArray(obj)) {
6219                         obj = { left: +obj[0], top: +obj[1] || 0 };
6220                 }
6221                 if ("left" in obj) {
6222                         this.offset.click.left = obj.left + this.margins.left;
6223                 }
6224                 if ("right" in obj) {
6225                         this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
6226                 }
6227                 if ("top" in obj) {
6228                         this.offset.click.top = obj.top + this.margins.top;
6229                 }
6230                 if ("bottom" in obj) {
6231                         this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
6232                 }
6233         },
6234
6235         _isRootNode: function( element ) {
6236                 return ( /(html|body)/i ).test( element.tagName ) || element === this.document[ 0 ];
6237         },
6238
6239         _getParentOffset: function() {
6240
6241                 //Get the offsetParent and cache its position
6242                 var po = this.offsetParent.offset(),
6243                         document = this.document[ 0 ];
6244
6245                 // This is a special case where we need to modify a offset calculated on start, since the following happened:
6246                 // 1. The position of the helper is absolute, so it's position is calculated based on the next positioned parent
6247                 // 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't the document, which means that
6248                 //    the scroll is included in the initial calculation of the offset of the parent, and never recalculated upon drag
6249                 if (this.cssPosition === "absolute" && this.scrollParent[0] !== document && $.contains(this.scrollParent[0], this.offsetParent[0])) {
6250                         po.left += this.scrollParent.scrollLeft();
6251                         po.top += this.scrollParent.scrollTop();
6252                 }
6253
6254                 if ( this._isRootNode( this.offsetParent[ 0 ] ) ) {
6255                         po = { top: 0, left: 0 };
6256                 }
6257
6258                 return {
6259                         top: po.top + (parseInt(this.offsetParent.css("borderTopWidth"), 10) || 0),
6260                         left: po.left + (parseInt(this.offsetParent.css("borderLeftWidth"), 10) || 0)
6261                 };
6262
6263         },
6264
6265         _getRelativeOffset: function() {
6266                 if ( this.cssPosition !== "relative" ) {
6267                         return { top: 0, left: 0 };
6268                 }
6269
6270                 var p = this.element.position(),
6271                         scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );
6272
6273                 return {
6274                         top: p.top - ( parseInt(this.helper.css( "top" ), 10) || 0 ) + ( !scrollIsRootNode ? this.scrollParent.scrollTop() : 0 ),
6275                         left: p.left - ( parseInt(this.helper.css( "left" ), 10) || 0 ) + ( !scrollIsRootNode ? this.scrollParent.scrollLeft() : 0 )
6276                 };
6277
6278         },
6279
6280         _cacheMargins: function() {
6281                 this.margins = {
6282                         left: (parseInt(this.element.css("marginLeft"), 10) || 0),
6283                         top: (parseInt(this.element.css("marginTop"), 10) || 0),
6284                         right: (parseInt(this.element.css("marginRight"), 10) || 0),
6285                         bottom: (parseInt(this.element.css("marginBottom"), 10) || 0)
6286                 };
6287         },
6288
6289         _cacheHelperProportions: function() {
6290                 this.helperProportions = {
6291                         width: this.helper.outerWidth(),
6292                         height: this.helper.outerHeight()
6293                 };
6294         },
6295
6296         _setContainment: function() {
6297
6298                 var isUserScrollable, c, ce,
6299                         o = this.options,
6300                         document = this.document[ 0 ];
6301
6302                 this.relativeContainer = null;
6303
6304                 if ( !o.containment ) {
6305                         this.containment = null;
6306                         return;
6307                 }
6308
6309                 if ( o.containment === "window" ) {
6310                         this.containment = [
6311                                 $( window ).scrollLeft() - this.offset.relative.left - this.offset.parent.left,
6312                                 $( window ).scrollTop() - this.offset.relative.top - this.offset.parent.top,
6313                                 $( window ).scrollLeft() + $( window ).width() - this.helperProportions.width - this.margins.left,
6314                                 $( window ).scrollTop() + ( $( window ).height() || document.body.parentNode.scrollHeight ) - this.helperProportions.height - this.margins.top
6315                         ];
6316                         return;
6317                 }
6318
6319                 if ( o.containment === "document") {
6320                         this.containment = [
6321                                 0,
6322                                 0,
6323                                 $( document ).width() - this.helperProportions.width - this.margins.left,
6324                                 ( $( document ).height() || document.body.parentNode.scrollHeight ) - this.helperProportions.height - this.margins.top
6325                         ];
6326                         return;
6327                 }
6328
6329                 if ( o.containment.constructor === Array ) {
6330                         this.containment = o.containment;
6331                         return;
6332                 }
6333
6334                 if ( o.containment === "parent" ) {
6335                         o.containment = this.helper[ 0 ].parentNode;
6336                 }
6337
6338                 c = $( o.containment );
6339                 ce = c[ 0 ];
6340
6341                 if ( !ce ) {
6342                         return;
6343                 }
6344
6345                 isUserScrollable = /(scroll|auto)/.test( c.css( "overflow" ) );
6346
6347                 this.containment = [
6348                         ( parseInt( c.css( "borderLeftWidth" ), 10 ) || 0 ) + ( parseInt( c.css( "paddingLeft" ), 10 ) || 0 ),
6349                         ( parseInt( c.css( "borderTopWidth" ), 10 ) || 0 ) + ( parseInt( c.css( "paddingTop" ), 10 ) || 0 ),
6350                         ( isUserScrollable ? Math.max( ce.scrollWidth, ce.offsetWidth ) : ce.offsetWidth ) -
6351                                 ( parseInt( c.css( "borderRightWidth" ), 10 ) || 0 ) -
6352                                 ( parseInt( c.css( "paddingRight" ), 10 ) || 0 ) -
6353                                 this.helperProportions.width -
6354                                 this.margins.left -
6355                                 this.margins.right,
6356                         ( isUserScrollable ? Math.max( ce.scrollHeight, ce.offsetHeight ) : ce.offsetHeight ) -
6357                                 ( parseInt( c.css( "borderBottomWidth" ), 10 ) || 0 ) -
6358                                 ( parseInt( c.css( "paddingBottom" ), 10 ) || 0 ) -
6359                                 this.helperProportions.height -
6360                                 this.margins.top -
6361                                 this.margins.bottom
6362                 ];
6363                 this.relativeContainer = c;
6364         },
6365
6366         _convertPositionTo: function(d, pos) {
6367
6368                 if (!pos) {
6369                         pos = this.position;
6370                 }
6371
6372                 var mod = d === "absolute" ? 1 : -1,
6373                         scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] );
6374
6375                 return {
6376                         top: (
6377                                 pos.top +                                                                                                                               // The absolute mouse position
6378                                 this.offset.relative.top * mod +                                                                                // Only for relative positioned nodes: Relative offset from element to offset parent
6379                                 this.offset.parent.top * mod -                                                                          // The offsetParent's offset without borders (offset + border)
6380                                 ( ( this.cssPosition === "fixed" ? -this.offset.scroll.top : ( scrollIsRootNode ? 0 : this.offset.scroll.top ) ) * mod)
6381                         ),
6382                         left: (
6383                                 pos.left +                                                                                                                              // The absolute mouse position
6384                                 this.offset.relative.left * mod +                                                                               // Only for relative positioned nodes: Relative offset from element to offset parent
6385                                 this.offset.parent.left * mod   -                                                                               // The offsetParent's offset without borders (offset + border)
6386                                 ( ( this.cssPosition === "fixed" ? -this.offset.scroll.left : ( scrollIsRootNode ? 0 : this.offset.scroll.left ) ) * mod)
6387                         )
6388                 };
6389
6390         },
6391
6392         _generatePosition: function( event, constrainPosition ) {
6393
6394                 var containment, co, top, left,
6395                         o = this.options,
6396                         scrollIsRootNode = this._isRootNode( this.scrollParent[ 0 ] ),
6397                         pageX = event.pageX,
6398                         pageY = event.pageY;
6399
6400                 // Cache the scroll
6401                 if ( !scrollIsRootNode || !this.offset.scroll ) {
6402                         this.offset.scroll = {
6403                                 top: this.scrollParent.scrollTop(),
6404                                 left: this.scrollParent.scrollLeft()
6405                         };
6406                 }
6407
6408                 /*
6409                  * - Position constraining -
6410                  * Constrain the position to a mix of grid, containment.
6411                  */
6412
6413                 // If we are not dragging yet, we won't check for options
6414                 if ( constrainPosition ) {
6415                         if ( this.containment ) {
6416                                 if ( this.relativeContainer ){
6417                                         co = this.relativeContainer.offset();
6418                                         containment = [
6419                                                 this.containment[ 0 ] + co.left,
6420                                                 this.containment[ 1 ] + co.top,
6421                                                 this.containment[ 2 ] + co.left,
6422                                                 this.containment[ 3 ] + co.top
6423                                         ];
6424                                 } else {
6425                                         containment = this.containment;
6426                                 }
6427
6428                                 if (event.pageX - this.offset.click.left < containment[0]) {
6429                                         pageX = containment[0] + this.offset.click.left;
6430                                 }
6431                                 if (event.pageY - this.offset.click.top < containment[1]) {
6432                                         pageY = containment[1] + this.offset.click.top;
6433                                 }
6434                                 if (event.pageX - this.offset.click.left > containment[2]) {
6435                                         pageX = containment[2] + this.offset.click.left;
6436                                 }
6437                                 if (event.pageY - this.offset.click.top > containment[3]) {
6438                                         pageY = containment[3] + this.offset.click.top;
6439                                 }
6440                         }
6441
6442                         if (o.grid) {
6443                                 //Check for grid elements set to 0 to prevent divide by 0 error causing invalid argument errors in IE (see ticket #6950)
6444                                 top = o.grid[1] ? this.originalPageY + Math.round((pageY - this.originalPageY) / o.grid[1]) * o.grid[1] : this.originalPageY;
6445                                 pageY = containment ? ((top - this.offset.click.top >= containment[1] || top - this.offset.click.top > containment[3]) ? top : ((top - this.offset.click.top >= containment[1]) ? top - o.grid[1] : top + o.grid[1])) : top;
6446
6447                                 left = o.grid[0] ? this.originalPageX + Math.round((pageX - this.originalPageX) / o.grid[0]) * o.grid[0] : this.originalPageX;
6448                                 pageX = containment ? ((left - this.offset.click.left >= containment[0] || left - this.offset.click.left > containment[2]) ? left : ((left - this.offset.click.left >= containment[0]) ? left - o.grid[0] : left + o.grid[0])) : left;
6449                         }
6450
6451                         if ( o.axis === "y" ) {
6452                                 pageX = this.originalPageX;
6453                         }
6454
6455                         if ( o.axis === "x" ) {
6456                                 pageY = this.originalPageY;
6457                         }
6458                 }
6459
6460                 return {
6461                         top: (
6462                                 pageY -                                                                                                                                 // The absolute mouse position
6463                                 this.offset.click.top   -                                                                                               // Click offset (relative to the element)
6464                                 this.offset.relative.top -                                                                                              // Only for relative positioned nodes: Relative offset from element to offset parent
6465                                 this.offset.parent.top +                                                                                                // The offsetParent's offset without borders (offset + border)
6466                                 ( this.cssPosition === "fixed" ? -this.offset.scroll.top : ( scrollIsRootNode ? 0 : this.offset.scroll.top ) )
6467                         ),
6468                         left: (
6469                                 pageX -                                                                                                                                 // The absolute mouse position
6470                                 this.offset.click.left -                                                                                                // Click offset (relative to the element)
6471                                 this.offset.relative.left -                                                                                             // Only for relative positioned nodes: Relative offset from element to offset parent
6472                                 this.offset.parent.left +                                                                                               // The offsetParent's offset without borders (offset + border)
6473                                 ( this.cssPosition === "fixed" ? -this.offset.scroll.left : ( scrollIsRootNode ? 0 : this.offset.scroll.left ) )
6474                         )
6475                 };
6476
6477         },
6478
6479         _clear: function() {
6480                 this.helper.removeClass("ui-draggable-dragging");
6481                 if (this.helper[0] !== this.element[0] && !this.cancelHelperRemoval) {
6482                         this.helper.remove();
6483                 }
6484                 this.helper = null;
6485                 this.cancelHelperRemoval = false;
6486                 if ( this.destroyOnClear ) {
6487                         this.destroy();
6488                 }
6489         },
6490
6491         _normalizeRightBottom: function() {
6492                 if ( this.options.axis !== "y" && this.helper.css( "right" ) !== "auto" ) {
6493                         this.helper.width( this.helper.width() );
6494                         this.helper.css( "right", "auto" );
6495                 }
6496                 if ( this.options.axis !== "x" && this.helper.css( "bottom" ) !== "auto" ) {
6497                         this.helper.height( this.helper.height() );
6498                         this.helper.css( "bottom", "auto" );
6499                 }
6500         },
6501
6502         // From now on bulk stuff - mainly helpers
6503
6504         _trigger: function( type, event, ui ) {
6505                 ui = ui || this._uiHash();
6506                 $.ui.plugin.call( this, type, [ event, ui, this ], true );
6507
6508                 // Absolute position and offset (see #6884 ) have to be recalculated after plugins
6509                 if ( /^(drag|start|stop)/.test( type ) ) {
6510                         this.positionAbs = this._convertPositionTo( "absolute" );
6511                         ui.offset = this.positionAbs;
6512                 }
6513                 return $.Widget.prototype._trigger.call( this, type, event, ui );
6514         },
6515
6516         plugins: {},
6517
6518         _uiHash: function() {
6519                 return {
6520                         helper: this.helper,
6521                         position: this.position,
6522                         originalPosition: this.originalPosition,
6523                         offset: this.positionAbs
6524                 };
6525         }
6526
6527 });
6528
6529 $.ui.plugin.add( "draggable", "connectToSortable", {
6530         start: function( event, ui, draggable ) {
6531                 var uiSortable = $.extend( {}, ui, {
6532                         item: draggable.element
6533                 });
6534
6535                 draggable.sortables = [];
6536                 $( draggable.options.connectToSortable ).each(function() {
6537                         var sortable = $( this ).sortable( "instance" );
6538
6539                         if ( sortable && !sortable.options.disabled ) {
6540                                 draggable.sortables.push( sortable );
6541
6542                                 // refreshPositions is called at drag start to refresh the containerCache
6543                                 // which is used in drag. This ensures it's initialized and synchronized
6544                                 // with any changes that might have happened on the page since initialization.
6545                                 sortable.refreshPositions();
6546                                 sortable._trigger("activate", event, uiSortable);
6547                         }
6548                 });
6549         },
6550         stop: function( event, ui, draggable ) {
6551                 var uiSortable = $.extend( {}, ui, {
6552                         item: draggable.element
6553                 });
6554
6555                 draggable.cancelHelperRemoval = false;
6556
6557                 $.each( draggable.sortables, function() {
6558                         var sortable = this;
6559
6560                         if ( sortable.isOver ) {
6561                                 sortable.isOver = 0;
6562
6563                                 // Allow this sortable to handle removing the helper
6564                                 draggable.cancelHelperRemoval = true;
6565                                 sortable.cancelHelperRemoval = false;
6566
6567                                 // Use _storedCSS To restore properties in the sortable,
6568                                 // as this also handles revert (#9675) since the draggable
6569                                 // may have modified them in unexpected ways (#8809)
6570                                 sortable._storedCSS = {
6571                                         position: sortable.placeholder.css( "position" ),
6572                                         top: sortable.placeholder.css( "top" ),
6573                                         left: sortable.placeholder.css( "left" )
6574                                 };
6575
6576                                 sortable._mouseStop(event);
6577
6578                                 // Once drag has ended, the sortable should return to using
6579                                 // its original helper, not the shared helper from draggable
6580                                 sortable.options.helper = sortable.options._helper;
6581                         } else {
6582                                 // Prevent this Sortable from removing the helper.
6583                                 // However, don't set the draggable to remove the helper
6584                                 // either as another connected Sortable may yet handle the removal.
6585                                 sortable.cancelHelperRemoval = true;
6586
6587                                 sortable._trigger( "deactivate", event, uiSortable );
6588                         }
6589                 });
6590         },
6591         drag: function( event, ui, draggable ) {
6592                 $.each( draggable.sortables, function() {
6593                         var innermostIntersecting = false,
6594                                 sortable = this;
6595
6596                         // Copy over variables that sortable's _intersectsWith uses
6597                         sortable.positionAbs = draggable.positionAbs;
6598                         sortable.helperProportions = draggable.helperProportions;
6599                         sortable.offset.click = draggable.offset.click;
6600
6601                         if ( sortable._intersectsWith( sortable.containerCache ) ) {
6602                                 innermostIntersecting = true;
6603
6604                                 $.each( draggable.sortables, function() {
6605                                         // Copy over variables that sortable's _intersectsWith uses
6606                                         this.positionAbs = draggable.positionAbs;
6607                                         this.helperProportions = draggable.helperProportions;
6608                                         this.offset.click = draggable.offset.click;
6609
6610                                         if ( this !== sortable &&
6611                                                         this._intersectsWith( this.containerCache ) &&
6612                                                         $.contains( sortable.element[ 0 ], this.element[ 0 ] ) ) {
6613                                                 innermostIntersecting = false;
6614                                         }
6615
6616                                         return innermostIntersecting;
6617                                 });
6618                         }
6619
6620                         if ( innermostIntersecting ) {
6621                                 // If it intersects, we use a little isOver variable and set it once,
6622                                 // so that the move-in stuff gets fired only once.
6623                                 if ( !sortable.isOver ) {
6624                                         sortable.isOver = 1;
6625
6626                                         // Store draggable's parent in case we need to reappend to it later.
6627                                         draggable._parent = ui.helper.parent();
6628
6629                                         sortable.currentItem = ui.helper
6630                                                 .appendTo( sortable.element )
6631                                                 .data( "ui-sortable-item", true );
6632
6633                                         // Store helper option to later restore it
6634                                         sortable.options._helper = sortable.options.helper;
6635
6636                                         sortable.options.helper = function() {
6637                                                 return ui.helper[ 0 ];
6638                                         };
6639
6640                                         // Fire the start events of the sortable with our passed browser event,
6641                                         // and our own helper (so it doesn't create a new one)
6642                                         event.target = sortable.currentItem[ 0 ];
6643                                         sortable._mouseCapture( event, true );
6644                                         sortable._mouseStart( event, true, true );
6645
6646                                         // Because the browser event is way off the new appended portlet,
6647                                         // modify necessary variables to reflect the changes
6648                                         sortable.offset.click.top = draggable.offset.click.top;
6649                                         sortable.offset.click.left = draggable.offset.click.left;
6650                                         sortable.offset.parent.left -= draggable.offset.parent.left -
6651                                                 sortable.offset.parent.left;
6652                                         sortable.offset.parent.top -= draggable.offset.parent.top -
6653                                                 sortable.offset.parent.top;
6654
6655                                         draggable._trigger( "toSortable", event );
6656
6657                                         // Inform draggable that the helper is in a valid drop zone,
6658                                         // used solely in the revert option to handle "valid/invalid".
6659                                         draggable.dropped = sortable.element;
6660
6661                                         // Need to refreshPositions of all sortables in the case that
6662                                         // adding to one sortable changes the location of the other sortables (#9675)
6663                                         $.each( draggable.sortables, function() {
6664                                                 this.refreshPositions();
6665                                         });
6666
6667                                         // hack so receive/update callbacks work (mostly)
6668                                         draggable.currentItem = draggable.element;
6669                                         sortable.fromOutside = draggable;
6670                                 }
6671
6672                                 if ( sortable.currentItem ) {
6673                                         sortable._mouseDrag( event );
6674                                         // Copy the sortable's position because the draggable's can potentially reflect
6675                                         // a relative position, while sortable is always absolute, which the dragged
6676                                         // element has now become. (#8809)
6677                                         ui.position = sortable.position;
6678                                 }
6679                         } else {
6680                                 // If it doesn't intersect with the sortable, and it intersected before,
6681                                 // we fake the drag stop of the sortable, but make sure it doesn't remove
6682                                 // the helper by using cancelHelperRemoval.
6683                                 if ( sortable.isOver ) {
6684
6685                                         sortable.isOver = 0;
6686                                         sortable.cancelHelperRemoval = true;
6687
6688                                         // Calling sortable's mouseStop would trigger a revert,
6689                                         // so revert must be temporarily false until after mouseStop is called.
6690                                         sortable.options._revert = sortable.options.revert;
6691                                         sortable.options.revert = false;
6692
6693                                         sortable._trigger( "out", event, sortable._uiHash( sortable ) );
6694                                         sortable._mouseStop( event, true );
6695
6696                                         // restore sortable behaviors that were modfied
6697                                         // when the draggable entered the sortable area (#9481)
6698                                         sortable.options.revert = sortable.options._revert;
6699                                         sortable.options.helper = sortable.options._helper;
6700
6701                                         if ( sortable.placeholder ) {
6702                                                 sortable.placeholder.remove();
6703                                         }
6704
6705                                         // Restore and recalculate the draggable's offset considering the sortable
6706                                         // may have modified them in unexpected ways. (#8809, #10669)
6707                                         ui.helper.appendTo( draggable._parent );
6708                                         draggable._refreshOffsets( event );
6709                                         ui.position = draggable._generatePosition( event, true );
6710
6711                                         draggable._trigger( "fromSortable", event );
6712
6713                                         // Inform draggable that the helper is no longer in a valid drop zone
6714                                         draggable.dropped = false;
6715
6716                                         // Need to refreshPositions of all sortables just in case removing
6717                                         // from one sortable changes the location of other sortables (#9675)
6718                                         $.each( draggable.sortables, function() {
6719                                                 this.refreshPositions();
6720                                         });
6721                                 }
6722                         }
6723                 });
6724         }
6725 });
6726
6727 $.ui.plugin.add("draggable", "cursor", {
6728         start: function( event, ui, instance ) {
6729                 var t = $( "body" ),
6730                         o = instance.options;
6731
6732                 if (t.css("cursor")) {
6733                         o._cursor = t.css("cursor");
6734                 }
6735                 t.css("cursor", o.cursor);
6736         },
6737         stop: function( event, ui, instance ) {
6738                 var o = instance.options;
6739                 if (o._cursor) {
6740                         $("body").css("cursor", o._cursor);
6741                 }
6742         }
6743 });
6744
6745 $.ui.plugin.add("draggable", "opacity", {
6746         start: function( event, ui, instance ) {
6747                 var t = $( ui.helper ),
6748                         o = instance.options;
6749                 if (t.css("opacity")) {
6750                         o._opacity = t.css("opacity");
6751                 }
6752                 t.css("opacity", o.opacity);
6753         },
6754         stop: function( event, ui, instance ) {
6755                 var o = instance.options;
6756                 if (o._opacity) {
6757                         $(ui.helper).css("opacity", o._opacity);
6758                 }
6759         }
6760 });
6761
6762 $.ui.plugin.add("draggable", "scroll", {
6763         start: function( event, ui, i ) {
6764                 if ( !i.scrollParentNotHidden ) {
6765                         i.scrollParentNotHidden = i.helper.scrollParent( false );
6766                 }
6767
6768                 if ( i.scrollParentNotHidden[ 0 ] !== i.document[ 0 ] && i.scrollParentNotHidden[ 0 ].tagName !== "HTML" ) {
6769                         i.overflowOffset = i.scrollParentNotHidden.offset();
6770                 }
6771         },
6772         drag: function( event, ui, i  ) {
6773
6774                 var o = i.options,
6775                         scrolled = false,
6776                         scrollParent = i.scrollParentNotHidden[ 0 ],
6777                         document = i.document[ 0 ];
6778
6779                 if ( scrollParent !== document && scrollParent.tagName !== "HTML" ) {
6780                         if ( !o.axis || o.axis !== "x" ) {
6781                                 if ( ( i.overflowOffset.top + scrollParent.offsetHeight ) - event.pageY < o.scrollSensitivity ) {
6782                                         scrollParent.scrollTop = scrolled = scrollParent.scrollTop + o.scrollSpeed;
6783                                 } else if ( event.pageY - i.overflowOffset.top < o.scrollSensitivity ) {
6784                                         scrollParent.scrollTop = scrolled = scrollParent.scrollTop - o.scrollSpeed;
6785                                 }
6786                         }
6787
6788                         if ( !o.axis || o.axis !== "y" ) {
6789                                 if ( ( i.overflowOffset.left + scrollParent.offsetWidth ) - event.pageX < o.scrollSensitivity ) {
6790                                         scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft + o.scrollSpeed;
6791                                 } else if ( event.pageX - i.overflowOffset.left < o.scrollSensitivity ) {
6792                                         scrollParent.scrollLeft = scrolled = scrollParent.scrollLeft - o.scrollSpeed;
6793                                 }
6794                         }
6795
6796                 } else {
6797
6798                         if (!o.axis || o.axis !== "x") {
6799                                 if (event.pageY - $(document).scrollTop() < o.scrollSensitivity) {
6800                                         scrolled = $(document).scrollTop($(document).scrollTop() - o.scrollSpeed);
6801                                 } else if ($(window).height() - (event.pageY - $(document).scrollTop()) < o.scrollSensitivity) {
6802                                         scrolled = $(document).scrollTop($(document).scrollTop() + o.scrollSpeed);
6803                                 }
6804                         }
6805
6806                         if (!o.axis || o.axis !== "y") {
6807                                 if (event.pageX - $(document).scrollLeft() < o.scrollSensitivity) {
6808                                         scrolled = $(document).scrollLeft($(document).scrollLeft() - o.scrollSpeed);
6809                                 } else if ($(window).width() - (event.pageX - $(document).scrollLeft()) < o.scrollSensitivity) {
6810                                         scrolled = $(document).scrollLeft($(document).scrollLeft() + o.scrollSpeed);
6811                                 }
6812                         }
6813
6814                 }
6815
6816                 if (scrolled !== false && $.ui.ddmanager && !o.dropBehaviour) {
6817                         $.ui.ddmanager.prepareOffsets(i, event);
6818                 }
6819
6820         }
6821 });
6822
6823 $.ui.plugin.add("draggable", "snap", {
6824         start: function( event, ui, i ) {
6825
6826                 var o = i.options;
6827
6828                 i.snapElements = [];
6829
6830                 $(o.snap.constructor !== String ? ( o.snap.items || ":data(ui-draggable)" ) : o.snap).each(function() {
6831                         var $t = $(this),
6832                                 $o = $t.offset();
6833                         if (this !== i.element[0]) {
6834                                 i.snapElements.push({
6835                                         item: this,
6836                                         width: $t.outerWidth(), height: $t.outerHeight(),
6837                                         top: $o.top, left: $o.left
6838                                 });
6839                         }
6840                 });
6841
6842         },
6843         drag: function( event, ui, inst ) {
6844
6845                 var ts, bs, ls, rs, l, r, t, b, i, first,
6846                         o = inst.options,
6847                         d = o.snapTolerance,
6848                         x1 = ui.offset.left, x2 = x1 + inst.helperProportions.width,
6849                         y1 = ui.offset.top, y2 = y1 + inst.helperProportions.height;
6850
6851                 for (i = inst.snapElements.length - 1; i >= 0; i--){
6852
6853                         l = inst.snapElements[i].left - inst.margins.left;
6854                         r = l + inst.snapElements[i].width;
6855                         t = inst.snapElements[i].top - inst.margins.top;
6856                         b = t + inst.snapElements[i].height;
6857
6858                         if ( x2 < l - d || x1 > r + d || y2 < t - d || y1 > b + d || !$.contains( inst.snapElements[ i ].item.ownerDocument, inst.snapElements[ i ].item ) ) {
6859                                 if (inst.snapElements[i].snapping) {
6860                                         (inst.options.snap.release && inst.options.snap.release.call(inst.element, event, $.extend(inst._uiHash(), { snapItem: inst.snapElements[i].item })));
6861                                 }
6862                                 inst.snapElements[i].snapping = false;
6863                                 continue;
6864                         }
6865
6866                         if (o.snapMode !== "inner") {
6867                                 ts = Math.abs(t - y2) <= d;
6868                                 bs = Math.abs(b - y1) <= d;
6869                                 ls = Math.abs(l - x2) <= d;
6870                                 rs = Math.abs(r - x1) <= d;
6871                                 if (ts) {
6872                                         ui.position.top = inst._convertPositionTo("relative", { top: t - inst.helperProportions.height, left: 0 }).top;
6873                                 }
6874                                 if (bs) {
6875                                         ui.position.top = inst._convertPositionTo("relative", { top: b, left: 0 }).top;
6876                                 }
6877                                 if (ls) {
6878                                         ui.position.left = inst._convertPositionTo("relative", { top: 0, left: l - inst.helperProportions.width }).left;
6879                                 }
6880                                 if (rs) {
6881                                         ui.position.left = inst._convertPositionTo("relative", { top: 0, left: r }).left;
6882                                 }
6883                         }
6884
6885                         first = (ts || bs || ls || rs);
6886
6887                         if (o.snapMode !== "outer") {
6888                                 ts = Math.abs(t - y1) <= d;
6889                                 bs = Math.abs(b - y2) <= d;
6890                                 ls = Math.abs(l - x1) <= d;
6891                                 rs = Math.abs(r - x2) <= d;
6892                                 if (ts) {
6893                                         ui.position.top = inst._convertPositionTo("relative", { top: t, left: 0 }).top;
6894                                 }
6895                                 if (bs) {
6896                                         ui.position.top = inst._convertPositionTo("relative", { top: b - inst.helperProportions.height, left: 0 }).top;
6897                                 }
6898                                 if (ls) {
6899                                         ui.position.left = inst._convertPositionTo("relative", { top: 0, left: l }).left;
6900                                 }
6901                                 if (rs) {
6902                                         ui.position.left = inst._convertPositionTo("relative", { top: 0, left: r - inst.helperProportions.width }).left;
6903                                 }
6904                         }
6905
6906                         if (!inst.snapElements[i].snapping && (ts || bs || ls || rs || first)) {
6907                                 (inst.options.snap.snap && inst.options.snap.snap.call(inst.element, event, $.extend(inst._uiHash(), { snapItem: inst.snapElements[i].item })));
6908                         }
6909                         inst.snapElements[i].snapping = (ts || bs || ls || rs || first);
6910
6911                 }
6912
6913         }
6914 });
6915
6916 $.ui.plugin.add("draggable", "stack", {
6917         start: function( event, ui, instance ) {
6918                 var min,
6919                         o = instance.options,
6920                         group = $.makeArray($(o.stack)).sort(function(a, b) {
6921                                 return (parseInt($(a).css("zIndex"), 10) || 0) - (parseInt($(b).css("zIndex"), 10) || 0);
6922                         });
6923
6924                 if (!group.length) { return; }
6925
6926                 min = parseInt($(group[0]).css("zIndex"), 10) || 0;
6927                 $(group).each(function(i) {
6928                         $(this).css("zIndex", min + i);
6929                 });
6930                 this.css("zIndex", (min + group.length));
6931         }
6932 });
6933
6934 $.ui.plugin.add("draggable", "zIndex", {
6935         start: function( event, ui, instance ) {
6936                 var t = $( ui.helper ),
6937                         o = instance.options;
6938
6939                 if (t.css("zIndex")) {
6940                         o._zIndex = t.css("zIndex");
6941                 }
6942                 t.css("zIndex", o.zIndex);
6943         },
6944         stop: function( event, ui, instance ) {
6945                 var o = instance.options;
6946
6947                 if (o._zIndex) {
6948                         $(ui.helper).css("zIndex", o._zIndex);
6949                 }
6950         }
6951 });
6952
6953 var draggable = $.ui.draggable;
6954
6955
6956 /*!
6957  * jQuery UI Resizable 1.11.4
6958  * http://jqueryui.com
6959  *
6960  * Copyright jQuery Foundation and other contributors
6961  * Released under the MIT license.
6962  * http://jquery.org/license
6963  *
6964  * http://api.jqueryui.com/resizable/
6965  */
6966
6967
6968 $.widget("ui.resizable", $.ui.mouse, {
6969         version: "1.11.4",
6970         widgetEventPrefix: "resize",
6971         options: {
6972                 alsoResize: false,
6973                 animate: false,
6974                 animateDuration: "slow",
6975                 animateEasing: "swing",
6976                 aspectRatio: false,
6977                 autoHide: false,
6978                 containment: false,
6979                 ghost: false,
6980                 grid: false,
6981                 handles: "e,s,se",
6982                 helper: false,
6983                 maxHeight: null,
6984                 maxWidth: null,
6985                 minHeight: 10,
6986                 minWidth: 10,
6987                 // See #7960
6988                 zIndex: 90,
6989
6990                 // callbacks
6991                 resize: null,
6992                 start: null,
6993                 stop: null
6994         },
6995
6996         _num: function( value ) {
6997                 return parseInt( value, 10 ) || 0;
6998         },
6999
7000         _isNumber: function( value ) {
7001                 return !isNaN( parseInt( value, 10 ) );
7002         },
7003
7004         _hasScroll: function( el, a ) {
7005
7006                 if ( $( el ).css( "overflow" ) === "hidden") {
7007                         return false;
7008                 }
7009
7010                 var scroll = ( a && a === "left" ) ? "scrollLeft" : "scrollTop",
7011                         has = false;
7012
7013                 if ( el[ scroll ] > 0 ) {
7014                         return true;
7015                 }
7016
7017                 // TODO: determine which cases actually cause this to happen
7018                 // if the element doesn't have the scroll set, see if it's possible to
7019                 // set the scroll
7020                 el[ scroll ] = 1;
7021                 has = ( el[ scroll ] > 0 );
7022                 el[ scroll ] = 0;
7023                 return has;
7024         },
7025
7026         _create: function() {
7027
7028                 var n, i, handle, axis, hname,
7029                         that = this,
7030                         o = this.options;
7031                 this.element.addClass("ui-resizable");
7032
7033                 $.extend(this, {
7034                         _aspectRatio: !!(o.aspectRatio),
7035                         aspectRatio: o.aspectRatio,
7036                         originalElement: this.element,
7037                         _proportionallyResizeElements: [],
7038                         _helper: o.helper || o.ghost || o.animate ? o.helper || "ui-resizable-helper" : null
7039                 });
7040
7041                 // Wrap the element if it cannot hold child nodes
7042                 if (this.element[0].nodeName.match(/^(canvas|textarea|input|select|button|img)$/i)) {
7043
7044                         this.element.wrap(
7045                                 $("<div class='ui-wrapper' style='overflow: hidden;'></div>").css({
7046                                         position: this.element.css("position"),
7047                                         width: this.element.outerWidth(),
7048                                         height: this.element.outerHeight(),
7049                                         top: this.element.css("top"),
7050                                         left: this.element.css("left")
7051                                 })
7052                         );
7053
7054                         this.element = this.element.parent().data(
7055                                 "ui-resizable", this.element.resizable( "instance" )
7056                         );
7057
7058                         this.elementIsWrapper = true;
7059
7060                         this.element.css({
7061                                 marginLeft: this.originalElement.css("marginLeft"),
7062                                 marginTop: this.originalElement.css("marginTop"),
7063                                 marginRight: this.originalElement.css("marginRight"),
7064                                 marginBottom: this.originalElement.css("marginBottom")
7065                         });
7066                         this.originalElement.css({
7067                                 marginLeft: 0,
7068                                 marginTop: 0,
7069                                 marginRight: 0,
7070                                 marginBottom: 0
7071                         });
7072                         // support: Safari
7073                         // Prevent Safari textarea resize
7074                         this.originalResizeStyle = this.originalElement.css("resize");
7075                         this.originalElement.css("resize", "none");
7076
7077                         this._proportionallyResizeElements.push( this.originalElement.css({
7078                                 position: "static",
7079                                 zoom: 1,
7080                                 display: "block"
7081                         }) );
7082
7083                         // support: IE9
7084                         // avoid IE jump (hard set the margin)
7085                         this.originalElement.css({ margin: this.originalElement.css("margin") });
7086
7087                         this._proportionallyResize();
7088                 }
7089
7090                 this.handles = o.handles ||
7091                         ( !$(".ui-resizable-handle", this.element).length ?
7092                                 "e,s,se" : {
7093                                         n: ".ui-resizable-n",
7094                                         e: ".ui-resizable-e",
7095                                         s: ".ui-resizable-s",
7096                                         w: ".ui-resizable-w",
7097                                         se: ".ui-resizable-se",
7098                                         sw: ".ui-resizable-sw",
7099                                         ne: ".ui-resizable-ne",
7100                                         nw: ".ui-resizable-nw"
7101                                 } );
7102
7103                 this._handles = $();
7104                 if ( this.handles.constructor === String ) {
7105
7106                         if ( this.handles === "all") {
7107                                 this.handles = "n,e,s,w,se,sw,ne,nw";
7108                         }
7109
7110                         n = this.handles.split(",");
7111                         this.handles = {};
7112
7113                         for (i = 0; i < n.length; i++) {
7114
7115                                 handle = $.trim(n[i]);
7116                                 hname = "ui-resizable-" + handle;
7117                                 axis = $("<div class='ui-resizable-handle " + hname + "'></div>");
7118
7119                                 axis.css({ zIndex: o.zIndex });
7120
7121                                 // TODO : What's going on here?
7122                                 if ("se" === handle) {
7123                                         axis.addClass("ui-icon ui-icon-gripsmall-diagonal-se");
7124                                 }
7125
7126                                 this.handles[handle] = ".ui-resizable-" + handle;
7127                                 this.element.append(axis);
7128                         }
7129
7130                 }
7131
7132                 this._renderAxis = function(target) {
7133
7134                         var i, axis, padPos, padWrapper;
7135
7136                         target = target || this.element;
7137
7138                         for (i in this.handles) {
7139
7140                                 if (this.handles[i].constructor === String) {
7141                                         this.handles[i] = this.element.children( this.handles[ i ] ).first().show();
7142                                 } else if ( this.handles[ i ].jquery || this.handles[ i ].nodeType ) {
7143                                         this.handles[ i ] = $( this.handles[ i ] );
7144                                         this._on( this.handles[ i ], { "mousedown": that._mouseDown });
7145                                 }
7146
7147                                 if (this.elementIsWrapper && this.originalElement[0].nodeName.match(/^(textarea|input|select|button)$/i)) {
7148
7149                                         axis = $(this.handles[i], this.element);
7150
7151                                         padWrapper = /sw|ne|nw|se|n|s/.test(i) ? axis.outerHeight() : axis.outerWidth();
7152
7153                                         padPos = [ "padding",
7154                                                 /ne|nw|n/.test(i) ? "Top" :
7155                                                 /se|sw|s/.test(i) ? "Bottom" :
7156                                                 /^e$/.test(i) ? "Right" : "Left" ].join("");
7157
7158                                         target.css(padPos, padWrapper);
7159
7160                                         this._proportionallyResize();
7161                                 }
7162
7163                                 this._handles = this._handles.add( this.handles[ i ] );
7164                         }
7165                 };
7166
7167                 // TODO: make renderAxis a prototype function
7168                 this._renderAxis(this.element);
7169
7170                 this._handles = this._handles.add( this.element.find( ".ui-resizable-handle" ) );
7171                 this._handles.disableSelection();
7172
7173                 this._handles.mouseover(function() {
7174                         if (!that.resizing) {
7175                                 if (this.className) {
7176                                         axis = this.className.match(/ui-resizable-(se|sw|ne|nw|n|e|s|w)/i);
7177                                 }
7178                                 that.axis = axis && axis[1] ? axis[1] : "se";
7179                         }
7180                 });
7181
7182                 if (o.autoHide) {
7183                         this._handles.hide();
7184                         $(this.element)
7185                                 .addClass("ui-resizable-autohide")
7186                                 .mouseenter(function() {
7187                                         if (o.disabled) {
7188                                                 return;
7189                                         }
7190                                         $(this).removeClass("ui-resizable-autohide");
7191                                         that._handles.show();
7192                                 })
7193                                 .mouseleave(function() {
7194                                         if (o.disabled) {
7195                                                 return;
7196                                         }
7197                                         if (!that.resizing) {
7198                                                 $(this).addClass("ui-resizable-autohide");
7199                                                 that._handles.hide();
7200                                         }
7201                                 });
7202                 }
7203
7204                 this._mouseInit();
7205         },
7206
7207         _destroy: function() {
7208
7209                 this._mouseDestroy();
7210
7211                 var wrapper,
7212                         _destroy = function(exp) {
7213                                 $(exp)
7214                                         .removeClass("ui-resizable ui-resizable-disabled ui-resizable-resizing")
7215                                         .removeData("resizable")
7216                                         .removeData("ui-resizable")
7217                                         .unbind(".resizable")
7218                                         .find(".ui-resizable-handle")
7219                                                 .remove();
7220                         };
7221
7222                 // TODO: Unwrap at same DOM position
7223                 if (this.elementIsWrapper) {
7224                         _destroy(this.element);
7225                         wrapper = this.element;
7226                         this.originalElement.css({
7227                                 position: wrapper.css("position"),
7228                                 width: wrapper.outerWidth(),
7229                                 height: wrapper.outerHeight(),
7230                                 top: wrapper.css("top"),
7231                                 left: wrapper.css("left")
7232                         }).insertAfter( wrapper );
7233                         wrapper.remove();
7234                 }
7235
7236                 this.originalElement.css("resize", this.originalResizeStyle);
7237                 _destroy(this.originalElement);
7238
7239                 return this;
7240         },
7241
7242         _mouseCapture: function(event) {
7243                 var i, handle,
7244                         capture = false;
7245
7246                 for (i in this.handles) {
7247                         handle = $(this.handles[i])[0];
7248                         if (handle === event.target || $.contains(handle, event.target)) {
7249                                 capture = true;
7250                         }
7251                 }
7252
7253                 return !this.options.disabled && capture;
7254         },
7255
7256         _mouseStart: function(event) {
7257
7258                 var curleft, curtop, cursor,
7259                         o = this.options,
7260                         el = this.element;
7261
7262                 this.resizing = true;
7263
7264                 this._renderProxy();
7265
7266                 curleft = this._num(this.helper.css("left"));
7267                 curtop = this._num(this.helper.css("top"));
7268
7269                 if (o.containment) {
7270                         curleft += $(o.containment).scrollLeft() || 0;
7271                         curtop += $(o.containment).scrollTop() || 0;
7272                 }
7273
7274                 this.offset = this.helper.offset();
7275                 this.position = { left: curleft, top: curtop };
7276
7277                 this.size = this._helper ? {
7278                                 width: this.helper.width(),
7279                                 height: this.helper.height()
7280                         } : {
7281                                 width: el.width(),
7282                                 height: el.height()
7283                         };
7284
7285                 this.originalSize = this._helper ? {
7286                                 width: el.outerWidth(),
7287                                 height: el.outerHeight()
7288                         } : {
7289                                 width: el.width(),
7290                                 height: el.height()
7291                         };
7292
7293                 this.sizeDiff = {
7294                         width: el.outerWidth() - el.width(),
7295                         height: el.outerHeight() - el.height()
7296                 };
7297
7298                 this.originalPosition = { left: curleft, top: curtop };
7299                 this.originalMousePosition = { left: event.pageX, top: event.pageY };
7300
7301                 this.aspectRatio = (typeof o.aspectRatio === "number") ?
7302                         o.aspectRatio :
7303                         ((this.originalSize.width / this.originalSize.height) || 1);
7304
7305                 cursor = $(".ui-resizable-" + this.axis).css("cursor");
7306                 $("body").css("cursor", cursor === "auto" ? this.axis + "-resize" : cursor);
7307
7308                 el.addClass("ui-resizable-resizing");
7309                 this._propagate("start", event);
7310                 return true;
7311         },
7312
7313         _mouseDrag: function(event) {
7314
7315                 var data, props,
7316                         smp = this.originalMousePosition,
7317                         a = this.axis,
7318                         dx = (event.pageX - smp.left) || 0,
7319                         dy = (event.pageY - smp.top) || 0,
7320                         trigger = this._change[a];
7321
7322                 this._updatePrevProperties();
7323
7324                 if (!trigger) {
7325                         return false;
7326                 }
7327
7328                 data = trigger.apply(this, [ event, dx, dy ]);
7329
7330                 this._updateVirtualBoundaries(event.shiftKey);
7331                 if (this._aspectRatio || event.shiftKey) {
7332                         data = this._updateRatio(data, event);
7333                 }
7334
7335                 data = this._respectSize(data, event);
7336
7337                 this._updateCache(data);
7338
7339                 this._propagate("resize", event);
7340
7341                 props = this._applyChanges();
7342
7343                 if ( !this._helper && this._proportionallyResizeElements.length ) {
7344                         this._proportionallyResize();
7345                 }
7346
7347                 if ( !$.isEmptyObject( props ) ) {
7348                         this._updatePrevProperties();
7349                         this._trigger( "resize", event, this.ui() );
7350                         this._applyChanges();
7351                 }
7352
7353                 return false;
7354         },
7355
7356         _mouseStop: function(event) {
7357
7358                 this.resizing = false;
7359                 var pr, ista, soffseth, soffsetw, s, left, top,
7360                         o = this.options, that = this;
7361
7362                 if (this._helper) {
7363
7364                         pr = this._proportionallyResizeElements;
7365                         ista = pr.length && (/textarea/i).test(pr[0].nodeName);
7366                         soffseth = ista && this._hasScroll(pr[0], "left") ? 0 : that.sizeDiff.height;
7367                         soffsetw = ista ? 0 : that.sizeDiff.width;
7368
7369                         s = {
7370                                 width: (that.helper.width()  - soffsetw),
7371                                 height: (that.helper.height() - soffseth)
7372                         };
7373                         left = (parseInt(that.element.css("left"), 10) +
7374                                 (that.position.left - that.originalPosition.left)) || null;
7375                         top = (parseInt(that.element.css("top"), 10) +
7376                                 (that.position.top - that.originalPosition.top)) || null;
7377
7378                         if (!o.animate) {
7379                                 this.element.css($.extend(s, { top: top, left: left }));
7380                         }
7381
7382                         that.helper.height(that.size.height);
7383                         that.helper.width(that.size.width);
7384
7385                         if (this._helper && !o.animate) {
7386                                 this._proportionallyResize();
7387                         }
7388                 }
7389
7390                 $("body").css("cursor", "auto");
7391
7392                 this.element.removeClass("ui-resizable-resizing");
7393
7394                 this._propagate("stop", event);
7395
7396                 if (this._helper) {
7397                         this.helper.remove();
7398                 }
7399
7400                 return false;
7401
7402         },
7403
7404         _updatePrevProperties: function() {
7405                 this.prevPosition = {
7406                         top: this.position.top,
7407                         left: this.position.left
7408                 };
7409                 this.prevSize = {
7410                         width: this.size.width,
7411                         height: this.size.height
7412                 };
7413         },
7414
7415         _applyChanges: function() {
7416                 var props = {};
7417
7418                 if ( this.position.top !== this.prevPosition.top ) {
7419                         props.top = this.position.top + "px";
7420                 }
7421                 if ( this.position.left !== this.prevPosition.left ) {
7422                         props.left = this.position.left + "px";
7423                 }
7424                 if ( this.size.width !== this.prevSize.width ) {
7425                         props.width = this.size.width + "px";
7426                 }
7427                 if ( this.size.height !== this.prevSize.height ) {
7428                         props.height = this.size.height + "px";
7429                 }
7430
7431                 this.helper.css( props );
7432
7433                 return props;
7434         },
7435
7436         _updateVirtualBoundaries: function(forceAspectRatio) {
7437                 var pMinWidth, pMaxWidth, pMinHeight, pMaxHeight, b,
7438                         o = this.options;
7439
7440                 b = {
7441                         minWidth: this._isNumber(o.minWidth) ? o.minWidth : 0,
7442                         maxWidth: this._isNumber(o.maxWidth) ? o.maxWidth : Infinity,
7443                         minHeight: this._isNumber(o.minHeight) ? o.minHeight : 0,
7444                         maxHeight: this._isNumber(o.maxHeight) ? o.maxHeight : Infinity
7445                 };
7446
7447                 if (this._aspectRatio || forceAspectRatio) {
7448                         pMinWidth = b.minHeight * this.aspectRatio;
7449                         pMinHeight = b.minWidth / this.aspectRatio;
7450                         pMaxWidth = b.maxHeight * this.aspectRatio;
7451                         pMaxHeight = b.maxWidth / this.aspectRatio;
7452
7453                         if (pMinWidth > b.minWidth) {
7454                                 b.minWidth = pMinWidth;
7455                         }
7456                         if (pMinHeight > b.minHeight) {
7457                                 b.minHeight = pMinHeight;
7458                         }
7459                         if (pMaxWidth < b.maxWidth) {
7460                                 b.maxWidth = pMaxWidth;
7461                         }
7462                         if (pMaxHeight < b.maxHeight) {
7463                                 b.maxHeight = pMaxHeight;
7464                         }
7465                 }
7466                 this._vBoundaries = b;
7467         },
7468
7469         _updateCache: function(data) {
7470                 this.offset = this.helper.offset();
7471                 if (this._isNumber(data.left)) {
7472                         this.position.left = data.left;
7473                 }
7474                 if (this._isNumber(data.top)) {
7475                         this.position.top = data.top;
7476                 }
7477                 if (this._isNumber(data.height)) {
7478                         this.size.height = data.height;
7479                 }
7480                 if (this._isNumber(data.width)) {
7481                         this.size.width = data.width;
7482                 }
7483         },
7484
7485         _updateRatio: function( data ) {
7486
7487                 var cpos = this.position,
7488                         csize = this.size,
7489                         a = this.axis;
7490
7491                 if (this._isNumber(data.height)) {
7492                         data.width = (data.height * this.aspectRatio);
7493                 } else if (this._isNumber(data.width)) {
7494                         data.height = (data.width / this.aspectRatio);
7495                 }
7496
7497                 if (a === "sw") {
7498                         data.left = cpos.left + (csize.width - data.width);
7499                         data.top = null;
7500                 }
7501                 if (a === "nw") {
7502                         data.top = cpos.top + (csize.height - data.height);
7503                         data.left = cpos.left + (csize.width - data.width);
7504                 }
7505
7506                 return data;
7507         },
7508
7509         _respectSize: function( data ) {
7510
7511                 var o = this._vBoundaries,
7512                         a = this.axis,
7513                         ismaxw = this._isNumber(data.width) && o.maxWidth && (o.maxWidth < data.width),
7514                         ismaxh = this._isNumber(data.height) && o.maxHeight && (o.maxHeight < data.height),
7515                         isminw = this._isNumber(data.width) && o.minWidth && (o.minWidth > data.width),
7516                         isminh = this._isNumber(data.height) && o.minHeight && (o.minHeight > data.height),
7517                         dw = this.originalPosition.left + this.originalSize.width,
7518                         dh = this.position.top + this.size.height,
7519                         cw = /sw|nw|w/.test(a), ch = /nw|ne|n/.test(a);
7520                 if (isminw) {
7521                         data.width = o.minWidth;
7522                 }
7523                 if (isminh) {
7524                         data.height = o.minHeight;
7525                 }
7526                 if (ismaxw) {
7527                         data.width = o.maxWidth;
7528                 }
7529                 if (ismaxh) {
7530                         data.height = o.maxHeight;
7531                 }
7532
7533                 if (isminw && cw) {
7534                         data.left = dw - o.minWidth;
7535                 }
7536                 if (ismaxw && cw) {
7537                         data.left = dw - o.maxWidth;
7538                 }
7539                 if (isminh && ch) {
7540                         data.top = dh - o.minHeight;
7541                 }
7542                 if (ismaxh && ch) {
7543                         data.top = dh - o.maxHeight;
7544                 }
7545
7546                 // Fixing jump error on top/left - bug #2330
7547                 if (!data.width && !data.height && !data.left && data.top) {
7548                         data.top = null;
7549                 } else if (!data.width && !data.height && !data.top && data.left) {
7550                         data.left = null;
7551                 }
7552
7553                 return data;
7554         },
7555
7556         _getPaddingPlusBorderDimensions: function( element ) {
7557                 var i = 0,
7558                         widths = [],
7559                         borders = [
7560                                 element.css( "borderTopWidth" ),
7561                                 element.css( "borderRightWidth" ),
7562                                 element.css( "borderBottomWidth" ),
7563                                 element.css( "borderLeftWidth" )
7564                         ],
7565                         paddings = [
7566                                 element.css( "paddingTop" ),
7567                                 element.css( "paddingRight" ),
7568                                 element.css( "paddingBottom" ),
7569                                 element.css( "paddingLeft" )
7570                         ];
7571
7572                 for ( ; i < 4; i++ ) {
7573                         widths[ i ] = ( parseInt( borders[ i ], 10 ) || 0 );
7574                         widths[ i ] += ( parseInt( paddings[ i ], 10 ) || 0 );
7575                 }
7576
7577                 return {
7578                         height: widths[ 0 ] + widths[ 2 ],
7579                         width: widths[ 1 ] + widths[ 3 ]
7580                 };
7581         },
7582
7583         _proportionallyResize: function() {
7584
7585                 if (!this._proportionallyResizeElements.length) {
7586                         return;
7587                 }
7588
7589                 var prel,
7590                         i = 0,
7591                         element = this.helper || this.element;
7592
7593                 for ( ; i < this._proportionallyResizeElements.length; i++) {
7594
7595                         prel = this._proportionallyResizeElements[i];
7596
7597                         // TODO: Seems like a bug to cache this.outerDimensions
7598                         // considering that we are in a loop.
7599                         if (!this.outerDimensions) {
7600                                 this.outerDimensions = this._getPaddingPlusBorderDimensions( prel );
7601                         }
7602
7603                         prel.css({
7604                                 height: (element.height() - this.outerDimensions.height) || 0,
7605                                 width: (element.width() - this.outerDimensions.width) || 0
7606                         });
7607
7608                 }
7609
7610         },
7611
7612         _renderProxy: function() {
7613
7614                 var el = this.element, o = this.options;
7615                 this.elementOffset = el.offset();
7616
7617                 if (this._helper) {
7618
7619                         this.helper = this.helper || $("<div style='overflow:hidden;'></div>");
7620
7621                         this.helper.addClass(this._helper).css({
7622                                 width: this.element.outerWidth() - 1,
7623                                 height: this.element.outerHeight() - 1,
7624                                 position: "absolute",
7625                                 left: this.elementOffset.left + "px",
7626                                 top: this.elementOffset.top + "px",
7627                                 zIndex: ++o.zIndex //TODO: Don't modify option
7628                         });
7629
7630                         this.helper
7631                                 .appendTo("body")
7632                                 .disableSelection();
7633
7634                 } else {
7635                         this.helper = this.element;
7636                 }
7637
7638         },
7639
7640         _change: {
7641                 e: function(event, dx) {
7642                         return { width: this.originalSize.width + dx };
7643                 },
7644                 w: function(event, dx) {
7645                         var cs = this.originalSize, sp = this.originalPosition;
7646                         return { left: sp.left + dx, width: cs.width - dx };
7647                 },
7648                 n: function(event, dx, dy) {
7649                         var cs = this.originalSize, sp = this.originalPosition;
7650                         return { top: sp.top + dy, height: cs.height - dy };
7651                 },
7652                 s: function(event, dx, dy) {
7653                         return { height: this.originalSize.height + dy };
7654                 },
7655                 se: function(event, dx, dy) {
7656                         return $.extend(this._change.s.apply(this, arguments),
7657                                 this._change.e.apply(this, [ event, dx, dy ]));
7658                 },
7659                 sw: function(event, dx, dy) {
7660                         return $.extend(this._change.s.apply(this, arguments),
7661                                 this._change.w.apply(this, [ event, dx, dy ]));
7662                 },
7663                 ne: function(event, dx, dy) {
7664                         return $.extend(this._change.n.apply(this, arguments),
7665                                 this._change.e.apply(this, [ event, dx, dy ]));
7666                 },
7667                 nw: function(event, dx, dy) {
7668                         return $.extend(this._change.n.apply(this, arguments),
7669                                 this._change.w.apply(this, [ event, dx, dy ]));
7670                 }
7671         },
7672
7673         _propagate: function(n, event) {
7674                 $.ui.plugin.call(this, n, [ event, this.ui() ]);
7675                 (n !== "resize" && this._trigger(n, event, this.ui()));
7676         },
7677
7678         plugins: {},
7679
7680         ui: function() {
7681                 return {
7682                         originalElement: this.originalElement,
7683                         element: this.element,
7684                         helper: this.helper,
7685                         position: this.position,
7686                         size: this.size,
7687                         originalSize: this.originalSize,
7688                         originalPosition: this.originalPosition
7689                 };
7690         }
7691
7692 });
7693
7694 /*
7695  * Resizable Extensions
7696  */
7697
7698 $.ui.plugin.add("resizable", "animate", {
7699
7700         stop: function( event ) {
7701                 var that = $(this).resizable( "instance" ),
7702                         o = that.options,
7703                         pr = that._proportionallyResizeElements,
7704                         ista = pr.length && (/textarea/i).test(pr[0].nodeName),
7705                         soffseth = ista && that._hasScroll(pr[0], "left") ? 0 : that.sizeDiff.height,
7706                         soffsetw = ista ? 0 : that.sizeDiff.width,
7707                         style = { width: (that.size.width - soffsetw), height: (that.size.height - soffseth) },
7708                         left = (parseInt(that.element.css("left"), 10) +
7709                                 (that.position.left - that.originalPosition.left)) || null,
7710                         top = (parseInt(that.element.css("top"), 10) +
7711                                 (that.position.top - that.originalPosition.top)) || null;
7712
7713                 that.element.animate(
7714                         $.extend(style, top && left ? { top: top, left: left } : {}), {
7715                                 duration: o.animateDuration,
7716                                 easing: o.animateEasing,
7717                                 step: function() {
7718
7719                                         var data = {
7720                                                 width: parseInt(that.element.css("width"), 10),
7721                                                 height: parseInt(that.element.css("height"), 10),
7722                                                 top: parseInt(that.element.css("top"), 10),
7723                                                 left: parseInt(that.element.css("left"), 10)
7724                                         };
7725
7726                                         if (pr && pr.length) {
7727                                                 $(pr[0]).css({ width: data.width, height: data.height });
7728                                         }
7729
7730                                         // propagating resize, and updating values for each animation step
7731                                         that._updateCache(data);
7732                                         that._propagate("resize", event);
7733
7734                                 }
7735                         }
7736                 );
7737         }
7738
7739 });
7740
7741 $.ui.plugin.add( "resizable", "containment", {
7742
7743         start: function() {
7744                 var element, p, co, ch, cw, width, height,
7745                         that = $( this ).resizable( "instance" ),
7746                         o = that.options,
7747                         el = that.element,
7748                         oc = o.containment,
7749                         ce = ( oc instanceof $ ) ? oc.get( 0 ) : ( /parent/.test( oc ) ) ? el.parent().get( 0 ) : oc;
7750
7751                 if ( !ce ) {
7752                         return;
7753                 }
7754
7755                 that.containerElement = $( ce );
7756
7757                 if ( /document/.test( oc ) || oc === document ) {
7758                         that.containerOffset = {
7759                                 left: 0,
7760                                 top: 0
7761                         };
7762                         that.containerPosition = {
7763                                 left: 0,
7764                                 top: 0
7765                         };
7766
7767                         that.parentData = {
7768                                 element: $( document ),
7769                                 left: 0,
7770                                 top: 0,
7771                                 width: $( document ).width(),
7772                                 height: $( document ).height() || document.body.parentNode.scrollHeight
7773                         };
7774                 } else {
7775                         element = $( ce );
7776                         p = [];
7777                         $([ "Top", "Right", "Left", "Bottom" ]).each(function( i, name ) {
7778                                 p[ i ] = that._num( element.css( "padding" + name ) );
7779                         });
7780
7781                         that.containerOffset = element.offset();
7782                         that.containerPosition = element.position();
7783                         that.containerSize = {
7784                                 height: ( element.innerHeight() - p[ 3 ] ),
7785                                 width: ( element.innerWidth() - p[ 1 ] )
7786                         };
7787
7788                         co = that.containerOffset;
7789                         ch = that.containerSize.height;
7790                         cw = that.containerSize.width;
7791                         width = ( that._hasScroll ( ce, "left" ) ? ce.scrollWidth : cw );
7792                         height = ( that._hasScroll ( ce ) ? ce.scrollHeight : ch ) ;
7793
7794                         that.parentData = {
7795                                 element: ce,
7796                                 left: co.left,
7797                                 top: co.top,
7798                                 width: width,
7799                                 height: height
7800                         };
7801                 }
7802         },
7803
7804         resize: function( event ) {
7805                 var woset, hoset, isParent, isOffsetRelative,
7806                         that = $( this ).resizable( "instance" ),
7807                         o = that.options,
7808                         co = that.containerOffset,
7809                         cp = that.position,
7810                         pRatio = that._aspectRatio || event.shiftKey,
7811                         cop = {
7812                                 top: 0,
7813                                 left: 0
7814                         },
7815                         ce = that.containerElement,
7816                         continueResize = true;
7817
7818                 if ( ce[ 0 ] !== document && ( /static/ ).test( ce.css( "position" ) ) ) {
7819                         cop = co;
7820                 }
7821
7822                 if ( cp.left < ( that._helper ? co.left : 0 ) ) {
7823                         that.size.width = that.size.width +
7824                                 ( that._helper ?
7825                                         ( that.position.left - co.left ) :
7826                                         ( that.position.left - cop.left ) );
7827
7828                         if ( pRatio ) {
7829                                 that.size.height = that.size.width / that.aspectRatio;
7830                                 continueResize = false;
7831                         }
7832                         that.position.left = o.helper ? co.left : 0;
7833                 }
7834
7835                 if ( cp.top < ( that._helper ? co.top : 0 ) ) {
7836                         that.size.height = that.size.height +
7837                                 ( that._helper ?
7838                                         ( that.position.top - co.top ) :
7839                                         that.position.top );
7840
7841                         if ( pRatio ) {
7842                                 that.size.width = that.size.height * that.aspectRatio;
7843                                 continueResize = false;
7844                         }
7845                         that.position.top = that._helper ? co.top : 0;
7846                 }
7847
7848                 isParent = that.containerElement.get( 0 ) === that.element.parent().get( 0 );
7849                 isOffsetRelative = /relative|absolute/.test( that.containerElement.css( "position" ) );
7850
7851                 if ( isParent && isOffsetRelative ) {
7852                         that.offset.left = that.parentData.left + that.position.left;
7853                         that.offset.top = that.parentData.top + that.position.top;
7854                 } else {
7855                         that.offset.left = that.element.offset().left;
7856                         that.offset.top = that.element.offset().top;
7857                 }
7858
7859                 woset = Math.abs( that.sizeDiff.width +
7860                         (that._helper ?
7861                                 that.offset.left - cop.left :
7862                                 (that.offset.left - co.left)) );
7863
7864                 hoset = Math.abs( that.sizeDiff.height +
7865                         (that._helper ?
7866                                 that.offset.top - cop.top :
7867                                 (that.offset.top - co.top)) );
7868
7869                 if ( woset + that.size.width >= that.parentData.width ) {
7870                         that.size.width = that.parentData.width - woset;
7871                         if ( pRatio ) {
7872                                 that.size.height = that.size.width / that.aspectRatio;
7873                                 continueResize = false;
7874                         }
7875                 }
7876
7877                 if ( hoset + that.size.height >= that.parentData.height ) {
7878                         that.size.height = that.parentData.height - hoset;
7879                         if ( pRatio ) {
7880                                 that.size.width = that.size.height * that.aspectRatio;
7881                                 continueResize = false;
7882                         }
7883                 }
7884
7885                 if ( !continueResize ) {
7886                         that.position.left = that.prevPosition.left;
7887                         that.position.top = that.prevPosition.top;
7888                         that.size.width = that.prevSize.width;
7889                         that.size.height = that.prevSize.height;
7890                 }
7891         },
7892
7893         stop: function() {
7894                 var that = $( this ).resizable( "instance" ),
7895                         o = that.options,
7896                         co = that.containerOffset,
7897                         cop = that.containerPosition,
7898                         ce = that.containerElement,
7899                         helper = $( that.helper ),
7900                         ho = helper.offset(),
7901                         w = helper.outerWidth() - that.sizeDiff.width,
7902                         h = helper.outerHeight() - that.sizeDiff.height;
7903
7904                 if ( that._helper && !o.animate && ( /relative/ ).test( ce.css( "position" ) ) ) {
7905                         $( this ).css({
7906                                 left: ho.left - cop.left - co.left,
7907                                 width: w,
7908                                 height: h
7909                         });
7910                 }
7911
7912                 if ( that._helper && !o.animate && ( /static/ ).test( ce.css( "position" ) ) ) {
7913                         $( this ).css({
7914                                 left: ho.left - cop.left - co.left,
7915                                 width: w,
7916                                 height: h
7917                         });
7918                 }
7919         }
7920 });
7921
7922 $.ui.plugin.add("resizable", "alsoResize", {
7923
7924         start: function() {
7925                 var that = $(this).resizable( "instance" ),
7926                         o = that.options;
7927
7928                 $(o.alsoResize).each(function() {
7929                         var el = $(this);
7930                         el.data("ui-resizable-alsoresize", {
7931                                 width: parseInt(el.width(), 10), height: parseInt(el.height(), 10),
7932                                 left: parseInt(el.css("left"), 10), top: parseInt(el.css("top"), 10)
7933                         });
7934                 });
7935         },
7936
7937         resize: function(event, ui) {
7938                 var that = $(this).resizable( "instance" ),
7939                         o = that.options,
7940                         os = that.originalSize,
7941                         op = that.originalPosition,
7942                         delta = {
7943                                 height: (that.size.height - os.height) || 0,
7944                                 width: (that.size.width - os.width) || 0,
7945                                 top: (that.position.top - op.top) || 0,
7946                                 left: (that.position.left - op.left) || 0
7947                         };
7948
7949                         $(o.alsoResize).each(function() {
7950                                 var el = $(this), start = $(this).data("ui-resizable-alsoresize"), style = {},
7951                                         css = el.parents(ui.originalElement[0]).length ?
7952                                                         [ "width", "height" ] :
7953                                                         [ "width", "height", "top", "left" ];
7954
7955                                 $.each(css, function(i, prop) {
7956                                         var sum = (start[prop] || 0) + (delta[prop] || 0);
7957                                         if (sum && sum >= 0) {
7958                                                 style[prop] = sum || null;
7959                                         }
7960                                 });
7961
7962                                 el.css(style);
7963                         });
7964         },
7965
7966         stop: function() {
7967                 $(this).removeData("resizable-alsoresize");
7968         }
7969 });
7970
7971 $.ui.plugin.add("resizable", "ghost", {
7972
7973         start: function() {
7974
7975                 var that = $(this).resizable( "instance" ), o = that.options, cs = that.size;
7976
7977                 that.ghost = that.originalElement.clone();
7978                 that.ghost
7979                         .css({
7980                                 opacity: 0.25,
7981                                 display: "block",
7982                                 position: "relative",
7983                                 height: cs.height,
7984                                 width: cs.width,
7985                                 margin: 0,
7986                                 left: 0,
7987                                 top: 0
7988                         })
7989                         .addClass("ui-resizable-ghost")
7990                         .addClass(typeof o.ghost === "string" ? o.ghost : "");
7991
7992                 that.ghost.appendTo(that.helper);
7993
7994         },
7995
7996         resize: function() {
7997                 var that = $(this).resizable( "instance" );
7998                 if (that.ghost) {
7999                         that.ghost.css({
8000                                 position: "relative",
8001                                 height: that.size.height,
8002                                 width: that.size.width
8003                         });
8004                 }
8005         },
8006
8007         stop: function() {
8008                 var that = $(this).resizable( "instance" );
8009                 if (that.ghost && that.helper) {
8010                         that.helper.get(0).removeChild(that.ghost.get(0));
8011                 }
8012         }
8013
8014 });
8015
8016 $.ui.plugin.add("resizable", "grid", {
8017
8018         resize: function() {
8019                 var outerDimensions,
8020                         that = $(this).resizable( "instance" ),
8021                         o = that.options,
8022                         cs = that.size,
8023                         os = that.originalSize,
8024                         op = that.originalPosition,
8025                         a = that.axis,
8026                         grid = typeof o.grid === "number" ? [ o.grid, o.grid ] : o.grid,
8027                         gridX = (grid[0] || 1),
8028                         gridY = (grid[1] || 1),
8029                         ox = Math.round((cs.width - os.width) / gridX) * gridX,
8030                         oy = Math.round((cs.height - os.height) / gridY) * gridY,
8031                         newWidth = os.width + ox,
8032                         newHeight = os.height + oy,
8033                         isMaxWidth = o.maxWidth && (o.maxWidth < newWidth),
8034                         isMaxHeight = o.maxHeight && (o.maxHeight < newHeight),
8035                         isMinWidth = o.minWidth && (o.minWidth > newWidth),
8036                         isMinHeight = o.minHeight && (o.minHeight > newHeight);
8037
8038                 o.grid = grid;
8039
8040                 if (isMinWidth) {
8041                         newWidth += gridX;
8042                 }
8043                 if (isMinHeight) {
8044                         newHeight += gridY;
8045                 }
8046                 if (isMaxWidth) {
8047                         newWidth -= gridX;
8048                 }
8049                 if (isMaxHeight) {
8050                         newHeight -= gridY;
8051                 }
8052
8053                 if (/^(se|s|e)$/.test(a)) {
8054                         that.size.width = newWidth;
8055                         that.size.height = newHeight;
8056                 } else if (/^(ne)$/.test(a)) {
8057                         that.size.width = newWidth;
8058                         that.size.height = newHeight;
8059                         that.position.top = op.top - oy;
8060                 } else if (/^(sw)$/.test(a)) {
8061                         that.size.width = newWidth;
8062                         that.size.height = newHeight;
8063                         that.position.left = op.left - ox;
8064                 } else {
8065                         if ( newHeight - gridY <= 0 || newWidth - gridX <= 0) {
8066                                 outerDimensions = that._getPaddingPlusBorderDimensions( this );
8067                         }
8068
8069                         if ( newHeight - gridY > 0 ) {
8070                                 that.size.height = newHeight;
8071                                 that.position.top = op.top - oy;
8072                         } else {
8073                                 newHeight = gridY - outerDimensions.height;
8074                                 that.size.height = newHeight;
8075                                 that.position.top = op.top + os.height - newHeight;
8076                         }
8077                         if ( newWidth - gridX > 0 ) {
8078                                 that.size.width = newWidth;
8079                                 that.position.left = op.left - ox;
8080                         } else {
8081                                 newWidth = gridX - outerDimensions.width;
8082                                 that.size.width = newWidth;
8083                                 that.position.left = op.left + os.width - newWidth;
8084                         }
8085                 }
8086         }
8087
8088 });
8089
8090 var resizable = $.ui.resizable;
8091
8092
8093 /*!
8094  * jQuery UI Dialog 1.11.4
8095  * http://jqueryui.com
8096  *
8097  * Copyright jQuery Foundation and other contributors
8098  * Released under the MIT license.
8099  * http://jquery.org/license
8100  *
8101  * http://api.jqueryui.com/dialog/
8102  */
8103
8104
8105 var dialog = $.widget( "ui.dialog", {
8106         version: "1.11.4",
8107         options: {
8108                 appendTo: "body",
8109                 autoOpen: true,
8110                 buttons: [],
8111                 closeOnEscape: true,
8112                 closeText: "Close",
8113                 dialogClass: "",
8114                 draggable: true,
8115                 hide: null,
8116                 height: "auto",
8117                 maxHeight: null,
8118                 maxWidth: null,
8119                 minHeight: 150,
8120                 minWidth: 150,
8121                 modal: false,
8122                 position: {
8123                         my: "center",
8124                         at: "center",
8125                         of: window,
8126                         collision: "fit",
8127                         // Ensure the titlebar is always visible
8128                         using: function( pos ) {
8129                                 var topOffset = $( this ).css( pos ).offset().top;
8130                                 if ( topOffset < 0 ) {
8131                                         $( this ).css( "top", pos.top - topOffset );
8132                                 }
8133                         }
8134                 },
8135                 resizable: true,
8136                 show: null,
8137                 title: null,
8138                 width: 300,
8139
8140                 // callbacks
8141                 beforeClose: null,
8142                 close: null,
8143                 drag: null,
8144                 dragStart: null,
8145                 dragStop: null,
8146                 focus: null,
8147                 open: null,
8148                 resize: null,
8149                 resizeStart: null,
8150                 resizeStop: null
8151         },
8152
8153         sizeRelatedOptions: {
8154                 buttons: true,
8155                 height: true,
8156                 maxHeight: true,
8157                 maxWidth: true,
8158                 minHeight: true,
8159                 minWidth: true,
8160                 width: true
8161         },
8162
8163         resizableRelatedOptions: {
8164                 maxHeight: true,
8165                 maxWidth: true,
8166                 minHeight: true,
8167                 minWidth: true
8168         },
8169
8170         _create: function() {
8171                 this.originalCss = {
8172                         display: this.element[ 0 ].style.display,
8173                         width: this.element[ 0 ].style.width,
8174                         minHeight: this.element[ 0 ].style.minHeight,
8175                         maxHeight: this.element[ 0 ].style.maxHeight,
8176                         height: this.element[ 0 ].style.height
8177                 };
8178                 this.originalPosition = {
8179                         parent: this.element.parent(),
8180                         index: this.element.parent().children().index( this.element )
8181                 };
8182                 this.originalTitle = this.element.attr( "title" );
8183                 this.options.title = this.options.title || this.originalTitle;
8184
8185                 this._createWrapper();
8186
8187                 this.element
8188                         .show()
8189                         .removeAttr( "title" )
8190                         .addClass( "ui-dialog-content ui-widget-content" )
8191                         .appendTo( this.uiDialog );
8192
8193                 this._createTitlebar();
8194                 this._createButtonPane();
8195
8196                 if ( this.options.draggable && $.fn.draggable ) {
8197                         this._makeDraggable();
8198                 }
8199                 if ( this.options.resizable && $.fn.resizable ) {
8200                         this._makeResizable();
8201                 }
8202
8203                 this._isOpen = false;
8204
8205                 this._trackFocus();
8206         },
8207
8208         _init: function() {
8209                 if ( this.options.autoOpen ) {
8210                         this.open();
8211                 }
8212         },
8213
8214         _appendTo: function() {
8215                 var element = this.options.appendTo;
8216                 if ( element && (element.jquery || element.nodeType) ) {
8217                         return $( element );
8218                 }
8219                 return this.document.find( element || "body" ).eq( 0 );
8220         },
8221
8222         _destroy: function() {
8223                 var next,
8224                         originalPosition = this.originalPosition;
8225
8226                 this._untrackInstance();
8227                 this._destroyOverlay();
8228
8229                 this.element
8230                         .removeUniqueId()
8231                         .removeClass( "ui-dialog-content ui-widget-content" )
8232                         .css( this.originalCss )
8233                         // Without detaching first, the following becomes really slow
8234                         .detach();
8235
8236                 this.uiDialog.stop( true, true ).remove();
8237
8238                 if ( this.originalTitle ) {
8239                         this.element.attr( "title", this.originalTitle );
8240                 }
8241
8242                 next = originalPosition.parent.children().eq( originalPosition.index );
8243                 // Don't try to place the dialog next to itself (#8613)
8244                 if ( next.length && next[ 0 ] !== this.element[ 0 ] ) {
8245                         next.before( this.element );
8246                 } else {
8247                         originalPosition.parent.append( this.element );
8248                 }
8249         },
8250
8251         widget: function() {
8252                 return this.uiDialog;
8253         },
8254
8255         disable: $.noop,
8256         enable: $.noop,
8257
8258         close: function( event ) {
8259                 var activeElement,
8260                         that = this;
8261
8262                 if ( !this._isOpen || this._trigger( "beforeClose", event ) === false ) {
8263                         return;
8264                 }
8265
8266                 this._isOpen = false;
8267                 this._focusedElement = null;
8268                 this._destroyOverlay();
8269                 this._untrackInstance();
8270
8271                 if ( !this.opener.filter( ":focusable" ).focus().length ) {
8272
8273                         // support: IE9
8274                         // IE9 throws an "Unspecified error" accessing document.activeElement from an <iframe>
8275                         try {
8276                                 activeElement = this.document[ 0 ].activeElement;
8277
8278                                 // Support: IE9, IE10
8279                                 // If the <body> is blurred, IE will switch windows, see #4520
8280                                 if ( activeElement && activeElement.nodeName.toLowerCase() !== "body" ) {
8281
8282                                         // Hiding a focused element doesn't trigger blur in WebKit
8283                                         // so in case we have nothing to focus on, explicitly blur the active element
8284                                         // https://bugs.webkit.org/show_bug.cgi?id=47182
8285                                         $( activeElement ).blur();
8286                                 }
8287                         } catch ( error ) {}
8288                 }
8289
8290                 this._hide( this.uiDialog, this.options.hide, function() {
8291                         that._trigger( "close", event );
8292                 });
8293         },
8294
8295         isOpen: function() {
8296                 return this._isOpen;
8297         },
8298
8299         moveToTop: function() {
8300                 this._moveToTop();
8301         },
8302
8303         _moveToTop: function( event, silent ) {
8304                 var moved = false,
8305                         zIndices = this.uiDialog.siblings( ".ui-front:visible" ).map(function() {
8306                                 return +$( this ).css( "z-index" );
8307                         }).get(),
8308                         zIndexMax = Math.max.apply( null, zIndices );
8309
8310                 if ( zIndexMax >= +this.uiDialog.css( "z-index" ) ) {
8311                         this.uiDialog.css( "z-index", zIndexMax + 1 );
8312                         moved = true;
8313                 }
8314
8315                 if ( moved && !silent ) {
8316                         this._trigger( "focus", event );
8317                 }
8318                 return moved;
8319         },
8320
8321         open: function() {
8322                 var that = this;
8323                 if ( this._isOpen ) {
8324                         if ( this._moveToTop() ) {
8325                                 this._focusTabbable();
8326                         }
8327                         return;
8328                 }
8329
8330                 this._isOpen = true;
8331                 this.opener = $( this.document[ 0 ].activeElement );
8332
8333                 this._size();
8334                 this._position();
8335                 this._createOverlay();
8336                 this._moveToTop( null, true );
8337
8338                 // Ensure the overlay is moved to the top with the dialog, but only when
8339                 // opening. The overlay shouldn't move after the dialog is open so that
8340                 // modeless dialogs opened after the modal dialog stack properly.
8341                 if ( this.overlay ) {
8342                         this.overlay.css( "z-index", this.uiDialog.css( "z-index" ) - 1 );
8343                 }
8344
8345                 this._show( this.uiDialog, this.options.show, function() {
8346                         that._focusTabbable();
8347                         that._trigger( "focus" );
8348                 });
8349
8350                 // Track the dialog immediately upon openening in case a focus event
8351                 // somehow occurs outside of the dialog before an element inside the
8352                 // dialog is focused (#10152)
8353                 this._makeFocusTarget();
8354
8355                 this._trigger( "open" );
8356         },
8357
8358         _focusTabbable: function() {
8359                 // Set focus to the first match:
8360                 // 1. An element that was focused previously
8361                 // 2. First element inside the dialog matching [autofocus]
8362                 // 3. Tabbable element inside the content element
8363                 // 4. Tabbable element inside the buttonpane
8364                 // 5. The close button
8365                 // 6. The dialog itself
8366                 var hasFocus = this._focusedElement;
8367                 if ( !hasFocus ) {
8368                         hasFocus = this.element.find( "[autofocus]" );
8369                 }
8370                 if ( !hasFocus.length ) {
8371                         hasFocus = this.element.find( ":tabbable" );
8372                 }
8373                 if ( !hasFocus.length ) {
8374                         hasFocus = this.uiDialogButtonPane.find( ":tabbable" );
8375                 }
8376                 if ( !hasFocus.length ) {
8377                         hasFocus = this.uiDialogTitlebarClose.filter( ":tabbable" );
8378                 }
8379                 if ( !hasFocus.length ) {
8380                         hasFocus = this.uiDialog;
8381                 }
8382                 hasFocus.eq( 0 ).focus();
8383         },
8384
8385         _keepFocus: function( event ) {
8386                 function checkFocus() {
8387                         var activeElement = this.document[0].activeElement,
8388                                 isActive = this.uiDialog[0] === activeElement ||
8389                                         $.contains( this.uiDialog[0], activeElement );
8390                         if ( !isActive ) {
8391                                 this._focusTabbable();
8392                         }
8393                 }
8394                 event.preventDefault();
8395                 checkFocus.call( this );
8396                 // support: IE
8397                 // IE <= 8 doesn't prevent moving focus even with event.preventDefault()
8398                 // so we check again later
8399                 this._delay( checkFocus );
8400         },
8401
8402         _createWrapper: function() {
8403                 this.uiDialog = $("<div>")
8404                         .addClass( "ui-dialog ui-widget ui-widget-content ui-corner-all ui-front " +
8405                                 this.options.dialogClass )
8406                         .hide()
8407                         .attr({
8408                                 // Setting tabIndex makes the div focusable
8409                                 tabIndex: -1,
8410                                 role: "dialog"
8411                         })
8412                         .appendTo( this._appendTo() );
8413
8414                 this._on( this.uiDialog, {
8415                         keydown: function( event ) {
8416                                 if ( this.options.closeOnEscape && !event.isDefaultPrevented() && event.keyCode &&
8417                                                 event.keyCode === $.ui.keyCode.ESCAPE ) {
8418                                         event.preventDefault();
8419                                         this.close( event );
8420                                         return;
8421                                 }
8422
8423                                 // prevent tabbing out of dialogs
8424                                 if ( event.keyCode !== $.ui.keyCode.TAB || event.isDefaultPrevented() ) {
8425                                         return;
8426                                 }
8427                                 var tabbables = this.uiDialog.find( ":tabbable" ),
8428                                         first = tabbables.filter( ":first" ),
8429                                         last = tabbables.filter( ":last" );
8430
8431                                 if ( ( event.target === last[0] || event.target === this.uiDialog[0] ) && !event.shiftKey ) {
8432                                         this._delay(function() {
8433                                                 first.focus();
8434                                         });
8435                                         event.preventDefault();
8436                                 } else if ( ( event.target === first[0] || event.target === this.uiDialog[0] ) && event.shiftKey ) {
8437                                         this._delay(function() {
8438                                                 last.focus();
8439                                         });
8440                                         event.preventDefault();
8441                                 }
8442                         },
8443                         mousedown: function( event ) {
8444                                 if ( this._moveToTop( event ) ) {
8445                                         this._focusTabbable();
8446                                 }
8447                         }
8448                 });
8449
8450                 // We assume that any existing aria-describedby attribute means
8451                 // that the dialog content is marked up properly
8452                 // otherwise we brute force the content as the description
8453                 if ( !this.element.find( "[aria-describedby]" ).length ) {
8454                         this.uiDialog.attr({
8455                                 "aria-describedby": this.element.uniqueId().attr( "id" )
8456                         });
8457                 }
8458         },
8459
8460         _createTitlebar: function() {
8461                 var uiDialogTitle;
8462
8463                 this.uiDialogTitlebar = $( "<div>" )
8464                         .addClass( "ui-dialog-titlebar ui-widget-header ui-corner-all ui-helper-clearfix" )
8465                         .prependTo( this.uiDialog );
8466                 this._on( this.uiDialogTitlebar, {
8467                         mousedown: function( event ) {
8468                                 // Don't prevent click on close button (#8838)
8469                                 // Focusing a dialog that is partially scrolled out of view
8470                                 // causes the browser to scroll it into view, preventing the click event
8471                                 if ( !$( event.target ).closest( ".ui-dialog-titlebar-close" ) ) {
8472                                         // Dialog isn't getting focus when dragging (#8063)
8473                                         this.uiDialog.focus();
8474                                 }
8475                         }
8476                 });
8477
8478                 // support: IE
8479                 // Use type="button" to prevent enter keypresses in textboxes from closing the
8480                 // dialog in IE (#9312)
8481                 this.uiDialogTitlebarClose = $( "<button type='button'></button>" )
8482                         .button({
8483                                 label: this.options.closeText,
8484                                 icons: {
8485                                         primary: "ui-icon-closethick"
8486                                 },
8487                                 text: false
8488                         })
8489                         .addClass( "ui-dialog-titlebar-close" )
8490                         .appendTo( this.uiDialogTitlebar );
8491                 this._on( this.uiDialogTitlebarClose, {
8492                         click: function( event ) {
8493                                 event.preventDefault();
8494                                 this.close( event );
8495                         }
8496                 });
8497
8498                 uiDialogTitle = $( "<span>" )
8499                         .uniqueId()
8500                         .addClass( "ui-dialog-title" )
8501                         .prependTo( this.uiDialogTitlebar );
8502                 this._title( uiDialogTitle );
8503
8504                 this.uiDialog.attr({
8505                         "aria-labelledby": uiDialogTitle.attr( "id" )
8506                 });
8507         },
8508
8509         _title: function( title ) {
8510                 if ( !this.options.title ) {
8511                         title.html( "&#160;" );
8512                 }
8513                 title.text( this.options.title );
8514         },
8515
8516         _createButtonPane: function() {
8517                 this.uiDialogButtonPane = $( "<div>" )
8518                         .addClass( "ui-dialog-buttonpane ui-widget-content ui-helper-clearfix" );
8519
8520                 this.uiButtonSet = $( "<div>" )
8521                         .addClass( "ui-dialog-buttonset" )
8522                         .appendTo( this.uiDialogButtonPane );
8523
8524                 this._createButtons();
8525         },
8526
8527         _createButtons: function() {
8528                 var that = this,
8529                         buttons = this.options.buttons;
8530
8531                 // if we already have a button pane, remove it
8532                 this.uiDialogButtonPane.remove();
8533                 this.uiButtonSet.empty();
8534
8535                 if ( $.isEmptyObject( buttons ) || ($.isArray( buttons ) && !buttons.length) ) {
8536                         this.uiDialog.removeClass( "ui-dialog-buttons" );
8537                         return;
8538                 }
8539
8540                 $.each( buttons, function( name, props ) {
8541                         var click, buttonOptions;
8542                         props = $.isFunction( props ) ?
8543                                 { click: props, text: name } :
8544                                 props;
8545                         // Default to a non-submitting button
8546                         props = $.extend( { type: "button" }, props );
8547                         // Change the context for the click callback to be the main element
8548                         click = props.click;
8549                         props.click = function() {
8550                                 click.apply( that.element[ 0 ], arguments );
8551                         };
8552                         buttonOptions = {
8553                                 icons: props.icons,
8554                                 text: props.showText
8555                         };
8556                         delete props.icons;
8557                         delete props.showText;
8558                         $( "<button></button>", props )
8559                                 .button( buttonOptions )
8560                                 .appendTo( that.uiButtonSet );
8561                 });
8562                 this.uiDialog.addClass( "ui-dialog-buttons" );
8563                 this.uiDialogButtonPane.appendTo( this.uiDialog );
8564         },
8565
8566         _makeDraggable: function() {
8567                 var that = this,
8568                         options = this.options;
8569
8570                 function filteredUi( ui ) {
8571                         return {
8572                                 position: ui.position,
8573                                 offset: ui.offset
8574                         };
8575                 }
8576
8577                 this.uiDialog.draggable({
8578                         cancel: ".ui-dialog-content, .ui-dialog-titlebar-close",
8579                         handle: ".ui-dialog-titlebar",
8580                         containment: "document",
8581                         start: function( event, ui ) {
8582                                 $( this ).addClass( "ui-dialog-dragging" );
8583                                 that._blockFrames();
8584                                 that._trigger( "dragStart", event, filteredUi( ui ) );
8585                         },
8586                         drag: function( event, ui ) {
8587                                 that._trigger( "drag", event, filteredUi( ui ) );
8588                         },
8589                         stop: function( event, ui ) {
8590                                 var left = ui.offset.left - that.document.scrollLeft(),
8591                                         top = ui.offset.top - that.document.scrollTop();
8592
8593                                 options.position = {
8594                                         my: "left top",
8595                                         at: "left" + (left >= 0 ? "+" : "") + left + " " +
8596                                                 "top" + (top >= 0 ? "+" : "") + top,
8597                                         of: that.window
8598                                 };
8599                                 $( this ).removeClass( "ui-dialog-dragging" );
8600                                 that._unblockFrames();
8601                                 that._trigger( "dragStop", event, filteredUi( ui ) );
8602                         }
8603                 });
8604         },
8605
8606         _makeResizable: function() {
8607                 var that = this,
8608                         options = this.options,
8609                         handles = options.resizable,
8610                         // .ui-resizable has position: relative defined in the stylesheet
8611                         // but dialogs have to use absolute or fixed positioning
8612                         position = this.uiDialog.css("position"),
8613                         resizeHandles = typeof handles === "string" ?
8614                                 handles :
8615                                 "n,e,s,w,se,sw,ne,nw";
8616
8617                 function filteredUi( ui ) {
8618                         return {
8619                                 originalPosition: ui.originalPosition,
8620                                 originalSize: ui.originalSize,
8621                                 position: ui.position,
8622                                 size: ui.size
8623                         };
8624                 }
8625
8626                 this.uiDialog.resizable({
8627                         cancel: ".ui-dialog-content",
8628                         containment: "document",
8629                         alsoResize: this.element,
8630                         maxWidth: options.maxWidth,
8631                         maxHeight: options.maxHeight,
8632                         minWidth: options.minWidth,
8633                         minHeight: this._minHeight(),
8634                         handles: resizeHandles,
8635                         start: function( event, ui ) {
8636                                 $( this ).addClass( "ui-dialog-resizing" );
8637                                 that._blockFrames();
8638                                 that._trigger( "resizeStart", event, filteredUi( ui ) );
8639                         },
8640                         resize: function( event, ui ) {
8641                                 that._trigger( "resize", event, filteredUi( ui ) );
8642                         },
8643                         stop: function( event, ui ) {
8644                                 var offset = that.uiDialog.offset(),
8645                                         left = offset.left - that.document.scrollLeft(),
8646                                         top = offset.top - that.document.scrollTop();
8647
8648                                 options.height = that.uiDialog.height();
8649                                 options.width = that.uiDialog.width();
8650                                 options.position = {
8651                                         my: "left top",
8652                                         at: "left" + (left >= 0 ? "+" : "") + left + " " +
8653                                                 "top" + (top >= 0 ? "+" : "") + top,
8654                                         of: that.window
8655                                 };
8656                                 $( this ).removeClass( "ui-dialog-resizing" );
8657                                 that._unblockFrames();
8658                                 that._trigger( "resizeStop", event, filteredUi( ui ) );
8659                         }
8660                 })
8661                 .css( "position", position );
8662         },
8663
8664         _trackFocus: function() {
8665                 this._on( this.widget(), {
8666                         focusin: function( event ) {
8667                                 this._makeFocusTarget();
8668                                 this._focusedElement = $( event.target );
8669                         }
8670                 });
8671         },
8672
8673         _makeFocusTarget: function() {
8674                 this._untrackInstance();
8675                 this._trackingInstances().unshift( this );
8676         },
8677
8678         _untrackInstance: function() {
8679                 var instances = this._trackingInstances(),
8680                         exists = $.inArray( this, instances );
8681                 if ( exists !== -1 ) {
8682                         instances.splice( exists, 1 );
8683                 }
8684         },
8685
8686         _trackingInstances: function() {
8687                 var instances = this.document.data( "ui-dialog-instances" );
8688                 if ( !instances ) {
8689                         instances = [];
8690                         this.document.data( "ui-dialog-instances", instances );
8691                 }
8692                 return instances;
8693         },
8694
8695         _minHeight: function() {
8696                 var options = this.options;
8697
8698                 return options.height === "auto" ?
8699                         options.minHeight :
8700                         Math.min( options.minHeight, options.height );
8701         },
8702
8703         _position: function() {
8704                 // Need to show the dialog to get the actual offset in the position plugin
8705                 var isVisible = this.uiDialog.is( ":visible" );
8706                 if ( !isVisible ) {
8707                         this.uiDialog.show();
8708                 }
8709                 this.uiDialog.position( this.options.position );
8710                 if ( !isVisible ) {
8711                         this.uiDialog.hide();
8712                 }
8713         },
8714
8715         _setOptions: function( options ) {
8716                 var that = this,
8717                         resize = false,
8718                         resizableOptions = {};
8719
8720                 $.each( options, function( key, value ) {
8721                         that._setOption( key, value );
8722
8723                         if ( key in that.sizeRelatedOptions ) {
8724                                 resize = true;
8725                         }
8726                         if ( key in that.resizableRelatedOptions ) {
8727                                 resizableOptions[ key ] = value;
8728                         }
8729                 });
8730
8731                 if ( resize ) {
8732                         this._size();
8733                         this._position();
8734                 }
8735                 if ( this.uiDialog.is( ":data(ui-resizable)" ) ) {
8736                         this.uiDialog.resizable( "option", resizableOptions );
8737                 }
8738         },
8739
8740         _setOption: function( key, value ) {
8741                 var isDraggable, isResizable,
8742                         uiDialog = this.uiDialog;
8743
8744                 if ( key === "dialogClass" ) {
8745                         uiDialog
8746                                 .removeClass( this.options.dialogClass )
8747                                 .addClass( value );
8748                 }
8749
8750                 if ( key === "disabled" ) {
8751                         return;
8752                 }
8753
8754                 this._super( key, value );
8755
8756                 if ( key === "appendTo" ) {
8757                         this.uiDialog.appendTo( this._appendTo() );
8758                 }
8759
8760                 if ( key === "buttons" ) {
8761                         this._createButtons();
8762                 }
8763
8764                 if ( key === "closeText" ) {
8765                         this.uiDialogTitlebarClose.button({
8766                                 // Ensure that we always pass a string
8767                                 label: "" + value
8768                         });
8769                 }
8770
8771                 if ( key === "draggable" ) {
8772                         isDraggable = uiDialog.is( ":data(ui-draggable)" );
8773                         if ( isDraggable && !value ) {
8774                                 uiDialog.draggable( "destroy" );
8775                         }
8776
8777                         if ( !isDraggable && value ) {
8778                                 this._makeDraggable();
8779                         }
8780                 }
8781
8782                 if ( key === "position" ) {
8783                         this._position();
8784                 }
8785
8786                 if ( key === "resizable" ) {
8787                         // currently resizable, becoming non-resizable
8788                         isResizable = uiDialog.is( ":data(ui-resizable)" );
8789                         if ( isResizable && !value ) {
8790                                 uiDialog.resizable( "destroy" );
8791                         }
8792
8793                         // currently resizable, changing handles
8794                         if ( isResizable && typeof value === "string" ) {
8795                                 uiDialog.resizable( "option", "handles", value );
8796                         }
8797
8798                         // currently non-resizable, becoming resizable
8799                         if ( !isResizable && value !== false ) {
8800                                 this._makeResizable();
8801                         }
8802                 }
8803
8804                 if ( key === "title" ) {
8805                         this._title( this.uiDialogTitlebar.find( ".ui-dialog-title" ) );
8806                 }
8807         },
8808
8809         _size: function() {
8810                 // If the user has resized the dialog, the .ui-dialog and .ui-dialog-content
8811                 // divs will both have width and height set, so we need to reset them
8812                 var nonContentHeight, minContentHeight, maxContentHeight,
8813                         options = this.options;
8814
8815                 // Reset content sizing
8816                 this.element.show().css({
8817                         width: "auto",
8818                         minHeight: 0,
8819                         maxHeight: "none",
8820                         height: 0
8821                 });
8822
8823                 if ( options.minWidth > options.width ) {
8824                         options.width = options.minWidth;
8825                 }
8826
8827                 // reset wrapper sizing
8828                 // determine the height of all the non-content elements
8829                 nonContentHeight = this.uiDialog.css({
8830                                 height: "auto",
8831                                 width: options.width
8832                         })
8833                         .outerHeight();
8834                 minContentHeight = Math.max( 0, options.minHeight - nonContentHeight );
8835                 maxContentHeight = typeof options.maxHeight === "number" ?
8836                         Math.max( 0, options.maxHeight - nonContentHeight ) :
8837                         "none";
8838
8839                 if ( options.height === "auto" ) {
8840                         this.element.css({
8841                                 minHeight: minContentHeight,
8842                                 maxHeight: maxContentHeight,
8843                                 height: "auto"
8844                         });
8845                 } else {
8846                         this.element.height( Math.max( 0, options.height - nonContentHeight ) );
8847                 }
8848
8849                 if ( this.uiDialog.is( ":data(ui-resizable)" ) ) {
8850                         this.uiDialog.resizable( "option", "minHeight", this._minHeight() );
8851                 }
8852         },
8853
8854         _blockFrames: function() {
8855                 this.iframeBlocks = this.document.find( "iframe" ).map(function() {
8856                         var iframe = $( this );
8857
8858                         return $( "<div>" )
8859                                 .css({
8860                                         position: "absolute",
8861                                         width: iframe.outerWidth(),
8862                                         height: iframe.outerHeight()
8863                                 })
8864                                 .appendTo( iframe.parent() )
8865                                 .offset( iframe.offset() )[0];
8866                 });
8867         },
8868
8869         _unblockFrames: function() {
8870                 if ( this.iframeBlocks ) {
8871                         this.iframeBlocks.remove();
8872                         delete this.iframeBlocks;
8873                 }
8874         },
8875
8876         _allowInteraction: function( event ) {
8877                 if ( $( event.target ).closest( ".ui-dialog" ).length ) {
8878                         return true;
8879                 }
8880
8881                 // TODO: Remove hack when datepicker implements
8882                 // the .ui-front logic (#8989)
8883                 return !!$( event.target ).closest( ".ui-datepicker" ).length;
8884         },
8885
8886         _createOverlay: function() {
8887                 if ( !this.options.modal ) {
8888                         return;
8889                 }
8890
8891                 // We use a delay in case the overlay is created from an
8892                 // event that we're going to be cancelling (#2804)
8893                 var isOpening = true;
8894                 this._delay(function() {
8895                         isOpening = false;
8896                 });
8897
8898                 if ( !this.document.data( "ui-dialog-overlays" ) ) {
8899
8900                         // Prevent use of anchors and inputs
8901                         // Using _on() for an event handler shared across many instances is
8902                         // safe because the dialogs stack and must be closed in reverse order
8903                         this._on( this.document, {
8904                                 focusin: function( event ) {
8905                                         if ( isOpening ) {
8906                                                 return;
8907                                         }
8908
8909                                         if ( !this._allowInteraction( event ) ) {
8910                                                 event.preventDefault();
8911                                                 this._trackingInstances()[ 0 ]._focusTabbable();
8912                                         }
8913                                 }
8914                         });
8915                 }
8916
8917                 this.overlay = $( "<div>" )
8918                         .addClass( "ui-widget-overlay ui-front" )
8919                         .appendTo( this._appendTo() );
8920                 this._on( this.overlay, {
8921                         mousedown: "_keepFocus"
8922                 });
8923                 this.document.data( "ui-dialog-overlays",
8924                         (this.document.data( "ui-dialog-overlays" ) || 0) + 1 );
8925         },
8926
8927         _destroyOverlay: function() {
8928                 if ( !this.options.modal ) {
8929                         return;
8930                 }
8931
8932                 if ( this.overlay ) {
8933                         var overlays = this.document.data( "ui-dialog-overlays" ) - 1;
8934
8935                         if ( !overlays ) {
8936                                 this.document
8937                                         .unbind( "focusin" )
8938                                         .removeData( "ui-dialog-overlays" );
8939                         } else {
8940                                 this.document.data( "ui-dialog-overlays", overlays );
8941                         }
8942
8943                         this.overlay.remove();
8944                         this.overlay = null;
8945                 }
8946         }
8947 });
8948
8949
8950 /*!
8951  * jQuery UI Droppable 1.11.4
8952  * http://jqueryui.com
8953  *
8954  * Copyright jQuery Foundation and other contributors
8955  * Released under the MIT license.
8956  * http://jquery.org/license
8957  *
8958  * http://api.jqueryui.com/droppable/
8959  */
8960
8961
8962 $.widget( "ui.droppable", {
8963         version: "1.11.4",
8964         widgetEventPrefix: "drop",
8965         options: {
8966                 accept: "*",
8967                 activeClass: false,
8968                 addClasses: true,
8969                 greedy: false,
8970                 hoverClass: false,
8971                 scope: "default",
8972                 tolerance: "intersect",
8973
8974                 // callbacks
8975                 activate: null,
8976                 deactivate: null,
8977                 drop: null,
8978                 out: null,
8979                 over: null
8980         },
8981         _create: function() {
8982
8983                 var proportions,
8984                         o = this.options,
8985                         accept = o.accept;
8986
8987                 this.isover = false;
8988                 this.isout = true;
8989
8990                 this.accept = $.isFunction( accept ) ? accept : function( d ) {
8991                         return d.is( accept );
8992                 };
8993
8994                 this.proportions = function( /* valueToWrite */ ) {
8995                         if ( arguments.length ) {
8996                                 // Store the droppable's proportions
8997                                 proportions = arguments[ 0 ];
8998                         } else {
8999                                 // Retrieve or derive the droppable's proportions
9000                                 return proportions ?
9001                                         proportions :
9002                                         proportions = {
9003                                                 width: this.element[ 0 ].offsetWidth,
9004                                                 height: this.element[ 0 ].offsetHeight
9005                                         };
9006                         }
9007                 };
9008
9009                 this._addToManager( o.scope );
9010
9011                 o.addClasses && this.element.addClass( "ui-droppable" );
9012
9013         },
9014
9015         _addToManager: function( scope ) {
9016                 // Add the reference and positions to the manager
9017                 $.ui.ddmanager.droppables[ scope ] = $.ui.ddmanager.droppables[ scope ] || [];
9018                 $.ui.ddmanager.droppables[ scope ].push( this );
9019         },
9020
9021         _splice: function( drop ) {
9022                 var i = 0;
9023                 for ( ; i < drop.length; i++ ) {
9024                         if ( drop[ i ] === this ) {
9025                                 drop.splice( i, 1 );
9026                         }
9027                 }
9028         },
9029
9030         _destroy: function() {
9031                 var drop = $.ui.ddmanager.droppables[ this.options.scope ];
9032
9033                 this._splice( drop );
9034
9035                 this.element.removeClass( "ui-droppable ui-droppable-disabled" );
9036         },
9037
9038         _setOption: function( key, value ) {
9039
9040                 if ( key === "accept" ) {
9041                         this.accept = $.isFunction( value ) ? value : function( d ) {
9042                                 return d.is( value );
9043                         };
9044                 } else if ( key === "scope" ) {
9045                         var drop = $.ui.ddmanager.droppables[ this.options.scope ];
9046
9047                         this._splice( drop );
9048                         this._addToManager( value );
9049                 }
9050
9051                 this._super( key, value );
9052         },
9053
9054         _activate: function( event ) {
9055                 var draggable = $.ui.ddmanager.current;
9056                 if ( this.options.activeClass ) {
9057                         this.element.addClass( this.options.activeClass );
9058                 }
9059                 if ( draggable ){
9060                         this._trigger( "activate", event, this.ui( draggable ) );
9061                 }
9062         },
9063
9064         _deactivate: function( event ) {
9065                 var draggable = $.ui.ddmanager.current;
9066                 if ( this.options.activeClass ) {
9067                         this.element.removeClass( this.options.activeClass );
9068                 }
9069                 if ( draggable ){
9070                         this._trigger( "deactivate", event, this.ui( draggable ) );
9071                 }
9072         },
9073
9074         _over: function( event ) {
9075
9076                 var draggable = $.ui.ddmanager.current;
9077
9078                 // Bail if draggable and droppable are same element
9079                 if ( !draggable || ( draggable.currentItem || draggable.element )[ 0 ] === this.element[ 0 ] ) {
9080                         return;
9081                 }
9082
9083                 if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
9084                         if ( this.options.hoverClass ) {
9085                                 this.element.addClass( this.options.hoverClass );
9086                         }
9087                         this._trigger( "over", event, this.ui( draggable ) );
9088                 }
9089
9090         },
9091
9092         _out: function( event ) {
9093
9094                 var draggable = $.ui.ddmanager.current;
9095
9096                 // Bail if draggable and droppable are same element
9097                 if ( !draggable || ( draggable.currentItem || draggable.element )[ 0 ] === this.element[ 0 ] ) {
9098                         return;
9099                 }
9100
9101                 if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
9102                         if ( this.options.hoverClass ) {
9103                                 this.element.removeClass( this.options.hoverClass );
9104                         }
9105                         this._trigger( "out", event, this.ui( draggable ) );
9106                 }
9107
9108         },
9109
9110         _drop: function( event, custom ) {
9111
9112                 var draggable = custom || $.ui.ddmanager.current,
9113                         childrenIntersection = false;
9114
9115                 // Bail if draggable and droppable are same element
9116                 if ( !draggable || ( draggable.currentItem || draggable.element )[ 0 ] === this.element[ 0 ] ) {
9117                         return false;
9118                 }
9119
9120                 this.element.find( ":data(ui-droppable)" ).not( ".ui-draggable-dragging" ).each(function() {
9121                         var inst = $( this ).droppable( "instance" );
9122                         if (
9123                                 inst.options.greedy &&
9124                                 !inst.options.disabled &&
9125                                 inst.options.scope === draggable.options.scope &&
9126                                 inst.accept.call( inst.element[ 0 ], ( draggable.currentItem || draggable.element ) ) &&
9127                                 $.ui.intersect( draggable, $.extend( inst, { offset: inst.element.offset() } ), inst.options.tolerance, event )
9128                         ) { childrenIntersection = true; return false; }
9129                 });
9130                 if ( childrenIntersection ) {
9131                         return false;
9132                 }
9133
9134                 if ( this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
9135                         if ( this.options.activeClass ) {
9136                                 this.element.removeClass( this.options.activeClass );
9137                         }
9138                         if ( this.options.hoverClass ) {
9139                                 this.element.removeClass( this.options.hoverClass );
9140                         }
9141                         this._trigger( "drop", event, this.ui( draggable ) );
9142                         return this.element;
9143                 }
9144
9145                 return false;
9146
9147         },
9148
9149         ui: function( c ) {
9150                 return {
9151                         draggable: ( c.currentItem || c.element ),
9152                         helper: c.helper,
9153                         position: c.position,
9154                         offset: c.positionAbs
9155                 };
9156         }
9157
9158 });
9159
9160 $.ui.intersect = (function() {
9161         function isOverAxis( x, reference, size ) {
9162                 return ( x >= reference ) && ( x < ( reference + size ) );
9163         }
9164
9165         return function( draggable, droppable, toleranceMode, event ) {
9166
9167                 if ( !droppable.offset ) {
9168                         return false;
9169                 }
9170
9171                 var x1 = ( draggable.positionAbs || draggable.position.absolute ).left + draggable.margins.left,
9172                         y1 = ( draggable.positionAbs || draggable.position.absolute ).top + draggable.margins.top,
9173                         x2 = x1 + draggable.helperProportions.width,
9174                         y2 = y1 + draggable.helperProportions.height,
9175                         l = droppable.offset.left,
9176                         t = droppable.offset.top,
9177                         r = l + droppable.proportions().width,
9178                         b = t + droppable.proportions().height;
9179
9180                 switch ( toleranceMode ) {
9181                 case "fit":
9182                         return ( l <= x1 && x2 <= r && t <= y1 && y2 <= b );
9183                 case "intersect":
9184                         return ( l < x1 + ( draggable.helperProportions.width / 2 ) && // Right Half
9185                                 x2 - ( draggable.helperProportions.width / 2 ) < r && // Left Half
9186                                 t < y1 + ( draggable.helperProportions.height / 2 ) && // Bottom Half
9187                                 y2 - ( draggable.helperProportions.height / 2 ) < b ); // Top Half
9188                 case "pointer":
9189                         return isOverAxis( event.pageY, t, droppable.proportions().height ) && isOverAxis( event.pageX, l, droppable.proportions().width );
9190                 case "touch":
9191                         return (
9192                                 ( y1 >= t && y1 <= b ) || // Top edge touching
9193                                 ( y2 >= t && y2 <= b ) || // Bottom edge touching
9194                                 ( y1 < t && y2 > b ) // Surrounded vertically
9195                         ) && (
9196                                 ( x1 >= l && x1 <= r ) || // Left edge touching
9197                                 ( x2 >= l && x2 <= r ) || // Right edge touching
9198                                 ( x1 < l && x2 > r ) // Surrounded horizontally
9199                         );
9200                 default:
9201                         return false;
9202                 }
9203         };
9204 })();
9205
9206 /*
9207         This manager tracks offsets of draggables and droppables
9208 */
9209 $.ui.ddmanager = {
9210         current: null,
9211         droppables: { "default": [] },
9212         prepareOffsets: function( t, event ) {
9213
9214                 var i, j,
9215                         m = $.ui.ddmanager.droppables[ t.options.scope ] || [],
9216                         type = event ? event.type : null, // workaround for #2317
9217                         list = ( t.currentItem || t.element ).find( ":data(ui-droppable)" ).addBack();
9218
9219                 droppablesLoop: for ( i = 0; i < m.length; i++ ) {
9220
9221                         // No disabled and non-accepted
9222                         if ( m[ i ].options.disabled || ( t && !m[ i ].accept.call( m[ i ].element[ 0 ], ( t.currentItem || t.element ) ) ) ) {
9223                                 continue;
9224                         }
9225
9226                         // Filter out elements in the current dragged item
9227                         for ( j = 0; j < list.length; j++ ) {
9228                                 if ( list[ j ] === m[ i ].element[ 0 ] ) {
9229                                         m[ i ].proportions().height = 0;
9230                                         continue droppablesLoop;
9231                                 }
9232                         }
9233
9234                         m[ i ].visible = m[ i ].element.css( "display" ) !== "none";
9235                         if ( !m[ i ].visible ) {
9236                                 continue;
9237                         }
9238
9239                         // Activate the droppable if used directly from draggables
9240                         if ( type === "mousedown" ) {
9241                                 m[ i ]._activate.call( m[ i ], event );
9242                         }
9243
9244                         m[ i ].offset = m[ i ].element.offset();
9245                         m[ i ].proportions({ width: m[ i ].element[ 0 ].offsetWidth, height: m[ i ].element[ 0 ].offsetHeight });
9246
9247                 }
9248
9249         },
9250         drop: function( draggable, event ) {
9251
9252                 var dropped = false;
9253                 // Create a copy of the droppables in case the list changes during the drop (#9116)
9254                 $.each( ( $.ui.ddmanager.droppables[ draggable.options.scope ] || [] ).slice(), function() {
9255
9256                         if ( !this.options ) {
9257                                 return;
9258                         }
9259                         if ( !this.options.disabled && this.visible && $.ui.intersect( draggable, this, this.options.tolerance, event ) ) {
9260                                 dropped = this._drop.call( this, event ) || dropped;
9261                         }
9262
9263                         if ( !this.options.disabled && this.visible && this.accept.call( this.element[ 0 ], ( draggable.currentItem || draggable.element ) ) ) {
9264                                 this.isout = true;
9265                                 this.isover = false;
9266                                 this._deactivate.call( this, event );
9267                         }
9268
9269                 });
9270                 return dropped;
9271
9272         },
9273         dragStart: function( draggable, event ) {
9274                 // Listen for scrolling so that if the dragging causes scrolling the position of the droppables can be recalculated (see #5003)
9275                 draggable.element.parentsUntil( "body" ).bind( "scroll.droppable", function() {
9276                         if ( !draggable.options.refreshPositions ) {
9277                                 $.ui.ddmanager.prepareOffsets( draggable, event );
9278                         }
9279                 });
9280         },
9281         drag: function( draggable, event ) {
9282
9283                 // If you have a highly dynamic page, you might try this option. It renders positions every time you move the mouse.
9284                 if ( draggable.options.refreshPositions ) {
9285                         $.ui.ddmanager.prepareOffsets( draggable, event );
9286                 }
9287
9288                 // Run through all droppables and check their positions based on specific tolerance options
9289                 $.each( $.ui.ddmanager.droppables[ draggable.options.scope ] || [], function() {
9290
9291                         if ( this.options.disabled || this.greedyChild || !this.visible ) {
9292                                 return;
9293                         }
9294
9295                         var parentInstance, scope, parent,
9296                                 intersects = $.ui.intersect( draggable, this, this.options.tolerance, event ),
9297                                 c = !intersects && this.isover ? "isout" : ( intersects && !this.isover ? "isover" : null );
9298                         if ( !c ) {
9299                                 return;
9300                         }
9301
9302                         if ( this.options.greedy ) {
9303                                 // find droppable parents with same scope
9304                                 scope = this.options.scope;
9305                                 parent = this.element.parents( ":data(ui-droppable)" ).filter(function() {
9306                                         return $( this ).droppable( "instance" ).options.scope === scope;
9307                                 });
9308
9309                                 if ( parent.length ) {
9310                                         parentInstance = $( parent[ 0 ] ).droppable( "instance" );
9311                                         parentInstance.greedyChild = ( c === "isover" );
9312                                 }
9313                         }
9314
9315                         // we just moved into a greedy child
9316                         if ( parentInstance && c === "isover" ) {
9317                                 parentInstance.isover = false;
9318                                 parentInstance.isout = true;
9319                                 parentInstance._out.call( parentInstance, event );
9320                         }
9321
9322                         this[ c ] = true;
9323                         this[c === "isout" ? "isover" : "isout"] = false;
9324                         this[c === "isover" ? "_over" : "_out"].call( this, event );
9325
9326                         // we just moved out of a greedy child
9327                         if ( parentInstance && c === "isout" ) {
9328                                 parentInstance.isout = false;
9329                                 parentInstance.isover = true;
9330                                 parentInstance._over.call( parentInstance, event );
9331                         }
9332                 });
9333
9334         },
9335         dragStop: function( draggable, event ) {
9336                 draggable.element.parentsUntil( "body" ).unbind( "scroll.droppable" );
9337                 // Call prepareOffsets one final time since IE does not fire return scroll events when overflow was caused by drag (see #5003)
9338                 if ( !draggable.options.refreshPositions ) {
9339                         $.ui.ddmanager.prepareOffsets( draggable, event );
9340                 }
9341         }
9342 };
9343
9344 var droppable = $.ui.droppable;
9345
9346
9347 /*!
9348  * jQuery UI Effects 1.11.4
9349  * http://jqueryui.com
9350  *
9351  * Copyright jQuery Foundation and other contributors
9352  * Released under the MIT license.
9353  * http://jquery.org/license
9354  *
9355  * http://api.jqueryui.com/category/effects-core/
9356  */
9357
9358
9359 var dataSpace = "ui-effects-",
9360
9361         // Create a local jQuery because jQuery Color relies on it and the
9362         // global may not exist with AMD and a custom build (#10199)
9363         jQuery = $;
9364
9365 $.effects = {
9366         effect: {}
9367 };
9368
9369 /*!
9370  * jQuery Color Animations v2.1.2
9371  * https://github.com/jquery/jquery-color
9372  *
9373  * Copyright 2014 jQuery Foundation and other contributors
9374  * Released under the MIT license.
9375  * http://jquery.org/license
9376  *
9377  * Date: Wed Jan 16 08:47:09 2013 -0600
9378  */
9379 (function( jQuery, undefined ) {
9380
9381         var stepHooks = "backgroundColor borderBottomColor borderLeftColor borderRightColor borderTopColor color columnRuleColor outlineColor textDecorationColor textEmphasisColor",
9382
9383         // plusequals test for += 100 -= 100
9384         rplusequals = /^([\-+])=\s*(\d+\.?\d*)/,
9385         // a set of RE's that can match strings and generate color tuples.
9386         stringParsers = [ {
9387                         re: /rgba?\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
9388                         parse: function( execResult ) {
9389                                 return [
9390                                         execResult[ 1 ],
9391                                         execResult[ 2 ],
9392                                         execResult[ 3 ],
9393                                         execResult[ 4 ]
9394                                 ];
9395                         }
9396                 }, {
9397                         re: /rgba?\(\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
9398                         parse: function( execResult ) {
9399                                 return [
9400                                         execResult[ 1 ] * 2.55,
9401                                         execResult[ 2 ] * 2.55,
9402                                         execResult[ 3 ] * 2.55,
9403                                         execResult[ 4 ]
9404                                 ];
9405                         }
9406                 }, {
9407                         // this regex ignores A-F because it's compared against an already lowercased string
9408                         re: /#([a-f0-9]{2})([a-f0-9]{2})([a-f0-9]{2})/,
9409                         parse: function( execResult ) {
9410                                 return [
9411                                         parseInt( execResult[ 1 ], 16 ),
9412                                         parseInt( execResult[ 2 ], 16 ),
9413                                         parseInt( execResult[ 3 ], 16 )
9414                                 ];
9415                         }
9416                 }, {
9417                         // this regex ignores A-F because it's compared against an already lowercased string
9418                         re: /#([a-f0-9])([a-f0-9])([a-f0-9])/,
9419                         parse: function( execResult ) {
9420                                 return [
9421                                         parseInt( execResult[ 1 ] + execResult[ 1 ], 16 ),
9422                                         parseInt( execResult[ 2 ] + execResult[ 2 ], 16 ),
9423                                         parseInt( execResult[ 3 ] + execResult[ 3 ], 16 )
9424                                 ];
9425                         }
9426                 }, {
9427                         re: /hsla?\(\s*(\d+(?:\.\d+)?)\s*,\s*(\d+(?:\.\d+)?)\%\s*,\s*(\d+(?:\.\d+)?)\%\s*(?:,\s*(\d?(?:\.\d+)?)\s*)?\)/,
9428                         space: "hsla",
9429                         parse: function( execResult ) {
9430                                 return [
9431                                         execResult[ 1 ],
9432                                         execResult[ 2 ] / 100,
9433                                         execResult[ 3 ] / 100,
9434                                         execResult[ 4 ]
9435                                 ];
9436                         }
9437                 } ],
9438
9439         // jQuery.Color( )
9440         color = jQuery.Color = function( color, green, blue, alpha ) {
9441                 return new jQuery.Color.fn.parse( color, green, blue, alpha );
9442         },
9443         spaces = {
9444                 rgba: {
9445                         props: {
9446                                 red: {
9447                                         idx: 0,
9448                                         type: "byte"
9449                                 },
9450                                 green: {
9451                                         idx: 1,
9452                                         type: "byte"
9453                                 },
9454                                 blue: {
9455                                         idx: 2,
9456                                         type: "byte"
9457                                 }
9458                         }
9459                 },
9460
9461                 hsla: {
9462                         props: {
9463                                 hue: {
9464                                         idx: 0,
9465                                         type: "degrees"
9466                                 },
9467                                 saturation: {
9468                                         idx: 1,
9469                                         type: "percent"
9470                                 },
9471                                 lightness: {
9472                                         idx: 2,
9473                                         type: "percent"
9474                                 }
9475                         }
9476                 }
9477         },
9478         propTypes = {
9479                 "byte": {
9480                         floor: true,
9481                         max: 255
9482                 },
9483                 "percent": {
9484                         max: 1
9485                 },
9486                 "degrees": {
9487                         mod: 360,
9488                         floor: true
9489                 }
9490         },
9491         support = color.support = {},
9492
9493         // element for support tests
9494         supportElem = jQuery( "<p>" )[ 0 ],
9495
9496         // colors = jQuery.Color.names
9497         colors,
9498
9499         // local aliases of functions called often
9500         each = jQuery.each;
9501
9502 // determine rgba support immediately
9503 supportElem.style.cssText = "background-color:rgba(1,1,1,.5)";
9504 support.rgba = supportElem.style.backgroundColor.indexOf( "rgba" ) > -1;
9505
9506 // define cache name and alpha properties
9507 // for rgba and hsla spaces
9508 each( spaces, function( spaceName, space ) {
9509         space.cache = "_" + spaceName;
9510         space.props.alpha = {
9511                 idx: 3,
9512                 type: "percent",
9513                 def: 1
9514         };
9515 });
9516
9517 function clamp( value, prop, allowEmpty ) {
9518         var type = propTypes[ prop.type ] || {};
9519
9520         if ( value == null ) {
9521                 return (allowEmpty || !prop.def) ? null : prop.def;
9522         }
9523
9524         // ~~ is an short way of doing floor for positive numbers
9525         value = type.floor ? ~~value : parseFloat( value );
9526
9527         // IE will pass in empty strings as value for alpha,
9528         // which will hit this case
9529         if ( isNaN( value ) ) {
9530                 return prop.def;
9531         }
9532
9533         if ( type.mod ) {
9534                 // we add mod before modding to make sure that negatives values
9535                 // get converted properly: -10 -> 350
9536                 return (value + type.mod) % type.mod;
9537         }
9538
9539         // for now all property types without mod have min and max
9540         return 0 > value ? 0 : type.max < value ? type.max : value;
9541 }
9542
9543 function stringParse( string ) {
9544         var inst = color(),
9545                 rgba = inst._rgba = [];
9546
9547         string = string.toLowerCase();
9548
9549         each( stringParsers, function( i, parser ) {
9550                 var parsed,
9551                         match = parser.re.exec( string ),
9552                         values = match && parser.parse( match ),
9553                         spaceName = parser.space || "rgba";
9554
9555                 if ( values ) {
9556                         parsed = inst[ spaceName ]( values );
9557
9558                         // if this was an rgba parse the assignment might happen twice
9559                         // oh well....
9560                         inst[ spaces[ spaceName ].cache ] = parsed[ spaces[ spaceName ].cache ];
9561                         rgba = inst._rgba = parsed._rgba;
9562
9563                         // exit each( stringParsers ) here because we matched
9564                         return false;
9565                 }
9566         });
9567
9568         // Found a stringParser that handled it
9569         if ( rgba.length ) {
9570
9571                 // if this came from a parsed string, force "transparent" when alpha is 0
9572                 // chrome, (and maybe others) return "transparent" as rgba(0,0,0,0)
9573                 if ( rgba.join() === "0,0,0,0" ) {
9574                         jQuery.extend( rgba, colors.transparent );
9575                 }
9576                 return inst;
9577         }
9578
9579         // named colors
9580         return colors[ string ];
9581 }
9582
9583 color.fn = jQuery.extend( color.prototype, {
9584         parse: function( red, green, blue, alpha ) {
9585                 if ( red === undefined ) {
9586                         this._rgba = [ null, null, null, null ];
9587                         return this;
9588                 }
9589                 if ( red.jquery || red.nodeType ) {
9590                         red = jQuery( red ).css( green );
9591                         green = undefined;
9592                 }
9593
9594                 var inst = this,
9595                         type = jQuery.type( red ),
9596                         rgba = this._rgba = [];
9597
9598                 // more than 1 argument specified - assume ( red, green, blue, alpha )
9599                 if ( green !== undefined ) {
9600                         red = [ red, green, blue, alpha ];
9601                         type = "array";
9602                 }
9603
9604                 if ( type === "string" ) {
9605                         return this.parse( stringParse( red ) || colors._default );
9606                 }
9607
9608                 if ( type === "array" ) {
9609                         each( spaces.rgba.props, function( key, prop ) {
9610                                 rgba[ prop.idx ] = clamp( red[ prop.idx ], prop );
9611                         });
9612                         return this;
9613                 }
9614
9615                 if ( type === "object" ) {
9616                         if ( red instanceof color ) {
9617                                 each( spaces, function( spaceName, space ) {
9618                                         if ( red[ space.cache ] ) {
9619                                                 inst[ space.cache ] = red[ space.cache ].slice();
9620                                         }
9621                                 });
9622                         } else {
9623                                 each( spaces, function( spaceName, space ) {
9624                                         var cache = space.cache;
9625                                         each( space.props, function( key, prop ) {
9626
9627                                                 // if the cache doesn't exist, and we know how to convert
9628                                                 if ( !inst[ cache ] && space.to ) {
9629
9630                                                         // if the value was null, we don't need to copy it
9631                                                         // if the key was alpha, we don't need to copy it either
9632                                                         if ( key === "alpha" || red[ key ] == null ) {
9633                                                                 return;
9634                                                         }
9635                                                         inst[ cache ] = space.to( inst._rgba );
9636                                                 }
9637
9638                                                 // this is the only case where we allow nulls for ALL properties.
9639                                                 // call clamp with alwaysAllowEmpty
9640                                                 inst[ cache ][ prop.idx ] = clamp( red[ key ], prop, true );
9641                                         });
9642
9643                                         // everything defined but alpha?
9644                                         if ( inst[ cache ] && jQuery.inArray( null, inst[ cache ].slice( 0, 3 ) ) < 0 ) {
9645                                                 // use the default of 1
9646                                                 inst[ cache ][ 3 ] = 1;
9647                                                 if ( space.from ) {
9648                                                         inst._rgba = space.from( inst[ cache ] );
9649                                                 }
9650                                         }
9651                                 });
9652                         }
9653                         return this;
9654                 }
9655         },
9656         is: function( compare ) {
9657                 var is = color( compare ),
9658                         same = true,
9659                         inst = this;
9660
9661                 each( spaces, function( _, space ) {
9662                         var localCache,
9663                                 isCache = is[ space.cache ];
9664                         if (isCache) {
9665                                 localCache = inst[ space.cache ] || space.to && space.to( inst._rgba ) || [];
9666                                 each( space.props, function( _, prop ) {
9667                                         if ( isCache[ prop.idx ] != null ) {
9668                                                 same = ( isCache[ prop.idx ] === localCache[ prop.idx ] );
9669                                                 return same;
9670                                         }
9671                                 });
9672                         }
9673                         return same;
9674                 });
9675                 return same;
9676         },
9677         _space: function() {
9678                 var used = [],
9679                         inst = this;
9680                 each( spaces, function( spaceName, space ) {
9681                         if ( inst[ space.cache ] ) {
9682                                 used.push( spaceName );
9683                         }
9684                 });
9685                 return used.pop();
9686         },
9687         transition: function( other, distance ) {
9688                 var end = color( other ),
9689                         spaceName = end._space(),
9690                         space = spaces[ spaceName ],
9691                         startColor = this.alpha() === 0 ? color( "transparent" ) : this,
9692                         start = startColor[ space.cache ] || space.to( startColor._rgba ),
9693                         result = start.slice();
9694
9695                 end = end[ space.cache ];
9696                 each( space.props, function( key, prop ) {
9697                         var index = prop.idx,
9698                                 startValue = start[ index ],
9699                                 endValue = end[ index ],
9700                                 type = propTypes[ prop.type ] || {};
9701
9702                         // if null, don't override start value
9703                         if ( endValue === null ) {
9704                                 return;
9705                         }
9706                         // if null - use end
9707                         if ( startValue === null ) {
9708                                 result[ index ] = endValue;
9709                         } else {
9710                                 if ( type.mod ) {
9711                                         if ( endValue - startValue > type.mod / 2 ) {
9712                                                 startValue += type.mod;
9713                                         } else if ( startValue - endValue > type.mod / 2 ) {
9714                                                 startValue -= type.mod;
9715                                         }
9716                                 }
9717                                 result[ index ] = clamp( ( endValue - startValue ) * distance + startValue, prop );
9718                         }
9719                 });
9720                 return this[ spaceName ]( result );
9721         },
9722         blend: function( opaque ) {
9723                 // if we are already opaque - return ourself
9724                 if ( this._rgba[ 3 ] === 1 ) {
9725                         return this;
9726                 }
9727
9728                 var rgb = this._rgba.slice(),
9729                         a = rgb.pop(),
9730                         blend = color( opaque )._rgba;
9731
9732                 return color( jQuery.map( rgb, function( v, i ) {
9733                         return ( 1 - a ) * blend[ i ] + a * v;
9734                 }));
9735         },
9736         toRgbaString: function() {
9737                 var prefix = "rgba(",
9738                         rgba = jQuery.map( this._rgba, function( v, i ) {
9739                                 return v == null ? ( i > 2 ? 1 : 0 ) : v;
9740                         });
9741
9742                 if ( rgba[ 3 ] === 1 ) {
9743                         rgba.pop();
9744                         prefix = "rgb(";
9745                 }
9746
9747                 return prefix + rgba.join() + ")";
9748         },
9749         toHslaString: function() {
9750                 var prefix = "hsla(",
9751                         hsla = jQuery.map( this.hsla(), function( v, i ) {
9752                                 if ( v == null ) {
9753                                         v = i > 2 ? 1 : 0;
9754                                 }
9755
9756                                 // catch 1 and 2
9757                                 if ( i && i < 3 ) {
9758                                         v = Math.round( v * 100 ) + "%";
9759                                 }
9760                                 return v;
9761                         });
9762
9763                 if ( hsla[ 3 ] === 1 ) {
9764                         hsla.pop();
9765                         prefix = "hsl(";
9766                 }
9767                 return prefix + hsla.join() + ")";
9768         },
9769         toHexString: function( includeAlpha ) {
9770                 var rgba = this._rgba.slice(),
9771                         alpha = rgba.pop();
9772
9773                 if ( includeAlpha ) {
9774                         rgba.push( ~~( alpha * 255 ) );
9775                 }
9776
9777                 return "#" + jQuery.map( rgba, function( v ) {
9778
9779                         // default to 0 when nulls exist
9780                         v = ( v || 0 ).toString( 16 );
9781                         return v.length === 1 ? "0" + v : v;
9782                 }).join("");
9783         },
9784         toString: function() {
9785                 return this._rgba[ 3 ] === 0 ? "transparent" : this.toRgbaString();
9786         }
9787 });
9788 color.fn.parse.prototype = color.fn;
9789
9790 // hsla conversions adapted from:
9791 // https://code.google.com/p/maashaack/source/browse/packages/graphics/trunk/src/graphics/colors/HUE2RGB.as?r=5021
9792
9793 function hue2rgb( p, q, h ) {
9794         h = ( h + 1 ) % 1;
9795         if ( h * 6 < 1 ) {
9796                 return p + ( q - p ) * h * 6;
9797         }
9798         if ( h * 2 < 1) {
9799                 return q;
9800         }
9801         if ( h * 3 < 2 ) {
9802                 return p + ( q - p ) * ( ( 2 / 3 ) - h ) * 6;
9803         }
9804         return p;
9805 }
9806
9807 spaces.hsla.to = function( rgba ) {
9808         if ( rgba[ 0 ] == null || rgba[ 1 ] == null || rgba[ 2 ] == null ) {
9809                 return [ null, null, null, rgba[ 3 ] ];
9810         }
9811         var r = rgba[ 0 ] / 255,
9812                 g = rgba[ 1 ] / 255,
9813                 b = rgba[ 2 ] / 255,
9814                 a = rgba[ 3 ],
9815                 max = Math.max( r, g, b ),
9816                 min = Math.min( r, g, b ),
9817                 diff = max - min,
9818                 add = max + min,
9819                 l = add * 0.5,
9820                 h, s;
9821
9822         if ( min === max ) {
9823                 h = 0;
9824         } else if ( r === max ) {
9825                 h = ( 60 * ( g - b ) / diff ) + 360;
9826         } else if ( g === max ) {
9827                 h = ( 60 * ( b - r ) / diff ) + 120;
9828         } else {
9829                 h = ( 60 * ( r - g ) / diff ) + 240;
9830         }
9831
9832         // chroma (diff) == 0 means greyscale which, by definition, saturation = 0%
9833         // otherwise, saturation is based on the ratio of chroma (diff) to lightness (add)
9834         if ( diff === 0 ) {
9835                 s = 0;
9836         } else if ( l <= 0.5 ) {
9837                 s = diff / add;
9838         } else {
9839                 s = diff / ( 2 - add );
9840         }
9841         return [ Math.round(h) % 360, s, l, a == null ? 1 : a ];
9842 };
9843
9844 spaces.hsla.from = function( hsla ) {
9845         if ( hsla[ 0 ] == null || hsla[ 1 ] == null || hsla[ 2 ] == null ) {
9846                 return [ null, null, null, hsla[ 3 ] ];
9847         }
9848         var h = hsla[ 0 ] / 360,
9849                 s = hsla[ 1 ],
9850                 l = hsla[ 2 ],
9851                 a = hsla[ 3 ],
9852                 q = l <= 0.5 ? l * ( 1 + s ) : l + s - l * s,
9853                 p = 2 * l - q;
9854
9855         return [
9856                 Math.round( hue2rgb( p, q, h + ( 1 / 3 ) ) * 255 ),
9857                 Math.round( hue2rgb( p, q, h ) * 255 ),
9858                 Math.round( hue2rgb( p, q, h - ( 1 / 3 ) ) * 255 ),
9859                 a
9860         ];
9861 };
9862
9863 each( spaces, function( spaceName, space ) {
9864         var props = space.props,
9865                 cache = space.cache,
9866                 to = space.to,
9867                 from = space.from;
9868
9869         // makes rgba() and hsla()
9870         color.fn[ spaceName ] = function( value ) {
9871
9872                 // generate a cache for this space if it doesn't exist
9873                 if ( to && !this[ cache ] ) {
9874                         this[ cache ] = to( this._rgba );
9875                 }
9876                 if ( value === undefined ) {
9877                         return this[ cache ].slice();
9878                 }
9879
9880                 var ret,
9881                         type = jQuery.type( value ),
9882                         arr = ( type === "array" || type === "object" ) ? value : arguments,
9883                         local = this[ cache ].slice();
9884
9885                 each( props, function( key, prop ) {
9886                         var val = arr[ type === "object" ? key : prop.idx ];
9887                         if ( val == null ) {
9888                                 val = local[ prop.idx ];
9889                         }
9890                         local[ prop.idx ] = clamp( val, prop );
9891                 });
9892
9893                 if ( from ) {
9894                         ret = color( from( local ) );
9895                         ret[ cache ] = local;
9896                         return ret;
9897                 } else {
9898                         return color( local );
9899                 }
9900         };
9901
9902         // makes red() green() blue() alpha() hue() saturation() lightness()
9903         each( props, function( key, prop ) {
9904                 // alpha is included in more than one space
9905                 if ( color.fn[ key ] ) {
9906                         return;
9907                 }
9908                 color.fn[ key ] = function( value ) {
9909                         var vtype = jQuery.type( value ),
9910                                 fn = ( key === "alpha" ? ( this._hsla ? "hsla" : "rgba" ) : spaceName ),
9911                                 local = this[ fn ](),
9912                                 cur = local[ prop.idx ],
9913                                 match;
9914
9915                         if ( vtype === "undefined" ) {
9916                                 return cur;
9917                         }
9918
9919                         if ( vtype === "function" ) {
9920                                 value = value.call( this, cur );
9921                                 vtype = jQuery.type( value );
9922                         }
9923                         if ( value == null && prop.empty ) {
9924                                 return this;
9925                         }
9926                         if ( vtype === "string" ) {
9927                                 match = rplusequals.exec( value );
9928                                 if ( match ) {
9929                                         value = cur + parseFloat( match[ 2 ] ) * ( match[ 1 ] === "+" ? 1 : -1 );
9930                                 }
9931                         }
9932                         local[ prop.idx ] = value;
9933                         return this[ fn ]( local );
9934                 };
9935         });
9936 });
9937
9938 // add cssHook and .fx.step function for each named hook.
9939 // accept a space separated string of properties
9940 color.hook = function( hook ) {
9941         var hooks = hook.split( " " );
9942         each( hooks, function( i, hook ) {
9943                 jQuery.cssHooks[ hook ] = {
9944                         set: function( elem, value ) {
9945                                 var parsed, curElem,
9946                                         backgroundColor = "";
9947
9948                                 if ( value !== "transparent" && ( jQuery.type( value ) !== "string" || ( parsed = stringParse( value ) ) ) ) {
9949                                         value = color( parsed || value );
9950                                         if ( !support.rgba && value._rgba[ 3 ] !== 1 ) {
9951                                                 curElem = hook === "backgroundColor" ? elem.parentNode : elem;
9952                                                 while (
9953                                                         (backgroundColor === "" || backgroundColor === "transparent") &&
9954                                                         curElem && curElem.style
9955                                                 ) {
9956                                                         try {
9957                                                                 backgroundColor = jQuery.css( curElem, "backgroundColor" );
9958                                                                 curElem = curElem.parentNode;
9959                                                         } catch ( e ) {
9960                                                         }
9961                                                 }
9962
9963                                                 value = value.blend( backgroundColor && backgroundColor !== "transparent" ?
9964                                                         backgroundColor :
9965                                                         "_default" );
9966                                         }
9967
9968                                         value = value.toRgbaString();
9969                                 }
9970                                 try {
9971                                         elem.style[ hook ] = value;
9972                                 } catch ( e ) {
9973                                         // wrapped to prevent IE from throwing errors on "invalid" values like 'auto' or 'inherit'
9974                                 }
9975                         }
9976                 };
9977                 jQuery.fx.step[ hook ] = function( fx ) {
9978                         if ( !fx.colorInit ) {
9979                                 fx.start = color( fx.elem, hook );
9980                                 fx.end = color( fx.end );
9981                                 fx.colorInit = true;
9982                         }
9983                         jQuery.cssHooks[ hook ].set( fx.elem, fx.start.transition( fx.end, fx.pos ) );
9984                 };
9985         });
9986
9987 };
9988
9989 color.hook( stepHooks );
9990
9991 jQuery.cssHooks.borderColor = {
9992         expand: function( value ) {
9993                 var expanded = {};
9994
9995                 each( [ "Top", "Right", "Bottom", "Left" ], function( i, part ) {
9996                         expanded[ "border" + part + "Color" ] = value;
9997                 });
9998                 return expanded;
9999         }
10000 };
10001
10002 // Basic color names only.
10003 // Usage of any of the other color names requires adding yourself or including
10004 // jquery.color.svg-names.js.
10005 colors = jQuery.Color.names = {
10006         // 4.1. Basic color keywords
10007         aqua: "#00ffff",
10008         black: "#000000",
10009         blue: "#0000ff",
10010         fuchsia: "#ff00ff",
10011         gray: "#808080",
10012         green: "#008000",
10013         lime: "#00ff00",
10014         maroon: "#800000",
10015         navy: "#000080",
10016         olive: "#808000",
10017         purple: "#800080",
10018         red: "#ff0000",
10019         silver: "#c0c0c0",
10020         teal: "#008080",
10021         white: "#ffffff",
10022         yellow: "#ffff00",
10023
10024         // 4.2.3. "transparent" color keyword
10025         transparent: [ null, null, null, 0 ],
10026
10027         _default: "#ffffff"
10028 };
10029
10030 })( jQuery );
10031
10032 /******************************************************************************/
10033 /****************************** CLASS ANIMATIONS ******************************/
10034 /******************************************************************************/
10035 (function() {
10036
10037 var classAnimationActions = [ "add", "remove", "toggle" ],
10038         shorthandStyles = {
10039                 border: 1,
10040                 borderBottom: 1,
10041                 borderColor: 1,
10042                 borderLeft: 1,
10043                 borderRight: 1,
10044                 borderTop: 1,
10045                 borderWidth: 1,
10046                 margin: 1,
10047                 padding: 1
10048         };
10049
10050 $.each([ "borderLeftStyle", "borderRightStyle", "borderBottomStyle", "borderTopStyle" ], function( _, prop ) {
10051         $.fx.step[ prop ] = function( fx ) {
10052                 if ( fx.end !== "none" && !fx.setAttr || fx.pos === 1 && !fx.setAttr ) {
10053                         jQuery.style( fx.elem, prop, fx.end );
10054                         fx.setAttr = true;
10055                 }
10056         };
10057 });
10058
10059 function getElementStyles( elem ) {
10060         var key, len,
10061                 style = elem.ownerDocument.defaultView ?
10062                         elem.ownerDocument.defaultView.getComputedStyle( elem, null ) :
10063                         elem.currentStyle,
10064                 styles = {};
10065
10066         if ( style && style.length && style[ 0 ] && style[ style[ 0 ] ] ) {
10067                 len = style.length;
10068                 while ( len-- ) {
10069                         key = style[ len ];
10070                         if ( typeof style[ key ] === "string" ) {
10071                                 styles[ $.camelCase( key ) ] = style[ key ];
10072                         }
10073                 }
10074         // support: Opera, IE <9
10075         } else {
10076                 for ( key in style ) {
10077                         if ( typeof style[ key ] === "string" ) {
10078                                 styles[ key ] = style[ key ];
10079                         }
10080                 }
10081         }
10082
10083         return styles;
10084 }
10085
10086 function styleDifference( oldStyle, newStyle ) {
10087         var diff = {},
10088                 name, value;
10089
10090         for ( name in newStyle ) {
10091                 value = newStyle[ name ];
10092                 if ( oldStyle[ name ] !== value ) {
10093                         if ( !shorthandStyles[ name ] ) {
10094                                 if ( $.fx.step[ name ] || !isNaN( parseFloat( value ) ) ) {
10095                                         diff[ name ] = value;
10096                                 }
10097                         }
10098                 }
10099         }
10100
10101         return diff;
10102 }
10103
10104 // support: jQuery <1.8
10105 if ( !$.fn.addBack ) {
10106         $.fn.addBack = function( selector ) {
10107                 return this.add( selector == null ?
10108                         this.prevObject : this.prevObject.filter( selector )
10109                 );
10110         };
10111 }
10112
10113 $.effects.animateClass = function( value, duration, easing, callback ) {
10114         var o = $.speed( duration, easing, callback );
10115
10116         return this.queue( function() {
10117                 var animated = $( this ),
10118                         baseClass = animated.attr( "class" ) || "",
10119                         applyClassChange,
10120                         allAnimations = o.children ? animated.find( "*" ).addBack() : animated;
10121
10122                 // map the animated objects to store the original styles.
10123                 allAnimations = allAnimations.map(function() {
10124                         var el = $( this );
10125                         return {
10126                                 el: el,
10127                                 start: getElementStyles( this )
10128                         };
10129                 });
10130
10131                 // apply class change
10132                 applyClassChange = function() {
10133                         $.each( classAnimationActions, function(i, action) {
10134                                 if ( value[ action ] ) {
10135                                         animated[ action + "Class" ]( value[ action ] );
10136                                 }
10137                         });
10138                 };
10139                 applyClassChange();
10140
10141                 // map all animated objects again - calculate new styles and diff
10142                 allAnimations = allAnimations.map(function() {
10143                         this.end = getElementStyles( this.el[ 0 ] );
10144                         this.diff = styleDifference( this.start, this.end );
10145                         return this;
10146                 });
10147
10148                 // apply original class
10149                 animated.attr( "class", baseClass );
10150
10151                 // map all animated objects again - this time collecting a promise
10152                 allAnimations = allAnimations.map(function() {
10153                         var styleInfo = this,
10154                                 dfd = $.Deferred(),
10155                                 opts = $.extend({}, o, {
10156                                         queue: false,
10157                                         complete: function() {
10158                                                 dfd.resolve( styleInfo );
10159                                         }
10160                                 });
10161
10162                         this.el.animate( this.diff, opts );
10163                         return dfd.promise();
10164                 });
10165
10166                 // once all animations have completed:
10167                 $.when.apply( $, allAnimations.get() ).done(function() {
10168
10169                         // set the final class
10170                         applyClassChange();
10171
10172                         // for each animated element,
10173                         // clear all css properties that were animated
10174                         $.each( arguments, function() {
10175                                 var el = this.el;
10176                                 $.each( this.diff, function(key) {
10177                                         el.css( key, "" );
10178                                 });
10179                         });
10180
10181                         // this is guarnteed to be there if you use jQuery.speed()
10182                         // it also handles dequeuing the next anim...
10183                         o.complete.call( animated[ 0 ] );
10184                 });
10185         });
10186 };
10187
10188 $.fn.extend({
10189         addClass: (function( orig ) {
10190                 return function( classNames, speed, easing, callback ) {
10191                         return speed ?
10192                                 $.effects.animateClass.call( this,
10193                                         { add: classNames }, speed, easing, callback ) :
10194                                 orig.apply( this, arguments );
10195                 };
10196         })( $.fn.addClass ),
10197
10198         removeClass: (function( orig ) {
10199                 return function( classNames, speed, easing, callback ) {
10200                         return arguments.length > 1 ?
10201                                 $.effects.animateClass.call( this,
10202                                         { remove: classNames }, speed, easing, callback ) :
10203                                 orig.apply( this, arguments );
10204                 };
10205         })( $.fn.removeClass ),
10206
10207         toggleClass: (function( orig ) {
10208                 return function( classNames, force, speed, easing, callback ) {
10209                         if ( typeof force === "boolean" || force === undefined ) {
10210                                 if ( !speed ) {
10211                                         // without speed parameter
10212                                         return orig.apply( this, arguments );
10213                                 } else {
10214                                         return $.effects.animateClass.call( this,
10215                                                 (force ? { add: classNames } : { remove: classNames }),
10216                                                 speed, easing, callback );
10217                                 }
10218                         } else {
10219                                 // without force parameter
10220                                 return $.effects.animateClass.call( this,
10221                                         { toggle: classNames }, force, speed, easing );
10222                         }
10223                 };
10224         })( $.fn.toggleClass ),
10225
10226         switchClass: function( remove, add, speed, easing, callback) {
10227                 return $.effects.animateClass.call( this, {
10228                         add: add,
10229                         remove: remove
10230                 }, speed, easing, callback );
10231         }
10232 });
10233
10234 })();
10235
10236 /******************************************************************************/
10237 /*********************************** EFFECTS **********************************/
10238 /******************************************************************************/
10239
10240 (function() {
10241
10242 $.extend( $.effects, {
10243         version: "1.11.4",
10244
10245         // Saves a set of properties in a data storage
10246         save: function( element, set ) {
10247                 for ( var i = 0; i < set.length; i++ ) {
10248                         if ( set[ i ] !== null ) {
10249                                 element.data( dataSpace + set[ i ], element[ 0 ].style[ set[ i ] ] );
10250                         }
10251                 }
10252         },
10253
10254         // Restores a set of previously saved properties from a data storage
10255         restore: function( element, set ) {
10256                 var val, i;
10257                 for ( i = 0; i < set.length; i++ ) {
10258                         if ( set[ i ] !== null ) {
10259                                 val = element.data( dataSpace + set[ i ] );
10260                                 // support: jQuery 1.6.2
10261                                 // http://bugs.jquery.com/ticket/9917
10262                                 // jQuery 1.6.2 incorrectly returns undefined for any falsy value.
10263                                 // We can't differentiate between "" and 0 here, so we just assume
10264                                 // empty string since it's likely to be a more common value...
10265                                 if ( val === undefined ) {
10266                                         val = "";
10267                                 }
10268                                 element.css( set[ i ], val );
10269                         }
10270                 }
10271         },
10272
10273         setMode: function( el, mode ) {
10274                 if (mode === "toggle") {
10275                         mode = el.is( ":hidden" ) ? "show" : "hide";
10276                 }
10277                 return mode;
10278         },
10279
10280         // Translates a [top,left] array into a baseline value
10281         // this should be a little more flexible in the future to handle a string & hash
10282         getBaseline: function( origin, original ) {
10283                 var y, x;
10284                 switch ( origin[ 0 ] ) {
10285                         case "top": y = 0; break;
10286                         case "middle": y = 0.5; break;
10287                         case "bottom": y = 1; break;
10288                         default: y = origin[ 0 ] / original.height;
10289                 }
10290                 switch ( origin[ 1 ] ) {
10291                         case "left": x = 0; break;
10292                         case "center": x = 0.5; break;
10293                         case "right": x = 1; break;
10294                         default: x = origin[ 1 ] / original.width;
10295                 }
10296                 return {
10297                         x: x,
10298                         y: y
10299                 };
10300         },
10301
10302         // Wraps the element around a wrapper that copies position properties
10303         createWrapper: function( element ) {
10304
10305                 // if the element is already wrapped, return it
10306                 if ( element.parent().is( ".ui-effects-wrapper" )) {
10307                         return element.parent();
10308                 }
10309
10310                 // wrap the element
10311                 var props = {
10312                                 width: element.outerWidth(true),
10313                                 height: element.outerHeight(true),
10314                                 "float": element.css( "float" )
10315                         },
10316                         wrapper = $( "<div></div>" )
10317                                 .addClass( "ui-effects-wrapper" )
10318                                 .css({
10319                                         fontSize: "100%",
10320                                         background: "transparent",
10321                                         border: "none",
10322                                         margin: 0,
10323                                         padding: 0
10324                                 }),
10325                         // Store the size in case width/height are defined in % - Fixes #5245
10326                         size = {
10327                                 width: element.width(),
10328                                 height: element.height()
10329                         },
10330                         active = document.activeElement;
10331
10332                 // support: Firefox
10333                 // Firefox incorrectly exposes anonymous content
10334                 // https://bugzilla.mozilla.org/show_bug.cgi?id=561664
10335                 try {
10336                         active.id;
10337                 } catch ( e ) {
10338                         active = document.body;
10339                 }
10340
10341                 element.wrap( wrapper );
10342
10343                 // Fixes #7595 - Elements lose focus when wrapped.
10344                 if ( element[ 0 ] === active || $.contains( element[ 0 ], active ) ) {
10345                         $( active ).focus();
10346                 }
10347
10348                 wrapper = element.parent(); //Hotfix for jQuery 1.4 since some change in wrap() seems to actually lose the reference to the wrapped element
10349
10350                 // transfer positioning properties to the wrapper
10351                 if ( element.css( "position" ) === "static" ) {
10352                         wrapper.css({ position: "relative" });
10353                         element.css({ position: "relative" });
10354                 } else {
10355                         $.extend( props, {
10356                                 position: element.css( "position" ),
10357                                 zIndex: element.css( "z-index" )
10358                         });
10359                         $.each([ "top", "left", "bottom", "right" ], function(i, pos) {
10360                                 props[ pos ] = element.css( pos );
10361                                 if ( isNaN( parseInt( props[ pos ], 10 ) ) ) {
10362                                         props[ pos ] = "auto";
10363                                 }
10364                         });
10365                         element.css({
10366                                 position: "relative",
10367                                 top: 0,
10368                                 left: 0,
10369                                 right: "auto",
10370                                 bottom: "auto"
10371                         });
10372                 }
10373                 element.css(size);
10374
10375                 return wrapper.css( props ).show();
10376         },
10377
10378         removeWrapper: function( element ) {
10379                 var active = document.activeElement;
10380
10381                 if ( element.parent().is( ".ui-effects-wrapper" ) ) {
10382                         element.parent().replaceWith( element );
10383
10384                         // Fixes #7595 - Elements lose focus when wrapped.
10385                         if ( element[ 0 ] === active || $.contains( element[ 0 ], active ) ) {
10386                                 $( active ).focus();
10387                         }
10388                 }
10389
10390                 return element;
10391         },
10392
10393         setTransition: function( element, list, factor, value ) {
10394                 value = value || {};
10395                 $.each( list, function( i, x ) {
10396                         var unit = element.cssUnit( x );
10397                         if ( unit[ 0 ] > 0 ) {
10398                                 value[ x ] = unit[ 0 ] * factor + unit[ 1 ];
10399                         }
10400                 });
10401                 return value;
10402         }
10403 });
10404
10405 // return an effect options object for the given parameters:
10406 function _normalizeArguments( effect, options, speed, callback ) {
10407
10408         // allow passing all options as the first parameter
10409         if ( $.isPlainObject( effect ) ) {
10410                 options = effect;
10411                 effect = effect.effect;
10412         }
10413
10414         // convert to an object
10415         effect = { effect: effect };
10416
10417         // catch (effect, null, ...)
10418         if ( options == null ) {
10419                 options = {};
10420         }
10421
10422         // catch (effect, callback)
10423         if ( $.isFunction( options ) ) {
10424                 callback = options;
10425                 speed = null;
10426                 options = {};
10427         }
10428
10429         // catch (effect, speed, ?)
10430         if ( typeof options === "number" || $.fx.speeds[ options ] ) {
10431                 callback = speed;
10432                 speed = options;
10433                 options = {};
10434         }
10435
10436         // catch (effect, options, callback)
10437         if ( $.isFunction( speed ) ) {
10438                 callback = speed;
10439                 speed = null;
10440         }
10441
10442         // add options to effect
10443         if ( options ) {
10444                 $.extend( effect, options );
10445         }
10446
10447         speed = speed || options.duration;
10448         effect.duration = $.fx.off ? 0 :
10449                 typeof speed === "number" ? speed :
10450                 speed in $.fx.speeds ? $.fx.speeds[ speed ] :
10451                 $.fx.speeds._default;
10452
10453         effect.complete = callback || options.complete;
10454
10455         return effect;
10456 }
10457
10458 function standardAnimationOption( option ) {
10459         // Valid standard speeds (nothing, number, named speed)
10460         if ( !option || typeof option === "number" || $.fx.speeds[ option ] ) {
10461                 return true;
10462         }
10463
10464         // Invalid strings - treat as "normal" speed
10465         if ( typeof option === "string" && !$.effects.effect[ option ] ) {
10466                 return true;
10467         }
10468
10469         // Complete callback
10470         if ( $.isFunction( option ) ) {
10471                 return true;
10472         }
10473
10474         // Options hash (but not naming an effect)
10475         if ( typeof option === "object" && !option.effect ) {
10476                 return true;
10477         }
10478
10479         // Didn't match any standard API
10480         return false;
10481 }
10482
10483 $.fn.extend({
10484         effect: function( /* effect, options, speed, callback */ ) {
10485                 var args = _normalizeArguments.apply( this, arguments ),
10486                         mode = args.mode,
10487                         queue = args.queue,
10488                         effectMethod = $.effects.effect[ args.effect ];
10489
10490                 if ( $.fx.off || !effectMethod ) {
10491                         // delegate to the original method (e.g., .show()) if possible
10492                         if ( mode ) {
10493                                 return this[ mode ]( args.duration, args.complete );
10494                         } else {
10495                                 return this.each( function() {
10496                                         if ( args.complete ) {
10497                                                 args.complete.call( this );
10498                                         }
10499                                 });
10500                         }
10501                 }
10502
10503                 function run( next ) {
10504                         var elem = $( this ),
10505                                 complete = args.complete,
10506                                 mode = args.mode;
10507
10508                         function done() {
10509                                 if ( $.isFunction( complete ) ) {
10510                                         complete.call( elem[0] );
10511                                 }
10512                                 if ( $.isFunction( next ) ) {
10513                                         next();
10514                                 }
10515                         }
10516
10517                         // If the element already has the correct final state, delegate to
10518                         // the core methods so the internal tracking of "olddisplay" works.
10519                         if ( elem.is( ":hidden" ) ? mode === "hide" : mode === "show" ) {
10520                                 elem[ mode ]();
10521                                 done();
10522                         } else {
10523                                 effectMethod.call( elem[0], args, done );
10524                         }
10525                 }
10526
10527                 return queue === false ? this.each( run ) : this.queue( queue || "fx", run );
10528         },
10529
10530         show: (function( orig ) {
10531                 return function( option ) {
10532                         if ( standardAnimationOption( option ) ) {
10533                                 return orig.apply( this, arguments );
10534                         } else {
10535                                 var args = _normalizeArguments.apply( this, arguments );
10536                                 args.mode = "show";
10537                                 return this.effect.call( this, args );
10538                         }
10539                 };
10540         })( $.fn.show ),
10541
10542         hide: (function( orig ) {
10543                 return function( option ) {
10544                         if ( standardAnimationOption( option ) ) {
10545                                 return orig.apply( this, arguments );
10546                         } else {
10547                                 var args = _normalizeArguments.apply( this, arguments );
10548                                 args.mode = "hide";
10549                                 return this.effect.call( this, args );
10550                         }
10551                 };
10552         })( $.fn.hide ),
10553
10554         toggle: (function( orig ) {
10555                 return function( option ) {
10556                         if ( standardAnimationOption( option ) || typeof option === "boolean" ) {
10557                                 return orig.apply( this, arguments );
10558                         } else {
10559                                 var args = _normalizeArguments.apply( this, arguments );
10560                                 args.mode = "toggle";
10561                                 return this.effect.call( this, args );
10562                         }
10563                 };
10564         })( $.fn.toggle ),
10565
10566         // helper functions
10567         cssUnit: function(key) {
10568                 var style = this.css( key ),
10569                         val = [];
10570
10571                 $.each( [ "em", "px", "%", "pt" ], function( i, unit ) {
10572                         if ( style.indexOf( unit ) > 0 ) {
10573                                 val = [ parseFloat( style ), unit ];
10574                         }
10575                 });
10576                 return val;
10577         }
10578 });
10579
10580 })();
10581
10582 /******************************************************************************/
10583 /*********************************** EASING ***********************************/
10584 /******************************************************************************/
10585
10586 (function() {
10587
10588 // based on easing equations from Robert Penner (http://www.robertpenner.com/easing)
10589
10590 var baseEasings = {};
10591
10592 $.each( [ "Quad", "Cubic", "Quart", "Quint", "Expo" ], function( i, name ) {
10593         baseEasings[ name ] = function( p ) {
10594                 return Math.pow( p, i + 2 );
10595         };
10596 });
10597
10598 $.extend( baseEasings, {
10599         Sine: function( p ) {
10600                 return 1 - Math.cos( p * Math.PI / 2 );
10601         },
10602         Circ: function( p ) {
10603                 return 1 - Math.sqrt( 1 - p * p );
10604         },
10605         Elastic: function( p ) {
10606                 return p === 0 || p === 1 ? p :
10607                         -Math.pow( 2, 8 * (p - 1) ) * Math.sin( ( (p - 1) * 80 - 7.5 ) * Math.PI / 15 );
10608         },
10609         Back: function( p ) {
10610                 return p * p * ( 3 * p - 2 );
10611         },
10612         Bounce: function( p ) {
10613                 var pow2,
10614                         bounce = 4;
10615
10616                 while ( p < ( ( pow2 = Math.pow( 2, --bounce ) ) - 1 ) / 11 ) {}
10617                 return 1 / Math.pow( 4, 3 - bounce ) - 7.5625 * Math.pow( ( pow2 * 3 - 2 ) / 22 - p, 2 );
10618         }
10619 });
10620
10621 $.each( baseEasings, function( name, easeIn ) {
10622         $.easing[ "easeIn" + name ] = easeIn;
10623         $.easing[ "easeOut" + name ] = function( p ) {
10624                 return 1 - easeIn( 1 - p );
10625         };
10626         $.easing[ "easeInOut" + name ] = function( p ) {
10627                 return p < 0.5 ?
10628                         easeIn( p * 2 ) / 2 :
10629                         1 - easeIn( p * -2 + 2 ) / 2;
10630         };
10631 });
10632
10633 })();
10634
10635 var effect = $.effects;
10636
10637
10638 /*!
10639  * jQuery UI Effects Blind 1.11.4
10640  * http://jqueryui.com
10641  *
10642  * Copyright jQuery Foundation and other contributors
10643  * Released under the MIT license.
10644  * http://jquery.org/license
10645  *
10646  * http://api.jqueryui.com/blind-effect/
10647  */
10648
10649
10650 var effectBlind = $.effects.effect.blind = function( o, done ) {
10651         // Create element
10652         var el = $( this ),
10653                 rvertical = /up|down|vertical/,
10654                 rpositivemotion = /up|left|vertical|horizontal/,
10655                 props = [ "position", "top", "bottom", "left", "right", "height", "width" ],
10656                 mode = $.effects.setMode( el, o.mode || "hide" ),
10657                 direction = o.direction || "up",
10658                 vertical = rvertical.test( direction ),
10659                 ref = vertical ? "height" : "width",
10660                 ref2 = vertical ? "top" : "left",
10661                 motion = rpositivemotion.test( direction ),
10662                 animation = {},
10663                 show = mode === "show",
10664                 wrapper, distance, margin;
10665
10666         // if already wrapped, the wrapper's properties are my property. #6245
10667         if ( el.parent().is( ".ui-effects-wrapper" ) ) {
10668                 $.effects.save( el.parent(), props );
10669         } else {
10670                 $.effects.save( el, props );
10671         }
10672         el.show();
10673         wrapper = $.effects.createWrapper( el ).css({
10674                 overflow: "hidden"
10675         });
10676
10677         distance = wrapper[ ref ]();
10678         margin = parseFloat( wrapper.css( ref2 ) ) || 0;
10679
10680         animation[ ref ] = show ? distance : 0;
10681         if ( !motion ) {
10682                 el
10683                         .css( vertical ? "bottom" : "right", 0 )
10684                         .css( vertical ? "top" : "left", "auto" )
10685                         .css({ position: "absolute" });
10686
10687                 animation[ ref2 ] = show ? margin : distance + margin;
10688         }
10689
10690         // start at 0 if we are showing
10691         if ( show ) {
10692                 wrapper.css( ref, 0 );
10693                 if ( !motion ) {
10694                         wrapper.css( ref2, margin + distance );
10695                 }
10696         }
10697
10698         // Animate
10699         wrapper.animate( animation, {
10700                 duration: o.duration,
10701                 easing: o.easing,
10702                 queue: false,
10703                 complete: function() {
10704                         if ( mode === "hide" ) {
10705                                 el.hide();
10706                         }
10707                         $.effects.restore( el, props );
10708                         $.effects.removeWrapper( el );
10709                         done();
10710                 }
10711         });
10712 };
10713
10714
10715 /*!
10716  * jQuery UI Effects Bounce 1.11.4
10717  * http://jqueryui.com
10718  *
10719  * Copyright jQuery Foundation and other contributors
10720  * Released under the MIT license.
10721  * http://jquery.org/license
10722  *
10723  * http://api.jqueryui.com/bounce-effect/
10724  */
10725
10726
10727 var effectBounce = $.effects.effect.bounce = function( o, done ) {
10728         var el = $( this ),
10729                 props = [ "position", "top", "bottom", "left", "right", "height", "width" ],
10730
10731                 // defaults:
10732                 mode = $.effects.setMode( el, o.mode || "effect" ),
10733                 hide = mode === "hide",
10734                 show = mode === "show",
10735                 direction = o.direction || "up",
10736                 distance = o.distance,
10737                 times = o.times || 5,
10738
10739                 // number of internal animations
10740                 anims = times * 2 + ( show || hide ? 1 : 0 ),
10741                 speed = o.duration / anims,
10742                 easing = o.easing,
10743
10744                 // utility:
10745                 ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
10746                 motion = ( direction === "up" || direction === "left" ),
10747                 i,
10748                 upAnim,
10749                 downAnim,
10750
10751                 // we will need to re-assemble the queue to stack our animations in place
10752                 queue = el.queue(),
10753                 queuelen = queue.length;
10754
10755         // Avoid touching opacity to prevent clearType and PNG issues in IE
10756         if ( show || hide ) {
10757                 props.push( "opacity" );
10758         }
10759
10760         $.effects.save( el, props );
10761         el.show();
10762         $.effects.createWrapper( el ); // Create Wrapper
10763
10764         // default distance for the BIGGEST bounce is the outer Distance / 3
10765         if ( !distance ) {
10766                 distance = el[ ref === "top" ? "outerHeight" : "outerWidth" ]() / 3;
10767         }
10768
10769         if ( show ) {
10770                 downAnim = { opacity: 1 };
10771                 downAnim[ ref ] = 0;
10772
10773                 // if we are showing, force opacity 0 and set the initial position
10774                 // then do the "first" animation
10775                 el.css( "opacity", 0 )
10776                         .css( ref, motion ? -distance * 2 : distance * 2 )
10777                         .animate( downAnim, speed, easing );
10778         }
10779
10780         // start at the smallest distance if we are hiding
10781         if ( hide ) {
10782                 distance = distance / Math.pow( 2, times - 1 );
10783         }
10784
10785         downAnim = {};
10786         downAnim[ ref ] = 0;
10787         // Bounces up/down/left/right then back to 0 -- times * 2 animations happen here
10788         for ( i = 0; i < times; i++ ) {
10789                 upAnim = {};
10790                 upAnim[ ref ] = ( motion ? "-=" : "+=" ) + distance;
10791
10792                 el.animate( upAnim, speed, easing )
10793                         .animate( downAnim, speed, easing );
10794
10795                 distance = hide ? distance * 2 : distance / 2;
10796         }
10797
10798         // Last Bounce when Hiding
10799         if ( hide ) {
10800                 upAnim = { opacity: 0 };
10801                 upAnim[ ref ] = ( motion ? "-=" : "+=" ) + distance;
10802
10803                 el.animate( upAnim, speed, easing );
10804         }
10805
10806         el.queue(function() {
10807                 if ( hide ) {
10808                         el.hide();
10809                 }
10810                 $.effects.restore( el, props );
10811                 $.effects.removeWrapper( el );
10812                 done();
10813         });
10814
10815         // inject all the animations we just queued to be first in line (after "inprogress")
10816         if ( queuelen > 1) {
10817                 queue.splice.apply( queue,
10818                         [ 1, 0 ].concat( queue.splice( queuelen, anims + 1 ) ) );
10819         }
10820         el.dequeue();
10821
10822 };
10823
10824
10825 /*!
10826  * jQuery UI Effects Clip 1.11.4
10827  * http://jqueryui.com
10828  *
10829  * Copyright jQuery Foundation and other contributors
10830  * Released under the MIT license.
10831  * http://jquery.org/license
10832  *
10833  * http://api.jqueryui.com/clip-effect/
10834  */
10835
10836
10837 var effectClip = $.effects.effect.clip = function( o, done ) {
10838         // Create element
10839         var el = $( this ),
10840                 props = [ "position", "top", "bottom", "left", "right", "height", "width" ],
10841                 mode = $.effects.setMode( el, o.mode || "hide" ),
10842                 show = mode === "show",
10843                 direction = o.direction || "vertical",
10844                 vert = direction === "vertical",
10845                 size = vert ? "height" : "width",
10846                 position = vert ? "top" : "left",
10847                 animation = {},
10848                 wrapper, animate, distance;
10849
10850         // Save & Show
10851         $.effects.save( el, props );
10852         el.show();
10853
10854         // Create Wrapper
10855         wrapper = $.effects.createWrapper( el ).css({
10856                 overflow: "hidden"
10857         });
10858         animate = ( el[0].tagName === "IMG" ) ? wrapper : el;
10859         distance = animate[ size ]();
10860
10861         // Shift
10862         if ( show ) {
10863                 animate.css( size, 0 );
10864                 animate.css( position, distance / 2 );
10865         }
10866
10867         // Create Animation Object:
10868         animation[ size ] = show ? distance : 0;
10869         animation[ position ] = show ? 0 : distance / 2;
10870
10871         // Animate
10872         animate.animate( animation, {
10873                 queue: false,
10874                 duration: o.duration,
10875                 easing: o.easing,
10876                 complete: function() {
10877                         if ( !show ) {
10878                                 el.hide();
10879                         }
10880                         $.effects.restore( el, props );
10881                         $.effects.removeWrapper( el );
10882                         done();
10883                 }
10884         });
10885
10886 };
10887
10888
10889 /*!
10890  * jQuery UI Effects Drop 1.11.4
10891  * http://jqueryui.com
10892  *
10893  * Copyright jQuery Foundation and other contributors
10894  * Released under the MIT license.
10895  * http://jquery.org/license
10896  *
10897  * http://api.jqueryui.com/drop-effect/
10898  */
10899
10900
10901 var effectDrop = $.effects.effect.drop = function( o, done ) {
10902
10903         var el = $( this ),
10904                 props = [ "position", "top", "bottom", "left", "right", "opacity", "height", "width" ],
10905                 mode = $.effects.setMode( el, o.mode || "hide" ),
10906                 show = mode === "show",
10907                 direction = o.direction || "left",
10908                 ref = ( direction === "up" || direction === "down" ) ? "top" : "left",
10909                 motion = ( direction === "up" || direction === "left" ) ? "pos" : "neg",
10910                 animation = {
10911                         opacity: show ? 1 : 0
10912                 },
10913                 distance;
10914
10915         // Adjust
10916         $.effects.save( el, props );
10917         el.show();
10918         $.effects.createWrapper( el );
10919
10920         distance = o.distance || el[ ref === "top" ? "outerHeight" : "outerWidth" ]( true ) / 2;
10921
10922         if ( show ) {
10923                 el
10924                         .css( "opacity", 0 )
10925                         .css( ref, motion === "pos" ? -distance : distance );
10926         }
10927
10928         // Animation
10929         animation[ ref ] = ( show ?
10930                 ( motion === "pos" ? "+=" : "-=" ) :
10931                 ( motion === "pos" ? "-=" : "+=" ) ) +
10932                 distance;
10933
10934         // Animate
10935         el.animate( animation, {
10936                 queue: false,
10937                 duration: o.duration,
10938                 easing: o.easing,
10939                 complete: function() {
10940                         if ( mode === "hide" ) {
10941                                 el.hide();
10942                         }
10943                         $.effects.restore( el, props );
10944                         $.effects.removeWrapper( el );
10945                         done();
10946                 }
10947         });
10948 };
10949
10950
10951 /*!
10952  * jQuery UI Effects Explode 1.11.4
10953  * http://jqueryui.com
10954  *
10955  * Copyright jQuery Foundation and other contributors
10956  * Released under the MIT license.
10957  * http://jquery.org/license
10958  *
10959  * http://api.jqueryui.com/explode-effect/
10960  */
10961
10962
10963 var effectExplode = $.effects.effect.explode = function( o, done ) {
10964
10965         var rows = o.pieces ? Math.round( Math.sqrt( o.pieces ) ) : 3,
10966                 cells = rows,
10967                 el = $( this ),
10968                 mode = $.effects.setMode( el, o.mode || "hide" ),
10969                 show = mode === "show",
10970
10971                 // show and then visibility:hidden the element before calculating offset
10972                 offset = el.show().css( "visibility", "hidden" ).offset(),
10973
10974                 // width and height of a piece
10975                 width = Math.ceil( el.outerWidth() / cells ),
10976                 height = Math.ceil( el.outerHeight() / rows ),
10977                 pieces = [],
10978
10979                 // loop
10980                 i, j, left, top, mx, my;
10981
10982         // children animate complete:
10983         function childComplete() {
10984                 pieces.push( this );
10985                 if ( pieces.length === rows * cells ) {
10986                         animComplete();
10987                 }
10988         }
10989
10990         // clone the element for each row and cell.
10991         for ( i = 0; i < rows ; i++ ) { // ===>
10992                 top = offset.top + i * height;
10993                 my = i - ( rows - 1 ) / 2 ;
10994
10995                 for ( j = 0; j < cells ; j++ ) { // |||
10996                         left = offset.left + j * width;
10997                         mx = j - ( cells - 1 ) / 2 ;
10998
10999                         // Create a clone of the now hidden main element that will be absolute positioned
11000                         // within a wrapper div off the -left and -top equal to size of our pieces
11001                         el
11002                                 .clone()
11003                                 .appendTo( "body" )
11004                                 .wrap( "<div></div>" )
11005                                 .css({
11006                                         position: "absolute",
11007                                         visibility: "visible",
11008                                         left: -j * width,
11009                                         top: -i * height
11010                                 })
11011
11012                         // select the wrapper - make it overflow: hidden and absolute positioned based on
11013                         // where the original was located +left and +top equal to the size of pieces
11014                                 .parent()
11015                                 .addClass( "ui-effects-explode" )
11016                                 .css({
11017                                         position: "absolute",
11018                                         overflow: "hidden",
11019                                         width: width,
11020                                         height: height,
11021                                         left: left + ( show ? mx * width : 0 ),
11022                                         top: top + ( show ? my * height : 0 ),
11023                                         opacity: show ? 0 : 1
11024                                 }).animate({
11025                                         left: left + ( show ? 0 : mx * width ),
11026                                         top: top + ( show ? 0 : my * height ),
11027                                         opacity: show ? 1 : 0
11028                                 }, o.duration || 500, o.easing, childComplete );
11029                 }
11030         }
11031
11032         function animComplete() {
11033                 el.css({
11034                         visibility: "visible"
11035                 });
11036                 $( pieces ).remove();
11037                 if ( !show ) {
11038                         el.hide();
11039                 }
11040                 done();
11041         }
11042 };
11043
11044
11045 /*!
11046  * jQuery UI Effects Fade 1.11.4
11047  * http://jqueryui.com
11048  *
11049  * Copyright jQuery Foundation and other contributors
11050  * Released under the MIT license.
11051  * http://jquery.org/license
11052  *
11053  * http://api.jqueryui.com/fade-effect/
11054  */
11055
11056
11057 var effectFade = $.effects.effect.fade = function( o, done ) {
11058         var el = $( this ),
11059                 mode = $.effects.setMode( el, o.mode || "toggle" );
11060
11061         el.animate({
11062                 opacity: mode
11063         }, {
11064                 queue: false,
11065                 duration: o.duration,
11066                 easing: o.easing,
11067                 complete: done
11068         });
11069 };
11070
11071
11072 /*!
11073  * jQuery UI Effects Fold 1.11.4
11074  * http://jqueryui.com
11075  *
11076  * Copyright jQuery Foundation and other contributors
11077  * Released under the MIT license.
11078  * http://jquery.org/license
11079  *
11080  * http://api.jqueryui.com/fold-effect/
11081  */
11082
11083
11084 var effectFold = $.effects.effect.fold = function( o, done ) {
11085
11086         // Create element
11087         var el = $( this ),
11088                 props = [ "position", "top", "bottom", "left", "right", "height", "width" ],
11089                 mode = $.effects.setMode( el, o.mode || "hide" ),
11090                 show = mode === "show",
11091                 hide = mode === "hide",
11092                 size = o.size || 15,
11093                 percent = /([0-9]+)%/.exec( size ),
11094                 horizFirst = !!o.horizFirst,
11095                 widthFirst = show !== horizFirst,
11096                 ref = widthFirst ? [ "width", "height" ] : [ "height", "width" ],
11097                 duration = o.duration / 2,
11098                 wrapper, distance,
11099                 animation1 = {},
11100                 animation2 = {};
11101
11102         $.effects.save( el, props );
11103         el.show();
11104
11105         // Create Wrapper
11106         wrapper = $.effects.createWrapper( el ).css({
11107                 overflow: "hidden"
11108         });
11109         distance = widthFirst ?
11110                 [ wrapper.width(), wrapper.height() ] :
11111                 [ wrapper.height(), wrapper.width() ];
11112
11113         if ( percent ) {
11114                 size = parseInt( percent[ 1 ], 10 ) / 100 * distance[ hide ? 0 : 1 ];
11115         }
11116         if ( show ) {
11117                 wrapper.css( horizFirst ? {
11118                         height: 0,
11119                         width: size
11120                 } : {
11121                         height: size,
11122                         width: 0
11123                 });
11124         }
11125
11126         // Animation
11127         animation1[ ref[ 0 ] ] = show ? distance[ 0 ] : size;
11128         animation2[ ref[ 1 ] ] = show ? distance[ 1 ] : 0;
11129
11130         // Animate
11131         wrapper
11132                 .animate( animation1, duration, o.easing )
11133                 .animate( animation2, duration, o.easing, function() {
11134                         if ( hide ) {
11135                                 el.hide();
11136                         }
11137                         $.effects.restore( el, props );
11138                         $.effects.removeWrapper( el );
11139                         done();
11140                 });
11141
11142 };
11143
11144
11145 /*!
11146  * jQuery UI Effects Highlight 1.11.4
11147  * http://jqueryui.com
11148  *
11149  * Copyright jQuery Foundation and other contributors
11150  * Released under the MIT license.
11151  * http://jquery.org/license
11152  *
11153  * http://api.jqueryui.com/highlight-effect/
11154  */
11155
11156
11157 var effectHighlight = $.effects.effect.highlight = function( o, done ) {
11158         var elem = $( this ),
11159                 props = [ "backgroundImage", "backgroundColor", "opacity" ],
11160                 mode = $.effects.setMode( elem, o.mode || "show" ),
11161                 animation = {
11162                         backgroundColor: elem.css( "backgroundColor" )
11163                 };
11164
11165         if (mode === "hide") {
11166                 animation.opacity = 0;
11167         }
11168
11169         $.effects.save( elem, props );
11170
11171         elem
11172                 .show()
11173                 .css({
11174                         backgroundImage: "none",
11175                         backgroundColor: o.color || "#ffff99"
11176                 })
11177                 .animate( animation, {
11178                         queue: false,
11179                         duration: o.duration,
11180                         easing: o.easing,
11181                         complete: function() {
11182                                 if ( mode === "hide" ) {
11183                                         elem.hide();
11184                                 }
11185                                 $.effects.restore( elem, props );
11186                                 done();
11187                         }
11188                 });
11189 };
11190
11191
11192 /*!
11193  * jQuery UI Effects Size 1.11.4
11194  * http://jqueryui.com
11195  *
11196  * Copyright jQuery Foundation and other contributors
11197  * Released under the MIT license.
11198  * http://jquery.org/license
11199  *
11200  * http://api.jqueryui.com/size-effect/
11201  */
11202
11203
11204 var effectSize = $.effects.effect.size = function( o, done ) {
11205
11206         // Create element
11207         var original, baseline, factor,
11208                 el = $( this ),
11209                 props0 = [ "position", "top", "bottom", "left", "right", "width", "height", "overflow", "opacity" ],
11210
11211                 // Always restore
11212                 props1 = [ "position", "top", "bottom", "left", "right", "overflow", "opacity" ],
11213
11214                 // Copy for children
11215                 props2 = [ "width", "height", "overflow" ],
11216                 cProps = [ "fontSize" ],
11217                 vProps = [ "borderTopWidth", "borderBottomWidth", "paddingTop", "paddingBottom" ],
11218                 hProps = [ "borderLeftWidth", "borderRightWidth", "paddingLeft", "paddingRight" ],
11219
11220                 // Set options
11221                 mode = $.effects.setMode( el, o.mode || "effect" ),
11222                 restore = o.restore || mode !== "effect",
11223                 scale = o.scale || "both",
11224                 origin = o.origin || [ "middle", "center" ],
11225                 position = el.css( "position" ),
11226                 props = restore ? props0 : props1,
11227                 zero = {
11228                         height: 0,
11229                         width: 0,
11230                         outerHeight: 0,
11231                         outerWidth: 0
11232                 };
11233
11234         if ( mode === "show" ) {
11235                 el.show();
11236         }
11237         original = {
11238                 height: el.height(),
11239                 width: el.width(),
11240                 outerHeight: el.outerHeight(),
11241                 outerWidth: el.outerWidth()
11242         };
11243
11244         if ( o.mode === "toggle" && mode === "show" ) {
11245                 el.from = o.to || zero;
11246                 el.to = o.from || original;
11247         } else {
11248                 el.from = o.from || ( mode === "show" ? zero : original );
11249                 el.to = o.to || ( mode === "hide" ? zero : original );
11250         }
11251
11252         // Set scaling factor
11253         factor = {
11254                 from: {
11255                         y: el.from.height / original.height,
11256                         x: el.from.width / original.width
11257                 },
11258                 to: {
11259                         y: el.to.height / original.height,
11260                         x: el.to.width / original.width
11261                 }
11262         };
11263
11264         // Scale the css box
11265         if ( scale === "box" || scale === "both" ) {
11266
11267                 // Vertical props scaling
11268                 if ( factor.from.y !== factor.to.y ) {
11269                         props = props.concat( vProps );
11270                         el.from = $.effects.setTransition( el, vProps, factor.from.y, el.from );
11271                         el.to = $.effects.setTransition( el, vProps, factor.to.y, el.to );
11272                 }
11273
11274                 // Horizontal props scaling
11275                 if ( factor.from.x !== factor.to.x ) {
11276                         props = props.concat( hProps );
11277                         el.from = $.effects.setTransition( el, hProps, factor.from.x, el.from );
11278                         el.to = $.effects.setTransition( el, hProps, factor.to.x, el.to );
11279                 }
11280         }
11281
11282         // Scale the content
11283         if ( scale === "content" || scale === "both" ) {
11284
11285                 // Vertical props scaling
11286                 if ( factor.from.y !== factor.to.y ) {
11287                         props = props.concat( cProps ).concat( props2 );
11288                         el.from = $.effects.setTransition( el, cProps, factor.from.y, el.from );
11289                         el.to = $.effects.setTransition( el, cProps, factor.to.y, el.to );
11290                 }
11291         }
11292
11293         $.effects.save( el, props );
11294         el.show();
11295         $.effects.createWrapper( el );
11296         el.css( "overflow", "hidden" ).css( el.from );
11297
11298         // Adjust
11299         if (origin) { // Calculate baseline shifts
11300                 baseline = $.effects.getBaseline( origin, original );
11301                 el.from.top = ( original.outerHeight - el.outerHeight() ) * baseline.y;
11302                 el.from.left = ( original.outerWidth - el.outerWidth() ) * baseline.x;
11303                 el.to.top = ( original.outerHeight - el.to.outerHeight ) * baseline.y;
11304                 el.to.left = ( original.outerWidth - el.to.outerWidth ) * baseline.x;
11305         }
11306         el.css( el.from ); // set top & left
11307
11308         // Animate
11309         if ( scale === "content" || scale === "both" ) { // Scale the children
11310
11311                 // Add margins/font-size
11312                 vProps = vProps.concat([ "marginTop", "marginBottom" ]).concat(cProps);
11313                 hProps = hProps.concat([ "marginLeft", "marginRight" ]);
11314                 props2 = props0.concat(vProps).concat(hProps);
11315
11316                 el.find( "*[width]" ).each( function() {
11317                         var child = $( this ),
11318                                 c_original = {
11319                                         height: child.height(),
11320                                         width: child.width(),
11321                                         outerHeight: child.outerHeight(),
11322                                         outerWidth: child.outerWidth()
11323                                 };
11324                         if (restore) {
11325                                 $.effects.save(child, props2);
11326                         }
11327
11328                         child.from = {
11329                                 height: c_original.height * factor.from.y,
11330                                 width: c_original.width * factor.from.x,
11331                                 outerHeight: c_original.outerHeight * factor.from.y,
11332                                 outerWidth: c_original.outerWidth * factor.from.x
11333                         };
11334                         child.to = {
11335                                 height: c_original.height * factor.to.y,
11336                                 width: c_original.width * factor.to.x,
11337                                 outerHeight: c_original.height * factor.to.y,
11338                                 outerWidth: c_original.width * factor.to.x
11339                         };
11340
11341                         // Vertical props scaling
11342                         if ( factor.from.y !== factor.to.y ) {
11343                                 child.from = $.effects.setTransition( child, vProps, factor.from.y, child.from );
11344                                 child.to = $.effects.setTransition( child, vProps, factor.to.y, child.to );
11345                         }
11346
11347                         // Horizontal props scaling
11348                         if ( factor.from.x !== factor.to.x ) {
11349                                 child.from = $.effects.setTransition( child, hProps, factor.from.x, child.from );
11350                                 child.to = $.effects.setTransition( child, hProps, factor.to.x, child.to );
11351                         }
11352
11353                         // Animate children
11354                         child.css( child.from );
11355                         child.animate( child.to, o.duration, o.easing, function() {
11356
11357                                 // Restore children
11358                                 if ( restore ) {
11359                                         $.effects.restore( child, props2 );
11360                                 }
11361                         });
11362                 });
11363         }
11364
11365         // Animate
11366         el.animate( el.to, {
11367                 queue: false,
11368                 duration: o.duration,
11369                 easing: o.easing,
11370                 complete: function() {
11371                         if ( el.to.opacity === 0 ) {
11372                                 el.css( "opacity", el.from.opacity );
11373                         }
11374                         if ( mode === "hide" ) {
11375                                 el.hide();
11376                         }
11377                         $.effects.restore( el, props );
11378                         if ( !restore ) {
11379
11380                                 // we need to calculate our new positioning based on the scaling
11381                                 if ( position === "static" ) {
11382                                         el.css({
11383                                                 position: "relative",
11384                                                 top: el.to.top,
11385                                                 left: el.to.left
11386                                         });
11387                                 } else {
11388                                         $.each([ "top", "left" ], function( idx, pos ) {
11389                                                 el.css( pos, function( _, str ) {
11390                                                         var val = parseInt( str, 10 ),
11391                                                                 toRef = idx ? el.to.left : el.to.top;
11392
11393                                                         // if original was "auto", recalculate the new value from wrapper
11394                                                         if ( str === "auto" ) {
11395                                                                 return toRef + "px";
11396                                                         }
11397
11398                                                         return val + toRef + "px";
11399                                                 });
11400                                         });
11401                                 }
11402                         }
11403
11404                         $.effects.removeWrapper( el );
11405                         done();
11406                 }
11407         });
11408
11409 };
11410
11411
11412 /*!
11413  * jQuery UI Effects Scale 1.11.4
11414  * http://jqueryui.com
11415  *
11416  * Copyright jQuery Foundation and other contributors
11417  * Released under the MIT license.
11418  * http://jquery.org/license
11419  *
11420  * http://api.jqueryui.com/scale-effect/
11421  */
11422
11423
11424 var effectScale = $.effects.effect.scale = function( o, done ) {
11425
11426         // Create element
11427         var el = $( this ),
11428                 options = $.extend( true, {}, o ),
11429                 mode = $.effects.setMode( el, o.mode || "effect" ),
11430                 percent = parseInt( o.percent, 10 ) ||
11431                         ( parseInt( o.percent, 10 ) === 0 ? 0 : ( mode === "hide" ? 0 : 100 ) ),
11432                 direction = o.direction || "both",
11433                 origin = o.origin,
11434                 original = {
11435                         height: el.height(),
11436                         width: el.width(),
11437                         outerHeight: el.outerHeight(),
11438                         outerWidth: el.outerWidth()
11439                 },
11440                 factor = {
11441                         y: direction !== "horizontal" ? (percent / 100) : 1,
11442                         x: direction !== "vertical" ? (percent / 100) : 1
11443                 };
11444
11445         // We are going to pass this effect to the size effect:
11446         options.effect = "size";
11447         options.queue = false;
11448         options.complete = done;
11449
11450         // Set default origin and restore for show/hide
11451         if ( mode !== "effect" ) {
11452                 options.origin = origin || [ "middle", "center" ];
11453                 options.restore = true;
11454         }
11455
11456         options.from = o.from || ( mode === "show" ? {
11457                 height: 0,
11458                 width: 0,
11459                 outerHeight: 0,
11460                 outerWidth: 0
11461         } : original );
11462         options.to = {
11463                 height: original.height * factor.y,
11464                 width: original.width * factor.x,
11465                 outerHeight: original.outerHeight * factor.y,
11466                 outerWidth: original.outerWidth * factor.x
11467         };
11468
11469         // Fade option to support puff
11470         if ( options.fade ) {
11471                 if ( mode === "show" ) {
11472                         options.from.opacity = 0;
11473                         options.to.opacity = 1;
11474                 }
11475                 if ( mode === "hide" ) {
11476                         options.from.opacity = 1;
11477                         options.to.opacity = 0;
11478                 }
11479         }
11480
11481         // Animate
11482         el.effect( options );
11483
11484 };
11485
11486
11487 /*!
11488  * jQuery UI Effects Puff 1.11.4
11489  * http://jqueryui.com
11490  *
11491  * Copyright jQuery Foundation and other contributors
11492  * Released under the MIT license.
11493  * http://jquery.org/license
11494  *
11495  * http://api.jqueryui.com/puff-effect/
11496  */
11497
11498
11499 var effectPuff = $.effects.effect.puff = function( o, done ) {
11500         var elem = $( this ),
11501                 mode = $.effects.setMode( elem, o.mode || "hide" ),
11502                 hide = mode === "hide",
11503                 percent = parseInt( o.percent, 10 ) || 150,
11504                 factor = percent / 100,
11505                 original = {
11506                         height: elem.height(),
11507                         width: elem.width(),
11508                         outerHeight: elem.outerHeight(),
11509                         outerWidth: elem.outerWidth()
11510                 };
11511
11512         $.extend( o, {
11513                 effect: "scale",
11514                 queue: false,
11515                 fade: true,
11516                 mode: mode,
11517                 complete: done,
11518                 percent: hide ? percent : 100,
11519                 from: hide ?
11520                         original :
11521                         {
11522                                 height: original.height * factor,
11523                                 width: original.width * factor,
11524                                 outerHeight: original.outerHeight * factor,
11525                                 outerWidth: original.outerWidth * factor
11526                         }
11527         });
11528
11529         elem.effect( o );
11530 };
11531
11532
11533 /*!
11534  * jQuery UI Effects Pulsate 1.11.4
11535  * http://jqueryui.com
11536  *
11537  * Copyright jQuery Foundation and other contributors
11538  * Released under the MIT license.
11539  * http://jquery.org/license
11540  *
11541  * http://api.jqueryui.com/pulsate-effect/
11542  */
11543
11544
11545 var effectPulsate = $.effects.effect.pulsate = function( o, done ) {
11546         var elem = $( this ),
11547                 mode = $.effects.setMode( elem, o.mode || "show" ),
11548                 show = mode === "show",
11549                 hide = mode === "hide",
11550                 showhide = ( show || mode === "hide" ),
11551
11552                 // showing or hiding leaves of the "last" animation
11553                 anims = ( ( o.times || 5 ) * 2 ) + ( showhide ? 1 : 0 ),
11554                 duration = o.duration / anims,
11555                 animateTo = 0,
11556                 queue = elem.queue(),
11557                 queuelen = queue.length,
11558                 i;
11559
11560         if ( show || !elem.is(":visible")) {
11561                 elem.css( "opacity", 0 ).show();
11562                 animateTo = 1;
11563         }
11564
11565         // anims - 1 opacity "toggles"
11566         for ( i = 1; i < anims; i++ ) {
11567                 elem.animate({
11568                         opacity: animateTo
11569                 }, duration, o.easing );
11570                 animateTo = 1 - animateTo;
11571         }
11572
11573         elem.animate({
11574                 opacity: animateTo
11575         }, duration, o.easing);
11576
11577         elem.queue(function() {
11578                 if ( hide ) {
11579                         elem.hide();
11580                 }
11581                 done();
11582         });
11583
11584         // We just queued up "anims" animations, we need to put them next in the queue
11585         if ( queuelen > 1 ) {
11586                 queue.splice.apply( queue,
11587                         [ 1, 0 ].concat( queue.splice( queuelen, anims + 1 ) ) );
11588         }
11589         elem.dequeue();
11590 };
11591
11592
11593 /*!
11594  * jQuery UI Effects Shake 1.11.4
11595  * http://jqueryui.com
11596  *
11597  * Copyright jQuery Foundation and other contributors
11598  * Released under the MIT license.
11599  * http://jquery.org/license
11600  *
11601  * http://api.jqueryui.com/shake-effect/
11602  */
11603
11604
11605 var effectShake = $.effects.effect.shake = function( o, done ) {
11606
11607         var el = $( this ),
11608                 props = [ "position", "top", "bottom", "left", "right", "height", "width" ],
11609                 mode = $.effects.setMode( el, o.mode || "effect" ),
11610                 direction = o.direction || "left",
11611                 distance = o.distance || 20,
11612                 times = o.times || 3,
11613                 anims = times * 2 + 1,
11614                 speed = Math.round( o.duration / anims ),
11615                 ref = (direction === "up" || direction === "down") ? "top" : "left",
11616                 positiveMotion = (direction === "up" || direction === "left"),
11617                 animation = {},
11618                 animation1 = {},
11619                 animation2 = {},
11620                 i,
11621
11622                 // we will need to re-assemble the queue to stack our animations in place
11623                 queue = el.queue(),
11624                 queuelen = queue.length;
11625
11626         $.effects.save( el, props );
11627         el.show();
11628         $.effects.createWrapper( el );
11629
11630         // Animation
11631         animation[ ref ] = ( positiveMotion ? "-=" : "+=" ) + distance;
11632         animation1[ ref ] = ( positiveMotion ? "+=" : "-=" ) + distance * 2;
11633         animation2[ ref ] = ( positiveMotion ? "-=" : "+=" ) + distance * 2;
11634
11635         // Animate
11636         el.animate( animation, speed, o.easing );
11637
11638         // Shakes
11639         for ( i = 1; i < times; i++ ) {
11640                 el.animate( animation1, speed, o.easing ).animate( animation2, speed, o.easing );
11641         }
11642         el
11643                 .animate( animation1, speed, o.easing )
11644                 .animate( animation, speed / 2, o.easing )
11645                 .queue(function() {
11646                         if ( mode === "hide" ) {
11647                                 el.hide();
11648                         }
11649                         $.effects.restore( el, props );
11650                         $.effects.removeWrapper( el );
11651                         done();
11652                 });
11653
11654         // inject all the animations we just queued to be first in line (after "inprogress")
11655         if ( queuelen > 1) {
11656                 queue.splice.apply( queue,
11657                         [ 1, 0 ].concat( queue.splice( queuelen, anims + 1 ) ) );
11658         }
11659         el.dequeue();
11660
11661 };
11662
11663
11664 /*!
11665  * jQuery UI Effects Slide 1.11.4
11666  * http://jqueryui.com
11667  *
11668  * Copyright jQuery Foundation and other contributors
11669  * Released under the MIT license.
11670  * http://jquery.org/license
11671  *
11672  * http://api.jqueryui.com/slide-effect/
11673  */
11674
11675
11676 var effectSlide = $.effects.effect.slide = function( o, done ) {
11677
11678         // Create element
11679         var el = $( this ),
11680                 props = [ "position", "top", "bottom", "left", "right", "width", "height" ],
11681                 mode = $.effects.setMode( el, o.mode || "show" ),
11682                 show = mode === "show",
11683                 direction = o.direction || "left",
11684                 ref = (direction === "up" || direction === "down") ? "top" : "left",
11685                 positiveMotion = (direction === "up" || direction === "left"),
11686                 distance,
11687                 animation = {};
11688
11689         // Adjust
11690         $.effects.save( el, props );
11691         el.show();
11692         distance = o.distance || el[ ref === "top" ? "outerHeight" : "outerWidth" ]( true );
11693
11694         $.effects.createWrapper( el ).css({
11695                 overflow: "hidden"
11696         });
11697
11698         if ( show ) {
11699                 el.css( ref, positiveMotion ? (isNaN(distance) ? "-" + distance : -distance) : distance );
11700         }
11701
11702         // Animation
11703         animation[ ref ] = ( show ?
11704                 ( positiveMotion ? "+=" : "-=") :
11705                 ( positiveMotion ? "-=" : "+=")) +
11706                 distance;
11707
11708         // Animate
11709         el.animate( animation, {
11710                 queue: false,
11711                 duration: o.duration,
11712                 easing: o.easing,
11713                 complete: function() {
11714                         if ( mode === "hide" ) {
11715                                 el.hide();
11716                         }
11717                         $.effects.restore( el, props );
11718                         $.effects.removeWrapper( el );
11719                         done();
11720                 }
11721         });
11722 };
11723
11724
11725 /*!
11726  * jQuery UI Effects Transfer 1.11.4
11727  * http://jqueryui.com
11728  *
11729  * Copyright jQuery Foundation and other contributors
11730  * Released under the MIT license.
11731  * http://jquery.org/license
11732  *
11733  * http://api.jqueryui.com/transfer-effect/
11734  */
11735
11736
11737 var effectTransfer = $.effects.effect.transfer = function( o, done ) {
11738         var elem = $( this ),
11739                 target = $( o.to ),
11740                 targetFixed = target.css( "position" ) === "fixed",
11741                 body = $("body"),
11742                 fixTop = targetFixed ? body.scrollTop() : 0,
11743                 fixLeft = targetFixed ? body.scrollLeft() : 0,
11744                 endPosition = target.offset(),
11745                 animation = {
11746                         top: endPosition.top - fixTop,
11747                         left: endPosition.left - fixLeft,
11748                         height: target.innerHeight(),
11749                         width: target.innerWidth()
11750                 },
11751                 startPosition = elem.offset(),
11752                 transfer = $( "<div class='ui-effects-transfer'></div>" )
11753                         .appendTo( document.body )
11754                         .addClass( o.className )
11755                         .css({
11756                                 top: startPosition.top - fixTop,
11757                                 left: startPosition.left - fixLeft,
11758                                 height: elem.innerHeight(),
11759                                 width: elem.innerWidth(),
11760                                 position: targetFixed ? "fixed" : "absolute"
11761                         })
11762                         .animate( animation, o.duration, o.easing, function() {
11763                                 transfer.remove();
11764                                 done();
11765                         });
11766 };
11767
11768
11769 /*!
11770  * jQuery UI Progressbar 1.11.4
11771  * http://jqueryui.com
11772  *
11773  * Copyright jQuery Foundation and other contributors
11774  * Released under the MIT license.
11775  * http://jquery.org/license
11776  *
11777  * http://api.jqueryui.com/progressbar/
11778  */
11779
11780
11781 var progressbar = $.widget( "ui.progressbar", {
11782         version: "1.11.4",
11783         options: {
11784                 max: 100,
11785                 value: 0,
11786
11787                 change: null,
11788                 complete: null
11789         },
11790
11791         min: 0,
11792
11793         _create: function() {
11794                 // Constrain initial value
11795                 this.oldValue = this.options.value = this._constrainedValue();
11796
11797                 this.element
11798                         .addClass( "ui-progressbar ui-widget ui-widget-content ui-corner-all" )
11799                         .attr({
11800                                 // Only set static values, aria-valuenow and aria-valuemax are
11801                                 // set inside _refreshValue()
11802                                 role: "progressbar",
11803                                 "aria-valuemin": this.min
11804                         });
11805
11806                 this.valueDiv = $( "<div class='ui-progressbar-value ui-widget-header ui-corner-left'></div>" )
11807                         .appendTo( this.element );
11808
11809                 this._refreshValue();
11810         },
11811
11812         _destroy: function() {
11813                 this.element
11814                         .removeClass( "ui-progressbar ui-widget ui-widget-content ui-corner-all" )
11815                         .removeAttr( "role" )
11816                         .removeAttr( "aria-valuemin" )
11817                         .removeAttr( "aria-valuemax" )
11818                         .removeAttr( "aria-valuenow" );
11819
11820                 this.valueDiv.remove();
11821         },
11822
11823         value: function( newValue ) {
11824                 if ( newValue === undefined ) {
11825                         return this.options.value;
11826                 }
11827
11828                 this.options.value = this._constrainedValue( newValue );
11829                 this._refreshValue();
11830         },
11831
11832         _constrainedValue: function( newValue ) {
11833                 if ( newValue === undefined ) {
11834                         newValue = this.options.value;
11835                 }
11836
11837                 this.indeterminate = newValue === false;
11838
11839                 // sanitize value
11840                 if ( typeof newValue !== "number" ) {
11841                         newValue = 0;
11842                 }
11843
11844                 return this.indeterminate ? false :
11845                         Math.min( this.options.max, Math.max( this.min, newValue ) );
11846         },
11847
11848         _setOptions: function( options ) {
11849                 // Ensure "value" option is set after other values (like max)
11850                 var value = options.value;
11851                 delete options.value;
11852
11853                 this._super( options );
11854
11855                 this.options.value = this._constrainedValue( value );
11856                 this._refreshValue();
11857         },
11858
11859         _setOption: function( key, value ) {
11860                 if ( key === "max" ) {
11861                         // Don't allow a max less than min
11862                         value = Math.max( this.min, value );
11863                 }
11864                 if ( key === "disabled" ) {
11865                         this.element
11866                                 .toggleClass( "ui-state-disabled", !!value )
11867                                 .attr( "aria-disabled", value );
11868                 }
11869                 this._super( key, value );
11870         },
11871
11872         _percentage: function() {
11873                 return this.indeterminate ? 100 : 100 * ( this.options.value - this.min ) / ( this.options.max - this.min );
11874         },
11875
11876         _refreshValue: function() {
11877                 var value = this.options.value,
11878                         percentage = this._percentage();
11879
11880                 this.valueDiv
11881                         .toggle( this.indeterminate || value > this.min )
11882                         .toggleClass( "ui-corner-right", value === this.options.max )
11883                         .width( percentage.toFixed(0) + "%" );
11884
11885                 this.element.toggleClass( "ui-progressbar-indeterminate", this.indeterminate );
11886
11887                 if ( this.indeterminate ) {
11888                         this.element.removeAttr( "aria-valuenow" );
11889                         if ( !this.overlayDiv ) {
11890                                 this.overlayDiv = $( "<div class='ui-progressbar-overlay'></div>" ).appendTo( this.valueDiv );
11891                         }
11892                 } else {
11893                         this.element.attr({
11894                                 "aria-valuemax": this.options.max,
11895                                 "aria-valuenow": value
11896                         });
11897                         if ( this.overlayDiv ) {
11898                                 this.overlayDiv.remove();
11899                                 this.overlayDiv = null;
11900                         }
11901                 }
11902
11903                 if ( this.oldValue !== value ) {
11904                         this.oldValue = value;
11905                         this._trigger( "change" );
11906                 }
11907                 if ( value === this.options.max ) {
11908                         this._trigger( "complete" );
11909                 }
11910         }
11911 });
11912
11913
11914 /*!
11915  * jQuery UI Selectable 1.11.4
11916  * http://jqueryui.com
11917  *
11918  * Copyright jQuery Foundation and other contributors
11919  * Released under the MIT license.
11920  * http://jquery.org/license
11921  *
11922  * http://api.jqueryui.com/selectable/
11923  */
11924
11925
11926 var selectable = $.widget("ui.selectable", $.ui.mouse, {
11927         version: "1.11.4",
11928         options: {
11929                 appendTo: "body",
11930                 autoRefresh: true,
11931                 distance: 0,
11932                 filter: "*",
11933                 tolerance: "touch",
11934
11935                 // callbacks
11936                 selected: null,
11937                 selecting: null,
11938                 start: null,
11939                 stop: null,
11940                 unselected: null,
11941                 unselecting: null
11942         },
11943         _create: function() {
11944                 var selectees,
11945                         that = this;
11946
11947                 this.element.addClass("ui-selectable");
11948
11949                 this.dragged = false;
11950
11951                 // cache selectee children based on filter
11952                 this.refresh = function() {
11953                         selectees = $(that.options.filter, that.element[0]);
11954                         selectees.addClass("ui-selectee");
11955                         selectees.each(function() {
11956                                 var $this = $(this),
11957                                         pos = $this.offset();
11958                                 $.data(this, "selectable-item", {
11959                                         element: this,
11960                                         $element: $this,
11961                                         left: pos.left,
11962                                         top: pos.top,
11963                                         right: pos.left + $this.outerWidth(),
11964                                         bottom: pos.top + $this.outerHeight(),
11965                                         startselected: false,
11966                                         selected: $this.hasClass("ui-selected"),
11967                                         selecting: $this.hasClass("ui-selecting"),
11968                                         unselecting: $this.hasClass("ui-unselecting")
11969                                 });
11970                         });
11971                 };
11972                 this.refresh();
11973
11974                 this.selectees = selectees.addClass("ui-selectee");
11975
11976                 this._mouseInit();
11977
11978                 this.helper = $("<div class='ui-selectable-helper'></div>");
11979         },
11980
11981         _destroy: function() {
11982                 this.selectees
11983                         .removeClass("ui-selectee")
11984                         .removeData("selectable-item");
11985                 this.element
11986                         .removeClass("ui-selectable ui-selectable-disabled");
11987                 this._mouseDestroy();
11988         },
11989
11990         _mouseStart: function(event) {
11991                 var that = this,
11992                         options = this.options;
11993
11994                 this.opos = [ event.pageX, event.pageY ];
11995
11996                 if (this.options.disabled) {
11997                         return;
11998                 }
11999
12000                 this.selectees = $(options.filter, this.element[0]);
12001
12002                 this._trigger("start", event);
12003
12004                 $(options.appendTo).append(this.helper);
12005                 // position helper (lasso)
12006                 this.helper.css({
12007                         "left": event.pageX,
12008                         "top": event.pageY,
12009                         "width": 0,
12010                         "height": 0
12011                 });
12012
12013                 if (options.autoRefresh) {
12014                         this.refresh();
12015                 }
12016
12017                 this.selectees.filter(".ui-selected").each(function() {
12018                         var selectee = $.data(this, "selectable-item");
12019                         selectee.startselected = true;
12020                         if (!event.metaKey && !event.ctrlKey) {
12021                                 selectee.$element.removeClass("ui-selected");
12022                                 selectee.selected = false;
12023                                 selectee.$element.addClass("ui-unselecting");
12024                                 selectee.unselecting = true;
12025                                 // selectable UNSELECTING callback
12026                                 that._trigger("unselecting", event, {
12027                                         unselecting: selectee.element
12028                                 });
12029                         }
12030                 });
12031
12032                 $(event.target).parents().addBack().each(function() {
12033                         var doSelect,
12034                                 selectee = $.data(this, "selectable-item");
12035                         if (selectee) {
12036                                 doSelect = (!event.metaKey && !event.ctrlKey) || !selectee.$element.hasClass("ui-selected");
12037                                 selectee.$element
12038                                         .removeClass(doSelect ? "ui-unselecting" : "ui-selected")
12039                                         .addClass(doSelect ? "ui-selecting" : "ui-unselecting");
12040                                 selectee.unselecting = !doSelect;
12041                                 selectee.selecting = doSelect;
12042                                 selectee.selected = doSelect;
12043                                 // selectable (UN)SELECTING callback
12044                                 if (doSelect) {
12045                                         that._trigger("selecting", event, {
12046                                                 selecting: selectee.element
12047                                         });
12048                                 } else {
12049                                         that._trigger("unselecting", event, {
12050                                                 unselecting: selectee.element
12051                                         });
12052                                 }
12053                                 return false;
12054                         }
12055                 });
12056
12057         },
12058
12059         _mouseDrag: function(event) {
12060
12061                 this.dragged = true;
12062
12063                 if (this.options.disabled) {
12064                         return;
12065                 }
12066
12067                 var tmp,
12068                         that = this,
12069                         options = this.options,
12070                         x1 = this.opos[0],
12071                         y1 = this.opos[1],
12072                         x2 = event.pageX,
12073                         y2 = event.pageY;
12074
12075                 if (x1 > x2) { tmp = x2; x2 = x1; x1 = tmp; }
12076                 if (y1 > y2) { tmp = y2; y2 = y1; y1 = tmp; }
12077                 this.helper.css({ left: x1, top: y1, width: x2 - x1, height: y2 - y1 });
12078
12079                 this.selectees.each(function() {
12080                         var selectee = $.data(this, "selectable-item"),
12081                                 hit = false;
12082
12083                         //prevent helper from being selected if appendTo: selectable
12084                         if (!selectee || selectee.element === that.element[0]) {
12085                                 return;
12086                         }
12087
12088                         if (options.tolerance === "touch") {
12089                                 hit = ( !(selectee.left > x2 || selectee.right < x1 || selectee.top > y2 || selectee.bottom < y1) );
12090                         } else if (options.tolerance === "fit") {
12091                                 hit = (selectee.left > x1 && selectee.right < x2 && selectee.top > y1 && selectee.bottom < y2);
12092                         }
12093
12094                         if (hit) {
12095                                 // SELECT
12096                                 if (selectee.selected) {
12097                                         selectee.$element.removeClass("ui-selected");
12098                                         selectee.selected = false;
12099                                 }
12100                                 if (selectee.unselecting) {
12101                                         selectee.$element.removeClass("ui-unselecting");
12102                                         selectee.unselecting = false;
12103                                 }
12104                                 if (!selectee.selecting) {
12105                                         selectee.$element.addClass("ui-selecting");
12106                                         selectee.selecting = true;
12107                                         // selectable SELECTING callback
12108                                         that._trigger("selecting", event, {
12109                                                 selecting: selectee.element
12110                                         });
12111                                 }
12112                         } else {
12113                                 // UNSELECT
12114                                 if (selectee.selecting) {
12115                                         if ((event.metaKey || event.ctrlKey) && selectee.startselected) {
12116                                                 selectee.$element.removeClass("ui-selecting");
12117                                                 selectee.selecting = false;
12118                                                 selectee.$element.addClass("ui-selected");
12119                                                 selectee.selected = true;
12120                                         } else {
12121                                                 selectee.$element.removeClass("ui-selecting");
12122                                                 selectee.selecting = false;
12123                                                 if (selectee.startselected) {
12124                                                         selectee.$element.addClass("ui-unselecting");
12125                                                         selectee.unselecting = true;
12126                                                 }
12127                                                 // selectable UNSELECTING callback
12128                                                 that._trigger("unselecting", event, {
12129                                                         unselecting: selectee.element
12130                                                 });
12131                                         }
12132                                 }
12133                                 if (selectee.selected) {
12134                                         if (!event.metaKey && !event.ctrlKey && !selectee.startselected) {
12135                                                 selectee.$element.removeClass("ui-selected");
12136                                                 selectee.selected = false;
12137
12138                                                 selectee.$element.addClass("ui-unselecting");
12139                                                 selectee.unselecting = true;
12140                                                 // selectable UNSELECTING callback
12141                                                 that._trigger("unselecting", event, {
12142                                                         unselecting: selectee.element
12143                                                 });
12144                                         }
12145                                 }
12146                         }
12147                 });
12148
12149                 return false;
12150         },
12151
12152         _mouseStop: function(event) {
12153                 var that = this;
12154
12155                 this.dragged = false;
12156
12157                 $(".ui-unselecting", this.element[0]).each(function() {
12158                         var selectee = $.data(this, "selectable-item");
12159                         selectee.$element.removeClass("ui-unselecting");
12160                         selectee.unselecting = false;
12161                         selectee.startselected = false;
12162                         that._trigger("unselected", event, {
12163                                 unselected: selectee.element
12164                         });
12165                 });
12166                 $(".ui-selecting", this.element[0]).each(function() {
12167                         var selectee = $.data(this, "selectable-item");
12168                         selectee.$element.removeClass("ui-selecting").addClass("ui-selected");
12169                         selectee.selecting = false;
12170                         selectee.selected = true;
12171                         selectee.startselected = true;
12172                         that._trigger("selected", event, {
12173                                 selected: selectee.element
12174                         });
12175                 });
12176                 this._trigger("stop", event);
12177
12178                 this.helper.remove();
12179
12180                 return false;
12181         }
12182
12183 });
12184
12185
12186 /*!
12187  * jQuery UI Selectmenu 1.11.4
12188  * http://jqueryui.com
12189  *
12190  * Copyright jQuery Foundation and other contributors
12191  * Released under the MIT license.
12192  * http://jquery.org/license
12193  *
12194  * http://api.jqueryui.com/selectmenu
12195  */
12196
12197
12198 var selectmenu = $.widget( "ui.selectmenu", {
12199         version: "1.11.4",
12200         defaultElement: "<select>",
12201         options: {
12202                 appendTo: null,
12203                 disabled: null,
12204                 icons: {
12205                         button: "ui-icon-triangle-1-s"
12206                 },
12207                 position: {
12208                         my: "left top",
12209                         at: "left bottom",
12210                         collision: "none"
12211                 },
12212                 width: null,
12213
12214                 // callbacks
12215                 change: null,
12216                 close: null,
12217                 focus: null,
12218                 open: null,
12219                 select: null
12220         },
12221
12222         _create: function() {
12223                 var selectmenuId = this.element.uniqueId().attr( "id" );
12224                 this.ids = {
12225                         element: selectmenuId,
12226                         button: selectmenuId + "-button",
12227                         menu: selectmenuId + "-menu"
12228                 };
12229
12230                 this._drawButton();
12231                 this._drawMenu();
12232
12233                 if ( this.options.disabled ) {
12234                         this.disable();
12235                 }
12236         },
12237
12238         _drawButton: function() {
12239                 var that = this;
12240
12241                 // Associate existing label with the new button
12242                 this.label = $( "label[for='" + this.ids.element + "']" ).attr( "for", this.ids.button );
12243                 this._on( this.label, {
12244                         click: function( event ) {
12245                                 this.button.focus();
12246                                 event.preventDefault();
12247                         }
12248                 });
12249
12250                 // Hide original select element
12251                 this.element.hide();
12252
12253                 // Create button
12254                 this.button = $( "<span>", {
12255                         "class": "ui-selectmenu-button ui-widget ui-state-default ui-corner-all",
12256                         tabindex: this.options.disabled ? -1 : 0,
12257                         id: this.ids.button,
12258                         role: "combobox",
12259                         "aria-expanded": "false",
12260                         "aria-autocomplete": "list",
12261                         "aria-owns": this.ids.menu,
12262                         "aria-haspopup": "true"
12263                 })
12264                         .insertAfter( this.element );
12265
12266                 $( "<span>", {
12267                         "class": "ui-icon " + this.options.icons.button
12268                 })
12269                         .prependTo( this.button );
12270
12271                 this.buttonText = $( "<span>", {
12272                         "class": "ui-selectmenu-text"
12273                 })
12274                         .appendTo( this.button );
12275
12276                 this._setText( this.buttonText, this.element.find( "option:selected" ).text() );
12277                 this._resizeButton();
12278
12279                 this._on( this.button, this._buttonEvents );
12280                 this.button.one( "focusin", function() {
12281
12282                         // Delay rendering the menu items until the button receives focus.
12283                         // The menu may have already been rendered via a programmatic open.
12284                         if ( !that.menuItems ) {
12285                                 that._refreshMenu();
12286                         }
12287                 });
12288                 this._hoverable( this.button );
12289                 this._focusable( this.button );
12290         },
12291
12292         _drawMenu: function() {
12293                 var that = this;
12294
12295                 // Create menu
12296                 this.menu = $( "<ul>", {
12297                         "aria-hidden": "true",
12298                         "aria-labelledby": this.ids.button,
12299                         id: this.ids.menu
12300                 });
12301
12302                 // Wrap menu
12303                 this.menuWrap = $( "<div>", {
12304                         "class": "ui-selectmenu-menu ui-front"
12305                 })
12306                         .append( this.menu )
12307                         .appendTo( this._appendTo() );
12308
12309                 // Initialize menu widget
12310                 this.menuInstance = this.menu
12311                         .menu({
12312                                 role: "listbox",
12313                                 select: function( event, ui ) {
12314                                         event.preventDefault();
12315
12316                                         // support: IE8
12317                                         // If the item was selected via a click, the text selection
12318                                         // will be destroyed in IE
12319                                         that._setSelection();
12320
12321                                         that._select( ui.item.data( "ui-selectmenu-item" ), event );
12322                                 },
12323                                 focus: function( event, ui ) {
12324                                         var item = ui.item.data( "ui-selectmenu-item" );
12325
12326                                         // Prevent inital focus from firing and check if its a newly focused item
12327                                         if ( that.focusIndex != null && item.index !== that.focusIndex ) {
12328                                                 that._trigger( "focus", event, { item: item } );
12329                                                 if ( !that.isOpen ) {
12330                                                         that._select( item, event );
12331                                                 }
12332                                         }
12333                                         that.focusIndex = item.index;
12334
12335                                         that.button.attr( "aria-activedescendant",
12336                                                 that.menuItems.eq( item.index ).attr( "id" ) );
12337                                 }
12338                         })
12339                         .menu( "instance" );
12340
12341                 // Adjust menu styles to dropdown
12342                 this.menu
12343                         .addClass( "ui-corner-bottom" )
12344                         .removeClass( "ui-corner-all" );
12345
12346                 // Don't close the menu on mouseleave
12347                 this.menuInstance._off( this.menu, "mouseleave" );
12348
12349                 // Cancel the menu's collapseAll on document click
12350                 this.menuInstance._closeOnDocumentClick = function() {
12351                         return false;
12352                 };
12353
12354                 // Selects often contain empty items, but never contain dividers
12355                 this.menuInstance._isDivider = function() {
12356                         return false;
12357                 };
12358         },
12359
12360         refresh: function() {
12361                 this._refreshMenu();
12362                 this._setText( this.buttonText, this._getSelectedItem().text() );
12363                 if ( !this.options.width ) {
12364                         this._resizeButton();
12365                 }
12366         },
12367
12368         _refreshMenu: function() {
12369                 this.menu.empty();
12370
12371                 var item,
12372                         options = this.element.find( "option" );
12373
12374                 if ( !options.length ) {
12375                         return;
12376                 }
12377
12378                 this._parseOptions( options );
12379                 this._renderMenu( this.menu, this.items );
12380
12381                 this.menuInstance.refresh();
12382                 this.menuItems = this.menu.find( "li" ).not( ".ui-selectmenu-optgroup" );
12383
12384                 item = this._getSelectedItem();
12385
12386                 // Update the menu to have the correct item focused
12387                 this.menuInstance.focus( null, item );
12388                 this._setAria( item.data( "ui-selectmenu-item" ) );
12389
12390                 // Set disabled state
12391                 this._setOption( "disabled", this.element.prop( "disabled" ) );
12392         },
12393
12394         open: function( event ) {
12395                 if ( this.options.disabled ) {
12396                         return;
12397                 }
12398
12399                 // If this is the first time the menu is being opened, render the items
12400                 if ( !this.menuItems ) {
12401                         this._refreshMenu();
12402                 } else {
12403
12404                         // Menu clears focus on close, reset focus to selected item
12405                         this.menu.find( ".ui-state-focus" ).removeClass( "ui-state-focus" );
12406                         this.menuInstance.focus( null, this._getSelectedItem() );
12407                 }
12408
12409                 this.isOpen = true;
12410                 this._toggleAttr();
12411                 this._resizeMenu();
12412                 this._position();
12413
12414                 this._on( this.document, this._documentClick );
12415
12416                 this._trigger( "open", event );
12417         },
12418
12419         _position: function() {
12420                 this.menuWrap.position( $.extend( { of: this.button }, this.options.position ) );
12421         },
12422
12423         close: function( event ) {
12424                 if ( !this.isOpen ) {
12425                         return;
12426                 }
12427
12428                 this.isOpen = false;
12429                 this._toggleAttr();
12430
12431                 this.range = null;
12432                 this._off( this.document );
12433
12434                 this._trigger( "close", event );
12435         },
12436
12437         widget: function() {
12438                 return this.button;
12439         },
12440
12441         menuWidget: function() {
12442                 return this.menu;
12443         },
12444
12445         _renderMenu: function( ul, items ) {
12446                 var that = this,
12447                         currentOptgroup = "";
12448
12449                 $.each( items, function( index, item ) {
12450                         if ( item.optgroup !== currentOptgroup ) {
12451                                 $( "<li>", {
12452                                         "class": "ui-selectmenu-optgroup ui-menu-divider" +
12453                                                 ( item.element.parent( "optgroup" ).prop( "disabled" ) ?
12454                                                         " ui-state-disabled" :
12455                                                         "" ),
12456                                         text: item.optgroup
12457                                 })
12458                                         .appendTo( ul );
12459
12460                                 currentOptgroup = item.optgroup;
12461                         }
12462
12463                         that._renderItemData( ul, item );
12464                 });
12465         },
12466
12467         _renderItemData: function( ul, item ) {
12468                 return this._renderItem( ul, item ).data( "ui-selectmenu-item", item );
12469         },
12470
12471         _renderItem: function( ul, item ) {
12472                 var li = $( "<li>" );
12473
12474                 if ( item.disabled ) {
12475                         li.addClass( "ui-state-disabled" );
12476                 }
12477                 this._setText( li, item.label );
12478
12479                 return li.appendTo( ul );
12480         },
12481
12482         _setText: function( element, value ) {
12483                 if ( value ) {
12484                         element.text( value );
12485                 } else {
12486                         element.html( "&#160;" );
12487                 }
12488         },
12489
12490         _move: function( direction, event ) {
12491                 var item, next,
12492                         filter = ".ui-menu-item";
12493
12494                 if ( this.isOpen ) {
12495                         item = this.menuItems.eq( this.focusIndex );
12496                 } else {
12497                         item = this.menuItems.eq( this.element[ 0 ].selectedIndex );
12498                         filter += ":not(.ui-state-disabled)";
12499                 }
12500
12501                 if ( direction === "first" || direction === "last" ) {
12502                         next = item[ direction === "first" ? "prevAll" : "nextAll" ]( filter ).eq( -1 );
12503                 } else {
12504                         next = item[ direction + "All" ]( filter ).eq( 0 );
12505                 }
12506
12507                 if ( next.length ) {
12508                         this.menuInstance.focus( event, next );
12509                 }
12510         },
12511
12512         _getSelectedItem: function() {
12513                 return this.menuItems.eq( this.element[ 0 ].selectedIndex );
12514         },
12515
12516         _toggle: function( event ) {
12517                 this[ this.isOpen ? "close" : "open" ]( event );
12518         },
12519
12520         _setSelection: function() {
12521                 var selection;
12522
12523                 if ( !this.range ) {
12524                         return;
12525                 }
12526
12527                 if ( window.getSelection ) {
12528                         selection = window.getSelection();
12529                         selection.removeAllRanges();
12530                         selection.addRange( this.range );
12531
12532                 // support: IE8
12533                 } else {
12534                         this.range.select();
12535                 }
12536
12537                 // support: IE
12538                 // Setting the text selection kills the button focus in IE, but
12539                 // restoring the focus doesn't kill the selection.
12540                 this.button.focus();
12541         },
12542
12543         _documentClick: {
12544                 mousedown: function( event ) {
12545                         if ( !this.isOpen ) {
12546                                 return;
12547                         }
12548
12549                         if ( !$( event.target ).closest( ".ui-selectmenu-menu, #" + this.ids.button ).length ) {
12550                                 this.close( event );
12551                         }
12552                 }
12553         },
12554
12555         _buttonEvents: {
12556
12557                 // Prevent text selection from being reset when interacting with the selectmenu (#10144)
12558                 mousedown: function() {
12559                         var selection;
12560
12561                         if ( window.getSelection ) {
12562                                 selection = window.getSelection();
12563                                 if ( selection.rangeCount ) {
12564                                         this.range = selection.getRangeAt( 0 );
12565                                 }
12566
12567                         // support: IE8
12568                         } else {
12569                                 this.range = document.selection.createRange();
12570                         }
12571                 },
12572
12573                 click: function( event ) {
12574                         this._setSelection();
12575                         this._toggle( event );
12576                 },
12577
12578                 keydown: function( event ) {
12579                         var preventDefault = true;
12580                         switch ( event.keyCode ) {
12581                                 case $.ui.keyCode.TAB:
12582                                 case $.ui.keyCode.ESCAPE:
12583                                         this.close( event );
12584                                         preventDefault = false;
12585                                         break;
12586                                 case $.ui.keyCode.ENTER:
12587                                         if ( this.isOpen ) {
12588                                                 this._selectFocusedItem( event );
12589                                         }
12590                                         break;
12591                                 case $.ui.keyCode.UP:
12592                                         if ( event.altKey ) {
12593                                                 this._toggle( event );
12594                                         } else {
12595                                                 this._move( "prev", event );
12596                                         }
12597                                         break;
12598                                 case $.ui.keyCode.DOWN:
12599                                         if ( event.altKey ) {
12600                                                 this._toggle( event );
12601                                         } else {
12602                                                 this._move( "next", event );
12603                                         }
12604                                         break;
12605                                 case $.ui.keyCode.SPACE:
12606                                         if ( this.isOpen ) {
12607                                                 this._selectFocusedItem( event );
12608                                         } else {
12609                                                 this._toggle( event );
12610                                         }
12611                                         break;
12612                                 case $.ui.keyCode.LEFT:
12613                                         this._move( "prev", event );
12614                                         break;
12615                                 case $.ui.keyCode.RIGHT:
12616                                         this._move( "next", event );
12617                                         break;
12618                                 case $.ui.keyCode.HOME:
12619                                 case $.ui.keyCode.PAGE_UP:
12620                                         this._move( "first", event );
12621                                         break;
12622                                 case $.ui.keyCode.END:
12623                                 case $.ui.keyCode.PAGE_DOWN:
12624                                         this._move( "last", event );
12625                                         break;
12626                                 default:
12627                                         this.menu.trigger( event );
12628                                         preventDefault = false;
12629                         }
12630
12631                         if ( preventDefault ) {
12632                                 event.preventDefault();
12633                         }
12634                 }
12635         },
12636
12637         _selectFocusedItem: function( event ) {
12638                 var item = this.menuItems.eq( this.focusIndex );
12639                 if ( !item.hasClass( "ui-state-disabled" ) ) {
12640                         this._select( item.data( "ui-selectmenu-item" ), event );
12641                 }
12642         },
12643
12644         _select: function( item, event ) {
12645                 var oldIndex = this.element[ 0 ].selectedIndex;
12646
12647                 // Change native select element
12648                 this.element[ 0 ].selectedIndex = item.index;
12649                 this._setText( this.buttonText, item.label );
12650                 this._setAria( item );
12651                 this._trigger( "select", event, { item: item } );
12652
12653                 if ( item.index !== oldIndex ) {
12654                         this._trigger( "change", event, { item: item } );
12655                 }
12656
12657                 this.close( event );
12658         },
12659
12660         _setAria: function( item ) {
12661                 var id = this.menuItems.eq( item.index ).attr( "id" );
12662
12663                 this.button.attr({
12664                         "aria-labelledby": id,
12665                         "aria-activedescendant": id
12666                 });
12667                 this.menu.attr( "aria-activedescendant", id );
12668         },
12669
12670         _setOption: function( key, value ) {
12671                 if ( key === "icons" ) {
12672                         this.button.find( "span.ui-icon" )
12673                                 .removeClass( this.options.icons.button )
12674                                 .addClass( value.button );
12675                 }
12676
12677                 this._super( key, value );
12678
12679                 if ( key === "appendTo" ) {
12680                         this.menuWrap.appendTo( this._appendTo() );
12681                 }
12682
12683                 if ( key === "disabled" ) {
12684                         this.menuInstance.option( "disabled", value );
12685                         this.button
12686                                 .toggleClass( "ui-state-disabled", value )
12687                                 .attr( "aria-disabled", value );
12688
12689                         this.element.prop( "disabled", value );
12690                         if ( value ) {
12691                                 this.button.attr( "tabindex", -1 );
12692                                 this.close();
12693                         } else {
12694                                 this.button.attr( "tabindex", 0 );
12695                         }
12696                 }
12697
12698                 if ( key === "width" ) {
12699                         this._resizeButton();
12700                 }
12701         },
12702
12703         _appendTo: function() {
12704                 var element = this.options.appendTo;
12705
12706                 if ( element ) {
12707                         element = element.jquery || element.nodeType ?
12708                                 $( element ) :
12709                                 this.document.find( element ).eq( 0 );
12710                 }
12711
12712                 if ( !element || !element[ 0 ] ) {
12713                         element = this.element.closest( ".ui-front" );
12714                 }
12715
12716                 if ( !element.length ) {
12717                         element = this.document[ 0 ].body;
12718                 }
12719
12720                 return element;
12721         },
12722
12723         _toggleAttr: function() {
12724                 this.button
12725                         .toggleClass( "ui-corner-top", this.isOpen )
12726                         .toggleClass( "ui-corner-all", !this.isOpen )
12727                         .attr( "aria-expanded", this.isOpen );
12728                 this.menuWrap.toggleClass( "ui-selectmenu-open", this.isOpen );
12729                 this.menu.attr( "aria-hidden", !this.isOpen );
12730         },
12731
12732         _resizeButton: function() {
12733                 var width = this.options.width;
12734
12735                 if ( !width ) {
12736                         width = this.element.show().outerWidth();
12737                         this.element.hide();
12738                 }
12739
12740                 this.button.outerWidth( width );
12741         },
12742
12743         _resizeMenu: function() {
12744                 this.menu.outerWidth( Math.max(
12745                         this.button.outerWidth(),
12746
12747                         // support: IE10
12748                         // IE10 wraps long text (possibly a rounding bug)
12749                         // so we add 1px to avoid the wrapping
12750                         this.menu.width( "" ).outerWidth() + 1
12751                 ) );
12752         },
12753
12754         _getCreateOptions: function() {
12755                 return { disabled: this.element.prop( "disabled" ) };
12756         },
12757
12758         _parseOptions: function( options ) {
12759                 var data = [];
12760                 options.each(function( index, item ) {
12761                         var option = $( item ),
12762                                 optgroup = option.parent( "optgroup" );
12763                         data.push({
12764                                 element: option,
12765                                 index: index,
12766                                 value: option.val(),
12767                                 label: option.text(),
12768                                 optgroup: optgroup.attr( "label" ) || "",
12769                                 disabled: optgroup.prop( "disabled" ) || option.prop( "disabled" )
12770                         });
12771                 });
12772                 this.items = data;
12773         },
12774
12775         _destroy: function() {
12776                 this.menuWrap.remove();
12777                 this.button.remove();
12778                 this.element.show();
12779                 this.element.removeUniqueId();
12780                 this.label.attr( "for", this.ids.element );
12781         }
12782 });
12783
12784
12785 /*!
12786  * jQuery UI Slider 1.11.4
12787  * http://jqueryui.com
12788  *
12789  * Copyright jQuery Foundation and other contributors
12790  * Released under the MIT license.
12791  * http://jquery.org/license
12792  *
12793  * http://api.jqueryui.com/slider/
12794  */
12795
12796
12797 var slider = $.widget( "ui.slider", $.ui.mouse, {
12798         version: "1.11.4",
12799         widgetEventPrefix: "slide",
12800
12801         options: {
12802                 animate: false,
12803                 distance: 0,
12804                 max: 100,
12805                 min: 0,
12806                 orientation: "horizontal",
12807                 range: false,
12808                 step: 1,
12809                 value: 0,
12810                 values: null,
12811
12812                 // callbacks
12813                 change: null,
12814                 slide: null,
12815                 start: null,
12816                 stop: null
12817         },
12818
12819         // number of pages in a slider
12820         // (how many times can you page up/down to go through the whole range)
12821         numPages: 5,
12822
12823         _create: function() {
12824                 this._keySliding = false;
12825                 this._mouseSliding = false;
12826                 this._animateOff = true;
12827                 this._handleIndex = null;
12828                 this._detectOrientation();
12829                 this._mouseInit();
12830                 this._calculateNewMax();
12831
12832                 this.element
12833                         .addClass( "ui-slider" +
12834                                 " ui-slider-" + this.orientation +
12835                                 " ui-widget" +
12836                                 " ui-widget-content" +
12837                                 " ui-corner-all");
12838
12839                 this._refresh();
12840                 this._setOption( "disabled", this.options.disabled );
12841
12842                 this._animateOff = false;
12843         },
12844
12845         _refresh: function() {
12846                 this._createRange();
12847                 this._createHandles();
12848                 this._setupEvents();
12849                 this._refreshValue();
12850         },
12851
12852         _createHandles: function() {
12853                 var i, handleCount,
12854                         options = this.options,
12855                         existingHandles = this.element.find( ".ui-slider-handle" ).addClass( "ui-state-default ui-corner-all" ),
12856                         handle = "<span class='ui-slider-handle ui-state-default ui-corner-all' tabindex='0'></span>",
12857                         handles = [];
12858
12859                 handleCount = ( options.values && options.values.length ) || 1;
12860
12861                 if ( existingHandles.length > handleCount ) {
12862                         existingHandles.slice( handleCount ).remove();
12863                         existingHandles = existingHandles.slice( 0, handleCount );
12864                 }
12865
12866                 for ( i = existingHandles.length; i < handleCount; i++ ) {
12867                         handles.push( handle );
12868                 }
12869
12870                 this.handles = existingHandles.add( $( handles.join( "" ) ).appendTo( this.element ) );
12871
12872                 this.handle = this.handles.eq( 0 );
12873
12874                 this.handles.each(function( i ) {
12875                         $( this ).data( "ui-slider-handle-index", i );
12876                 });
12877         },
12878
12879         _createRange: function() {
12880                 var options = this.options,
12881                         classes = "";
12882
12883                 if ( options.range ) {
12884                         if ( options.range === true ) {
12885                                 if ( !options.values ) {
12886                                         options.values = [ this._valueMin(), this._valueMin() ];
12887                                 } else if ( options.values.length && options.values.length !== 2 ) {
12888                                         options.values = [ options.values[0], options.values[0] ];
12889                                 } else if ( $.isArray( options.values ) ) {
12890                                         options.values = options.values.slice(0);
12891                                 }
12892                         }
12893
12894                         if ( !this.range || !this.range.length ) {
12895                                 this.range = $( "<div></div>" )
12896                                         .appendTo( this.element );
12897
12898                                 classes = "ui-slider-range" +
12899                                 // note: this isn't the most fittingly semantic framework class for this element,
12900                                 // but worked best visually with a variety of themes
12901                                 " ui-widget-header ui-corner-all";
12902                         } else {
12903                                 this.range.removeClass( "ui-slider-range-min ui-slider-range-max" )
12904                                         // Handle range switching from true to min/max
12905                                         .css({
12906                                                 "left": "",
12907                                                 "bottom": ""
12908                                         });
12909                         }
12910
12911                         this.range.addClass( classes +
12912                                 ( ( options.range === "min" || options.range === "max" ) ? " ui-slider-range-" + options.range : "" ) );
12913                 } else {
12914                         if ( this.range ) {
12915                                 this.range.remove();
12916                         }
12917                         this.range = null;
12918                 }
12919         },
12920
12921         _setupEvents: function() {
12922                 this._off( this.handles );
12923                 this._on( this.handles, this._handleEvents );
12924                 this._hoverable( this.handles );
12925                 this._focusable( this.handles );
12926         },
12927
12928         _destroy: function() {
12929                 this.handles.remove();
12930                 if ( this.range ) {
12931                         this.range.remove();
12932                 }
12933
12934                 this.element
12935                         .removeClass( "ui-slider" +
12936                                 " ui-slider-horizontal" +
12937                                 " ui-slider-vertical" +
12938                                 " ui-widget" +
12939                                 " ui-widget-content" +
12940                                 " ui-corner-all" );
12941
12942                 this._mouseDestroy();
12943         },
12944
12945         _mouseCapture: function( event ) {
12946                 var position, normValue, distance, closestHandle, index, allowed, offset, mouseOverHandle,
12947                         that = this,
12948                         o = this.options;
12949
12950                 if ( o.disabled ) {
12951                         return false;
12952                 }
12953
12954                 this.elementSize = {
12955                         width: this.element.outerWidth(),
12956                         height: this.element.outerHeight()
12957                 };
12958                 this.elementOffset = this.element.offset();
12959
12960                 position = { x: event.pageX, y: event.pageY };
12961                 normValue = this._normValueFromMouse( position );
12962                 distance = this._valueMax() - this._valueMin() + 1;
12963                 this.handles.each(function( i ) {
12964                         var thisDistance = Math.abs( normValue - that.values(i) );
12965                         if (( distance > thisDistance ) ||
12966                                 ( distance === thisDistance &&
12967                                         (i === that._lastChangedValue || that.values(i) === o.min ))) {
12968                                 distance = thisDistance;
12969                                 closestHandle = $( this );
12970                                 index = i;
12971                         }
12972                 });
12973
12974                 allowed = this._start( event, index );
12975                 if ( allowed === false ) {
12976                         return false;
12977                 }
12978                 this._mouseSliding = true;
12979
12980                 this._handleIndex = index;
12981
12982                 closestHandle
12983                         .addClass( "ui-state-active" )
12984                         .focus();
12985
12986                 offset = closestHandle.offset();
12987                 mouseOverHandle = !$( event.target ).parents().addBack().is( ".ui-slider-handle" );
12988                 this._clickOffset = mouseOverHandle ? { left: 0, top: 0 } : {
12989                         left: event.pageX - offset.left - ( closestHandle.width() / 2 ),
12990                         top: event.pageY - offset.top -
12991                                 ( closestHandle.height() / 2 ) -
12992                                 ( parseInt( closestHandle.css("borderTopWidth"), 10 ) || 0 ) -
12993                                 ( parseInt( closestHandle.css("borderBottomWidth"), 10 ) || 0) +
12994                                 ( parseInt( closestHandle.css("marginTop"), 10 ) || 0)
12995                 };
12996
12997                 if ( !this.handles.hasClass( "ui-state-hover" ) ) {
12998                         this._slide( event, index, normValue );
12999                 }
13000                 this._animateOff = true;
13001                 return true;
13002         },
13003
13004         _mouseStart: function() {
13005                 return true;
13006         },
13007
13008         _mouseDrag: function( event ) {
13009                 var position = { x: event.pageX, y: event.pageY },
13010                         normValue = this._normValueFromMouse( position );
13011
13012                 this._slide( event, this._handleIndex, normValue );
13013
13014                 return false;
13015         },
13016
13017         _mouseStop: function( event ) {
13018                 this.handles.removeClass( "ui-state-active" );
13019                 this._mouseSliding = false;
13020
13021                 this._stop( event, this._handleIndex );
13022                 this._change( event, this._handleIndex );
13023
13024                 this._handleIndex = null;
13025                 this._clickOffset = null;
13026                 this._animateOff = false;
13027
13028                 return false;
13029         },
13030
13031         _detectOrientation: function() {
13032                 this.orientation = ( this.options.orientation === "vertical" ) ? "vertical" : "horizontal";
13033         },
13034
13035         _normValueFromMouse: function( position ) {
13036                 var pixelTotal,
13037                         pixelMouse,
13038                         percentMouse,
13039                         valueTotal,
13040                         valueMouse;
13041
13042                 if ( this.orientation === "horizontal" ) {
13043                         pixelTotal = this.elementSize.width;
13044                         pixelMouse = position.x - this.elementOffset.left - ( this._clickOffset ? this._clickOffset.left : 0 );
13045                 } else {
13046                         pixelTotal = this.elementSize.height;
13047                         pixelMouse = position.y - this.elementOffset.top - ( this._clickOffset ? this._clickOffset.top : 0 );
13048                 }
13049
13050                 percentMouse = ( pixelMouse / pixelTotal );
13051                 if ( percentMouse > 1 ) {
13052                         percentMouse = 1;
13053                 }
13054                 if ( percentMouse < 0 ) {
13055                         percentMouse = 0;
13056                 }
13057                 if ( this.orientation === "vertical" ) {
13058                         percentMouse = 1 - percentMouse;
13059                 }
13060
13061                 valueTotal = this._valueMax() - this._valueMin();
13062                 valueMouse = this._valueMin() + percentMouse * valueTotal;
13063
13064                 return this._trimAlignValue( valueMouse );
13065         },
13066
13067         _start: function( event, index ) {
13068                 var uiHash = {
13069                         handle: this.handles[ index ],
13070                         value: this.value()
13071                 };
13072                 if ( this.options.values && this.options.values.length ) {
13073                         uiHash.value = this.values( index );
13074                         uiHash.values = this.values();
13075                 }
13076                 return this._trigger( "start", event, uiHash );
13077         },
13078
13079         _slide: function( event, index, newVal ) {
13080                 var otherVal,
13081                         newValues,
13082                         allowed;
13083
13084                 if ( this.options.values && this.options.values.length ) {
13085                         otherVal = this.values( index ? 0 : 1 );
13086
13087                         if ( ( this.options.values.length === 2 && this.options.range === true ) &&
13088                                         ( ( index === 0 && newVal > otherVal) || ( index === 1 && newVal < otherVal ) )
13089                                 ) {
13090                                 newVal = otherVal;
13091                         }
13092
13093                         if ( newVal !== this.values( index ) ) {
13094                                 newValues = this.values();
13095                                 newValues[ index ] = newVal;
13096                                 // A slide can be canceled by returning false from the slide callback
13097                                 allowed = this._trigger( "slide", event, {
13098                                         handle: this.handles[ index ],
13099                                         value: newVal,
13100                                         values: newValues
13101                                 } );
13102                                 otherVal = this.values( index ? 0 : 1 );
13103                                 if ( allowed !== false ) {
13104                                         this.values( index, newVal );
13105                                 }
13106                         }
13107                 } else {
13108                         if ( newVal !== this.value() ) {
13109                                 // A slide can be canceled by returning false from the slide callback
13110                                 allowed = this._trigger( "slide", event, {
13111                                         handle: this.handles[ index ],
13112                                         value: newVal
13113                                 } );
13114                                 if ( allowed !== false ) {
13115                                         this.value( newVal );
13116                                 }
13117                         }
13118                 }
13119         },
13120
13121         _stop: function( event, index ) {
13122                 var uiHash = {
13123                         handle: this.handles[ index ],
13124                         value: this.value()
13125                 };
13126                 if ( this.options.values && this.options.values.length ) {
13127                         uiHash.value = this.values( index );
13128                         uiHash.values = this.values();
13129                 }
13130
13131                 this._trigger( "stop", event, uiHash );
13132         },
13133
13134         _change: function( event, index ) {
13135                 if ( !this._keySliding && !this._mouseSliding ) {
13136                         var uiHash = {
13137                                 handle: this.handles[ index ],
13138                                 value: this.value()
13139                         };
13140                         if ( this.options.values && this.options.values.length ) {
13141                                 uiHash.value = this.values( index );
13142                                 uiHash.values = this.values();
13143                         }
13144
13145                         //store the last changed value index for reference when handles overlap
13146                         this._lastChangedValue = index;
13147
13148                         this._trigger( "change", event, uiHash );
13149                 }
13150         },
13151
13152         value: function( newValue ) {
13153                 if ( arguments.length ) {
13154                         this.options.value = this._trimAlignValue( newValue );
13155                         this._refreshValue();
13156                         this._change( null, 0 );
13157                         return;
13158                 }
13159
13160                 return this._value();
13161         },
13162
13163         values: function( index, newValue ) {
13164                 var vals,
13165                         newValues,
13166                         i;
13167
13168                 if ( arguments.length > 1 ) {
13169                         this.options.values[ index ] = this._trimAlignValue( newValue );
13170                         this._refreshValue();
13171                         this._change( null, index );
13172                         return;
13173                 }
13174
13175                 if ( arguments.length ) {
13176                         if ( $.isArray( arguments[ 0 ] ) ) {
13177                                 vals = this.options.values;
13178                                 newValues = arguments[ 0 ];
13179                                 for ( i = 0; i < vals.length; i += 1 ) {
13180                                         vals[ i ] = this._trimAlignValue( newValues[ i ] );
13181                                         this._change( null, i );
13182                                 }
13183                                 this._refreshValue();
13184                         } else {
13185                                 if ( this.options.values && this.options.values.length ) {
13186                                         return this._values( index );
13187                                 } else {
13188                                         return this.value();
13189                                 }
13190                         }
13191                 } else {
13192                         return this._values();
13193                 }
13194         },
13195
13196         _setOption: function( key, value ) {
13197                 var i,
13198                         valsLength = 0;
13199
13200                 if ( key === "range" && this.options.range === true ) {
13201                         if ( value === "min" ) {
13202                                 this.options.value = this._values( 0 );
13203                                 this.options.values = null;
13204                         } else if ( value === "max" ) {
13205                                 this.options.value = this._values( this.options.values.length - 1 );
13206                                 this.options.values = null;
13207                         }
13208                 }
13209
13210                 if ( $.isArray( this.options.values ) ) {
13211                         valsLength = this.options.values.length;
13212                 }
13213
13214                 if ( key === "disabled" ) {
13215                         this.element.toggleClass( "ui-state-disabled", !!value );
13216                 }
13217
13218                 this._super( key, value );
13219
13220                 switch ( key ) {
13221                         case "orientation":
13222                                 this._detectOrientation();
13223                                 this.element
13224                                         .removeClass( "ui-slider-horizontal ui-slider-vertical" )
13225                                         .addClass( "ui-slider-" + this.orientation );
13226                                 this._refreshValue();
13227
13228                                 // Reset positioning from previous orientation
13229                                 this.handles.css( value === "horizontal" ? "bottom" : "left", "" );
13230                                 break;
13231                         case "value":
13232                                 this._animateOff = true;
13233                                 this._refreshValue();
13234                                 this._change( null, 0 );
13235                                 this._animateOff = false;
13236                                 break;
13237                         case "values":
13238                                 this._animateOff = true;
13239                                 this._refreshValue();
13240                                 for ( i = 0; i < valsLength; i += 1 ) {
13241                                         this._change( null, i );
13242                                 }
13243                                 this._animateOff = false;
13244                                 break;
13245                         case "step":
13246                         case "min":
13247                         case "max":
13248                                 this._animateOff = true;
13249                                 this._calculateNewMax();
13250                                 this._refreshValue();
13251                                 this._animateOff = false;
13252                                 break;
13253                         case "range":
13254                                 this._animateOff = true;
13255                                 this._refresh();
13256                                 this._animateOff = false;
13257                                 break;
13258                 }
13259         },
13260
13261         //internal value getter
13262         // _value() returns value trimmed by min and max, aligned by step
13263         _value: function() {
13264                 var val = this.options.value;
13265                 val = this._trimAlignValue( val );
13266
13267                 return val;
13268         },
13269
13270         //internal values getter
13271         // _values() returns array of values trimmed by min and max, aligned by step
13272         // _values( index ) returns single value trimmed by min and max, aligned by step
13273         _values: function( index ) {
13274                 var val,
13275                         vals,
13276                         i;
13277
13278                 if ( arguments.length ) {
13279                         val = this.options.values[ index ];
13280                         val = this._trimAlignValue( val );
13281
13282                         return val;
13283                 } else if ( this.options.values && this.options.values.length ) {
13284                         // .slice() creates a copy of the array
13285                         // this copy gets trimmed by min and max and then returned
13286                         vals = this.options.values.slice();
13287                         for ( i = 0; i < vals.length; i += 1) {
13288                                 vals[ i ] = this._trimAlignValue( vals[ i ] );
13289                         }
13290
13291                         return vals;
13292                 } else {
13293                         return [];
13294                 }
13295         },
13296
13297         // returns the step-aligned value that val is closest to, between (inclusive) min and max
13298         _trimAlignValue: function( val ) {
13299                 if ( val <= this._valueMin() ) {
13300                         return this._valueMin();
13301                 }
13302                 if ( val >= this._valueMax() ) {
13303                         return this._valueMax();
13304                 }
13305                 var step = ( this.options.step > 0 ) ? this.options.step : 1,
13306                         valModStep = (val - this._valueMin()) % step,
13307                         alignValue = val - valModStep;
13308
13309                 if ( Math.abs(valModStep) * 2 >= step ) {
13310                         alignValue += ( valModStep > 0 ) ? step : ( -step );
13311                 }
13312
13313                 // Since JavaScript has problems with large floats, round
13314                 // the final value to 5 digits after the decimal point (see #4124)
13315                 return parseFloat( alignValue.toFixed(5) );
13316         },
13317
13318         _calculateNewMax: function() {
13319                 var max = this.options.max,
13320                         min = this._valueMin(),
13321                         step = this.options.step,
13322                         aboveMin = Math.floor( ( +( max - min ).toFixed( this._precision() ) ) / step ) * step;
13323                 max = aboveMin + min;
13324                 this.max = parseFloat( max.toFixed( this._precision() ) );
13325         },
13326
13327         _precision: function() {
13328                 var precision = this._precisionOf( this.options.step );
13329                 if ( this.options.min !== null ) {
13330                         precision = Math.max( precision, this._precisionOf( this.options.min ) );
13331                 }
13332                 return precision;
13333         },
13334
13335         _precisionOf: function( num ) {
13336                 var str = num.toString(),
13337                         decimal = str.indexOf( "." );
13338                 return decimal === -1 ? 0 : str.length - decimal - 1;
13339         },
13340
13341         _valueMin: function() {
13342                 return this.options.min;
13343         },
13344
13345         _valueMax: function() {
13346                 return this.max;
13347         },
13348
13349         _refreshValue: function() {
13350                 var lastValPercent, valPercent, value, valueMin, valueMax,
13351                         oRange = this.options.range,
13352                         o = this.options,
13353                         that = this,
13354                         animate = ( !this._animateOff ) ? o.animate : false,
13355                         _set = {};
13356
13357                 if ( this.options.values && this.options.values.length ) {
13358                         this.handles.each(function( i ) {
13359                                 valPercent = ( that.values(i) - that._valueMin() ) / ( that._valueMax() - that._valueMin() ) * 100;
13360                                 _set[ that.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
13361                                 $( this ).stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
13362                                 if ( that.options.range === true ) {
13363                                         if ( that.orientation === "horizontal" ) {
13364                                                 if ( i === 0 ) {
13365                                                         that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { left: valPercent + "%" }, o.animate );
13366                                                 }
13367                                                 if ( i === 1 ) {
13368                                                         that.range[ animate ? "animate" : "css" ]( { width: ( valPercent - lastValPercent ) + "%" }, { queue: false, duration: o.animate } );
13369                                                 }
13370                                         } else {
13371                                                 if ( i === 0 ) {
13372                                                         that.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { bottom: ( valPercent ) + "%" }, o.animate );
13373                                                 }
13374                                                 if ( i === 1 ) {
13375                                                         that.range[ animate ? "animate" : "css" ]( { height: ( valPercent - lastValPercent ) + "%" }, { queue: false, duration: o.animate } );
13376                                                 }
13377                                         }
13378                                 }
13379                                 lastValPercent = valPercent;
13380                         });
13381                 } else {
13382                         value = this.value();
13383                         valueMin = this._valueMin();
13384                         valueMax = this._valueMax();
13385                         valPercent = ( valueMax !== valueMin ) ?
13386                                         ( value - valueMin ) / ( valueMax - valueMin ) * 100 :
13387                                         0;
13388                         _set[ this.orientation === "horizontal" ? "left" : "bottom" ] = valPercent + "%";
13389                         this.handle.stop( 1, 1 )[ animate ? "animate" : "css" ]( _set, o.animate );
13390
13391                         if ( oRange === "min" && this.orientation === "horizontal" ) {
13392                                 this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { width: valPercent + "%" }, o.animate );
13393                         }
13394                         if ( oRange === "max" && this.orientation === "horizontal" ) {
13395                                 this.range[ animate ? "animate" : "css" ]( { width: ( 100 - valPercent ) + "%" }, { queue: false, duration: o.animate } );
13396                         }
13397                         if ( oRange === "min" && this.orientation === "vertical" ) {
13398                                 this.range.stop( 1, 1 )[ animate ? "animate" : "css" ]( { height: valPercent + "%" }, o.animate );
13399                         }
13400                         if ( oRange === "max" && this.orientation === "vertical" ) {
13401                                 this.range[ animate ? "animate" : "css" ]( { height: ( 100 - valPercent ) + "%" }, { queue: false, duration: o.animate } );
13402                         }
13403                 }
13404         },
13405
13406         _handleEvents: {
13407                 keydown: function( event ) {
13408                         var allowed, curVal, newVal, step,
13409                                 index = $( event.target ).data( "ui-slider-handle-index" );
13410
13411                         switch ( event.keyCode ) {
13412                                 case $.ui.keyCode.HOME:
13413                                 case $.ui.keyCode.END:
13414                                 case $.ui.keyCode.PAGE_UP:
13415                                 case $.ui.keyCode.PAGE_DOWN:
13416                                 case $.ui.keyCode.UP:
13417                                 case $.ui.keyCode.RIGHT:
13418                                 case $.ui.keyCode.DOWN:
13419                                 case $.ui.keyCode.LEFT:
13420                                         event.preventDefault();
13421                                         if ( !this._keySliding ) {
13422                                                 this._keySliding = true;
13423                                                 $( event.target ).addClass( "ui-state-active" );
13424                                                 allowed = this._start( event, index );
13425                                                 if ( allowed === false ) {
13426                                                         return;
13427                                                 }
13428                                         }
13429                                         break;
13430                         }
13431
13432                         step = this.options.step;
13433                         if ( this.options.values && this.options.values.length ) {
13434                                 curVal = newVal = this.values( index );
13435                         } else {
13436                                 curVal = newVal = this.value();
13437                         }
13438
13439                         switch ( event.keyCode ) {
13440                                 case $.ui.keyCode.HOME:
13441                                         newVal = this._valueMin();
13442                                         break;
13443                                 case $.ui.keyCode.END:
13444                                         newVal = this._valueMax();
13445                                         break;
13446                                 case $.ui.keyCode.PAGE_UP:
13447                                         newVal = this._trimAlignValue(
13448                                                 curVal + ( ( this._valueMax() - this._valueMin() ) / this.numPages )
13449                                         );
13450                                         break;
13451                                 case $.ui.keyCode.PAGE_DOWN:
13452                                         newVal = this._trimAlignValue(
13453                                                 curVal - ( (this._valueMax() - this._valueMin()) / this.numPages ) );
13454                                         break;
13455                                 case $.ui.keyCode.UP:
13456                                 case $.ui.keyCode.RIGHT:
13457                                         if ( curVal === this._valueMax() ) {
13458                                                 return;
13459                                         }
13460                                         newVal = this._trimAlignValue( curVal + step );
13461                                         break;
13462                                 case $.ui.keyCode.DOWN:
13463                                 case $.ui.keyCode.LEFT:
13464                                         if ( curVal === this._valueMin() ) {
13465                                                 return;
13466                                         }
13467                                         newVal = this._trimAlignValue( curVal - step );
13468                                         break;
13469                         }
13470
13471                         this._slide( event, index, newVal );
13472                 },
13473                 keyup: function( event ) {
13474                         var index = $( event.target ).data( "ui-slider-handle-index" );
13475
13476                         if ( this._keySliding ) {
13477                                 this._keySliding = false;
13478                                 this._stop( event, index );
13479                                 this._change( event, index );
13480                                 $( event.target ).removeClass( "ui-state-active" );
13481                         }
13482                 }
13483         }
13484 });
13485
13486
13487 /*!
13488  * jQuery UI Sortable 1.11.4
13489  * http://jqueryui.com
13490  *
13491  * Copyright jQuery Foundation and other contributors
13492  * Released under the MIT license.
13493  * http://jquery.org/license
13494  *
13495  * http://api.jqueryui.com/sortable/
13496  */
13497
13498
13499 var sortable = $.widget("ui.sortable", $.ui.mouse, {
13500         version: "1.11.4",
13501         widgetEventPrefix: "sort",
13502         ready: false,
13503         options: {
13504                 appendTo: "parent",
13505                 axis: false,
13506                 connectWith: false,
13507                 containment: false,
13508                 cursor: "auto",
13509                 cursorAt: false,
13510                 dropOnEmpty: true,
13511                 forcePlaceholderSize: false,
13512                 forceHelperSize: false,
13513                 grid: false,
13514                 handle: false,
13515                 helper: "original",
13516                 items: "> *",
13517                 opacity: false,
13518                 placeholder: false,
13519                 revert: false,
13520                 scroll: true,
13521                 scrollSensitivity: 20,
13522                 scrollSpeed: 20,
13523                 scope: "default",
13524                 tolerance: "intersect",
13525                 zIndex: 1000,
13526
13527                 // callbacks
13528                 activate: null,
13529                 beforeStop: null,
13530                 change: null,
13531                 deactivate: null,
13532                 out: null,
13533                 over: null,
13534                 receive: null,
13535                 remove: null,
13536                 sort: null,
13537                 start: null,
13538                 stop: null,
13539                 update: null
13540         },
13541
13542         _isOverAxis: function( x, reference, size ) {
13543                 return ( x >= reference ) && ( x < ( reference + size ) );
13544         },
13545
13546         _isFloating: function( item ) {
13547                 return (/left|right/).test(item.css("float")) || (/inline|table-cell/).test(item.css("display"));
13548         },
13549
13550         _create: function() {
13551                 this.containerCache = {};
13552                 this.element.addClass("ui-sortable");
13553
13554                 //Get the items
13555                 this.refresh();
13556
13557                 //Let's determine the parent's offset
13558                 this.offset = this.element.offset();
13559
13560                 //Initialize mouse events for interaction
13561                 this._mouseInit();
13562
13563                 this._setHandleClassName();
13564
13565                 //We're ready to go
13566                 this.ready = true;
13567
13568         },
13569
13570         _setOption: function( key, value ) {
13571                 this._super( key, value );
13572
13573                 if ( key === "handle" ) {
13574                         this._setHandleClassName();
13575                 }
13576         },
13577
13578         _setHandleClassName: function() {
13579                 this.element.find( ".ui-sortable-handle" ).removeClass( "ui-sortable-handle" );
13580                 $.each( this.items, function() {
13581                         ( this.instance.options.handle ?
13582                                 this.item.find( this.instance.options.handle ) : this.item )
13583                                 .addClass( "ui-sortable-handle" );
13584                 });
13585         },
13586
13587         _destroy: function() {
13588                 this.element
13589                         .removeClass( "ui-sortable ui-sortable-disabled" )
13590                         .find( ".ui-sortable-handle" )
13591                                 .removeClass( "ui-sortable-handle" );
13592                 this._mouseDestroy();
13593
13594                 for ( var i = this.items.length - 1; i >= 0; i-- ) {
13595                         this.items[i].item.removeData(this.widgetName + "-item");
13596                 }
13597
13598                 return this;
13599         },
13600
13601         _mouseCapture: function(event, overrideHandle) {
13602                 var currentItem = null,
13603                         validHandle = false,
13604                         that = this;
13605
13606                 if (this.reverting) {
13607                         return false;
13608                 }
13609
13610                 if(this.options.disabled || this.options.type === "static") {
13611                         return false;
13612                 }
13613
13614                 //We have to refresh the items data once first
13615                 this._refreshItems(event);
13616
13617                 //Find out if the clicked node (or one of its parents) is a actual item in this.items
13618                 $(event.target).parents().each(function() {
13619                         if($.data(this, that.widgetName + "-item") === that) {
13620                                 currentItem = $(this);
13621                                 return false;
13622                         }
13623                 });
13624                 if($.data(event.target, that.widgetName + "-item") === that) {
13625                         currentItem = $(event.target);
13626                 }
13627
13628                 if(!currentItem) {
13629                         return false;
13630                 }
13631                 if(this.options.handle && !overrideHandle) {
13632                         $(this.options.handle, currentItem).find("*").addBack().each(function() {
13633                                 if(this === event.target) {
13634                                         validHandle = true;
13635                                 }
13636                         });
13637                         if(!validHandle) {
13638                                 return false;
13639                         }
13640                 }
13641
13642                 this.currentItem = currentItem;
13643                 this._removeCurrentsFromItems();
13644                 return true;
13645
13646         },
13647
13648         _mouseStart: function(event, overrideHandle, noActivation) {
13649
13650                 var i, body,
13651                         o = this.options;
13652
13653                 this.currentContainer = this;
13654
13655                 //We only need to call refreshPositions, because the refreshItems call has been moved to mouseCapture
13656                 this.refreshPositions();
13657
13658                 //Create and append the visible helper
13659                 this.helper = this._createHelper(event);
13660
13661                 //Cache the helper size
13662                 this._cacheHelperProportions();
13663
13664                 /*
13665                  * - Position generation -
13666                  * This block generates everything position related - it's the core of draggables.
13667                  */
13668
13669                 //Cache the margins of the original element
13670                 this._cacheMargins();
13671
13672                 //Get the next scrolling parent
13673                 this.scrollParent = this.helper.scrollParent();
13674
13675                 //The element's absolute position on the page minus margins
13676                 this.offset = this.currentItem.offset();
13677                 this.offset = {
13678                         top: this.offset.top - this.margins.top,
13679                         left: this.offset.left - this.margins.left
13680                 };
13681
13682                 $.extend(this.offset, {
13683                         click: { //Where the click happened, relative to the element
13684                                 left: event.pageX - this.offset.left,
13685                                 top: event.pageY - this.offset.top
13686                         },
13687                         parent: this._getParentOffset(),
13688                         relative: this._getRelativeOffset() //This is a relative to absolute position minus the actual position calculation - only used for relative positioned helper
13689                 });
13690
13691                 // Only after we got the offset, we can change the helper's position to absolute
13692                 // TODO: Still need to figure out a way to make relative sorting possible
13693                 this.helper.css("position", "absolute");
13694                 this.cssPosition = this.helper.css("position");
13695
13696                 //Generate the original position
13697                 this.originalPosition = this._generatePosition(event);
13698                 this.originalPageX = event.pageX;
13699                 this.originalPageY = event.pageY;
13700
13701                 //Adjust the mouse offset relative to the helper if "cursorAt" is supplied
13702                 (o.cursorAt && this._adjustOffsetFromHelper(o.cursorAt));
13703
13704                 //Cache the former DOM position
13705                 this.domPosition = { prev: this.currentItem.prev()[0], parent: this.currentItem.parent()[0] };
13706
13707                 //If the helper is not the original, hide the original so it's not playing any role during the drag, won't cause anything bad this way
13708                 if(this.helper[0] !== this.currentItem[0]) {
13709                         this.currentItem.hide();
13710                 }
13711
13712                 //Create the placeholder
13713                 this._createPlaceholder();
13714
13715                 //Set a containment if given in the options
13716                 if(o.containment) {
13717                         this._setContainment();
13718                 }
13719
13720                 if( o.cursor && o.cursor !== "auto" ) { // cursor option
13721                         body = this.document.find( "body" );
13722
13723                         // support: IE
13724                         this.storedCursor = body.css( "cursor" );
13725                         body.css( "cursor", o.cursor );
13726
13727                         this.storedStylesheet = $( "<style>*{ cursor: "+o.cursor+" !important; }</style>" ).appendTo( body );
13728                 }
13729
13730                 if(o.opacity) { // opacity option
13731                         if (this.helper.css("opacity")) {
13732                                 this._storedOpacity = this.helper.css("opacity");
13733                         }
13734                         this.helper.css("opacity", o.opacity);
13735                 }
13736
13737                 if(o.zIndex) { // zIndex option
13738                         if (this.helper.css("zIndex")) {
13739                                 this._storedZIndex = this.helper.css("zIndex");
13740                         }
13741                         this.helper.css("zIndex", o.zIndex);
13742                 }
13743
13744                 //Prepare scrolling
13745                 if(this.scrollParent[0] !== this.document[0] && this.scrollParent[0].tagName !== "HTML") {
13746                         this.overflowOffset = this.scrollParent.offset();
13747                 }
13748
13749                 //Call callbacks
13750                 this._trigger("start", event, this._uiHash());
13751
13752                 //Recache the helper size
13753                 if(!this._preserveHelperProportions) {
13754                         this._cacheHelperProportions();
13755                 }
13756
13757
13758                 //Post "activate" events to possible containers
13759                 if( !noActivation ) {
13760                         for ( i = this.containers.length - 1; i >= 0; i-- ) {
13761                                 this.containers[ i ]._trigger( "activate", event, this._uiHash( this ) );
13762                         }
13763                 }
13764
13765                 //Prepare possible droppables
13766                 if($.ui.ddmanager) {
13767                         $.ui.ddmanager.current = this;
13768                 }
13769
13770                 if ($.ui.ddmanager && !o.dropBehaviour) {
13771                         $.ui.ddmanager.prepareOffsets(this, event);
13772                 }
13773
13774                 this.dragging = true;
13775
13776                 this.helper.addClass("ui-sortable-helper");
13777                 this._mouseDrag(event); //Execute the drag once - this causes the helper not to be visible before getting its correct position
13778                 return true;
13779
13780         },
13781
13782         _mouseDrag: function(event) {
13783                 var i, item, itemElement, intersection,
13784                         o = this.options,
13785                         scrolled = false;
13786
13787                 //Compute the helpers position
13788                 this.position = this._generatePosition(event);
13789                 this.positionAbs = this._convertPositionTo("absolute");
13790
13791                 if (!this.lastPositionAbs) {
13792                         this.lastPositionAbs = this.positionAbs;
13793                 }
13794
13795                 //Do scrolling
13796                 if(this.options.scroll) {
13797                         if(this.scrollParent[0] !== this.document[0] && this.scrollParent[0].tagName !== "HTML") {
13798
13799                                 if((this.overflowOffset.top + this.scrollParent[0].offsetHeight) - event.pageY < o.scrollSensitivity) {
13800                                         this.scrollParent[0].scrollTop = scrolled = this.scrollParent[0].scrollTop + o.scrollSpeed;
13801                                 } else if(event.pageY - this.overflowOffset.top < o.scrollSensitivity) {
13802                                         this.scrollParent[0].scrollTop = scrolled = this.scrollParent[0].scrollTop - o.scrollSpeed;
13803                                 }
13804
13805                                 if((this.overflowOffset.left + this.scrollParent[0].offsetWidth) - event.pageX < o.scrollSensitivity) {
13806                                         this.scrollParent[0].scrollLeft = scrolled = this.scrollParent[0].scrollLeft + o.scrollSpeed;
13807                                 } else if(event.pageX - this.overflowOffset.left < o.scrollSensitivity) {
13808                                         this.scrollParent[0].scrollLeft = scrolled = this.scrollParent[0].scrollLeft - o.scrollSpeed;
13809                                 }
13810
13811                         } else {
13812
13813                                 if(event.pageY - this.document.scrollTop() < o.scrollSensitivity) {
13814                                         scrolled = this.document.scrollTop(this.document.scrollTop() - o.scrollSpeed);
13815                                 } else if(this.window.height() - (event.pageY - this.document.scrollTop()) < o.scrollSensitivity) {
13816                                         scrolled = this.document.scrollTop(this.document.scrollTop() + o.scrollSpeed);
13817                                 }
13818
13819                                 if(event.pageX - this.document.scrollLeft() < o.scrollSensitivity) {
13820                                         scrolled = this.document.scrollLeft(this.document.scrollLeft() - o.scrollSpeed);
13821                                 } else if(this.window.width() - (event.pageX - this.document.scrollLeft()) < o.scrollSensitivity) {
13822                                         scrolled = this.document.scrollLeft(this.document.scrollLeft() + o.scrollSpeed);
13823                                 }
13824
13825                         }
13826
13827                         if(scrolled !== false && $.ui.ddmanager && !o.dropBehaviour) {
13828                                 $.ui.ddmanager.prepareOffsets(this, event);
13829                         }
13830                 }
13831
13832                 //Regenerate the absolute position used for position checks
13833                 this.positionAbs = this._convertPositionTo("absolute");
13834
13835                 //Set the helper position
13836                 if(!this.options.axis || this.options.axis !== "y") {
13837                         this.helper[0].style.left = this.position.left+"px";
13838                 }
13839                 if(!this.options.axis || this.options.axis !== "x") {
13840                         this.helper[0].style.top = this.position.top+"px";
13841                 }
13842
13843                 //Rearrange
13844                 for (i = this.items.length - 1; i >= 0; i--) {
13845
13846                         //Cache variables and intersection, continue if no intersection
13847                         item = this.items[i];
13848                         itemElement = item.item[0];
13849                         intersection = this._intersectsWithPointer(item);
13850                         if (!intersection) {
13851                                 continue;
13852                         }
13853
13854                         // Only put the placeholder inside the current Container, skip all
13855                         // items from other containers. This works because when moving
13856                         // an item from one container to another the
13857                         // currentContainer is switched before the placeholder is moved.
13858                         //
13859                         // Without this, moving items in "sub-sortables" can cause
13860                         // the placeholder to jitter between the outer and inner container.
13861                         if (item.instance !== this.currentContainer) {
13862                                 continue;
13863                         }
13864
13865                         // cannot intersect with itself
13866                         // no useless actions that have been done before
13867                         // no action if the item moved is the parent of the item checked
13868                         if (itemElement !== this.currentItem[0] &&
13869                                 this.placeholder[intersection === 1 ? "next" : "prev"]()[0] !== itemElement &&
13870                                 !$.contains(this.placeholder[0], itemElement) &&
13871                                 (this.options.type === "semi-dynamic" ? !$.contains(this.element[0], itemElement) : true)
13872                         ) {
13873
13874                                 this.direction = intersection === 1 ? "down" : "up";
13875
13876                                 if (this.options.tolerance === "pointer" || this._intersectsWithSides(item)) {
13877                                         this._rearrange(event, item);
13878                                 } else {
13879                                         break;
13880                                 }
13881
13882                                 this._trigger("change", event, this._uiHash());
13883                                 break;
13884                         }
13885                 }
13886
13887                 //Post events to containers
13888                 this._contactContainers(event);
13889
13890                 //Interconnect with droppables
13891                 if($.ui.ddmanager) {
13892                         $.ui.ddmanager.drag(this, event);
13893                 }
13894
13895                 //Call callbacks
13896                 this._trigger("sort", event, this._uiHash());
13897
13898                 this.lastPositionAbs = this.positionAbs;
13899                 return false;
13900
13901         },
13902
13903         _mouseStop: function(event, noPropagation) {
13904
13905                 if(!event) {
13906                         return;
13907                 }
13908
13909                 //If we are using droppables, inform the manager about the drop
13910                 if ($.ui.ddmanager && !this.options.dropBehaviour) {
13911                         $.ui.ddmanager.drop(this, event);
13912                 }
13913
13914                 if(this.options.revert) {
13915                         var that = this,
13916                                 cur = this.placeholder.offset(),
13917                                 axis = this.options.axis,
13918                                 animation = {};
13919
13920                         if ( !axis || axis === "x" ) {
13921                                 animation.left = cur.left - this.offset.parent.left - this.margins.left + (this.offsetParent[0] === this.document[0].body ? 0 : this.offsetParent[0].scrollLeft);
13922                         }
13923                         if ( !axis || axis === "y" ) {
13924                                 animation.top = cur.top - this.offset.parent.top - this.margins.top + (this.offsetParent[0] === this.document[0].body ? 0 : this.offsetParent[0].scrollTop);
13925                         }
13926                         this.reverting = true;
13927                         $(this.helper).animate( animation, parseInt(this.options.revert, 10) || 500, function() {
13928                                 that._clear(event);
13929                         });
13930                 } else {
13931                         this._clear(event, noPropagation);
13932                 }
13933
13934                 return false;
13935
13936         },
13937
13938         cancel: function() {
13939
13940                 if(this.dragging) {
13941
13942                         this._mouseUp({ target: null });
13943
13944                         if(this.options.helper === "original") {
13945                                 this.currentItem.css(this._storedCSS).removeClass("ui-sortable-helper");
13946                         } else {
13947                                 this.currentItem.show();
13948                         }
13949
13950                         //Post deactivating events to containers
13951                         for (var i = this.containers.length - 1; i >= 0; i--){
13952                                 this.containers[i]._trigger("deactivate", null, this._uiHash(this));
13953                                 if(this.containers[i].containerCache.over) {
13954                                         this.containers[i]._trigger("out", null, this._uiHash(this));
13955                                         this.containers[i].containerCache.over = 0;
13956                                 }
13957                         }
13958
13959                 }
13960
13961                 if (this.placeholder) {
13962                         //$(this.placeholder[0]).remove(); would have been the jQuery way - unfortunately, it unbinds ALL events from the original node!
13963                         if(this.placeholder[0].parentNode) {
13964                                 this.placeholder[0].parentNode.removeChild(this.placeholder[0]);
13965                         }
13966                         if(this.options.helper !== "original" && this.helper && this.helper[0].parentNode) {
13967                                 this.helper.remove();
13968                         }
13969
13970                         $.extend(this, {
13971                                 helper: null,
13972                                 dragging: false,
13973                                 reverting: false,
13974                                 _noFinalSort: null
13975                         });
13976
13977                         if(this.domPosition.prev) {
13978                                 $(this.domPosition.prev).after(this.currentItem);
13979                         } else {
13980                                 $(this.domPosition.parent).prepend(this.currentItem);
13981                         }
13982                 }
13983
13984                 return this;
13985
13986         },
13987
13988         serialize: function(o) {
13989
13990                 var items = this._getItemsAsjQuery(o && o.connected),
13991                         str = [];
13992                 o = o || {};
13993
13994                 $(items).each(function() {
13995                         var res = ($(o.item || this).attr(o.attribute || "id") || "").match(o.expression || (/(.+)[\-=_](.+)/));
13996                         if (res) {
13997                                 str.push((o.key || res[1]+"[]")+"="+(o.key && o.expression ? res[1] : res[2]));
13998                         }
13999                 });
14000
14001                 if(!str.length && o.key) {
14002                         str.push(o.key + "=");
14003                 }
14004
14005                 return str.join("&");
14006
14007         },
14008
14009         toArray: function(o) {
14010
14011                 var items = this._getItemsAsjQuery(o && o.connected),
14012                         ret = [];
14013
14014                 o = o || {};
14015
14016                 items.each(function() { ret.push($(o.item || this).attr(o.attribute || "id") || ""); });
14017                 return ret;
14018
14019         },
14020
14021         /* Be careful with the following core functions */
14022         _intersectsWith: function(item) {
14023
14024                 var x1 = this.positionAbs.left,
14025                         x2 = x1 + this.helperProportions.width,
14026                         y1 = this.positionAbs.top,
14027                         y2 = y1 + this.helperProportions.height,
14028                         l = item.left,
14029                         r = l + item.width,
14030                         t = item.top,
14031                         b = t + item.height,
14032                         dyClick = this.offset.click.top,
14033                         dxClick = this.offset.click.left,
14034                         isOverElementHeight = ( this.options.axis === "x" ) || ( ( y1 + dyClick ) > t && ( y1 + dyClick ) < b ),
14035                         isOverElementWidth = ( this.options.axis === "y" ) || ( ( x1 + dxClick ) > l && ( x1 + dxClick ) < r ),
14036                         isOverElement = isOverElementHeight && isOverElementWidth;
14037
14038                 if ( this.options.tolerance === "pointer" ||
14039                         this.options.forcePointerForContainers ||
14040                         (this.options.tolerance !== "pointer" && this.helperProportions[this.floating ? "width" : "height"] > item[this.floating ? "width" : "height"])
14041                 ) {
14042                         return isOverElement;
14043                 } else {
14044
14045                         return (l < x1 + (this.helperProportions.width / 2) && // Right Half
14046                                 x2 - (this.helperProportions.width / 2) < r && // Left Half
14047                                 t < y1 + (this.helperProportions.height / 2) && // Bottom Half
14048                                 y2 - (this.helperProportions.height / 2) < b ); // Top Half
14049
14050                 }
14051         },
14052
14053         _intersectsWithPointer: function(item) {
14054
14055                 var isOverElementHeight = (this.options.axis === "x") || this._isOverAxis(this.positionAbs.top + this.offset.click.top, item.top, item.height),
14056                         isOverElementWidth = (this.options.axis === "y") || this._isOverAxis(this.positionAbs.left + this.offset.click.left, item.left, item.width),
14057                         isOverElement = isOverElementHeight && isOverElementWidth,
14058                         verticalDirection = this._getDragVerticalDirection(),
14059                         horizontalDirection = this._getDragHorizontalDirection();
14060
14061                 if (!isOverElement) {
14062                         return false;
14063                 }
14064
14065                 return this.floating ?
14066                         ( ((horizontalDirection && horizontalDirection === "right") || verticalDirection === "down") ? 2 : 1 )
14067                         : ( verticalDirection && (verticalDirection === "down" ? 2 : 1) );
14068
14069         },
14070
14071         _intersectsWithSides: function(item) {
14072
14073                 var isOverBottomHalf = this._isOverAxis(this.positionAbs.top + this.offset.click.top, item.top + (item.height/2), item.height),
14074                         isOverRightHalf = this._isOverAxis(this.positionAbs.left + this.offset.click.left, item.left + (item.width/2), item.width),
14075                         verticalDirection = this._getDragVerticalDirection(),
14076                         horizontalDirection = this._getDragHorizontalDirection();
14077
14078                 if (this.floating && horizontalDirection) {
14079                         return ((horizontalDirection === "right" && isOverRightHalf) || (horizontalDirection === "left" && !isOverRightHalf));
14080                 } else {
14081                         return verticalDirection && ((verticalDirection === "down" && isOverBottomHalf) || (verticalDirection === "up" && !isOverBottomHalf));
14082                 }
14083
14084         },
14085
14086         _getDragVerticalDirection: function() {
14087                 var delta = this.positionAbs.top - this.lastPositionAbs.top;
14088                 return delta !== 0 && (delta > 0 ? "down" : "up");
14089         },
14090
14091         _getDragHorizontalDirection: function() {
14092                 var delta = this.positionAbs.left - this.lastPositionAbs.left;
14093                 return delta !== 0 && (delta > 0 ? "right" : "left");
14094         },
14095
14096         refresh: function(event) {
14097                 this._refreshItems(event);
14098                 this._setHandleClassName();
14099                 this.refreshPositions();
14100                 return this;
14101         },
14102
14103         _connectWith: function() {
14104                 var options = this.options;
14105                 return options.connectWith.constructor === String ? [options.connectWith] : options.connectWith;
14106         },
14107
14108         _getItemsAsjQuery: function(connected) {
14109
14110                 var i, j, cur, inst,
14111                         items = [],
14112                         queries = [],
14113                         connectWith = this._connectWith();
14114
14115                 if(connectWith && connected) {
14116                         for (i = connectWith.length - 1; i >= 0; i--){
14117                                 cur = $(connectWith[i], this.document[0]);
14118                                 for ( j = cur.length - 1; j >= 0; j--){
14119                                         inst = $.data(cur[j], this.widgetFullName);
14120                                         if(inst && inst !== this && !inst.options.disabled) {
14121                                                 queries.push([$.isFunction(inst.options.items) ? inst.options.items.call(inst.element) : $(inst.options.items, inst.element).not(".ui-sortable-helper").not(".ui-sortable-placeholder"), inst]);
14122                                         }
14123                                 }
14124                         }
14125                 }
14126
14127                 queries.push([$.isFunction(this.options.items) ? this.options.items.call(this.element, null, { options: this.options, item: this.currentItem }) : $(this.options.items, this.element).not(".ui-sortable-helper").not(".ui-sortable-placeholder"), this]);
14128
14129                 function addItems() {
14130                         items.push( this );
14131                 }
14132                 for (i = queries.length - 1; i >= 0; i--){
14133                         queries[i][0].each( addItems );
14134                 }
14135
14136                 return $(items);
14137
14138         },
14139
14140         _removeCurrentsFromItems: function() {
14141
14142                 var list = this.currentItem.find(":data(" + this.widgetName + "-item)");
14143
14144                 this.items = $.grep(this.items, function (item) {
14145                         for (var j=0; j < list.length; j++) {
14146                                 if(list[j] === item.item[0]) {
14147                                         return false;
14148                                 }
14149                         }
14150                         return true;
14151                 });
14152
14153         },
14154
14155         _refreshItems: function(event) {
14156
14157                 this.items = [];
14158                 this.containers = [this];
14159
14160                 var i, j, cur, inst, targetData, _queries, item, queriesLength,
14161                         items = this.items,
14162                         queries = [[$.isFunction(this.options.items) ? this.options.items.call(this.element[0], event, { item: this.currentItem }) : $(this.options.items, this.element), this]],
14163                         connectWith = this._connectWith();
14164
14165                 if(connectWith && this.ready) { //Shouldn't be run the first time through due to massive slow-down
14166                         for (i = connectWith.length - 1; i >= 0; i--){
14167                                 cur = $(connectWith[i], this.document[0]);
14168                                 for (j = cur.length - 1; j >= 0; j--){
14169                                         inst = $.data(cur[j], this.widgetFullName);
14170                                         if(inst && inst !== this && !inst.options.disabled) {
14171                                                 queries.push([$.isFunction(inst.options.items) ? inst.options.items.call(inst.element[0], event, { item: this.currentItem }) : $(inst.options.items, inst.element), inst]);
14172                                                 this.containers.push(inst);
14173                                         }
14174                                 }
14175                         }
14176                 }
14177
14178                 for (i = queries.length - 1; i >= 0; i--) {
14179                         targetData = queries[i][1];
14180                         _queries = queries[i][0];
14181
14182                         for (j=0, queriesLength = _queries.length; j < queriesLength; j++) {
14183                                 item = $(_queries[j]);
14184
14185                                 item.data(this.widgetName + "-item", targetData); // Data for target checking (mouse manager)
14186
14187                                 items.push({
14188                                         item: item,
14189                                         instance: targetData,
14190                                         width: 0, height: 0,
14191                                         left: 0, top: 0
14192                                 });
14193                         }
14194                 }
14195
14196         },
14197
14198         refreshPositions: function(fast) {
14199
14200                 // Determine whether items are being displayed horizontally
14201                 this.floating = this.items.length ?
14202                         this.options.axis === "x" || this._isFloating( this.items[ 0 ].item ) :
14203                         false;
14204
14205                 //This has to be redone because due to the item being moved out/into the offsetParent, the offsetParent's position will change
14206                 if(this.offsetParent && this.helper) {
14207                         this.offset.parent = this._getParentOffset();
14208                 }
14209
14210                 var i, item, t, p;
14211
14212                 for (i = this.items.length - 1; i >= 0; i--){
14213                         item = this.items[i];
14214
14215                         //We ignore calculating positions of all connected containers when we're not over them
14216                         if(item.instance !== this.currentContainer && this.currentContainer && item.item[0] !== this.currentItem[0]) {
14217                                 continue;
14218                         }
14219
14220                         t = this.options.toleranceElement ? $(this.options.toleranceElement, item.item) : item.item;
14221
14222                         if (!fast) {
14223                                 item.width = t.outerWidth();
14224                                 item.height = t.outerHeight();
14225                         }
14226
14227                         p = t.offset();
14228                         item.left = p.left;
14229                         item.top = p.top;
14230                 }
14231
14232                 if(this.options.custom && this.options.custom.refreshContainers) {
14233                         this.options.custom.refreshContainers.call(this);
14234                 } else {
14235                         for (i = this.containers.length - 1; i >= 0; i--){
14236                                 p = this.containers[i].element.offset();
14237                                 this.containers[i].containerCache.left = p.left;
14238                                 this.containers[i].containerCache.top = p.top;
14239                                 this.containers[i].containerCache.width = this.containers[i].element.outerWidth();
14240                                 this.containers[i].containerCache.height = this.containers[i].element.outerHeight();
14241                         }
14242                 }
14243
14244                 return this;
14245         },
14246
14247         _createPlaceholder: function(that) {
14248                 that = that || this;
14249                 var className,
14250                         o = that.options;
14251
14252                 if(!o.placeholder || o.placeholder.constructor === String) {
14253                         className = o.placeholder;
14254                         o.placeholder = {
14255                                 element: function() {
14256
14257                                         var nodeName = that.currentItem[0].nodeName.toLowerCase(),
14258                                                 element = $( "<" + nodeName + ">", that.document[0] )
14259                                                         .addClass(className || that.currentItem[0].className+" ui-sortable-placeholder")
14260                                                         .removeClass("ui-sortable-helper");
14261
14262                                         if ( nodeName === "tbody" ) {
14263                                                 that._createTrPlaceholder(
14264                                                         that.currentItem.find( "tr" ).eq( 0 ),
14265                                                         $( "<tr>", that.document[ 0 ] ).appendTo( element )
14266                                                 );
14267                                         } else if ( nodeName === "tr" ) {
14268                                                 that._createTrPlaceholder( that.currentItem, element );
14269                                         } else if ( nodeName === "img" ) {
14270                                                 element.attr( "src", that.currentItem.attr( "src" ) );
14271                                         }
14272
14273                                         if ( !className ) {
14274                                                 element.css( "visibility", "hidden" );
14275                                         }
14276
14277                                         return element;
14278                                 },
14279                                 update: function(container, p) {
14280
14281                                         // 1. If a className is set as 'placeholder option, we don't force sizes - the class is responsible for that
14282                                         // 2. The option 'forcePlaceholderSize can be enabled to force it even if a class name is specified
14283                                         if(className && !o.forcePlaceholderSize) {
14284                                                 return;
14285                                         }
14286
14287                                         //If the element doesn't have a actual height by itself (without styles coming from a stylesheet), it receives the inline height from the dragged item
14288                                         if(!p.height()) { p.height(that.currentItem.innerHeight() - parseInt(that.currentItem.css("paddingTop")||0, 10) - parseInt(that.currentItem.css("paddingBottom")||0, 10)); }
14289                                         if(!p.width()) { p.width(that.currentItem.innerWidth() - parseInt(that.currentItem.css("paddingLeft")||0, 10) - parseInt(that.currentItem.css("paddingRight")||0, 10)); }
14290                                 }
14291                         };
14292                 }
14293
14294                 //Create the placeholder
14295                 that.placeholder = $(o.placeholder.element.call(that.element, that.currentItem));
14296
14297                 //Append it after the actual current item
14298                 that.currentItem.after(that.placeholder);
14299
14300                 //Update the size of the placeholder (TODO: Logic to fuzzy, see line 316/317)
14301                 o.placeholder.update(that, that.placeholder);
14302
14303         },
14304
14305         _createTrPlaceholder: function( sourceTr, targetTr ) {
14306                 var that = this;
14307
14308                 sourceTr.children().each(function() {
14309                         $( "<td>&#160;</td>", that.document[ 0 ] )
14310                                 .attr( "colspan", $( this ).attr( "colspan" ) || 1 )
14311                                 .appendTo( targetTr );
14312                 });
14313         },
14314
14315         _contactContainers: function(event) {
14316                 var i, j, dist, itemWithLeastDistance, posProperty, sizeProperty, cur, nearBottom, floating, axis,
14317                         innermostContainer = null,
14318                         innermostIndex = null;
14319
14320                 // get innermost container that intersects with item
14321                 for (i = this.containers.length - 1; i >= 0; i--) {
14322
14323                         // never consider a container that's located within the item itself
14324                         if($.contains(this.currentItem[0], this.containers[i].element[0])) {
14325                                 continue;
14326                         }
14327
14328                         if(this._intersectsWith(this.containers[i].containerCache)) {
14329
14330                                 // if we've already found a container and it's more "inner" than this, then continue
14331                                 if(innermostContainer && $.contains(this.containers[i].element[0], innermostContainer.element[0])) {
14332                                         continue;
14333                                 }
14334
14335                                 innermostContainer = this.containers[i];
14336                                 innermostIndex = i;
14337
14338                         } else {
14339                                 // container doesn't intersect. trigger "out" event if necessary
14340                                 if(this.containers[i].containerCache.over) {
14341                                         this.containers[i]._trigger("out", event, this._uiHash(this));
14342                                         this.containers[i].containerCache.over = 0;
14343                                 }
14344                         }
14345
14346                 }
14347
14348                 // if no intersecting containers found, return
14349                 if(!innermostContainer) {
14350                         return;
14351                 }
14352
14353                 // move the item into the container if it's not there already
14354                 if(this.containers.length === 1) {
14355                         if (!this.containers[innermostIndex].containerCache.over) {
14356                                 this.containers[innermostIndex]._trigger("over", event, this._uiHash(this));
14357                                 this.containers[innermostIndex].containerCache.over = 1;
14358                         }
14359                 } else {
14360
14361                         //When entering a new container, we will find the item with the least distance and append our item near it
14362                         dist = 10000;
14363                         itemWithLeastDistance = null;
14364                         floating = innermostContainer.floating || this._isFloating(this.currentItem);
14365                         posProperty = floating ? "left" : "top";
14366                         sizeProperty = floating ? "width" : "height";
14367                         axis = floating ? "clientX" : "clientY";
14368
14369                         for (j = this.items.length - 1; j >= 0; j--) {
14370                                 if(!$.contains(this.containers[innermostIndex].element[0], this.items[j].item[0])) {
14371                                         continue;
14372                                 }
14373                                 if(this.items[j].item[0] === this.currentItem[0]) {
14374                                         continue;
14375                                 }
14376
14377                                 cur = this.items[j].item.offset()[posProperty];
14378                                 nearBottom = false;
14379                                 if ( event[ axis ] - cur > this.items[ j ][ sizeProperty ] / 2 ) {
14380                                         nearBottom = true;
14381                                 }
14382
14383                                 if ( Math.abs( event[ axis ] - cur ) < dist ) {
14384                                         dist = Math.abs( event[ axis ] - cur );
14385                                         itemWithLeastDistance = this.items[ j ];
14386                                         this.direction = nearBottom ? "up": "down";
14387                                 }
14388                         }
14389
14390                         //Check if dropOnEmpty is enabled
14391                         if(!itemWithLeastDistance && !this.options.dropOnEmpty) {
14392                                 return;
14393                         }
14394
14395                         if(this.currentContainer === this.containers[innermostIndex]) {
14396                                 if ( !this.currentContainer.containerCache.over ) {
14397                                         this.containers[ innermostIndex ]._trigger( "over", event, this._uiHash() );
14398                                         this.currentContainer.containerCache.over = 1;
14399                                 }
14400                                 return;
14401                         }
14402
14403                         itemWithLeastDistance ? this._rearrange(event, itemWithLeastDistance, null, true) : this._rearrange(event, null, this.containers[innermostIndex].element, true);
14404                         this._trigger("change", event, this._uiHash());
14405                         this.containers[innermostIndex]._trigger("change", event, this._uiHash(this));
14406                         this.currentContainer = this.containers[innermostIndex];
14407
14408                         //Update the placeholder
14409                         this.options.placeholder.update(this.currentContainer, this.placeholder);
14410
14411                         this.containers[innermostIndex]._trigger("over", event, this._uiHash(this));
14412                         this.containers[innermostIndex].containerCache.over = 1;
14413                 }
14414
14415
14416         },
14417
14418         _createHelper: function(event) {
14419
14420                 var o = this.options,
14421                         helper = $.isFunction(o.helper) ? $(o.helper.apply(this.element[0], [event, this.currentItem])) : (o.helper === "clone" ? this.currentItem.clone() : this.currentItem);
14422
14423                 //Add the helper to the DOM if that didn't happen already
14424                 if(!helper.parents("body").length) {
14425                         $(o.appendTo !== "parent" ? o.appendTo : this.currentItem[0].parentNode)[0].appendChild(helper[0]);
14426                 }
14427
14428                 if(helper[0] === this.currentItem[0]) {
14429                         this._storedCSS = { width: this.currentItem[0].style.width, height: this.currentItem[0].style.height, position: this.currentItem.css("position"), top: this.currentItem.css("top"), left: this.currentItem.css("left") };
14430                 }
14431
14432                 if(!helper[0].style.width || o.forceHelperSize) {
14433                         helper.width(this.currentItem.width());
14434                 }
14435                 if(!helper[0].style.height || o.forceHelperSize) {
14436                         helper.height(this.currentItem.height());
14437                 }
14438
14439                 return helper;
14440
14441         },
14442
14443         _adjustOffsetFromHelper: function(obj) {
14444                 if (typeof obj === "string") {
14445                         obj = obj.split(" ");
14446                 }
14447                 if ($.isArray(obj)) {
14448                         obj = {left: +obj[0], top: +obj[1] || 0};
14449                 }
14450                 if ("left" in obj) {
14451                         this.offset.click.left = obj.left + this.margins.left;
14452                 }
14453                 if ("right" in obj) {
14454                         this.offset.click.left = this.helperProportions.width - obj.right + this.margins.left;
14455                 }
14456                 if ("top" in obj) {
14457                         this.offset.click.top = obj.top + this.margins.top;
14458                 }
14459                 if ("bottom" in obj) {
14460                         this.offset.click.top = this.helperProportions.height - obj.bottom + this.margins.top;
14461                 }
14462         },
14463
14464         _getParentOffset: function() {
14465
14466
14467                 //Get the offsetParent and cache its position
14468                 this.offsetParent = this.helper.offsetParent();
14469                 var po = this.offsetParent.offset();
14470
14471                 // This is a special case where we need to modify a offset calculated on start, since the following happened:
14472                 // 1. The position of the helper is absolute, so it's position is calculated based on the next positioned parent
14473                 // 2. The actual offset parent is a child of the scroll parent, and the scroll parent isn't the document, which means that
14474                 //    the scroll is included in the initial calculation of the offset of the parent, and never recalculated upon drag
14475                 if(this.cssPosition === "absolute" && this.scrollParent[0] !== this.document[0] && $.contains(this.scrollParent[0], this.offsetParent[0])) {
14476                         po.left += this.scrollParent.scrollLeft();
14477                         po.top += this.scrollParent.scrollTop();
14478                 }
14479
14480                 // This needs to be actually done for all browsers, since pageX/pageY includes this information
14481                 // with an ugly IE fix
14482                 if( this.offsetParent[0] === this.document[0].body || (this.offsetParent[0].tagName && this.offsetParent[0].tagName.toLowerCase() === "html" && $.ui.ie)) {
14483                         po = { top: 0, left: 0 };
14484                 }
14485
14486                 return {
14487                         top: po.top + (parseInt(this.offsetParent.css("borderTopWidth"),10) || 0),
14488                         left: po.left + (parseInt(this.offsetParent.css("borderLeftWidth"),10) || 0)
14489                 };
14490
14491         },
14492
14493         _getRelativeOffset: function() {
14494
14495                 if(this.cssPosition === "relative") {
14496                         var p = this.currentItem.position();
14497                         return {
14498                                 top: p.top - (parseInt(this.helper.css("top"),10) || 0) + this.scrollParent.scrollTop(),
14499                                 left: p.left - (parseInt(this.helper.css("left"),10) || 0) + this.scrollParent.scrollLeft()
14500                         };
14501                 } else {
14502                         return { top: 0, left: 0 };
14503                 }
14504
14505         },
14506
14507         _cacheMargins: function() {
14508                 this.margins = {
14509                         left: (parseInt(this.currentItem.css("marginLeft"),10) || 0),
14510                         top: (parseInt(this.currentItem.css("marginTop"),10) || 0)
14511                 };
14512         },
14513
14514         _cacheHelperProportions: function() {
14515                 this.helperProportions = {
14516                         width: this.helper.outerWidth(),
14517                         height: this.helper.outerHeight()
14518                 };
14519         },
14520
14521         _setContainment: function() {
14522
14523                 var ce, co, over,
14524                         o = this.options;
14525                 if(o.containment === "parent") {
14526                         o.containment = this.helper[0].parentNode;
14527                 }
14528                 if(o.containment === "document" || o.containment === "window") {
14529                         this.containment = [
14530                                 0 - this.offset.relative.left - this.offset.parent.left,
14531                                 0 - this.offset.relative.top - this.offset.parent.top,
14532                                 o.containment === "document" ? this.document.width() : this.window.width() - this.helperProportions.width - this.margins.left,
14533                                 (o.containment === "document" ? this.document.width() : this.window.height() || this.document[0].body.parentNode.scrollHeight) - this.helperProportions.height - this.margins.top
14534                         ];
14535                 }
14536
14537                 if(!(/^(document|window|parent)$/).test(o.containment)) {
14538                         ce = $(o.containment)[0];
14539                         co = $(o.containment).offset();
14540                         over = ($(ce).css("overflow") !== "hidden");
14541
14542                         this.containment = [
14543                                 co.left + (parseInt($(ce).css("borderLeftWidth"),10) || 0) + (parseInt($(ce).css("paddingLeft"),10) || 0) - this.margins.left,
14544                                 co.top + (parseInt($(ce).css("borderTopWidth"),10) || 0) + (parseInt($(ce).css("paddingTop"),10) || 0) - this.margins.top,
14545                                 co.left+(over ? Math.max(ce.scrollWidth,ce.offsetWidth) : ce.offsetWidth) - (parseInt($(ce).css("borderLeftWidth"),10) || 0) - (parseInt($(ce).css("paddingRight"),10) || 0) - this.helperProportions.width - this.margins.left,
14546                                 co.top+(over ? Math.max(ce.scrollHeight,ce.offsetHeight) : ce.offsetHeight) - (parseInt($(ce).css("borderTopWidth"),10) || 0) - (parseInt($(ce).css("paddingBottom"),10) || 0) - this.helperProportions.height - this.margins.top
14547                         ];
14548                 }
14549
14550         },
14551
14552         _convertPositionTo: function(d, pos) {
14553
14554                 if(!pos) {
14555                         pos = this.position;
14556                 }
14557                 var mod = d === "absolute" ? 1 : -1,
14558                         scroll = this.cssPosition === "absolute" && !(this.scrollParent[0] !== this.document[0] && $.contains(this.scrollParent[0], this.offsetParent[0])) ? this.offsetParent : this.scrollParent,
14559                         scrollIsRootNode = (/(html|body)/i).test(scroll[0].tagName);
14560
14561                 return {
14562                         top: (
14563                                 pos.top +                                                                                                                               // The absolute mouse position
14564                                 this.offset.relative.top * mod +                                                                                // Only for relative positioned nodes: Relative offset from element to offset parent
14565                                 this.offset.parent.top * mod -                                                                                  // The offsetParent's offset without borders (offset + border)
14566                                 ( ( this.cssPosition === "fixed" ? -this.scrollParent.scrollTop() : ( scrollIsRootNode ? 0 : scroll.scrollTop() ) ) * mod)
14567                         ),
14568                         left: (
14569                                 pos.left +                                                                                                                              // The absolute mouse position
14570                                 this.offset.relative.left * mod +                                                                               // Only for relative positioned nodes: Relative offset from element to offset parent
14571                                 this.offset.parent.left * mod   -                                                                               // The offsetParent's offset without borders (offset + border)
14572                                 ( ( this.cssPosition === "fixed" ? -this.scrollParent.scrollLeft() : scrollIsRootNode ? 0 : scroll.scrollLeft() ) * mod)
14573                         )
14574                 };
14575
14576         },
14577
14578         _generatePosition: function(event) {
14579
14580                 var top, left,
14581                         o = this.options,
14582                         pageX = event.pageX,
14583                         pageY = event.pageY,
14584                         scroll = this.cssPosition === "absolute" && !(this.scrollParent[0] !== this.document[0] && $.contains(this.scrollParent[0], this.offsetParent[0])) ? this.offsetParent : this.scrollParent, scrollIsRootNode = (/(html|body)/i).test(scroll[0].tagName);
14585
14586                 // This is another very weird special case that only happens for relative elements:
14587                 // 1. If the css position is relative
14588                 // 2. and the scroll parent is the document or similar to the offset parent
14589                 // we have to refresh the relative offset during the scroll so there are no jumps
14590                 if(this.cssPosition === "relative" && !(this.scrollParent[0] !== this.document[0] && this.scrollParent[0] !== this.offsetParent[0])) {
14591                         this.offset.relative = this._getRelativeOffset();
14592                 }
14593
14594                 /*
14595                  * - Position constraining -
14596                  * Constrain the position to a mix of grid, containment.
14597                  */
14598
14599                 if(this.originalPosition) { //If we are not dragging yet, we won't check for options
14600
14601                         if(this.containment) {
14602                                 if(event.pageX - this.offset.click.left < this.containment[0]) {
14603                                         pageX = this.containment[0] + this.offset.click.left;
14604                                 }
14605                                 if(event.pageY - this.offset.click.top < this.containment[1]) {
14606                                         pageY = this.containment[1] + this.offset.click.top;
14607                                 }
14608                                 if(event.pageX - this.offset.click.left > this.containment[2]) {
14609                                         pageX = this.containment[2] + this.offset.click.left;
14610                                 }
14611                                 if(event.pageY - this.offset.click.top > this.containment[3]) {
14612                                         pageY = this.containment[3] + this.offset.click.top;
14613                                 }
14614                         }
14615
14616                         if(o.grid) {
14617                                 top = this.originalPageY + Math.round((pageY - this.originalPageY) / o.grid[1]) * o.grid[1];
14618                                 pageY = this.containment ? ( (top - this.offset.click.top >= this.containment[1] && top - this.offset.click.top <= this.containment[3]) ? top : ((top - this.offset.click.top >= this.containment[1]) ? top - o.grid[1] : top + o.grid[1])) : top;
14619
14620                                 left = this.originalPageX + Math.round((pageX - this.originalPageX) / o.grid[0]) * o.grid[0];
14621                                 pageX = this.containment ? ( (left - this.offset.click.left >= this.containment[0] && left - this.offset.click.left <= this.containment[2]) ? left : ((left - this.offset.click.left >= this.containment[0]) ? left - o.grid[0] : left + o.grid[0])) : left;
14622                         }
14623
14624                 }
14625
14626                 return {
14627                         top: (
14628                                 pageY -                                                                                                                         // The absolute mouse position
14629                                 this.offset.click.top -                                                                                                 // Click offset (relative to the element)
14630                                 this.offset.relative.top        -                                                                                       // Only for relative positioned nodes: Relative offset from element to offset parent
14631                                 this.offset.parent.top +                                                                                                // The offsetParent's offset without borders (offset + border)
14632                                 ( ( this.cssPosition === "fixed" ? -this.scrollParent.scrollTop() : ( scrollIsRootNode ? 0 : scroll.scrollTop() ) ))
14633                         ),
14634                         left: (
14635                                 pageX -                                                                                                                         // The absolute mouse position
14636                                 this.offset.click.left -                                                                                                // Click offset (relative to the element)
14637                                 this.offset.relative.left       -                                                                                       // Only for relative positioned nodes: Relative offset from element to offset parent
14638                                 this.offset.parent.left +                                                                                               // The offsetParent's offset without borders (offset + border)
14639                                 ( ( this.cssPosition === "fixed" ? -this.scrollParent.scrollLeft() : scrollIsRootNode ? 0 : scroll.scrollLeft() ))
14640                         )
14641                 };
14642
14643         },
14644
14645         _rearrange: function(event, i, a, hardRefresh) {
14646
14647                 a ? a[0].appendChild(this.placeholder[0]) : i.item[0].parentNode.insertBefore(this.placeholder[0], (this.direction === "down" ? i.item[0] : i.item[0].nextSibling));
14648
14649                 //Various things done here to improve the performance:
14650                 // 1. we create a setTimeout, that calls refreshPositions
14651                 // 2. on the instance, we have a counter variable, that get's higher after every append
14652                 // 3. on the local scope, we copy the counter variable, and check in the timeout, if it's still the same
14653                 // 4. this lets only the last addition to the timeout stack through
14654                 this.counter = this.counter ? ++this.counter : 1;
14655                 var counter = this.counter;
14656
14657                 this._delay(function() {
14658                         if(counter === this.counter) {
14659                                 this.refreshPositions(!hardRefresh); //Precompute after each DOM insertion, NOT on mousemove
14660                         }
14661                 });
14662
14663         },
14664
14665         _clear: function(event, noPropagation) {
14666
14667                 this.reverting = false;
14668                 // We delay all events that have to be triggered to after the point where the placeholder has been removed and
14669                 // everything else normalized again
14670                 var i,
14671                         delayedTriggers = [];
14672
14673                 // We first have to update the dom position of the actual currentItem
14674                 // Note: don't do it if the current item is already removed (by a user), or it gets reappended (see #4088)
14675                 if(!this._noFinalSort && this.currentItem.parent().length) {
14676                         this.placeholder.before(this.currentItem);
14677                 }
14678                 this._noFinalSort = null;
14679
14680                 if(this.helper[0] === this.currentItem[0]) {
14681                         for(i in this._storedCSS) {
14682                                 if(this._storedCSS[i] === "auto" || this._storedCSS[i] === "static") {
14683                                         this._storedCSS[i] = "";
14684                                 }
14685                         }
14686                         this.currentItem.css(this._storedCSS).removeClass("ui-sortable-helper");
14687                 } else {
14688                         this.currentItem.show();
14689                 }
14690
14691                 if(this.fromOutside && !noPropagation) {
14692                         delayedTriggers.push(function(event) { this._trigger("receive", event, this._uiHash(this.fromOutside)); });
14693                 }
14694                 if((this.fromOutside || this.domPosition.prev !== this.currentItem.prev().not(".ui-sortable-helper")[0] || this.domPosition.parent !== this.currentItem.parent()[0]) && !noPropagation) {
14695                         delayedTriggers.push(function(event) { this._trigger("update", event, this._uiHash()); }); //Trigger update callback if the DOM position has changed
14696                 }
14697
14698                 // Check if the items Container has Changed and trigger appropriate
14699                 // events.
14700                 if (this !== this.currentContainer) {
14701                         if(!noPropagation) {
14702                                 delayedTriggers.push(function(event) { this._trigger("remove", event, this._uiHash()); });
14703                                 delayedTriggers.push((function(c) { return function(event) { c._trigger("receive", event, this._uiHash(this)); };  }).call(this, this.currentContainer));
14704                                 delayedTriggers.push((function(c) { return function(event) { c._trigger("update", event, this._uiHash(this));  }; }).call(this, this.currentContainer));
14705                         }
14706                 }
14707
14708
14709                 //Post events to containers
14710                 function delayEvent( type, instance, container ) {
14711                         return function( event ) {
14712                                 container._trigger( type, event, instance._uiHash( instance ) );
14713                         };
14714                 }
14715                 for (i = this.containers.length - 1; i >= 0; i--){
14716                         if (!noPropagation) {
14717                                 delayedTriggers.push( delayEvent( "deactivate", this, this.containers[ i ] ) );
14718                         }
14719                         if(this.containers[i].containerCache.over) {
14720                                 delayedTriggers.push( delayEvent( "out", this, this.containers[ i ] ) );
14721                                 this.containers[i].containerCache.over = 0;
14722                         }
14723                 }
14724
14725                 //Do what was originally in plugins
14726                 if ( this.storedCursor ) {
14727                         this.document.find( "body" ).css( "cursor", this.storedCursor );
14728                         this.storedStylesheet.remove();
14729                 }
14730                 if(this._storedOpacity) {
14731                         this.helper.css("opacity", this._storedOpacity);
14732                 }
14733                 if(this._storedZIndex) {
14734                         this.helper.css("zIndex", this._storedZIndex === "auto" ? "" : this._storedZIndex);
14735                 }
14736
14737                 this.dragging = false;
14738
14739                 if(!noPropagation) {
14740                         this._trigger("beforeStop", event, this._uiHash());
14741                 }
14742
14743                 //$(this.placeholder[0]).remove(); would have been the jQuery way - unfortunately, it unbinds ALL events from the original node!
14744                 this.placeholder[0].parentNode.removeChild(this.placeholder[0]);
14745
14746                 if ( !this.cancelHelperRemoval ) {
14747                         if ( this.helper[ 0 ] !== this.currentItem[ 0 ] ) {
14748                                 this.helper.remove();
14749                         }
14750                         this.helper = null;
14751                 }
14752
14753                 if(!noPropagation) {
14754                         for (i=0; i < delayedTriggers.length; i++) {
14755                                 delayedTriggers[i].call(this, event);
14756                         } //Trigger all delayed events
14757                         this._trigger("stop", event, this._uiHash());
14758                 }
14759
14760                 this.fromOutside = false;
14761                 return !this.cancelHelperRemoval;
14762
14763         },
14764
14765         _trigger: function() {
14766                 if ($.Widget.prototype._trigger.apply(this, arguments) === false) {
14767                         this.cancel();
14768                 }
14769         },
14770
14771         _uiHash: function(_inst) {
14772                 var inst = _inst || this;
14773                 return {
14774                         helper: inst.helper,
14775                         placeholder: inst.placeholder || $([]),
14776                         position: inst.position,
14777                         originalPosition: inst.originalPosition,
14778                         offset: inst.positionAbs,
14779                         item: inst.currentItem,
14780                         sender: _inst ? _inst.element : null
14781                 };
14782         }
14783
14784 });
14785
14786
14787 /*!
14788  * jQuery UI Spinner 1.11.4
14789  * http://jqueryui.com
14790  *
14791  * Copyright jQuery Foundation and other contributors
14792  * Released under the MIT license.
14793  * http://jquery.org/license
14794  *
14795  * http://api.jqueryui.com/spinner/
14796  */
14797
14798
14799 function spinner_modifier( fn ) {
14800         return function() {
14801                 var previous = this.element.val();
14802                 fn.apply( this, arguments );
14803                 this._refresh();
14804                 if ( previous !== this.element.val() ) {
14805                         this._trigger( "change" );
14806                 }
14807         };
14808 }
14809
14810 var spinner = $.widget( "ui.spinner", {
14811         version: "1.11.4",
14812         defaultElement: "<input>",
14813         widgetEventPrefix: "spin",
14814         options: {
14815                 culture: null,
14816                 icons: {
14817                         down: "ui-icon-triangle-1-s",
14818                         up: "ui-icon-triangle-1-n"
14819                 },
14820                 incremental: true,
14821                 max: null,
14822                 min: null,
14823                 numberFormat: null,
14824                 page: 10,
14825                 step: 1,
14826
14827                 change: null,
14828                 spin: null,
14829                 start: null,
14830                 stop: null
14831         },
14832
14833         _create: function() {
14834                 // handle string values that need to be parsed
14835                 this._setOption( "max", this.options.max );
14836                 this._setOption( "min", this.options.min );
14837                 this._setOption( "step", this.options.step );
14838
14839                 // Only format if there is a value, prevents the field from being marked
14840                 // as invalid in Firefox, see #9573.
14841                 if ( this.value() !== "" ) {
14842                         // Format the value, but don't constrain.
14843                         this._value( this.element.val(), true );
14844                 }
14845
14846                 this._draw();
14847                 this._on( this._events );
14848                 this._refresh();
14849
14850                 // turning off autocomplete prevents the browser from remembering the
14851                 // value when navigating through history, so we re-enable autocomplete
14852                 // if the page is unloaded before the widget is destroyed. #7790
14853                 this._on( this.window, {
14854                         beforeunload: function() {
14855                                 this.element.removeAttr( "autocomplete" );
14856                         }
14857                 });
14858         },
14859
14860         _getCreateOptions: function() {
14861                 var options = {},
14862                         element = this.element;
14863
14864                 $.each( [ "min", "max", "step" ], function( i, option ) {
14865                         var value = element.attr( option );
14866                         if ( value !== undefined && value.length ) {
14867                                 options[ option ] = value;
14868                         }
14869                 });
14870
14871                 return options;
14872         },
14873
14874         _events: {
14875                 keydown: function( event ) {
14876                         if ( this._start( event ) && this._keydown( event ) ) {
14877                                 event.preventDefault();
14878                         }
14879                 },
14880                 keyup: "_stop",
14881                 focus: function() {
14882                         this.previous = this.element.val();
14883                 },
14884                 blur: function( event ) {
14885                         if ( this.cancelBlur ) {
14886                                 delete this.cancelBlur;
14887                                 return;
14888                         }
14889
14890                         this._stop();
14891                         this._refresh();
14892                         if ( this.previous !== this.element.val() ) {
14893                                 this._trigger( "change", event );
14894                         }
14895                 },
14896                 mousewheel: function( event, delta ) {
14897                         if ( !delta ) {
14898                                 return;
14899                         }
14900                         if ( !this.spinning && !this._start( event ) ) {
14901                                 return false;
14902                         }
14903
14904                         this._spin( (delta > 0 ? 1 : -1) * this.options.step, event );
14905                         clearTimeout( this.mousewheelTimer );
14906                         this.mousewheelTimer = this._delay(function() {
14907                                 if ( this.spinning ) {
14908                                         this._stop( event );
14909                                 }
14910                         }, 100 );
14911                         event.preventDefault();
14912                 },
14913                 "mousedown .ui-spinner-button": function( event ) {
14914                         var previous;
14915
14916                         // We never want the buttons to have focus; whenever the user is
14917                         // interacting with the spinner, the focus should be on the input.
14918                         // If the input is focused then this.previous is properly set from
14919                         // when the input first received focus. If the input is not focused
14920                         // then we need to set this.previous based on the value before spinning.
14921                         previous = this.element[0] === this.document[0].activeElement ?
14922                                 this.previous : this.element.val();
14923                         function checkFocus() {
14924                                 var isActive = this.element[0] === this.document[0].activeElement;
14925                                 if ( !isActive ) {
14926                                         this.element.focus();
14927                                         this.previous = previous;
14928                                         // support: IE
14929                                         // IE sets focus asynchronously, so we need to check if focus
14930                                         // moved off of the input because the user clicked on the button.
14931                                         this._delay(function() {
14932                                                 this.previous = previous;
14933                                         });
14934                                 }
14935                         }
14936
14937                         // ensure focus is on (or stays on) the text field
14938                         event.preventDefault();
14939                         checkFocus.call( this );
14940
14941                         // support: IE
14942                         // IE doesn't prevent moving focus even with event.preventDefault()
14943                         // so we set a flag to know when we should ignore the blur event
14944                         // and check (again) if focus moved off of the input.
14945                         this.cancelBlur = true;
14946                         this._delay(function() {
14947                                 delete this.cancelBlur;
14948                                 checkFocus.call( this );
14949                         });
14950
14951                         if ( this._start( event ) === false ) {
14952                                 return;
14953                         }
14954
14955                         this._repeat( null, $( event.currentTarget ).hasClass( "ui-spinner-up" ) ? 1 : -1, event );
14956                 },
14957                 "mouseup .ui-spinner-button": "_stop",
14958                 "mouseenter .ui-spinner-button": function( event ) {
14959                         // button will add ui-state-active if mouse was down while mouseleave and kept down
14960                         if ( !$( event.currentTarget ).hasClass( "ui-state-active" ) ) {
14961                                 return;
14962                         }
14963
14964                         if ( this._start( event ) === false ) {
14965                                 return false;
14966                         }
14967                         this._repeat( null, $( event.currentTarget ).hasClass( "ui-spinner-up" ) ? 1 : -1, event );
14968                 },
14969                 // TODO: do we really want to consider this a stop?
14970                 // shouldn't we just stop the repeater and wait until mouseup before
14971                 // we trigger the stop event?
14972                 "mouseleave .ui-spinner-button": "_stop"
14973         },
14974
14975         _draw: function() {
14976                 var uiSpinner = this.uiSpinner = this.element
14977                         .addClass( "ui-spinner-input" )
14978                         .attr( "autocomplete", "off" )
14979                         .wrap( this._uiSpinnerHtml() )
14980                         .parent()
14981                                 // add buttons
14982                                 .append( this._buttonHtml() );
14983
14984                 this.element.attr( "role", "spinbutton" );
14985
14986                 // button bindings
14987                 this.buttons = uiSpinner.find( ".ui-spinner-button" )
14988                         .attr( "tabIndex", -1 )
14989                         .button()
14990                         .removeClass( "ui-corner-all" );
14991
14992                 // IE 6 doesn't understand height: 50% for the buttons
14993                 // unless the wrapper has an explicit height
14994                 if ( this.buttons.height() > Math.ceil( uiSpinner.height() * 0.5 ) &&
14995                                 uiSpinner.height() > 0 ) {
14996                         uiSpinner.height( uiSpinner.height() );
14997                 }
14998
14999                 // disable spinner if element was already disabled
15000                 if ( this.options.disabled ) {
15001                         this.disable();
15002                 }
15003         },
15004
15005         _keydown: function( event ) {
15006                 var options = this.options,
15007                         keyCode = $.ui.keyCode;
15008
15009                 switch ( event.keyCode ) {
15010                 case keyCode.UP:
15011                         this._repeat( null, 1, event );
15012                         return true;
15013                 case keyCode.DOWN:
15014                         this._repeat( null, -1, event );
15015                         return true;
15016                 case keyCode.PAGE_UP:
15017                         this._repeat( null, options.page, event );
15018                         return true;
15019                 case keyCode.PAGE_DOWN:
15020                         this._repeat( null, -options.page, event );
15021                         return true;
15022                 }
15023
15024                 return false;
15025         },
15026
15027         _uiSpinnerHtml: function() {
15028                 return "<span class='ui-spinner ui-widget ui-widget-content ui-corner-all'></span>";
15029         },
15030
15031         _buttonHtml: function() {
15032                 return "" +
15033                         "<a class='ui-spinner-button ui-spinner-up ui-corner-tr'>" +
15034                                 "<span class='ui-icon " + this.options.icons.up + "'>&#9650;</span>" +
15035                         "</a>" +
15036                         "<a class='ui-spinner-button ui-spinner-down ui-corner-br'>" +
15037                                 "<span class='ui-icon " + this.options.icons.down + "'>&#9660;</span>" +
15038                         "</a>";
15039         },
15040
15041         _start: function( event ) {
15042                 if ( !this.spinning && this._trigger( "start", event ) === false ) {
15043                         return false;
15044                 }
15045
15046                 if ( !this.counter ) {
15047                         this.counter = 1;
15048                 }
15049                 this.spinning = true;
15050                 return true;
15051         },
15052
15053         _repeat: function( i, steps, event ) {
15054                 i = i || 500;
15055
15056                 clearTimeout( this.timer );
15057                 this.timer = this._delay(function() {
15058                         this._repeat( 40, steps, event );
15059                 }, i );
15060
15061                 this._spin( steps * this.options.step, event );
15062         },
15063
15064         _spin: function( step, event ) {
15065                 var value = this.value() || 0;
15066
15067                 if ( !this.counter ) {
15068                         this.counter = 1;
15069                 }
15070
15071                 value = this._adjustValue( value + step * this._increment( this.counter ) );
15072
15073                 if ( !this.spinning || this._trigger( "spin", event, { value: value } ) !== false) {
15074                         this._value( value );
15075                         this.counter++;
15076                 }
15077         },
15078
15079         _increment: function( i ) {
15080                 var incremental = this.options.incremental;
15081
15082                 if ( incremental ) {
15083                         return $.isFunction( incremental ) ?
15084                                 incremental( i ) :
15085                                 Math.floor( i * i * i / 50000 - i * i / 500 + 17 * i / 200 + 1 );
15086                 }
15087
15088                 return 1;
15089         },
15090
15091         _precision: function() {
15092                 var precision = this._precisionOf( this.options.step );
15093                 if ( this.options.min !== null ) {
15094                         precision = Math.max( precision, this._precisionOf( this.options.min ) );
15095                 }
15096                 return precision;
15097         },
15098
15099         _precisionOf: function( num ) {
15100                 var str = num.toString(),
15101                         decimal = str.indexOf( "." );
15102                 return decimal === -1 ? 0 : str.length - decimal - 1;
15103         },
15104
15105         _adjustValue: function( value ) {
15106                 var base, aboveMin,
15107                         options = this.options;
15108
15109                 // make sure we're at a valid step
15110                 // - find out where we are relative to the base (min or 0)
15111                 base = options.min !== null ? options.min : 0;
15112                 aboveMin = value - base;
15113                 // - round to the nearest step
15114                 aboveMin = Math.round(aboveMin / options.step) * options.step;
15115                 // - rounding is based on 0, so adjust back to our base
15116                 value = base + aboveMin;
15117
15118                 // fix precision from bad JS floating point math
15119                 value = parseFloat( value.toFixed( this._precision() ) );
15120
15121                 // clamp the value
15122                 if ( options.max !== null && value > options.max) {
15123                         return options.max;
15124                 }
15125                 if ( options.min !== null && value < options.min ) {
15126                         return options.min;
15127                 }
15128
15129                 return value;
15130         },
15131
15132         _stop: function( event ) {
15133                 if ( !this.spinning ) {
15134                         return;
15135                 }
15136
15137                 clearTimeout( this.timer );
15138                 clearTimeout( this.mousewheelTimer );
15139                 this.counter = 0;
15140                 this.spinning = false;
15141                 this._trigger( "stop", event );
15142         },
15143
15144         _setOption: function( key, value ) {
15145                 if ( key === "culture" || key === "numberFormat" ) {
15146                         var prevValue = this._parse( this.element.val() );
15147                         this.options[ key ] = value;
15148                         this.element.val( this._format( prevValue ) );
15149                         return;
15150                 }
15151
15152                 if ( key === "max" || key === "min" || key === "step" ) {
15153                         if ( typeof value === "string" ) {
15154                                 value = this._parse( value );
15155                         }
15156                 }
15157                 if ( key === "icons" ) {
15158                         this.buttons.first().find( ".ui-icon" )
15159                                 .removeClass( this.options.icons.up )
15160                                 .addClass( value.up );
15161                         this.buttons.last().find( ".ui-icon" )
15162                                 .removeClass( this.options.icons.down )
15163                                 .addClass( value.down );
15164                 }
15165
15166                 this._super( key, value );
15167
15168                 if ( key === "disabled" ) {
15169                         this.widget().toggleClass( "ui-state-disabled", !!value );
15170                         this.element.prop( "disabled", !!value );
15171                         this.buttons.button( value ? "disable" : "enable" );
15172                 }
15173         },
15174
15175         _setOptions: spinner_modifier(function( options ) {
15176                 this._super( options );
15177         }),
15178
15179         _parse: function( val ) {
15180                 if ( typeof val === "string" && val !== "" ) {
15181                         val = window.Globalize && this.options.numberFormat ?
15182                                 Globalize.parseFloat( val, 10, this.options.culture ) : +val;
15183                 }
15184                 return val === "" || isNaN( val ) ? null : val;
15185         },
15186
15187         _format: function( value ) {
15188                 if ( value === "" ) {
15189                         return "";
15190                 }
15191                 return window.Globalize && this.options.numberFormat ?
15192                         Globalize.format( value, this.options.numberFormat, this.options.culture ) :
15193                         value;
15194         },
15195
15196         _refresh: function() {
15197                 this.element.attr({
15198                         "aria-valuemin": this.options.min,
15199                         "aria-valuemax": this.options.max,
15200                         // TODO: what should we do with values that can't be parsed?
15201                         "aria-valuenow": this._parse( this.element.val() )
15202                 });
15203         },
15204
15205         isValid: function() {
15206                 var value = this.value();
15207
15208                 // null is invalid
15209                 if ( value === null ) {
15210                         return false;
15211                 }
15212
15213                 // if value gets adjusted, it's invalid
15214                 return value === this._adjustValue( value );
15215         },
15216
15217         // update the value without triggering change
15218         _value: function( value, allowAny ) {
15219                 var parsed;
15220                 if ( value !== "" ) {
15221                         parsed = this._parse( value );
15222                         if ( parsed !== null ) {
15223                                 if ( !allowAny ) {
15224                                         parsed = this._adjustValue( parsed );
15225                                 }
15226                                 value = this._format( parsed );
15227                         }
15228                 }
15229                 this.element.val( value );
15230                 this._refresh();
15231         },
15232
15233         _destroy: function() {
15234                 this.element
15235                         .removeClass( "ui-spinner-input" )
15236                         .prop( "disabled", false )
15237                         .removeAttr( "autocomplete" )
15238                         .removeAttr( "role" )
15239                         .removeAttr( "aria-valuemin" )
15240                         .removeAttr( "aria-valuemax" )
15241                         .removeAttr( "aria-valuenow" );
15242                 this.uiSpinner.replaceWith( this.element );
15243         },
15244
15245         stepUp: spinner_modifier(function( steps ) {
15246                 this._stepUp( steps );
15247         }),
15248         _stepUp: function( steps ) {
15249                 if ( this._start() ) {
15250                         this._spin( (steps || 1) * this.options.step );
15251                         this._stop();
15252                 }
15253         },
15254
15255         stepDown: spinner_modifier(function( steps ) {
15256                 this._stepDown( steps );
15257         }),
15258         _stepDown: function( steps ) {
15259                 if ( this._start() ) {
15260                         this._spin( (steps || 1) * -this.options.step );
15261                         this._stop();
15262                 }
15263         },
15264
15265         pageUp: spinner_modifier(function( pages ) {
15266                 this._stepUp( (pages || 1) * this.options.page );
15267         }),
15268
15269         pageDown: spinner_modifier(function( pages ) {
15270                 this._stepDown( (pages || 1) * this.options.page );
15271         }),
15272
15273         value: function( newVal ) {
15274                 if ( !arguments.length ) {
15275                         return this._parse( this.element.val() );
15276                 }
15277                 spinner_modifier( this._value ).call( this, newVal );
15278         },
15279
15280         widget: function() {
15281                 return this.uiSpinner;
15282         }
15283 });
15284
15285
15286 /*!
15287  * jQuery UI Tabs 1.11.4
15288  * http://jqueryui.com
15289  *
15290  * Copyright jQuery Foundation and other contributors
15291  * Released under the MIT license.
15292  * http://jquery.org/license
15293  *
15294  * http://api.jqueryui.com/tabs/
15295  */
15296
15297
15298 var tabs = $.widget( "ui.tabs", {
15299         version: "1.11.4",
15300         delay: 300,
15301         options: {
15302                 active: null,
15303                 collapsible: false,
15304                 event: "click",
15305                 heightStyle: "content",
15306                 hide: null,
15307                 show: null,
15308
15309                 // callbacks
15310                 activate: null,
15311                 beforeActivate: null,
15312                 beforeLoad: null,
15313                 load: null
15314         },
15315
15316         _isLocal: (function() {
15317                 var rhash = /#.*$/;
15318
15319                 return function( anchor ) {
15320                         var anchorUrl, locationUrl;
15321
15322                         // support: IE7
15323                         // IE7 doesn't normalize the href property when set via script (#9317)
15324                         anchor = anchor.cloneNode( false );
15325
15326                         anchorUrl = anchor.href.replace( rhash, "" );
15327                         locationUrl = location.href.replace( rhash, "" );
15328
15329                         // decoding may throw an error if the URL isn't UTF-8 (#9518)
15330                         try {
15331                                 anchorUrl = decodeURIComponent( anchorUrl );
15332                         } catch ( error ) {}
15333                         try {
15334                                 locationUrl = decodeURIComponent( locationUrl );
15335                         } catch ( error ) {}
15336
15337                         return anchor.hash.length > 1 && anchorUrl === locationUrl;
15338                 };
15339         })(),
15340
15341         _create: function() {
15342                 var that = this,
15343                         options = this.options;
15344
15345                 this.running = false;
15346
15347                 this.element
15348                         .addClass( "ui-tabs ui-widget ui-widget-content ui-corner-all" )
15349                         .toggleClass( "ui-tabs-collapsible", options.collapsible );
15350
15351                 this._processTabs();
15352                 options.active = this._initialActive();
15353
15354                 // Take disabling tabs via class attribute from HTML
15355                 // into account and update option properly.
15356                 if ( $.isArray( options.disabled ) ) {
15357                         options.disabled = $.unique( options.disabled.concat(
15358                                 $.map( this.tabs.filter( ".ui-state-disabled" ), function( li ) {
15359                                         return that.tabs.index( li );
15360                                 })
15361                         ) ).sort();
15362                 }
15363
15364                 // check for length avoids error when initializing empty list
15365                 if ( this.options.active !== false && this.anchors.length ) {
15366                         this.active = this._findActive( options.active );
15367                 } else {
15368                         this.active = $();
15369                 }
15370
15371                 this._refresh();
15372
15373                 if ( this.active.length ) {
15374                         this.load( options.active );
15375                 }
15376         },
15377
15378         _initialActive: function() {
15379                 var active = this.options.active,
15380                         collapsible = this.options.collapsible,
15381                         locationHash = location.hash.substring( 1 );
15382
15383                 if ( active === null ) {
15384                         // check the fragment identifier in the URL
15385                         if ( locationHash ) {
15386                                 this.tabs.each(function( i, tab ) {
15387                                         if ( $( tab ).attr( "aria-controls" ) === locationHash ) {
15388                                                 active = i;
15389                                                 return false;
15390                                         }
15391                                 });
15392                         }
15393
15394                         // check for a tab marked active via a class
15395                         if ( active === null ) {
15396                                 active = this.tabs.index( this.tabs.filter( ".ui-tabs-active" ) );
15397                         }
15398
15399                         // no active tab, set to false
15400                         if ( active === null || active === -1 ) {
15401                                 active = this.tabs.length ? 0 : false;
15402                         }
15403                 }
15404
15405                 // handle numbers: negative, out of range
15406                 if ( active !== false ) {
15407                         active = this.tabs.index( this.tabs.eq( active ) );
15408                         if ( active === -1 ) {
15409                                 active = collapsible ? false : 0;
15410                         }
15411                 }
15412
15413                 // don't allow collapsible: false and active: false
15414                 if ( !collapsible && active === false && this.anchors.length ) {
15415                         active = 0;
15416                 }
15417
15418                 return active;
15419         },
15420
15421         _getCreateEventData: function() {
15422                 return {
15423                         tab: this.active,
15424                         panel: !this.active.length ? $() : this._getPanelForTab( this.active )
15425                 };
15426         },
15427
15428         _tabKeydown: function( event ) {
15429                 var focusedTab = $( this.document[0].activeElement ).closest( "li" ),
15430                         selectedIndex = this.tabs.index( focusedTab ),
15431                         goingForward = true;
15432
15433                 if ( this._handlePageNav( event ) ) {
15434                         return;
15435                 }
15436
15437                 switch ( event.keyCode ) {
15438                         case $.ui.keyCode.RIGHT:
15439                         case $.ui.keyCode.DOWN:
15440                                 selectedIndex++;
15441                                 break;
15442                         case $.ui.keyCode.UP:
15443                         case $.ui.keyCode.LEFT:
15444                                 goingForward = false;
15445                                 selectedIndex--;
15446                                 break;
15447                         case $.ui.keyCode.END:
15448                                 selectedIndex = this.anchors.length - 1;
15449                                 break;
15450                         case $.ui.keyCode.HOME:
15451                                 selectedIndex = 0;
15452                                 break;
15453                         case $.ui.keyCode.SPACE:
15454                                 // Activate only, no collapsing
15455                                 event.preventDefault();
15456                                 clearTimeout( this.activating );
15457                                 this._activate( selectedIndex );
15458                                 return;
15459                         case $.ui.keyCode.ENTER:
15460                                 // Toggle (cancel delayed activation, allow collapsing)
15461                                 event.preventDefault();
15462                                 clearTimeout( this.activating );
15463                                 // Determine if we should collapse or activate
15464                                 this._activate( selectedIndex === this.options.active ? false : selectedIndex );
15465                                 return;
15466                         default:
15467                                 return;
15468                 }
15469
15470                 // Focus the appropriate tab, based on which key was pressed
15471                 event.preventDefault();
15472                 clearTimeout( this.activating );
15473                 selectedIndex = this._focusNextTab( selectedIndex, goingForward );
15474
15475                 // Navigating with control/command key will prevent automatic activation
15476                 if ( !event.ctrlKey && !event.metaKey ) {
15477
15478                         // Update aria-selected immediately so that AT think the tab is already selected.
15479                         // Otherwise AT may confuse the user by stating that they need to activate the tab,
15480                         // but the tab will already be activated by the time the announcement finishes.
15481                         focusedTab.attr( "aria-selected", "false" );
15482                         this.tabs.eq( selectedIndex ).attr( "aria-selected", "true" );
15483
15484                         this.activating = this._delay(function() {
15485                                 this.option( "active", selectedIndex );
15486                         }, this.delay );
15487                 }
15488         },
15489
15490         _panelKeydown: function( event ) {
15491                 if ( this._handlePageNav( event ) ) {
15492                         return;
15493                 }
15494
15495                 // Ctrl+up moves focus to the current tab
15496                 if ( event.ctrlKey && event.keyCode === $.ui.keyCode.UP ) {
15497                         event.preventDefault();
15498                         this.active.focus();
15499                 }
15500         },
15501
15502         // Alt+page up/down moves focus to the previous/next tab (and activates)
15503         _handlePageNav: function( event ) {
15504                 if ( event.altKey && event.keyCode === $.ui.keyCode.PAGE_UP ) {
15505                         this._activate( this._focusNextTab( this.options.active - 1, false ) );
15506                         return true;
15507                 }
15508                 if ( event.altKey && event.keyCode === $.ui.keyCode.PAGE_DOWN ) {
15509                         this._activate( this._focusNextTab( this.options.active + 1, true ) );
15510                         return true;
15511                 }
15512         },
15513
15514         _findNextTab: function( index, goingForward ) {
15515                 var lastTabIndex = this.tabs.length - 1;
15516
15517                 function constrain() {
15518                         if ( index > lastTabIndex ) {
15519                                 index = 0;
15520                         }
15521                         if ( index < 0 ) {
15522                                 index = lastTabIndex;
15523                         }
15524                         return index;
15525                 }
15526
15527                 while ( $.inArray( constrain(), this.options.disabled ) !== -1 ) {
15528                         index = goingForward ? index + 1 : index - 1;
15529                 }
15530
15531                 return index;
15532         },
15533
15534         _focusNextTab: function( index, goingForward ) {
15535                 index = this._findNextTab( index, goingForward );
15536                 this.tabs.eq( index ).focus();
15537                 return index;
15538         },
15539
15540         _setOption: function( key, value ) {
15541                 if ( key === "active" ) {
15542                         // _activate() will handle invalid values and update this.options
15543                         this._activate( value );
15544                         return;
15545                 }
15546
15547                 if ( key === "disabled" ) {
15548                         // don't use the widget factory's disabled handling
15549                         this._setupDisabled( value );
15550                         return;
15551                 }
15552
15553                 this._super( key, value);
15554
15555                 if ( key === "collapsible" ) {
15556                         this.element.toggleClass( "ui-tabs-collapsible", value );
15557                         // Setting collapsible: false while collapsed; open first panel
15558                         if ( !value && this.options.active === false ) {
15559                                 this._activate( 0 );
15560                         }
15561                 }
15562
15563                 if ( key === "event" ) {
15564                         this._setupEvents( value );
15565                 }
15566
15567                 if ( key === "heightStyle" ) {
15568                         this._setupHeightStyle( value );
15569                 }
15570         },
15571
15572         _sanitizeSelector: function( hash ) {
15573                 return hash ? hash.replace( /[!"$%&'()*+,.\/:;<=>?@\[\]\^`{|}~]/g, "\\$&" ) : "";
15574         },
15575
15576         refresh: function() {
15577                 var options = this.options,
15578                         lis = this.tablist.children( ":has(a[href])" );
15579
15580                 // get disabled tabs from class attribute from HTML
15581                 // this will get converted to a boolean if needed in _refresh()
15582                 options.disabled = $.map( lis.filter( ".ui-state-disabled" ), function( tab ) {
15583                         return lis.index( tab );
15584                 });
15585
15586                 this._processTabs();
15587
15588                 // was collapsed or no tabs
15589                 if ( options.active === false || !this.anchors.length ) {
15590                         options.active = false;
15591                         this.active = $();
15592                 // was active, but active tab is gone
15593                 } else if ( this.active.length && !$.contains( this.tablist[ 0 ], this.active[ 0 ] ) ) {
15594                         // all remaining tabs are disabled
15595                         if ( this.tabs.length === options.disabled.length ) {
15596                                 options.active = false;
15597                                 this.active = $();
15598                         // activate previous tab
15599                         } else {
15600                                 this._activate( this._findNextTab( Math.max( 0, options.active - 1 ), false ) );
15601                         }
15602                 // was active, active tab still exists
15603                 } else {
15604                         // make sure active index is correct
15605                         options.active = this.tabs.index( this.active );
15606                 }
15607
15608                 this._refresh();
15609         },
15610
15611         _refresh: function() {
15612                 this._setupDisabled( this.options.disabled );
15613                 this._setupEvents( this.options.event );
15614                 this._setupHeightStyle( this.options.heightStyle );
15615
15616                 this.tabs.not( this.active ).attr({
15617                         "aria-selected": "false",
15618                         "aria-expanded": "false",
15619                         tabIndex: -1
15620                 });
15621                 this.panels.not( this._getPanelForTab( this.active ) )
15622                         .hide()
15623                         .attr({
15624                                 "aria-hidden": "true"
15625                         });
15626
15627                 // Make sure one tab is in the tab order
15628                 if ( !this.active.length ) {
15629                         this.tabs.eq( 0 ).attr( "tabIndex", 0 );
15630                 } else {
15631                         this.active
15632                                 .addClass( "ui-tabs-active ui-state-active" )
15633                                 .attr({
15634                                         "aria-selected": "true",
15635                                         "aria-expanded": "true",
15636                                         tabIndex: 0
15637                                 });
15638                         this._getPanelForTab( this.active )
15639                                 .show()
15640                                 .attr({
15641                                         "aria-hidden": "false"
15642                                 });
15643                 }
15644         },
15645
15646         _processTabs: function() {
15647                 var that = this,
15648                         prevTabs = this.tabs,
15649                         prevAnchors = this.anchors,
15650                         prevPanels = this.panels;
15651
15652                 this.tablist = this._getList()
15653                         .addClass( "ui-tabs-nav ui-helper-reset ui-helper-clearfix ui-widget-header ui-corner-all" )
15654                         .attr( "role", "tablist" )
15655
15656                         // Prevent users from focusing disabled tabs via click
15657                         .delegate( "> li", "mousedown" + this.eventNamespace, function( event ) {
15658                                 if ( $( this ).is( ".ui-state-disabled" ) ) {
15659                                         event.preventDefault();
15660                                 }
15661                         })
15662
15663                         // support: IE <9
15664                         // Preventing the default action in mousedown doesn't prevent IE
15665                         // from focusing the element, so if the anchor gets focused, blur.
15666                         // We don't have to worry about focusing the previously focused
15667                         // element since clicking on a non-focusable element should focus
15668                         // the body anyway.
15669                         .delegate( ".ui-tabs-anchor", "focus" + this.eventNamespace, function() {
15670                                 if ( $( this ).closest( "li" ).is( ".ui-state-disabled" ) ) {
15671                                         this.blur();
15672                                 }
15673                         });
15674
15675                 this.tabs = this.tablist.find( "> li:has(a[href])" )
15676                         .addClass( "ui-state-default ui-corner-top" )
15677                         .attr({
15678                                 role: "tab",
15679                                 tabIndex: -1
15680                         });
15681
15682                 this.anchors = this.tabs.map(function() {
15683                                 return $( "a", this )[ 0 ];
15684                         })
15685                         .addClass( "ui-tabs-anchor" )
15686                         .attr({
15687                                 role: "presentation",
15688                                 tabIndex: -1
15689                         });
15690
15691                 this.panels = $();
15692
15693                 this.anchors.each(function( i, anchor ) {
15694                         var selector, panel, panelId,
15695                                 anchorId = $( anchor ).uniqueId().attr( "id" ),
15696                                 tab = $( anchor ).closest( "li" ),
15697                                 originalAriaControls = tab.attr( "aria-controls" );
15698
15699                         // inline tab
15700                         if ( that._isLocal( anchor ) ) {
15701                                 selector = anchor.hash;
15702                                 panelId = selector.substring( 1 );
15703                                 panel = that.element.find( that._sanitizeSelector( selector ) );
15704                         // remote tab
15705                         } else {
15706                                 // If the tab doesn't already have aria-controls,
15707                                 // generate an id by using a throw-away element
15708                                 panelId = tab.attr( "aria-controls" ) || $( {} ).uniqueId()[ 0 ].id;
15709                                 selector = "#" + panelId;
15710                                 panel = that.element.find( selector );
15711                                 if ( !panel.length ) {
15712                                         panel = that._createPanel( panelId );
15713                                         panel.insertAfter( that.panels[ i - 1 ] || that.tablist );
15714                                 }
15715                                 panel.attr( "aria-live", "polite" );
15716                         }
15717
15718                         if ( panel.length) {
15719                                 that.panels = that.panels.add( panel );
15720                         }
15721                         if ( originalAriaControls ) {
15722                                 tab.data( "ui-tabs-aria-controls", originalAriaControls );
15723                         }
15724                         tab.attr({
15725                                 "aria-controls": panelId,
15726                                 "aria-labelledby": anchorId
15727                         });
15728                         panel.attr( "aria-labelledby", anchorId );
15729                 });
15730
15731                 this.panels
15732                         .addClass( "ui-tabs-panel ui-widget-content ui-corner-bottom" )
15733                         .attr( "role", "tabpanel" );
15734
15735                 // Avoid memory leaks (#10056)
15736                 if ( prevTabs ) {
15737                         this._off( prevTabs.not( this.tabs ) );
15738                         this._off( prevAnchors.not( this.anchors ) );
15739                         this._off( prevPanels.not( this.panels ) );
15740                 }
15741         },
15742
15743         // allow overriding how to find the list for rare usage scenarios (#7715)
15744         _getList: function() {
15745                 return this.tablist || this.element.find( "ol,ul" ).eq( 0 );
15746         },
15747
15748         _createPanel: function( id ) {
15749                 return $( "<div>" )
15750                         .attr( "id", id )
15751                         .addClass( "ui-tabs-panel ui-widget-content ui-corner-bottom" )
15752                         .data( "ui-tabs-destroy", true );
15753         },
15754
15755         _setupDisabled: function( disabled ) {
15756                 if ( $.isArray( disabled ) ) {
15757                         if ( !disabled.length ) {
15758                                 disabled = false;
15759                         } else if ( disabled.length === this.anchors.length ) {
15760                                 disabled = true;
15761                         }
15762                 }
15763
15764                 // disable tabs
15765                 for ( var i = 0, li; ( li = this.tabs[ i ] ); i++ ) {
15766                         if ( disabled === true || $.inArray( i, disabled ) !== -1 ) {
15767                                 $( li )
15768                                         .addClass( "ui-state-disabled" )
15769                                         .attr( "aria-disabled", "true" );
15770                         } else {
15771                                 $( li )
15772                                         .removeClass( "ui-state-disabled" )
15773                                         .removeAttr( "aria-disabled" );
15774                         }
15775                 }
15776
15777                 this.options.disabled = disabled;
15778         },
15779
15780         _setupEvents: function( event ) {
15781                 var events = {};
15782                 if ( event ) {
15783                         $.each( event.split(" "), function( index, eventName ) {
15784                                 events[ eventName ] = "_eventHandler";
15785                         });
15786                 }
15787
15788                 this._off( this.anchors.add( this.tabs ).add( this.panels ) );
15789                 // Always prevent the default action, even when disabled
15790                 this._on( true, this.anchors, {
15791                         click: function( event ) {
15792                                 event.preventDefault();
15793                         }
15794                 });
15795                 this._on( this.anchors, events );
15796                 this._on( this.tabs, { keydown: "_tabKeydown" } );
15797                 this._on( this.panels, { keydown: "_panelKeydown" } );
15798
15799                 this._focusable( this.tabs );
15800                 this._hoverable( this.tabs );
15801         },
15802
15803         _setupHeightStyle: function( heightStyle ) {
15804                 var maxHeight,
15805                         parent = this.element.parent();
15806
15807                 if ( heightStyle === "fill" ) {
15808                         maxHeight = parent.height();
15809                         maxHeight -= this.element.outerHeight() - this.element.height();
15810
15811                         this.element.siblings( ":visible" ).each(function() {
15812                                 var elem = $( this ),
15813                                         position = elem.css( "position" );
15814
15815                                 if ( position === "absolute" || position === "fixed" ) {
15816                                         return;
15817                                 }
15818                                 maxHeight -= elem.outerHeight( true );
15819                         });
15820
15821                         this.element.children().not( this.panels ).each(function() {
15822                                 maxHeight -= $( this ).outerHeight( true );
15823                         });
15824
15825                         this.panels.each(function() {
15826                                 $( this ).height( Math.max( 0, maxHeight -
15827                                         $( this ).innerHeight() + $( this ).height() ) );
15828                         })
15829                         .css( "overflow", "auto" );
15830                 } else if ( heightStyle === "auto" ) {
15831                         maxHeight = 0;
15832                         this.panels.each(function() {
15833                                 maxHeight = Math.max( maxHeight, $( this ).height( "" ).height() );
15834                         }).height( maxHeight );
15835                 }
15836         },
15837
15838         _eventHandler: function( event ) {
15839                 var options = this.options,
15840                         active = this.active,
15841                         anchor = $( event.currentTarget ),
15842                         tab = anchor.closest( "li" ),
15843                         clickedIsActive = tab[ 0 ] === active[ 0 ],
15844                         collapsing = clickedIsActive && options.collapsible,
15845                         toShow = collapsing ? $() : this._getPanelForTab( tab ),
15846                         toHide = !active.length ? $() : this._getPanelForTab( active ),
15847                         eventData = {
15848                                 oldTab: active,
15849                                 oldPanel: toHide,
15850                                 newTab: collapsing ? $() : tab,
15851                                 newPanel: toShow
15852                         };
15853
15854                 event.preventDefault();
15855
15856                 if ( tab.hasClass( "ui-state-disabled" ) ||
15857                                 // tab is already loading
15858                                 tab.hasClass( "ui-tabs-loading" ) ||
15859                                 // can't switch durning an animation
15860                                 this.running ||
15861                                 // click on active header, but not collapsible
15862                                 ( clickedIsActive && !options.collapsible ) ||
15863                                 // allow canceling activation
15864                                 ( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
15865                         return;
15866                 }
15867
15868                 options.active = collapsing ? false : this.tabs.index( tab );
15869
15870                 this.active = clickedIsActive ? $() : tab;
15871                 if ( this.xhr ) {
15872                         this.xhr.abort();
15873                 }
15874
15875                 if ( !toHide.length && !toShow.length ) {
15876                         $.error( "jQuery UI Tabs: Mismatching fragment identifier." );
15877                 }
15878
15879                 if ( toShow.length ) {
15880                         this.load( this.tabs.index( tab ), event );
15881                 }
15882                 this._toggle( event, eventData );
15883         },
15884
15885         // handles show/hide for selecting tabs
15886         _toggle: function( event, eventData ) {
15887                 var that = this,
15888                         toShow = eventData.newPanel,
15889                         toHide = eventData.oldPanel;
15890
15891                 this.running = true;
15892
15893                 function complete() {
15894                         that.running = false;
15895                         that._trigger( "activate", event, eventData );
15896                 }
15897
15898                 function show() {
15899                         eventData.newTab.closest( "li" ).addClass( "ui-tabs-active ui-state-active" );
15900
15901                         if ( toShow.length && that.options.show ) {
15902                                 that._show( toShow, that.options.show, complete );
15903                         } else {
15904                                 toShow.show();
15905                                 complete();
15906                         }
15907                 }
15908
15909                 // start out by hiding, then showing, then completing
15910                 if ( toHide.length && this.options.hide ) {
15911                         this._hide( toHide, this.options.hide, function() {
15912                                 eventData.oldTab.closest( "li" ).removeClass( "ui-tabs-active ui-state-active" );
15913                                 show();
15914                         });
15915                 } else {
15916                         eventData.oldTab.closest( "li" ).removeClass( "ui-tabs-active ui-state-active" );
15917                         toHide.hide();
15918                         show();
15919                 }
15920
15921                 toHide.attr( "aria-hidden", "true" );
15922                 eventData.oldTab.attr({
15923                         "aria-selected": "false",
15924                         "aria-expanded": "false"
15925                 });
15926                 // If we're switching tabs, remove the old tab from the tab order.
15927                 // If we're opening from collapsed state, remove the previous tab from the tab order.
15928                 // If we're collapsing, then keep the collapsing tab in the tab order.
15929                 if ( toShow.length && toHide.length ) {
15930                         eventData.oldTab.attr( "tabIndex", -1 );
15931                 } else if ( toShow.length ) {
15932                         this.tabs.filter(function() {
15933                                 return $( this ).attr( "tabIndex" ) === 0;
15934                         })
15935                         .attr( "tabIndex", -1 );
15936                 }
15937
15938                 toShow.attr( "aria-hidden", "false" );
15939                 eventData.newTab.attr({
15940                         "aria-selected": "true",
15941                         "aria-expanded": "true",
15942                         tabIndex: 0
15943                 });
15944         },
15945
15946         _activate: function( index ) {
15947                 var anchor,
15948                         active = this._findActive( index );
15949
15950                 // trying to activate the already active panel
15951                 if ( active[ 0 ] === this.active[ 0 ] ) {
15952                         return;
15953                 }
15954
15955                 // trying to collapse, simulate a click on the current active header
15956                 if ( !active.length ) {
15957                         active = this.active;
15958                 }
15959
15960                 anchor = active.find( ".ui-tabs-anchor" )[ 0 ];
15961                 this._eventHandler({
15962                         target: anchor,
15963                         currentTarget: anchor,
15964                         preventDefault: $.noop
15965                 });
15966         },
15967
15968         _findActive: function( index ) {
15969                 return index === false ? $() : this.tabs.eq( index );
15970         },
15971
15972         _getIndex: function( index ) {
15973                 // meta-function to give users option to provide a href string instead of a numerical index.
15974                 if ( typeof index === "string" ) {
15975                         index = this.anchors.index( this.anchors.filter( "[href$='" + index + "']" ) );
15976                 }
15977
15978                 return index;
15979         },
15980
15981         _destroy: function() {
15982                 if ( this.xhr ) {
15983                         this.xhr.abort();
15984                 }
15985
15986                 this.element.removeClass( "ui-tabs ui-widget ui-widget-content ui-corner-all ui-tabs-collapsible" );
15987
15988                 this.tablist
15989                         .removeClass( "ui-tabs-nav ui-helper-reset ui-helper-clearfix ui-widget-header ui-corner-all" )
15990                         .removeAttr( "role" );
15991
15992                 this.anchors
15993                         .removeClass( "ui-tabs-anchor" )
15994                         .removeAttr( "role" )
15995                         .removeAttr( "tabIndex" )
15996                         .removeUniqueId();
15997
15998                 this.tablist.unbind( this.eventNamespace );
15999
16000                 this.tabs.add( this.panels ).each(function() {
16001                         if ( $.data( this, "ui-tabs-destroy" ) ) {
16002                                 $( this ).remove();
16003                         } else {
16004                                 $( this )
16005                                         .removeClass( "ui-state-default ui-state-active ui-state-disabled " +
16006                                                 "ui-corner-top ui-corner-bottom ui-widget-content ui-tabs-active ui-tabs-panel" )
16007                                         .removeAttr( "tabIndex" )
16008                                         .removeAttr( "aria-live" )
16009                                         .removeAttr( "aria-busy" )
16010                                         .removeAttr( "aria-selected" )
16011                                         .removeAttr( "aria-labelledby" )
16012                                         .removeAttr( "aria-hidden" )
16013                                         .removeAttr( "aria-expanded" )
16014                                         .removeAttr( "role" );
16015                         }
16016                 });
16017
16018                 this.tabs.each(function() {
16019                         var li = $( this ),
16020                                 prev = li.data( "ui-tabs-aria-controls" );
16021                         if ( prev ) {
16022                                 li
16023                                         .attr( "aria-controls", prev )
16024                                         .removeData( "ui-tabs-aria-controls" );
16025                         } else {
16026                                 li.removeAttr( "aria-controls" );
16027                         }
16028                 });
16029
16030                 this.panels.show();
16031
16032                 if ( this.options.heightStyle !== "content" ) {
16033                         this.panels.css( "height", "" );
16034                 }
16035         },
16036
16037         enable: function( index ) {
16038                 var disabled = this.options.disabled;
16039                 if ( disabled === false ) {
16040                         return;
16041                 }
16042
16043                 if ( index === undefined ) {
16044                         disabled = false;
16045                 } else {
16046                         index = this._getIndex( index );
16047                         if ( $.isArray( disabled ) ) {
16048                                 disabled = $.map( disabled, function( num ) {
16049                                         return num !== index ? num : null;
16050                                 });
16051                         } else {
16052                                 disabled = $.map( this.tabs, function( li, num ) {
16053                                         return num !== index ? num : null;
16054                                 });
16055                         }
16056                 }
16057                 this._setupDisabled( disabled );
16058         },
16059
16060         disable: function( index ) {
16061                 var disabled = this.options.disabled;
16062                 if ( disabled === true ) {
16063                         return;
16064                 }
16065
16066                 if ( index === undefined ) {
16067                         disabled = true;
16068                 } else {
16069                         index = this._getIndex( index );
16070                         if ( $.inArray( index, disabled ) !== -1 ) {
16071                                 return;
16072                         }
16073                         if ( $.isArray( disabled ) ) {
16074                                 disabled = $.merge( [ index ], disabled ).sort();
16075                         } else {
16076                                 disabled = [ index ];
16077                         }
16078                 }
16079                 this._setupDisabled( disabled );
16080         },
16081
16082         load: function( index, event ) {
16083                 index = this._getIndex( index );
16084                 var that = this,
16085                         tab = this.tabs.eq( index ),
16086                         anchor = tab.find( ".ui-tabs-anchor" ),
16087                         panel = this._getPanelForTab( tab ),
16088                         eventData = {
16089                                 tab: tab,
16090                                 panel: panel
16091                         },
16092                         complete = function( jqXHR, status ) {
16093                                 if ( status === "abort" ) {
16094                                         that.panels.stop( false, true );
16095                                 }
16096
16097                                 tab.removeClass( "ui-tabs-loading" );
16098                                 panel.removeAttr( "aria-busy" );
16099
16100                                 if ( jqXHR === that.xhr ) {
16101                                         delete that.xhr;
16102                                 }
16103                         };
16104
16105                 // not remote
16106                 if ( this._isLocal( anchor[ 0 ] ) ) {
16107                         return;
16108                 }
16109
16110                 this.xhr = $.ajax( this._ajaxSettings( anchor, event, eventData ) );
16111
16112                 // support: jQuery <1.8
16113                 // jQuery <1.8 returns false if the request is canceled in beforeSend,
16114                 // but as of 1.8, $.ajax() always returns a jqXHR object.
16115                 if ( this.xhr && this.xhr.statusText !== "canceled" ) {
16116                         tab.addClass( "ui-tabs-loading" );
16117                         panel.attr( "aria-busy", "true" );
16118
16119                         this.xhr
16120                                 .done(function( response, status, jqXHR ) {
16121                                         // support: jQuery <1.8
16122                                         // http://bugs.jquery.com/ticket/11778
16123                                         setTimeout(function() {
16124                                                 panel.html( response );
16125                                                 that._trigger( "load", event, eventData );
16126
16127                                                 complete( jqXHR, status );
16128                                         }, 1 );
16129                                 })
16130                                 .fail(function( jqXHR, status ) {
16131                                         // support: jQuery <1.8
16132                                         // http://bugs.jquery.com/ticket/11778
16133                                         setTimeout(function() {
16134                                                 complete( jqXHR, status );
16135                                         }, 1 );
16136                                 });
16137                 }
16138         },
16139
16140         _ajaxSettings: function( anchor, event, eventData ) {
16141                 var that = this;
16142                 return {
16143                         url: anchor.attr( "href" ),
16144                         beforeSend: function( jqXHR, settings ) {
16145                                 return that._trigger( "beforeLoad", event,
16146                                         $.extend( { jqXHR: jqXHR, ajaxSettings: settings }, eventData ) );
16147                         }
16148                 };
16149         },
16150
16151         _getPanelForTab: function( tab ) {
16152                 var id = $( tab ).attr( "aria-controls" );
16153                 return this.element.find( this._sanitizeSelector( "#" + id ) );
16154         }
16155 });
16156
16157
16158 /*!
16159  * jQuery UI Tooltip 1.11.4
16160  * http://jqueryui.com
16161  *
16162  * Copyright jQuery Foundation and other contributors
16163  * Released under the MIT license.
16164  * http://jquery.org/license
16165  *
16166  * http://api.jqueryui.com/tooltip/
16167  */
16168
16169
16170 var tooltip = $.widget( "ui.tooltip", {
16171         version: "1.11.4",
16172         options: {
16173                 content: function() {
16174                         // support: IE<9, Opera in jQuery <1.7
16175                         // .text() can't accept undefined, so coerce to a string
16176                         var title = $( this ).attr( "title" ) || "";
16177                         // Escape title, since we're going from an attribute to raw HTML
16178                         return $( "<a>" ).text( title ).html();
16179                 },
16180                 hide: true,
16181                 // Disabled elements have inconsistent behavior across browsers (#8661)
16182                 items: "[title]:not([disabled])",
16183                 position: {
16184                         my: "left top+15",
16185                         at: "left bottom",
16186                         collision: "flipfit flip"
16187                 },
16188                 show: true,
16189                 tooltipClass: null,
16190                 track: false,
16191
16192                 // callbacks
16193                 close: null,
16194                 open: null
16195         },
16196
16197         _addDescribedBy: function( elem, id ) {
16198                 var describedby = (elem.attr( "aria-describedby" ) || "").split( /\s+/ );
16199                 describedby.push( id );
16200                 elem
16201                         .data( "ui-tooltip-id", id )
16202                         .attr( "aria-describedby", $.trim( describedby.join( " " ) ) );
16203         },
16204
16205         _removeDescribedBy: function( elem ) {
16206                 var id = elem.data( "ui-tooltip-id" ),
16207                         describedby = (elem.attr( "aria-describedby" ) || "").split( /\s+/ ),
16208                         index = $.inArray( id, describedby );
16209
16210                 if ( index !== -1 ) {
16211                         describedby.splice( index, 1 );
16212                 }
16213
16214                 elem.removeData( "ui-tooltip-id" );
16215                 describedby = $.trim( describedby.join( " " ) );
16216                 if ( describedby ) {
16217                         elem.attr( "aria-describedby", describedby );
16218                 } else {
16219                         elem.removeAttr( "aria-describedby" );
16220                 }
16221         },
16222
16223         _create: function() {
16224                 this._on({
16225                         mouseover: "open",
16226                         focusin: "open"
16227                 });
16228
16229                 // IDs of generated tooltips, needed for destroy
16230                 this.tooltips = {};
16231
16232                 // IDs of parent tooltips where we removed the title attribute
16233                 this.parents = {};
16234
16235                 if ( this.options.disabled ) {
16236                         this._disable();
16237                 }
16238
16239                 // Append the aria-live region so tooltips announce correctly
16240                 this.liveRegion = $( "<div>" )
16241                         .attr({
16242                                 role: "log",
16243                                 "aria-live": "assertive",
16244                                 "aria-relevant": "additions"
16245                         })
16246                         .addClass( "ui-helper-hidden-accessible" )
16247                         .appendTo( this.document[ 0 ].body );
16248         },
16249
16250         _setOption: function( key, value ) {
16251                 var that = this;
16252
16253                 if ( key === "disabled" ) {
16254                         this[ value ? "_disable" : "_enable" ]();
16255                         this.options[ key ] = value;
16256                         // disable element style changes
16257                         return;
16258                 }
16259
16260                 this._super( key, value );
16261
16262                 if ( key === "content" ) {
16263                         $.each( this.tooltips, function( id, tooltipData ) {
16264                                 that._updateContent( tooltipData.element );
16265                         });
16266                 }
16267         },
16268
16269         _disable: function() {
16270                 var that = this;
16271
16272                 // close open tooltips
16273                 $.each( this.tooltips, function( id, tooltipData ) {
16274                         var event = $.Event( "blur" );
16275                         event.target = event.currentTarget = tooltipData.element[ 0 ];
16276                         that.close( event, true );
16277                 });
16278
16279                 // remove title attributes to prevent native tooltips
16280                 this.element.find( this.options.items ).addBack().each(function() {
16281                         var element = $( this );
16282                         if ( element.is( "[title]" ) ) {
16283                                 element
16284                                         .data( "ui-tooltip-title", element.attr( "title" ) )
16285                                         .removeAttr( "title" );
16286                         }
16287                 });
16288         },
16289
16290         _enable: function() {
16291                 // restore title attributes
16292                 this.element.find( this.options.items ).addBack().each(function() {
16293                         var element = $( this );
16294                         if ( element.data( "ui-tooltip-title" ) ) {
16295                                 element.attr( "title", element.data( "ui-tooltip-title" ) );
16296                         }
16297                 });
16298         },
16299
16300         open: function( event ) {
16301                 var that = this,
16302                         target = $( event ? event.target : this.element )
16303                                 // we need closest here due to mouseover bubbling,
16304                                 // but always pointing at the same event target
16305                                 .closest( this.options.items );
16306
16307                 // No element to show a tooltip for or the tooltip is already open
16308                 if ( !target.length || target.data( "ui-tooltip-id" ) ) {
16309                         return;
16310                 }
16311
16312                 if ( target.attr( "title" ) ) {
16313                         target.data( "ui-tooltip-title", target.attr( "title" ) );
16314                 }
16315
16316                 target.data( "ui-tooltip-open", true );
16317
16318                 // kill parent tooltips, custom or native, for hover
16319                 if ( event && event.type === "mouseover" ) {
16320                         target.parents().each(function() {
16321                                 var parent = $( this ),
16322                                         blurEvent;
16323                                 if ( parent.data( "ui-tooltip-open" ) ) {
16324                                         blurEvent = $.Event( "blur" );
16325                                         blurEvent.target = blurEvent.currentTarget = this;
16326                                         that.close( blurEvent, true );
16327                                 }
16328                                 if ( parent.attr( "title" ) ) {
16329                                         parent.uniqueId();
16330                                         that.parents[ this.id ] = {
16331                                                 element: this,
16332                                                 title: parent.attr( "title" )
16333                                         };
16334                                         parent.attr( "title", "" );
16335                                 }
16336                         });
16337                 }
16338
16339                 this._registerCloseHandlers( event, target );
16340                 this._updateContent( target, event );
16341         },
16342
16343         _updateContent: function( target, event ) {
16344                 var content,
16345                         contentOption = this.options.content,
16346                         that = this,
16347                         eventType = event ? event.type : null;
16348
16349                 if ( typeof contentOption === "string" ) {
16350                         return this._open( event, target, contentOption );
16351                 }
16352
16353                 content = contentOption.call( target[0], function( response ) {
16354
16355                         // IE may instantly serve a cached response for ajax requests
16356                         // delay this call to _open so the other call to _open runs first
16357                         that._delay(function() {
16358
16359                                 // Ignore async response if tooltip was closed already
16360                                 if ( !target.data( "ui-tooltip-open" ) ) {
16361                                         return;
16362                                 }
16363
16364                                 // jQuery creates a special event for focusin when it doesn't
16365                                 // exist natively. To improve performance, the native event
16366                                 // object is reused and the type is changed. Therefore, we can't
16367                                 // rely on the type being correct after the event finished
16368                                 // bubbling, so we set it back to the previous value. (#8740)
16369                                 if ( event ) {
16370                                         event.type = eventType;
16371                                 }
16372                                 this._open( event, target, response );
16373                         });
16374                 });
16375                 if ( content ) {
16376                         this._open( event, target, content );
16377                 }
16378         },
16379
16380         _open: function( event, target, content ) {
16381                 var tooltipData, tooltip, delayedShow, a11yContent,
16382                         positionOption = $.extend( {}, this.options.position );
16383
16384                 if ( !content ) {
16385                         return;
16386                 }
16387
16388                 // Content can be updated multiple times. If the tooltip already
16389                 // exists, then just update the content and bail.
16390                 tooltipData = this._find( target );
16391                 if ( tooltipData ) {
16392                         tooltipData.tooltip.find( ".ui-tooltip-content" ).html( content );
16393                         return;
16394                 }
16395
16396                 // if we have a title, clear it to prevent the native tooltip
16397                 // we have to check first to avoid defining a title if none exists
16398                 // (we don't want to cause an element to start matching [title])
16399                 //
16400                 // We use removeAttr only for key events, to allow IE to export the correct
16401                 // accessible attributes. For mouse events, set to empty string to avoid
16402                 // native tooltip showing up (happens only when removing inside mouseover).
16403                 if ( target.is( "[title]" ) ) {
16404                         if ( event && event.type === "mouseover" ) {
16405                                 target.attr( "title", "" );
16406                         } else {
16407                                 target.removeAttr( "title" );
16408                         }
16409                 }
16410
16411                 tooltipData = this._tooltip( target );
16412                 tooltip = tooltipData.tooltip;
16413                 this._addDescribedBy( target, tooltip.attr( "id" ) );
16414                 tooltip.find( ".ui-tooltip-content" ).html( content );
16415
16416                 // Support: Voiceover on OS X, JAWS on IE <= 9
16417                 // JAWS announces deletions even when aria-relevant="additions"
16418                 // Voiceover will sometimes re-read the entire log region's contents from the beginning
16419                 this.liveRegion.children().hide();
16420                 if ( content.clone ) {
16421                         a11yContent = content.clone();
16422                         a11yContent.removeAttr( "id" ).find( "[id]" ).removeAttr( "id" );
16423                 } else {
16424                         a11yContent = content;
16425                 }
16426                 $( "<div>" ).html( a11yContent ).appendTo( this.liveRegion );
16427
16428                 function position( event ) {
16429                         positionOption.of = event;
16430                         if ( tooltip.is( ":hidden" ) ) {
16431                                 return;
16432                         }
16433                         tooltip.position( positionOption );
16434                 }
16435                 if ( this.options.track && event && /^mouse/.test( event.type ) ) {
16436                         this._on( this.document, {
16437                                 mousemove: position
16438                         });
16439                         // trigger once to override element-relative positioning
16440                         position( event );
16441                 } else {
16442                         tooltip.position( $.extend({
16443                                 of: target
16444                         }, this.options.position ) );
16445                 }
16446
16447                 tooltip.hide();
16448
16449                 this._show( tooltip, this.options.show );
16450                 // Handle tracking tooltips that are shown with a delay (#8644). As soon
16451                 // as the tooltip is visible, position the tooltip using the most recent
16452                 // event.
16453                 if ( this.options.show && this.options.show.delay ) {
16454                         delayedShow = this.delayedShow = setInterval(function() {
16455                                 if ( tooltip.is( ":visible" ) ) {
16456                                         position( positionOption.of );
16457                                         clearInterval( delayedShow );
16458                                 }
16459                         }, $.fx.interval );
16460                 }
16461
16462                 this._trigger( "open", event, { tooltip: tooltip } );
16463         },
16464
16465         _registerCloseHandlers: function( event, target ) {
16466                 var events = {
16467                         keyup: function( event ) {
16468                                 if ( event.keyCode === $.ui.keyCode.ESCAPE ) {
16469                                         var fakeEvent = $.Event(event);
16470                                         fakeEvent.currentTarget = target[0];
16471                                         this.close( fakeEvent, true );
16472                                 }
16473                         }
16474                 };
16475
16476                 // Only bind remove handler for delegated targets. Non-delegated
16477                 // tooltips will handle this in destroy.
16478                 if ( target[ 0 ] !== this.element[ 0 ] ) {
16479                         events.remove = function() {
16480                                 this._removeTooltip( this._find( target ).tooltip );
16481                         };
16482                 }
16483
16484                 if ( !event || event.type === "mouseover" ) {
16485                         events.mouseleave = "close";
16486                 }
16487                 if ( !event || event.type === "focusin" ) {
16488                         events.focusout = "close";
16489                 }
16490                 this._on( true, target, events );
16491         },
16492
16493         close: function( event ) {
16494                 var tooltip,
16495                         that = this,
16496                         target = $( event ? event.currentTarget : this.element ),
16497                         tooltipData = this._find( target );
16498
16499                 // The tooltip may already be closed
16500                 if ( !tooltipData ) {
16501
16502                         // We set ui-tooltip-open immediately upon open (in open()), but only set the
16503                         // additional data once there's actually content to show (in _open()). So even if the
16504                         // tooltip doesn't have full data, we always remove ui-tooltip-open in case we're in
16505                         // the period between open() and _open().
16506                         target.removeData( "ui-tooltip-open" );
16507                         return;
16508                 }
16509
16510                 tooltip = tooltipData.tooltip;
16511
16512                 // disabling closes the tooltip, so we need to track when we're closing
16513                 // to avoid an infinite loop in case the tooltip becomes disabled on close
16514                 if ( tooltipData.closing ) {
16515                         return;
16516                 }
16517
16518                 // Clear the interval for delayed tracking tooltips
16519                 clearInterval( this.delayedShow );
16520
16521                 // only set title if we had one before (see comment in _open())
16522                 // If the title attribute has changed since open(), don't restore
16523                 if ( target.data( "ui-tooltip-title" ) && !target.attr( "title" ) ) {
16524                         target.attr( "title", target.data( "ui-tooltip-title" ) );
16525                 }
16526
16527                 this._removeDescribedBy( target );
16528
16529                 tooltipData.hiding = true;
16530                 tooltip.stop( true );
16531                 this._hide( tooltip, this.options.hide, function() {
16532                         that._removeTooltip( $( this ) );
16533                 });
16534
16535                 target.removeData( "ui-tooltip-open" );
16536                 this._off( target, "mouseleave focusout keyup" );
16537
16538                 // Remove 'remove' binding only on delegated targets
16539                 if ( target[ 0 ] !== this.element[ 0 ] ) {
16540                         this._off( target, "remove" );
16541                 }
16542                 this._off( this.document, "mousemove" );
16543
16544                 if ( event && event.type === "mouseleave" ) {
16545                         $.each( this.parents, function( id, parent ) {
16546                                 $( parent.element ).attr( "title", parent.title );
16547                                 delete that.parents[ id ];
16548                         });
16549                 }
16550
16551                 tooltipData.closing = true;
16552                 this._trigger( "close", event, { tooltip: tooltip } );
16553                 if ( !tooltipData.hiding ) {
16554                         tooltipData.closing = false;
16555                 }
16556         },
16557
16558         _tooltip: function( element ) {
16559                 var tooltip = $( "<div>" )
16560                                 .attr( "role", "tooltip" )
16561                                 .addClass( "ui-tooltip ui-widget ui-corner-all ui-widget-content " +
16562                                         ( this.options.tooltipClass || "" ) ),
16563                         id = tooltip.uniqueId().attr( "id" );
16564
16565                 $( "<div>" )
16566                         .addClass( "ui-tooltip-content" )
16567                         .appendTo( tooltip );
16568
16569                 tooltip.appendTo( this.document[0].body );
16570
16571                 return this.tooltips[ id ] = {
16572                         element: element,
16573                         tooltip: tooltip
16574                 };
16575         },
16576
16577         _find: function( target ) {
16578                 var id = target.data( "ui-tooltip-id" );
16579                 return id ? this.tooltips[ id ] : null;
16580         },
16581
16582         _removeTooltip: function( tooltip ) {
16583                 tooltip.remove();
16584                 delete this.tooltips[ tooltip.attr( "id" ) ];
16585         },
16586
16587         _destroy: function() {
16588                 var that = this;
16589
16590                 // close open tooltips
16591                 $.each( this.tooltips, function( id, tooltipData ) {
16592                         // Delegate to close method to handle common cleanup
16593                         var event = $.Event( "blur" ),
16594                                 element = tooltipData.element;
16595                         event.target = event.currentTarget = element[ 0 ];
16596                         that.close( event, true );
16597
16598                         // Remove immediately; destroying an open tooltip doesn't use the
16599                         // hide animation
16600                         $( "#" + id ).remove();
16601
16602                         // Restore the title
16603                         if ( element.data( "ui-tooltip-title" ) ) {
16604                                 // If the title attribute has changed since open(), don't restore
16605                                 if ( !element.attr( "title" ) ) {
16606                                         element.attr( "title", element.data( "ui-tooltip-title" ) );
16607                                 }
16608                                 element.removeData( "ui-tooltip-title" );
16609                         }
16610                 });
16611                 this.liveRegion.remove();
16612         }
16613 });
16614
16615
16616
16617 }));