jquery-ui-rails 2.0.2 → 3.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (131) hide show
  1. data/History.md +15 -0
  2. data/License.txt +2 -3
  3. data/README.md +17 -19
  4. data/Rakefile +79 -28
  5. data/lib/jquery/ui/rails/version.rb +1 -1
  6. data/vendor/assets/javascripts/jquery.ui.accordion.js +537 -417
  7. data/vendor/assets/javascripts/jquery.ui.all.js +17 -14
  8. data/vendor/assets/javascripts/jquery.ui.autocomplete.js +311 -339
  9. data/vendor/assets/javascripts/jquery.ui.button.js +63 -59
  10. data/vendor/assets/javascripts/jquery.ui.core.js +134 -112
  11. data/vendor/assets/javascripts/jquery.ui.datepicker-ar-DZ.js +2 -2
  12. data/vendor/assets/javascripts/jquery.ui.datepicker-ar.js +3 -3
  13. data/vendor/assets/javascripts/jquery.ui.datepicker-az.js +3 -3
  14. data/vendor/assets/javascripts/jquery.ui.datepicker-bg.js +16 -16
  15. data/vendor/assets/javascripts/jquery.ui.datepicker-bs.js +5 -5
  16. data/vendor/assets/javascripts/jquery.ui.datepicker-ca.js +13 -13
  17. data/vendor/assets/javascripts/jquery.ui.datepicker-cs.js +3 -3
  18. data/vendor/assets/javascripts/jquery.ui.datepicker-cy-GB.js +1 -1
  19. data/vendor/assets/javascripts/jquery.ui.datepicker-da.js +9 -9
  20. data/vendor/assets/javascripts/jquery.ui.datepicker-de.js +2 -2
  21. data/vendor/assets/javascripts/jquery.ui.datepicker-el.js +1 -1
  22. data/vendor/assets/javascripts/jquery.ui.datepicker-eo.js +2 -2
  23. data/vendor/assets/javascripts/jquery.ui.datepicker-es.js +6 -6
  24. data/vendor/assets/javascripts/jquery.ui.datepicker-et.js +1 -1
  25. data/vendor/assets/javascripts/jquery.ui.datepicker-eu.js +3 -3
  26. data/vendor/assets/javascripts/jquery.ui.datepicker-fa.js +3 -3
  27. data/vendor/assets/javascripts/jquery.ui.datepicker-fi.js +5 -5
  28. data/vendor/assets/javascripts/jquery.ui.datepicker-fo.js +3 -3
  29. data/vendor/assets/javascripts/jquery.ui.datepicker-fr-CH.js +3 -3
  30. data/vendor/assets/javascripts/jquery.ui.datepicker-fr.js +2 -2
  31. data/vendor/assets/javascripts/jquery.ui.datepicker-gl.js +6 -6
  32. data/vendor/assets/javascripts/jquery.ui.datepicker-he.js +2 -2
  33. data/vendor/assets/javascripts/jquery.ui.datepicker-hr.js +3 -3
  34. data/vendor/assets/javascripts/jquery.ui.datepicker-hy.js +3 -3
  35. data/vendor/assets/javascripts/jquery.ui.datepicker-id.js +3 -3
  36. data/vendor/assets/javascripts/jquery.ui.datepicker-is.js +11 -11
  37. data/vendor/assets/javascripts/jquery.ui.datepicker-it.js +3 -3
  38. data/vendor/assets/javascripts/jquery.ui.datepicker-ja.js +3 -3
  39. data/vendor/assets/javascripts/jquery.ui.datepicker-kk.js +2 -2
  40. data/vendor/assets/javascripts/jquery.ui.datepicker-ko.js +1 -1
  41. data/vendor/assets/javascripts/jquery.ui.datepicker-lt.js +3 -3
  42. data/vendor/assets/javascripts/jquery.ui.datepicker-lv.js +1 -1
  43. data/vendor/assets/javascripts/jquery.ui.datepicker-ml.js +1 -1
  44. data/vendor/assets/javascripts/jquery.ui.datepicker-ms.js +3 -3
  45. data/vendor/assets/javascripts/jquery.ui.datepicker-nl.js +1 -1
  46. data/vendor/assets/javascripts/jquery.ui.datepicker-no.js +18 -18
  47. data/vendor/assets/javascripts/jquery.ui.datepicker-pl.js +2 -2
  48. data/vendor/assets/javascripts/jquery.ui.datepicker-pt-BR.js +7 -7
  49. data/vendor/assets/javascripts/jquery.ui.datepicker-pt.js +6 -6
  50. data/vendor/assets/javascripts/jquery.ui.datepicker-rm.js +2 -2
  51. data/vendor/assets/javascripts/jquery.ui.datepicker-ro.js +2 -2
  52. data/vendor/assets/javascripts/jquery.ui.datepicker-ru.js +3 -3
  53. data/vendor/assets/javascripts/jquery.ui.datepicker-sk.js +2 -2
  54. data/vendor/assets/javascripts/jquery.ui.datepicker-sl.js +6 -6
  55. data/vendor/assets/javascripts/jquery.ui.datepicker-sq.js +2 -2
  56. data/vendor/assets/javascripts/jquery.ui.datepicker-sr-SR.js +2 -2
  57. data/vendor/assets/javascripts/jquery.ui.datepicker-sr.js +2 -2
  58. data/vendor/assets/javascripts/jquery.ui.datepicker-sv.js +9 -9
  59. data/vendor/assets/javascripts/jquery.ui.datepicker-th.js +3 -3
  60. data/vendor/assets/javascripts/jquery.ui.datepicker-tj.js +1 -1
  61. data/vendor/assets/javascripts/jquery.ui.datepicker-tr.js +2 -2
  62. data/vendor/assets/javascripts/jquery.ui.datepicker-uk.js +3 -3
  63. data/vendor/assets/javascripts/jquery.ui.datepicker-vi.js +2 -2
  64. data/vendor/assets/javascripts/jquery.ui.datepicker-zh-CN.js +2 -2
  65. data/vendor/assets/javascripts/jquery.ui.datepicker-zh-HK.js +2 -2
  66. data/vendor/assets/javascripts/jquery.ui.datepicker-zh-TW.js +2 -2
  67. data/vendor/assets/javascripts/jquery.ui.datepicker.js +51 -59
  68. data/vendor/assets/javascripts/jquery.ui.dialog.js +402 -409
  69. data/vendor/assets/javascripts/jquery.ui.draggable.js +79 -75
  70. data/vendor/assets/javascripts/jquery.ui.droppable.js +10 -17
  71. data/vendor/assets/javascripts/jquery.ui.effect-blind.js +84 -0
  72. data/vendor/assets/javascripts/jquery.ui.effect-bounce.js +115 -0
  73. data/vendor/assets/javascripts/jquery.ui.effect-clip.js +69 -0
  74. data/vendor/assets/javascripts/jquery.ui.effect-drop.js +67 -0
  75. data/vendor/assets/javascripts/jquery.ui.effect-explode.js +99 -0
  76. data/vendor/assets/javascripts/jquery.ui.effect-fade.js +32 -0
  77. data/vendor/assets/javascripts/jquery.ui.effect-fold.js +78 -0
  78. data/vendor/assets/javascripts/jquery.ui.effect-highlight.js +52 -0
  79. data/vendor/assets/javascripts/jquery.ui.effect-pulsate.js +65 -0
  80. data/vendor/assets/javascripts/jquery.ui.effect-scale.js +320 -0
  81. data/vendor/assets/javascripts/jquery.ui.effect-shake.js +76 -0
  82. data/vendor/assets/javascripts/jquery.ui.effect-slide.js +66 -0
  83. data/vendor/assets/javascripts/jquery.ui.effect-transfer.js +49 -0
  84. data/vendor/assets/javascripts/jquery.ui.effect.all.js +14 -0
  85. data/vendor/assets/javascripts/jquery.ui.effect.js +1276 -0
  86. data/vendor/assets/javascripts/jquery.ui.menu.js +614 -0
  87. data/vendor/assets/javascripts/jquery.ui.mouse.js +22 -20
  88. data/vendor/assets/javascripts/jquery.ui.position.js +367 -158
  89. data/vendor/assets/javascripts/jquery.ui.progressbar.js +10 -14
  90. data/vendor/assets/javascripts/jquery.ui.resizable.js +143 -149
  91. data/vendor/assets/javascripts/jquery.ui.selectable.js +22 -28
  92. data/vendor/assets/javascripts/jquery.ui.slider.js +88 -106
  93. data/vendor/assets/javascripts/jquery.ui.sortable.js +97 -95
  94. data/vendor/assets/javascripts/jquery.ui.spinner.js +482 -0
  95. data/vendor/assets/javascripts/jquery.ui.tabs.js +1189 -580
  96. data/vendor/assets/javascripts/jquery.ui.tooltip.js +402 -0
  97. data/vendor/assets/javascripts/jquery.ui.widget.js +373 -117
  98. data/vendor/assets/stylesheets/jquery.ui.accordion.css.erb +10 -13
  99. data/vendor/assets/stylesheets/jquery.ui.all.css.erb +4 -3
  100. data/vendor/assets/stylesheets/jquery.ui.autocomplete.css.erb +10 -44
  101. data/vendor/assets/stylesheets/jquery.ui.base.css.erb +7 -3
  102. data/vendor/assets/stylesheets/jquery.ui.button.css.erb +6 -4
  103. data/vendor/assets/stylesheets/jquery.ui.core.css.erb +5 -4
  104. data/vendor/assets/stylesheets/jquery.ui.datepicker.css.erb +4 -3
  105. data/vendor/assets/stylesheets/jquery.ui.dialog.css.erb +6 -5
  106. data/vendor/assets/stylesheets/jquery.ui.menu.css.erb +34 -0
  107. data/vendor/assets/stylesheets/jquery.ui.progressbar.css.erb +4 -3
  108. data/vendor/assets/stylesheets/jquery.ui.resizable.css.erb +4 -3
  109. data/vendor/assets/stylesheets/jquery.ui.selectable.css.erb +4 -3
  110. data/vendor/assets/stylesheets/jquery.ui.slider.css.erb +4 -3
  111. data/vendor/assets/stylesheets/jquery.ui.spinner.css.erb +27 -0
  112. data/vendor/assets/stylesheets/jquery.ui.tabs.css.erb +8 -8
  113. data/vendor/assets/stylesheets/jquery.ui.theme.css.erb +8 -7
  114. data/vendor/assets/stylesheets/jquery.ui.tooltip.css.erb +25 -0
  115. metadata +24 -19
  116. data/dependencies.js +0 -31
  117. data/vendor/assets/javascripts/jquery.effects.all.js +0 -14
  118. data/vendor/assets/javascripts/jquery.effects.blind.js +0 -51
  119. data/vendor/assets/javascripts/jquery.effects.bounce.js +0 -80
  120. data/vendor/assets/javascripts/jquery.effects.clip.js +0 -56
  121. data/vendor/assets/javascripts/jquery.effects.core.js +0 -612
  122. data/vendor/assets/javascripts/jquery.effects.drop.js +0 -52
  123. data/vendor/assets/javascripts/jquery.effects.explode.js +0 -81
  124. data/vendor/assets/javascripts/jquery.effects.fade.js +0 -34
  125. data/vendor/assets/javascripts/jquery.effects.fold.js +0 -58
  126. data/vendor/assets/javascripts/jquery.effects.highlight.js +0 -52
  127. data/vendor/assets/javascripts/jquery.effects.pulsate.js +0 -53
  128. data/vendor/assets/javascripts/jquery.effects.scale.js +0 -180
  129. data/vendor/assets/javascripts/jquery.effects.shake.js +0 -59
  130. data/vendor/assets/javascripts/jquery.effects.slide.js +0 -52
  131. data/vendor/assets/javascripts/jquery.effects.transfer.js +0 -47
data/History.md CHANGED
@@ -1,5 +1,20 @@
1
1
  # master
2
2
 
3
+ # 3.0.0
4
+
5
+ * Upgrade to jQuery UI 1.9.2
6
+ * Switched from storing the map of file dependencies locally to leveraging
7
+ the grunt build system's .json files for determining file dependencies.
8
+ This simplifies the maintenance of this wrapper project, and allows us to
9
+ delete dependencies.js
10
+ * Renamed jquery.effects.all to jquery.ui.effect.all, to match the effects files
11
+ renamed in 1.9.2 (see [Renamed all effects files][1])
12
+ * Changed license to MIT only instead of MIT or GPL, to match jQuery UI's
13
+ license (see [commit][2])
14
+
15
+ [1]: http://jqueryui.com/upgrade-guide/1.9/#renamed-all-effects-files
16
+ [2]: https://github.com/jquery/jquery-ui/commit/485ca7192ac57d018b8ce4f03e7dec6e694a53b7
17
+
3
18
  # 2.0.2
4
19
 
5
20
  * Upgrade to jQuery UI 1.8.24
@@ -1,3 +1,2 @@
1
- jQuery UI as well as this gem are dual-licensed under the MIT license (see
2
- jquery-ui/MIT-LICENSE.txt) and the GPL version 2 (see
3
- jquery-ui/GPL-LICENSE.txt).
1
+ jQuery UI as well as this gem are licensed under the MIT license (see
2
+ jquery-ui/MIT-LICENSE.txt).
data/README.md CHANGED
@@ -2,7 +2,7 @@
2
2
 
3
3
  [![Build Status](https://secure.travis-ci.org/joliss/jquery-ui-rails.png?branch=master)](http://travis-ci.org/joliss/jquery-ui-rails) [![Dependency Status](https://gemnasium.com/joliss/jquery-ui-rails.png)](https://gemnasium.com/joliss/jquery-ui-rails)
4
4
 
5
- This gem packages the jQuery UI 1.8.23 assets (JavaScripts, stylesheets, and
5
+ This gem packages the jQuery UI 1.9.2 assets (JavaScripts, stylesheets, and
6
6
  images) for the Rails 3.1+ [asset
7
7
  pipeline](http://guides.rubyonrails.org/asset_pipeline.html), so you never have
8
8
  to download a custom package through the [web
@@ -13,9 +13,7 @@ interface](http://jqueryui.com/download) again.
13
13
  In your Gemfile, add:
14
14
 
15
15
  ```ruby
16
- group :assets do
17
- gem 'jquery-ui-rails'
18
- end
16
+ gem 'jquery-ui-rails'
19
17
  ```
20
18
 
21
19
  ## Require Everything
@@ -128,21 +126,21 @@ reasons](https://github.com/joliss/jquery-ui-rails/issues/9#issuecomment-6524987
128
126
  ### Effects
129
127
 
130
128
  ```javascript
131
- //= require jquery.effects.all
132
- //= require jquery.effects.core
133
- //= require jquery.effects.blind
134
- //= require jquery.effects.bounce
135
- //= require jquery.effects.clip
136
- //= require jquery.effects.drop
137
- //= require jquery.effects.explode
138
- //= require jquery.effects.fade
139
- //= require jquery.effects.fold
140
- //= require jquery.effects.highlight
141
- //= require jquery.effects.pulsate
142
- //= require jquery.effects.scale
143
- //= require jquery.effects.shake
144
- //= require jquery.effects.slide
145
- //= require jquery.effects.transfer
129
+ //= require jquery.ui.effect.all
130
+ //= require jquery.ui.effect
131
+ //= require jquery.ui.effect-blind
132
+ //= require jquery.ui.effect-bounce
133
+ //= require jquery.ui.effect-clip
134
+ //= require jquery.ui.effect-drop
135
+ //= require jquery.ui.effect-explode
136
+ //= require jquery.ui.effect-fade
137
+ //= require jquery.ui.effect-fold
138
+ //= require jquery.ui.effect-highlight
139
+ //= require jquery.ui.effect-pulsate
140
+ //= require jquery.ui.effect-scale
141
+ //= require jquery.ui.effect-shake
142
+ //= require jquery.ui.effect-slide
143
+ //= require jquery.ui.effect-transfer
146
144
  ```
147
145
 
148
146
  ## Stylesheet Assets
data/Rakefile CHANGED
@@ -1,11 +1,58 @@
1
1
  require 'json'
2
2
  require 'bundler/gem_tasks'
3
3
 
4
- DEPENDENCY_HASH = JSON.load(File.read('dependencies.js'))
5
- # Fix dependencies. https://github.com/joliss/jquery-ui-rails/issues/1#issuecomment-8512917
6
- DEPENDENCY_HASH['ui.dialog.js'].concat ['ui.draggable.js', 'ui.resizable.js']
4
+ # returns the source filename for a given JSON build file
5
+ # (e.g., "ui.core.jquery.json" returns "jquery.ui.core.js")
6
+ def source_file_for_build_file(build_file)
7
+ "jquery.#{build_file.sub('.jquery.json', '')}.js"
8
+ end
9
+
10
+ # returns the source filename for a named file in the 'dependencies'
11
+ # array of a JSON build file
12
+ # (e.g., if the JSON build file contains
13
+ #
14
+ # "dependencies": {
15
+ # "jquery": ">=1.6",
16
+ # "ui.core": "1.9.2",
17
+ # "ui.widget": "1.9.2"
18
+ # },
19
+ #
20
+ # then "ui.widget" returns "jquery.ui.widget.js")
21
+ #
22
+ # The only exception is "jquery", which doesn't follow the
23
+ # same naming conventions so its a special case.
24
+ def source_file_for_dependency_entry(dep_entry)
25
+ # if the dependent file is jquery.js itself, return its filename
26
+ return "jquery.js" if dep_entry == 'jquery'
27
+
28
+ # otherwise, tack 'jquery.' on the front
29
+ "jquery.#{dep_entry}.js"
30
+ end
31
+
32
+ # return a Hash of dependency info, whose keys are jquery-ui
33
+ # source files and values are Arrays containing the source files
34
+ # they depend on
35
+ def map_dependencies
36
+ dependencies = {}
37
+ Dir.glob("jquery-ui/*.jquery.json").each do |build_file|
38
+ build_info = JSON.parse(File.read build_file)
39
+ source_file_name = source_file_for_build_file(File.basename(build_file))
40
+
41
+ deps = build_info['dependencies'].keys
7
42
 
8
- LANGUAGE_REGEX = /-[-a-zA-Z]+(?=\.js\z)/
43
+ # jquery.ui.core.js (and only it) should depend on jquery.js itself,
44
+ # so we remove 'jquery' from the list of dependencies for all files except
45
+ # jquery.ui.core.js
46
+ deps.reject! {|d| d == "jquery" } unless source_file_name == 'jquery.ui.core.js'
47
+
48
+ deps.map! {|d| source_file_for_dependency_entry d }
49
+
50
+ dependencies[source_file_name] = deps
51
+ end
52
+ dependencies
53
+ end
54
+
55
+ DEPENDENCY_HASH = map_dependencies
9
56
 
10
57
  def version
11
58
  JSON.load(File.read('jquery-ui/package.json'))['version']
@@ -16,26 +63,18 @@ task :submodule do
16
63
  end
17
64
 
18
65
  def get_js_dependencies(basename)
19
- if basename.match LANGUAGE_REGEX
20
- # This is an i18n file. We used to depend on the main module for i18n
21
- # files, but this slows down asset precompilation.
22
- # https://github.com/joliss/jquery-ui-rails/issues/9
23
- []
24
- else
25
- dependencies = DEPENDENCY_HASH[basename.sub(/\Ajquery\./, '')]
26
- if dependencies.nil?
27
- puts "Warning: No dependencies found for #{basename}"
28
- dependencies = []
29
- end
30
- dependencies = dependencies
31
- .reject { |dep| dep == 'theme' } # 'theme' pseudo-dependency handled by CSS
32
- .map { |dep| "jquery.#{dep}" }
33
- # Make sure we do not package assets with broken dependencies
34
- dependencies.each do |dep|
35
- fail "#{basename}: missing #{dep}" unless File.exist? "jquery-ui/ui/#{dep}"
66
+ dependencies = DEPENDENCY_HASH[basename]
67
+ if dependencies.nil?
68
+ puts "Warning: No dependencies found for #{basename}"
69
+ dependencies = []
70
+ end
71
+ # Make sure we do not package assets with broken dependencies
72
+ dependencies.each do |dep|
73
+ unless dep == "jquery.js" || File.exist?("jquery-ui/ui/#{dep}")
74
+ fail "#{basename}: missing #{dep}"
36
75
  end
37
- dependencies
38
76
  end
77
+ dependencies
39
78
  end
40
79
 
41
80
  def remove_js_extension(path)
@@ -59,10 +98,9 @@ task :javascripts => :submodule do
59
98
  target_dir = "vendor/assets/javascripts"
60
99
  mkdir_p target_dir
61
100
  Rake.rake_output_message 'Generating javascripts'
62
- Dir.glob("jquery-ui/ui/**/*.js").each do |path|
101
+ Dir.glob("jquery-ui/ui/*.js").each do |path|
63
102
  basename = File.basename(path)
64
103
  dep_modules = get_js_dependencies(basename).map(&method(:remove_js_extension))
65
- dep_modules << 'jquery' if basename == 'jquery.ui.core.js'
66
104
  File.open("#{target_dir}/#{basename}", "w") do |out|
67
105
  dep_modules.each do |mod|
68
106
  out.write("//= require #{mod}\n")
@@ -74,8 +112,21 @@ task :javascripts => :submodule do
74
112
  out.write(source_code)
75
113
  end
76
114
  end
77
- File.open("#{target_dir}/jquery.effects.all.js", "w") do |out|
78
- Dir.glob("jquery-ui/ui/jquery.effects.*.js").sort.each do |path|
115
+
116
+ # process the i18n files separately for performance, since they will not have dependencies
117
+ # https://github.com/joliss/jquery-ui-rails/issues/9
118
+ Dir.glob("jquery-ui/ui/i18n/*.js").each do |path|
119
+ basename = File.basename(path)
120
+ File.open("#{target_dir}/#{basename}", "w") do |out|
121
+ source_code = File.read(path)
122
+ source_code.gsub!('@VERSION', version)
123
+ protect_copyright_notice(source_code)
124
+ out.write(source_code)
125
+ end
126
+ end
127
+
128
+ File.open("#{target_dir}/jquery.ui.effect.all.js", "w") do |out|
129
+ Dir.glob("jquery-ui/ui/jquery.ui.effect*.js").sort.each do |path|
79
130
  asset_name = remove_js_extension(File.basename(path))
80
131
  out.write("//= require #{asset_name}\n")
81
132
  end
@@ -102,11 +153,11 @@ task :stylesheets => :submodule do
102
153
  extra_dependencies << 'jquery.ui.core' unless basename =~ /\.(all|base|core)\./
103
154
  # Is "theme" listed among the dependencies for the matching JS file?
104
155
  unless basename =~ /\.(all|base|core|theme)\./
105
- dependencies = DEPENDENCY_HASH[basename.sub(/\Ajquery\./, '').sub(/\.css/, '.js')]
156
+ dependencies = DEPENDENCY_HASH[basename.sub(/\.css/, '.js')]
106
157
  if dependencies.nil?
107
158
  puts "Warning: No matching JavaScript dependencies found for #{basename}"
108
159
  else
109
- extra_dependencies << 'jquery.ui.theme' if dependencies.include? 'theme'
160
+ extra_dependencies << 'jquery.ui.theme'
110
161
  end
111
162
  end
112
163
  extra_dependencies.reverse.each do |dep|
@@ -1,7 +1,7 @@
1
1
  module Jquery
2
2
  module Ui
3
3
  module Rails
4
- VERSION = "2.0.2"
4
+ VERSION = "3.0.0"
5
5
  end
6
6
  end
7
7
  end
@@ -2,13 +2,14 @@
2
2
  //= require jquery.ui.widget
3
3
 
4
4
  /*!
5
- * jQuery UI Accordion 1.8.24
5
+ * jQuery UI Accordion 1.9.2
6
+ * http://jqueryui.com
6
7
  *
7
- * Copyright 2012, AUTHORS.txt (http://jqueryui.com/about)
8
- * Dual licensed under the MIT or GPL Version 2 licenses.
8
+ * Copyright 2012 jQuery Foundation and other contributors
9
+ * Released under the MIT license.
9
10
  * http://jquery.org/license
10
11
  *
11
- * http://docs.jquery.com/UI/Accordion
12
+ * http://api.jqueryui.com/accordion/
12
13
  *
13
14
  * Depends:
14
15
  * jquery.ui.core.js
@@ -16,207 +17,231 @@
16
17
  */
17
18
  (function( $, undefined ) {
18
19
 
20
+ var uid = 0,
21
+ hideProps = {},
22
+ showProps = {};
23
+
24
+ hideProps.height = hideProps.paddingTop = hideProps.paddingBottom =
25
+ hideProps.borderTopWidth = hideProps.borderBottomWidth = "hide";
26
+ showProps.height = showProps.paddingTop = showProps.paddingBottom =
27
+ showProps.borderTopWidth = showProps.borderBottomWidth = "show";
28
+
19
29
  $.widget( "ui.accordion", {
30
+ version: "1.9.2",
20
31
  options: {
21
32
  active: 0,
22
- animated: "slide",
23
- autoHeight: true,
24
- clearStyle: false,
33
+ animate: {},
25
34
  collapsible: false,
26
35
  event: "click",
27
- fillSpace: false,
28
36
  header: "> li > :first-child,> :not(li):even",
37
+ heightStyle: "auto",
29
38
  icons: {
30
- header: "ui-icon-triangle-1-e",
31
- headerSelected: "ui-icon-triangle-1-s"
39
+ activeHeader: "ui-icon-triangle-1-s",
40
+ header: "ui-icon-triangle-1-e"
32
41
  },
33
- navigation: false,
34
- navigationFilter: function() {
35
- return this.href.toLowerCase() === location.href.toLowerCase();
36
- }
42
+
43
+ // callbacks
44
+ activate: null,
45
+ beforeActivate: null
37
46
  },
38
47
 
39
48
  _create: function() {
40
- var self = this,
41
- options = self.options;
42
-
43
- self.running = 0;
44
-
45
- self.element
46
- .addClass( "ui-accordion ui-widget ui-helper-reset" )
47
- // in lack of child-selectors in CSS
48
- // we need to mark top-LIs in a UL-accordion for some IE-fix
49
- .children( "li" )
50
- .addClass( "ui-accordion-li-fix" );
51
-
52
- self.headers = self.element.find( options.header )
53
- .addClass( "ui-accordion-header ui-helper-reset ui-state-default ui-corner-all" )
54
- .bind( "mouseenter.accordion", function() {
55
- if ( options.disabled ) {
56
- return;
57
- }
58
- $( this ).addClass( "ui-state-hover" );
59
- })
60
- .bind( "mouseleave.accordion", function() {
61
- if ( options.disabled ) {
62
- return;
63
- }
64
- $( this ).removeClass( "ui-state-hover" );
65
- })
66
- .bind( "focus.accordion", function() {
67
- if ( options.disabled ) {
68
- return;
69
- }
70
- $( this ).addClass( "ui-state-focus" );
71
- })
72
- .bind( "blur.accordion", function() {
73
- if ( options.disabled ) {
74
- return;
75
- }
76
- $( this ).removeClass( "ui-state-focus" );
77
- });
49
+ var accordionId = this.accordionId = "ui-accordion-" +
50
+ (this.element.attr( "id" ) || ++uid),
51
+ options = this.options;
78
52
 
79
- self.headers.next()
80
- .addClass( "ui-accordion-content ui-helper-reset ui-widget-content ui-corner-bottom" );
53
+ this.prevShow = this.prevHide = $();
54
+ this.element.addClass( "ui-accordion ui-widget ui-helper-reset" );
81
55
 
82
- if ( options.navigation ) {
83
- var current = self.element.find( "a" ).filter( options.navigationFilter ).eq( 0 );
84
- if ( current.length ) {
85
- var header = current.closest( ".ui-accordion-header" );
86
- if ( header.length ) {
87
- // anchor within header
88
- self.active = header;
89
- } else {
90
- // anchor within content
91
- self.active = current.closest( ".ui-accordion-content" ).prev();
92
- }
93
- }
56
+ this.headers = this.element.find( options.header )
57
+ .addClass( "ui-accordion-header ui-helper-reset ui-state-default ui-corner-all" );
58
+ this._hoverable( this.headers );
59
+ this._focusable( this.headers );
60
+
61
+ this.headers.next()
62
+ .addClass( "ui-accordion-content ui-helper-reset ui-widget-content ui-corner-bottom" )
63
+ .hide();
64
+
65
+ // don't allow collapsible: false and active: false / null
66
+ if ( !options.collapsible && (options.active === false || options.active == null) ) {
67
+ options.active = 0;
68
+ }
69
+ // handle negative values
70
+ if ( options.active < 0 ) {
71
+ options.active += this.headers.length;
94
72
  }
73
+ this.active = this._findActive( options.active )
74
+ .addClass( "ui-accordion-header-active ui-state-active" )
75
+ .toggleClass( "ui-corner-all ui-corner-top" );
76
+ this.active.next()
77
+ .addClass( "ui-accordion-content-active" )
78
+ .show();
95
79
 
96
- self.active = self._findActive( self.active || options.active )
97
- .addClass( "ui-state-default ui-state-active" )
98
- .toggleClass( "ui-corner-all" )
99
- .toggleClass( "ui-corner-top" );
100
- self.active.next().addClass( "ui-accordion-content-active" );
80
+ this._createIcons();
81
+ this.refresh();
101
82
 
102
- self._createIcons();
103
- self.resize();
104
-
105
83
  // ARIA
106
- self.element.attr( "role", "tablist" );
84
+ this.element.attr( "role", "tablist" );
107
85
 
108
- self.headers
86
+ this.headers
109
87
  .attr( "role", "tab" )
110
- .bind( "keydown.accordion", function( event ) {
111
- return self._keydown( event );
88
+ .each(function( i ) {
89
+ var header = $( this ),
90
+ headerId = header.attr( "id" ),
91
+ panel = header.next(),
92
+ panelId = panel.attr( "id" );
93
+ if ( !headerId ) {
94
+ headerId = accordionId + "-header-" + i;
95
+ header.attr( "id", headerId );
96
+ }
97
+ if ( !panelId ) {
98
+ panelId = accordionId + "-panel-" + i;
99
+ panel.attr( "id", panelId );
100
+ }
101
+ header.attr( "aria-controls", panelId );
102
+ panel.attr( "aria-labelledby", headerId );
112
103
  })
113
104
  .next()
114
105
  .attr( "role", "tabpanel" );
115
106
 
116
- self.headers
117
- .not( self.active || "" )
107
+ this.headers
108
+ .not( this.active )
118
109
  .attr({
119
- "aria-expanded": "false",
120
110
  "aria-selected": "false",
121
111
  tabIndex: -1
122
112
  })
123
113
  .next()
114
+ .attr({
115
+ "aria-expanded": "false",
116
+ "aria-hidden": "true"
117
+ })
124
118
  .hide();
125
119
 
126
120
  // make sure at least one header is in the tab order
127
- if ( !self.active.length ) {
128
- self.headers.eq( 0 ).attr( "tabIndex", 0 );
121
+ if ( !this.active.length ) {
122
+ this.headers.eq( 0 ).attr( "tabIndex", 0 );
129
123
  } else {
130
- self.active
124
+ this.active.attr({
125
+ "aria-selected": "true",
126
+ tabIndex: 0
127
+ })
128
+ .next()
131
129
  .attr({
132
130
  "aria-expanded": "true",
133
- "aria-selected": "true",
134
- tabIndex: 0
131
+ "aria-hidden": "false"
135
132
  });
136
133
  }
137
134
 
138
- // only need links in tab order for Safari
139
- if ( !$.browser.safari ) {
140
- self.headers.find( "a" ).attr( "tabIndex", -1 );
141
- }
135
+ this._on( this.headers, { keydown: "_keydown" });
136
+ this._on( this.headers.next(), { keydown: "_panelKeyDown" });
137
+ this._setupEvents( options.event );
138
+ },
142
139
 
143
- if ( options.event ) {
144
- self.headers.bind( options.event.split(" ").join(".accordion ") + ".accordion", function(event) {
145
- self._clickHandler.call( self, event, this );
146
- event.preventDefault();
147
- });
148
- }
140
+ _getCreateEventData: function() {
141
+ return {
142
+ header: this.active,
143
+ content: !this.active.length ? $() : this.active.next()
144
+ };
149
145
  },
150
146
 
151
147
  _createIcons: function() {
152
- var options = this.options;
153
- if ( options.icons ) {
154
- $( "<span></span>" )
155
- .addClass( "ui-icon " + options.icons.header )
148
+ var icons = this.options.icons;
149
+ if ( icons ) {
150
+ $( "<span>" )
151
+ .addClass( "ui-accordion-header-icon ui-icon " + icons.header )
156
152
  .prependTo( this.headers );
157
- this.active.children( ".ui-icon" )
158
- .toggleClass(options.icons.header)
159
- .toggleClass(options.icons.headerSelected);
160
- this.element.addClass( "ui-accordion-icons" );
153
+ this.active.children( ".ui-accordion-header-icon" )
154
+ .removeClass( icons.header )
155
+ .addClass( icons.activeHeader );
156
+ this.headers.addClass( "ui-accordion-icons" );
161
157
  }
162
158
  },
163
159
 
164
160
  _destroyIcons: function() {
165
- this.headers.children( ".ui-icon" ).remove();
166
- this.element.removeClass( "ui-accordion-icons" );
161
+ this.headers
162
+ .removeClass( "ui-accordion-icons" )
163
+ .children( ".ui-accordion-header-icon" )
164
+ .remove();
167
165
  },
168
166
 
169
- destroy: function() {
170
- var options = this.options;
167
+ _destroy: function() {
168
+ var contents;
171
169
 
170
+ // clean up main element
172
171
  this.element
173
172
  .removeClass( "ui-accordion ui-widget ui-helper-reset" )
174
173
  .removeAttr( "role" );
175
174
 
175
+ // clean up headers
176
176
  this.headers
177
- .unbind( ".accordion" )
178
- .removeClass( "ui-accordion-header ui-accordion-disabled ui-helper-reset ui-state-default ui-corner-all ui-state-active ui-state-disabled ui-corner-top" )
177
+ .removeClass( "ui-accordion-header ui-accordion-header-active ui-helper-reset ui-state-default ui-corner-all ui-state-active ui-state-disabled ui-corner-top" )
179
178
  .removeAttr( "role" )
180
- .removeAttr( "aria-expanded" )
181
179
  .removeAttr( "aria-selected" )
182
- .removeAttr( "tabIndex" );
183
-
184
- this.headers.find( "a" ).removeAttr( "tabIndex" );
180
+ .removeAttr( "aria-controls" )
181
+ .removeAttr( "tabIndex" )
182
+ .each(function() {
183
+ if ( /^ui-accordion/.test( this.id ) ) {
184
+ this.removeAttribute( "id" );
185
+ }
186
+ });
185
187
  this._destroyIcons();
186
- var contents = this.headers.next()
188
+
189
+ // clean up content panels
190
+ contents = this.headers.next()
187
191
  .css( "display", "" )
188
192
  .removeAttr( "role" )
189
- .removeClass( "ui-helper-reset ui-widget-content ui-corner-bottom ui-accordion-content ui-accordion-content-active ui-accordion-disabled ui-state-disabled" );
190
- if ( options.autoHeight || options.fillHeight ) {
193
+ .removeAttr( "aria-expanded" )
194
+ .removeAttr( "aria-hidden" )
195
+ .removeAttr( "aria-labelledby" )
196
+ .removeClass( "ui-helper-reset ui-widget-content ui-corner-bottom ui-accordion-content ui-accordion-content-active ui-state-disabled" )
197
+ .each(function() {
198
+ if ( /^ui-accordion/.test( this.id ) ) {
199
+ this.removeAttribute( "id" );
200
+ }
201
+ });
202
+ if ( this.options.heightStyle !== "content" ) {
191
203
  contents.css( "height", "" );
192
204
  }
193
-
194
- return $.Widget.prototype.destroy.call( this );
195
205
  },
196
206
 
197
207
  _setOption: function( key, value ) {
198
- $.Widget.prototype._setOption.apply( this, arguments );
199
-
200
- if ( key == "active" ) {
201
- this.activate( value );
208
+ if ( key === "active" ) {
209
+ // _activate() will handle invalid values and update this.options
210
+ this._activate( value );
211
+ return;
212
+ }
213
+
214
+ if ( key === "event" ) {
215
+ if ( this.options.event ) {
216
+ this._off( this.headers, this.options.event );
217
+ }
218
+ this._setupEvents( value );
219
+ }
220
+
221
+ this._super( key, value );
222
+
223
+ // setting collapsible: false while collapsed; open first panel
224
+ if ( key === "collapsible" && !value && this.options.active === false ) {
225
+ this._activate( 0 );
202
226
  }
203
- if ( key == "icons" ) {
227
+
228
+ if ( key === "icons" ) {
204
229
  this._destroyIcons();
205
230
  if ( value ) {
206
231
  this._createIcons();
207
232
  }
208
233
  }
234
+
209
235
  // #5332 - opacity doesn't cascade to positioned elements in IE
210
236
  // so we need to add the disabled class to the headers and panels
211
- if ( key == "disabled" ) {
212
- this.headers.add(this.headers.next())
213
- [ value ? "addClass" : "removeClass" ](
214
- "ui-accordion-disabled ui-state-disabled" );
237
+ if ( key === "disabled" ) {
238
+ this.headers.add( this.headers.next() )
239
+ .toggleClass( "ui-state-disabled", !!value );
215
240
  }
216
241
  },
217
242
 
218
243
  _keydown: function( event ) {
219
- if ( this.options.disabled || event.altKey || event.ctrlKey ) {
244
+ if ( event.altKey || event.ctrlKey ) {
220
245
  return;
221
246
  }
222
247
 
@@ -236,32 +261,57 @@ $.widget( "ui.accordion", {
236
261
  break;
237
262
  case keyCode.SPACE:
238
263
  case keyCode.ENTER:
239
- this._clickHandler( { target: event.target }, event.target );
240
- event.preventDefault();
264
+ this._eventHandler( event );
265
+ break;
266
+ case keyCode.HOME:
267
+ toFocus = this.headers[ 0 ];
268
+ break;
269
+ case keyCode.END:
270
+ toFocus = this.headers[ length - 1 ];
271
+ break;
241
272
  }
242
273
 
243
274
  if ( toFocus ) {
244
275
  $( event.target ).attr( "tabIndex", -1 );
245
276
  $( toFocus ).attr( "tabIndex", 0 );
246
277
  toFocus.focus();
247
- return false;
278
+ event.preventDefault();
248
279
  }
280
+ },
249
281
 
250
- return true;
282
+ _panelKeyDown : function( event ) {
283
+ if ( event.keyCode === $.ui.keyCode.UP && event.ctrlKey ) {
284
+ $( event.currentTarget ).prev().focus();
285
+ }
251
286
  },
252
287
 
253
- resize: function() {
254
- var options = this.options,
255
- maxHeight;
288
+ refresh: function() {
289
+ var maxHeight, overflow,
290
+ heightStyle = this.options.heightStyle,
291
+ parent = this.element.parent();
292
+
256
293
 
257
- if ( options.fillSpace ) {
258
- if ( $.browser.msie ) {
259
- var defOverflow = this.element.parent().css( "overflow" );
260
- this.element.parent().css( "overflow", "hidden");
294
+ if ( heightStyle === "fill" ) {
295
+ // IE 6 treats height like minHeight, so we need to turn off overflow
296
+ // in order to get a reliable height
297
+ // we use the minHeight support test because we assume that only
298
+ // browsers that don't support minHeight will treat height as minHeight
299
+ if ( !$.support.minHeight ) {
300
+ overflow = parent.css( "overflow" );
301
+ parent.css( "overflow", "hidden");
261
302
  }
262
- maxHeight = this.element.parent().height();
263
- if ($.browser.msie) {
264
- this.element.parent().css( "overflow", defOverflow );
303
+ maxHeight = parent.height();
304
+ this.element.siblings( ":visible" ).each(function() {
305
+ var elem = $( this ),
306
+ position = elem.css( "position" );
307
+
308
+ if ( position === "absolute" || position === "fixed" ) {
309
+ return;
310
+ }
311
+ maxHeight -= elem.outerHeight( true );
312
+ });
313
+ if ( overflow ) {
314
+ parent.css( "overflow", overflow );
265
315
  }
266
316
 
267
317
  this.headers.each(function() {
@@ -274,341 +324,411 @@ $.widget( "ui.accordion", {
274
324
  $( this ).innerHeight() + $( this ).height() ) );
275
325
  })
276
326
  .css( "overflow", "auto" );
277
- } else if ( options.autoHeight ) {
327
+ } else if ( heightStyle === "auto" ) {
278
328
  maxHeight = 0;
279
329
  this.headers.next()
280
330
  .each(function() {
281
- maxHeight = Math.max( maxHeight, $( this ).height( "" ).height() );
331
+ maxHeight = Math.max( maxHeight, $( this ).css( "height", "" ).height() );
282
332
  })
283
333
  .height( maxHeight );
284
334
  }
285
-
286
- return this;
287
335
  },
288
336
 
289
- activate: function( index ) {
290
- // TODO this gets called on init, changing the option without an explicit call for that
291
- this.options.active = index;
292
- // call clickHandler with custom event
337
+ _activate: function( index ) {
293
338
  var active = this._findActive( index )[ 0 ];
294
- this._clickHandler( { target: active }, active );
295
339
 
296
- return this;
340
+ // trying to activate the already active panel
341
+ if ( active === this.active[ 0 ] ) {
342
+ return;
343
+ }
344
+
345
+ // trying to collapse, simulate a click on the currently active header
346
+ active = active || this.active[ 0 ];
347
+
348
+ this._eventHandler({
349
+ target: active,
350
+ currentTarget: active,
351
+ preventDefault: $.noop
352
+ });
297
353
  },
298
354
 
299
355
  _findActive: function( selector ) {
300
- return selector
301
- ? typeof selector === "number"
302
- ? this.headers.filter( ":eq(" + selector + ")" )
303
- : this.headers.not( this.headers.not( selector ) )
304
- : selector === false
305
- ? $( [] )
306
- : this.headers.filter( ":eq(0)" );
356
+ return typeof selector === "number" ? this.headers.eq( selector ) : $();
307
357
  },
308
358
 
309
- // TODO isn't event.target enough? why the separate target argument?
310
- _clickHandler: function( event, target ) {
311
- var options = this.options;
312
- if ( options.disabled ) {
313
- return;
314
- }
315
-
316
- // called only when using activate(false) to close all parts programmatically
317
- if ( !event.target ) {
318
- if ( !options.collapsible ) {
319
- return;
320
- }
321
- this.active
322
- .removeClass( "ui-state-active ui-corner-top" )
323
- .addClass( "ui-state-default ui-corner-all" )
324
- .children( ".ui-icon" )
325
- .removeClass( options.icons.headerSelected )
326
- .addClass( options.icons.header );
327
- this.active.next().addClass( "ui-accordion-content-active" );
328
- var toHide = this.active.next(),
329
- data = {
330
- options: options,
331
- newHeader: $( [] ),
332
- oldHeader: options.active,
333
- newContent: $( [] ),
334
- oldContent: toHide
335
- },
336
- toShow = ( this.active = $( [] ) );
337
- this._toggle( toShow, toHide, data );
359
+ _setupEvents: function( event ) {
360
+ var events = {};
361
+ if ( !event ) {
338
362
  return;
339
363
  }
364
+ $.each( event.split(" "), function( index, eventName ) {
365
+ events[ eventName ] = "_eventHandler";
366
+ });
367
+ this._on( this.headers, events );
368
+ },
340
369
 
341
- // get the click target
342
- var clicked = $( event.currentTarget || target ),
343
- clickedIsActive = clicked[0] === this.active[0];
344
-
345
- // TODO the option is changed, is that correct?
346
- // TODO if it is correct, shouldn't that happen after determining that the click is valid?
347
- options.active = options.collapsible && clickedIsActive ?
348
- false :
349
- this.headers.index( clicked );
350
-
351
- // if animations are still active, or the active header is the target, ignore click
352
- if ( this.running || ( !options.collapsible && clickedIsActive ) ) {
370
+ _eventHandler: function( event ) {
371
+ var options = this.options,
372
+ active = this.active,
373
+ clicked = $( event.currentTarget ),
374
+ clickedIsActive = clicked[ 0 ] === active[ 0 ],
375
+ collapsing = clickedIsActive && options.collapsible,
376
+ toShow = collapsing ? $() : clicked.next(),
377
+ toHide = active.next(),
378
+ eventData = {
379
+ oldHeader: active,
380
+ oldPanel: toHide,
381
+ newHeader: collapsing ? $() : clicked,
382
+ newPanel: toShow
383
+ };
384
+
385
+ event.preventDefault();
386
+
387
+ if (
388
+ // click on active header, but not collapsible
389
+ ( clickedIsActive && !options.collapsible ) ||
390
+ // allow canceling activation
391
+ ( this._trigger( "beforeActivate", event, eventData ) === false ) ) {
353
392
  return;
354
393
  }
355
394
 
356
- // find elements to show and hide
357
- var active = this.active,
358
- toShow = clicked.next(),
359
- toHide = this.active.next(),
360
- data = {
361
- options: options,
362
- newHeader: clickedIsActive && options.collapsible ? $([]) : clicked,
363
- oldHeader: this.active,
364
- newContent: clickedIsActive && options.collapsible ? $([]) : toShow,
365
- oldContent: toHide
366
- },
367
- down = this.headers.index( this.active[0] ) > this.headers.index( clicked[0] );
395
+ options.active = collapsing ? false : this.headers.index( clicked );
368
396
 
369
397
  // when the call to ._toggle() comes after the class changes
370
398
  // it causes a very odd bug in IE 8 (see #6720)
371
- this.active = clickedIsActive ? $([]) : clicked;
372
- this._toggle( toShow, toHide, data, clickedIsActive, down );
399
+ this.active = clickedIsActive ? $() : clicked;
400
+ this._toggle( eventData );
373
401
 
374
402
  // switch classes
375
- active
376
- .removeClass( "ui-state-active ui-corner-top" )
377
- .addClass( "ui-state-default ui-corner-all" )
378
- .children( ".ui-icon" )
379
- .removeClass( options.icons.headerSelected )
403
+ // corner classes on the previously active header stay after the animation
404
+ active.removeClass( "ui-accordion-header-active ui-state-active" );
405
+ if ( options.icons ) {
406
+ active.children( ".ui-accordion-header-icon" )
407
+ .removeClass( options.icons.activeHeader )
380
408
  .addClass( options.icons.header );
409
+ }
410
+
381
411
  if ( !clickedIsActive ) {
382
412
  clicked
383
- .removeClass( "ui-state-default ui-corner-all" )
384
- .addClass( "ui-state-active ui-corner-top" )
385
- .children( ".ui-icon" )
413
+ .removeClass( "ui-corner-all" )
414
+ .addClass( "ui-accordion-header-active ui-state-active ui-corner-top" );
415
+ if ( options.icons ) {
416
+ clicked.children( ".ui-accordion-header-icon" )
386
417
  .removeClass( options.icons.header )
387
- .addClass( options.icons.headerSelected );
418
+ .addClass( options.icons.activeHeader );
419
+ }
420
+
388
421
  clicked
389
422
  .next()
390
423
  .addClass( "ui-accordion-content-active" );
391
424
  }
425
+ },
426
+
427
+ _toggle: function( data ) {
428
+ var toShow = data.newPanel,
429
+ toHide = this.prevShow.length ? this.prevShow : data.oldPanel;
392
430
 
393
- return;
431
+ // handle activating a panel during the animation for another activation
432
+ this.prevShow.add( this.prevHide ).stop( true, true );
433
+ this.prevShow = toShow;
434
+ this.prevHide = toHide;
435
+
436
+ if ( this.options.animate ) {
437
+ this._animate( toShow, toHide, data );
438
+ } else {
439
+ toHide.hide();
440
+ toShow.show();
441
+ this._toggleComplete( data );
442
+ }
443
+
444
+ toHide.attr({
445
+ "aria-expanded": "false",
446
+ "aria-hidden": "true"
447
+ });
448
+ toHide.prev().attr( "aria-selected", "false" );
449
+ // if we're switching panels, remove the old header from the tab order
450
+ // if we're opening from collapsed state, remove the previous header from the tab order
451
+ // if we're collapsing, then keep the collapsing header in the tab order
452
+ if ( toShow.length && toHide.length ) {
453
+ toHide.prev().attr( "tabIndex", -1 );
454
+ } else if ( toShow.length ) {
455
+ this.headers.filter(function() {
456
+ return $( this ).attr( "tabIndex" ) === 0;
457
+ })
458
+ .attr( "tabIndex", -1 );
459
+ }
460
+
461
+ toShow
462
+ .attr({
463
+ "aria-expanded": "true",
464
+ "aria-hidden": "false"
465
+ })
466
+ .prev()
467
+ .attr({
468
+ "aria-selected": "true",
469
+ tabIndex: 0
470
+ });
394
471
  },
395
472
 
396
- _toggle: function( toShow, toHide, data, clickedIsActive, down ) {
397
- var self = this,
398
- options = self.options;
473
+ _animate: function( toShow, toHide, data ) {
474
+ var total, easing, duration,
475
+ that = this,
476
+ adjust = 0,
477
+ down = toShow.length &&
478
+ ( !toHide.length || ( toShow.index() < toHide.index() ) ),
479
+ animate = this.options.animate || {},
480
+ options = down && animate.down || animate,
481
+ complete = function() {
482
+ that._toggleComplete( data );
483
+ };
484
+
485
+ if ( typeof options === "number" ) {
486
+ duration = options;
487
+ }
488
+ if ( typeof options === "string" ) {
489
+ easing = options;
490
+ }
491
+ // fall back from options to animation in case of partial down settings
492
+ easing = easing || options.easing || animate.easing;
493
+ duration = duration || options.duration || animate.duration;
399
494
 
400
- self.toShow = toShow;
401
- self.toHide = toHide;
402
- self.data = data;
495
+ if ( !toHide.length ) {
496
+ return toShow.animate( showProps, duration, easing, complete );
497
+ }
498
+ if ( !toShow.length ) {
499
+ return toHide.animate( hideProps, duration, easing, complete );
500
+ }
403
501
 
404
- var complete = function() {
405
- if ( !self ) {
406
- return;
502
+ total = toShow.show().outerHeight();
503
+ toHide.animate( hideProps, {
504
+ duration: duration,
505
+ easing: easing,
506
+ step: function( now, fx ) {
507
+ fx.now = Math.round( now );
407
508
  }
408
- return self._completed.apply( self, arguments );
409
- };
509
+ });
510
+ toShow
511
+ .hide()
512
+ .animate( showProps, {
513
+ duration: duration,
514
+ easing: easing,
515
+ complete: complete,
516
+ step: function( now, fx ) {
517
+ fx.now = Math.round( now );
518
+ if ( fx.prop !== "height" ) {
519
+ adjust += fx.now;
520
+ } else if ( that.options.heightStyle !== "content" ) {
521
+ fx.now = Math.round( total - toHide.outerHeight() - adjust );
522
+ adjust = 0;
523
+ }
524
+ }
525
+ });
526
+ },
410
527
 
411
- // trigger changestart event
412
- self._trigger( "changestart", null, self.data );
413
-
414
- // count elements to animate
415
- self.running = toHide.size() === 0 ? toShow.size() : toHide.size();
416
-
417
- if ( options.animated ) {
418
- var animOptions = {};
419
-
420
- if ( options.collapsible && clickedIsActive ) {
421
- animOptions = {
422
- toShow: $( [] ),
423
- toHide: toHide,
424
- complete: complete,
425
- down: down,
426
- autoHeight: options.autoHeight || options.fillSpace
427
- };
428
- } else {
429
- animOptions = {
430
- toShow: toShow,
431
- toHide: toHide,
432
- complete: complete,
433
- down: down,
434
- autoHeight: options.autoHeight || options.fillSpace
435
- };
436
- }
528
+ _toggleComplete: function( data ) {
529
+ var toHide = data.oldPanel;
437
530
 
438
- if ( !options.proxied ) {
439
- options.proxied = options.animated;
440
- }
531
+ toHide
532
+ .removeClass( "ui-accordion-content-active" )
533
+ .prev()
534
+ .removeClass( "ui-corner-top" )
535
+ .addClass( "ui-corner-all" );
441
536
 
442
- if ( !options.proxiedDuration ) {
443
- options.proxiedDuration = options.duration;
444
- }
537
+ // Work around for rendering bug in IE (#5421)
538
+ if ( toHide.length ) {
539
+ toHide.parent()[0].className = toHide.parent()[0].className;
540
+ }
445
541
 
446
- options.animated = $.isFunction( options.proxied ) ?
447
- options.proxied( animOptions ) :
448
- options.proxied;
542
+ this._trigger( "activate", null, data );
543
+ }
544
+ });
449
545
 
450
- options.duration = $.isFunction( options.proxiedDuration ) ?
451
- options.proxiedDuration( animOptions ) :
452
- options.proxiedDuration;
453
546
 
454
- var animations = $.ui.accordion.animations,
455
- duration = options.duration,
456
- easing = options.animated;
457
547
 
458
- if ( easing && !animations[ easing ] && !$.easing[ easing ] ) {
459
- easing = "slide";
548
+ // DEPRECATED
549
+ if ( $.uiBackCompat !== false ) {
550
+ // navigation options
551
+ (function( $, prototype ) {
552
+ $.extend( prototype.options, {
553
+ navigation: false,
554
+ navigationFilter: function() {
555
+ return this.href.toLowerCase() === location.href.toLowerCase();
460
556
  }
461
- if ( !animations[ easing ] ) {
462
- animations[ easing ] = function( options ) {
463
- this.slide( options, {
464
- easing: easing,
465
- duration: duration || 700
557
+ });
558
+
559
+ var _create = prototype._create;
560
+ prototype._create = function() {
561
+ if ( this.options.navigation ) {
562
+ var that = this,
563
+ headers = this.element.find( this.options.header ),
564
+ content = headers.next(),
565
+ current = headers.add( content )
566
+ .find( "a" )
567
+ .filter( this.options.navigationFilter )
568
+ [ 0 ];
569
+ if ( current ) {
570
+ headers.add( content ).each( function( index ) {
571
+ if ( $.contains( this, current ) ) {
572
+ that.options.active = Math.floor( index / 2 );
573
+ return false;
574
+ }
466
575
  });
467
- };
576
+ }
468
577
  }
578
+ _create.call( this );
579
+ };
580
+ }( jQuery, jQuery.ui.accordion.prototype ) );
581
+
582
+ // height options
583
+ (function( $, prototype ) {
584
+ $.extend( prototype.options, {
585
+ heightStyle: null, // remove default so we fall back to old values
586
+ autoHeight: true, // use heightStyle: "auto"
587
+ clearStyle: false, // use heightStyle: "content"
588
+ fillSpace: false // use heightStyle: "fill"
589
+ });
590
+
591
+ var _create = prototype._create,
592
+ _setOption = prototype._setOption;
593
+
594
+ $.extend( prototype, {
595
+ _create: function() {
596
+ this.options.heightStyle = this.options.heightStyle ||
597
+ this._mergeHeightStyle();
598
+
599
+ _create.call( this );
600
+ },
469
601
 
470
- animations[ easing ]( animOptions );
471
- } else {
472
- if ( options.collapsible && clickedIsActive ) {
473
- toShow.toggle();
474
- } else {
475
- toHide.hide();
476
- toShow.show();
477
- }
602
+ _setOption: function( key ) {
603
+ if ( key === "autoHeight" || key === "clearStyle" || key === "fillSpace" ) {
604
+ this.options.heightStyle = this._mergeHeightStyle();
605
+ }
606
+ _setOption.apply( this, arguments );
607
+ },
478
608
 
479
- complete( true );
480
- }
609
+ _mergeHeightStyle: function() {
610
+ var options = this.options;
481
611
 
482
- // TODO assert that the blur and focus triggers are really necessary, remove otherwise
483
- toHide.prev()
484
- .attr({
485
- "aria-expanded": "false",
486
- "aria-selected": "false",
487
- tabIndex: -1
488
- })
489
- .blur();
490
- toShow.prev()
491
- .attr({
492
- "aria-expanded": "true",
493
- "aria-selected": "true",
494
- tabIndex: 0
495
- })
496
- .focus();
497
- },
612
+ if ( options.fillSpace ) {
613
+ return "fill";
614
+ }
498
615
 
499
- _completed: function( cancel ) {
500
- this.running = cancel ? 0 : --this.running;
501
- if ( this.running ) {
502
- return;
503
- }
616
+ if ( options.clearStyle ) {
617
+ return "content";
618
+ }
504
619
 
505
- if ( this.options.clearStyle ) {
506
- this.toShow.add( this.toHide ).css({
507
- height: "",
508
- overflow: ""
509
- });
510
- }
620
+ if ( options.autoHeight ) {
621
+ return "auto";
622
+ }
623
+ }
624
+ });
625
+ }( jQuery, jQuery.ui.accordion.prototype ) );
511
626
 
512
- // other classes are removed before the animation; this one needs to stay until completed
513
- this.toHide.removeClass( "ui-accordion-content-active" );
514
- // Work around for rendering bug in IE (#5421)
515
- if ( this.toHide.length ) {
516
- this.toHide.parent()[0].className = this.toHide.parent()[0].className;
517
- }
627
+ // icon options
628
+ (function( $, prototype ) {
629
+ $.extend( prototype.options.icons, {
630
+ activeHeader: null, // remove default so we fall back to old values
631
+ headerSelected: "ui-icon-triangle-1-s"
632
+ });
518
633
 
519
- this._trigger( "change", null, this.data );
520
- }
521
- });
634
+ var _createIcons = prototype._createIcons;
635
+ prototype._createIcons = function() {
636
+ if ( this.options.icons ) {
637
+ this.options.icons.activeHeader = this.options.icons.activeHeader ||
638
+ this.options.icons.headerSelected;
639
+ }
640
+ _createIcons.call( this );
641
+ };
642
+ }( jQuery, jQuery.ui.accordion.prototype ) );
522
643
 
523
- $.extend( $.ui.accordion, {
524
- version: "1.8.24",
525
- animations: {
526
- slide: function( options, additions ) {
527
- options = $.extend({
528
- easing: "swing",
529
- duration: 300
530
- }, options, additions );
531
- if ( !options.toHide.size() ) {
532
- options.toShow.animate({
533
- height: "show",
534
- paddingTop: "show",
535
- paddingBottom: "show"
536
- }, options );
537
- return;
644
+ // expanded active option, activate method
645
+ (function( $, prototype ) {
646
+ prototype.activate = prototype._activate;
647
+
648
+ var _findActive = prototype._findActive;
649
+ prototype._findActive = function( index ) {
650
+ if ( index === -1 ) {
651
+ index = false;
538
652
  }
539
- if ( !options.toShow.size() ) {
540
- options.toHide.animate({
541
- height: "hide",
542
- paddingTop: "hide",
543
- paddingBottom: "hide"
544
- }, options );
545
- return;
653
+ if ( index && typeof index !== "number" ) {
654
+ index = this.headers.index( this.headers.filter( index ) );
655
+ if ( index === -1 ) {
656
+ index = false;
657
+ }
658
+ }
659
+ return _findActive.call( this, index );
660
+ };
661
+ }( jQuery, jQuery.ui.accordion.prototype ) );
662
+
663
+ // resize method
664
+ jQuery.ui.accordion.prototype.resize = jQuery.ui.accordion.prototype.refresh;
665
+
666
+ // change events
667
+ (function( $, prototype ) {
668
+ $.extend( prototype.options, {
669
+ change: null,
670
+ changestart: null
671
+ });
672
+
673
+ var _trigger = prototype._trigger;
674
+ prototype._trigger = function( type, event, data ) {
675
+ var ret = _trigger.apply( this, arguments );
676
+ if ( !ret ) {
677
+ return false;
546
678
  }
547
- var overflow = options.toShow.css( "overflow" ),
548
- percentDone = 0,
549
- showProps = {},
550
- hideProps = {},
551
- fxAttrs = [ "height", "paddingTop", "paddingBottom" ],
552
- originalWidth;
553
- // fix width before calculating height of hidden element
554
- var s = options.toShow;
555
- originalWidth = s[0].style.width;
556
- s.width( s.parent().width()
557
- - parseFloat( s.css( "paddingLeft" ) )
558
- - parseFloat( s.css( "paddingRight" ) )
559
- - ( parseFloat( s.css( "borderLeftWidth" ) ) || 0 )
560
- - ( parseFloat( s.css( "borderRightWidth" ) ) || 0 ) );
561
-
562
- $.each( fxAttrs, function( i, prop ) {
563
- hideProps[ prop ] = "hide";
564
-
565
- var parts = ( "" + $.css( options.toShow[0], prop ) ).match( /^([\d+-.]+)(.*)$/ );
566
- showProps[ prop ] = {
567
- value: parts[ 1 ],
568
- unit: parts[ 2 ] || "px"
569
- };
570
- });
571
- options.toShow.css({ height: 0, overflow: "hidden" }).show();
572
- options.toHide
573
- .filter( ":hidden" )
574
- .each( options.complete )
575
- .end()
576
- .filter( ":visible" )
577
- .animate( hideProps, {
578
- step: function( now, settings ) {
579
- // only calculate the percent when animating height
580
- // IE gets very inconsistent results when animating elements
581
- // with small values, which is common for padding
582
- if ( settings.prop == "height" ) {
583
- percentDone = ( settings.end - settings.start === 0 ) ? 0 :
584
- ( settings.now - settings.start ) / ( settings.end - settings.start );
585
- }
586
679
 
587
- options.toShow[ 0 ].style[ settings.prop ] =
588
- ( percentDone * showProps[ settings.prop ].value )
589
- + showProps[ settings.prop ].unit;
590
- },
591
- duration: options.duration,
592
- easing: options.easing,
593
- complete: function() {
594
- if ( !options.autoHeight ) {
595
- options.toShow.css( "height", "" );
596
- }
597
- options.toShow.css({
598
- width: originalWidth,
599
- overflow: overflow
600
- });
601
- options.complete();
680
+ if ( type === "beforeActivate" ) {
681
+ ret = _trigger.call( this, "changestart", event, {
682
+ oldHeader: data.oldHeader,
683
+ oldContent: data.oldPanel,
684
+ newHeader: data.newHeader,
685
+ newContent: data.newPanel
686
+ });
687
+ } else if ( type === "activate" ) {
688
+ ret = _trigger.call( this, "change", event, {
689
+ oldHeader: data.oldHeader,
690
+ oldContent: data.oldPanel,
691
+ newHeader: data.newHeader,
692
+ newContent: data.newPanel
693
+ });
694
+ }
695
+ return ret;
696
+ };
697
+ }( jQuery, jQuery.ui.accordion.prototype ) );
698
+
699
+ // animated option
700
+ // NOTE: this only provides support for "slide", "bounceslide", and easings
701
+ // not the full $.ui.accordion.animations API
702
+ (function( $, prototype ) {
703
+ $.extend( prototype.options, {
704
+ animate: null,
705
+ animated: "slide"
706
+ });
707
+
708
+ var _create = prototype._create;
709
+ prototype._create = function() {
710
+ var options = this.options;
711
+ if ( options.animate === null ) {
712
+ if ( !options.animated ) {
713
+ options.animate = false;
714
+ } else if ( options.animated === "slide" ) {
715
+ options.animate = 300;
716
+ } else if ( options.animated === "bounceslide" ) {
717
+ options.animate = {
718
+ duration: 200,
719
+ down: {
720
+ easing: "easeOutBounce",
721
+ duration: 1000
722
+ }
723
+ };
724
+ } else {
725
+ options.animate = options.animated;
602
726
  }
603
- });
604
- },
605
- bounceslide: function( options ) {
606
- this.slide( options, {
607
- easing: options.down ? "easeOutBounce" : "swing",
608
- duration: options.down ? 1000 : 200
609
- });
610
- }
611
- }
612
- });
727
+ }
728
+
729
+ _create.call( this );
730
+ };
731
+ }( jQuery, jQuery.ui.accordion.prototype ) );
732
+ }
613
733
 
614
734
  })( jQuery );