html5-boilerplate 0.3.3 → 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
data/README.md CHANGED
@@ -46,7 +46,7 @@ Then run the following
46
46
 
47
47
  Now remove your application.html.erb so that Haml can do its thing
48
48
 
49
- mv apps/views/layouts/application.html.erb apps/views/layouts/application.html.old
49
+ mv app/views/layouts/application.html.erb app/views/layouts/application.html.old
50
50
 
51
51
  Start your Rails server, and you're done!
52
52
 
@@ -62,7 +62,6 @@ Start your Rails server, and you're done!
62
62
  app/views/layouts/_stylesheets.html.haml
63
63
 
64
64
  app/stylesheets/style.scss
65
- app/stylesheets/handheld.scss
66
65
  app/stylesheets/partials/_base.scss
67
66
  app/stylesheets/partials/_overrides.scss
68
67
  app/stylesheets/partials/_page.scss
@@ -76,8 +75,7 @@ Start your Rails server, and you're done!
76
75
  public/humans.txt
77
76
  public/apple-touch-icon.png
78
77
  public/favicon.ico
79
-
80
- public/javascripts/dd_belatedpng.js
78
+
81
79
  public/javascripts/jquery.min.js
82
80
  public/javascripts/modernizr.min.js
83
81
  public/javascripts/plugins.js
@@ -90,7 +88,6 @@ Start your Rails server, and you're done!
90
88
  The Scss files above will automatically get compiled to your Sass compilation directory:
91
89
 
92
90
  public/stylesheets/style.css
93
- public/stylesheets/handheld.css
94
91
 
95
92
  **Note:** If you already have a config/compass.rb file in your project, you may need to
96
93
  manually add the following line to the top:
@@ -133,14 +130,12 @@ If you omit them, be sure to edit your javascript and style tags accordingly in
133
130
  favicon.ico
134
131
 
135
132
  src/style.scss
136
- src/handheld.scss
137
133
  src/partials/_base.scss
138
134
  src/partials/_overrides.scss
139
135
  src/partials/_page.scss
140
136
  src/partials/_fonts.scss
141
137
  src/partials/_media.scss
142
138
 
143
- js/dd_belatedpng.js
144
139
  js/jquery.min.js
145
140
  js/modernizr.min.js
146
141
  js/plugins.js
@@ -152,7 +147,6 @@ Run `compass watch my_project` and the SCSS files above will automatically
152
147
  get compiled to your Sass compilation directory whenever a change is made:
153
148
 
154
149
  css/style.css
155
- css/handheld.css
156
150
 
157
151
  License
158
152
  =======
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.3.3
1
+ 1.0.0
@@ -15,8 +15,6 @@ $base-line-height: 1.231 !default;
15
15
  *font-size: small;
16
16
  }
17
17
 
18
- select, input, textarea, button { font: 99% $family; }
19
-
20
18
  // Normalize monospace sizing:
21
19
  // en.wikipedia.org/wiki/MediaWiki_talk:Common.css/Archive_11#Teletype_style_fix_for_Chrome
22
20
  pre, code, kbd, samp { font-family: monospace, sans-serif; }
@@ -1,4 +1,4 @@
1
- @import "compass/utilities/text/replacement";
1
+ @import "compass/typography/text/replacement";
2
2
  @import "compass/utilities/general/clearfix";
3
3
 
4
4
  //
@@ -13,7 +13,7 @@
13
13
 
14
14
  .visuallyhidden { @include visually-hidden; }
15
15
 
16
- .clearfix { @include pie-clearfix; }
16
+ .clearfix { @include micro-clearfix; }
17
17
  }
18
18
 
19
19
  // Almost the same as compass replace-text
@@ -55,8 +55,17 @@
55
55
  // Hide visually and from screenreaders, but maintain layout
56
56
  @mixin invisible { visibility: hidden; }
57
57
 
58
+ // The Magnificent Clearfix: Updated to prevent margin-collapsing on child elements in most situations.
59
+ // nicolasgallagher.com/micro-clearfix-hack/
60
+ @mixin micro-clearfix {
61
+ &:before, &:after { content: ""; display: table; }
62
+ &:after { clear: both; }
63
+ zoom: 1;
64
+ }
65
+
66
+
58
67
  // The Magnificent CLEARFIX << j.mp/phayesclearfix
59
68
  @mixin magnificent-clearfix {
60
69
  @warn "The 'magnificent-clearfix' mixin has been deprecated. Use 'pie-clearfix' in compass core instead.";
61
70
  @include pie-clearfix;
62
- }
71
+ }
@@ -1,19 +1,5 @@
1
1
  @mixin html5-boilerplate-media {
2
- @media print {
3
- @include media-print;
4
- }
5
-
6
- @media all and (orientation:portrait) {
7
- @include media-orientation-portrait;
8
- }
9
-
10
- @media all and (orientation:landscape) {
11
- @include media-orientation-landscape;
12
- }
13
-
14
- @media screen and (max-device-width: 480px) {
15
- @include media-mobile;
16
- }
2
+ @warn "The 'html5-boilerplate-media' mixin has been deprecated.";
17
3
  }
18
4
 
19
5
  //
@@ -30,31 +16,20 @@
30
16
  pre, blockquote { border: 1px solid #999; page-break-inside: avoid; }
31
17
  thead { display: table-header-group; } // css-discuss.incutio.com/wiki/Printing_Tables
32
18
  tr, img { page-break-inside: avoid; }
19
+ img { max-width: 100% !important; }
33
20
  @page { margin: 0.5cm; }
34
21
  p, h2, h3 { orphans: 3; widows: 3; }
35
22
  h2, h3{ page-break-after: avoid; }
36
23
  }
37
24
 
38
-
39
- //
40
- // Media queries for responsive design
41
- // These follow after primary styles so they will successfully override.
42
- //
43
-
44
25
  @mixin media-orientation-portrait {
45
- // Style adjustments for portrait mode goes here
26
+ @warn "The 'media-orientation-portrait' mixin has been deprecated.";
46
27
  }
47
28
 
48
29
  @mixin media-orientation-landscape {
49
- // Style adjustments for landscape mode goes here
30
+ @warn "The 'media-orientation-landscape' mixin has been deprecated.";
50
31
  }
51
32
 
52
- // Grade-A Mobile Browsers (Opera Mobile, Mobile Safari, Android Chrome)
53
- // consider this: www.cloudfour.com/css-media-query-for-mobile-is-fools-gold
54
33
  @mixin media-mobile($optimize: true) {
55
- // j.mp/textsizeadjust
56
- @if not $optimize {
57
- // Don't allow iOS and WinMobile to mobile-optimize text
58
- html { -webkit-text-size-adjust: none; -ms-text-size-adjust: none; }
59
- }
34
+ @warn "The 'media-mobile' mixin has been deprecated.";
60
35
  }
@@ -16,7 +16,6 @@
16
16
  padding: 0;
17
17
  border: 0;
18
18
  font-size: 100%;
19
- font: inherit;
20
19
  vertical-align: baseline;
21
20
  }
22
21
 
@@ -41,6 +40,4 @@
41
40
  table { border-collapse: collapse; border-spacing: 0; }
42
41
 
43
42
  hr { display: block; height: 1px; border: 0; border-top: 1px solid #ccc; margin: 1em 0; padding: 0; }
44
-
45
- input, select { vertical-align: middle; }
46
43
  }
@@ -23,14 +23,10 @@ $list-left-margin: 1.8em !default;
23
23
 
24
24
  sup { @include sup; }
25
25
 
26
- textarea { overflow: auto; } // www.sitepoint.com/blogs/2010/08/20/ie-remove-textarea-scrollbars
27
-
28
26
  @include accessible-focus;
29
27
 
30
28
  @include quoted-pre;
31
29
 
32
- @include align-input-labels;
33
-
34
30
  @include hand-cursor-inputs;
35
31
 
36
32
  @include reset-form-elements;
@@ -67,10 +63,7 @@ $list-left-margin: 1.8em !default;
67
63
 
68
64
  // Align checkboxes, radios, text inputs with their label by: Thierry Koblentz tjkdesign.com/ez-css/css/base.css
69
65
  @mixin align-input-labels {
70
- input[type="radio"] { vertical-align: text-bottom; }
71
- input[type="checkbox"] { vertical-align: bottom; }
72
- .ie7 input[type="checkbox"] { vertical-align: baseline; }
73
- .ie6 input { vertical-align: text-bottom; }
66
+ @warn "The 'align-input-labels' mixin has been deprecated.";
74
67
  }
75
68
 
76
69
  // Hand cursor on clickable input elements
@@ -82,7 +75,13 @@ $list-left-margin: 1.8em !default;
82
75
  // 1) Make inputs and buttons play nice in IE: www.viget.com/inspire/styling-the-button-element-in-internet-explorer/
83
76
  // 2) WebKit browsers add a 2px margin outside the chrome of form elements.
84
77
  // Firefox adds a 1px margin above and below textareas
85
- button, input, select, textarea { width: auto; overflow: visible; margin: 0; }
78
+ // 3) Set font-size to match <body>'s, and font-family to sans-serif
79
+ // 4) Align to baseline
80
+ button, input, select, textarea { width: auto; overflow: visible; margin: 0; font-size: 100%; font-family: sans-serif; vertical-align: baseline; }
81
+
82
+ // 1) Remove default scrollbar in IE: www.sitepoint.com/blogs/2010/08/20/ie-remove-textarea-scrollbars/
83
+ // 2) Align to text-top
84
+ textarea { overflow: auto; vertical-align: text-top; }
86
85
 
87
86
  // Remove extra padding and inner border in Firefox
88
87
  input::-moz-focus-inner,
@@ -106,9 +105,11 @@ $list-left-margin: 1.8em !default;
106
105
  a:link { -webkit-tap-highlight-color: $selected-background-color; }
107
106
  }
108
107
 
109
- // Always force a scrollbar in non-IE
108
+ // 1) Always force a scrollbar in non-IE
109
+ // 2) Remove iOS text size adjust without disabling user zoom:
110
+ // www.456bereastreet.com/archive/201012/controlling_text_size_in_safari_for_ios_without_disabling_user_zoom/
110
111
  @mixin force-scrollbar {
111
- overflow-y: scroll;
112
+ overflow-y: scroll; -webkit-text-size-adjust: 100%; -ms-text-size-adjust: 100%;
112
113
  }
113
114
 
114
115
  @mixin ie-hacks {
@@ -1,4 +1,4 @@
1
1
  #flash
2
2
  - flash.each do |key, value|
3
- %div{ :title => key.to_s.humanize, :class => key }
3
+ .message{ :class => key }
4
4
  %p= value
@@ -13,15 +13,14 @@
13
13
  -# Mobile viewport optimized: j.mp/bplateviewport
14
14
  %meta{ :name => "viewport", :content => "width=device-width, initial-scale=1.0" }/
15
15
 
16
- -# Place favicon.ico and apple-touch-icon.png in the root of your domain and delete these references
17
- -# %link{ :rel => "shortcut icon", :href => "/favicon.ico" }/
18
- -# %link{ :rel => "apple-touch-icon", :href => "/apple-touch-icon.png" }/
16
+ -# Place favicon.ico and apple-touch-icon.png in the root directory: mathiasbynens.be/notes/touch-icons
19
17
 
20
- -# You can specify a stylesheet_partial when rendering this partial (i.e. admin/stylesheets)
18
+ -# Pass in a stylesheet_partial to render inside your head
21
19
  - if local_assigns[:stylesheet_partial]
22
20
  = render :partial => local_assigns[:stylesheet_partial]
23
21
 
24
- -# All JavaScript at the bottom, except for Modernizr which enables HTML5 elements & feature detects
25
- = javascript_include_tag 'modernizr.min'
22
+ -# All JavaScript at the bottom, except for Modernizr and Respond.
23
+ -# Modernizr enables HTML5 elements & feature detects; Respond is a polyfill for min/max-width CSS3 Media Queries
24
+ = javascript_include_tag 'modernizr.min', 'respond.min'
26
25
 
27
26
  = csrf_meta_tag
@@ -4,21 +4,15 @@
4
4
  - if !google_api_key.blank?
5
5
  = javascript_include_tag "//www.google.com/jsapi?key=#{google_api_key}"
6
6
  :javascript
7
- google.load(#{ remote_jquery("1.5.2") });
7
+ google.load(#{ remote_jquery("1.6") });
8
8
  - else
9
- = javascript_include_tag "//ajax.googleapis.com/ajax/libs/jquery/#{ local_jquery("1.5.2") }"
9
+ = javascript_include_tag "//ajax.googleapis.com/ajax/libs/jquery/#{ local_jquery("1.6") }"
10
10
 
11
11
  -# fall back to local jQuery if necessary
12
12
  :javascript
13
13
  window.jQuery || document.write("<script src='/javascripts/jquery.min.js'>\x3C/script>")
14
14
 
15
15
  = javascript_include_tag 'rails', 'plugins', 'application'
16
-
17
- -# Fix any <img> or .png_bg bg-images. Also, please read goo.gl/mZiyb
18
- /[if lt IE 7 ]
19
- = javascript_include_tag 'dd_belatedpng.js'
20
- :javascript
21
- //DD_belatedPNG.fix('img, .png_bg');
22
16
 
23
17
  -# Append your own using content_for :javascripts
24
18
  = yield :javascripts
@@ -27,7 +21,7 @@
27
21
  -# Looks for google_account_id first in ENV['GOOGLE_ACCOUNT_ID'] then in config/google.yml
28
22
  - if !google_account_id.blank?
29
23
  :javascript
30
- var _gaq=[["_setAccount","#{google_account_id}"],["_trackPageview"]];
24
+ var _gaq=[["_setAccount","#{google_account_id}"],["_trackPageview"],["_trackPageLoadTime"]];
31
25
  (function(d,t){var g=d.createElement(t),s=d.getElementsByTagName(t)[0];g.async=1;
32
26
  g.src=("https:"==location.protocol?"//ssl":"//www")+".google-analytics.com/ga.js";
33
27
  s.parentNode.insertBefore(g,s)}(document,"script"));
@@ -1,8 +1,5 @@
1
1
  -# CSS: implied media="all"
2
2
  = stylesheet_link_tag 'style', :media => 'all'
3
3
 
4
- -# Uncomment if you are specifically targeting less enabled mobile browsers
5
- -#= stylesheet_link_tag 'handheld', :media => 'handheld'
6
-
7
4
  -# Append your own using content_for :stylesheets
8
5
  = yield :stylesheets
@@ -2,6 +2,8 @@
2
2
  -# http://paulirish.com/2008/conditional-stylesheets-vs-css-hacks-answer-neither
3
3
  -ie_html :class => 'no-js', :lang => 'en' do
4
4
  %head
5
+ -# To render a different stylesheet partial inside the head (i.e. for admin layout)
6
+ -# just copy _stylesheets.html.haml, and point to that partial instead.
5
7
  = render "layouts/head", :stylesheet_partial => "layouts/stylesheets"
6
8
 
7
9
  %body{ :class => "#{controller.controller_name}" }
@@ -9,57 +9,47 @@
9
9
  %head
10
10
  %meta{ :charset => "utf-8" }/
11
11
 
12
- -#
13
- Always force latest IE rendering engine (even in intranet) & Chrome Frame
14
- Remove this if you use the .htaccess
12
+ -# Always force latest IE rendering engine (even in intranet) & Chrome Frame
13
+ -# Remove this if you use the .htaccess
15
14
  %meta{ "http-equiv" => "X-UA-Compatible", :content => "IE=edge,chrome=1" }/
16
15
 
17
16
  %title
18
17
  %meta{ :name => "description", :content => "" }/
19
- %meta{ :name => "author" :content => "" }/
18
+ %meta{ :name => "author", :content => "" }/
20
19
 
21
20
  -# Mobile viewport optimized: j.mp/bplateviewport
22
- %meta{ :content => "width=device-width, initial-scale=1.0", :name => "viewport" }/
21
+ %meta{ :name => "viewport", :content => "width=device-width, initial-scale=1.0" }/
23
22
 
24
- -# Place favicon.ico and apple-touch-icon.png in the root of your domain and delete these references
25
- -# %link{ :href => "/favicon.ico", :rel => "shortcut icon" }/
26
- -# %link{ :href => "/apple-touch-icon.png", :rel => "apple-touch-icon" }/
23
+ -# Place favicon.ico and apple-touch-icon.png in the root directory: mathiasbynens.be/notes/touch-icons
27
24
 
28
25
  -# CSS: implied media="all"
29
26
  %link{ :href => "css/style.css?v=1", :media => "all", :rel => "stylesheet" }/
30
27
 
31
- -# Uncomment if you are specifically targeting less enabled mobile browsers
32
- -# %link{ :href => "css/handheld.css?v=1", :media => "handheld", :rel => "stylesheet" }/
33
-
34
- -# All JavaScript at the bottom, except for Modernizr which enables HTML5 elements & feature detects
28
+ -# All JavaScript at the bottom, except for Modernizr and Respond.
29
+ -# Modernizr enables HTML5 elements & feature detects; Respond is a polyfill for min/max-width CSS3 Media Queries
35
30
  %script{ :src => "js/modernizr.min.js" }
31
+ %script{ :src => "js/respond.min.js" }
36
32
 
37
33
  %body
38
34
  #container
39
35
  %header
40
- #main
36
+ #main{ :role => 'main' }
41
37
  %footer
42
38
 
43
39
  -#
44
40
  Javascript at the bottom for fast page loading
45
41
  Grab Google CDN's jQuery, with a protocol relative URL; fall back to local if necessary
46
- %script{ :src => "//ajax.googleapis.com/ajax/libs/jquery/1.5.2/jquery.js" }
42
+ %script{ :src => "//ajax.googleapis.com/ajax/libs/jquery/1.6/jquery.js" }
47
43
  :javascript
48
44
  window.jQuery || document.write("<script src='js/jquery.min.js'>\x3C/script>")
49
45
 
50
46
  %script{ :src => "js/plugins.js?v=1" }
51
47
  %script{ :src => "js/script.js?v=1" }
52
48
 
53
- /[if lt IE 7 ]
54
- %script{ :src => "js/dd_belatedpng.js" }
55
- :javascript
56
- //DD_belatedPNG.fix('img, .png_bg');
57
-
58
49
  -# asynchronous google analytics: mathiasbynens.be/notes/async-analytics-snippet
59
50
  -# change the UA-XXXXX-X to be your site's ID
60
51
  :javascript
61
- var _gaq=[["_setAccount","UA-XXXXX-X"],["_trackPageview"]];
52
+ var _gaq=[["_setAccount","UA-XXXXX-X"],["_trackPageview"],["_trackPageLoadTime"]];
62
53
  (function(d,t){var g=d.createElement(t),s=d.getElementsByTagName(t)[0];g.async=1;
63
54
  g.src=("https:"==location.protocol?"//ssl":"//www")+".google-analytics.com/ga.js";
64
55
  s.parentNode.insertBefore(g,s)}(document,"script"));
65
-
@@ -1,5 +1,5 @@
1
1
  /*!
2
- * jQuery JavaScript Library v1.5.2
2
+ * jQuery JavaScript Library v1.6
3
3
  * http://jquery.com/
4
4
  *
5
5
  * Copyright 2011, John Resig
@@ -11,12 +11,14 @@
11
11
  * Copyright 2011, The Dojo Foundation
12
12
  * Released under the MIT, BSD, and GPL Licenses.
13
13
  *
14
- * Date: Thu Mar 31 15:28:23 2011 -0400
14
+ * Date: Mon May 2 13:50:00 2011 -0400
15
15
  */
16
16
  (function( window, undefined ) {
17
17
 
18
18
  // Use the correct document accordingly with window argument (sandbox)
19
- var document = window.document;
19
+ var document = window.document,
20
+ navigator = window.navigator,
21
+ location = window.location;
20
22
  var jQuery = (function() {
21
23
 
22
24
  // Define a local copy of jQuery
@@ -36,7 +38,7 @@ var jQuery = function( selector, context ) {
36
38
 
37
39
  // A simple way to check for HTML strings or ID strings
38
40
  // (both of which we optimize for)
39
- quickExpr = /^(?:[^<]*(<[\w\W]+>)[^>]*$|#([\w\-]+)$)/,
41
+ quickExpr = /^(?:[^<]*(<[\w\W]+>)[^>]*$|#([\w\-]*)$)/,
40
42
 
41
43
  // Check if a string has a non-whitespace character in it
42
44
  rnotwhite = /\S/,
@@ -107,7 +109,7 @@ jQuery.fn = jQuery.prototype = {
107
109
  if ( selector === "body" && !context && document.body ) {
108
110
  this.context = document;
109
111
  this[0] = document.body;
110
- this.selector = "body";
112
+ this.selector = selector;
111
113
  this.length = 1;
112
114
  return this;
113
115
  }
@@ -115,7 +117,13 @@ jQuery.fn = jQuery.prototype = {
115
117
  // Handle HTML strings
116
118
  if ( typeof selector === "string" ) {
117
119
  // Are we dealing with HTML string or an ID?
118
- match = quickExpr.exec( selector );
120
+ if ( selector.charAt(0) === "<" && selector.charAt( selector.length - 1 ) === ">" && selector.length >= 3 ) {
121
+ // Assume that strings that start and end with <> are HTML and skip the regex check
122
+ match = [ null, selector, null ];
123
+
124
+ } else {
125
+ match = quickExpr.exec( selector );
126
+ }
119
127
 
120
128
  // Verify a match, and that no context was specified for #id
121
129
  if ( match && (match[1] || !context) ) {
@@ -196,7 +204,7 @@ jQuery.fn = jQuery.prototype = {
196
204
  selector: "",
197
205
 
198
206
  // The current version of jQuery being used
199
- jquery: "1.5.2",
207
+ jquery: "1.6",
200
208
 
201
209
  // The default length of a jQuery object is 0
202
210
  length: 0,
@@ -372,9 +380,11 @@ jQuery.extend = jQuery.fn.extend = function() {
372
380
 
373
381
  jQuery.extend({
374
382
  noConflict: function( deep ) {
375
- window.$ = _$;
383
+ if ( window.$ === jQuery ) {
384
+ window.$ = _$;
385
+ }
376
386
 
377
- if ( deep ) {
387
+ if ( deep && window.jQuery === jQuery ) {
378
388
  window.jQuery = _jQuery;
379
389
  }
380
390
 
@@ -388,15 +398,19 @@ jQuery.extend({
388
398
  // the ready event fires. See #6781
389
399
  readyWait: 1,
390
400
 
391
- // Handle when the DOM is ready
392
- ready: function( wait ) {
393
- // A third-party is pushing the ready event forwards
394
- if ( wait === true ) {
395
- jQuery.readyWait--;
401
+ // Hold (or release) the ready event
402
+ holdReady: function( hold ) {
403
+ if ( hold ) {
404
+ jQuery.readyWait++;
405
+ } else {
406
+ jQuery.ready( true );
396
407
  }
408
+ },
397
409
 
398
- // Make sure that the DOM is not already loaded
399
- if ( !jQuery.readyWait || (wait !== true && !jQuery.isReady) ) {
410
+ // Handle when the DOM is ready
411
+ ready: function( wait ) {
412
+ // Either a released hold or an DOMready/load event and not yet ready
413
+ if ( (wait === true && !--jQuery.readyWait) || (wait !== true && !jQuery.isReady) ) {
400
414
  // Make sure body exists, at least, in case IE gets a little overzealous (ticket #5443).
401
415
  if ( !document.body ) {
402
416
  return setTimeout( jQuery.ready, 1 );
@@ -446,7 +460,7 @@ jQuery.extend({
446
460
  } else if ( document.attachEvent ) {
447
461
  // ensure firing before onload,
448
462
  // maybe late but safe also for iframes
449
- document.attachEvent("onreadystatechange", DOMContentLoaded);
463
+ document.attachEvent( "onreadystatechange", DOMContentLoaded );
450
464
 
451
465
  // A fallback to window.onload, that will always work
452
466
  window.attachEvent( "onload", jQuery.ready );
@@ -534,20 +548,21 @@ jQuery.extend({
534
548
  // Make sure leading/trailing whitespace is removed (IE can't handle it)
535
549
  data = jQuery.trim( data );
536
550
 
551
+ // Attempt to parse using the native JSON parser first
552
+ if ( window.JSON && window.JSON.parse ) {
553
+ return window.JSON.parse( data );
554
+ }
555
+
537
556
  // Make sure the incoming data is actual JSON
538
557
  // Logic borrowed from http://json.org/json2.js
539
- if ( rvalidchars.test(data.replace(rvalidescape, "@")
540
- .replace(rvalidtokens, "]")
541
- .replace(rvalidbraces, "")) ) {
558
+ if ( rvalidchars.test( data.replace( rvalidescape, "@" )
559
+ .replace( rvalidtokens, "]" )
560
+ .replace( rvalidbraces, "")) ) {
542
561
 
543
- // Try to use the native JSON parser first
544
- return window.JSON && window.JSON.parse ?
545
- window.JSON.parse( data ) :
546
- (new Function("return " + data))();
562
+ return (new Function( "return " + data ))();
547
563
 
548
- } else {
549
- jQuery.error( "Invalid JSON: " + data );
550
564
  }
565
+ jQuery.error( "Invalid JSON: " + data );
551
566
  },
552
567
 
553
568
  // Cross-browser xml parsing
@@ -574,24 +589,17 @@ jQuery.extend({
574
589
 
575
590
  noop: function() {},
576
591
 
577
- // Evalulates a script in a global context
592
+ // Evaluates a script in a global context
593
+ // Workarounds based on findings by Jim Driscoll
594
+ // http://weblogs.java.net/blog/driscoll/archive/2009/09/08/eval-javascript-global-context
578
595
  globalEval: function( data ) {
579
- if ( data && rnotwhite.test(data) ) {
580
- // Inspired by code by Andrea Giammarchi
581
- // http://webreflection.blogspot.com/2007/08/global-scope-evaluation-and-dom.html
582
- var head = document.head || document.getElementsByTagName( "head" )[0] || document.documentElement,
583
- script = document.createElement( "script" );
584
-
585
- if ( jQuery.support.scriptEval() ) {
586
- script.appendChild( document.createTextNode( data ) );
587
- } else {
588
- script.text = data;
589
- }
590
-
591
- // Use insertBefore instead of appendChild to circumvent an IE6 bug.
592
- // This arises when a base node is used (#2709).
593
- head.insertBefore( script, head.firstChild );
594
- head.removeChild( script );
596
+ if ( data && rnotwhite.test( data ) ) {
597
+ // We use execScript on Internet Explorer
598
+ // We use an anonymous function so that context is window
599
+ // rather than jQuery in Firefox
600
+ ( window.execScript || function( data ) {
601
+ window[ "eval" ].call( window, data );
602
+ } )( data );
595
603
  }
596
604
  },
597
605
 
@@ -603,7 +611,7 @@ jQuery.extend({
603
611
  each: function( object, callback, args ) {
604
612
  var name, i = 0,
605
613
  length = object.length,
606
- isObj = length === undefined || jQuery.isFunction(object);
614
+ isObj = length === undefined || jQuery.isFunction( object );
607
615
 
608
616
  if ( args ) {
609
617
  if ( isObj ) {
@@ -629,8 +637,11 @@ jQuery.extend({
629
637
  }
630
638
  }
631
639
  } else {
632
- for ( var value = object[0];
633
- i < length && callback.call( value, i, value ) !== false; value = object[++i] ) {}
640
+ for ( ; i < length; ) {
641
+ if ( callback.call( object[ i ], i, object[ i++ ] ) === false ) {
642
+ break;
643
+ }
644
+ }
634
645
  }
635
646
  }
636
647
 
@@ -661,7 +672,7 @@ jQuery.extend({
661
672
  // The extra typeof function check is to prevent crashes
662
673
  // in Safari 2 (See: #3039)
663
674
  // Tweaked logic slightly to handle Blackberry 4.7 RegExp issues #6930
664
- var type = jQuery.type(array);
675
+ var type = jQuery.type( array );
665
676
 
666
677
  if ( array.length == null || type === "string" || type === "function" || type === "regexp" || jQuery.isWindow( array ) ) {
667
678
  push.call( ret, array );
@@ -674,8 +685,9 @@ jQuery.extend({
674
685
  },
675
686
 
676
687
  inArray: function( elem, array ) {
677
- if ( array.indexOf ) {
678
- return array.indexOf( elem );
688
+
689
+ if ( indexOf ) {
690
+ return indexOf.call( array, elem );
679
691
  }
680
692
 
681
693
  for ( var i = 0, length = array.length; i < length; i++ ) {
@@ -725,15 +737,30 @@ jQuery.extend({
725
737
 
726
738
  // arg is for internal usage only
727
739
  map: function( elems, callback, arg ) {
728
- var ret = [], value;
740
+ var value, key, ret = [],
741
+ i = 0,
742
+ length = elems.length,
743
+ // jquery objects are treated as arrays
744
+ isArray = elems instanceof jQuery || length !== undefined && typeof length === "number" && ( ( length > 0 && elems[ 0 ] && elems[ length -1 ] ) || length === 0 || jQuery.isArray( elems ) ) ;
729
745
 
730
746
  // Go through the array, translating each of the items to their
731
- // new value (or values).
732
- for ( var i = 0, length = elems.length; i < length; i++ ) {
733
- value = callback( elems[ i ], i, arg );
747
+ if ( isArray ) {
748
+ for ( ; i < length; i++ ) {
749
+ value = callback( elems[ i ], i, arg );
734
750
 
735
- if ( value != null ) {
736
- ret[ ret.length ] = value;
751
+ if ( value != null ) {
752
+ ret[ ret.length ] = value;
753
+ }
754
+ }
755
+
756
+ // Go through every key on the object,
757
+ } else {
758
+ for ( key in elems ) {
759
+ value = callback( elems[ key ], key, arg );
760
+
761
+ if ( value != null ) {
762
+ ret[ ret.length ] = value;
763
+ }
737
764
  }
738
765
  }
739
766
 
@@ -744,31 +771,30 @@ jQuery.extend({
744
771
  // A global GUID counter for objects
745
772
  guid: 1,
746
773
 
747
- proxy: function( fn, proxy, thisObject ) {
748
- if ( arguments.length === 2 ) {
749
- if ( typeof proxy === "string" ) {
750
- thisObject = fn;
751
- fn = thisObject[ proxy ];
752
- proxy = undefined;
774
+ // Bind a function to a context, optionally partially applying any
775
+ // arguments.
776
+ proxy: function( fn, context ) {
777
+ if ( typeof context === "string" ) {
778
+ var tmp = fn[ context ];
779
+ context = fn;
780
+ fn = tmp;
781
+ }
753
782
 
754
- } else if ( proxy && !jQuery.isFunction( proxy ) ) {
755
- thisObject = proxy;
756
- proxy = undefined;
757
- }
783
+ // Quick check to determine if target is callable, in the spec
784
+ // this throws a TypeError, but we will just return undefined.
785
+ if ( !jQuery.isFunction( fn ) ) {
786
+ return undefined;
758
787
  }
759
788
 
760
- if ( !proxy && fn ) {
789
+ // Simulated bind
790
+ var args = slice.call( arguments, 2 ),
761
791
  proxy = function() {
762
- return fn.apply( thisObject || this, arguments );
792
+ return fn.apply( context, args.concat( slice.call( arguments ) ) );
763
793
  };
764
- }
765
794
 
766
795
  // Set the guid of unique handler to the same of original handler, so it can be removed
767
- if ( fn ) {
768
- proxy.guid = fn.guid = fn.guid || proxy.guid || jQuery.guid++;
769
- }
796
+ proxy.guid = fn.guid = fn.guid || proxy.guid || jQuery.guid++;
770
797
 
771
- // So proxy can be declared as an argument
772
798
  return proxy;
773
799
  },
774
800
 
@@ -820,24 +846,24 @@ jQuery.extend({
820
846
  },
821
847
 
822
848
  sub: function() {
823
- function jQuerySubclass( selector, context ) {
824
- return new jQuerySubclass.fn.init( selector, context );
849
+ function jQuerySub( selector, context ) {
850
+ return new jQuerySub.fn.init( selector, context );
825
851
  }
826
- jQuery.extend( true, jQuerySubclass, this );
827
- jQuerySubclass.superclass = this;
828
- jQuerySubclass.fn = jQuerySubclass.prototype = this();
829
- jQuerySubclass.fn.constructor = jQuerySubclass;
830
- jQuerySubclass.subclass = this.subclass;
831
- jQuerySubclass.fn.init = function init( selector, context ) {
832
- if ( context && context instanceof jQuery && !(context instanceof jQuerySubclass) ) {
833
- context = jQuerySubclass(context);
852
+ jQuery.extend( true, jQuerySub, this );
853
+ jQuerySub.superclass = this;
854
+ jQuerySub.fn = jQuerySub.prototype = this();
855
+ jQuerySub.fn.constructor = jQuerySub;
856
+ jQuerySub.sub = this.sub;
857
+ jQuerySub.fn.init = function init( selector, context ) {
858
+ if ( context && context instanceof jQuery && !(context instanceof jQuerySub) ) {
859
+ context = jQuerySub( context );
834
860
  }
835
861
 
836
- return jQuery.fn.init.call( this, selector, context, rootjQuerySubclass );
862
+ return jQuery.fn.init.call( this, selector, context, rootjQuerySub );
837
863
  };
838
- jQuerySubclass.fn.init.prototype = jQuerySubclass.fn;
839
- var rootjQuerySubclass = jQuerySubclass(document);
840
- return jQuerySubclass;
864
+ jQuerySub.fn.init.prototype = jQuerySub.fn;
865
+ var rootjQuerySub = jQuerySub(document);
866
+ return jQuerySub;
841
867
  },
842
868
 
843
869
  browser: {}
@@ -859,12 +885,6 @@ if ( jQuery.browser.webkit ) {
859
885
  jQuery.browser.safari = true;
860
886
  }
861
887
 
862
- if ( indexOf ) {
863
- jQuery.inArray = function( elem, array ) {
864
- return indexOf.call( array, elem );
865
- };
866
- }
867
-
868
888
  // IE doesn't match non-breaking spaces with \s
869
889
  if ( rnotwhite.test( "\xA0" ) ) {
870
890
  trimLeft = /^[\s\xA0]+/;
@@ -917,7 +937,7 @@ return jQuery;
917
937
 
918
938
 
919
939
  var // Promise methods
920
- promiseMethods = "then done fail isResolved isRejected promise".split( " " ),
940
+ promiseMethods = "done fail isResolved isRejected promise then always pipe".split( " " ),
921
941
  // Static reference to slice
922
942
  sliceDeferred = [].slice;
923
943
 
@@ -1016,10 +1036,37 @@ jQuery.extend({
1016
1036
  deferred.done( doneCallbacks ).fail( failCallbacks );
1017
1037
  return this;
1018
1038
  },
1039
+ always: function() {
1040
+ return deferred.done.apply( deferred, arguments ).fail.apply( this, arguments );
1041
+ },
1019
1042
  fail: failDeferred.done,
1020
1043
  rejectWith: failDeferred.resolveWith,
1021
1044
  reject: failDeferred.resolve,
1022
1045
  isRejected: failDeferred.isResolved,
1046
+ pipe: function( fnDone, fnFail ) {
1047
+ return jQuery.Deferred(function( newDefer ) {
1048
+ jQuery.each( {
1049
+ done: [ fnDone, "resolve" ],
1050
+ fail: [ fnFail, "reject" ]
1051
+ }, function( handler, data ) {
1052
+ var fn = data[ 0 ],
1053
+ action = data[ 1 ],
1054
+ returned;
1055
+ if ( jQuery.isFunction( fn ) ) {
1056
+ deferred[ handler ](function() {
1057
+ returned = fn.apply( this, arguments );
1058
+ if ( jQuery.isFunction( returned.promise ) ) {
1059
+ returned.promise().then( newDefer.resolve, newDefer.reject );
1060
+ } else {
1061
+ newDefer[ action ]( returned );
1062
+ }
1063
+ });
1064
+ } else {
1065
+ deferred[ handler ]( newDefer[ action ] );
1066
+ }
1067
+ });
1068
+ }).promise();
1069
+ },
1023
1070
  // Get a promise for this deferred
1024
1071
  // If obj is provided, the promise aspect is added to the object
1025
1072
  promise: function( obj ) {
@@ -1035,7 +1082,7 @@ jQuery.extend({
1035
1082
  }
1036
1083
  return obj;
1037
1084
  }
1038
- } );
1085
+ });
1039
1086
  // Make sure only one callback list will be used
1040
1087
  deferred.done( failDeferred.cancel ).fail( deferred.cancel );
1041
1088
  // Unexpose cancel
@@ -1087,46 +1134,61 @@ jQuery.extend({
1087
1134
 
1088
1135
 
1089
1136
 
1137
+ jQuery.support = (function() {
1090
1138
 
1091
- (function() {
1092
-
1093
- jQuery.support = {};
1094
-
1095
- var div = document.createElement("div");
1139
+ var div = document.createElement( "div" ),
1140
+ all,
1141
+ a,
1142
+ select,
1143
+ opt,
1144
+ input,
1145
+ marginDiv,
1146
+ support,
1147
+ fragment,
1148
+ body,
1149
+ bodyStyle,
1150
+ tds,
1151
+ events,
1152
+ eventName,
1153
+ i,
1154
+ isSupported;
1096
1155
 
1097
- div.style.display = "none";
1098
- div.innerHTML = " <link/><table></table><a href='/a' style='color:red;float:left;opacity:.55;'>a</a><input type='checkbox'/>";
1156
+ // Preliminary tests
1157
+ div.setAttribute("className", "t");
1158
+ div.innerHTML = " <link/><table></table><a href='/a' style='top:1px;float:left;opacity:.55;'>a</a><input type='checkbox'/>";
1099
1159
 
1100
- var all = div.getElementsByTagName("*"),
1101
- a = div.getElementsByTagName("a")[0],
1102
- select = document.createElement("select"),
1103
- opt = select.appendChild( document.createElement("option") ),
1104
- input = div.getElementsByTagName("input")[0];
1160
+ all = div.getElementsByTagName( "*" );
1161
+ a = div.getElementsByTagName( "a" )[ 0 ];
1105
1162
 
1106
1163
  // Can't get basic test support
1107
1164
  if ( !all || !all.length || !a ) {
1108
- return;
1165
+ return {};
1109
1166
  }
1110
1167
 
1111
- jQuery.support = {
1168
+ // First batch of supports tests
1169
+ select = document.createElement( "select" );
1170
+ opt = select.appendChild( document.createElement("option") );
1171
+ input = div.getElementsByTagName( "input" )[ 0 ];
1172
+
1173
+ support = {
1112
1174
  // IE strips leading whitespace when .innerHTML is used
1113
- leadingWhitespace: div.firstChild.nodeType === 3,
1175
+ leadingWhitespace: ( div.firstChild.nodeType === 3 ),
1114
1176
 
1115
1177
  // Make sure that tbody elements aren't automatically inserted
1116
1178
  // IE will insert them into empty tables
1117
- tbody: !div.getElementsByTagName("tbody").length,
1179
+ tbody: !div.getElementsByTagName( "tbody" ).length,
1118
1180
 
1119
1181
  // Make sure that link elements get serialized correctly by innerHTML
1120
1182
  // This requires a wrapper element in IE
1121
- htmlSerialize: !!div.getElementsByTagName("link").length,
1183
+ htmlSerialize: !!div.getElementsByTagName( "link" ).length,
1122
1184
 
1123
1185
  // Get the style information from getAttribute
1124
- // (IE uses .cssText insted)
1125
- style: /red/.test( a.getAttribute("style") ),
1186
+ // (IE uses .cssText instead)
1187
+ style: /top/.test( a.getAttribute("style") ),
1126
1188
 
1127
1189
  // Make sure that URLs aren't manipulated
1128
1190
  // (IE normalizes it by default)
1129
- hrefNormalized: a.getAttribute("href") === "/a",
1191
+ hrefNormalized: ( a.getAttribute( "href" ) === "/a" ),
1130
1192
 
1131
1193
  // Make sure that element opacity exists
1132
1194
  // (IE uses filter instead)
@@ -1140,188 +1202,183 @@ jQuery.extend({
1140
1202
  // Make sure that if no value is specified for a checkbox
1141
1203
  // that it defaults to "on".
1142
1204
  // (WebKit defaults to "" instead)
1143
- checkOn: input.value === "on",
1205
+ checkOn: ( input.value === "on" ),
1144
1206
 
1145
1207
  // Make sure that a selected-by-default option has a working selected property.
1146
1208
  // (WebKit defaults to false instead of true, IE too, if it's in an optgroup)
1147
1209
  optSelected: opt.selected,
1148
1210
 
1211
+ // Test setAttribute on camelCase class. If it works, we need attrFixes when doing get/setAttribute (ie6/7)
1212
+ getSetAttribute: div.className !== "t",
1213
+
1149
1214
  // Will be defined later
1215
+ submitBubbles: true,
1216
+ changeBubbles: true,
1217
+ focusinBubbles: false,
1150
1218
  deleteExpando: true,
1151
- optDisabled: false,
1152
- checkClone: false,
1153
1219
  noCloneEvent: true,
1154
- noCloneChecked: true,
1155
- boxModel: null,
1156
1220
  inlineBlockNeedsLayout: false,
1157
1221
  shrinkWrapBlocks: false,
1158
- reliableHiddenOffsets: true,
1159
1222
  reliableMarginRight: true
1160
1223
  };
1161
1224
 
1225
+ // Make sure checked status is properly cloned
1162
1226
  input.checked = true;
1163
- jQuery.support.noCloneChecked = input.cloneNode( true ).checked;
1227
+ support.noCloneChecked = input.cloneNode( true ).checked;
1164
1228
 
1165
1229
  // Make sure that the options inside disabled selects aren't marked as disabled
1166
- // (WebKit marks them as diabled)
1230
+ // (WebKit marks them as disabled)
1167
1231
  select.disabled = true;
1168
- jQuery.support.optDisabled = !opt.disabled;
1169
-
1170
- var _scriptEval = null;
1171
- jQuery.support.scriptEval = function() {
1172
- if ( _scriptEval === null ) {
1173
- var root = document.documentElement,
1174
- script = document.createElement("script"),
1175
- id = "script" + jQuery.now();
1176
-
1177
- // Make sure that the execution of code works by injecting a script
1178
- // tag with appendChild/createTextNode
1179
- // (IE doesn't support this, fails, and uses .text instead)
1180
- try {
1181
- script.appendChild( document.createTextNode( "window." + id + "=1;" ) );
1182
- } catch(e) {}
1183
-
1184
- root.insertBefore( script, root.firstChild );
1185
-
1186
- if ( window[ id ] ) {
1187
- _scriptEval = true;
1188
- delete window[ id ];
1189
- } else {
1190
- _scriptEval = false;
1191
- }
1192
-
1193
- root.removeChild( script );
1194
- }
1195
-
1196
- return _scriptEval;
1197
- };
1232
+ support.optDisabled = !opt.disabled;
1198
1233
 
1199
1234
  // Test to see if it's possible to delete an expando from an element
1200
1235
  // Fails in Internet Explorer
1201
1236
  try {
1202
1237
  delete div.test;
1203
-
1204
- } catch(e) {
1205
- jQuery.support.deleteExpando = false;
1238
+ } catch( e ) {
1239
+ support.deleteExpando = false;
1206
1240
  }
1207
1241
 
1208
1242
  if ( !div.addEventListener && div.attachEvent && div.fireEvent ) {
1209
- div.attachEvent("onclick", function click() {
1243
+ div.attachEvent( "onclick", function click() {
1210
1244
  // Cloning a node shouldn't copy over any
1211
1245
  // bound event handlers (IE does this)
1212
- jQuery.support.noCloneEvent = false;
1213
- div.detachEvent("onclick", click);
1246
+ support.noCloneEvent = false;
1247
+ div.detachEvent( "onclick", click );
1214
1248
  });
1215
- div.cloneNode(true).fireEvent("onclick");
1249
+ div.cloneNode( true ).fireEvent( "onclick" );
1216
1250
  }
1217
1251
 
1218
- div = document.createElement("div");
1219
- div.innerHTML = "<input type='radio' name='radiotest' checked='checked'/>";
1252
+ // Check if a radio maintains it's value
1253
+ // after being appended to the DOM
1254
+ input = document.createElement("input");
1255
+ input.value = "t";
1256
+ input.setAttribute("type", "radio");
1257
+ support.radioValue = input.value === "t";
1220
1258
 
1221
- var fragment = document.createDocumentFragment();
1259
+ input.setAttribute("checked", "checked");
1260
+ div.appendChild( input );
1261
+ fragment = document.createDocumentFragment();
1222
1262
  fragment.appendChild( div.firstChild );
1223
1263
 
1224
1264
  // WebKit doesn't clone checked state correctly in fragments
1225
- jQuery.support.checkClone = fragment.cloneNode(true).cloneNode(true).lastChild.checked;
1265
+ support.checkClone = fragment.cloneNode( true ).cloneNode( true ).lastChild.checked;
1266
+
1267
+ div.innerHTML = "";
1226
1268
 
1227
1269
  // Figure out if the W3C box model works as expected
1228
- // document.body must exist before we can do this
1229
- jQuery(function() {
1230
- var div = document.createElement("div"),
1231
- body = document.getElementsByTagName("body")[0];
1270
+ div.style.width = div.style.paddingLeft = "1px";
1271
+
1272
+ // We use our own, invisible, body
1273
+ body = document.createElement( "body" );
1274
+ bodyStyle = {
1275
+ visibility: "hidden",
1276
+ width: 0,
1277
+ height: 0,
1278
+ border: 0,
1279
+ margin: 0,
1280
+ // Set background to avoid IE crashes when removing (#9028)
1281
+ background: "none"
1282
+ };
1283
+ for ( i in bodyStyle ) {
1284
+ body.style[ i ] = bodyStyle[ i ];
1285
+ }
1286
+ body.appendChild( div );
1287
+ document.documentElement.appendChild( body );
1288
+
1289
+ // Check if a disconnected checkbox will retain its checked
1290
+ // value of true after appended to the DOM (IE6/7)
1291
+ support.appendChecked = input.checked;
1292
+
1293
+ support.boxModel = div.offsetWidth === 2;
1294
+
1295
+ if ( "zoom" in div.style ) {
1296
+ // Check if natively block-level elements act like inline-block
1297
+ // elements when setting their display to 'inline' and giving
1298
+ // them layout
1299
+ // (IE < 8 does this)
1300
+ div.style.display = "inline";
1301
+ div.style.zoom = 1;
1302
+ support.inlineBlockNeedsLayout = ( div.offsetWidth === 2 );
1303
+
1304
+ // Check if elements with layout shrink-wrap their children
1305
+ // (IE 6 does this)
1306
+ div.style.display = "";
1307
+ div.innerHTML = "<div style='width:4px;'></div>";
1308
+ support.shrinkWrapBlocks = ( div.offsetWidth !== 2 );
1309
+ }
1232
1310
 
1233
- // Frameset documents with no body should not run this code
1234
- if ( !body ) {
1235
- return;
1236
- }
1311
+ div.innerHTML = "<table><tr><td style='padding:0;border:0;display:none'></td><td>t</td></tr></table>";
1312
+ tds = div.getElementsByTagName( "td" );
1313
+
1314
+ // Check if table cells still have offsetWidth/Height when they are set
1315
+ // to display:none and there are still other visible table cells in a
1316
+ // table row; if so, offsetWidth/Height are not reliable for use when
1317
+ // determining if an element has been hidden directly using
1318
+ // display:none (it is still safe to use offsets if a parent element is
1319
+ // hidden; don safety goggles and see bug #4512 for more information).
1320
+ // (only IE 8 fails this test)
1321
+ isSupported = ( tds[ 0 ].offsetHeight === 0 );
1322
+
1323
+ tds[ 0 ].style.display = "";
1324
+ tds[ 1 ].style.display = "none";
1325
+
1326
+ // Check if empty table cells still have offsetWidth/Height
1327
+ // (IE < 8 fail this test)
1328
+ support.reliableHiddenOffsets = isSupported && ( tds[ 0 ].offsetHeight === 0 );
1329
+ div.innerHTML = "";
1330
+
1331
+ // Check if div with explicit width and no margin-right incorrectly
1332
+ // gets computed margin-right based on width of container. For more
1333
+ // info see bug #3333
1334
+ // Fails in WebKit before Feb 2011 nightlies
1335
+ // WebKit Bug 13343 - getComputedStyle returns wrong value for margin-right
1336
+ if ( document.defaultView && document.defaultView.getComputedStyle ) {
1337
+ marginDiv = document.createElement( "div" );
1338
+ marginDiv.style.width = "0";
1339
+ marginDiv.style.marginRight = "0";
1340
+ div.appendChild( marginDiv );
1341
+ support.reliableMarginRight =
1342
+ ( parseInt( document.defaultView.getComputedStyle( marginDiv, null ).marginRight, 10 ) || 0 ) === 0;
1343
+ }
1237
1344
 
1238
- div.style.width = div.style.paddingLeft = "1px";
1239
- body.appendChild( div );
1240
- jQuery.boxModel = jQuery.support.boxModel = div.offsetWidth === 2;
1241
-
1242
- if ( "zoom" in div.style ) {
1243
- // Check if natively block-level elements act like inline-block
1244
- // elements when setting their display to 'inline' and giving
1245
- // them layout
1246
- // (IE < 8 does this)
1247
- div.style.display = "inline";
1248
- div.style.zoom = 1;
1249
- jQuery.support.inlineBlockNeedsLayout = div.offsetWidth === 2;
1250
-
1251
- // Check if elements with layout shrink-wrap their children
1252
- // (IE 6 does this)
1253
- div.style.display = "";
1254
- div.innerHTML = "<div style='width:4px;'></div>";
1255
- jQuery.support.shrinkWrapBlocks = div.offsetWidth !== 2;
1256
- }
1257
-
1258
- div.innerHTML = "<table><tr><td style='padding:0;border:0;display:none'></td><td>t</td></tr></table>";
1259
- var tds = div.getElementsByTagName("td");
1260
-
1261
- // Check if table cells still have offsetWidth/Height when they are set
1262
- // to display:none and there are still other visible table cells in a
1263
- // table row; if so, offsetWidth/Height are not reliable for use when
1264
- // determining if an element has been hidden directly using
1265
- // display:none (it is still safe to use offsets if a parent element is
1266
- // hidden; don safety goggles and see bug #4512 for more information).
1267
- // (only IE 8 fails this test)
1268
- jQuery.support.reliableHiddenOffsets = tds[0].offsetHeight === 0;
1269
-
1270
- tds[0].style.display = "";
1271
- tds[1].style.display = "none";
1272
-
1273
- // Check if empty table cells still have offsetWidth/Height
1274
- // (IE < 8 fail this test)
1275
- jQuery.support.reliableHiddenOffsets = jQuery.support.reliableHiddenOffsets && tds[0].offsetHeight === 0;
1276
- div.innerHTML = "";
1277
-
1278
- // Check if div with explicit width and no margin-right incorrectly
1279
- // gets computed margin-right based on width of container. For more
1280
- // info see bug #3333
1281
- // Fails in WebKit before Feb 2011 nightlies
1282
- // WebKit Bug 13343 - getComputedStyle returns wrong value for margin-right
1283
- if ( document.defaultView && document.defaultView.getComputedStyle ) {
1284
- div.style.width = "1px";
1285
- div.style.marginRight = "0";
1286
- jQuery.support.reliableMarginRight = ( parseInt(document.defaultView.getComputedStyle(div, null).marginRight, 10) || 0 ) === 0;
1287
- }
1288
-
1289
- body.removeChild( div ).style.display = "none";
1290
- div = tds = null;
1291
- });
1345
+ // Remove the body element we added
1346
+ body.innerHTML = "";
1347
+ document.documentElement.removeChild( body );
1292
1348
 
1293
1349
  // Technique from Juriy Zaytsev
1294
1350
  // http://thinkweb2.com/projects/prototype/detecting-event-support-without-browser-sniffing/
1295
- var eventSupported = function( eventName ) {
1296
- var el = document.createElement("div");
1297
- eventName = "on" + eventName;
1298
-
1299
- // We only care about the case where non-standard event systems
1300
- // are used, namely in IE. Short-circuiting here helps us to
1301
- // avoid an eval call (in setAttribute) which can cause CSP
1302
- // to go haywire. See: https://developer.mozilla.org/en/Security/CSP
1303
- if ( !el.attachEvent ) {
1304
- return true;
1351
+ // We only care about the case where non-standard event systems
1352
+ // are used, namely in IE. Short-circuiting here helps us to
1353
+ // avoid an eval call (in setAttribute) which can cause CSP
1354
+ // to go haywire. See: https://developer.mozilla.org/en/Security/CSP
1355
+ if ( div.attachEvent ) {
1356
+ for( i in {
1357
+ submit: 1,
1358
+ change: 1,
1359
+ focusin: 1
1360
+ } ) {
1361
+ eventName = "on" + i;
1362
+ isSupported = ( eventName in div );
1363
+ if ( !isSupported ) {
1364
+ div.setAttribute( eventName, "return;" );
1365
+ isSupported = ( typeof div[ eventName ] === "function" );
1366
+ }
1367
+ support[ i + "Bubbles" ] = isSupported;
1305
1368
  }
1369
+ }
1306
1370
 
1307
- var isSupported = (eventName in el);
1308
- if ( !isSupported ) {
1309
- el.setAttribute(eventName, "return;");
1310
- isSupported = typeof el[eventName] === "function";
1311
- }
1312
- return isSupported;
1313
- };
1371
+ return support;
1372
+ })();
1314
1373
 
1315
- jQuery.support.submitBubbles = eventSupported("submit");
1316
- jQuery.support.changeBubbles = eventSupported("change");
1374
+ // Keep track of boxModel
1375
+ jQuery.boxModel = jQuery.support.boxModel;
1317
1376
 
1318
- // release memory in IE
1319
- div = all = a = null;
1320
- })();
1321
1377
 
1322
1378
 
1323
1379
 
1324
- var rbrace = /^(?:\{.*\}|\[.*\])$/;
1380
+ var rbrace = /^(?:\{.*\}|\[.*\])$/,
1381
+ rmultiDash = /([a-z])([A-Z])/g;
1325
1382
 
1326
1383
  jQuery.extend({
1327
1384
  cache: {},
@@ -1544,12 +1601,13 @@ jQuery.fn.extend({
1544
1601
  data = jQuery.data( this[0] );
1545
1602
 
1546
1603
  if ( this[0].nodeType === 1 ) {
1547
- var attr = this[0].attributes, name;
1604
+ var attr = this[0].attributes, name;
1548
1605
  for ( var i = 0, l = attr.length; i < l; i++ ) {
1549
1606
  name = attr[i].name;
1550
1607
 
1551
1608
  if ( name.indexOf( "data-" ) === 0 ) {
1552
- name = name.substr( 5 );
1609
+ name = jQuery.camelCase( name.substring(5) );
1610
+
1553
1611
  dataAttr( this[0], name, data[ name ] );
1554
1612
  }
1555
1613
  }
@@ -1603,7 +1661,9 @@ function dataAttr( elem, key, data ) {
1603
1661
  // If nothing was found internally, try to fetch any
1604
1662
  // data from the HTML5 data-* attribute
1605
1663
  if ( data === undefined && elem.nodeType === 1 ) {
1606
- data = elem.getAttribute( "data-" + key );
1664
+ name = "data-" + key.replace( rmultiDash, "$1-$2" ).toLowerCase();
1665
+
1666
+ data = elem.getAttribute( name );
1607
1667
 
1608
1668
  if ( typeof data === "string" ) {
1609
1669
  try {
@@ -1642,35 +1702,76 @@ function isEmptyDataObject( obj ) {
1642
1702
 
1643
1703
 
1644
1704
 
1645
- jQuery.extend({
1646
- queue: function( elem, type, data ) {
1647
- if ( !elem ) {
1648
- return;
1649
- }
1705
+ function handleQueueMarkDefer( elem, type, src ) {
1706
+ var deferDataKey = type + "defer",
1707
+ queueDataKey = type + "queue",
1708
+ markDataKey = type + "mark",
1709
+ defer = jQuery.data( elem, deferDataKey, undefined, true );
1710
+ if ( defer &&
1711
+ ( src === "queue" || !jQuery.data( elem, queueDataKey, undefined, true ) ) &&
1712
+ ( src === "mark" || !jQuery.data( elem, markDataKey, undefined, true ) ) ) {
1713
+ // Give room for hard-coded callbacks to fire first
1714
+ // and eventually mark/queue something else on the element
1715
+ setTimeout( function() {
1716
+ if ( !jQuery.data( elem, queueDataKey, undefined, true ) &&
1717
+ !jQuery.data( elem, markDataKey, undefined, true ) ) {
1718
+ jQuery.removeData( elem, deferDataKey, true );
1719
+ defer.resolve();
1720
+ }
1721
+ }, 0 );
1722
+ }
1723
+ }
1650
1724
 
1651
- type = (type || "fx") + "queue";
1652
- var q = jQuery._data( elem, type );
1725
+ jQuery.extend({
1653
1726
 
1654
- // Speed up dequeue by getting out quickly if this is just a lookup
1655
- if ( !data ) {
1656
- return q || [];
1727
+ _mark: function( elem, type ) {
1728
+ if ( elem ) {
1729
+ type = (type || "fx") + "mark";
1730
+ jQuery.data( elem, type, (jQuery.data(elem,type,undefined,true) || 0) + 1, true );
1657
1731
  }
1732
+ },
1658
1733
 
1659
- if ( !q || jQuery.isArray(data) ) {
1660
- q = jQuery._data( elem, type, jQuery.makeArray(data) );
1661
-
1662
- } else {
1663
- q.push( data );
1734
+ _unmark: function( force, elem, type ) {
1735
+ if ( force !== true ) {
1736
+ type = elem;
1737
+ elem = force;
1738
+ force = false;
1739
+ }
1740
+ if ( elem ) {
1741
+ type = type || "fx";
1742
+ var key = type + "mark",
1743
+ count = force ? 0 : ( (jQuery.data( elem, key, undefined, true) || 1 ) - 1 );
1744
+ if ( count ) {
1745
+ jQuery.data( elem, key, count, true );
1746
+ } else {
1747
+ jQuery.removeData( elem, key, true );
1748
+ handleQueueMarkDefer( elem, type, "mark" );
1749
+ }
1664
1750
  }
1751
+ },
1665
1752
 
1666
- return q;
1753
+ queue: function( elem, type, data ) {
1754
+ if ( elem ) {
1755
+ type = (type || "fx") + "queue";
1756
+ var q = jQuery.data( elem, type, undefined, true );
1757
+ // Speed up dequeue by getting out quickly if this is just a lookup
1758
+ if ( data ) {
1759
+ if ( !q || jQuery.isArray(data) ) {
1760
+ q = jQuery.data( elem, type, jQuery.makeArray(data), true );
1761
+ } else {
1762
+ q.push( data );
1763
+ }
1764
+ }
1765
+ return q || [];
1766
+ }
1667
1767
  },
1668
1768
 
1669
1769
  dequeue: function( elem, type ) {
1670
1770
  type = type || "fx";
1671
1771
 
1672
1772
  var queue = jQuery.queue( elem, type ),
1673
- fn = queue.shift();
1773
+ fn = queue.shift(),
1774
+ defer;
1674
1775
 
1675
1776
  // If the fx queue is dequeued, always remove the progress sentinel
1676
1777
  if ( fn === "inprogress" ) {
@@ -1691,6 +1792,7 @@ jQuery.extend({
1691
1792
 
1692
1793
  if ( !queue.length ) {
1693
1794
  jQuery.removeData( elem, type + "queue", true );
1795
+ handleQueueMarkDefer( elem, type, "queue" );
1694
1796
  }
1695
1797
  }
1696
1798
  });
@@ -1705,7 +1807,7 @@ jQuery.fn.extend({
1705
1807
  if ( data === undefined ) {
1706
1808
  return jQuery.queue( this[0], type );
1707
1809
  }
1708
- return this.each(function( i ) {
1810
+ return this.each(function() {
1709
1811
  var queue = jQuery.queue( this, type, data );
1710
1812
 
1711
1813
  if ( type === "fx" && queue[0] !== "inprogress" ) {
@@ -1718,7 +1820,6 @@ jQuery.fn.extend({
1718
1820
  jQuery.dequeue( this, type );
1719
1821
  });
1720
1822
  },
1721
-
1722
1823
  // Based off of the plugin by Clint Helfers, with permission.
1723
1824
  // http://blindsignals.com/index.php/2009/07/jquery-delay/
1724
1825
  delay: function( time, type ) {
@@ -1732,9 +1833,40 @@ jQuery.fn.extend({
1732
1833
  }, time );
1733
1834
  });
1734
1835
  },
1735
-
1736
1836
  clearQueue: function( type ) {
1737
1837
  return this.queue( type || "fx", [] );
1838
+ },
1839
+ // Get a promise resolved when queues of a certain type
1840
+ // are emptied (fx is the type by default)
1841
+ promise: function( type, object ) {
1842
+ if ( typeof type !== "string" ) {
1843
+ object = type;
1844
+ type = undefined;
1845
+ }
1846
+ type = type || "fx";
1847
+ var defer = jQuery.Deferred(),
1848
+ elements = this,
1849
+ i = elements.length,
1850
+ count = 1,
1851
+ deferDataKey = type + "defer",
1852
+ queueDataKey = type + "queue",
1853
+ markDataKey = type + "mark";
1854
+ function resolve() {
1855
+ if ( !( --count ) ) {
1856
+ defer.resolveWith( elements, [ elements ] );
1857
+ }
1858
+ }
1859
+ while( i-- ) {
1860
+ if (( tmp = jQuery.data( elements[ i ], deferDataKey, undefined, true ) ||
1861
+ ( jQuery.data( elements[ i ], queueDataKey, undefined, true ) ||
1862
+ jQuery.data( elements[ i ], markDataKey, undefined, true ) ) &&
1863
+ jQuery.data( elements[ i ], deferDataKey, jQuery._Deferred(), true ) )) {
1864
+ count++;
1865
+ tmp.done( resolve );
1866
+ }
1867
+ }
1868
+ resolve();
1869
+ return defer.promise();
1738
1870
  }
1739
1871
  });
1740
1872
 
@@ -1742,51 +1874,50 @@ jQuery.fn.extend({
1742
1874
 
1743
1875
 
1744
1876
  var rclass = /[\n\t\r]/g,
1745
- rspaces = /\s+/,
1877
+ rspace = /\s+/,
1746
1878
  rreturn = /\r/g,
1747
- rspecialurl = /^(?:href|src|style)$/,
1748
1879
  rtype = /^(?:button|input)$/i,
1749
1880
  rfocusable = /^(?:button|input|object|select|textarea)$/i,
1750
1881
  rclickable = /^a(?:rea)?$/i,
1751
- rradiocheck = /^(?:radio|checkbox)$/i;
1752
-
1753
- jQuery.props = {
1754
- "for": "htmlFor",
1755
- "class": "className",
1756
- readonly: "readOnly",
1757
- maxlength: "maxLength",
1758
- cellspacing: "cellSpacing",
1759
- rowspan: "rowSpan",
1760
- colspan: "colSpan",
1761
- tabindex: "tabIndex",
1762
- usemap: "useMap",
1763
- frameborder: "frameBorder"
1764
- };
1882
+ rspecial = /^(?:data-|aria-)/,
1883
+ rinvalidChar = /\:/,
1884
+ formHook;
1765
1885
 
1766
1886
  jQuery.fn.extend({
1767
1887
  attr: function( name, value ) {
1768
1888
  return jQuery.access( this, name, value, true, jQuery.attr );
1769
1889
  },
1770
1890
 
1771
- removeAttr: function( name, fn ) {
1772
- return this.each(function(){
1773
- jQuery.attr( this, name, "" );
1774
- if ( this.nodeType === 1 ) {
1775
- this.removeAttribute( name );
1776
- }
1891
+ removeAttr: function( name ) {
1892
+ return this.each(function() {
1893
+ jQuery.removeAttr( this, name );
1894
+ });
1895
+ },
1896
+
1897
+ prop: function( name, value ) {
1898
+ return jQuery.access( this, name, value, true, jQuery.prop );
1899
+ },
1900
+
1901
+ removeProp: function( name ) {
1902
+ return this.each(function() {
1903
+ // try/catch handles cases where IE balks (such as removing a property on window)
1904
+ try {
1905
+ this[ name ] = undefined;
1906
+ delete this[ name ];
1907
+ } catch( e ) {}
1777
1908
  });
1778
1909
  },
1779
1910
 
1780
1911
  addClass: function( value ) {
1781
- if ( jQuery.isFunction(value) ) {
1912
+ if ( jQuery.isFunction( value ) ) {
1782
1913
  return this.each(function(i) {
1783
1914
  var self = jQuery(this);
1784
- self.addClass( value.call(this, i, self.attr("class")) );
1915
+ self.addClass( value.call(this, i, self.attr("class") || "") );
1785
1916
  });
1786
1917
  }
1787
1918
 
1788
1919
  if ( value && typeof value === "string" ) {
1789
- var classNames = (value || "").split( rspaces );
1920
+ var classNames = (value || "").split( rspace );
1790
1921
 
1791
1922
  for ( var i = 0, l = this.length; i < l; i++ ) {
1792
1923
  var elem = this[i];
@@ -1822,7 +1953,7 @@ jQuery.fn.extend({
1822
1953
  }
1823
1954
 
1824
1955
  if ( (value && typeof value === "string") || value === undefined ) {
1825
- var classNames = (value || "").split( rspaces );
1956
+ var classNames = (value || "").split( rspace );
1826
1957
 
1827
1958
  for ( var i = 0, l = this.length; i < l; i++ ) {
1828
1959
  var elem = this[i];
@@ -1863,7 +1994,7 @@ jQuery.fn.extend({
1863
1994
  i = 0,
1864
1995
  self = jQuery( this ),
1865
1996
  state = stateVal,
1866
- classNames = value.split( rspaces );
1997
+ classNames = value.split( rspace );
1867
1998
 
1868
1999
  while ( (className = classNames[ i++ ]) ) {
1869
2000
  // check each className given, space seperated list
@@ -1895,82 +2026,36 @@ jQuery.fn.extend({
1895
2026
  },
1896
2027
 
1897
2028
  val: function( value ) {
2029
+ var hooks, ret,
2030
+ elem = this[0];
2031
+
1898
2032
  if ( !arguments.length ) {
1899
- var elem = this[0];
1900
-
1901
2033
  if ( elem ) {
1902
- if ( jQuery.nodeName( elem, "option" ) ) {
1903
- // attributes.value is undefined in Blackberry 4.7 but
1904
- // uses .value. See #6932
1905
- var val = elem.attributes.value;
1906
- return !val || val.specified ? elem.value : elem.text;
1907
- }
1908
-
1909
- // We need to handle select boxes special
1910
- if ( jQuery.nodeName( elem, "select" ) ) {
1911
- var index = elem.selectedIndex,
1912
- values = [],
1913
- options = elem.options,
1914
- one = elem.type === "select-one";
1915
-
1916
- // Nothing was selected
1917
- if ( index < 0 ) {
1918
- return null;
1919
- }
1920
-
1921
- // Loop through all the selected options
1922
- for ( var i = one ? index : 0, max = one ? index + 1 : options.length; i < max; i++ ) {
1923
- var option = options[ i ];
1924
-
1925
- // Don't return options that are disabled or in a disabled optgroup
1926
- if ( option.selected && (jQuery.support.optDisabled ? !option.disabled : option.getAttribute("disabled") === null) &&
1927
- (!option.parentNode.disabled || !jQuery.nodeName( option.parentNode, "optgroup" )) ) {
2034
+ hooks = jQuery.valHooks[ elem.nodeName.toLowerCase() ] || jQuery.valHooks[ elem.type ];
1928
2035
 
1929
- // Get the specific value for the option
1930
- value = jQuery(option).val();
1931
-
1932
- // We don't need an array for one selects
1933
- if ( one ) {
1934
- return value;
1935
- }
1936
-
1937
- // Multi-Selects return an array
1938
- values.push( value );
1939
- }
1940
- }
1941
-
1942
- // Fixes Bug #2551 -- select.val() broken in IE after form.reset()
1943
- if ( one && !values.length && options.length ) {
1944
- return jQuery( options[ index ] ).val();
1945
- }
1946
-
1947
- return values;
2036
+ if ( hooks && "get" in hooks && (ret = hooks.get( elem, "value" )) !== undefined ) {
2037
+ return ret;
1948
2038
  }
1949
2039
 
1950
- // Handle the case where in Webkit "" is returned instead of "on" if a value isn't specified
1951
- if ( rradiocheck.test( elem.type ) && !jQuery.support.checkOn ) {
1952
- return elem.getAttribute("value") === null ? "on" : elem.value;
1953
- }
1954
-
1955
- // Everything else, we just grab the value
1956
2040
  return (elem.value || "").replace(rreturn, "");
1957
-
1958
2041
  }
1959
2042
 
1960
2043
  return undefined;
1961
2044
  }
1962
2045
 
1963
- var isFunction = jQuery.isFunction(value);
2046
+ var isFunction = jQuery.isFunction( value );
1964
2047
 
1965
- return this.each(function(i) {
1966
- var self = jQuery(this), val = value;
2048
+ return this.each(function( i ) {
2049
+ var self = jQuery(this), val;
1967
2050
 
1968
2051
  if ( this.nodeType !== 1 ) {
1969
2052
  return;
1970
2053
  }
1971
2054
 
1972
2055
  if ( isFunction ) {
1973
- val = value.call(this, i, self.val());
2056
+ val = value.call( this, i, self.val() );
2057
+ } else {
2058
+ val = value;
1974
2059
  }
1975
2060
 
1976
2061
  // Treat null/undefined as ""; convert numbers to string
@@ -1978,34 +2063,88 @@ jQuery.fn.extend({
1978
2063
  val = "";
1979
2064
  } else if ( typeof val === "number" ) {
1980
2065
  val += "";
1981
- } else if ( jQuery.isArray(val) ) {
1982
- val = jQuery.map(val, function (value) {
2066
+ } else if ( jQuery.isArray( val ) ) {
2067
+ val = jQuery.map(val, function ( value ) {
1983
2068
  return value == null ? "" : value + "";
1984
2069
  });
1985
2070
  }
1986
2071
 
1987
- if ( jQuery.isArray(val) && rradiocheck.test( this.type ) ) {
1988
- this.checked = jQuery.inArray( self.val(), val ) >= 0;
2072
+ hooks = jQuery.valHooks[ this.nodeName.toLowerCase() ] || jQuery.valHooks[ this.type ];
2073
+
2074
+ // If set returns undefined, fall back to normal setting
2075
+ if ( !hooks || ("set" in hooks && hooks.set( this, val, "value" ) === undefined) ) {
2076
+ this.value = val;
2077
+ }
2078
+ });
2079
+ }
2080
+ });
2081
+
2082
+ jQuery.extend({
2083
+ valHooks: {
2084
+ option: {
2085
+ get: function( elem ) {
2086
+ // attributes.value is undefined in Blackberry 4.7 but
2087
+ // uses .value. See #6932
2088
+ var val = elem.attributes.value;
2089
+ return !val || val.specified ? elem.value : elem.text;
2090
+ }
2091
+ },
2092
+ select: {
2093
+ get: function( elem ) {
2094
+ var index = elem.selectedIndex,
2095
+ values = [],
2096
+ options = elem.options,
2097
+ one = elem.type === "select-one";
2098
+
2099
+ // Nothing was selected
2100
+ if ( index < 0 ) {
2101
+ return null;
2102
+ }
2103
+
2104
+ // Loop through all the selected options
2105
+ for ( var i = one ? index : 0, max = one ? index + 1 : options.length; i < max; i++ ) {
2106
+ var option = options[ i ];
2107
+
2108
+ // Don't return options that are disabled or in a disabled optgroup
2109
+ if ( option.selected && (jQuery.support.optDisabled ? !option.disabled : option.getAttribute("disabled") === null) &&
2110
+ (!option.parentNode.disabled || !jQuery.nodeName( option.parentNode, "optgroup" )) ) {
1989
2111
 
1990
- } else if ( jQuery.nodeName( this, "select" ) ) {
1991
- var values = jQuery.makeArray(val);
2112
+ // Get the specific value for the option
2113
+ value = jQuery( option ).val();
1992
2114
 
1993
- jQuery( "option", this ).each(function() {
2115
+ // We don't need an array for one selects
2116
+ if ( one ) {
2117
+ return value;
2118
+ }
2119
+
2120
+ // Multi-Selects return an array
2121
+ values.push( value );
2122
+ }
2123
+ }
2124
+
2125
+ // Fixes Bug #2551 -- select.val() broken in IE after form.reset()
2126
+ if ( one && !values.length && options.length ) {
2127
+ return jQuery( options[ index ] ).val();
2128
+ }
2129
+
2130
+ return values;
2131
+ },
2132
+
2133
+ set: function( elem, value ) {
2134
+ var values = jQuery.makeArray( value );
2135
+
2136
+ jQuery(elem).find("option").each(function() {
1994
2137
  this.selected = jQuery.inArray( jQuery(this).val(), values ) >= 0;
1995
2138
  });
1996
2139
 
1997
2140
  if ( !values.length ) {
1998
- this.selectedIndex = -1;
2141
+ elem.selectedIndex = -1;
1999
2142
  }
2000
-
2001
- } else {
2002
- this.value = val;
2143
+ return values;
2003
2144
  }
2004
- });
2005
- }
2006
- });
2145
+ }
2146
+ },
2007
2147
 
2008
- jQuery.extend({
2009
2148
  attrFn: {
2010
2149
  val: true,
2011
2150
  css: true,
@@ -2016,124 +2155,288 @@ jQuery.extend({
2016
2155
  height: true,
2017
2156
  offset: true
2018
2157
  },
2019
-
2158
+
2159
+ attrFix: {
2160
+ // Always normalize to ensure hook usage
2161
+ tabindex: "tabIndex",
2162
+ readonly: "readOnly"
2163
+ },
2164
+
2020
2165
  attr: function( elem, name, value, pass ) {
2166
+ var nType = elem.nodeType;
2167
+
2021
2168
  // don't get/set attributes on text, comment and attribute nodes
2022
- if ( !elem || elem.nodeType === 3 || elem.nodeType === 8 || elem.nodeType === 2 ) {
2169
+ if ( !elem || nType === 3 || nType === 8 || nType === 2 ) {
2023
2170
  return undefined;
2024
2171
  }
2025
2172
 
2026
2173
  if ( pass && name in jQuery.attrFn ) {
2027
- return jQuery(elem)[name](value);
2174
+ return jQuery( elem )[ name ]( value );
2028
2175
  }
2176
+
2177
+ var ret, hooks,
2178
+ notxml = nType !== 1 || !jQuery.isXMLDoc( elem );
2179
+
2180
+ // Normalize the name if needed
2181
+ name = notxml && jQuery.attrFix[ name ] || name;
2029
2182
 
2030
- var notxml = elem.nodeType !== 1 || !jQuery.isXMLDoc( elem ),
2031
- // Whether we are setting (or getting)
2032
- set = value !== undefined;
2183
+ // Get the appropriate hook, or the formHook
2184
+ // if getSetAttribute is not supported and we have form objects in IE6/7
2185
+ hooks = jQuery.attrHooks[ name ] ||
2186
+ ( formHook && (jQuery.nodeName( elem, "form" ) || rinvalidChar.test( name )) ?
2187
+ formHook :
2188
+ undefined );
2033
2189
 
2034
- // Try to normalize/fix the name
2035
- name = notxml && jQuery.props[ name ] || name;
2190
+ if ( value !== undefined ) {
2036
2191
 
2037
- // Only do all the following if this is a node (faster for style)
2038
- if ( elem.nodeType === 1 ) {
2039
- // These attributes require special treatment
2040
- var special = rspecialurl.test( name );
2041
-
2042
- // Safari mis-reports the default selected property of an option
2043
- // Accessing the parent's selectedIndex property fixes it
2044
- if ( name === "selected" && !jQuery.support.optSelected ) {
2045
- var parent = elem.parentNode;
2046
- if ( parent ) {
2047
- parent.selectedIndex;
2048
-
2049
- // Make sure that it also works with optgroups, see #5701
2050
- if ( parent.parentNode ) {
2051
- parent.parentNode.selectedIndex;
2052
- }
2192
+ if ( value === null || (value === false && !rspecial.test( name )) ) {
2193
+ jQuery.removeAttr( elem, name );
2194
+ return undefined;
2195
+
2196
+ } else if ( hooks && "set" in hooks && notxml && (ret = hooks.set( elem, value, name )) !== undefined ) {
2197
+ return ret;
2198
+
2199
+ } else {
2200
+
2201
+ // Set boolean attributes to the same name
2202
+ if ( value === true && !rspecial.test( name ) ) {
2203
+ value = name;
2053
2204
  }
2205
+
2206
+ elem.setAttribute( name, "" + value );
2207
+ return value;
2054
2208
  }
2055
2209
 
2056
- // If applicable, access the attribute via the DOM 0 way
2057
- // 'in' checks fail in Blackberry 4.7 #6931
2058
- if ( (name in elem || elem[ name ] !== undefined) && notxml && !special ) {
2059
- if ( set ) {
2060
- // We can't allow the type property to be changed (since it causes problems in IE)
2061
- if ( name === "type" && rtype.test( elem.nodeName ) && elem.parentNode ) {
2062
- jQuery.error( "type property can't be changed" );
2063
- }
2210
+ } else {
2064
2211
 
2065
- if ( value === null ) {
2066
- if ( elem.nodeType === 1 ) {
2067
- elem.removeAttribute( name );
2068
- }
2212
+ if ( hooks && "get" in hooks && notxml ) {
2213
+ return hooks.get( elem, name );
2069
2214
 
2070
- } else {
2071
- elem[ name ] = value;
2072
- }
2073
- }
2215
+ } else {
2074
2216
 
2075
- // browsers index elements by id/name on forms, give priority to attributes.
2076
- if ( jQuery.nodeName( elem, "form" ) && elem.getAttributeNode(name) ) {
2077
- return elem.getAttributeNode( name ).nodeValue;
2078
- }
2217
+ ret = elem.getAttribute( name );
2079
2218
 
2219
+ // Non-existent attributes return null, we normalize to undefined
2220
+ return ret === null ?
2221
+ undefined :
2222
+ ret;
2223
+ }
2224
+ }
2225
+ },
2226
+
2227
+ removeAttr: function( elem, name ) {
2228
+ if ( elem.nodeType === 1 ) {
2229
+ name = jQuery.attrFix[ name ] || name;
2230
+
2231
+ if ( jQuery.support.getSetAttribute ) {
2232
+ // Use removeAttribute in browsers that support it
2233
+ elem.removeAttribute( name );
2234
+ } else {
2235
+ jQuery.attr( elem, name, "" );
2236
+ elem.removeAttributeNode( elem.getAttributeNode( name ) );
2237
+ }
2238
+ }
2239
+ },
2240
+
2241
+ attrHooks: {
2242
+ type: {
2243
+ set: function( elem, value ) {
2244
+ // We can't allow the type property to be changed (since it causes problems in IE)
2245
+ if ( rtype.test( elem.nodeName ) && elem.parentNode ) {
2246
+ jQuery.error( "type property can't be changed" );
2247
+ } else if ( !jQuery.support.radioValue && value === "radio" && jQuery.nodeName(elem, "input") ) {
2248
+ // Setting the type on a radio button after the value resets the value in IE6-9
2249
+ // Reset value to it's default in case type is set after value
2250
+ // This is for element creation
2251
+ var val = elem.getAttribute("value");
2252
+ elem.setAttribute( "type", value );
2253
+ if ( val ) {
2254
+ elem.value = val;
2255
+ }
2256
+ return value;
2257
+ }
2258
+ }
2259
+ },
2260
+ tabIndex: {
2261
+ get: function( elem ) {
2080
2262
  // elem.tabIndex doesn't always return the correct value when it hasn't been explicitly set
2081
2263
  // http://fluidproject.org/blog/2008/01/09/getting-setting-and-removing-tabindex-values-with-javascript/
2082
- if ( name === "tabIndex" ) {
2083
- var attributeNode = elem.getAttributeNode( "tabIndex" );
2084
-
2085
- return attributeNode && attributeNode.specified ?
2086
- attributeNode.value :
2087
- rfocusable.test( elem.nodeName ) || rclickable.test( elem.nodeName ) && elem.href ?
2088
- 0 :
2089
- undefined;
2090
- }
2264
+ var attributeNode = elem.getAttributeNode("tabIndex");
2091
2265
 
2266
+ return attributeNode && attributeNode.specified ?
2267
+ parseInt( attributeNode.value, 10 ) :
2268
+ rfocusable.test( elem.nodeName ) || rclickable.test( elem.nodeName ) && elem.href ?
2269
+ 0 :
2270
+ undefined;
2271
+ }
2272
+ }
2273
+ },
2274
+
2275
+ propFix: {},
2276
+
2277
+ prop: function( elem, name, value ) {
2278
+ var nType = elem.nodeType;
2279
+
2280
+ // don't get/set properties on text, comment and attribute nodes
2281
+ if ( !elem || nType === 3 || nType === 8 || nType === 2 ) {
2282
+ return undefined;
2283
+ }
2284
+
2285
+ var ret, hooks,
2286
+ notxml = nType !== 1 || !jQuery.isXMLDoc( elem );
2287
+
2288
+ // Try to normalize/fix the name
2289
+ name = notxml && jQuery.propFix[ name ] || name;
2290
+
2291
+ hooks = jQuery.propHooks[ name ];
2292
+
2293
+ if ( value !== undefined ) {
2294
+ if ( hooks && "set" in hooks && (ret = hooks.set( elem, value, name )) !== undefined ) {
2295
+ return ret;
2296
+
2297
+ } else {
2298
+ return (elem[ name ] = value);
2299
+ }
2300
+
2301
+ } else {
2302
+ if ( hooks && "get" in hooks && (ret = hooks.get( elem, name )) !== undefined ) {
2303
+ return ret;
2304
+
2305
+ } else {
2092
2306
  return elem[ name ];
2093
2307
  }
2308
+ }
2309
+ },
2310
+
2311
+ propHooks: {}
2312
+ });
2313
+
2314
+ // IE6/7 do not support getting/setting some attributes with get/setAttribute
2315
+ if ( !jQuery.support.getSetAttribute ) {
2316
+ jQuery.attrFix = jQuery.extend( jQuery.attrFix, {
2317
+ "for": "htmlFor",
2318
+ "class": "className",
2319
+ maxlength: "maxLength",
2320
+ cellspacing: "cellSpacing",
2321
+ cellpadding: "cellPadding",
2322
+ rowspan: "rowSpan",
2323
+ colspan: "colSpan",
2324
+ usemap: "useMap",
2325
+ frameborder: "frameBorder"
2326
+ });
2327
+
2328
+ // Use this for any attribute on a form in IE6/7
2329
+ formHook = jQuery.attrHooks.name = jQuery.attrHooks.value = jQuery.valHooks.button = {
2330
+ get: function( elem, name ) {
2331
+ var ret;
2332
+ if ( name === "value" && !jQuery.nodeName( elem, "button" ) ) {
2333
+ return elem.getAttribute( name );
2334
+ }
2335
+ ret = elem.getAttributeNode( name );
2336
+ // Return undefined if not specified instead of empty string
2337
+ return ret && ret.specified ?
2338
+ ret.nodeValue :
2339
+ undefined;
2340
+ },
2341
+ set: function( elem, value, name ) {
2342
+ // Check form objects in IE (multiple bugs related)
2343
+ // Only use nodeValue if the attribute node exists on the form
2344
+ var ret = elem.getAttributeNode( name );
2345
+ if ( ret ) {
2346
+ ret.nodeValue = value;
2347
+ return value;
2348
+ }
2349
+ }
2350
+ };
2351
+
2352
+ // Set width and height to auto instead of 0 on empty string( Bug #8150 )
2353
+ // This is for removals
2354
+ jQuery.each([ "width", "height" ], function( i, name ) {
2355
+ jQuery.attrHooks[ name ] = jQuery.extend( jQuery.attrHooks[ name ], {
2356
+ set: function( elem, value ) {
2357
+ if ( value === "" ) {
2358
+ elem.setAttribute( name, "auto" );
2359
+ return value;
2360
+ }
2361
+ }
2362
+ });
2363
+ });
2364
+ }
2094
2365
 
2095
- if ( !jQuery.support.style && notxml && name === "style" ) {
2096
- if ( set ) {
2097
- elem.style.cssText = "" + value;
2098
- }
2099
2366
 
2100
- return elem.style.cssText;
2367
+ // Some attributes require a special call on IE
2368
+ if ( !jQuery.support.hrefNormalized ) {
2369
+ jQuery.each([ "href", "src", "width", "height" ], function( i, name ) {
2370
+ jQuery.attrHooks[ name ] = jQuery.extend( jQuery.attrHooks[ name ], {
2371
+ get: function( elem ) {
2372
+ var ret = elem.getAttribute( name, 2 );
2373
+ return ret === null ? undefined : ret;
2101
2374
  }
2375
+ });
2376
+ });
2377
+ }
2102
2378
 
2103
- if ( set ) {
2104
- // convert the value to a string (all browsers do this but IE) see #1070
2105
- elem.setAttribute( name, "" + value );
2106
- }
2379
+ if ( !jQuery.support.style ) {
2380
+ jQuery.attrHooks.style = {
2381
+ get: function( elem ) {
2382
+ // Return undefined in the case of empty string
2383
+ // Normalize to lowercase since IE uppercases css property names
2384
+ return elem.style.cssText.toLowerCase() || undefined;
2385
+ },
2386
+ set: function( elem, value ) {
2387
+ return (elem.style.cssText = "" + value);
2388
+ }
2389
+ };
2390
+ }
2107
2391
 
2108
- // Ensure that missing attributes return undefined
2109
- // Blackberry 4.7 returns "" from getAttribute #6938
2110
- if ( !elem.attributes[ name ] && (elem.hasAttribute && !elem.hasAttribute( name )) ) {
2111
- return undefined;
2112
- }
2392
+ // Safari mis-reports the default selected property of an option
2393
+ // Accessing the parent's selectedIndex property fixes it
2394
+ if ( !jQuery.support.optSelected ) {
2395
+ jQuery.propHooks.selected = jQuery.extend( jQuery.propHooks.selected, {
2396
+ get: function( elem ) {
2397
+ var parent = elem.parentNode;
2113
2398
 
2114
- var attr = !jQuery.support.hrefNormalized && notxml && special ?
2115
- // Some attributes require a special call on IE
2116
- elem.getAttribute( name, 2 ) :
2117
- elem.getAttribute( name );
2399
+ if ( parent ) {
2400
+ parent.selectedIndex;
2118
2401
 
2119
- // Non-existent attributes return null, we normalize to undefined
2120
- return attr === null ? undefined : attr;
2402
+ // Make sure that it also works with optgroups, see #5701
2403
+ if ( parent.parentNode ) {
2404
+ parent.parentNode.selectedIndex;
2405
+ }
2406
+ }
2121
2407
  }
2122
- // Handle everything which isn't a DOM element node
2123
- if ( set ) {
2124
- elem[ name ] = value;
2408
+ });
2409
+ }
2410
+
2411
+ // Radios and checkboxes getter/setter
2412
+ if ( !jQuery.support.checkOn ) {
2413
+ jQuery.each([ "radio", "checkbox" ], function() {
2414
+ jQuery.valHooks[ this ] = {
2415
+ get: function( elem ) {
2416
+ // Handle the case where in Webkit "" is returned instead of "on" if a value isn't specified
2417
+ return elem.getAttribute("value") === null ? "on" : elem.value;
2418
+ }
2419
+ };
2420
+ });
2421
+ }
2422
+ jQuery.each([ "radio", "checkbox" ], function() {
2423
+ jQuery.valHooks[ this ] = jQuery.extend( jQuery.valHooks[ this ], {
2424
+ set: function( elem, value ) {
2425
+ if ( jQuery.isArray( value ) ) {
2426
+ return (elem.checked = jQuery.inArray( jQuery(elem).val(), value ) >= 0);
2427
+ }
2125
2428
  }
2126
- return elem[ name ];
2127
- }
2429
+ });
2128
2430
  });
2129
2431
 
2130
2432
 
2131
2433
 
2132
2434
 
2133
- var rnamespaces = /\.(.*)$/,
2435
+ var hasOwn = Object.prototype.hasOwnProperty,
2436
+ rnamespaces = /\.(.*)$/,
2134
2437
  rformElems = /^(?:textarea|input|select)$/i,
2135
2438
  rperiod = /\./g,
2136
- rspace = / /g,
2439
+ rspaces = / /g,
2137
2440
  rescape = /[^\w\s.|`]/g,
2138
2441
  fcleanup = function( nm ) {
2139
2442
  return nm.replace(rescape, "\\$&");
@@ -2153,17 +2456,6 @@ jQuery.event = {
2153
2456
  return;
2154
2457
  }
2155
2458
 
2156
- // TODO :: Use a try/catch until it's safe to pull this out (likely 1.6)
2157
- // Minor release fix for bug #8018
2158
- try {
2159
- // For whatever reason, IE has trouble passing the window object
2160
- // around, causing it to be cloned in the process
2161
- if ( jQuery.isWindow( elem ) && ( elem !== window && !elem.frameElement ) ) {
2162
- elem = window;
2163
- }
2164
- }
2165
- catch ( e ) {}
2166
-
2167
2459
  if ( handler === false ) {
2168
2460
  handler = returnFalse;
2169
2461
  } else if ( !handler ) {
@@ -2201,9 +2493,9 @@ jQuery.event = {
2201
2493
 
2202
2494
  if ( !eventHandle ) {
2203
2495
  elemData.handle = eventHandle = function( e ) {
2204
- // Handle the second event of a trigger and when
2205
- // an event is called after a page has unloaded
2206
- return typeof jQuery !== "undefined" && jQuery.event.triggered !== e.type ?
2496
+ // Discard the second event of a jQuery.event.trigger() and
2497
+ // when an event is called after a page has unloaded
2498
+ return typeof jQuery !== "undefined" && (!e || jQuery.event.triggered !== e.type) ?
2207
2499
  jQuery.event.handle.apply( eventHandle.elem, arguments ) :
2208
2500
  undefined;
2209
2501
  };
@@ -2273,7 +2565,7 @@ jQuery.event = {
2273
2565
  // Add the function to the element's handler list
2274
2566
  handlers.push( handleObj );
2275
2567
 
2276
- // Keep track of which events have been used, for global triggering
2568
+ // Keep track of which events have been used, for event optimization
2277
2569
  jQuery.event.global[ type ] = true;
2278
2570
  }
2279
2571
 
@@ -2406,182 +2698,185 @@ jQuery.event = {
2406
2698
  }
2407
2699
  }
2408
2700
  },
2701
+
2702
+ // Events that are safe to short-circuit if no handlers are attached.
2703
+ // Native DOM events should not be added, they may have inline handlers.
2704
+ customEvent: {
2705
+ "getData": true,
2706
+ "setData": true,
2707
+ "changeData": true
2708
+ },
2409
2709
 
2410
- // bubbling is internal
2411
- trigger: function( event, data, elem /*, bubbling */ ) {
2710
+ trigger: function( event, data, elem, onlyHandlers ) {
2412
2711
  // Event object or event type
2413
2712
  var type = event.type || event,
2414
- bubbling = arguments[3];
2713
+ namespaces = [],
2714
+ exclusive;
2415
2715
 
2416
- if ( !bubbling ) {
2417
- event = typeof event === "object" ?
2418
- // jQuery.Event object
2419
- event[ jQuery.expando ] ? event :
2420
- // Object literal
2421
- jQuery.extend( jQuery.Event(type), event ) :
2422
- // Just the event type (string)
2423
- jQuery.Event(type);
2716
+ if ( type.indexOf("!") >= 0 ) {
2717
+ // Exclusive events trigger only for the exact event (no namespaces)
2718
+ type = type.slice(0, -1);
2719
+ exclusive = true;
2720
+ }
2424
2721
 
2425
- if ( type.indexOf("!") >= 0 ) {
2426
- event.type = type = type.slice(0, -1);
2427
- event.exclusive = true;
2428
- }
2722
+ if ( type.indexOf(".") >= 0 ) {
2723
+ // Namespaced trigger; create a regexp to match event type in handle()
2724
+ namespaces = type.split(".");
2725
+ type = namespaces.shift();
2726
+ namespaces.sort();
2727
+ }
2429
2728
 
2430
- // Handle a global trigger
2431
- if ( !elem ) {
2432
- // Don't bubble custom events when global (to avoid too much overhead)
2433
- event.stopPropagation();
2434
-
2435
- // Only trigger if we've ever bound an event for it
2436
- if ( jQuery.event.global[ type ] ) {
2437
- // XXX This code smells terrible. event.js should not be directly
2438
- // inspecting the data cache
2439
- jQuery.each( jQuery.cache, function() {
2440
- // internalKey variable is just used to make it easier to find
2441
- // and potentially change this stuff later; currently it just
2442
- // points to jQuery.expando
2443
- var internalKey = jQuery.expando,
2444
- internalCache = this[ internalKey ];
2445
- if ( internalCache && internalCache.events && internalCache.events[ type ] ) {
2446
- jQuery.event.trigger( event, data, internalCache.handle.elem );
2447
- }
2448
- });
2449
- }
2450
- }
2729
+ if ( (!elem || jQuery.event.customEvent[ type ]) && !jQuery.event.global[ type ] ) {
2730
+ // No jQuery handlers for this event type, and it can't have inline handlers
2731
+ return;
2732
+ }
2451
2733
 
2452
- // Handle triggering a single element
2734
+ // Caller can pass in an Event, Object, or just an event type string
2735
+ event = typeof event === "object" ?
2736
+ // jQuery.Event object
2737
+ event[ jQuery.expando ] ? event :
2738
+ // Object literal
2739
+ new jQuery.Event( type, event ) :
2740
+ // Just the event type (string)
2741
+ new jQuery.Event( type );
2453
2742
 
2454
- // don't do events on text and comment nodes
2455
- if ( !elem || elem.nodeType === 3 || elem.nodeType === 8 ) {
2456
- return undefined;
2457
- }
2743
+ event.type = type;
2744
+ event.exclusive = exclusive;
2745
+ event.namespace = namespaces.join(".");
2746
+ event.namespace_re = new RegExp("(^|\\.)" + namespaces.join("\\.(?:.*\\.)?") + "(\\.|$)");
2747
+
2748
+ // triggerHandler() and global events don't bubble or run the default action
2749
+ if ( onlyHandlers || !elem ) {
2750
+ event.preventDefault();
2751
+ event.stopPropagation();
2752
+ }
2458
2753
 
2459
- // Clean up in case it is reused
2460
- event.result = undefined;
2461
- event.target = elem;
2754
+ // Handle a global trigger
2755
+ if ( !elem ) {
2756
+ // TODO: Stop taunting the data cache; remove global events and always attach to document
2757
+ jQuery.each( jQuery.cache, function() {
2758
+ // internalKey variable is just used to make it easier to find
2759
+ // and potentially change this stuff later; currently it just
2760
+ // points to jQuery.expando
2761
+ var internalKey = jQuery.expando,
2762
+ internalCache = this[ internalKey ];
2763
+ if ( internalCache && internalCache.events && internalCache.events[ type ] ) {
2764
+ jQuery.event.trigger( event, data, internalCache.handle.elem );
2765
+ }
2766
+ });
2767
+ return;
2768
+ }
2462
2769
 
2463
- // Clone the incoming data, if any
2464
- data = jQuery.makeArray( data );
2465
- data.unshift( event );
2770
+ // Don't do events on text and comment nodes
2771
+ if ( elem.nodeType === 3 || elem.nodeType === 8 ) {
2772
+ return;
2466
2773
  }
2467
2774
 
2468
- event.currentTarget = elem;
2775
+ // Clean up the event in case it is being reused
2776
+ event.result = undefined;
2777
+ event.target = elem;
2469
2778
 
2470
- // Trigger the event, it is assumed that "handle" is a function
2471
- var handle = jQuery._data( elem, "handle" );
2779
+ // Clone any incoming data and prepend the event, creating the handler arg list
2780
+ data = data ? jQuery.makeArray( data ) : [];
2781
+ data.unshift( event );
2472
2782
 
2473
- if ( handle ) {
2474
- handle.apply( elem, data );
2475
- }
2783
+ var cur = elem,
2784
+ // IE doesn't like method names with a colon (#3533, #8272)
2785
+ ontype = type.indexOf(":") < 0 ? "on" + type : "";
2476
2786
 
2477
- var parent = elem.parentNode || elem.ownerDocument;
2787
+ // Fire event on the current element, then bubble up the DOM tree
2788
+ do {
2789
+ var handle = jQuery._data( cur, "handle" );
2478
2790
 
2479
- // Trigger an inline bound script
2480
- try {
2481
- if ( !(elem && elem.nodeName && jQuery.noData[elem.nodeName.toLowerCase()]) ) {
2482
- if ( elem[ "on" + type ] && elem[ "on" + type ].apply( elem, data ) === false ) {
2483
- event.result = false;
2484
- event.preventDefault();
2485
- }
2791
+ event.currentTarget = cur;
2792
+ if ( handle ) {
2793
+ handle.apply( cur, data );
2486
2794
  }
2487
2795
 
2488
- // prevent IE from throwing an error for some elements with some event types, see #3533
2489
- } catch (inlineError) {}
2796
+ // Trigger an inline bound script
2797
+ if ( ontype && jQuery.acceptData( cur ) && cur[ ontype ] && cur[ ontype ].apply( cur, data ) === false ) {
2798
+ event.result = false;
2799
+ event.preventDefault();
2800
+ }
2490
2801
 
2491
- if ( !event.isPropagationStopped() && parent ) {
2492
- jQuery.event.trigger( event, data, parent, true );
2802
+ // Bubble up to document, then to window
2803
+ cur = cur.parentNode || cur.ownerDocument || cur === event.target.ownerDocument && window;
2804
+ } while ( cur && !event.isPropagationStopped() );
2493
2805
 
2494
- } else if ( !event.isDefaultPrevented() ) {
2806
+ // If nobody prevented the default action, do it now
2807
+ if ( !event.isDefaultPrevented() ) {
2495
2808
  var old,
2496
- target = event.target,
2497
- targetType = type.replace( rnamespaces, "" ),
2498
- isClick = jQuery.nodeName( target, "a" ) && targetType === "click",
2499
- special = jQuery.event.special[ targetType ] || {};
2809
+ special = jQuery.event.special[ type ] || {};
2500
2810
 
2501
- if ( (!special._default || special._default.call( elem, event ) === false) &&
2502
- !isClick && !(target && target.nodeName && jQuery.noData[target.nodeName.toLowerCase()]) ) {
2811
+ if ( (!special._default || special._default.call( elem.ownerDocument, event ) === false) &&
2812
+ !(type === "click" && jQuery.nodeName( elem, "a" )) && jQuery.acceptData( elem ) ) {
2503
2813
 
2814
+ // Call a native DOM method on the target with the same name name as the event.
2815
+ // Can't use an .isFunction)() check here because IE6/7 fails that test.
2816
+ // IE<9 dies on focus to hidden element (#1486), may want to revisit a try/catch.
2504
2817
  try {
2505
- if ( target[ targetType ] ) {
2506
- // Make sure that we don't accidentally re-trigger the onFOO events
2507
- old = target[ "on" + targetType ];
2818
+ if ( ontype && elem[ type ] ) {
2819
+ // Don't re-trigger an onFOO event when we call its FOO() method
2820
+ old = elem[ ontype ];
2508
2821
 
2509
2822
  if ( old ) {
2510
- target[ "on" + targetType ] = null;
2823
+ elem[ ontype ] = null;
2511
2824
  }
2512
2825
 
2513
- jQuery.event.triggered = event.type;
2514
- target[ targetType ]();
2826
+ jQuery.event.triggered = type;
2827
+ elem[ type ]();
2515
2828
  }
2516
-
2517
- // prevent IE from throwing an error for some elements with some event types, see #3533
2518
- } catch (triggerError) {}
2829
+ } catch ( ieError ) {}
2519
2830
 
2520
2831
  if ( old ) {
2521
- target[ "on" + targetType ] = old;
2832
+ elem[ ontype ] = old;
2522
2833
  }
2523
2834
 
2524
2835
  jQuery.event.triggered = undefined;
2525
2836
  }
2526
2837
  }
2838
+
2839
+ return event.result;
2527
2840
  },
2528
2841
 
2529
2842
  handle: function( event ) {
2530
- var all, handlers, namespaces, namespace_re, events,
2531
- namespace_sort = [],
2532
- args = jQuery.makeArray( arguments );
2533
-
2534
- event = args[0] = jQuery.event.fix( event || window.event );
2843
+ event = jQuery.event.fix( event || window.event );
2844
+ // Snapshot the handlers list since a called handler may add/remove events.
2845
+ var handlers = ((jQuery._data( this, "events" ) || {})[ event.type ] || []).slice(0),
2846
+ run_all = !event.exclusive && !event.namespace,
2847
+ args = Array.prototype.slice.call( arguments, 0 );
2848
+
2849
+ // Use the fix-ed Event rather than the (read-only) native event
2850
+ args[0] = event;
2535
2851
  event.currentTarget = this;
2536
2852
 
2537
- // Namespaced event handlers
2538
- all = event.type.indexOf(".") < 0 && !event.exclusive;
2539
-
2540
- if ( !all ) {
2541
- namespaces = event.type.split(".");
2542
- event.type = namespaces.shift();
2543
- namespace_sort = namespaces.slice(0).sort();
2544
- namespace_re = new RegExp("(^|\\.)" + namespace_sort.join("\\.(?:.*\\.)?") + "(\\.|$)");
2545
- }
2546
-
2547
- event.namespace = event.namespace || namespace_sort.join(".");
2548
-
2549
- events = jQuery._data(this, "events");
2550
-
2551
- handlers = (events || {})[ event.type ];
2552
-
2553
- if ( events && handlers ) {
2554
- // Clone the handlers to prevent manipulation
2555
- handlers = handlers.slice(0);
2556
-
2557
- for ( var j = 0, l = handlers.length; j < l; j++ ) {
2558
- var handleObj = handlers[ j ];
2559
-
2560
- // Filter the functions by class
2561
- if ( all || namespace_re.test( handleObj.namespace ) ) {
2562
- // Pass in a reference to the handler function itself
2563
- // So that we can later remove it
2564
- event.handler = handleObj.handler;
2565
- event.data = handleObj.data;
2566
- event.handleObj = handleObj;
2567
-
2568
- var ret = handleObj.handler.apply( this, args );
2569
-
2570
- if ( ret !== undefined ) {
2571
- event.result = ret;
2572
- if ( ret === false ) {
2573
- event.preventDefault();
2574
- event.stopPropagation();
2575
- }
2853
+ for ( var j = 0, l = handlers.length; j < l; j++ ) {
2854
+ var handleObj = handlers[ j ];
2855
+
2856
+ // Triggered event must 1) be non-exclusive and have no namespace, or
2857
+ // 2) have namespace(s) a subset or equal to those in the bound event.
2858
+ if ( run_all || event.namespace_re.test( handleObj.namespace ) ) {
2859
+ // Pass in a reference to the handler function itself
2860
+ // So that we can later remove it
2861
+ event.handler = handleObj.handler;
2862
+ event.data = handleObj.data;
2863
+ event.handleObj = handleObj;
2864
+
2865
+ var ret = handleObj.handler.apply( this, args );
2866
+
2867
+ if ( ret !== undefined ) {
2868
+ event.result = ret;
2869
+ if ( ret === false ) {
2870
+ event.preventDefault();
2871
+ event.stopPropagation();
2576
2872
  }
2873
+ }
2577
2874
 
2578
- if ( event.isImmediatePropagationStopped() ) {
2579
- break;
2580
- }
2875
+ if ( event.isImmediatePropagationStopped() ) {
2876
+ break;
2581
2877
  }
2582
2878
  }
2583
2879
  }
2584
-
2585
2880
  return event.result;
2586
2881
  },
2587
2882
 
@@ -2620,8 +2915,9 @@ jQuery.event = {
2620
2915
 
2621
2916
  // Calculate pageX/Y if missing and clientX/Y available
2622
2917
  if ( event.pageX == null && event.clientX != null ) {
2623
- var doc = document.documentElement,
2624
- body = document.body;
2918
+ var eventDocument = event.target.ownerDocument || document,
2919
+ doc = eventDocument.documentElement,
2920
+ body = eventDocument.body;
2625
2921
 
2626
2922
  event.pageX = event.clientX + (doc && doc.scrollLeft || body && body.scrollLeft || 0) - (doc && doc.clientLeft || body && body.clientLeft || 0);
2627
2923
  event.pageY = event.clientY + (doc && doc.scrollTop || body && body.scrollTop || 0) - (doc && doc.clientTop || body && body.clientTop || 0);
@@ -2700,10 +2996,10 @@ jQuery.removeEvent = document.removeEventListener ?
2700
2996
  }
2701
2997
  };
2702
2998
 
2703
- jQuery.Event = function( src ) {
2999
+ jQuery.Event = function( src, props ) {
2704
3000
  // Allow instantiation without the 'new' keyword
2705
3001
  if ( !this.preventDefault ) {
2706
- return new jQuery.Event( src );
3002
+ return new jQuery.Event( src, props );
2707
3003
  }
2708
3004
 
2709
3005
  // Event object
@@ -2721,6 +3017,11 @@ jQuery.Event = function( src ) {
2721
3017
  this.type = src;
2722
3018
  }
2723
3019
 
3020
+ // Put explicitly provided properties onto the event object
3021
+ if ( props ) {
3022
+ jQuery.extend( this, props );
3023
+ }
3024
+
2724
3025
  // timeStamp is buggy for some events on Firefox(#3843)
2725
3026
  // So we won't rely on the native value
2726
3027
  this.timeStamp = jQuery.now();
@@ -2838,7 +3139,7 @@ if ( !jQuery.support.submitBubbles ) {
2838
3139
 
2839
3140
  jQuery.event.special.submit = {
2840
3141
  setup: function( data, namespaces ) {
2841
- if ( this.nodeName && this.nodeName.toLowerCase() !== "form" ) {
3142
+ if ( !jQuery.nodeName( this, "form" ) ) {
2842
3143
  jQuery.event.add(this, "click.specialSubmit", function( e ) {
2843
3144
  var elem = e.target,
2844
3145
  type = elem.type;
@@ -2887,7 +3188,7 @@ if ( !jQuery.support.changeBubbles ) {
2887
3188
  }).join("-") :
2888
3189
  "";
2889
3190
 
2890
- } else if ( elem.nodeName.toLowerCase() === "select" ) {
3191
+ } else if ( jQuery.nodeName( elem, "select" ) ) {
2891
3192
  val = elem.selectedIndex;
2892
3193
  }
2893
3194
 
@@ -2927,9 +3228,9 @@ if ( !jQuery.support.changeBubbles ) {
2927
3228
  beforedeactivate: testChange,
2928
3229
 
2929
3230
  click: function( e ) {
2930
- var elem = e.target, type = elem.type;
3231
+ var elem = e.target, type = jQuery.nodeName( elem, "input" ) ? elem.type : "";
2931
3232
 
2932
- if ( type === "radio" || type === "checkbox" || elem.nodeName.toLowerCase() === "select" ) {
3233
+ if ( type === "radio" || type === "checkbox" || jQuery.nodeName( elem, "select" ) ) {
2933
3234
  testChange.call( this, e );
2934
3235
  }
2935
3236
  },
@@ -2937,9 +3238,9 @@ if ( !jQuery.support.changeBubbles ) {
2937
3238
  // Change has to be called before submit
2938
3239
  // Keydown will be called before keypress, which is used in submit-event delegation
2939
3240
  keydown: function( e ) {
2940
- var elem = e.target, type = elem.type;
3241
+ var elem = e.target, type = jQuery.nodeName( elem, "input" ) ? elem.type : "";
2941
3242
 
2942
- if ( (e.keyCode === 13 && elem.nodeName.toLowerCase() !== "textarea") ||
3243
+ if ( (e.keyCode === 13 && !jQuery.nodeName( elem, "textarea" ) ) ||
2943
3244
  (e.keyCode === 32 && (type === "checkbox" || type === "radio")) ||
2944
3245
  type === "select-multiple" ) {
2945
3246
  testChange.call( this, e );
@@ -2996,12 +3297,12 @@ function trigger( type, elem, args ) {
2996
3297
  }
2997
3298
 
2998
3299
  // Create "bubbling" focus and blur events
2999
- if ( document.addEventListener ) {
3300
+ if ( !jQuery.support.focusinBubbles ) {
3000
3301
  jQuery.each({ focus: "focusin", blur: "focusout" }, function( orig, fix ) {
3001
-
3302
+
3002
3303
  // Attach a single capturing handler while someone wants focusin/focusout
3003
3304
  var attaches = 0;
3004
-
3305
+
3005
3306
  jQuery.event.special[ fix ] = {
3006
3307
  setup: function() {
3007
3308
  if ( attaches++ === 0 ) {
@@ -3031,6 +3332,8 @@ if ( document.addEventListener ) {
3031
3332
 
3032
3333
  jQuery.each(["bind", "one"], function( i, name ) {
3033
3334
  jQuery.fn[ name ] = function( type, data, fn ) {
3335
+ var handler;
3336
+
3034
3337
  // Handle object literals
3035
3338
  if ( typeof type === "object" ) {
3036
3339
  for ( var key in type ) {
@@ -3039,15 +3342,20 @@ jQuery.each(["bind", "one"], function( i, name ) {
3039
3342
  return this;
3040
3343
  }
3041
3344
 
3042
- if ( jQuery.isFunction( data ) || data === false ) {
3345
+ if ( arguments.length === 2 || data === false ) {
3043
3346
  fn = data;
3044
3347
  data = undefined;
3045
3348
  }
3046
3349
 
3047
- var handler = name === "one" ? jQuery.proxy( fn, function( event ) {
3048
- jQuery( this ).unbind( event, handler );
3049
- return fn.apply( this, arguments );
3050
- }) : fn;
3350
+ if ( name === "one" ) {
3351
+ handler = function( event ) {
3352
+ jQuery( this ).unbind( event, handler );
3353
+ return fn.apply( this, arguments );
3354
+ };
3355
+ handler.guid = fn.guid || jQuery.guid++;
3356
+ } else {
3357
+ handler = fn;
3358
+ }
3051
3359
 
3052
3360
  if ( type === "unload" && name !== "one" ) {
3053
3361
  this.one( type, data, fn );
@@ -3085,7 +3393,7 @@ jQuery.fn.extend({
3085
3393
 
3086
3394
  undelegate: function( selector, types, fn ) {
3087
3395
  if ( arguments.length === 0 ) {
3088
- return this.unbind( "live" );
3396
+ return this.unbind( "live" );
3089
3397
 
3090
3398
  } else {
3091
3399
  return this.die( types, null, fn, selector );
@@ -3100,35 +3408,34 @@ jQuery.fn.extend({
3100
3408
 
3101
3409
  triggerHandler: function( type, data ) {
3102
3410
  if ( this[0] ) {
3103
- var event = jQuery.Event( type );
3104
- event.preventDefault();
3105
- event.stopPropagation();
3106
- jQuery.event.trigger( event, data, this[0] );
3107
- return event.result;
3411
+ return jQuery.event.trigger( type, data, this[0], true );
3108
3412
  }
3109
3413
  },
3110
3414
 
3111
3415
  toggle: function( fn ) {
3112
3416
  // Save reference to arguments for access in closure
3113
3417
  var args = arguments,
3114
- i = 1;
3418
+ guid = fn.guid || jQuery.guid++,
3419
+ i = 0,
3420
+ toggler = function( event ) {
3421
+ // Figure out which function to execute
3422
+ var lastToggle = ( jQuery.data( this, "lastToggle" + fn.guid ) || 0 ) % i;
3423
+ jQuery.data( this, "lastToggle" + fn.guid, lastToggle + 1 );
3424
+
3425
+ // Make sure that clicks stop
3426
+ event.preventDefault();
3427
+
3428
+ // and execute the function
3429
+ return args[ lastToggle ].apply( this, arguments ) || false;
3430
+ };
3115
3431
 
3116
3432
  // link all the functions, so any of them can unbind this click handler
3433
+ toggler.guid = guid;
3117
3434
  while ( i < args.length ) {
3118
- jQuery.proxy( fn, args[ i++ ] );
3435
+ args[ i++ ].guid = guid;
3119
3436
  }
3120
3437
 
3121
- return this.click( jQuery.proxy( fn, function( event ) {
3122
- // Figure out which function to execute
3123
- var lastToggle = ( jQuery._data( this, "lastToggle" + fn.guid ) || 0 ) % i;
3124
- jQuery._data( this, "lastToggle" + fn.guid, lastToggle + 1 );
3125
-
3126
- // Make sure that clicks stop
3127
- event.preventDefault();
3128
-
3129
- // and execute the function
3130
- return args[ lastToggle ].apply( this, arguments ) || false;
3131
- }));
3438
+ return this.click( toggler );
3132
3439
  },
3133
3440
 
3134
3441
  hover: function( fnOver, fnOut ) {
@@ -3157,8 +3464,16 @@ jQuery.each(["live", "die"], function( i, name ) {
3157
3464
  return this;
3158
3465
  }
3159
3466
 
3160
- if ( jQuery.isFunction( data ) ) {
3161
- fn = data;
3467
+ if ( name === "die" && !types &&
3468
+ origSelector && origSelector.charAt(0) === "." ) {
3469
+
3470
+ context.unbind( origSelector );
3471
+
3472
+ return this;
3473
+ }
3474
+
3475
+ if ( data === false || jQuery.isFunction( data ) ) {
3476
+ fn = data || returnFalse;
3162
3477
  data = undefined;
3163
3478
  }
3164
3479
 
@@ -3180,7 +3495,7 @@ jQuery.each(["live", "die"], function( i, name ) {
3180
3495
 
3181
3496
  preType = type;
3182
3497
 
3183
- if ( type === "focus" || type === "blur" ) {
3498
+ if ( liveMap[ type ] ) {
3184
3499
  types.push( liveMap[ type ] + namespaces );
3185
3500
  type = type + namespaces;
3186
3501
 
@@ -3251,6 +3566,11 @@ function liveHandler( event ) {
3251
3566
  if ( handleObj.preType === "mouseenter" || handleObj.preType === "mouseleave" ) {
3252
3567
  event.type = handleObj.preType;
3253
3568
  related = jQuery( event.relatedTarget ).closest( handleObj.selector )[0];
3569
+
3570
+ // Make sure not to accidentally match a child element with the same selector
3571
+ if ( related && jQuery.contains( elem, related ) ) {
3572
+ related = elem;
3573
+ }
3254
3574
  }
3255
3575
 
3256
3576
  if ( !related || related !== elem ) {
@@ -3289,7 +3609,7 @@ function liveHandler( event ) {
3289
3609
  }
3290
3610
 
3291
3611
  function liveConvert( type, selector ) {
3292
- return (type && type !== "*" ? type + "." : "") + selector.replace(rperiod, "`").replace(rspace, "&");
3612
+ return (type && type !== "*" ? type + "." : "") + selector.replace(rperiod, "`").replace(rspaces, "&");
3293
3613
  }
3294
3614
 
3295
3615
  jQuery.each( ("blur focus focusin focusout load resize scroll unload click dblclick " +
@@ -3314,6 +3634,7 @@ jQuery.each( ("blur focus focusin focusout load resize scroll unload click dblcl
3314
3634
  });
3315
3635
 
3316
3636
 
3637
+
3317
3638
  /*!
3318
3639
  * Sizzle CSS Selector Engine
3319
3640
  * Copyright 2011, The Dojo Foundation
@@ -3941,42 +4262,49 @@ var Expr = Sizzle.selectors = {
3941
4262
  var attr = elem.getAttribute( "type" ), type = elem.type;
3942
4263
  // IE6 and 7 will map elem.type to 'text' for new HTML5 types (search, etc)
3943
4264
  // use getAttribute instead to test this case
3944
- return "text" === type && ( attr === type || attr === null );
4265
+ return elem.nodeName.toLowerCase() === "input" && "text" === type && ( attr === type || attr === null );
3945
4266
  },
3946
4267
 
3947
4268
  radio: function( elem ) {
3948
- return "radio" === elem.type;
4269
+ return elem.nodeName.toLowerCase() === "input" && "radio" === elem.type;
3949
4270
  },
3950
4271
 
3951
4272
  checkbox: function( elem ) {
3952
- return "checkbox" === elem.type;
4273
+ return elem.nodeName.toLowerCase() === "input" && "checkbox" === elem.type;
3953
4274
  },
3954
4275
 
3955
4276
  file: function( elem ) {
3956
- return "file" === elem.type;
4277
+ return elem.nodeName.toLowerCase() === "input" && "file" === elem.type;
3957
4278
  },
4279
+
3958
4280
  password: function( elem ) {
3959
- return "password" === elem.type;
4281
+ return elem.nodeName.toLowerCase() === "input" && "password" === elem.type;
3960
4282
  },
3961
4283
 
3962
4284
  submit: function( elem ) {
3963
- return "submit" === elem.type;
4285
+ var name = elem.nodeName.toLowerCase();
4286
+ return (name === "input" || name === "button") && "submit" === elem.type;
3964
4287
  },
3965
4288
 
3966
4289
  image: function( elem ) {
3967
- return "image" === elem.type;
4290
+ return elem.nodeName.toLowerCase() === "input" && "image" === elem.type;
3968
4291
  },
3969
4292
 
3970
4293
  reset: function( elem ) {
3971
- return "reset" === elem.type;
4294
+ return elem.nodeName.toLowerCase() === "input" && "reset" === elem.type;
3972
4295
  },
3973
4296
 
3974
4297
  button: function( elem ) {
3975
- return "button" === elem.type || elem.nodeName.toLowerCase() === "button";
4298
+ var name = elem.nodeName.toLowerCase();
4299
+ return name === "input" && "button" === elem.type || name === "button";
3976
4300
  },
3977
4301
 
3978
4302
  input: function( elem ) {
3979
4303
  return (/input|select|textarea|button/i).test( elem.nodeName );
4304
+ },
4305
+
4306
+ focus: function( elem ) {
4307
+ return elem === elem.ownerDocument.activeElement;
3980
4308
  }
3981
4309
  },
3982
4310
  setFilters: {
@@ -4739,17 +5067,30 @@ var runtil = /Until$/,
4739
5067
 
4740
5068
  jQuery.fn.extend({
4741
5069
  find: function( selector ) {
5070
+ var self = this,
5071
+ i, l;
5072
+
5073
+ if ( typeof selector !== "string" ) {
5074
+ return jQuery( selector ).filter(function() {
5075
+ for ( i = 0, l = self.length; i < l; i++ ) {
5076
+ if ( jQuery.contains( self[ i ], this ) ) {
5077
+ return true;
5078
+ }
5079
+ }
5080
+ });
5081
+ }
5082
+
4742
5083
  var ret = this.pushStack( "", "find", selector ),
4743
- length = 0;
5084
+ length, n, r;
4744
5085
 
4745
- for ( var i = 0, l = this.length; i < l; i++ ) {
5086
+ for ( i = 0, l = this.length; i < l; i++ ) {
4746
5087
  length = ret.length;
4747
5088
  jQuery.find( selector, this[i], ret );
4748
5089
 
4749
5090
  if ( i > 0 ) {
4750
5091
  // Make sure that the results are unique
4751
- for ( var n = length; n < ret.length; n++ ) {
4752
- for ( var r = 0; r < length; r++ ) {
5092
+ for ( n = length; n < ret.length; n++ ) {
5093
+ for ( r = 0; r < length; r++ ) {
4753
5094
  if ( ret[r] === ret[n] ) {
4754
5095
  ret.splice(n--, 1);
4755
5096
  break;
@@ -4782,12 +5123,15 @@ jQuery.fn.extend({
4782
5123
  },
4783
5124
 
4784
5125
  is: function( selector ) {
4785
- return !!selector && jQuery.filter( selector, this ).length > 0;
5126
+ return !!selector && ( typeof selector === "string" ?
5127
+ jQuery.filter( selector, this ).length > 0 :
5128
+ this.filter( selector ).length > 0 );
4786
5129
  },
4787
5130
 
4788
5131
  closest: function( selectors, context ) {
4789
5132
  var ret = [], i, l, cur = this[0];
4790
-
5133
+
5134
+ // Array
4791
5135
  if ( jQuery.isArray( selectors ) ) {
4792
5136
  var match, selector,
4793
5137
  matches = {},
@@ -4797,8 +5141,8 @@ jQuery.fn.extend({
4797
5141
  for ( i = 0, l = selectors.length; i < l; i++ ) {
4798
5142
  selector = selectors[i];
4799
5143
 
4800
- if ( !matches[selector] ) {
4801
- matches[selector] = jQuery.expr.match.POS.test( selector ) ?
5144
+ if ( !matches[ selector ] ) {
5145
+ matches[ selector ] = POS.test( selector ) ?
4802
5146
  jQuery( selector, context || this.context ) :
4803
5147
  selector;
4804
5148
  }
@@ -4806,9 +5150,9 @@ jQuery.fn.extend({
4806
5150
 
4807
5151
  while ( cur && cur.ownerDocument && cur !== context ) {
4808
5152
  for ( selector in matches ) {
4809
- match = matches[selector];
5153
+ match = matches[ selector ];
4810
5154
 
4811
- if ( match.jquery ? match.index(cur) > -1 : jQuery(cur).is(match) ) {
5155
+ if ( match.jquery ? match.index( cur ) > -1 : jQuery( cur ).is( match ) ) {
4812
5156
  ret.push({ selector: selector, elem: cur, level: level });
4813
5157
  }
4814
5158
  }
@@ -4821,8 +5165,10 @@ jQuery.fn.extend({
4821
5165
  return ret;
4822
5166
  }
4823
5167
 
4824
- var pos = POS.test( selectors ) ?
4825
- jQuery( selectors, context || this.context ) : null;
5168
+ // String
5169
+ var pos = POS.test( selectors ) || typeof selectors !== "string" ?
5170
+ jQuery( selectors, context || this.context ) :
5171
+ 0;
4826
5172
 
4827
5173
  for ( i = 0, l = this.length; i < l; i++ ) {
4828
5174
  cur = this[i];
@@ -4834,14 +5180,14 @@ jQuery.fn.extend({
4834
5180
 
4835
5181
  } else {
4836
5182
  cur = cur.parentNode;
4837
- if ( !cur || !cur.ownerDocument || cur === context ) {
5183
+ if ( !cur || !cur.ownerDocument || cur === context || cur.nodeType === 11 ) {
4838
5184
  break;
4839
5185
  }
4840
5186
  }
4841
5187
  }
4842
5188
  }
4843
5189
 
4844
- ret = ret.length > 1 ? jQuery.unique(ret) : ret;
5190
+ ret = ret.length > 1 ? jQuery.unique( ret ) : ret;
4845
5191
 
4846
5192
  return this.pushStack( ret, "closest", selectors );
4847
5193
  },
@@ -4864,7 +5210,7 @@ jQuery.fn.extend({
4864
5210
  add: function( selector, context ) {
4865
5211
  var set = typeof selector === "string" ?
4866
5212
  jQuery( selector, context ) :
4867
- jQuery.makeArray( selector ),
5213
+ jQuery.makeArray( selector && selector.nodeType ? [ selector ] : selector ),
4868
5214
  all = jQuery.merge( this.get(), set );
4869
5215
 
4870
5216
  return this.pushStack( isDisconnected( set[0] ) || isDisconnected( all[0] ) ?
@@ -5002,6 +5348,11 @@ jQuery.extend({
5002
5348
 
5003
5349
  // Implement the identical functionality for filter and not
5004
5350
  function winnow( elements, qualifier, keep ) {
5351
+
5352
+ // Can't pass null or undefined to indexOf in Firefox 4
5353
+ // Set to 0 to skip string check
5354
+ qualifier = qualifier || 0;
5355
+
5005
5356
  if ( jQuery.isFunction( qualifier ) ) {
5006
5357
  return jQuery.grep(elements, function( elem, i ) {
5007
5358
  var retVal = !!qualifier.call( elem, i, elem );
@@ -5042,6 +5393,7 @@ var rinlinejQuery = / jQuery\d+="(?:\d+|null)"/g,
5042
5393
  rnocache = /<(?:script|object|embed|option|style)/i,
5043
5394
  // checked="checked" or checked
5044
5395
  rchecked = /checked\s*(?:[^=]|=\s*.checked.)/i,
5396
+ rscriptType = /\/(java|ecma)script/i,
5045
5397
  wrapMap = {
5046
5398
  option: [ 1, "<select multiple='multiple'>", "</select>" ],
5047
5399
  legend: [ 1, "<fieldset>", "</fieldset>" ],
@@ -5102,7 +5454,7 @@ jQuery.fn.extend({
5102
5454
  }
5103
5455
 
5104
5456
  return elem;
5105
- }).append(this);
5457
+ }).append( this );
5106
5458
  }
5107
5459
 
5108
5460
  return this;
@@ -5410,21 +5762,27 @@ function cloneCopyEvent( src, dest ) {
5410
5762
  }
5411
5763
  }
5412
5764
 
5413
- function cloneFixAttributes(src, dest) {
5765
+ function cloneFixAttributes( src, dest ) {
5766
+ var nodeName;
5767
+
5414
5768
  // We do not need to do anything for non-Elements
5415
5769
  if ( dest.nodeType !== 1 ) {
5416
5770
  return;
5417
5771
  }
5418
5772
 
5419
- var nodeName = dest.nodeName.toLowerCase();
5420
-
5421
5773
  // clearAttributes removes the attributes, which we don't want,
5422
5774
  // but also removes the attachEvent events, which we *do* want
5423
- dest.clearAttributes();
5775
+ if ( dest.clearAttributes ) {
5776
+ dest.clearAttributes();
5777
+ }
5424
5778
 
5425
5779
  // mergeAttributes, in contrast, only merges back on the
5426
5780
  // original attributes, not the events
5427
- dest.mergeAttributes(src);
5781
+ if ( dest.mergeAttributes ) {
5782
+ dest.mergeAttributes( src );
5783
+ }
5784
+
5785
+ nodeName = dest.nodeName.toLowerCase();
5428
5786
 
5429
5787
  // IE6-8 fail to clone children inside object elements that use
5430
5788
  // the proprietary classid attribute value (rather than the type
@@ -5474,11 +5832,10 @@ jQuery.buildFragment = function( args, nodes, scripts ) {
5474
5832
  args[0].charAt(0) === "<" && !rnocache.test( args[0] ) && (jQuery.support.checkClone || !rchecked.test( args[0] )) ) {
5475
5833
 
5476
5834
  cacheable = true;
5835
+
5477
5836
  cacheresults = jQuery.fragments[ args[0] ];
5478
- if ( cacheresults ) {
5479
- if ( cacheresults !== 1 ) {
5480
- fragment = cacheresults;
5481
- }
5837
+ if ( cacheresults && cacheresults !== 1 ) {
5838
+ fragment = cacheresults;
5482
5839
  }
5483
5840
  }
5484
5841
 
@@ -5536,6 +5893,21 @@ function getAll( elem ) {
5536
5893
  }
5537
5894
  }
5538
5895
 
5896
+ // Used in clean, fixes the defaultChecked property
5897
+ function fixDefaultChecked( elem ) {
5898
+ if ( elem.type === "checkbox" || elem.type === "radio" ) {
5899
+ elem.defaultChecked = elem.checked;
5900
+ }
5901
+ }
5902
+ // Finds all inputs and passes them to fixDefaultChecked
5903
+ function findInputs( elem ) {
5904
+ if ( jQuery.nodeName( elem, "input" ) ) {
5905
+ fixDefaultChecked( elem );
5906
+ } else if ( elem.getElementsByTagName ) {
5907
+ jQuery.grep( elem.getElementsByTagName("input"), fixDefaultChecked );
5908
+ }
5909
+ }
5910
+
5539
5911
  jQuery.extend({
5540
5912
  clone: function( elem, dataAndEvents, deepDataAndEvents ) {
5541
5913
  var clone = elem.cloneNode(true),
@@ -5582,8 +5954,11 @@ jQuery.extend({
5582
5954
 
5583
5955
  // Return the cloned set
5584
5956
  return clone;
5585
- },
5957
+ },
5958
+
5586
5959
  clean: function( elems, context, fragment, scripts ) {
5960
+ var checkScriptType;
5961
+
5587
5962
  context = context || document;
5588
5963
 
5589
5964
  // !context.createElement fails in IE with an error but returns typeof 'object'
@@ -5603,54 +5978,67 @@ jQuery.extend({
5603
5978
  }
5604
5979
 
5605
5980
  // Convert html string into DOM nodes
5606
- if ( typeof elem === "string" && !rhtml.test( elem ) ) {
5607
- elem = context.createTextNode( elem );
5608
-
5609
- } else if ( typeof elem === "string" ) {
5610
- // Fix "XHTML"-style tags in all browsers
5611
- elem = elem.replace(rxhtmlTag, "<$1></$2>");
5981
+ if ( typeof elem === "string" ) {
5982
+ if ( !rhtml.test( elem ) ) {
5983
+ elem = context.createTextNode( elem );
5984
+ } else {
5985
+ // Fix "XHTML"-style tags in all browsers
5986
+ elem = elem.replace(rxhtmlTag, "<$1></$2>");
5612
5987
 
5613
- // Trim whitespace, otherwise indexOf won't work as expected
5614
- var tag = (rtagName.exec( elem ) || ["", ""])[1].toLowerCase(),
5615
- wrap = wrapMap[ tag ] || wrapMap._default,
5616
- depth = wrap[0],
5617
- div = context.createElement("div");
5988
+ // Trim whitespace, otherwise indexOf won't work as expected
5989
+ var tag = (rtagName.exec( elem ) || ["", ""])[1].toLowerCase(),
5990
+ wrap = wrapMap[ tag ] || wrapMap._default,
5991
+ depth = wrap[0],
5992
+ div = context.createElement("div");
5618
5993
 
5619
- // Go to html and back, then peel off extra wrappers
5620
- div.innerHTML = wrap[1] + elem + wrap[2];
5994
+ // Go to html and back, then peel off extra wrappers
5995
+ div.innerHTML = wrap[1] + elem + wrap[2];
5621
5996
 
5622
- // Move to the right depth
5623
- while ( depth-- ) {
5624
- div = div.lastChild;
5625
- }
5997
+ // Move to the right depth
5998
+ while ( depth-- ) {
5999
+ div = div.lastChild;
6000
+ }
5626
6001
 
5627
- // Remove IE's autoinserted <tbody> from table fragments
5628
- if ( !jQuery.support.tbody ) {
6002
+ // Remove IE's autoinserted <tbody> from table fragments
6003
+ if ( !jQuery.support.tbody ) {
5629
6004
 
5630
- // String was a <table>, *may* have spurious <tbody>
5631
- var hasBody = rtbody.test(elem),
5632
- tbody = tag === "table" && !hasBody ?
5633
- div.firstChild && div.firstChild.childNodes :
6005
+ // String was a <table>, *may* have spurious <tbody>
6006
+ var hasBody = rtbody.test(elem),
6007
+ tbody = tag === "table" && !hasBody ?
6008
+ div.firstChild && div.firstChild.childNodes :
5634
6009
 
5635
- // String was a bare <thead> or <tfoot>
5636
- wrap[1] === "<table>" && !hasBody ?
5637
- div.childNodes :
5638
- [];
6010
+ // String was a bare <thead> or <tfoot>
6011
+ wrap[1] === "<table>" && !hasBody ?
6012
+ div.childNodes :
6013
+ [];
5639
6014
 
5640
- for ( var j = tbody.length - 1; j >= 0 ; --j ) {
5641
- if ( jQuery.nodeName( tbody[ j ], "tbody" ) && !tbody[ j ].childNodes.length ) {
5642
- tbody[ j ].parentNode.removeChild( tbody[ j ] );
6015
+ for ( var j = tbody.length - 1; j >= 0 ; --j ) {
6016
+ if ( jQuery.nodeName( tbody[ j ], "tbody" ) && !tbody[ j ].childNodes.length ) {
6017
+ tbody[ j ].parentNode.removeChild( tbody[ j ] );
6018
+ }
5643
6019
  }
5644
6020
  }
5645
6021
 
5646
- }
6022
+ // IE completely kills leading whitespace when innerHTML is used
6023
+ if ( !jQuery.support.leadingWhitespace && rleadingWhitespace.test( elem ) ) {
6024
+ div.insertBefore( context.createTextNode( rleadingWhitespace.exec(elem)[0] ), div.firstChild );
6025
+ }
5647
6026
 
5648
- // IE completely kills leading whitespace when innerHTML is used
5649
- if ( !jQuery.support.leadingWhitespace && rleadingWhitespace.test( elem ) ) {
5650
- div.insertBefore( context.createTextNode( rleadingWhitespace.exec(elem)[0] ), div.firstChild );
6027
+ elem = div.childNodes;
5651
6028
  }
6029
+ }
5652
6030
 
5653
- elem = div.childNodes;
6031
+ // Resets defaultChecked for any radios and checkboxes
6032
+ // about to be appended to the DOM in IE 6/7 (#8060)
6033
+ var len;
6034
+ if ( !jQuery.support.appendChecked ) {
6035
+ if ( elem[0] && typeof (len = elem.length) === "number" ) {
6036
+ for ( i = 0; i < len; i++ ) {
6037
+ findInputs( elem[i] );
6038
+ }
6039
+ } else {
6040
+ findInputs( elem );
6041
+ }
5654
6042
  }
5655
6043
 
5656
6044
  if ( elem.nodeType ) {
@@ -5661,13 +6049,18 @@ jQuery.extend({
5661
6049
  }
5662
6050
 
5663
6051
  if ( fragment ) {
6052
+ checkScriptType = function( elem ) {
6053
+ return !elem.type || rscriptType.test( elem.type );
6054
+ };
5664
6055
  for ( i = 0; ret[i]; i++ ) {
5665
6056
  if ( scripts && jQuery.nodeName( ret[i], "script" ) && (!ret[i].type || ret[i].type.toLowerCase() === "text/javascript") ) {
5666
6057
  scripts.push( ret[i].parentNode ? ret[i].parentNode.removeChild( ret[i] ) : ret[i] );
5667
6058
 
5668
6059
  } else {
5669
6060
  if ( ret[i].nodeType === 1 ) {
5670
- ret.splice.apply( ret, [i + 1, 0].concat(jQuery.makeArray(ret[i].getElementsByTagName("script"))) );
6061
+ var jsTags = jQuery.grep( ret[i].getElementsByTagName( "script" ), checkScriptType );
6062
+
6063
+ ret.splice.apply( ret, [i + 1, 0].concat( jsTags ) );
5671
6064
  }
5672
6065
  fragment.appendChild( ret[i] );
5673
6066
  }
@@ -5747,6 +6140,8 @@ var ralpha = /alpha\([^)]*\)/i,
5747
6140
  rupper = /([A-Z]|^ms)/g,
5748
6141
  rnumpx = /^-?\d+(?:px)?$/i,
5749
6142
  rnum = /^-?\d/,
6143
+ rrelNum = /^[+\-]=/,
6144
+ rrelNumFilter = /[^+\-\.\de]+/g,
5750
6145
 
5751
6146
  cssShow = { position: "absolute", visibility: "hidden", display: "block" },
5752
6147
  cssWidth = [ "Left", "Right" ],
@@ -5797,7 +6192,9 @@ jQuery.extend({
5797
6192
  "fontWeight": true,
5798
6193
  "opacity": true,
5799
6194
  "zoom": true,
5800
- "lineHeight": true
6195
+ "lineHeight": true,
6196
+ "widows": true,
6197
+ "orphans": true
5801
6198
  },
5802
6199
 
5803
6200
  // Add in properties whose names you wish to fix before
@@ -5815,20 +6212,27 @@ jQuery.extend({
5815
6212
  }
5816
6213
 
5817
6214
  // Make sure that we're working with the right name
5818
- var ret, origName = jQuery.camelCase( name ),
6215
+ var ret, type, origName = jQuery.camelCase( name ),
5819
6216
  style = elem.style, hooks = jQuery.cssHooks[ origName ];
5820
6217
 
5821
6218
  name = jQuery.cssProps[ origName ] || origName;
5822
6219
 
5823
6220
  // Check if we're setting a value
5824
6221
  if ( value !== undefined ) {
6222
+ type = typeof value;
6223
+
5825
6224
  // Make sure that NaN and null values aren't set. See: #7116
5826
- if ( typeof value === "number" && isNaN( value ) || value == null ) {
6225
+ if ( type === "number" && isNaN( value ) || value == null ) {
5827
6226
  return;
5828
6227
  }
5829
6228
 
6229
+ // convert relative number strings (+= or -=) to relative numbers. #7345
6230
+ if ( type === "string" && rrelNum.test( value ) ) {
6231
+ value = +value.replace( rrelNumFilter, "" ) + parseFloat( jQuery.css( elem, name ) );
6232
+ }
6233
+
5830
6234
  // If a number was passed in, add 'px' to the (except for certain CSS properties)
5831
- if ( typeof value === "number" && !jQuery.cssNumber[ origName ] ) {
6235
+ if ( type === "number" && !jQuery.cssNumber[ origName ] ) {
5832
6236
  value += "px";
5833
6237
  }
5834
6238
 
@@ -5853,11 +6257,17 @@ jQuery.extend({
5853
6257
  },
5854
6258
 
5855
6259
  css: function( elem, name, extra ) {
6260
+ var ret, hooks;
6261
+
5856
6262
  // Make sure that we're working with the right name
5857
- var ret, origName = jQuery.camelCase( name ),
5858
- hooks = jQuery.cssHooks[ origName ];
6263
+ name = jQuery.camelCase( name );
6264
+ hooks = jQuery.cssHooks[ name ];
6265
+ name = jQuery.cssProps[ name ] || name;
5859
6266
 
5860
- name = jQuery.cssProps[ origName ] || origName;
6267
+ // cssFloat needs a special treatment
6268
+ if ( name === "cssFloat" ) {
6269
+ name = "float";
6270
+ }
5861
6271
 
5862
6272
  // If a hook was provided get the computed value from there
5863
6273
  if ( hooks && "get" in hooks && (ret = hooks.get( elem, true, extra )) !== undefined ) {
@@ -5865,7 +6275,7 @@ jQuery.extend({
5865
6275
 
5866
6276
  // Otherwise, if a way to get the computed value exists, use that
5867
6277
  } else if ( curCSS ) {
5868
- return curCSS( elem, name, origName );
6278
+ return curCSS( elem, name );
5869
6279
  }
5870
6280
  },
5871
6281
 
@@ -5956,27 +6366,28 @@ if ( !jQuery.support.opacity ) {
5956
6366
  jQuery.cssHooks.opacity = {
5957
6367
  get: function( elem, computed ) {
5958
6368
  // IE uses filters for opacity
5959
- return ropacity.test((computed && elem.currentStyle ? elem.currentStyle.filter : elem.style.filter) || "") ?
5960
- (parseFloat(RegExp.$1) / 100) + "" :
6369
+ return ropacity.test( (computed && elem.currentStyle ? elem.currentStyle.filter : elem.style.filter) || "" ) ?
6370
+ ( parseFloat( RegExp.$1 ) / 100 ) + "" :
5961
6371
  computed ? "1" : "";
5962
6372
  },
5963
6373
 
5964
6374
  set: function( elem, value ) {
5965
- var style = elem.style;
6375
+ var style = elem.style,
6376
+ currentStyle = elem.currentStyle;
5966
6377
 
5967
6378
  // IE has trouble with opacity if it does not have layout
5968
6379
  // Force it by setting the zoom level
5969
6380
  style.zoom = 1;
5970
6381
 
5971
6382
  // Set the alpha filter to set the opacity
5972
- var opacity = jQuery.isNaN(value) ?
6383
+ var opacity = jQuery.isNaN( value ) ?
5973
6384
  "" :
5974
6385
  "alpha(opacity=" + value * 100 + ")",
5975
- filter = style.filter || "";
6386
+ filter = currentStyle && currentStyle.filter || style.filter || "";
5976
6387
 
5977
- style.filter = ralpha.test(filter) ?
5978
- filter.replace(ralpha, opacity) :
5979
- style.filter + ' ' + opacity;
6388
+ style.filter = ralpha.test( filter ) ?
6389
+ filter.replace( ralpha, opacity ) :
6390
+ filter + " " + opacity;
5980
6391
  }
5981
6392
  };
5982
6393
  }
@@ -6004,7 +6415,7 @@ jQuery(function() {
6004
6415
  });
6005
6416
 
6006
6417
  if ( document.defaultView && document.defaultView.getComputedStyle ) {
6007
- getComputedStyle = function( elem, newName, name ) {
6418
+ getComputedStyle = function( elem, name ) {
6008
6419
  var ret, defaultView, computedStyle;
6009
6420
 
6010
6421
  name = name.replace( rupper, "-$1" ).toLowerCase();
@@ -6115,10 +6526,6 @@ var r20 = /%20/g,
6115
6526
  rselectTextarea = /^(?:select|textarea)/i,
6116
6527
  rspacesAjax = /\s+/,
6117
6528
  rts = /([?&])_=[^&]*/,
6118
- rucHeaders = /(^|\-)([a-z])/g,
6119
- rucHeadersFunc = function( _, $1, $2 ) {
6120
- return $1 + $2.toUpperCase();
6121
- },
6122
6529
  rurl = /^([\w\+\.\-]+:)(?:\/\/([^\/?#:]*)(?::(\d+))?)?/,
6123
6530
 
6124
6531
  // Keep a copy of the old load method
@@ -6149,9 +6556,9 @@ var r20 = /%20/g,
6149
6556
  ajaxLocParts;
6150
6557
 
6151
6558
  // #8138, IE may throw an exception when accessing
6152
- // a field from document.location if document.domain has been set
6559
+ // a field from window.location if document.domain has been set
6153
6560
  try {
6154
- ajaxLocation = document.location.href;
6561
+ ajaxLocation = location.href;
6155
6562
  } catch( e ) {
6156
6563
  // Use the href attribute of an A element
6157
6564
  // since IE will modify it given document.location
@@ -6199,7 +6606,7 @@ function addToPrefiltersOrTransports( structure ) {
6199
6606
  };
6200
6607
  }
6201
6608
 
6202
- //Base inspection function for prefilters and transports
6609
+ // Base inspection function for prefilters and transports
6203
6610
  function inspectPrefiltersOrTransports( structure, options, originalOptions, jqXHR,
6204
6611
  dataType /* internal */, inspected /* internal */ ) {
6205
6612
 
@@ -6348,7 +6755,7 @@ jQuery.each( "ajaxStart ajaxStop ajaxComplete ajaxError ajaxSuccess ajaxSend".sp
6348
6755
  jQuery.fn[ o ] = function( f ){
6349
6756
  return this.bind( o, f );
6350
6757
  };
6351
- } );
6758
+ });
6352
6759
 
6353
6760
  jQuery.each( [ "get", "post" ], function( i, method ) {
6354
6761
  jQuery[ method ] = function( url, data, callback, type ) {
@@ -6367,7 +6774,7 @@ jQuery.each( [ "get", "post" ], function( i, method ) {
6367
6774
  dataType: type
6368
6775
  });
6369
6776
  };
6370
- } );
6777
+ });
6371
6778
 
6372
6779
  jQuery.extend({
6373
6780
 
@@ -6493,6 +6900,7 @@ jQuery.extend({
6493
6900
  ifModifiedKey,
6494
6901
  // Headers (they are sent all at once)
6495
6902
  requestHeaders = {},
6903
+ requestHeadersNames = {},
6496
6904
  // Response headers
6497
6905
  responseHeadersString,
6498
6906
  responseHeaders,
@@ -6516,7 +6924,9 @@ jQuery.extend({
6516
6924
  // Caches the header
6517
6925
  setRequestHeader: function( name, value ) {
6518
6926
  if ( !state ) {
6519
- requestHeaders[ name.toLowerCase().replace( rucHeaders, rucHeadersFunc ) ] = value;
6927
+ var lname = name.toLowerCase();
6928
+ name = requestHeadersNames[ lname ] = requestHeadersNames[ lname ] || name;
6929
+ requestHeaders[ name ] = value;
6520
6930
  }
6521
6931
  return this;
6522
6932
  },
@@ -6764,24 +7174,27 @@ jQuery.extend({
6764
7174
 
6765
7175
  // Set the correct header, if data is being sent
6766
7176
  if ( s.data && s.hasContent && s.contentType !== false || options.contentType ) {
6767
- requestHeaders[ "Content-Type" ] = s.contentType;
7177
+ jqXHR.setRequestHeader( "Content-Type", s.contentType );
6768
7178
  }
6769
7179
 
6770
7180
  // Set the If-Modified-Since and/or If-None-Match header, if in ifModified mode.
6771
7181
  if ( s.ifModified ) {
6772
7182
  ifModifiedKey = ifModifiedKey || s.url;
6773
7183
  if ( jQuery.lastModified[ ifModifiedKey ] ) {
6774
- requestHeaders[ "If-Modified-Since" ] = jQuery.lastModified[ ifModifiedKey ];
7184
+ jqXHR.setRequestHeader( "If-Modified-Since", jQuery.lastModified[ ifModifiedKey ] );
6775
7185
  }
6776
7186
  if ( jQuery.etag[ ifModifiedKey ] ) {
6777
- requestHeaders[ "If-None-Match" ] = jQuery.etag[ ifModifiedKey ];
7187
+ jqXHR.setRequestHeader( "If-None-Match", jQuery.etag[ ifModifiedKey ] );
6778
7188
  }
6779
7189
  }
6780
7190
 
6781
7191
  // Set the Accepts header for the server, depending on the dataType
6782
- requestHeaders.Accept = s.dataTypes[ 0 ] && s.accepts[ s.dataTypes[0] ] ?
6783
- s.accepts[ s.dataTypes[0] ] + ( s.dataTypes[ 0 ] !== "*" ? ", */*; q=0.01" : "" ) :
6784
- s.accepts[ "*" ];
7192
+ jqXHR.setRequestHeader(
7193
+ "Accept",
7194
+ s.dataTypes[ 0 ] && s.accepts[ s.dataTypes[0] ] ?
7195
+ s.accepts[ s.dataTypes[0] ] + ( s.dataTypes[ 0 ] !== "*" ? ", */*; q=0.01" : "" ) :
7196
+ s.accepts[ "*" ]
7197
+ );
6785
7198
 
6786
7199
  // Check for headers option
6787
7200
  for ( i in s.headers ) {
@@ -6857,7 +7270,7 @@ jQuery.extend({
6857
7270
  // Serialize the form elements
6858
7271
  jQuery.each( a, function() {
6859
7272
  add( this.name, this.value );
6860
- } );
7273
+ });
6861
7274
 
6862
7275
  } else {
6863
7276
  // If traditional, encode the "old" way (the way 1.3.2 or older
@@ -6873,7 +7286,7 @@ jQuery.extend({
6873
7286
  });
6874
7287
 
6875
7288
  function buildParams( prefix, obj, traditional, add ) {
6876
- if ( jQuery.isArray( obj ) && obj.length ) {
7289
+ if ( jQuery.isArray( obj ) ) {
6877
7290
  // Serialize array item.
6878
7291
  jQuery.each( obj, function( i, v ) {
6879
7292
  if ( traditional || rbracket.test( prefix ) ) {
@@ -6893,16 +7306,9 @@ function buildParams( prefix, obj, traditional, add ) {
6893
7306
  });
6894
7307
 
6895
7308
  } else if ( !traditional && obj != null && typeof obj === "object" ) {
6896
- // If we see an array here, it is empty and should be treated as an empty
6897
- // object
6898
- if ( jQuery.isArray( obj ) || jQuery.isEmptyObject( obj ) ) {
6899
- add( prefix, "" );
6900
-
6901
7309
  // Serialize object item.
6902
- } else {
6903
- for ( var name in obj ) {
6904
- buildParams( prefix + "[" + name + "]", obj[ name ], traditional, add );
6905
- }
7310
+ for ( var name in obj ) {
7311
+ buildParams( prefix + "[" + name + "]", obj[ name ], traditional, add );
6906
7312
  }
6907
7313
 
6908
7314
  } else {
@@ -7095,13 +7501,12 @@ jQuery.ajaxSetup({
7095
7501
  // Detect, normalize options and install callbacks for jsonp requests
7096
7502
  jQuery.ajaxPrefilter( "json jsonp", function( s, originalSettings, jqXHR ) {
7097
7503
 
7098
- var dataIsString = ( typeof s.data === "string" );
7504
+ var inspectData = s.contentType === "application/x-www-form-urlencoded" &&
7505
+ ( typeof s.data === "string" );
7099
7506
 
7100
7507
  if ( s.dataTypes[ 0 ] === "jsonp" ||
7101
- originalSettings.jsonpCallback ||
7102
- originalSettings.jsonp != null ||
7103
7508
  s.jsonp !== false && ( jsre.test( s.url ) ||
7104
- dataIsString && jsre.test( s.data ) ) ) {
7509
+ inspectData && jsre.test( s.data ) ) ) {
7105
7510
 
7106
7511
  var responseContainer,
7107
7512
  jsonpCallback = s.jsonpCallback =
@@ -7109,20 +7514,12 @@ jQuery.ajaxPrefilter( "json jsonp", function( s, originalSettings, jqXHR ) {
7109
7514
  previous = window[ jsonpCallback ],
7110
7515
  url = s.url,
7111
7516
  data = s.data,
7112
- replace = "$1" + jsonpCallback + "$2",
7113
- cleanUp = function() {
7114
- // Set callback back to previous value
7115
- window[ jsonpCallback ] = previous;
7116
- // Call if it was a function and we have a response
7117
- if ( responseContainer && jQuery.isFunction( previous ) ) {
7118
- window[ jsonpCallback ]( responseContainer[ 0 ] );
7119
- }
7120
- };
7517
+ replace = "$1" + jsonpCallback + "$2";
7121
7518
 
7122
7519
  if ( s.jsonp !== false ) {
7123
7520
  url = url.replace( jsre, replace );
7124
7521
  if ( s.url === url ) {
7125
- if ( dataIsString ) {
7522
+ if ( inspectData ) {
7126
7523
  data = data.replace( jsre, replace );
7127
7524
  }
7128
7525
  if ( s.data === data ) {
@@ -7140,8 +7537,15 @@ jQuery.ajaxPrefilter( "json jsonp", function( s, originalSettings, jqXHR ) {
7140
7537
  responseContainer = [ response ];
7141
7538
  };
7142
7539
 
7143
- // Install cleanUp function
7144
- jqXHR.then( cleanUp, cleanUp );
7540
+ // Clean-up function
7541
+ jqXHR.always(function() {
7542
+ // Set callback back to previous value
7543
+ window[ jsonpCallback ] = previous;
7544
+ // Call if it was a function and we have a response
7545
+ if ( responseContainer && jQuery.isFunction( previous ) ) {
7546
+ window[ jsonpCallback ]( responseContainer[ 0 ] );
7547
+ }
7548
+ });
7145
7549
 
7146
7550
  // Use data converter to retrieve json after script execution
7147
7551
  s.converters["script json"] = function() {
@@ -7157,7 +7561,7 @@ jQuery.ajaxPrefilter( "json jsonp", function( s, originalSettings, jqXHR ) {
7157
7561
  // Delegate to script
7158
7562
  return "script";
7159
7563
  }
7160
- } );
7564
+ });
7161
7565
 
7162
7566
 
7163
7567
 
@@ -7187,7 +7591,7 @@ jQuery.ajaxPrefilter( "script", function( s ) {
7187
7591
  s.type = "GET";
7188
7592
  s.global = false;
7189
7593
  }
7190
- } );
7594
+ });
7191
7595
 
7192
7596
  // Bind script tag hack transport
7193
7597
  jQuery.ajaxTransport( "script", function(s) {
@@ -7215,7 +7619,7 @@ jQuery.ajaxTransport( "script", function(s) {
7215
7619
  // Attach handlers for all browsers
7216
7620
  script.onload = script.onreadystatechange = function( _, isAbort ) {
7217
7621
 
7218
- if ( !script.readyState || /loaded|complete/.test( script.readyState ) ) {
7622
+ if ( isAbort || !script.readyState || /loaded|complete/.test( script.readyState ) ) {
7219
7623
 
7220
7624
  // Handle memory leak in IE
7221
7625
  script.onload = script.onreadystatechange = null;
@@ -7246,27 +7650,20 @@ jQuery.ajaxTransport( "script", function(s) {
7246
7650
  }
7247
7651
  };
7248
7652
  }
7249
- } );
7250
-
7251
-
7653
+ });
7252
7654
 
7253
7655
 
7254
- var // #5280: next active xhr id and list of active xhrs' callbacks
7255
- xhrId = jQuery.now(),
7256
- xhrCallbacks,
7257
7656
 
7258
- // XHR used to determine supports properties
7259
- testXHR;
7260
7657
 
7261
- // #5280: Internet Explorer will keep connections alive if we don't abort on unload
7262
- function xhrOnUnloadAbort() {
7263
- jQuery( window ).unload(function() {
7658
+ var // #5280: Internet Explorer will keep connections alive if we don't abort on unload
7659
+ xhrOnUnloadAbort = window.ActiveXObject ? function() {
7264
7660
  // Abort all pending requests
7265
7661
  for ( var key in xhrCallbacks ) {
7266
7662
  xhrCallbacks[ key ]( 0, 1 );
7267
7663
  }
7268
- });
7269
- }
7664
+ } : false,
7665
+ xhrId = 0,
7666
+ xhrCallbacks;
7270
7667
 
7271
7668
  // Functions to create xhrs
7272
7669
  function createStandardXHR() {
@@ -7296,15 +7693,13 @@ jQuery.ajaxSettings.xhr = window.ActiveXObject ?
7296
7693
  // For all other browsers, use the standard XMLHttpRequest object
7297
7694
  createStandardXHR;
7298
7695
 
7299
- // Test if we can create an xhr object
7300
- testXHR = jQuery.ajaxSettings.xhr();
7301
- jQuery.support.ajax = !!testXHR;
7302
-
7303
- // Does this browser support crossDomain XHR requests
7304
- jQuery.support.cors = testXHR && ( "withCredentials" in testXHR );
7305
-
7306
- // No need for the temporary xhr anymore
7307
- testXHR = undefined;
7696
+ // Determine support properties
7697
+ (function( xhr ) {
7698
+ jQuery.extend( jQuery.support, {
7699
+ ajax: !!xhr,
7700
+ cors: !!xhr && ( "withCredentials" in xhr )
7701
+ });
7702
+ })( jQuery.ajaxSettings.xhr() );
7308
7703
 
7309
7704
  // Create transport if the browser can provide an xhr
7310
7705
  if ( jQuery.support.ajax ) {
@@ -7387,7 +7782,9 @@ if ( jQuery.support.ajax ) {
7387
7782
  // Do not keep as active anymore
7388
7783
  if ( handle ) {
7389
7784
  xhr.onreadystatechange = jQuery.noop;
7390
- delete xhrCallbacks[ handle ];
7785
+ if ( xhrOnUnloadAbort ) {
7786
+ delete xhrCallbacks[ handle ];
7787
+ }
7391
7788
  }
7392
7789
 
7393
7790
  // If it's an abort
@@ -7448,15 +7845,18 @@ if ( jQuery.support.ajax ) {
7448
7845
  if ( !s.async || xhr.readyState === 4 ) {
7449
7846
  callback();
7450
7847
  } else {
7451
- // Create the active xhrs callbacks list if needed
7452
- // and attach the unload handler
7453
- if ( !xhrCallbacks ) {
7454
- xhrCallbacks = {};
7455
- xhrOnUnloadAbort();
7848
+ handle = ++xhrId;
7849
+ if ( xhrOnUnloadAbort ) {
7850
+ // Create the active xhrs callbacks list if needed
7851
+ // and attach the unload handler
7852
+ if ( !xhrCallbacks ) {
7853
+ xhrCallbacks = {};
7854
+ jQuery( window ).unload( xhrOnUnloadAbort );
7855
+ }
7856
+ // Add to list of active xhrs callbacks
7857
+ xhrCallbacks[ handle ] = callback;
7456
7858
  }
7457
- // Add to list of active xhrs callbacks
7458
- handle = xhrId++;
7459
- xhr.onreadystatechange = xhrCallbacks[ handle ] = callback;
7859
+ xhr.onreadystatechange = callback;
7460
7860
  }
7461
7861
  },
7462
7862
 
@@ -7474,6 +7874,7 @@ if ( jQuery.support.ajax ) {
7474
7874
 
7475
7875
 
7476
7876
  var elemdisplay = {},
7877
+ iframe, iframeDoc,
7477
7878
  rfxtypes = /^(?:toggle|show|hide)$/,
7478
7879
  rfxnum = /^([+\-]=)?([\d+.\-]+)([a-z%]*)$/i,
7479
7880
  timerId,
@@ -7484,7 +7885,11 @@ var elemdisplay = {},
7484
7885
  [ "width", "marginLeft", "marginRight", "paddingLeft", "paddingRight" ],
7485
7886
  // opacity animations
7486
7887
  [ "opacity" ]
7487
- ];
7888
+ ],
7889
+ fxNow,
7890
+ requestAnimationFrame = window.webkitRequestAnimationFrame ||
7891
+ window.mozRequestAnimationFrame ||
7892
+ window.oRequestAnimationFrame;
7488
7893
 
7489
7894
  jQuery.fn.extend({
7490
7895
  show: function( speed, easing, callback ) {
@@ -7496,19 +7901,22 @@ jQuery.fn.extend({
7496
7901
  } else {
7497
7902
  for ( var i = 0, j = this.length; i < j; i++ ) {
7498
7903
  elem = this[i];
7499
- display = elem.style.display;
7500
7904
 
7501
- // Reset the inline display of this element to learn if it is
7502
- // being hidden by cascaded rules or not
7503
- if ( !jQuery._data(elem, "olddisplay") && display === "none" ) {
7504
- display = elem.style.display = "";
7505
- }
7905
+ if ( elem.style ) {
7906
+ display = elem.style.display;
7907
+
7908
+ // Reset the inline display of this element to learn if it is
7909
+ // being hidden by cascaded rules or not
7910
+ if ( !jQuery._data(elem, "olddisplay") && display === "none" ) {
7911
+ display = elem.style.display = "";
7912
+ }
7506
7913
 
7507
- // Set elements which have been overridden with display: none
7508
- // in a stylesheet to whatever the default browser style is
7509
- // for such an element
7510
- if ( display === "" && jQuery.css( elem, "display" ) === "none" ) {
7511
- jQuery._data(elem, "olddisplay", defaultDisplay(elem.nodeName));
7914
+ // Set elements which have been overridden with display: none
7915
+ // in a stylesheet to whatever the default browser style is
7916
+ // for such an element
7917
+ if ( display === "" && jQuery.css( elem, "display" ) === "none" ) {
7918
+ jQuery._data(elem, "olddisplay", defaultDisplay(elem.nodeName));
7919
+ }
7512
7920
  }
7513
7921
  }
7514
7922
 
@@ -7516,10 +7924,13 @@ jQuery.fn.extend({
7516
7924
  // to avoid the constant reflow
7517
7925
  for ( i = 0; i < j; i++ ) {
7518
7926
  elem = this[i];
7519
- display = elem.style.display;
7520
7927
 
7521
- if ( display === "" || display === "none" ) {
7522
- elem.style.display = jQuery._data(elem, "olddisplay") || "";
7928
+ if ( elem.style ) {
7929
+ display = elem.style.display;
7930
+
7931
+ if ( display === "" || display === "none" ) {
7932
+ elem.style.display = jQuery._data(elem, "olddisplay") || "";
7933
+ }
7523
7934
  }
7524
7935
  }
7525
7936
 
@@ -7533,17 +7944,21 @@ jQuery.fn.extend({
7533
7944
 
7534
7945
  } else {
7535
7946
  for ( var i = 0, j = this.length; i < j; i++ ) {
7536
- var display = jQuery.css( this[i], "display" );
7947
+ if ( this[i].style ) {
7948
+ var display = jQuery.css( this[i], "display" );
7537
7949
 
7538
- if ( display !== "none" && !jQuery._data( this[i], "olddisplay" ) ) {
7539
- jQuery._data( this[i], "olddisplay", display );
7950
+ if ( display !== "none" && !jQuery._data( this[i], "olddisplay" ) ) {
7951
+ jQuery._data( this[i], "olddisplay", display );
7952
+ }
7540
7953
  }
7541
7954
  }
7542
7955
 
7543
7956
  // Set the display of the elements in a second loop
7544
7957
  // to avoid the constant reflow
7545
7958
  for ( i = 0; i < j; i++ ) {
7546
- this[i].style.display = "none";
7959
+ if ( this[i].style ) {
7960
+ this[i].style.display = "none";
7961
+ }
7547
7962
  }
7548
7963
 
7549
7964
  return this;
@@ -7581,32 +7996,43 @@ jQuery.fn.extend({
7581
7996
  var optall = jQuery.speed(speed, easing, callback);
7582
7997
 
7583
7998
  if ( jQuery.isEmptyObject( prop ) ) {
7584
- return this.each( optall.complete );
7999
+ return this.each( optall.complete, [ false ] );
7585
8000
  }
7586
8001
 
7587
8002
  return this[ optall.queue === false ? "each" : "queue" ](function() {
7588
8003
  // XXX 'this' does not always have a nodeName when running the
7589
8004
  // test suite
7590
8005
 
7591
- var opt = jQuery.extend({}, optall), p,
8006
+ if ( optall.queue === false ) {
8007
+ jQuery._mark( this );
8008
+ }
8009
+
8010
+ var opt = jQuery.extend({}, optall),
7592
8011
  isElement = this.nodeType === 1,
7593
8012
  hidden = isElement && jQuery(this).is(":hidden"),
7594
- self = this;
8013
+ name, val, p,
8014
+ display, e,
8015
+ parts, start, end, unit;
8016
+
8017
+ // will store per property easing and be used to determine when an animation is complete
8018
+ opt.animatedProperties = {};
7595
8019
 
7596
8020
  for ( p in prop ) {
7597
- var name = jQuery.camelCase( p );
7598
8021
 
8022
+ // property name normalization
8023
+ name = jQuery.camelCase( p );
7599
8024
  if ( p !== name ) {
7600
8025
  prop[ name ] = prop[ p ];
7601
8026
  delete prop[ p ];
7602
- p = name;
7603
8027
  }
7604
8028
 
7605
- if ( prop[p] === "hide" && hidden || prop[p] === "show" && !hidden ) {
8029
+ val = prop[name];
8030
+
8031
+ if ( val === "hide" && hidden || val === "show" && !hidden ) {
7606
8032
  return opt.complete.call(this);
7607
8033
  }
7608
8034
 
7609
- if ( isElement && ( p === "height" || p === "width" ) ) {
8035
+ if ( isElement && ( name === "height" || name === "width" ) ) {
7610
8036
  // Make sure that nothing sneaks out
7611
8037
  // Record all 3 overflow attributes because IE does not
7612
8038
  // change the overflow attribute when overflowX and
@@ -7622,7 +8048,7 @@ jQuery.fn.extend({
7622
8048
  this.style.display = "inline-block";
7623
8049
 
7624
8050
  } else {
7625
- var display = defaultDisplay(this.nodeName);
8051
+ display = defaultDisplay(this.nodeName);
7626
8052
 
7627
8053
  // inline-level elements accept inline-block;
7628
8054
  // block-level elements need to be inline with layout
@@ -7637,38 +8063,37 @@ jQuery.fn.extend({
7637
8063
  }
7638
8064
  }
7639
8065
 
7640
- if ( jQuery.isArray( prop[p] ) ) {
7641
- // Create (if needed) and add to specialEasing
7642
- (opt.specialEasing = opt.specialEasing || {})[p] = prop[p][1];
7643
- prop[p] = prop[p][0];
7644
- }
8066
+ // easing resolution: per property > opt.specialEasing > opt.easing > 'swing' (default)
8067
+ opt.animatedProperties[name] = jQuery.isArray( val ) ?
8068
+ val[1]:
8069
+ opt.specialEasing && opt.specialEasing[name] || opt.easing || 'swing';
7645
8070
  }
7646
8071
 
7647
8072
  if ( opt.overflow != null ) {
7648
8073
  this.style.overflow = "hidden";
7649
8074
  }
7650
8075
 
7651
- opt.curAnim = jQuery.extend({}, prop);
8076
+ for ( p in prop ) {
8077
+ e = new jQuery.fx( this, opt, p );
7652
8078
 
7653
- jQuery.each( prop, function( name, val ) {
7654
- var e = new jQuery.fx( self, opt, name );
8079
+ val = prop[p];
7655
8080
 
7656
8081
  if ( rfxtypes.test(val) ) {
7657
- e[ val === "toggle" ? hidden ? "show" : "hide" : val ]( prop );
8082
+ e[ val === "toggle" ? hidden ? "show" : "hide" : val ]();
7658
8083
 
7659
8084
  } else {
7660
- var parts = rfxnum.exec(val),
7661
- start = e.cur();
8085
+ parts = rfxnum.exec(val);
8086
+ start = e.cur();
7662
8087
 
7663
8088
  if ( parts ) {
7664
- var end = parseFloat( parts[2] ),
7665
- unit = parts[3] || ( jQuery.cssNumber[ name ] ? "" : "px" );
8089
+ end = parseFloat( parts[2] );
8090
+ unit = parts[3] || ( jQuery.cssNumber[ name ] ? "" : "px" );
7666
8091
 
7667
8092
  // We need to compute starting value
7668
8093
  if ( unit !== "px" ) {
7669
- jQuery.style( self, name, (end || 1) + unit);
8094
+ jQuery.style( this, p, (end || 1) + unit);
7670
8095
  start = ((end || 1) / e.cur()) * start;
7671
- jQuery.style( self, name, start + unit);
8096
+ jQuery.style( this, p, start + unit);
7672
8097
  }
7673
8098
 
7674
8099
  // If a +=/-= token was provided, we're doing a relative animation
@@ -7682,7 +8107,7 @@ jQuery.fn.extend({
7682
8107
  e.custom( start, val, "" );
7683
8108
  }
7684
8109
  }
7685
- });
8110
+ }
7686
8111
 
7687
8112
  // For JS strict compliance
7688
8113
  return true;
@@ -7690,15 +8115,19 @@ jQuery.fn.extend({
7690
8115
  },
7691
8116
 
7692
8117
  stop: function( clearQueue, gotoEnd ) {
7693
- var timers = jQuery.timers;
7694
-
7695
8118
  if ( clearQueue ) {
7696
8119
  this.queue([]);
7697
8120
  }
7698
8121
 
7699
8122
  this.each(function() {
8123
+ var timers = jQuery.timers,
8124
+ i = timers.length;
8125
+ // clear marker counters if we know they won't be
8126
+ if ( !gotoEnd ) {
8127
+ jQuery._unmark( true, this );
8128
+ }
7700
8129
  // go in reverse order so anything added to the queue during the loop is ignored
7701
- for ( var i = timers.length - 1; i >= 0; i-- ) {
8130
+ while ( i-- ) {
7702
8131
  if ( timers[i].elem === this ) {
7703
8132
  if (gotoEnd) {
7704
8133
  // force the next step to be the last
@@ -7720,6 +8149,17 @@ jQuery.fn.extend({
7720
8149
 
7721
8150
  });
7722
8151
 
8152
+ // Animations created synchronously will run synchronously
8153
+ function createFxNow() {
8154
+ setTimeout( clearFxNow, 0 );
8155
+ return ( fxNow = jQuery.now() );
8156
+ }
8157
+
8158
+ function clearFxNow() {
8159
+ fxNow = undefined;
8160
+ }
8161
+
8162
+ // Generate parameters to create a standard animation
7723
8163
  function genFx( type, num ) {
7724
8164
  var obj = {};
7725
8165
 
@@ -7758,10 +8198,13 @@ jQuery.extend({
7758
8198
 
7759
8199
  // Queueing
7760
8200
  opt.old = opt.complete;
7761
- opt.complete = function() {
8201
+ opt.complete = function( noUnmark ) {
7762
8202
  if ( opt.queue !== false ) {
7763
- jQuery(this).dequeue();
8203
+ jQuery.dequeue( this );
8204
+ } else if ( noUnmark !== false ) {
8205
+ jQuery._unmark( this );
7764
8206
  }
8207
+
7765
8208
  if ( jQuery.isFunction( opt.old ) ) {
7766
8209
  opt.old.call( this );
7767
8210
  }
@@ -7786,9 +8229,7 @@ jQuery.extend({
7786
8229
  this.elem = elem;
7787
8230
  this.prop = prop;
7788
8231
 
7789
- if ( !options.orig ) {
7790
- options.orig = {};
7791
- }
8232
+ options.orig = options.orig || {};
7792
8233
  }
7793
8234
 
7794
8235
  });
@@ -7820,9 +8261,10 @@ jQuery.fx.prototype = {
7820
8261
  // Start an animation from one number to another
7821
8262
  custom: function( from, to, unit ) {
7822
8263
  var self = this,
7823
- fx = jQuery.fx;
8264
+ fx = jQuery.fx,
8265
+ raf;
7824
8266
 
7825
- this.startTime = jQuery.now();
8267
+ this.startTime = fxNow || createFxNow();
7826
8268
  this.start = from;
7827
8269
  this.end = to;
7828
8270
  this.unit = unit || this.unit || ( jQuery.cssNumber[ this.prop ] ? "" : "px" );
@@ -7836,7 +8278,20 @@ jQuery.fx.prototype = {
7836
8278
  t.elem = this.elem;
7837
8279
 
7838
8280
  if ( t() && jQuery.timers.push(t) && !timerId ) {
7839
- timerId = setInterval(fx.tick, fx.interval);
8281
+ // Use requestAnimationFrame instead of setInterval if available
8282
+ if ( requestAnimationFrame ) {
8283
+ timerId = 1;
8284
+ raf = function() {
8285
+ // When timerId gets set to null at any point, this stops
8286
+ if ( timerId ) {
8287
+ requestAnimationFrame( raf );
8288
+ fx.tick();
8289
+ }
8290
+ };
8291
+ requestAnimationFrame( raf );
8292
+ } else {
8293
+ timerId = setInterval( fx.tick, fx.interval );
8294
+ }
7840
8295
  }
7841
8296
  },
7842
8297
 
@@ -7867,60 +8322,64 @@ jQuery.fx.prototype = {
7867
8322
 
7868
8323
  // Each step of an animation
7869
8324
  step: function( gotoEnd ) {
7870
- var t = jQuery.now(), done = true;
8325
+ var t = fxNow || createFxNow(),
8326
+ done = true,
8327
+ elem = this.elem,
8328
+ options = this.options,
8329
+ i, n;
7871
8330
 
7872
- if ( gotoEnd || t >= this.options.duration + this.startTime ) {
8331
+ if ( gotoEnd || t >= options.duration + this.startTime ) {
7873
8332
  this.now = this.end;
7874
8333
  this.pos = this.state = 1;
7875
8334
  this.update();
7876
8335
 
7877
- this.options.curAnim[ this.prop ] = true;
8336
+ options.animatedProperties[ this.prop ] = true;
7878
8337
 
7879
- for ( var i in this.options.curAnim ) {
7880
- if ( this.options.curAnim[i] !== true ) {
8338
+ for ( i in options.animatedProperties ) {
8339
+ if ( options.animatedProperties[i] !== true ) {
7881
8340
  done = false;
7882
8341
  }
7883
8342
  }
7884
8343
 
7885
8344
  if ( done ) {
7886
8345
  // Reset the overflow
7887
- if ( this.options.overflow != null && !jQuery.support.shrinkWrapBlocks ) {
7888
- var elem = this.elem,
7889
- options = this.options;
8346
+ if ( options.overflow != null && !jQuery.support.shrinkWrapBlocks ) {
7890
8347
 
7891
8348
  jQuery.each( [ "", "X", "Y" ], function (index, value) {
7892
8349
  elem.style[ "overflow" + value ] = options.overflow[index];
7893
- } );
8350
+ });
7894
8351
  }
7895
8352
 
7896
8353
  // Hide the element if the "hide" operation was done
7897
- if ( this.options.hide ) {
7898
- jQuery(this.elem).hide();
8354
+ if ( options.hide ) {
8355
+ jQuery(elem).hide();
7899
8356
  }
7900
8357
 
7901
8358
  // Reset the properties, if the item has been hidden or shown
7902
- if ( this.options.hide || this.options.show ) {
7903
- for ( var p in this.options.curAnim ) {
7904
- jQuery.style( this.elem, p, this.options.orig[p] );
8359
+ if ( options.hide || options.show ) {
8360
+ for ( var p in options.animatedProperties ) {
8361
+ jQuery.style( elem, p, options.orig[p] );
7905
8362
  }
7906
8363
  }
7907
8364
 
7908
8365
  // Execute the complete function
7909
- this.options.complete.call( this.elem );
8366
+ options.complete.call( elem );
7910
8367
  }
7911
8368
 
7912
8369
  return false;
7913
8370
 
7914
8371
  } else {
7915
- var n = t - this.startTime;
7916
- this.state = n / this.options.duration;
7917
-
7918
- // Perform the easing function, defaults to swing
7919
- var specialEasing = this.options.specialEasing && this.options.specialEasing[this.prop];
7920
- var defaultEasing = this.options.easing || (jQuery.easing.swing ? "swing" : "linear");
7921
- this.pos = jQuery.easing[specialEasing || defaultEasing](this.state, n, 0, 1, this.options.duration);
7922
- this.now = this.start + ((this.end - this.start) * this.pos);
8372
+ // classical easing cannot be used with an Infinity duration
8373
+ if ( options.duration == Infinity ) {
8374
+ this.now = t;
8375
+ } else {
8376
+ n = t - this.startTime;
7923
8377
 
8378
+ this.state = n / options.duration;
8379
+ // Perform the easing function, defaults to swing
8380
+ this.pos = jQuery.easing[options.animatedProperties[this.prop]](this.state, n, 0, 1, options.duration);
8381
+ this.now = this.start + ((this.end - this.start) * this.pos);
8382
+ }
7924
8383
  // Perform the next step of the animation
7925
8384
  this.update();
7926
8385
  }
@@ -7931,11 +8390,11 @@ jQuery.fx.prototype = {
7931
8390
 
7932
8391
  jQuery.extend( jQuery.fx, {
7933
8392
  tick: function() {
7934
- var timers = jQuery.timers;
7935
-
7936
- for ( var i = 0; i < timers.length; i++ ) {
8393
+ var timers = jQuery.timers,
8394
+ i = timers.length;
8395
+ while ( i-- ) {
7937
8396
  if ( !timers[i]() ) {
7938
- timers.splice(i--, 1);
8397
+ timers.splice(i, 1);
7939
8398
  }
7940
8399
  }
7941
8400
 
@@ -7981,17 +8440,45 @@ if ( jQuery.expr && jQuery.expr.filters ) {
7981
8440
  };
7982
8441
  }
7983
8442
 
8443
+ // Try to restore the default display value of an element
7984
8444
  function defaultDisplay( nodeName ) {
8445
+
7985
8446
  if ( !elemdisplay[ nodeName ] ) {
7986
- var elem = jQuery("<" + nodeName + ">").appendTo("body"),
7987
- display = elem.css("display");
8447
+
8448
+ var elem = jQuery( "<" + nodeName + ">" ).appendTo( "body" ),
8449
+ display = elem.css( "display" );
7988
8450
 
7989
8451
  elem.remove();
7990
8452
 
8453
+ // If the simple way fails,
8454
+ // get element's real default display by attaching it to a temp iframe
7991
8455
  if ( display === "none" || display === "" ) {
7992
- display = "block";
8456
+ // No iframe to use yet, so create it
8457
+ if ( !iframe ) {
8458
+ iframe = document.createElement( "iframe" );
8459
+ iframe.frameBorder = iframe.width = iframe.height = 0;
8460
+ }
8461
+
8462
+ document.body.appendChild( iframe );
8463
+
8464
+ // Create a cacheable copy of the iframe document on first call.
8465
+ // IE and Opera will allow us to reuse the iframeDoc without re-writing the fake html
8466
+ // document to it, Webkit & Firefox won't allow reusing the iframe document
8467
+ if ( !iframeDoc || !iframe.createElement ) {
8468
+ iframeDoc = ( iframe.contentWindow || iframe.contentDocument ).document;
8469
+ iframeDoc.write( "<!doctype><html><body></body></html>" );
8470
+ }
8471
+
8472
+ elem = iframeDoc.createElement( nodeName );
8473
+
8474
+ iframeDoc.body.appendChild( elem );
8475
+
8476
+ display = jQuery.css( elem, "display" );
8477
+
8478
+ document.body.removeChild( iframe );
7993
8479
  }
7994
8480
 
8481
+ // Store the correct default display
7995
8482
  elemdisplay[ nodeName ] = display;
7996
8483
  }
7997
8484
 
@@ -8181,17 +8668,19 @@ jQuery.offset = {
8181
8668
  curOffset = curElem.offset(),
8182
8669
  curCSSTop = jQuery.css( elem, "top" ),
8183
8670
  curCSSLeft = jQuery.css( elem, "left" ),
8184
- calculatePosition = (position === "absolute" || position === "fixed") && jQuery.inArray('auto', [curCSSTop, curCSSLeft]) > -1,
8671
+ calculatePosition = (position === "absolute" || position === "fixed") && jQuery.inArray("auto", [curCSSTop, curCSSLeft]) > -1,
8185
8672
  props = {}, curPosition = {}, curTop, curLeft;
8186
8673
 
8187
8674
  // need to be able to calculate position if either top or left is auto and position is either absolute or fixed
8188
8675
  if ( calculatePosition ) {
8189
8676
  curPosition = curElem.position();
8677
+ curTop = curPosition.top;
8678
+ curLeft = curPosition.left;
8679
+ } else {
8680
+ curTop = parseFloat( curCSSTop ) || 0;
8681
+ curLeft = parseFloat( curCSSLeft ) || 0;
8190
8682
  }
8191
8683
 
8192
- curTop = calculatePosition ? curPosition.top : parseInt( curCSSTop, 10 ) || 0;
8193
- curLeft = calculatePosition ? curPosition.left : parseInt( curCSSLeft, 10 ) || 0;
8194
-
8195
8684
  if ( jQuery.isFunction( options ) ) {
8196
8685
  options = options.call( elem, i, curOffset );
8197
8686
  }
@@ -8260,29 +8749,16 @@ jQuery.fn.extend({
8260
8749
  jQuery.each( ["Left", "Top"], function( i, name ) {
8261
8750
  var method = "scroll" + name;
8262
8751
 
8263
- jQuery.fn[ method ] = function(val) {
8264
- var elem = this[0], win;
8265
-
8266
- if ( !elem ) {
8267
- return null;
8268
- }
8752
+ jQuery.fn[ method ] = function( val ) {
8753
+ var elem, win;
8269
8754
 
8270
- if ( val !== undefined ) {
8271
- // Set the scroll offset
8272
- return this.each(function() {
8273
- win = getWindow( this );
8755
+ if ( val === undefined ) {
8756
+ elem = this[ 0 ];
8274
8757
 
8275
- if ( win ) {
8276
- win.scrollTo(
8277
- !i ? val : jQuery(win).scrollLeft(),
8278
- i ? val : jQuery(win).scrollTop()
8279
- );
8758
+ if ( !elem ) {
8759
+ return null;
8760
+ }
8280
8761
 
8281
- } else {
8282
- this[ method ] = val;
8283
- }
8284
- });
8285
- } else {
8286
8762
  win = getWindow( elem );
8287
8763
 
8288
8764
  // Return the scroll offset
@@ -8291,6 +8767,21 @@ jQuery.each( ["Left", "Top"], function( i, name ) {
8291
8767
  win.document.body[ method ] :
8292
8768
  elem[ method ];
8293
8769
  }
8770
+
8771
+ // Set the scroll offset
8772
+ return this.each(function() {
8773
+ win = getWindow( this );
8774
+
8775
+ if ( win ) {
8776
+ win.scrollTo(
8777
+ !i ? val : jQuery( win ).scrollLeft(),
8778
+ i ? val : jQuery( win ).scrollTop()
8779
+ );
8780
+
8781
+ } else {
8782
+ this[ method ] = val;
8783
+ }
8784
+ });
8294
8785
  };
8295
8786
  });
8296
8787