jquery-rails 4.2.2 → 4.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of jquery-rails might be problematic. Click here for more details.

checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 7996d2fc15acd7a01d2f6647ade819334d057331
4
- data.tar.gz: 418862a8521eb9e60228fc51a6b097884a0d100c
3
+ metadata.gz: 18e87e67370461ba4631fce650f1df3d964444e5
4
+ data.tar.gz: 90e06a9d9e5aa5215394e697e989480b90bb6b11
5
5
  SHA512:
6
- metadata.gz: 90076a29f609f4ed19417362c4634dff8bb76887dfc468cd2c60722d7a1dd82d54245b6e370b02216a1e1caf0f12f8dba4331f8bb2f0ef7102475a1dfefd3be8
7
- data.tar.gz: b60271df7f41e49c343f6159f664fb752645efd5c62b395172ca91f64d19334465adc8b7afba10e4d323f4bfcc50af34e4b598699cb645bf3af3adf8b9e56f34
6
+ metadata.gz: 49e157e947517316995db3458cd217f35cfae67e40538de6bb7144df6684a33eecbad23258ab830af61974aa2d9ad219afa27a57def6a71826ed80f79458cf98
7
+ data.tar.gz: b260b2d9136847c48aa95a684649d354644052742540d3505982fcf8ba6f6eb5fb356cf557dec7d955ae560811fdaaa42b847f020156b18adb3e128fdc5a5c44
@@ -1,3 +1,8 @@
1
+ ## 4.3.0
2
+
3
+ - update jquery to 3.2.0
4
+ - Add possibility to test HTML attribute selectors
5
+
1
6
  ## 4.2.2
2
7
 
3
8
  - update jquery to 3.1.1
data/Gemfile CHANGED
@@ -12,5 +12,11 @@ else
12
12
  gem 'json', '~> 1.8.0'
13
13
  end
14
14
 
15
+ if RUBY_VERSION >= '2.1'
16
+ gem 'nokogiri'
17
+ else
18
+ gem 'nokogiri', '~> 1.6.0'
19
+ end
20
+
15
21
  # Specify your gem's dependencies in jquery-rails.gemspec
16
22
  gemspec
@@ -2,6 +2,7 @@
2
2
 
3
3
  | Gem | jQuery | jQuery UJS | jQuery UI |
4
4
  |--------|--------|------------| ----------|
5
+ | 4.3.0 | 1.12.4 & 2.2.4 & 3.2.0 | 1.2.2 | - |
5
6
  | 4.2.2 | 1.12.4 & 2.2.4 & 3.1.1 | 1.2.2 | - |
6
7
  | 4.2.1 | 1.12.4 & 2.2.4 & 3.1.0 | 1.2.2 | - |
7
8
  | 4.2.0 | 1.12.4 & 2.2.4 & 3.0.0 | 1.2.2 | - |
@@ -54,7 +54,7 @@ module Rails::Dom::Testing::Assertions::SelectorAssertions
54
54
  def assert_select_jquery(*args, &block)
55
55
  jquery_method = args.first.is_a?(Symbol) ? args.shift : nil
56
56
  jquery_opt = args.first.is_a?(Symbol) ? args.shift : nil
57
- id = args.first.is_a?(String) ? args.shift : nil
57
+ id = args.first.is_a?(String) ? escape_id(args.shift) : nil
58
58
 
59
59
  target_pattern = "['\"]#{id || '.*'}['\"]"
60
60
  method_pattern = "#{jquery_method || '\\w+'}"
@@ -128,4 +128,13 @@ module Rails::Dom::Testing::Assertions::SelectorAssertions
128
128
  unescaped.gsub!(PATTERN_UNICODE_ESCAPED_CHAR) {|u| [$1.hex].pack('U*')}
129
129
  unescaped
130
130
  end
131
+
132
+ def escape_id(selector)
133
+ return unless selector
134
+
135
+ id = selector.gsub('[', '\[')
136
+ id.gsub!(']', '\]')
137
+
138
+ id
139
+ end
131
140
  end
@@ -1,9 +1,9 @@
1
1
  module Jquery
2
2
  module Rails
3
- VERSION = "4.2.2"
3
+ VERSION = "4.3.0"
4
4
  JQUERY_VERSION = "1.12.4"
5
5
  JQUERY_2_VERSION = "2.2.4"
6
- JQUERY_3_VERSION = "3.1.1"
6
+ JQUERY_3_VERSION = "3.2.0"
7
7
  JQUERY_UJS_VERSION = "1.2.2"
8
8
  end
9
9
  end
@@ -13,6 +13,7 @@ class AssertSelectJQueryTest < ActiveSupport::TestCase
13
13
  jQuery("<div><p>something</p></div>").prependTo("#id");
14
14
  $('#id').remove();
15
15
  jQuery("#id").hide();
16
+ $("[data-placeholder~=name]").remove();
16
17
  JS
17
18
 
18
19
  setup do
@@ -28,6 +29,7 @@ class AssertSelectJQueryTest < ActiveSupport::TestCase
28
29
  assert_select_jquery :replaceWith, '#id' do
29
30
  assert_select 'p', 'something'
30
31
  end
32
+ assert_select_jquery :remove, "[data-placeholder~=name]"
31
33
  end
32
34
 
33
35
  assert_raise Minitest::Assertion, "No JQuery call matches [:show, :some_wrong]" do
@@ -1,15 +1,15 @@
1
1
  /*!
2
- * jQuery JavaScript Library v3.1.1
2
+ * jQuery JavaScript Library v3.2.0
3
3
  * https://jquery.com/
4
4
  *
5
5
  * Includes Sizzle.js
6
6
  * https://sizzlejs.com/
7
7
  *
8
- * Copyright jQuery Foundation and other contributors
8
+ * Copyright JS Foundation and other contributors
9
9
  * Released under the MIT license
10
10
  * https://jquery.org/license
11
11
  *
12
- * Date: 2016-09-22T22:30Z
12
+ * Date: 2017-03-16T21:26Z
13
13
  */
14
14
  ( function( global, factory ) {
15
15
 
@@ -88,7 +88,7 @@ var support = {};
88
88
 
89
89
 
90
90
  var
91
- version = "3.1.1",
91
+ version = "3.2.0",
92
92
 
93
93
  // Define a local copy of jQuery
94
94
  jQuery = function( selector, context ) {
@@ -236,11 +236,11 @@ jQuery.extend = jQuery.fn.extend = function() {
236
236
 
237
237
  // Recurse if we're merging plain objects or arrays
238
238
  if ( deep && copy && ( jQuery.isPlainObject( copy ) ||
239
- ( copyIsArray = jQuery.isArray( copy ) ) ) ) {
239
+ ( copyIsArray = Array.isArray( copy ) ) ) ) {
240
240
 
241
241
  if ( copyIsArray ) {
242
242
  copyIsArray = false;
243
- clone = src && jQuery.isArray( src ) ? src : [];
243
+ clone = src && Array.isArray( src ) ? src : [];
244
244
 
245
245
  } else {
246
246
  clone = src && jQuery.isPlainObject( src ) ? src : {};
@@ -279,8 +279,6 @@ jQuery.extend( {
279
279
  return jQuery.type( obj ) === "function";
280
280
  },
281
281
 
282
- isArray: Array.isArray,
283
-
284
282
  isWindow: function( obj ) {
285
283
  return obj != null && obj === obj.window;
286
284
  },
@@ -355,10 +353,6 @@ jQuery.extend( {
355
353
  return string.replace( rmsPrefix, "ms-" ).replace( rdashAlpha, fcamelCase );
356
354
  },
357
355
 
358
- nodeName: function( elem, name ) {
359
- return elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase();
360
- },
361
-
362
356
  each: function( obj, callback ) {
363
357
  var length, i = 0;
364
358
 
@@ -2843,6 +2837,13 @@ var siblings = function( n, elem ) {
2843
2837
 
2844
2838
  var rneedsContext = jQuery.expr.match.needsContext;
2845
2839
 
2840
+
2841
+
2842
+ function nodeName( elem, name ) {
2843
+
2844
+ return elem.nodeName && elem.nodeName.toLowerCase() === name.toLowerCase();
2845
+
2846
+ };
2846
2847
  var rsingleTag = ( /^<([a-z][^\/\0>:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i );
2847
2848
 
2848
2849
 
@@ -3194,7 +3195,18 @@ jQuery.each( {
3194
3195
  return siblings( elem.firstChild );
3195
3196
  },
3196
3197
  contents: function( elem ) {
3197
- return elem.contentDocument || jQuery.merge( [], elem.childNodes );
3198
+ if ( nodeName( elem, "iframe" ) ) {
3199
+ return elem.contentDocument;
3200
+ }
3201
+
3202
+ // Support: IE 9 - 11 only, iOS 7 only, Android Browser <=4.3 only
3203
+ // Treat the template element as a regular one in browsers that
3204
+ // don't support it.
3205
+ if ( nodeName( elem, "template" ) ) {
3206
+ elem = elem.content || elem;
3207
+ }
3208
+
3209
+ return jQuery.merge( [], elem.childNodes );
3198
3210
  }
3199
3211
  }, function( name, fn ) {
3200
3212
  jQuery.fn[ name ] = function( until, selector ) {
@@ -3292,7 +3304,7 @@ jQuery.Callbacks = function( options ) {
3292
3304
  fire = function() {
3293
3305
 
3294
3306
  // Enforce single-firing
3295
- locked = options.once;
3307
+ locked = locked || options.once;
3296
3308
 
3297
3309
  // Execute callbacks for all pending executions,
3298
3310
  // respecting firingIndex overrides and runtime changes
@@ -3461,7 +3473,7 @@ function Thrower( ex ) {
3461
3473
  throw ex;
3462
3474
  }
3463
3475
 
3464
- function adoptValue( value, resolve, reject ) {
3476
+ function adoptValue( value, resolve, reject, noValue ) {
3465
3477
  var method;
3466
3478
 
3467
3479
  try {
@@ -3477,9 +3489,10 @@ function adoptValue( value, resolve, reject ) {
3477
3489
  // Other non-thenables
3478
3490
  } else {
3479
3491
 
3480
- // Support: Android 4.0 only
3481
- // Strict mode functions invoked without .call/.apply get global-object context
3482
- resolve.call( undefined, value );
3492
+ // Control `resolve` arguments by letting Array#slice cast boolean `noValue` to integer:
3493
+ // * false: [ value ].slice( 0 ) => resolve( value )
3494
+ // * true: [ value ].slice( 1 ) => resolve()
3495
+ resolve.apply( undefined, [ value ].slice( noValue ) );
3483
3496
  }
3484
3497
 
3485
3498
  // For Promises/A+, convert exceptions into rejections
@@ -3489,7 +3502,7 @@ function adoptValue( value, resolve, reject ) {
3489
3502
 
3490
3503
  // Support: Android 4.0 only
3491
3504
  // Strict mode functions invoked without .call/.apply get global-object context
3492
- reject.call( undefined, value );
3505
+ reject.apply( undefined, [ value ] );
3493
3506
  }
3494
3507
  }
3495
3508
 
@@ -3814,7 +3827,8 @@ jQuery.extend( {
3814
3827
 
3815
3828
  // Single- and empty arguments are adopted like Promise.resolve
3816
3829
  if ( remaining <= 1 ) {
3817
- adoptValue( singleValue, master.done( updateFunc( i ) ).resolve, master.reject );
3830
+ adoptValue( singleValue, master.done( updateFunc( i ) ).resolve, master.reject,
3831
+ !remaining );
3818
3832
 
3819
3833
  // Use .then() to unwrap secondary thenables (cf. gh-3000)
3820
3834
  if ( master.state() === "pending" ||
@@ -3886,15 +3900,6 @@ jQuery.extend( {
3886
3900
  // the ready event fires. See #6781
3887
3901
  readyWait: 1,
3888
3902
 
3889
- // Hold (or release) the ready event
3890
- holdReady: function( hold ) {
3891
- if ( hold ) {
3892
- jQuery.readyWait++;
3893
- } else {
3894
- jQuery.ready( true );
3895
- }
3896
- },
3897
-
3898
3903
  // Handle when the DOM is ready
3899
3904
  ready: function( wait ) {
3900
3905
 
@@ -4130,7 +4135,7 @@ Data.prototype = {
4130
4135
  if ( key !== undefined ) {
4131
4136
 
4132
4137
  // Support array or space separated string of keys
4133
- if ( jQuery.isArray( key ) ) {
4138
+ if ( Array.isArray( key ) ) {
4134
4139
 
4135
4140
  // If key is an array of keys...
4136
4141
  // We always set camelCase keys, so remove that.
@@ -4356,7 +4361,7 @@ jQuery.extend( {
4356
4361
 
4357
4362
  // Speed up dequeue by getting out quickly if this is just a lookup
4358
4363
  if ( data ) {
4359
- if ( !queue || jQuery.isArray( data ) ) {
4364
+ if ( !queue || Array.isArray( data ) ) {
4360
4365
  queue = dataPriv.access( elem, type, jQuery.makeArray( data ) );
4361
4366
  } else {
4362
4367
  queue.push( data );
@@ -4733,7 +4738,7 @@ function getAll( context, tag ) {
4733
4738
  ret = [];
4734
4739
  }
4735
4740
 
4736
- if ( tag === undefined || tag && jQuery.nodeName( context, tag ) ) {
4741
+ if ( tag === undefined || tag && nodeName( context, tag ) ) {
4737
4742
  return jQuery.merge( [ context ], ret );
4738
4743
  }
4739
4744
 
@@ -5338,9 +5343,11 @@ jQuery.event = {
5338
5343
  },
5339
5344
  click: {
5340
5345
 
5341
- // For checkbox, fire native event so checked state will be right
5346
+ // For checkable types, fire native event so checked state will be right
5342
5347
  trigger: function() {
5343
- if ( this.type === "checkbox" && this.click && jQuery.nodeName( this, "input" ) ) {
5348
+ if ( rcheckableType.test( this.type ) &&
5349
+ this.click && nodeName( this, "input" ) ) {
5350
+
5344
5351
  this.click();
5345
5352
  return false;
5346
5353
  }
@@ -5348,7 +5355,7 @@ jQuery.event = {
5348
5355
 
5349
5356
  // For cross-browser consistency, don't fire native .click() on links
5350
5357
  _default: function( event ) {
5351
- return jQuery.nodeName( event.target, "a" );
5358
+ return nodeName( event.target, "a" );
5352
5359
  }
5353
5360
  },
5354
5361
 
@@ -5625,11 +5632,12 @@ var
5625
5632
  rscriptTypeMasked = /^true\/(.*)/,
5626
5633
  rcleanScript = /^\s*<!(?:\[CDATA\[|--)|(?:\]\]|--)>\s*$/g;
5627
5634
 
5635
+ // Prefer a tbody over its parent table for containing new rows
5628
5636
  function manipulationTarget( elem, content ) {
5629
- if ( jQuery.nodeName( elem, "table" ) &&
5630
- jQuery.nodeName( content.nodeType !== 11 ? content : content.firstChild, "tr" ) ) {
5637
+ if ( nodeName( elem, "table" ) &&
5638
+ nodeName( content.nodeType !== 11 ? content : content.firstChild, "tr" ) ) {
5631
5639
 
5632
- return elem.getElementsByTagName( "tbody" )[ 0 ] || elem;
5640
+ return jQuery( ">tbody", elem )[ 0 ] || elem;
5633
5641
  }
5634
5642
 
5635
5643
  return elem;
@@ -6163,8 +6171,9 @@ function curCSS( elem, name, computed ) {
6163
6171
 
6164
6172
  computed = computed || getStyles( elem );
6165
6173
 
6166
- // Support: IE <=9 only
6167
- // getPropertyValue is only needed for .css('filter') (#12537)
6174
+ // getPropertyValue is needed for:
6175
+ // .css('filter') (IE 9 only, #12537)
6176
+ // .css('--customProperty) (#3144)
6168
6177
  if ( computed ) {
6169
6178
  ret = computed.getPropertyValue( name ) || computed[ name ];
6170
6179
 
@@ -6230,6 +6239,7 @@ var
6230
6239
  // except "table", "table-cell", or "table-caption"
6231
6240
  // See here for display values: https://developer.mozilla.org/en-US/docs/CSS/display
6232
6241
  rdisplayswap = /^(none|table(?!-c[ea]).+)/,
6242
+ rcustomProp = /^--/,
6233
6243
  cssShow = { position: "absolute", visibility: "hidden", display: "block" },
6234
6244
  cssNormalTransform = {
6235
6245
  letterSpacing: "0",
@@ -6259,6 +6269,16 @@ function vendorPropName( name ) {
6259
6269
  }
6260
6270
  }
6261
6271
 
6272
+ // Return a property mapped along what jQuery.cssProps suggests or to
6273
+ // a vendor prefixed property.
6274
+ function finalPropName( name ) {
6275
+ var ret = jQuery.cssProps[ name ];
6276
+ if ( !ret ) {
6277
+ ret = jQuery.cssProps[ name ] = vendorPropName( name ) || name;
6278
+ }
6279
+ return ret;
6280
+ }
6281
+
6262
6282
  function setPositiveNumber( elem, value, subtract ) {
6263
6283
 
6264
6284
  // Any relative (+/-) values have already been
@@ -6319,43 +6339,24 @@ function augmentWidthOrHeight( elem, name, extra, isBorderBox, styles ) {
6319
6339
 
6320
6340
  function getWidthOrHeight( elem, name, extra ) {
6321
6341
 
6322
- // Start with offset property, which is equivalent to the border-box value
6323
- var val,
6324
- valueIsBorderBox = true,
6342
+ // Start with computed style
6343
+ var valueIsBorderBox,
6325
6344
  styles = getStyles( elem ),
6345
+ val = curCSS( elem, name, styles ),
6326
6346
  isBorderBox = jQuery.css( elem, "boxSizing", false, styles ) === "border-box";
6327
6347
 
6328
- // Support: IE <=11 only
6329
- // Running getBoundingClientRect on a disconnected node
6330
- // in IE throws an error.
6331
- if ( elem.getClientRects().length ) {
6332
- val = elem.getBoundingClientRect()[ name ];
6348
+ // Computed unit is not pixels. Stop here and return.
6349
+ if ( rnumnonpx.test( val ) ) {
6350
+ return val;
6333
6351
  }
6334
6352
 
6335
- // Some non-html elements return undefined for offsetWidth, so check for null/undefined
6336
- // svg - https://bugzilla.mozilla.org/show_bug.cgi?id=649285
6337
- // MathML - https://bugzilla.mozilla.org/show_bug.cgi?id=491668
6338
- if ( val <= 0 || val == null ) {
6339
-
6340
- // Fall back to computed then uncomputed css if necessary
6341
- val = curCSS( elem, name, styles );
6342
- if ( val < 0 || val == null ) {
6343
- val = elem.style[ name ];
6344
- }
6345
-
6346
- // Computed unit is not pixels. Stop here and return.
6347
- if ( rnumnonpx.test( val ) ) {
6348
- return val;
6349
- }
6350
-
6351
- // Check for style in case a browser which returns unreliable values
6352
- // for getComputedStyle silently falls back to the reliable elem.style
6353
- valueIsBorderBox = isBorderBox &&
6354
- ( support.boxSizingReliable() || val === elem.style[ name ] );
6353
+ // Check for style in case a browser which returns unreliable values
6354
+ // for getComputedStyle silently falls back to the reliable elem.style
6355
+ valueIsBorderBox = isBorderBox &&
6356
+ ( support.boxSizingReliable() || val === elem.style[ name ] );
6355
6357
 
6356
- // Normalize "", auto, and prepare for extra
6357
- val = parseFloat( val ) || 0;
6358
- }
6358
+ // Normalize "", auto, and prepare for extra
6359
+ val = parseFloat( val ) || 0;
6359
6360
 
6360
6361
  // Use the active box-sizing model to add/subtract irrelevant styles
6361
6362
  return ( val +
@@ -6420,10 +6421,15 @@ jQuery.extend( {
6420
6421
  // Make sure that we're working with the right name
6421
6422
  var ret, type, hooks,
6422
6423
  origName = jQuery.camelCase( name ),
6424
+ isCustomProp = rcustomProp.test( name ),
6423
6425
  style = elem.style;
6424
6426
 
6425
- name = jQuery.cssProps[ origName ] ||
6426
- ( jQuery.cssProps[ origName ] = vendorPropName( origName ) || origName );
6427
+ // Make sure that we're working with the right name. We don't
6428
+ // want to query the value if it is a CSS custom property
6429
+ // since they are user-defined.
6430
+ if ( !isCustomProp ) {
6431
+ name = finalPropName( origName );
6432
+ }
6427
6433
 
6428
6434
  // Gets hook for the prefixed version, then unprefixed version
6429
6435
  hooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];
@@ -6459,7 +6465,11 @@ jQuery.extend( {
6459
6465
  if ( !hooks || !( "set" in hooks ) ||
6460
6466
  ( value = hooks.set( elem, value, extra ) ) !== undefined ) {
6461
6467
 
6462
- style[ name ] = value;
6468
+ if ( isCustomProp ) {
6469
+ style.setProperty( name, value );
6470
+ } else {
6471
+ style[ name ] = value;
6472
+ }
6463
6473
  }
6464
6474
 
6465
6475
  } else {
@@ -6478,11 +6488,15 @@ jQuery.extend( {
6478
6488
 
6479
6489
  css: function( elem, name, extra, styles ) {
6480
6490
  var val, num, hooks,
6481
- origName = jQuery.camelCase( name );
6491
+ origName = jQuery.camelCase( name ),
6492
+ isCustomProp = rcustomProp.test( name );
6482
6493
 
6483
- // Make sure that we're working with the right name
6484
- name = jQuery.cssProps[ origName ] ||
6485
- ( jQuery.cssProps[ origName ] = vendorPropName( origName ) || origName );
6494
+ // Make sure that we're working with the right name. We don't
6495
+ // want to modify the value if it is a CSS custom property
6496
+ // since they are user-defined.
6497
+ if ( !isCustomProp ) {
6498
+ name = finalPropName( origName );
6499
+ }
6486
6500
 
6487
6501
  // Try prefixed name followed by the unprefixed name
6488
6502
  hooks = jQuery.cssHooks[ name ] || jQuery.cssHooks[ origName ];
@@ -6507,6 +6521,7 @@ jQuery.extend( {
6507
6521
  num = parseFloat( val );
6508
6522
  return extra === true || isFinite( num ) ? num || 0 : val;
6509
6523
  }
6524
+
6510
6525
  return val;
6511
6526
  }
6512
6527
  } );
@@ -6606,7 +6621,7 @@ jQuery.fn.extend( {
6606
6621
  map = {},
6607
6622
  i = 0;
6608
6623
 
6609
- if ( jQuery.isArray( name ) ) {
6624
+ if ( Array.isArray( name ) ) {
6610
6625
  styles = getStyles( elem );
6611
6626
  len = name.length;
6612
6627
 
@@ -6744,13 +6759,18 @@ jQuery.fx.step = {};
6744
6759
 
6745
6760
 
6746
6761
  var
6747
- fxNow, timerId,
6762
+ fxNow, inProgress,
6748
6763
  rfxtypes = /^(?:toggle|show|hide)$/,
6749
6764
  rrun = /queueHooks$/;
6750
6765
 
6751
- function raf() {
6752
- if ( timerId ) {
6753
- window.requestAnimationFrame( raf );
6766
+ function schedule() {
6767
+ if ( inProgress ) {
6768
+ if ( document.hidden === false && window.requestAnimationFrame ) {
6769
+ window.requestAnimationFrame( schedule );
6770
+ } else {
6771
+ window.setTimeout( schedule, jQuery.fx.interval );
6772
+ }
6773
+
6754
6774
  jQuery.fx.tick();
6755
6775
  }
6756
6776
  }
@@ -6977,7 +6997,7 @@ function propFilter( props, specialEasing ) {
6977
6997
  name = jQuery.camelCase( index );
6978
6998
  easing = specialEasing[ name ];
6979
6999
  value = props[ index ];
6980
- if ( jQuery.isArray( value ) ) {
7000
+ if ( Array.isArray( value ) ) {
6981
7001
  easing = value[ 1 ];
6982
7002
  value = props[ index ] = value[ 0 ];
6983
7003
  }
@@ -7036,12 +7056,19 @@ function Animation( elem, properties, options ) {
7036
7056
 
7037
7057
  deferred.notifyWith( elem, [ animation, percent, remaining ] );
7038
7058
 
7059
+ // If there's more to do, yield
7039
7060
  if ( percent < 1 && length ) {
7040
7061
  return remaining;
7041
- } else {
7042
- deferred.resolveWith( elem, [ animation ] );
7043
- return false;
7044
7062
  }
7063
+
7064
+ // If this was an empty animation, synthesize a final progress notification
7065
+ if ( !length ) {
7066
+ deferred.notifyWith( elem, [ animation, 1, 0 ] );
7067
+ }
7068
+
7069
+ // Resolve the animation and report its conclusion
7070
+ deferred.resolveWith( elem, [ animation ] );
7071
+ return false;
7045
7072
  },
7046
7073
  animation = deferred.promise( {
7047
7074
  elem: elem,
@@ -7106,6 +7133,13 @@ function Animation( elem, properties, options ) {
7106
7133
  animation.opts.start.call( elem, animation );
7107
7134
  }
7108
7135
 
7136
+ // Attach callbacks from options
7137
+ animation
7138
+ .progress( animation.opts.progress )
7139
+ .done( animation.opts.done, animation.opts.complete )
7140
+ .fail( animation.opts.fail )
7141
+ .always( animation.opts.always );
7142
+
7109
7143
  jQuery.fx.timer(
7110
7144
  jQuery.extend( tick, {
7111
7145
  elem: elem,
@@ -7114,11 +7148,7 @@ function Animation( elem, properties, options ) {
7114
7148
  } )
7115
7149
  );
7116
7150
 
7117
- // attach callbacks from options
7118
- return animation.progress( animation.opts.progress )
7119
- .done( animation.opts.done, animation.opts.complete )
7120
- .fail( animation.opts.fail )
7121
- .always( animation.opts.always );
7151
+ return animation;
7122
7152
  }
7123
7153
 
7124
7154
  jQuery.Animation = jQuery.extend( Animation, {
@@ -7169,8 +7199,8 @@ jQuery.speed = function( speed, easing, fn ) {
7169
7199
  easing: fn && easing || easing && !jQuery.isFunction( easing ) && easing
7170
7200
  };
7171
7201
 
7172
- // Go to the end state if fx are off or if document is hidden
7173
- if ( jQuery.fx.off || document.hidden ) {
7202
+ // Go to the end state if fx are off
7203
+ if ( jQuery.fx.off ) {
7174
7204
  opt.duration = 0;
7175
7205
 
7176
7206
  } else {
@@ -7362,7 +7392,7 @@ jQuery.fx.tick = function() {
7362
7392
  for ( ; i < timers.length; i++ ) {
7363
7393
  timer = timers[ i ];
7364
7394
 
7365
- // Checks the timer has not already been removed
7395
+ // Run the timer and safely remove it when done (allowing for external removal)
7366
7396
  if ( !timer() && timers[ i ] === timer ) {
7367
7397
  timers.splice( i--, 1 );
7368
7398
  }
@@ -7376,30 +7406,21 @@ jQuery.fx.tick = function() {
7376
7406
 
7377
7407
  jQuery.fx.timer = function( timer ) {
7378
7408
  jQuery.timers.push( timer );
7379
- if ( timer() ) {
7380
- jQuery.fx.start();
7381
- } else {
7382
- jQuery.timers.pop();
7383
- }
7409
+ jQuery.fx.start();
7384
7410
  };
7385
7411
 
7386
7412
  jQuery.fx.interval = 13;
7387
7413
  jQuery.fx.start = function() {
7388
- if ( !timerId ) {
7389
- timerId = window.requestAnimationFrame ?
7390
- window.requestAnimationFrame( raf ) :
7391
- window.setInterval( jQuery.fx.tick, jQuery.fx.interval );
7414
+ if ( inProgress ) {
7415
+ return;
7392
7416
  }
7417
+
7418
+ inProgress = true;
7419
+ schedule();
7393
7420
  };
7394
7421
 
7395
7422
  jQuery.fx.stop = function() {
7396
- if ( window.cancelAnimationFrame ) {
7397
- window.cancelAnimationFrame( timerId );
7398
- } else {
7399
- window.clearInterval( timerId );
7400
- }
7401
-
7402
- timerId = null;
7423
+ inProgress = null;
7403
7424
  };
7404
7425
 
7405
7426
  jQuery.fx.speeds = {
@@ -7516,7 +7537,7 @@ jQuery.extend( {
7516
7537
  type: {
7517
7538
  set: function( elem, value ) {
7518
7539
  if ( !support.radioValue && value === "radio" &&
7519
- jQuery.nodeName( elem, "input" ) ) {
7540
+ nodeName( elem, "input" ) ) {
7520
7541
  var val = elem.value;
7521
7542
  elem.setAttribute( "type", value );
7522
7543
  if ( val ) {
@@ -7947,7 +7968,7 @@ jQuery.fn.extend( {
7947
7968
  } else if ( typeof val === "number" ) {
7948
7969
  val += "";
7949
7970
 
7950
- } else if ( jQuery.isArray( val ) ) {
7971
+ } else if ( Array.isArray( val ) ) {
7951
7972
  val = jQuery.map( val, function( value ) {
7952
7973
  return value == null ? "" : value + "";
7953
7974
  } );
@@ -8006,7 +8027,7 @@ jQuery.extend( {
8006
8027
  // Don't return options that are disabled or in a disabled optgroup
8007
8028
  !option.disabled &&
8008
8029
  ( !option.parentNode.disabled ||
8009
- !jQuery.nodeName( option.parentNode, "optgroup" ) ) ) {
8030
+ !nodeName( option.parentNode, "optgroup" ) ) ) {
8010
8031
 
8011
8032
  // Get the specific value for the option
8012
8033
  value = jQuery( option ).val();
@@ -8058,7 +8079,7 @@ jQuery.extend( {
8058
8079
  jQuery.each( [ "radio", "checkbox" ], function() {
8059
8080
  jQuery.valHooks[ this ] = {
8060
8081
  set: function( elem, value ) {
8061
- if ( jQuery.isArray( value ) ) {
8082
+ if ( Array.isArray( value ) ) {
8062
8083
  return ( elem.checked = jQuery.inArray( jQuery( elem ).val(), value ) > -1 );
8063
8084
  }
8064
8085
  }
@@ -8353,7 +8374,7 @@ var
8353
8374
  function buildParams( prefix, obj, traditional, add ) {
8354
8375
  var name;
8355
8376
 
8356
- if ( jQuery.isArray( obj ) ) {
8377
+ if ( Array.isArray( obj ) ) {
8357
8378
 
8358
8379
  // Serialize array item.
8359
8380
  jQuery.each( obj, function( i, v ) {
@@ -8405,7 +8426,7 @@ jQuery.param = function( a, traditional ) {
8405
8426
  };
8406
8427
 
8407
8428
  // If an array was passed in, assume that it is an array of form elements.
8408
- if ( jQuery.isArray( a ) || ( a.jquery && !jQuery.isPlainObject( a ) ) ) {
8429
+ if ( Array.isArray( a ) || ( a.jquery && !jQuery.isPlainObject( a ) ) ) {
8409
8430
 
8410
8431
  // Serialize the form elements
8411
8432
  jQuery.each( a, function() {
@@ -8451,7 +8472,7 @@ jQuery.fn.extend( {
8451
8472
  return null;
8452
8473
  }
8453
8474
 
8454
- if ( jQuery.isArray( val ) ) {
8475
+ if ( Array.isArray( val ) ) {
8455
8476
  return jQuery.map( val, function( val ) {
8456
8477
  return { name: elem.name, value: val.replace( rCRLF, "\r\n" ) };
8457
8478
  } );
@@ -9876,13 +9897,6 @@ jQuery.expr.pseudos.animated = function( elem ) {
9876
9897
 
9877
9898
 
9878
9899
 
9879
- /**
9880
- * Gets a window from an element
9881
- */
9882
- function getWindow( elem ) {
9883
- return jQuery.isWindow( elem ) ? elem : elem.nodeType === 9 && elem.defaultView;
9884
- }
9885
-
9886
9900
  jQuery.offset = {
9887
9901
  setOffset: function( elem, options, i ) {
9888
9902
  var curPosition, curLeft, curCSSTop, curTop, curOffset, curCSSLeft, calculatePosition,
@@ -9947,13 +9961,14 @@ jQuery.fn.extend( {
9947
9961
  } );
9948
9962
  }
9949
9963
 
9950
- var docElem, win, rect, doc,
9964
+ var doc, docElem, rect, win,
9951
9965
  elem = this[ 0 ];
9952
9966
 
9953
9967
  if ( !elem ) {
9954
9968
  return;
9955
9969
  }
9956
9970
 
9971
+ // Return zeros for disconnected and hidden (display: none) elements (gh-2310)
9957
9972
  // Support: IE <=11 only
9958
9973
  // Running getBoundingClientRect on a
9959
9974
  // disconnected node in IE throws an error
@@ -9963,20 +9978,14 @@ jQuery.fn.extend( {
9963
9978
 
9964
9979
  rect = elem.getBoundingClientRect();
9965
9980
 
9966
- // Make sure element is not hidden (display: none)
9967
- if ( rect.width || rect.height ) {
9968
- doc = elem.ownerDocument;
9969
- win = getWindow( doc );
9970
- docElem = doc.documentElement;
9981
+ doc = elem.ownerDocument;
9982
+ docElem = doc.documentElement;
9983
+ win = doc.defaultView;
9971
9984
 
9972
- return {
9973
- top: rect.top + win.pageYOffset - docElem.clientTop,
9974
- left: rect.left + win.pageXOffset - docElem.clientLeft
9975
- };
9976
- }
9977
-
9978
- // Return zeros for disconnected and hidden elements (gh-2310)
9979
- return rect;
9985
+ return {
9986
+ top: rect.top + win.pageYOffset - docElem.clientTop,
9987
+ left: rect.left + win.pageXOffset - docElem.clientLeft
9988
+ };
9980
9989
  },
9981
9990
 
9982
9991
  position: function() {
@@ -10002,7 +10011,7 @@ jQuery.fn.extend( {
10002
10011
 
10003
10012
  // Get correct offsets
10004
10013
  offset = this.offset();
10005
- if ( !jQuery.nodeName( offsetParent[ 0 ], "html" ) ) {
10014
+ if ( !nodeName( offsetParent[ 0 ], "html" ) ) {
10006
10015
  parentOffset = offsetParent.offset();
10007
10016
  }
10008
10017
 
@@ -10049,7 +10058,14 @@ jQuery.each( { scrollLeft: "pageXOffset", scrollTop: "pageYOffset" }, function(
10049
10058
 
10050
10059
  jQuery.fn[ method ] = function( val ) {
10051
10060
  return access( this, function( elem, method, val ) {
10052
- var win = getWindow( elem );
10061
+
10062
+ // Coalesce documents and windows
10063
+ var win;
10064
+ if ( jQuery.isWindow( elem ) ) {
10065
+ win = elem;
10066
+ } else if ( elem.nodeType === 9 ) {
10067
+ win = elem.defaultView;
10068
+ }
10053
10069
 
10054
10070
  if ( val === undefined ) {
10055
10071
  return win ? win[ prop ] : elem[ method ];
@@ -10155,10 +10171,19 @@ jQuery.fn.extend( {
10155
10171
  return arguments.length === 1 ?
10156
10172
  this.off( selector, "**" ) :
10157
10173
  this.off( types, selector || "**", fn );
10174
+ },
10175
+ holdReady: function( hold ) {
10176
+ if ( hold ) {
10177
+ jQuery.readyWait++;
10178
+ } else {
10179
+ jQuery.ready( true );
10180
+ }
10158
10181
  }
10159
10182
  } );
10160
10183
 
10184
+ jQuery.isArray = Array.isArray;
10161
10185
  jQuery.parseJSON = JSON.parse;
10186
+ jQuery.nodeName = nodeName;
10162
10187
 
10163
10188
 
10164
10189
 
@@ -10215,6 +10240,5 @@ if ( !noGlobal ) {
10215
10240
 
10216
10241
 
10217
10242
 
10218
-
10219
10243
  return jQuery;
10220
10244
  } );