1 | /*! jQuery UI - v1.11.4 - 2015-05-31 |
||
2 | * http://jqueryui.com |
||
3 | * Includes: core.js, widget.js, position.js, autocomplete.js, menu.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 ) { |
||
0 ignored issues
–
show
|
|||
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 ) { |
||
0 ignored issues
–
show
There is no return statement if
methodValue !== instance...thodValue !== undefined is false . Are you sure this is correct? If so, consider adding return; explicitly.
This check looks for functions where a Consider this little piece of code function isBig(a) {
if (a > 5000) {
return "yes";
}
}
console.log(isBig(5001)); //returns yes
console.log(isBig(42)); //returns undefined
The function This behaviour may not be what you had intended. In any case, you can add a
![]() |
|||
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 Position 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/position/ |
||
868 | */ |
||
869 | |||
870 | (function() { |
||
871 | |||
872 | $.ui = $.ui || {}; |
||
873 | |||
874 | var cachedScrollbarWidth, supportsOffsetFractions, |
||
875 | max = Math.max, |
||
876 | abs = Math.abs, |
||
877 | round = Math.round, |
||
878 | rhorizontal = /left|center|right/, |
||
879 | rvertical = /top|center|bottom/, |
||
880 | roffset = /[\+\-]\d+(\.[\d]+)?%?/, |
||
881 | rposition = /^\w+/, |
||
882 | rpercent = /%$/, |
||
883 | _position = $.fn.position; |
||
884 | |||
885 | function getOffsets( offsets, width, height ) { |
||
886 | return [ |
||
887 | parseFloat( offsets[ 0 ] ) * ( rpercent.test( offsets[ 0 ] ) ? width / 100 : 1 ), |
||
888 | parseFloat( offsets[ 1 ] ) * ( rpercent.test( offsets[ 1 ] ) ? height / 100 : 1 ) |
||
889 | ]; |
||
890 | } |
||
891 | |||
892 | function parseCss( element, property ) { |
||
893 | return parseInt( $.css( element, property ), 10 ) || 0; |
||
894 | } |
||
895 | |||
896 | function getDimensions( elem ) { |
||
897 | var raw = elem[0]; |
||
898 | if ( raw.nodeType === 9 ) { |
||
899 | return { |
||
900 | width: elem.width(), |
||
901 | height: elem.height(), |
||
902 | offset: { top: 0, left: 0 } |
||
903 | }; |
||
904 | } |
||
905 | if ( $.isWindow( raw ) ) { |
||
906 | return { |
||
907 | width: elem.width(), |
||
908 | height: elem.height(), |
||
909 | offset: { top: elem.scrollTop(), left: elem.scrollLeft() } |
||
910 | }; |
||
911 | } |
||
912 | if ( raw.preventDefault ) { |
||
913 | return { |
||
914 | width: 0, |
||
915 | height: 0, |
||
916 | offset: { top: raw.pageY, left: raw.pageX } |
||
917 | }; |
||
918 | } |
||
919 | return { |
||
920 | width: elem.outerWidth(), |
||
921 | height: elem.outerHeight(), |
||
922 | offset: elem.offset() |
||
923 | }; |
||
924 | } |
||
925 | |||
926 | $.position = { |
||
927 | scrollbarWidth: function() { |
||
928 | if ( cachedScrollbarWidth !== undefined ) { |
||
929 | return cachedScrollbarWidth; |
||
930 | } |
||
931 | var w1, w2, |
||
932 | div = $( "<div style='display:block;position:absolute;width:50px;height:50px;overflow:hidden;'><div style='height:100px;width:auto;'></div></div>" ), |
||
933 | innerDiv = div.children()[0]; |
||
934 | |||
935 | $( "body" ).append( div ); |
||
936 | w1 = innerDiv.offsetWidth; |
||
937 | div.css( "overflow", "scroll" ); |
||
938 | |||
939 | w2 = innerDiv.offsetWidth; |
||
940 | |||
941 | if ( w1 === w2 ) { |
||
942 | w2 = div[0].clientWidth; |
||
943 | } |
||
944 | |||
945 | div.remove(); |
||
946 | |||
947 | return (cachedScrollbarWidth = w1 - w2); |
||
948 | }, |
||
949 | getScrollInfo: function( within ) { |
||
950 | var overflowX = within.isWindow || within.isDocument ? "" : |
||
951 | within.element.css( "overflow-x" ), |
||
952 | overflowY = within.isWindow || within.isDocument ? "" : |
||
953 | within.element.css( "overflow-y" ), |
||
954 | hasOverflowX = overflowX === "scroll" || |
||
955 | ( overflowX === "auto" && within.width < within.element[0].scrollWidth ), |
||
956 | hasOverflowY = overflowY === "scroll" || |
||
957 | ( overflowY === "auto" && within.height < within.element[0].scrollHeight ); |
||
958 | return { |
||
959 | width: hasOverflowY ? $.position.scrollbarWidth() : 0, |
||
960 | height: hasOverflowX ? $.position.scrollbarWidth() : 0 |
||
961 | }; |
||
962 | }, |
||
963 | getWithinInfo: function( element ) { |
||
964 | var withinElement = $( element || window ), |
||
965 | isWindow = $.isWindow( withinElement[0] ), |
||
966 | isDocument = !!withinElement[ 0 ] && withinElement[ 0 ].nodeType === 9; |
||
967 | return { |
||
968 | element: withinElement, |
||
969 | isWindow: isWindow, |
||
970 | isDocument: isDocument, |
||
971 | offset: withinElement.offset() || { left: 0, top: 0 }, |
||
972 | scrollLeft: withinElement.scrollLeft(), |
||
973 | scrollTop: withinElement.scrollTop(), |
||
974 | |||
975 | // support: jQuery 1.6.x |
||
976 | // jQuery 1.6 doesn't support .outerWidth/Height() on documents or windows |
||
977 | width: isWindow || isDocument ? withinElement.width() : withinElement.outerWidth(), |
||
978 | height: isWindow || isDocument ? withinElement.height() : withinElement.outerHeight() |
||
979 | }; |
||
980 | } |
||
981 | }; |
||
982 | |||
983 | $.fn.position = function( options ) { |
||
984 | if ( !options || !options.of ) { |
||
985 | return _position.apply( this, arguments ); |
||
986 | } |
||
987 | |||
988 | // make a copy, we don't want to modify arguments |
||
989 | options = $.extend( {}, options ); |
||
990 | |||
991 | var atOffset, targetWidth, targetHeight, targetOffset, basePosition, dimensions, |
||
992 | target = $( options.of ), |
||
993 | within = $.position.getWithinInfo( options.within ), |
||
994 | scrollInfo = $.position.getScrollInfo( within ), |
||
995 | collision = ( options.collision || "flip" ).split( " " ), |
||
996 | offsets = {}; |
||
997 | |||
998 | dimensions = getDimensions( target ); |
||
999 | if ( target[0].preventDefault ) { |
||
1000 | // force left top to allow flipping |
||
1001 | options.at = "left top"; |
||
1002 | } |
||
1003 | targetWidth = dimensions.width; |
||
1004 | targetHeight = dimensions.height; |
||
1005 | targetOffset = dimensions.offset; |
||
1006 | // clone to reuse original targetOffset later |
||
1007 | basePosition = $.extend( {}, targetOffset ); |
||
1008 | |||
1009 | // force my and at to have valid horizontal and vertical positions |
||
1010 | // if a value is missing or invalid, it will be converted to center |
||
1011 | $.each( [ "my", "at" ], function() { |
||
1012 | var pos = ( options[ this ] || "" ).split( " " ), |
||
1013 | horizontalOffset, |
||
1014 | verticalOffset; |
||
1015 | |||
1016 | if ( pos.length === 1) { |
||
1017 | pos = rhorizontal.test( pos[ 0 ] ) ? |
||
1018 | pos.concat( [ "center" ] ) : |
||
1019 | rvertical.test( pos[ 0 ] ) ? |
||
1020 | [ "center" ].concat( pos ) : |
||
1021 | [ "center", "center" ]; |
||
1022 | } |
||
1023 | pos[ 0 ] = rhorizontal.test( pos[ 0 ] ) ? pos[ 0 ] : "center"; |
||
1024 | pos[ 1 ] = rvertical.test( pos[ 1 ] ) ? pos[ 1 ] : "center"; |
||
1025 | |||
1026 | // calculate offsets |
||
1027 | horizontalOffset = roffset.exec( pos[ 0 ] ); |
||
1028 | verticalOffset = roffset.exec( pos[ 1 ] ); |
||
1029 | offsets[ this ] = [ |
||
1030 | horizontalOffset ? horizontalOffset[ 0 ] : 0, |
||
1031 | verticalOffset ? verticalOffset[ 0 ] : 0 |
||
1032 | ]; |
||
1033 | |||
1034 | // reduce to just the positions without the offsets |
||
1035 | options[ this ] = [ |
||
1036 | rposition.exec( pos[ 0 ] )[ 0 ], |
||
1037 | rposition.exec( pos[ 1 ] )[ 0 ] |
||
1038 | ]; |
||
1039 | }); |
||
1040 | |||
1041 | // normalize collision option |
||
1042 | if ( collision.length === 1 ) { |
||
1043 | collision[ 1 ] = collision[ 0 ]; |
||
1044 | } |
||
1045 | |||
1046 | if ( options.at[ 0 ] === "right" ) { |
||
1047 | basePosition.left += targetWidth; |
||
1048 | } else if ( options.at[ 0 ] === "center" ) { |
||
1049 | basePosition.left += targetWidth / 2; |
||
1050 | } |
||
1051 | |||
1052 | if ( options.at[ 1 ] === "bottom" ) { |
||
1053 | basePosition.top += targetHeight; |
||
1054 | } else if ( options.at[ 1 ] === "center" ) { |
||
1055 | basePosition.top += targetHeight / 2; |
||
1056 | } |
||
1057 | |||
1058 | atOffset = getOffsets( offsets.at, targetWidth, targetHeight ); |
||
1059 | basePosition.left += atOffset[ 0 ]; |
||
1060 | basePosition.top += atOffset[ 1 ]; |
||
1061 | |||
1062 | return this.each(function() { |
||
1063 | var collisionPosition, using, |
||
1064 | elem = $( this ), |
||
1065 | elemWidth = elem.outerWidth(), |
||
1066 | elemHeight = elem.outerHeight(), |
||
1067 | marginLeft = parseCss( this, "marginLeft" ), |
||
1068 | marginTop = parseCss( this, "marginTop" ), |
||
1069 | collisionWidth = elemWidth + marginLeft + parseCss( this, "marginRight" ) + scrollInfo.width, |
||
1070 | collisionHeight = elemHeight + marginTop + parseCss( this, "marginBottom" ) + scrollInfo.height, |
||
1071 | position = $.extend( {}, basePosition ), |
||
1072 | myOffset = getOffsets( offsets.my, elem.outerWidth(), elem.outerHeight() ); |
||
1073 | |||
1074 | if ( options.my[ 0 ] === "right" ) { |
||
1075 | position.left -= elemWidth; |
||
1076 | } else if ( options.my[ 0 ] === "center" ) { |
||
1077 | position.left -= elemWidth / 2; |
||
1078 | } |
||
1079 | |||
1080 | if ( options.my[ 1 ] === "bottom" ) { |
||
1081 | position.top -= elemHeight; |
||
1082 | } else if ( options.my[ 1 ] === "center" ) { |
||
1083 | position.top -= elemHeight / 2; |
||
1084 | } |
||
1085 | |||
1086 | position.left += myOffset[ 0 ]; |
||
1087 | position.top += myOffset[ 1 ]; |
||
1088 | |||
1089 | // if the browser doesn't support fractions, then round for consistent results |
||
1090 | if ( !supportsOffsetFractions ) { |
||
1091 | position.left = round( position.left ); |
||
1092 | position.top = round( position.top ); |
||
1093 | } |
||
1094 | |||
1095 | collisionPosition = { |
||
1096 | marginLeft: marginLeft, |
||
1097 | marginTop: marginTop |
||
1098 | }; |
||
1099 | |||
1100 | $.each( [ "left", "top" ], function( i, dir ) { |
||
1101 | if ( $.ui.position[ collision[ i ] ] ) { |
||
1102 | $.ui.position[ collision[ i ] ][ dir ]( position, { |
||
1103 | targetWidth: targetWidth, |
||
1104 | targetHeight: targetHeight, |
||
1105 | elemWidth: elemWidth, |
||
1106 | elemHeight: elemHeight, |
||
1107 | collisionPosition: collisionPosition, |
||
1108 | collisionWidth: collisionWidth, |
||
1109 | collisionHeight: collisionHeight, |
||
1110 | offset: [ atOffset[ 0 ] + myOffset[ 0 ], atOffset [ 1 ] + myOffset[ 1 ] ], |
||
1111 | my: options.my, |
||
1112 | at: options.at, |
||
1113 | within: within, |
||
1114 | elem: elem |
||
1115 | }); |
||
1116 | } |
||
1117 | }); |
||
1118 | |||
1119 | if ( options.using ) { |
||
1120 | // adds feedback as second argument to using callback, if present |
||
1121 | using = function( props ) { |
||
1122 | var left = targetOffset.left - position.left, |
||
1123 | right = left + targetWidth - elemWidth, |
||
1124 | top = targetOffset.top - position.top, |
||
1125 | bottom = top + targetHeight - elemHeight, |
||
1126 | feedback = { |
||
1127 | target: { |
||
1128 | element: target, |
||
1129 | left: targetOffset.left, |
||
1130 | top: targetOffset.top, |
||
1131 | width: targetWidth, |
||
1132 | height: targetHeight |
||
1133 | }, |
||
1134 | element: { |
||
1135 | element: elem, |
||
1136 | left: position.left, |
||
1137 | top: position.top, |
||
1138 | width: elemWidth, |
||
1139 | height: elemHeight |
||
1140 | }, |
||
1141 | horizontal: right < 0 ? "left" : left > 0 ? "right" : "center", |
||
1142 | vertical: bottom < 0 ? "top" : top > 0 ? "bottom" : "middle" |
||
1143 | }; |
||
1144 | if ( targetWidth < elemWidth && abs( left + right ) < targetWidth ) { |
||
1145 | feedback.horizontal = "center"; |
||
1146 | } |
||
1147 | if ( targetHeight < elemHeight && abs( top + bottom ) < targetHeight ) { |
||
1148 | feedback.vertical = "middle"; |
||
1149 | } |
||
1150 | if ( max( abs( left ), abs( right ) ) > max( abs( top ), abs( bottom ) ) ) { |
||
1151 | feedback.important = "horizontal"; |
||
1152 | } else { |
||
1153 | feedback.important = "vertical"; |
||
1154 | } |
||
1155 | options.using.call( this, props, feedback ); |
||
1156 | }; |
||
1157 | } |
||
1158 | |||
1159 | elem.offset( $.extend( position, { using: using } ) ); |
||
1160 | }); |
||
1161 | }; |
||
1162 | |||
1163 | $.ui.position = { |
||
1164 | fit: { |
||
1165 | left: function( position, data ) { |
||
1166 | var within = data.within, |
||
1167 | withinOffset = within.isWindow ? within.scrollLeft : within.offset.left, |
||
1168 | outerWidth = within.width, |
||
1169 | collisionPosLeft = position.left - data.collisionPosition.marginLeft, |
||
1170 | overLeft = withinOffset - collisionPosLeft, |
||
1171 | overRight = collisionPosLeft + data.collisionWidth - outerWidth - withinOffset, |
||
1172 | newOverRight; |
||
1173 | |||
1174 | // element is wider than within |
||
1175 | if ( data.collisionWidth > outerWidth ) { |
||
1176 | // element is initially over the left side of within |
||
1177 | if ( overLeft > 0 && overRight <= 0 ) { |
||
1178 | newOverRight = position.left + overLeft + data.collisionWidth - outerWidth - withinOffset; |
||
1179 | position.left += overLeft - newOverRight; |
||
1180 | // element is initially over right side of within |
||
1181 | } else if ( overRight > 0 && overLeft <= 0 ) { |
||
1182 | position.left = withinOffset; |
||
1183 | // element is initially over both left and right sides of within |
||
1184 | } else { |
||
1185 | if ( overLeft > overRight ) { |
||
1186 | position.left = withinOffset + outerWidth - data.collisionWidth; |
||
1187 | } else { |
||
1188 | position.left = withinOffset; |
||
1189 | } |
||
1190 | } |
||
1191 | // too far left -> align with left edge |
||
1192 | } else if ( overLeft > 0 ) { |
||
1193 | position.left += overLeft; |
||
1194 | // too far right -> align with right edge |
||
1195 | } else if ( overRight > 0 ) { |
||
1196 | position.left -= overRight; |
||
1197 | // adjust based on position and margin |
||
1198 | } else { |
||
1199 | position.left = max( position.left - collisionPosLeft, position.left ); |
||
1200 | } |
||
1201 | }, |
||
1202 | top: function( position, data ) { |
||
1203 | var within = data.within, |
||
1204 | withinOffset = within.isWindow ? within.scrollTop : within.offset.top, |
||
1205 | outerHeight = data.within.height, |
||
1206 | collisionPosTop = position.top - data.collisionPosition.marginTop, |
||
1207 | overTop = withinOffset - collisionPosTop, |
||
1208 | overBottom = collisionPosTop + data.collisionHeight - outerHeight - withinOffset, |
||
1209 | newOverBottom; |
||
1210 | |||
1211 | // element is taller than within |
||
1212 | if ( data.collisionHeight > outerHeight ) { |
||
1213 | // element is initially over the top of within |
||
1214 | if ( overTop > 0 && overBottom <= 0 ) { |
||
1215 | newOverBottom = position.top + overTop + data.collisionHeight - outerHeight - withinOffset; |
||
1216 | position.top += overTop - newOverBottom; |
||
1217 | // element is initially over bottom of within |
||
1218 | } else if ( overBottom > 0 && overTop <= 0 ) { |
||
1219 | position.top = withinOffset; |
||
1220 | // element is initially over both top and bottom of within |
||
1221 | } else { |
||
1222 | if ( overTop > overBottom ) { |
||
1223 | position.top = withinOffset + outerHeight - data.collisionHeight; |
||
1224 | } else { |
||
1225 | position.top = withinOffset; |
||
1226 | } |
||
1227 | } |
||
1228 | // too far up -> align with top |
||
1229 | } else if ( overTop > 0 ) { |
||
1230 | position.top += overTop; |
||
1231 | // too far down -> align with bottom edge |
||
1232 | } else if ( overBottom > 0 ) { |
||
1233 | position.top -= overBottom; |
||
1234 | // adjust based on position and margin |
||
1235 | } else { |
||
1236 | position.top = max( position.top - collisionPosTop, position.top ); |
||
1237 | } |
||
1238 | } |
||
1239 | }, |
||
1240 | flip: { |
||
1241 | left: function( position, data ) { |
||
1242 | var within = data.within, |
||
1243 | withinOffset = within.offset.left + within.scrollLeft, |
||
1244 | outerWidth = within.width, |
||
1245 | offsetLeft = within.isWindow ? within.scrollLeft : within.offset.left, |
||
1246 | collisionPosLeft = position.left - data.collisionPosition.marginLeft, |
||
1247 | overLeft = collisionPosLeft - offsetLeft, |
||
1248 | overRight = collisionPosLeft + data.collisionWidth - outerWidth - offsetLeft, |
||
1249 | myOffset = data.my[ 0 ] === "left" ? |
||
1250 | -data.elemWidth : |
||
1251 | data.my[ 0 ] === "right" ? |
||
1252 | data.elemWidth : |
||
1253 | 0, |
||
1254 | atOffset = data.at[ 0 ] === "left" ? |
||
1255 | data.targetWidth : |
||
1256 | data.at[ 0 ] === "right" ? |
||
1257 | -data.targetWidth : |
||
1258 | 0, |
||
1259 | offset = -2 * data.offset[ 0 ], |
||
1260 | newOverRight, |
||
1261 | newOverLeft; |
||
1262 | |||
1263 | if ( overLeft < 0 ) { |
||
1264 | newOverRight = position.left + myOffset + atOffset + offset + data.collisionWidth - outerWidth - withinOffset; |
||
1265 | if ( newOverRight < 0 || newOverRight < abs( overLeft ) ) { |
||
1266 | position.left += myOffset + atOffset + offset; |
||
1267 | } |
||
1268 | } else if ( overRight > 0 ) { |
||
1269 | newOverLeft = position.left - data.collisionPosition.marginLeft + myOffset + atOffset + offset - offsetLeft; |
||
1270 | if ( newOverLeft > 0 || abs( newOverLeft ) < overRight ) { |
||
1271 | position.left += myOffset + atOffset + offset; |
||
1272 | } |
||
1273 | } |
||
1274 | }, |
||
1275 | top: function( position, data ) { |
||
1276 | var within = data.within, |
||
1277 | withinOffset = within.offset.top + within.scrollTop, |
||
1278 | outerHeight = within.height, |
||
1279 | offsetTop = within.isWindow ? within.scrollTop : within.offset.top, |
||
1280 | collisionPosTop = position.top - data.collisionPosition.marginTop, |
||
1281 | overTop = collisionPosTop - offsetTop, |
||
1282 | overBottom = collisionPosTop + data.collisionHeight - outerHeight - offsetTop, |
||
1283 | top = data.my[ 1 ] === "top", |
||
1284 | myOffset = top ? |
||
1285 | -data.elemHeight : |
||
1286 | data.my[ 1 ] === "bottom" ? |
||
1287 | data.elemHeight : |
||
1288 | 0, |
||
1289 | atOffset = data.at[ 1 ] === "top" ? |
||
1290 | data.targetHeight : |
||
1291 | data.at[ 1 ] === "bottom" ? |
||
1292 | -data.targetHeight : |
||
1293 | 0, |
||
1294 | offset = -2 * data.offset[ 1 ], |
||
1295 | newOverTop, |
||
1296 | newOverBottom; |
||
1297 | if ( overTop < 0 ) { |
||
1298 | newOverBottom = position.top + myOffset + atOffset + offset + data.collisionHeight - outerHeight - withinOffset; |
||
1299 | if ( newOverBottom < 0 || newOverBottom < abs( overTop ) ) { |
||
1300 | position.top += myOffset + atOffset + offset; |
||
1301 | } |
||
1302 | } else if ( overBottom > 0 ) { |
||
1303 | newOverTop = position.top - data.collisionPosition.marginTop + myOffset + atOffset + offset - offsetTop; |
||
1304 | if ( newOverTop > 0 || abs( newOverTop ) < overBottom ) { |
||
1305 | position.top += myOffset + atOffset + offset; |
||
1306 | } |
||
1307 | } |
||
1308 | } |
||
1309 | }, |
||
1310 | flipfit: { |
||
1311 | left: function() { |
||
1312 | $.ui.position.flip.left.apply( this, arguments ); |
||
1313 | $.ui.position.fit.left.apply( this, arguments ); |
||
1314 | }, |
||
1315 | top: function() { |
||
1316 | $.ui.position.flip.top.apply( this, arguments ); |
||
1317 | $.ui.position.fit.top.apply( this, arguments ); |
||
1318 | } |
||
1319 | } |
||
1320 | }; |
||
1321 | |||
1322 | // fraction support test |
||
1323 | (function() { |
||
1324 | var testElement, testElementParent, testElementStyle, offsetLeft, i, |
||
1325 | body = document.getElementsByTagName( "body" )[ 0 ], |
||
1326 | div = document.createElement( "div" ); |
||
1327 | |||
1328 | //Create a "fake body" for testing based on method used in jQuery.support |
||
1329 | testElement = document.createElement( body ? "div" : "body" ); |
||
1330 | testElementStyle = { |
||
1331 | visibility: "hidden", |
||
1332 | width: 0, |
||
1333 | height: 0, |
||
1334 | border: 0, |
||
1335 | margin: 0, |
||
1336 | background: "none" |
||
1337 | }; |
||
1338 | if ( body ) { |
||
1339 | $.extend( testElementStyle, { |
||
1340 | position: "absolute", |
||
1341 | left: "-1000px", |
||
1342 | top: "-1000px" |
||
1343 | }); |
||
1344 | } |
||
1345 | for ( i in testElementStyle ) { |
||
1346 | testElement.style[ i ] = testElementStyle[ i ]; |
||
1347 | } |
||
1348 | testElement.appendChild( div ); |
||
1349 | testElementParent = body || document.documentElement; |
||
1350 | testElementParent.insertBefore( testElement, testElementParent.firstChild ); |
||
1351 | |||
1352 | div.style.cssText = "position: absolute; left: 10.7432222px;"; |
||
1353 | |||
1354 | offsetLeft = $( div ).offset().left; |
||
1355 | supportsOffsetFractions = offsetLeft > 10 && offsetLeft < 11; |
||
1356 | |||
1357 | testElement.innerHTML = ""; |
||
1358 | testElementParent.removeChild( testElement ); |
||
1359 | })(); |
||
1360 | |||
1361 | })(); |
||
1362 | |||
1363 | var position = $.ui.position; |
||
1364 | |||
1365 | |||
1366 | /*! |
||
1367 | * jQuery UI Menu 1.11.4 |
||
1368 | * http://jqueryui.com |
||
1369 | * |
||
1370 | * Copyright jQuery Foundation and other contributors |
||
1371 | * Released under the MIT license. |
||
1372 | * http://jquery.org/license |
||
1373 | * |
||
1374 | * http://api.jqueryui.com/menu/ |
||
1375 | */ |
||
1376 | |||
1377 | |||
1378 | var menu = $.widget( "ui.menu", { |
||
1379 | version: "1.11.4", |
||
1380 | defaultElement: "<ul>", |
||
1381 | delay: 300, |
||
1382 | options: { |
||
1383 | icons: { |
||
1384 | submenu: "ui-icon-carat-1-e" |
||
1385 | }, |
||
1386 | items: "> *", |
||
1387 | menus: "ul", |
||
1388 | position: { |
||
1389 | my: "left-1 top", |
||
1390 | at: "right top" |
||
1391 | }, |
||
1392 | role: "menu", |
||
1393 | |||
1394 | // callbacks |
||
1395 | blur: null, |
||
1396 | focus: null, |
||
1397 | select: null |
||
1398 | }, |
||
1399 | |||
1400 | _create: function() { |
||
1401 | this.activeMenu = this.element; |
||
1402 | |||
1403 | // Flag used to prevent firing of the click handler |
||
1404 | // as the event bubbles up through nested menus |
||
1405 | this.mouseHandled = false; |
||
1406 | this.element |
||
1407 | .uniqueId() |
||
1408 | .addClass( "ui-menu ui-widget ui-widget-content" ) |
||
1409 | .toggleClass( "ui-menu-icons", !!this.element.find( ".ui-icon" ).length ) |
||
1410 | .attr({ |
||
1411 | role: this.options.role, |
||
1412 | tabIndex: 0 |
||
1413 | }); |
||
1414 | |||
1415 | if ( this.options.disabled ) { |
||
1416 | this.element |
||
1417 | .addClass( "ui-state-disabled" ) |
||
1418 | .attr( "aria-disabled", "true" ); |
||
1419 | } |
||
1420 | |||
1421 | this._on({ |
||
1422 | // Prevent focus from sticking to links inside menu after clicking |
||
1423 | // them (focus should always stay on UL during navigation). |
||
1424 | "mousedown .ui-menu-item": function( event ) { |
||
1425 | event.preventDefault(); |
||
1426 | }, |
||
1427 | "click .ui-menu-item": function( event ) { |
||
1428 | var target = $( event.target ); |
||
1429 | if ( !this.mouseHandled && target.not( ".ui-state-disabled" ).length ) { |
||
1430 | this.select( event ); |
||
1431 | |||
1432 | // Only set the mouseHandled flag if the event will bubble, see #9469. |
||
1433 | if ( !event.isPropagationStopped() ) { |
||
1434 | this.mouseHandled = true; |
||
1435 | } |
||
1436 | |||
1437 | // Open submenu on click |
||
1438 | if ( target.has( ".ui-menu" ).length ) { |
||
1439 | this.expand( event ); |
||
1440 | } else if ( !this.element.is( ":focus" ) && $( this.document[ 0 ].activeElement ).closest( ".ui-menu" ).length ) { |
||
1441 | |||
1442 | // Redirect focus to the menu |
||
1443 | this.element.trigger( "focus", [ true ] ); |
||
1444 | |||
1445 | // If the active item is on the top level, let it stay active. |
||
1446 | // Otherwise, blur the active item since it is no longer visible. |
||
1447 | if ( this.active && this.active.parents( ".ui-menu" ).length === 1 ) { |
||
1448 | clearTimeout( this.timer ); |
||
1449 | } |
||
1450 | } |
||
1451 | } |
||
1452 | }, |
||
1453 | "mouseenter .ui-menu-item": function( event ) { |
||
1454 | // Ignore mouse events while typeahead is active, see #10458. |
||
1455 | // Prevents focusing the wrong item when typeahead causes a scroll while the mouse |
||
1456 | // is over an item in the menu |
||
1457 | if ( this.previousFilter ) { |
||
1458 | return; |
||
1459 | } |
||
1460 | var target = $( event.currentTarget ); |
||
1461 | // Remove ui-state-active class from siblings of the newly focused menu item |
||
1462 | // to avoid a jump caused by adjacent elements both having a class with a border |
||
1463 | target.siblings( ".ui-state-active" ).removeClass( "ui-state-active" ); |
||
1464 | this.focus( event, target ); |
||
1465 | }, |
||
1466 | mouseleave: "collapseAll", |
||
1467 | "mouseleave .ui-menu": "collapseAll", |
||
1468 | focus: function( event, keepActiveItem ) { |
||
1469 | // If there's already an active item, keep it active |
||
1470 | // If not, activate the first item |
||
1471 | var item = this.active || this.element.find( this.options.items ).eq( 0 ); |
||
1472 | |||
1473 | if ( !keepActiveItem ) { |
||
1474 | this.focus( event, item ); |
||
1475 | } |
||
1476 | }, |
||
1477 | blur: function( event ) { |
||
1478 | this._delay(function() { |
||
1479 | if ( !$.contains( this.element[0], this.document[0].activeElement ) ) { |
||
1480 | this.collapseAll( event ); |
||
1481 | } |
||
1482 | }); |
||
1483 | }, |
||
1484 | keydown: "_keydown" |
||
1485 | }); |
||
1486 | |||
1487 | this.refresh(); |
||
1488 | |||
1489 | // Clicks outside of a menu collapse any open menus |
||
1490 | this._on( this.document, { |
||
1491 | click: function( event ) { |
||
1492 | if ( this._closeOnDocumentClick( event ) ) { |
||
1493 | this.collapseAll( event ); |
||
1494 | } |
||
1495 | |||
1496 | // Reset the mouseHandled flag |
||
1497 | this.mouseHandled = false; |
||
1498 | } |
||
1499 | }); |
||
1500 | }, |
||
1501 | |||
1502 | _destroy: function() { |
||
1503 | // Destroy (sub)menus |
||
1504 | this.element |
||
1505 | .removeAttr( "aria-activedescendant" ) |
||
1506 | .find( ".ui-menu" ).addBack() |
||
1507 | .removeClass( "ui-menu ui-widget ui-widget-content ui-menu-icons ui-front" ) |
||
1508 | .removeAttr( "role" ) |
||
1509 | .removeAttr( "tabIndex" ) |
||
1510 | .removeAttr( "aria-labelledby" ) |
||
1511 | .removeAttr( "aria-expanded" ) |
||
1512 | .removeAttr( "aria-hidden" ) |
||
1513 | .removeAttr( "aria-disabled" ) |
||
1514 | .removeUniqueId() |
||
1515 | .show(); |
||
1516 | |||
1517 | // Destroy menu items |
||
1518 | this.element.find( ".ui-menu-item" ) |
||
1519 | .removeClass( "ui-menu-item" ) |
||
1520 | .removeAttr( "role" ) |
||
1521 | .removeAttr( "aria-disabled" ) |
||
1522 | .removeUniqueId() |
||
1523 | .removeClass( "ui-state-hover" ) |
||
1524 | .removeAttr( "tabIndex" ) |
||
1525 | .removeAttr( "role" ) |
||
1526 | .removeAttr( "aria-haspopup" ) |
||
1527 | .children().each( function() { |
||
1528 | var elem = $( this ); |
||
1529 | if ( elem.data( "ui-menu-submenu-carat" ) ) { |
||
1530 | elem.remove(); |
||
1531 | } |
||
1532 | }); |
||
1533 | |||
1534 | // Destroy menu dividers |
||
1535 | this.element.find( ".ui-menu-divider" ).removeClass( "ui-menu-divider ui-widget-content" ); |
||
1536 | }, |
||
1537 | |||
1538 | _keydown: function( event ) { |
||
1539 | var match, prev, character, skip, |
||
1540 | preventDefault = true; |
||
1541 | |||
1542 | switch ( event.keyCode ) { |
||
1543 | case $.ui.keyCode.PAGE_UP: |
||
1544 | this.previousPage( event ); |
||
1545 | break; |
||
1546 | case $.ui.keyCode.PAGE_DOWN: |
||
1547 | this.nextPage( event ); |
||
1548 | break; |
||
1549 | case $.ui.keyCode.HOME: |
||
1550 | this._move( "first", "first", event ); |
||
1551 | break; |
||
1552 | case $.ui.keyCode.END: |
||
1553 | this._move( "last", "last", event ); |
||
1554 | break; |
||
1555 | case $.ui.keyCode.UP: |
||
1556 | this.previous( event ); |
||
1557 | break; |
||
1558 | case $.ui.keyCode.DOWN: |
||
1559 | this.next( event ); |
||
1560 | break; |
||
1561 | case $.ui.keyCode.LEFT: |
||
1562 | this.collapse( event ); |
||
1563 | break; |
||
1564 | case $.ui.keyCode.RIGHT: |
||
1565 | if ( this.active && !this.active.is( ".ui-state-disabled" ) ) { |
||
1566 | this.expand( event ); |
||
1567 | } |
||
1568 | break; |
||
1569 | case $.ui.keyCode.ENTER: |
||
1570 | case $.ui.keyCode.SPACE: |
||
1571 | this._activate( event ); |
||
1572 | break; |
||
1573 | case $.ui.keyCode.ESCAPE: |
||
1574 | this.collapse( event ); |
||
1575 | break; |
||
1576 | default: |
||
1577 | preventDefault = false; |
||
1578 | prev = this.previousFilter || ""; |
||
1579 | character = String.fromCharCode( event.keyCode ); |
||
1580 | skip = false; |
||
1581 | |||
1582 | clearTimeout( this.filterTimer ); |
||
1583 | |||
1584 | if ( character === prev ) { |
||
1585 | skip = true; |
||
1586 | } else { |
||
1587 | character = prev + character; |
||
1588 | } |
||
1589 | |||
1590 | match = this._filterMenuItems( character ); |
||
1591 | match = skip && match.index( this.active.next() ) !== -1 ? |
||
1592 | this.active.nextAll( ".ui-menu-item" ) : |
||
1593 | match; |
||
1594 | |||
1595 | // If no matches on the current filter, reset to the last character pressed |
||
1596 | // to move down the menu to the first item that starts with that character |
||
1597 | if ( !match.length ) { |
||
1598 | character = String.fromCharCode( event.keyCode ); |
||
1599 | match = this._filterMenuItems( character ); |
||
1600 | } |
||
1601 | |||
1602 | if ( match.length ) { |
||
1603 | this.focus( event, match ); |
||
1604 | this.previousFilter = character; |
||
1605 | this.filterTimer = this._delay(function() { |
||
1606 | delete this.previousFilter; |
||
1607 | }, 1000 ); |
||
1608 | } else { |
||
1609 | delete this.previousFilter; |
||
1610 | } |
||
1611 | } |
||
1612 | |||
1613 | if ( preventDefault ) { |
||
1614 | event.preventDefault(); |
||
1615 | } |
||
1616 | }, |
||
1617 | |||
1618 | _activate: function( event ) { |
||
1619 | if ( !this.active.is( ".ui-state-disabled" ) ) { |
||
1620 | if ( this.active.is( "[aria-haspopup='true']" ) ) { |
||
1621 | this.expand( event ); |
||
1622 | } else { |
||
1623 | this.select( event ); |
||
1624 | } |
||
1625 | } |
||
1626 | }, |
||
1627 | |||
1628 | refresh: function() { |
||
1629 | var menus, items, |
||
1630 | that = this, |
||
1631 | icon = this.options.icons.submenu, |
||
1632 | submenus = this.element.find( this.options.menus ); |
||
1633 | |||
1634 | this.element.toggleClass( "ui-menu-icons", !!this.element.find( ".ui-icon" ).length ); |
||
1635 | |||
1636 | // Initialize nested menus |
||
1637 | submenus.filter( ":not(.ui-menu)" ) |
||
1638 | .addClass( "ui-menu ui-widget ui-widget-content ui-front" ) |
||
1639 | .hide() |
||
1640 | .attr({ |
||
1641 | role: this.options.role, |
||
1642 | "aria-hidden": "true", |
||
1643 | "aria-expanded": "false" |
||
1644 | }) |
||
1645 | .each(function() { |
||
1646 | var menu = $( this ), |
||
1647 | item = menu.parent(), |
||
1648 | submenuCarat = $( "<span>" ) |
||
1649 | .addClass( "ui-menu-icon ui-icon " + icon ) |
||
1650 | .data( "ui-menu-submenu-carat", true ); |
||
1651 | |||
1652 | item |
||
1653 | .attr( "aria-haspopup", "true" ) |
||
1654 | .prepend( submenuCarat ); |
||
1655 | menu.attr( "aria-labelledby", item.attr( "id" ) ); |
||
1656 | }); |
||
1657 | |||
1658 | menus = submenus.add( this.element ); |
||
1659 | items = menus.find( this.options.items ); |
||
1660 | |||
1661 | // Initialize menu-items containing spaces and/or dashes only as dividers |
||
1662 | items.not( ".ui-menu-item" ).each(function() { |
||
1663 | var item = $( this ); |
||
1664 | if ( that._isDivider( item ) ) { |
||
1665 | item.addClass( "ui-widget-content ui-menu-divider" ); |
||
1666 | } |
||
1667 | }); |
||
1668 | |||
1669 | // Don't refresh list items that are already adapted |
||
1670 | items.not( ".ui-menu-item, .ui-menu-divider" ) |
||
1671 | .addClass( "ui-menu-item" ) |
||
1672 | .uniqueId() |
||
1673 | .attr({ |
||
1674 | tabIndex: -1, |
||
1675 | role: this._itemRole() |
||
1676 | }); |
||
1677 | |||
1678 | // Add aria-disabled attribute to any disabled menu item |
||
1679 | items.filter( ".ui-state-disabled" ).attr( "aria-disabled", "true" ); |
||
1680 | |||
1681 | // If the active item has been removed, blur the menu |
||
1682 | if ( this.active && !$.contains( this.element[ 0 ], this.active[ 0 ] ) ) { |
||
1683 | this.blur(); |
||
1684 | } |
||
1685 | }, |
||
1686 | |||
1687 | _itemRole: function() { |
||
1688 | return { |
||
1689 | menu: "menuitem", |
||
1690 | listbox: "option" |
||
1691 | }[ this.options.role ]; |
||
1692 | }, |
||
1693 | |||
1694 | _setOption: function( key, value ) { |
||
1695 | if ( key === "icons" ) { |
||
1696 | this.element.find( ".ui-menu-icon" ) |
||
1697 | .removeClass( this.options.icons.submenu ) |
||
1698 | .addClass( value.submenu ); |
||
1699 | } |
||
1700 | if ( key === "disabled" ) { |
||
1701 | this.element |
||
1702 | .toggleClass( "ui-state-disabled", !!value ) |
||
1703 | .attr( "aria-disabled", value ); |
||
1704 | } |
||
1705 | this._super( key, value ); |
||
1706 | }, |
||
1707 | |||
1708 | focus: function( event, item ) { |
||
1709 | var nested, focused; |
||
1710 | this.blur( event, event && event.type === "focus" ); |
||
1711 | |||
1712 | this._scrollIntoView( item ); |
||
1713 | |||
1714 | this.active = item.first(); |
||
1715 | focused = this.active.addClass( "ui-state-focus" ).removeClass( "ui-state-active" ); |
||
1716 | // Only update aria-activedescendant if there's a role |
||
1717 | // otherwise we assume focus is managed elsewhere |
||
1718 | if ( this.options.role ) { |
||
1719 | this.element.attr( "aria-activedescendant", focused.attr( "id" ) ); |
||
1720 | } |
||
1721 | |||
1722 | // Highlight active parent menu item, if any |
||
1723 | this.active |
||
1724 | .parent() |
||
1725 | .closest( ".ui-menu-item" ) |
||
1726 | .addClass( "ui-state-active" ); |
||
1727 | |||
1728 | if ( event && event.type === "keydown" ) { |
||
1729 | this._close(); |
||
1730 | } else { |
||
1731 | this.timer = this._delay(function() { |
||
1732 | this._close(); |
||
1733 | }, this.delay ); |
||
1734 | } |
||
1735 | |||
1736 | nested = item.children( ".ui-menu" ); |
||
1737 | if ( nested.length && event && ( /^mouse/.test( event.type ) ) ) { |
||
1738 | this._startOpening(nested); |
||
1739 | } |
||
1740 | this.activeMenu = item.parent(); |
||
1741 | |||
1742 | this._trigger( "focus", event, { item: item } ); |
||
1743 | }, |
||
1744 | |||
1745 | _scrollIntoView: function( item ) { |
||
1746 | var borderTop, paddingTop, offset, scroll, elementHeight, itemHeight; |
||
1747 | if ( this._hasScroll() ) { |
||
1748 | borderTop = parseFloat( $.css( this.activeMenu[0], "borderTopWidth" ) ) || 0; |
||
1749 | paddingTop = parseFloat( $.css( this.activeMenu[0], "paddingTop" ) ) || 0; |
||
1750 | offset = item.offset().top - this.activeMenu.offset().top - borderTop - paddingTop; |
||
1751 | scroll = this.activeMenu.scrollTop(); |
||
1752 | elementHeight = this.activeMenu.height(); |
||
1753 | itemHeight = item.outerHeight(); |
||
1754 | |||
1755 | if ( offset < 0 ) { |
||
1756 | this.activeMenu.scrollTop( scroll + offset ); |
||
1757 | } else if ( offset + itemHeight > elementHeight ) { |
||
1758 | this.activeMenu.scrollTop( scroll + offset - elementHeight + itemHeight ); |
||
1759 | } |
||
1760 | } |
||
1761 | }, |
||
1762 | |||
1763 | blur: function( event, fromFocus ) { |
||
1764 | if ( !fromFocus ) { |
||
1765 | clearTimeout( this.timer ); |
||
1766 | } |
||
1767 | |||
1768 | if ( !this.active ) { |
||
1769 | return; |
||
1770 | } |
||
1771 | |||
1772 | this.active.removeClass( "ui-state-focus" ); |
||
1773 | this.active = null; |
||
1774 | |||
1775 | this._trigger( "blur", event, { item: this.active } ); |
||
1776 | }, |
||
1777 | |||
1778 | _startOpening: function( submenu ) { |
||
1779 | clearTimeout( this.timer ); |
||
1780 | |||
1781 | // Don't open if already open fixes a Firefox bug that caused a .5 pixel |
||
1782 | // shift in the submenu position when mousing over the carat icon |
||
1783 | if ( submenu.attr( "aria-hidden" ) !== "true" ) { |
||
1784 | return; |
||
1785 | } |
||
1786 | |||
1787 | this.timer = this._delay(function() { |
||
1788 | this._close(); |
||
1789 | this._open( submenu ); |
||
1790 | }, this.delay ); |
||
1791 | }, |
||
1792 | |||
1793 | _open: function( submenu ) { |
||
1794 | var position = $.extend({ |
||
1795 | of: this.active |
||
1796 | }, this.options.position ); |
||
1797 | |||
1798 | clearTimeout( this.timer ); |
||
1799 | this.element.find( ".ui-menu" ).not( submenu.parents( ".ui-menu" ) ) |
||
1800 | .hide() |
||
1801 | .attr( "aria-hidden", "true" ); |
||
1802 | |||
1803 | submenu |
||
1804 | .show() |
||
1805 | .removeAttr( "aria-hidden" ) |
||
1806 | .attr( "aria-expanded", "true" ) |
||
1807 | .position( position ); |
||
1808 | }, |
||
1809 | |||
1810 | collapseAll: function( event, all ) { |
||
1811 | clearTimeout( this.timer ); |
||
1812 | this.timer = this._delay(function() { |
||
1813 | // If we were passed an event, look for the submenu that contains the event |
||
1814 | var currentMenu = all ? this.element : |
||
1815 | $( event && event.target ).closest( this.element.find( ".ui-menu" ) ); |
||
1816 | |||
1817 | // If we found no valid submenu ancestor, use the main menu to close all sub menus anyway |
||
1818 | if ( !currentMenu.length ) { |
||
1819 | currentMenu = this.element; |
||
1820 | } |
||
1821 | |||
1822 | this._close( currentMenu ); |
||
1823 | |||
1824 | this.blur( event ); |
||
1825 | this.activeMenu = currentMenu; |
||
1826 | }, this.delay ); |
||
1827 | }, |
||
1828 | |||
1829 | // With no arguments, closes the currently active menu - if nothing is active |
||
1830 | // it closes all menus. If passed an argument, it will search for menus BELOW |
||
1831 | _close: function( startMenu ) { |
||
1832 | if ( !startMenu ) { |
||
1833 | startMenu = this.active ? this.active.parent() : this.element; |
||
1834 | } |
||
1835 | |||
1836 | startMenu |
||
1837 | .find( ".ui-menu" ) |
||
1838 | .hide() |
||
1839 | .attr( "aria-hidden", "true" ) |
||
1840 | .attr( "aria-expanded", "false" ) |
||
1841 | .end() |
||
1842 | .find( ".ui-state-active" ).not( ".ui-state-focus" ) |
||
1843 | .removeClass( "ui-state-active" ); |
||
1844 | }, |
||
1845 | |||
1846 | _closeOnDocumentClick: function( event ) { |
||
1847 | return !$( event.target ).closest( ".ui-menu" ).length; |
||
1848 | }, |
||
1849 | |||
1850 | _isDivider: function( item ) { |
||
1851 | |||
1852 | // Match hyphen, em dash, en dash |
||
1853 | return !/[^\-\u2014\u2013\s]/.test( item.text() ); |
||
1854 | }, |
||
1855 | |||
1856 | collapse: function( event ) { |
||
1857 | var newItem = this.active && |
||
1858 | this.active.parent().closest( ".ui-menu-item", this.element ); |
||
1859 | if ( newItem && newItem.length ) { |
||
1860 | this._close(); |
||
1861 | this.focus( event, newItem ); |
||
1862 | } |
||
1863 | }, |
||
1864 | |||
1865 | expand: function( event ) { |
||
1866 | var newItem = this.active && |
||
1867 | this.active |
||
1868 | .children( ".ui-menu " ) |
||
1869 | .find( this.options.items ) |
||
1870 | .first(); |
||
1871 | |||
1872 | if ( newItem && newItem.length ) { |
||
1873 | this._open( newItem.parent() ); |
||
1874 | |||
1875 | // Delay so Firefox will not hide activedescendant change in expanding submenu from AT |
||
1876 | this._delay(function() { |
||
1877 | this.focus( event, newItem ); |
||
1878 | }); |
||
1879 | } |
||
1880 | }, |
||
1881 | |||
1882 | next: function( event ) { |
||
1883 | this._move( "next", "first", event ); |
||
1884 | }, |
||
1885 | |||
1886 | previous: function( event ) { |
||
1887 | this._move( "prev", "last", event ); |
||
1888 | }, |
||
1889 | |||
1890 | isFirstItem: function() { |
||
1891 | return this.active && !this.active.prevAll( ".ui-menu-item" ).length; |
||
1892 | }, |
||
1893 | |||
1894 | isLastItem: function() { |
||
1895 | return this.active && !this.active.nextAll( ".ui-menu-item" ).length; |
||
1896 | }, |
||
1897 | |||
1898 | _move: function( direction, filter, event ) { |
||
1899 | var next; |
||
1900 | if ( this.active ) { |
||
1901 | if ( direction === "first" || direction === "last" ) { |
||
1902 | next = this.active |
||
1903 | [ direction === "first" ? "prevAll" : "nextAll" ]( ".ui-menu-item" ) |
||
1904 | .eq( -1 ); |
||
1905 | } else { |
||
1906 | next = this.active |
||
1907 | [ direction + "All" ]( ".ui-menu-item" ) |
||
1908 | .eq( 0 ); |
||
1909 | } |
||
1910 | } |
||
1911 | if ( !next || !next.length || !this.active ) { |
||
1912 | next = this.activeMenu.find( this.options.items )[ filter ](); |
||
1913 | } |
||
1914 | |||
1915 | this.focus( event, next ); |
||
1916 | }, |
||
1917 | |||
1918 | nextPage: function( event ) { |
||
1919 | var item, base, height; |
||
1920 | |||
1921 | if ( !this.active ) { |
||
1922 | this.next( event ); |
||
1923 | return; |
||
1924 | } |
||
1925 | if ( this.isLastItem() ) { |
||
1926 | return; |
||
1927 | } |
||
1928 | if ( this._hasScroll() ) { |
||
1929 | base = this.active.offset().top; |
||
1930 | height = this.element.height(); |
||
1931 | this.active.nextAll( ".ui-menu-item" ).each(function() { |
||
1932 | item = $( this ); |
||
1933 | return item.offset().top - base - height < 0; |
||
1934 | }); |
||
1935 | |||
1936 | this.focus( event, item ); |
||
1937 | } else { |
||
1938 | this.focus( event, this.activeMenu.find( this.options.items ) |
||
1939 | [ !this.active ? "first" : "last" ]() ); |
||
1940 | } |
||
1941 | }, |
||
1942 | |||
1943 | previousPage: function( event ) { |
||
1944 | var item, base, height; |
||
1945 | if ( !this.active ) { |
||
1946 | this.next( event ); |
||
1947 | return; |
||
1948 | } |
||
1949 | if ( this.isFirstItem() ) { |
||
1950 | return; |
||
1951 | } |
||
1952 | if ( this._hasScroll() ) { |
||
1953 | base = this.active.offset().top; |
||
1954 | height = this.element.height(); |
||
1955 | this.active.prevAll( ".ui-menu-item" ).each(function() { |
||
1956 | item = $( this ); |
||
1957 | return item.offset().top - base + height > 0; |
||
1958 | }); |
||
1959 | |||
1960 | this.focus( event, item ); |
||
1961 | } else { |
||
1962 | this.focus( event, this.activeMenu.find( this.options.items ).first() ); |
||
1963 | } |
||
1964 | }, |
||
1965 | |||
1966 | _hasScroll: function() { |
||
1967 | return this.element.outerHeight() < this.element.prop( "scrollHeight" ); |
||
1968 | }, |
||
1969 | |||
1970 | select: function( event ) { |
||
1971 | // TODO: It should never be possible to not have an active item at this |
||
1972 | // point, but the tests don't trigger mouseenter before click. |
||
1973 | this.active = this.active || $( event.target ).closest( ".ui-menu-item" ); |
||
1974 | var ui = { item: this.active }; |
||
1975 | if ( !this.active.has( ".ui-menu" ).length ) { |
||
1976 | this.collapseAll( event, true ); |
||
1977 | } |
||
1978 | this._trigger( "select", event, ui ); |
||
1979 | }, |
||
1980 | |||
1981 | _filterMenuItems: function(character) { |
||
1982 | var escapedCharacter = character.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" ), |
||
1983 | regex = new RegExp( "^" + escapedCharacter, "i" ); |
||
1984 | |||
1985 | return this.activeMenu |
||
1986 | .find( this.options.items ) |
||
1987 | |||
1988 | // Only match on items, not dividers or other content (#10571) |
||
1989 | .filter( ".ui-menu-item" ) |
||
1990 | .filter(function() { |
||
1991 | return regex.test( $.trim( $( this ).text() ) ); |
||
1992 | }); |
||
1993 | } |
||
1994 | }); |
||
1995 | |||
1996 | |||
1997 | /*! |
||
1998 | * jQuery UI Autocomplete 1.11.4 |
||
1999 | * http://jqueryui.com |
||
2000 | * |
||
2001 | * Copyright jQuery Foundation and other contributors |
||
2002 | * Released under the MIT license. |
||
2003 | * http://jquery.org/license |
||
2004 | * |
||
2005 | * http://api.jqueryui.com/autocomplete/ |
||
2006 | */ |
||
2007 | |||
2008 | |||
2009 | $.widget( "ui.autocomplete", { |
||
2010 | version: "1.11.4", |
||
2011 | defaultElement: "<input>", |
||
2012 | options: { |
||
2013 | appendTo: null, |
||
2014 | autoFocus: false, |
||
2015 | delay: 300, |
||
2016 | minLength: 1, |
||
2017 | position: { |
||
2018 | my: "left top", |
||
2019 | at: "left bottom", |
||
2020 | collision: "none" |
||
2021 | }, |
||
2022 | source: null, |
||
2023 | |||
2024 | // callbacks |
||
2025 | change: null, |
||
2026 | close: null, |
||
2027 | focus: null, |
||
2028 | open: null, |
||
2029 | response: null, |
||
2030 | search: null, |
||
2031 | select: null |
||
2032 | }, |
||
2033 | |||
2034 | requestIndex: 0, |
||
2035 | pending: 0, |
||
2036 | |||
2037 | _create: function() { |
||
2038 | // Some browsers only repeat keydown events, not keypress events, |
||
2039 | // so we use the suppressKeyPress flag to determine if we've already |
||
2040 | // handled the keydown event. #7269 |
||
2041 | // Unfortunately the code for & in keypress is the same as the up arrow, |
||
2042 | // so we use the suppressKeyPressRepeat flag to avoid handling keypress |
||
2043 | // events when we know the keydown event was used to modify the |
||
2044 | // search term. #7799 |
||
2045 | var suppressKeyPress, suppressKeyPressRepeat, suppressInput, |
||
2046 | nodeName = this.element[ 0 ].nodeName.toLowerCase(), |
||
2047 | isTextarea = nodeName === "textarea", |
||
2048 | isInput = nodeName === "input"; |
||
2049 | |||
2050 | this.isMultiLine = |
||
2051 | // Textareas are always multi-line |
||
2052 | isTextarea ? true : |
||
2053 | // Inputs are always single-line, even if inside a contentEditable element |
||
2054 | // IE also treats inputs as contentEditable |
||
2055 | isInput ? false : |
||
2056 | // All other element types are determined by whether or not they're contentEditable |
||
2057 | this.element.prop( "isContentEditable" ); |
||
2058 | |||
2059 | this.valueMethod = this.element[ isTextarea || isInput ? "val" : "text" ]; |
||
2060 | this.isNewMenu = true; |
||
2061 | |||
2062 | this.element |
||
2063 | .addClass( "ui-autocomplete-input" ) |
||
2064 | .attr( "autocomplete", "off" ); |
||
2065 | |||
2066 | this._on( this.element, { |
||
2067 | keydown: function( event ) { |
||
2068 | if ( this.element.prop( "readOnly" ) ) { |
||
2069 | suppressKeyPress = true; |
||
2070 | suppressInput = true; |
||
2071 | suppressKeyPressRepeat = true; |
||
2072 | return; |
||
2073 | } |
||
2074 | |||
2075 | suppressKeyPress = false; |
||
2076 | suppressInput = false; |
||
2077 | suppressKeyPressRepeat = false; |
||
2078 | var keyCode = $.ui.keyCode; |
||
2079 | switch ( event.keyCode ) { |
||
2080 | case keyCode.PAGE_UP: |
||
2081 | suppressKeyPress = true; |
||
2082 | this._move( "previousPage", event ); |
||
2083 | break; |
||
2084 | case keyCode.PAGE_DOWN: |
||
2085 | suppressKeyPress = true; |
||
2086 | this._move( "nextPage", event ); |
||
2087 | break; |
||
2088 | case keyCode.UP: |
||
2089 | suppressKeyPress = true; |
||
2090 | this._keyEvent( "previous", event ); |
||
2091 | break; |
||
2092 | case keyCode.DOWN: |
||
2093 | suppressKeyPress = true; |
||
2094 | this._keyEvent( "next", event ); |
||
2095 | break; |
||
2096 | case keyCode.ENTER: |
||
2097 | // when menu is open and has focus |
||
2098 | if ( this.menu.active ) { |
||
2099 | // #6055 - Opera still allows the keypress to occur |
||
2100 | // which causes forms to submit |
||
2101 | suppressKeyPress = true; |
||
2102 | event.preventDefault(); |
||
2103 | this.menu.select( event ); |
||
2104 | } |
||
2105 | break; |
||
2106 | case keyCode.TAB: |
||
2107 | if ( this.menu.active ) { |
||
2108 | this.menu.select( event ); |
||
2109 | } |
||
2110 | break; |
||
2111 | case keyCode.ESCAPE: |
||
2112 | if ( this.menu.element.is( ":visible" ) ) { |
||
2113 | if ( !this.isMultiLine ) { |
||
2114 | this._value( this.term ); |
||
2115 | } |
||
2116 | this.close( event ); |
||
2117 | // Different browsers have different default behavior for escape |
||
2118 | // Single press can mean undo or clear |
||
2119 | // Double press in IE means clear the whole form |
||
2120 | event.preventDefault(); |
||
2121 | } |
||
2122 | break; |
||
2123 | default: |
||
2124 | suppressKeyPressRepeat = true; |
||
2125 | // search timeout should be triggered before the input value is changed |
||
2126 | this._searchTimeout( event ); |
||
2127 | break; |
||
2128 | } |
||
2129 | }, |
||
2130 | keypress: function( event ) { |
||
2131 | if ( suppressKeyPress ) { |
||
2132 | suppressKeyPress = false; |
||
2133 | if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) { |
||
2134 | event.preventDefault(); |
||
2135 | } |
||
2136 | return; |
||
2137 | } |
||
2138 | if ( suppressKeyPressRepeat ) { |
||
2139 | return; |
||
2140 | } |
||
2141 | |||
2142 | // replicate some key handlers to allow them to repeat in Firefox and Opera |
||
2143 | var keyCode = $.ui.keyCode; |
||
2144 | switch ( event.keyCode ) { |
||
2145 | case keyCode.PAGE_UP: |
||
2146 | this._move( "previousPage", event ); |
||
2147 | break; |
||
2148 | case keyCode.PAGE_DOWN: |
||
2149 | this._move( "nextPage", event ); |
||
2150 | break; |
||
2151 | case keyCode.UP: |
||
2152 | this._keyEvent( "previous", event ); |
||
2153 | break; |
||
2154 | case keyCode.DOWN: |
||
2155 | this._keyEvent( "next", event ); |
||
2156 | break; |
||
2157 | } |
||
2158 | }, |
||
2159 | input: function( event ) { |
||
2160 | if ( suppressInput ) { |
||
2161 | suppressInput = false; |
||
2162 | event.preventDefault(); |
||
2163 | return; |
||
2164 | } |
||
2165 | this._searchTimeout( event ); |
||
2166 | }, |
||
2167 | focus: function() { |
||
2168 | this.selectedItem = null; |
||
2169 | this.previous = this._value(); |
||
2170 | }, |
||
2171 | blur: function( event ) { |
||
2172 | if ( this.cancelBlur ) { |
||
2173 | delete this.cancelBlur; |
||
2174 | return; |
||
2175 | } |
||
2176 | |||
2177 | clearTimeout( this.searching ); |
||
2178 | this.close( event ); |
||
2179 | this._change( event ); |
||
2180 | } |
||
2181 | }); |
||
2182 | |||
2183 | this._initSource(); |
||
2184 | this.menu = $( "<ul>" ) |
||
2185 | .addClass( "ui-autocomplete ui-front" ) |
||
2186 | .appendTo( this._appendTo() ) |
||
2187 | .menu({ |
||
2188 | // disable ARIA support, the live region takes care of that |
||
2189 | role: null |
||
2190 | }) |
||
2191 | .hide() |
||
2192 | .menu( "instance" ); |
||
2193 | |||
2194 | this._on( this.menu.element, { |
||
2195 | mousedown: function( event ) { |
||
2196 | // prevent moving focus out of the text field |
||
2197 | event.preventDefault(); |
||
2198 | |||
2199 | // IE doesn't prevent moving focus even with event.preventDefault() |
||
2200 | // so we set a flag to know when we should ignore the blur event |
||
2201 | this.cancelBlur = true; |
||
2202 | this._delay(function() { |
||
2203 | delete this.cancelBlur; |
||
2204 | }); |
||
2205 | |||
2206 | // clicking on the scrollbar causes focus to shift to the body |
||
2207 | // but we can't detect a mouseup or a click immediately afterward |
||
2208 | // so we have to track the next mousedown and close the menu if |
||
2209 | // the user clicks somewhere outside of the autocomplete |
||
2210 | var menuElement = this.menu.element[ 0 ]; |
||
2211 | if ( !$( event.target ).closest( ".ui-menu-item" ).length ) { |
||
2212 | this._delay(function() { |
||
2213 | var that = this; |
||
2214 | this.document.one( "mousedown", function( event ) { |
||
2215 | if ( event.target !== that.element[ 0 ] && |
||
2216 | event.target !== menuElement && |
||
2217 | !$.contains( menuElement, event.target ) ) { |
||
2218 | that.close(); |
||
2219 | } |
||
2220 | }); |
||
2221 | }); |
||
2222 | } |
||
2223 | }, |
||
2224 | menufocus: function( event, ui ) { |
||
2225 | var label, item; |
||
2226 | // support: Firefox |
||
2227 | // Prevent accidental activation of menu items in Firefox (#7024 #9118) |
||
2228 | if ( this.isNewMenu ) { |
||
2229 | this.isNewMenu = false; |
||
2230 | if ( event.originalEvent && /^mouse/.test( event.originalEvent.type ) ) { |
||
2231 | this.menu.blur(); |
||
2232 | |||
2233 | this.document.one( "mousemove", function() { |
||
2234 | $( event.target ).trigger( event.originalEvent ); |
||
2235 | }); |
||
2236 | |||
2237 | return; |
||
2238 | } |
||
2239 | } |
||
2240 | |||
2241 | item = ui.item.data( "ui-autocomplete-item" ); |
||
2242 | if ( false !== this._trigger( "focus", event, { item: item } ) ) { |
||
2243 | // use value to match what will end up in the input, if it was a key event |
||
2244 | if ( event.originalEvent && /^key/.test( event.originalEvent.type ) ) { |
||
2245 | this._value( item.value ); |
||
2246 | } |
||
2247 | } |
||
2248 | |||
2249 | // Announce the value in the liveRegion |
||
2250 | label = ui.item.attr( "aria-label" ) || item.value; |
||
2251 | if ( label && $.trim( label ).length ) { |
||
2252 | this.liveRegion.children().hide(); |
||
2253 | $( "<div>" ).text( label ).appendTo( this.liveRegion ); |
||
2254 | } |
||
2255 | }, |
||
2256 | menuselect: function( event, ui ) { |
||
2257 | var item = ui.item.data( "ui-autocomplete-item" ), |
||
2258 | previous = this.previous; |
||
2259 | |||
2260 | // only trigger when focus was lost (click on menu) |
||
2261 | if ( this.element[ 0 ] !== this.document[ 0 ].activeElement ) { |
||
2262 | this.element.focus(); |
||
2263 | this.previous = previous; |
||
2264 | // #6109 - IE triggers two focus events and the second |
||
2265 | // is asynchronous, so we need to reset the previous |
||
2266 | // term synchronously and asynchronously :-( |
||
2267 | this._delay(function() { |
||
2268 | this.previous = previous; |
||
2269 | this.selectedItem = item; |
||
2270 | }); |
||
2271 | } |
||
2272 | |||
2273 | if ( false !== this._trigger( "select", event, { item: item } ) ) { |
||
2274 | this._value( item.value ); |
||
2275 | } |
||
2276 | // reset the term after the select event |
||
2277 | // this allows custom select handling to work properly |
||
2278 | this.term = this._value(); |
||
2279 | |||
2280 | this.close( event ); |
||
2281 | this.selectedItem = item; |
||
2282 | } |
||
2283 | }); |
||
2284 | |||
2285 | this.liveRegion = $( "<span>", { |
||
2286 | role: "status", |
||
2287 | "aria-live": "assertive", |
||
2288 | "aria-relevant": "additions" |
||
2289 | }) |
||
2290 | .addClass( "ui-helper-hidden-accessible" ) |
||
2291 | .appendTo( this.document[ 0 ].body ); |
||
2292 | |||
2293 | // turning off autocomplete prevents the browser from remembering the |
||
2294 | // value when navigating through history, so we re-enable autocomplete |
||
2295 | // if the page is unloaded before the widget is destroyed. #7790 |
||
2296 | this._on( this.window, { |
||
2297 | beforeunload: function() { |
||
2298 | this.element.removeAttr( "autocomplete" ); |
||
2299 | } |
||
2300 | }); |
||
2301 | }, |
||
2302 | |||
2303 | _destroy: function() { |
||
2304 | clearTimeout( this.searching ); |
||
2305 | this.element |
||
2306 | .removeClass( "ui-autocomplete-input" ) |
||
2307 | .removeAttr( "autocomplete" ); |
||
2308 | this.menu.element.remove(); |
||
2309 | this.liveRegion.remove(); |
||
2310 | }, |
||
2311 | |||
2312 | _setOption: function( key, value ) { |
||
2313 | this._super( key, value ); |
||
2314 | if ( key === "source" ) { |
||
2315 | this._initSource(); |
||
2316 | } |
||
2317 | if ( key === "appendTo" ) { |
||
2318 | this.menu.element.appendTo( this._appendTo() ); |
||
2319 | } |
||
2320 | if ( key === "disabled" && value && this.xhr ) { |
||
2321 | this.xhr.abort(); |
||
2322 | } |
||
2323 | }, |
||
2324 | |||
2325 | _appendTo: function() { |
||
2326 | var element = this.options.appendTo; |
||
2327 | |||
2328 | if ( element ) { |
||
2329 | element = element.jquery || element.nodeType ? |
||
2330 | $( element ) : |
||
2331 | this.document.find( element ).eq( 0 ); |
||
2332 | } |
||
2333 | |||
2334 | if ( !element || !element[ 0 ] ) { |
||
2335 | element = this.element.closest( ".ui-front" ); |
||
2336 | } |
||
2337 | |||
2338 | if ( !element.length ) { |
||
2339 | element = this.document[ 0 ].body; |
||
2340 | } |
||
2341 | |||
2342 | return element; |
||
2343 | }, |
||
2344 | |||
2345 | _initSource: function() { |
||
2346 | var array, url, |
||
2347 | that = this; |
||
2348 | if ( $.isArray( this.options.source ) ) { |
||
2349 | array = this.options.source; |
||
2350 | this.source = function( request, response ) { |
||
2351 | response( $.ui.autocomplete.filter( array, request.term ) ); |
||
2352 | }; |
||
2353 | } else if ( typeof this.options.source === "string" ) { |
||
2354 | url = this.options.source; |
||
2355 | this.source = function( request, response ) { |
||
2356 | if ( that.xhr ) { |
||
2357 | that.xhr.abort(); |
||
2358 | } |
||
2359 | that.xhr = $.ajax({ |
||
2360 | url: url, |
||
2361 | data: request, |
||
2362 | dataType: "json", |
||
2363 | success: function( data ) { |
||
2364 | response( data ); |
||
2365 | }, |
||
2366 | error: function() { |
||
2367 | response([]); |
||
2368 | } |
||
2369 | }); |
||
2370 | }; |
||
2371 | } else { |
||
2372 | this.source = this.options.source; |
||
2373 | } |
||
2374 | }, |
||
2375 | |||
2376 | _searchTimeout: function( event ) { |
||
2377 | clearTimeout( this.searching ); |
||
2378 | this.searching = this._delay(function() { |
||
2379 | |||
2380 | // Search if the value has changed, or if the user retypes the same value (see #7434) |
||
2381 | var equalValues = this.term === this._value(), |
||
2382 | menuVisible = this.menu.element.is( ":visible" ), |
||
2383 | modifierKey = event.altKey || event.ctrlKey || event.metaKey || event.shiftKey; |
||
2384 | |||
2385 | if ( !equalValues || ( equalValues && !menuVisible && !modifierKey ) ) { |
||
2386 | this.selectedItem = null; |
||
2387 | this.search( null, event ); |
||
2388 | } |
||
2389 | }, this.options.delay ); |
||
2390 | }, |
||
2391 | |||
2392 | search: function( value, event ) { |
||
2393 | value = value != null ? value : this._value(); |
||
2394 | |||
2395 | // always save the actual value, not the one passed as an argument |
||
2396 | this.term = this._value(); |
||
2397 | |||
2398 | if ( value.length < this.options.minLength ) { |
||
2399 | return this.close( event ); |
||
2400 | } |
||
2401 | |||
2402 | if ( this._trigger( "search", event ) === false ) { |
||
2403 | return; |
||
2404 | } |
||
2405 | |||
2406 | return this._search( value ); |
||
2407 | }, |
||
2408 | |||
2409 | _search: function( value ) { |
||
2410 | this.pending++; |
||
2411 | this.element.addClass( "ui-autocomplete-loading" ); |
||
2412 | this.cancelSearch = false; |
||
2413 | |||
2414 | this.source( { term: value }, this._response() ); |
||
2415 | }, |
||
2416 | |||
2417 | _response: function() { |
||
2418 | var index = ++this.requestIndex; |
||
2419 | |||
2420 | return $.proxy(function( content ) { |
||
2421 | if ( index === this.requestIndex ) { |
||
2422 | this.__response( content ); |
||
2423 | } |
||
2424 | |||
2425 | this.pending--; |
||
2426 | if ( !this.pending ) { |
||
2427 | this.element.removeClass( "ui-autocomplete-loading" ); |
||
2428 | } |
||
2429 | }, this ); |
||
2430 | }, |
||
2431 | |||
2432 | __response: function( content ) { |
||
2433 | if ( content ) { |
||
2434 | content = this._normalize( content ); |
||
2435 | } |
||
2436 | this._trigger( "response", null, { content: content } ); |
||
2437 | if ( !this.options.disabled && content && content.length && !this.cancelSearch ) { |
||
2438 | this._suggest( content ); |
||
2439 | this._trigger( "open" ); |
||
2440 | } else { |
||
2441 | // use ._close() instead of .close() so we don't cancel future searches |
||
2442 | this._close(); |
||
2443 | } |
||
2444 | }, |
||
2445 | |||
2446 | close: function( event ) { |
||
2447 | this.cancelSearch = true; |
||
2448 | this._close( event ); |
||
2449 | }, |
||
2450 | |||
2451 | _close: function( event ) { |
||
2452 | if ( this.menu.element.is( ":visible" ) ) { |
||
2453 | this.menu.element.hide(); |
||
2454 | this.menu.blur(); |
||
2455 | this.isNewMenu = true; |
||
2456 | this._trigger( "close", event ); |
||
2457 | } |
||
2458 | }, |
||
2459 | |||
2460 | _change: function( event ) { |
||
2461 | if ( this.previous !== this._value() ) { |
||
2462 | this._trigger( "change", event, { item: this.selectedItem } ); |
||
2463 | } |
||
2464 | }, |
||
2465 | |||
2466 | _normalize: function( items ) { |
||
2467 | // assume all items have the right format when the first item is complete |
||
2468 | if ( items.length && items[ 0 ].label && items[ 0 ].value ) { |
||
2469 | return items; |
||
2470 | } |
||
2471 | return $.map( items, function( item ) { |
||
2472 | if ( typeof item === "string" ) { |
||
2473 | return { |
||
2474 | label: item, |
||
2475 | value: item |
||
2476 | }; |
||
2477 | } |
||
2478 | return $.extend( {}, item, { |
||
2479 | label: item.label || item.value, |
||
2480 | value: item.value || item.label |
||
2481 | }); |
||
2482 | }); |
||
2483 | }, |
||
2484 | |||
2485 | _suggest: function( items ) { |
||
2486 | var ul = this.menu.element.empty(); |
||
2487 | this._renderMenu( ul, items ); |
||
2488 | this.isNewMenu = true; |
||
2489 | this.menu.refresh(); |
||
2490 | |||
2491 | // size and position menu |
||
2492 | ul.show(); |
||
2493 | this._resizeMenu(); |
||
2494 | ul.position( $.extend({ |
||
2495 | of: this.element |
||
2496 | }, this.options.position ) ); |
||
2497 | |||
2498 | if ( this.options.autoFocus ) { |
||
2499 | this.menu.next(); |
||
2500 | } |
||
2501 | }, |
||
2502 | |||
2503 | _resizeMenu: function() { |
||
2504 | var ul = this.menu.element; |
||
2505 | ul.outerWidth( Math.max( |
||
2506 | // Firefox wraps long text (possibly a rounding bug) |
||
2507 | // so we add 1px to avoid the wrapping (#7513) |
||
2508 | ul.width( "" ).outerWidth() + 1, |
||
2509 | this.element.outerWidth() |
||
2510 | ) ); |
||
2511 | }, |
||
2512 | |||
2513 | _renderMenu: function( ul, items ) { |
||
2514 | var that = this; |
||
2515 | $.each( items, function( index, item ) { |
||
2516 | that._renderItemData( ul, item ); |
||
2517 | }); |
||
2518 | }, |
||
2519 | |||
2520 | _renderItemData: function( ul, item ) { |
||
2521 | return this._renderItem( ul, item ).data( "ui-autocomplete-item", item ); |
||
2522 | }, |
||
2523 | |||
2524 | _renderItem: function( ul, item ) { |
||
2525 | return $( "<li>" ).text( item.label ).appendTo( ul ); |
||
2526 | }, |
||
2527 | |||
2528 | _move: function( direction, event ) { |
||
2529 | if ( !this.menu.element.is( ":visible" ) ) { |
||
2530 | this.search( null, event ); |
||
2531 | return; |
||
2532 | } |
||
2533 | if ( this.menu.isFirstItem() && /^previous/.test( direction ) || |
||
2534 | this.menu.isLastItem() && /^next/.test( direction ) ) { |
||
2535 | |||
2536 | if ( !this.isMultiLine ) { |
||
2537 | this._value( this.term ); |
||
2538 | } |
||
2539 | |||
2540 | this.menu.blur(); |
||
2541 | return; |
||
2542 | } |
||
2543 | this.menu[ direction ]( event ); |
||
2544 | }, |
||
2545 | |||
2546 | widget: function() { |
||
2547 | return this.menu.element; |
||
2548 | }, |
||
2549 | |||
2550 | _value: function() { |
||
2551 | return this.valueMethod.apply( this.element, arguments ); |
||
2552 | }, |
||
2553 | |||
2554 | _keyEvent: function( keyEvent, event ) { |
||
2555 | if ( !this.isMultiLine || this.menu.element.is( ":visible" ) ) { |
||
2556 | this._move( keyEvent, event ); |
||
2557 | |||
2558 | // prevents moving cursor to beginning/end of the text field in some browsers |
||
2559 | event.preventDefault(); |
||
2560 | } |
||
2561 | } |
||
2562 | }); |
||
2563 | |||
2564 | $.extend( $.ui.autocomplete, { |
||
2565 | escapeRegex: function( value ) { |
||
2566 | return value.replace( /[\-\[\]{}()*+?.,\\\^$|#\s]/g, "\\$&" ); |
||
2567 | }, |
||
2568 | filter: function( array, term ) { |
||
2569 | var matcher = new RegExp( $.ui.autocomplete.escapeRegex( term ), "i" ); |
||
2570 | return $.grep( array, function( value ) { |
||
2571 | return matcher.test( value.label || value.value || value ); |
||
2572 | }); |
||
2573 | } |
||
2574 | }); |
||
2575 | |||
2576 | // live region extension, adding a `messages` option |
||
2577 | // NOTE: This is an experimental API. We are still investigating |
||
2578 | // a full solution for string manipulation and internationalization. |
||
2579 | $.widget( "ui.autocomplete", $.ui.autocomplete, { |
||
2580 | options: { |
||
2581 | messages: { |
||
2582 | noResults: "No search results.", |
||
2583 | results: function( amount ) { |
||
2584 | return amount + ( amount > 1 ? " results are" : " result is" ) + |
||
2585 | " available, use up and down arrow keys to navigate."; |
||
2586 | } |
||
2587 | } |
||
2588 | }, |
||
2589 | |||
2590 | __response: function( content ) { |
||
2591 | var message; |
||
2592 | this._superApply( arguments ); |
||
2593 | if ( this.options.disabled || this.cancelSearch ) { |
||
2594 | return; |
||
2595 | } |
||
2596 | if ( content && content.length ) { |
||
2597 | message = this.options.messages.results( content.length ); |
||
2598 | } else { |
||
2599 | message = this.options.messages.noResults; |
||
2600 | } |
||
2601 | this.liveRegion.children().hide(); |
||
2602 | $( "<div>" ).text( message ).appendTo( this.liveRegion ); |
||
2603 | } |
||
2604 | }); |
||
2605 | |||
2606 | var autocomplete = $.ui.autocomplete; |
||
2607 | |||
2608 | |||
2609 | |||
2610 | })); |
This check looks for functions where a
return
statement is found in some execution paths, but not in all.Consider this little piece of code
The function
isBig
will only return a specific value when its parameter is bigger than 5000. In any other case, it will implicitly returnundefined
.This behaviour may not be what you had intended. In any case, you can add a
return undefined
to the other execution path to make the return value explicit.