anjlab-bootstrap-rails 2.0.4.4 → 2.1.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 (73) hide show
  1. data/README.md +21 -20
  2. data/Rakefile +39 -26
  3. data/lib/bootstrap-rails/engine.rb +3 -0
  4. data/lib/bootstrap-rails/version.rb +1 -1
  5. data/vendor/assets/images/{glyphicons-halflings-white.png → twitter/glyphicons-halflings-white.png} +0 -0
  6. data/vendor/assets/images/twitter/glyphicons-halflings.png +0 -0
  7. data/vendor/assets/javascripts/twitter/bootstrap.js +13 -0
  8. data/vendor/assets/javascripts/twitter/bootstrap/affix.js +104 -0
  9. data/vendor/assets/javascripts/{bootstrap-alert.js → twitter/bootstrap/alert.js} +1 -1
  10. data/vendor/assets/javascripts/{bootstrap-button.js → twitter/bootstrap/button.js} +1 -1
  11. data/vendor/assets/javascripts/{bootstrap-carousel.js → twitter/bootstrap/carousel.js} +12 -5
  12. data/vendor/assets/javascripts/{bootstrap-collapse.js → twitter/bootstrap/collapse.js} +4 -3
  13. data/vendor/assets/javascripts/{bootstrap-dropdown.js → twitter/bootstrap/dropdown.js} +66 -16
  14. data/vendor/assets/javascripts/{bootstrap-modal.js → twitter/bootstrap/modal.js} +95 -74
  15. data/vendor/assets/javascripts/{bootstrap-popover.js → twitter/bootstrap/popover.js} +9 -4
  16. data/vendor/assets/javascripts/{bootstrap-scrollspy.js → twitter/bootstrap/scrollspy.js} +9 -9
  17. data/vendor/assets/javascripts/{bootstrap-tab.js → twitter/bootstrap/tab.js} +2 -2
  18. data/vendor/assets/javascripts/{bootstrap-tooltip.js → twitter/bootstrap/tooltip.js} +15 -15
  19. data/vendor/assets/javascripts/{bootstrap-transition.js → twitter/bootstrap/transition.js} +2 -3
  20. data/vendor/assets/javascripts/{bootstrap-typeahead.js → twitter/bootstrap/typeahead.js} +50 -35
  21. data/vendor/assets/stylesheets/twitter/bootstrap-responsive.scss +1 -0
  22. data/vendor/assets/stylesheets/twitter/bootstrap.scss +1 -0
  23. data/vendor/frameworks/twitter/bootstrap.scss +1 -0
  24. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/accordion.scss +3 -2
  25. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/alerts.scss +15 -8
  26. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/bootstrap.scss +1 -1
  27. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/breadcrumbs.scss +10 -10
  28. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/button-groups.scss +76 -23
  29. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/buttons.scss +76 -56
  30. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/carousel.scss +13 -3
  31. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/close.scss +4 -2
  32. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/code.scss +6 -5
  33. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/component-animations.scss +5 -2
  34. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/dropdowns.scss +81 -14
  35. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/forms.scss +99 -46
  36. data/vendor/frameworks/twitter/bootstrap/grid.scss +21 -0
  37. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/hero-unit.scss +4 -2
  38. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/labels-badges.scss +19 -2
  39. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/layouts.scss +1 -2
  40. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/mixins.scss +105 -81
  41. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/modals.scss +9 -2
  42. data/vendor/frameworks/twitter/bootstrap/navbar.scss +468 -0
  43. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/navs.scss +38 -17
  44. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/pager.scss +5 -4
  45. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/pagination.scss +16 -8
  46. data/vendor/frameworks/twitter/bootstrap/popovers.scss +117 -0
  47. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/progress-bars.scss +18 -13
  48. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/reset.scss +6 -3
  49. data/vendor/frameworks/twitter/bootstrap/responsive-1200px-min.scss +28 -0
  50. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/responsive-767px-max.scss +83 -69
  51. data/vendor/frameworks/twitter/bootstrap/responsive-768px-979px.scss +19 -0
  52. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/responsive-navbar.scss +17 -4
  53. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/responsive-utilities.scss +17 -15
  54. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/responsive.scss +5 -5
  55. data/vendor/frameworks/twitter/bootstrap/scaffolding.scss +51 -0
  56. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/sprites.scss +17 -20
  57. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/tables.scss +60 -15
  58. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/thumbnails.scss +9 -4
  59. data/vendor/frameworks/twitter/bootstrap/tooltip.scss +70 -0
  60. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/type.scss +56 -83
  61. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/utilities.scss +9 -2
  62. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/variables.scss +109 -36
  63. data/vendor/{assets/stylesheets → frameworks/twitter/bootstrap}/wells.scss +7 -5
  64. metadata +63 -59
  65. data/vendor/assets/images/glyphicons-halflings.png +0 -0
  66. data/vendor/assets/javascripts/bootstrap.js +0 -12
  67. data/vendor/assets/stylesheets/grid.scss +0 -5
  68. data/vendor/assets/stylesheets/navbar.scss +0 -358
  69. data/vendor/assets/stylesheets/popovers.scss +0 -49
  70. data/vendor/assets/stylesheets/responsive-1200px-min.scss +0 -26
  71. data/vendor/assets/stylesheets/responsive-768px-979px.scss +0 -17
  72. data/vendor/assets/stylesheets/scaffolding.scss +0 -29
  73. data/vendor/assets/stylesheets/tooltip.scss +0 -35
data/README.md CHANGED
@@ -1,4 +1,4 @@
1
- # Twitter Bootstrap v2.0.4 for Rails 3
1
+ # Twitter Bootstrap v2.1.0 for Rails 3
2
2
  Bootstrap is a toolkit from Twitter designed to kickstart development of webapps and sites.
3
3
  It includes base CSS and HTML for typography, forms, buttons, tables, grids, navigation, and more.
4
4
 
@@ -10,7 +10,7 @@ anjlab-bootstrap-rails project integrates Bootstrap CSS (with Sass flavour) and
10
10
  Include Bootstrap in Gemfile;
11
11
 
12
12
  ``` ruby
13
- gem 'anjlab-bootstrap-rails', '>= 2.0', :require => 'bootstrap-rails'
13
+ gem 'anjlab-bootstrap-rails', '>= 2.1', :require => 'bootstrap-rails'
14
14
  ```
15
15
 
16
16
  or you can install from latest build;
@@ -27,13 +27,13 @@ and run bundle install.
27
27
  Add necessary stylesheet file to app/assets/stylesheets/application.css
28
28
 
29
29
  ``` css
30
- *= require bootstrap
31
- *= require responsive
30
+ *= require twitter/bootstrap
31
+ *= require twitter/bootstrap-responsive
32
32
  ```
33
33
 
34
34
  You can override bootstrap variables:
35
35
 
36
- 1. replace `*= require bootstrap` with `*= require app_bootstrap`
36
+ 1. replace `*= require twitter/bootstrap` with `*= require app_bootstrap`
37
37
  2. create `app_bootstrap.css.scss` :
38
38
 
39
39
  ```scss
@@ -45,8 +45,8 @@ $gridColumnWidth: 70px;
45
45
  $gridGutterWidth: 10px;
46
46
 
47
47
  // import original bootstrap
48
- @import "bootstrap";
49
- @import "responsive";
48
+ @import "twitter/bootstrap";
49
+ @import "twitter/bootstrap-responsive";
50
50
  ```
51
51
  NOTE: restart `pow` if you are using it.
52
52
 
@@ -56,21 +56,22 @@ Add necessary javascript(s) files to app/assets/javascripts/application.js
56
56
 
57
57
  ``` javascript
58
58
  // Include all twitter's javascripts
59
- //= require bootstrap
59
+ //= require twitter/bootstrap
60
60
 
61
61
  // Or peek any of them yourself
62
- //= require bootstrap-transition
63
- //= require bootstrap-alert
64
- //= require bootstrap-modal
65
- //= require bootstrap-dropdown
66
- //= require bootstrap-scrollspy
67
- //= require bootstrap-tab
68
- //= require bootstrap-tooltip
69
- //= require bootstrap-popover
70
- //= require bootstrap-button
71
- //= require bootstrap-collapse
72
- //= require bootstrap-carousel
73
- //= require bootstrap-typeahead
62
+ //= require twitter/bootstrap/transition
63
+ //= require twitter/bootstrap/alert
64
+ //= require twitter/bootstrap/modal
65
+ //= require twitter/bootstrap/dropdown
66
+ //= require twitter/bootstrap/scrollspy
67
+ //= require twitter/bootstrap/tab
68
+ //= require twitter/bootstrap/tooltip
69
+ //= require twitter/bootstrap/popover
70
+ //= require twitter/bootstrap/button
71
+ //= require twitter/bootstrap/collapse
72
+ //= require twitter/bootstrap/carousel
73
+ //= require twitter/bootstrap/typeahead
74
+ //= require twitter/bootstrap/affix
74
75
  ```
75
76
 
76
77
  ## Upgrade notes from 1.4
data/Rakefile CHANGED
@@ -10,40 +10,53 @@ namespace :twitter do
10
10
  end
11
11
  end
12
12
 
13
- desc "Update Twitter's Bootstrap Assets"
14
- task :update => :pull do
15
13
 
16
- Dir["vendor/twitter/img/*.*"].each do |file|
17
- cp file, "vendor/assets/images/", :verbose => true
18
- end
14
+ TW_IMGS = FileList["vendor/twitter/img/*.*"]
15
+ ASSETS_IMGS = TW_IMGS.pathmap("vendor/assets/images/twitter/%f")
16
+ ASSETS_IMGS.zip(TW_IMGS).each do |target, source|
17
+ file target => [source] { cp source, target, verbose: true }
18
+ end
19
19
 
20
- Dir["vendor/assets/stylesheets/*.*"].each {|f| FileUtils.rm(f)}
21
- Dir["vendor/twitter/scss/*.scss"].each do |file|
22
- cp file, "vendor/assets/stylesheets/", :verbose => true
23
- end
20
+ TW_JS = FileList["vendor/twitter/js/*.*"]
21
+ ASSETS_JS = TW_JS.pathmap("vendor/assets/javascripts/twitter/bootstrap/%{bootstrap-,}f")
22
+ ASSETS_JS.zip(TW_JS).each do |target, source|
23
+ file target => [source] { cp source, target, verbose: true }
24
+ end
24
25
 
25
- Dir["vendor/assets/javascripts/*.*"].each {|f| FileUtils.rm(f)}
26
- js_files = Dir["vendor/twitter/js/*.js"].map()
27
- js_files.each do |file|
28
- cp file, "vendor/assets/javascripts/", :verbose => true
29
- end
26
+ TW_SCSS = FileList["vendor/twitter/scss/*.*"]
27
+ ASSETS_SCSS = TW_SCSS.pathmap("vendor/frameworks/twitter/bootstrap/%f")
28
+ ASSETS_SCSS.zip(TW_SCSS).each do |target, source|
29
+ file target => [source] { cp source, target, verbose: true }
30
+ end
30
31
 
31
- js_priorities = {}
32
- js_files.each {|f| js_priorities[File.basename(f)] = 1}
32
+ desc "Update Twitter's Bootstrap Images"
33
+ task :imgs => ASSETS_IMGS
34
+
35
+ desc "Update Twitter's Bootstrap JS"
36
+ task :js => ASSETS_JS do
37
+ js = {}
38
+ ASSETS_JS.pathmap("%f").each do |f|
39
+ js[f] = 1
40
+ end
33
41
 
34
42
  # dependencies
35
- js_priorities["bootstrap-transition.js"] = 0
36
- js_priorities["bootstrap-tooltip.js"] = 2
37
- js_priorities["bootstrap-popover.js"] = 3
38
-
39
- js_list = js_priorities.to_a.sort {|a,b| a[1] <=> b[1]}.map{|p| p[0]}
43
+ js["transition.js"] = 0
44
+ js["tooltip.js"] = 2
45
+ js["popover.js"] = 3
40
46
 
41
- File.open("vendor/assets/javascripts/bootstrap.js", "w") do |f|
42
- js_list.each do |js|
43
- f.write "//= require #{js}\n"
44
- end
45
- end
47
+ list = js.to_a.sort {|a,b| a[1] <=> b[1]}.map{|p| p[0]}
48
+ File.write "vendor/assets/javascripts/twitter/bootstrap.js", list.map {|f| "//= require twitter/bootstrap/#{f}"}.join("\n")
46
49
  end
50
+
51
+ desc "Update Twitter's Bootstrap SCSS"
52
+ task :scss => ASSETS_SCSS do
53
+ File.write "vendor/frameworks/twitter/bootstrap.scss", '@import "bootstrap/bootstrap.scss";'
54
+ File.write "vendor/assets/stylesheets/twitter/bootstrap.scss", '@import "twitter/bootstrap/bootstrap.scss";'
55
+ File.write "vendor/assets/stylesheets/twitter/bootstrap-responsive.scss", '@import "twitter/bootstrap/responsive.scss";'
56
+ end
57
+
58
+ desc "Update Twitter's Bootstrap Assets"
59
+ task :assets => [:pull, :imgs, :scss, :js]
47
60
 
48
61
  end
49
62
 
@@ -1,6 +1,9 @@
1
1
  module Bootstrap
2
2
  module Rails
3
3
  class Engine < ::Rails::Engine
4
+ initializer 'anjlab-bootstrap-rails.setup' do |app|
5
+ config.sass.load_paths << File.join(config.root, 'vendor', 'frameworks')
6
+ end
4
7
  end
5
8
  end
6
9
  end
@@ -1,5 +1,5 @@
1
1
  module Bootstrap
2
2
  module Rails
3
- VERSION = "2.0.4.4"
3
+ VERSION = "2.1.0.0"
4
4
  end
5
5
  end
@@ -0,0 +1,13 @@
1
+ //= require twitter/bootstrap/transition.js
2
+ //= require twitter/bootstrap/dropdown.js
3
+ //= require twitter/bootstrap/button.js
4
+ //= require twitter/bootstrap/carousel.js
5
+ //= require twitter/bootstrap/collapse.js
6
+ //= require twitter/bootstrap/alert.js
7
+ //= require twitter/bootstrap/affix.js
8
+ //= require twitter/bootstrap/typeahead.js
9
+ //= require twitter/bootstrap/scrollspy.js
10
+ //= require twitter/bootstrap/tab.js
11
+ //= require twitter/bootstrap/modal.js
12
+ //= require twitter/bootstrap/tooltip.js
13
+ //= require twitter/bootstrap/popover.js
@@ -0,0 +1,104 @@
1
+ /* ==========================================================
2
+ * bootstrap-affix.js v2.1.0
3
+ * http://twitter.github.com/bootstrap/javascript.html#affix
4
+ * ==========================================================
5
+ * Copyright 2012 Twitter, Inc.
6
+ *
7
+ * Licensed under the Apache License, Version 2.0 (the "License");
8
+ * you may not use this file except in compliance with the License.
9
+ * You may obtain a copy of the License at
10
+ *
11
+ * http://www.apache.org/licenses/LICENSE-2.0
12
+ *
13
+ * Unless required by applicable law or agreed to in writing, software
14
+ * distributed under the License is distributed on an "AS IS" BASIS,
15
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
+ * See the License for the specific language governing permissions and
17
+ * limitations under the License.
18
+ * ========================================================== */
19
+
20
+
21
+ !function ($) {
22
+
23
+ "use strict"; // jshint ;_;
24
+
25
+
26
+ /* AFFIX CLASS DEFINITION
27
+ * ====================== */
28
+
29
+ var Affix = function (element, options) {
30
+ this.options = $.extend({}, $.fn.affix.defaults, options)
31
+ this.$window = $(window).on('scroll.affix.data-api', $.proxy(this.checkPosition, this))
32
+ this.$element = $(element)
33
+ this.checkPosition()
34
+ }
35
+
36
+ Affix.prototype.checkPosition = function () {
37
+ if (!this.$element.is(':visible')) return
38
+
39
+ var scrollHeight = $(document).height()
40
+ , scrollTop = this.$window.scrollTop()
41
+ , position = this.$element.offset()
42
+ , offset = this.options.offset
43
+ , offsetBottom = offset.bottom
44
+ , offsetTop = offset.top
45
+ , reset = 'affix affix-top affix-bottom'
46
+ , affix
47
+
48
+ if (typeof offset != 'object') offsetBottom = offsetTop = offset
49
+ if (typeof offsetTop == 'function') offsetTop = offset.top()
50
+ if (typeof offsetBottom == 'function') offsetBottom = offset.bottom()
51
+
52
+ affix = this.unpin != null && (scrollTop + this.unpin <= position.top) ?
53
+ false : offsetBottom != null && (position.top + this.$element.height() >= scrollHeight - offsetBottom) ?
54
+ 'bottom' : offsetTop != null && scrollTop <= offsetTop ?
55
+ 'top' : false
56
+
57
+ if (this.affixed === affix) return
58
+
59
+ this.affixed = affix
60
+ this.unpin = affix == 'bottom' ? position.top - scrollTop : null
61
+
62
+ this.$element.removeClass(reset).addClass('affix' + (affix ? '-' + affix : ''))
63
+ }
64
+
65
+
66
+ /* AFFIX PLUGIN DEFINITION
67
+ * ======================= */
68
+
69
+ $.fn.affix = function (option) {
70
+ return this.each(function () {
71
+ var $this = $(this)
72
+ , data = $this.data('affix')
73
+ , options = typeof option == 'object' && option
74
+ if (!data) $this.data('affix', (data = new Affix(this, options)))
75
+ if (typeof option == 'string') data[option]()
76
+ })
77
+ }
78
+
79
+ $.fn.affix.Constructor = Affix
80
+
81
+ $.fn.affix.defaults = {
82
+ offset: 0
83
+ }
84
+
85
+
86
+ /* AFFIX DATA-API
87
+ * ============== */
88
+
89
+ $(window).on('load', function () {
90
+ $('[data-spy="affix"]').each(function () {
91
+ var $spy = $(this)
92
+ , data = $spy.data()
93
+
94
+ data.offset = data.offset || {}
95
+
96
+ data.offsetBottom && (data.offset.bottom = data.offsetBottom)
97
+ data.offsetTop && (data.offset.top = data.offsetTop)
98
+
99
+ $spy.affix(data)
100
+ })
101
+ })
102
+
103
+
104
+ }(window.jQuery);
@@ -1,5 +1,5 @@
1
1
  /* ==========================================================
2
- * bootstrap-alert.js v2.0.4
2
+ * bootstrap-alert.js v2.1.0
3
3
  * http://twitter.github.com/bootstrap/javascript.html#alerts
4
4
  * ==========================================================
5
5
  * Copyright 2012 Twitter, Inc.
@@ -1,5 +1,5 @@
1
1
  /* ============================================================
2
- * bootstrap-button.js v2.0.4
2
+ * bootstrap-button.js v2.1.0
3
3
  * http://twitter.github.com/bootstrap/javascript.html#buttons
4
4
  * ============================================================
5
5
  * Copyright 2012 Twitter, Inc.
@@ -1,5 +1,5 @@
1
1
  /* ==========================================================
2
- * bootstrap-carousel.js v2.0.4
2
+ * bootstrap-carousel.js v2.1.0
3
3
  * http://twitter.github.com/bootstrap/javascript.html#carousel
4
4
  * ==========================================================
5
5
  * Copyright 2012 Twitter, Inc.
@@ -46,7 +46,7 @@
46
46
  }
47
47
 
48
48
  , to: function (pos) {
49
- var $active = this.$element.find('.active')
49
+ var $active = this.$element.find('.item.active')
50
50
  , children = $active.parent().children()
51
51
  , activePos = children.index($active)
52
52
  , that = this
@@ -68,6 +68,10 @@
68
68
 
69
69
  , pause: function (e) {
70
70
  if (!e) this.paused = true
71
+ if (this.$element.find('.next, .prev').length && $.support.transition.end) {
72
+ this.$element.trigger($.support.transition.end)
73
+ this.cycle()
74
+ }
71
75
  clearInterval(this.interval)
72
76
  this.interval = null
73
77
  return this
@@ -84,13 +88,15 @@
84
88
  }
85
89
 
86
90
  , slide: function (type, next) {
87
- var $active = this.$element.find('.active')
91
+ var $active = this.$element.find('.item.active')
88
92
  , $next = next || $active[type]()
89
93
  , isCycling = this.interval
90
94
  , direction = type == 'next' ? 'left' : 'right'
91
95
  , fallback = type == 'next' ? 'first' : 'last'
92
96
  , that = this
93
- , e = $.Event('slide')
97
+ , e = $.Event('slide', {
98
+ relatedTarget: $next[0]
99
+ })
94
100
 
95
101
  this.sliding = true
96
102
 
@@ -138,9 +144,10 @@
138
144
  var $this = $(this)
139
145
  , data = $this.data('carousel')
140
146
  , options = $.extend({}, $.fn.carousel.defaults, typeof option == 'object' && option)
147
+ , action = typeof option == 'string' ? option : options.slide
141
148
  if (!data) $this.data('carousel', (data = new Carousel(this, options)))
142
149
  if (typeof option == 'number') data.to(option)
143
- else if (typeof option == 'string' || (option = options.slide)) data[option]()
150
+ else if (action) data[action]()
144
151
  else if (options.interval) data.cycle()
145
152
  })
146
153
  }
@@ -1,5 +1,5 @@
1
1
  /* =============================================================
2
- * bootstrap-collapse.js v2.0.4
2
+ * bootstrap-collapse.js v2.1.0
3
3
  * http://twitter.github.com/bootstrap/javascript.html#collapse
4
4
  * =============================================================
5
5
  * Copyright 2012 Twitter, Inc.
@@ -67,7 +67,7 @@
67
67
 
68
68
  this.$element[dimension](0)
69
69
  this.transition('addClass', $.Event('show'), 'shown')
70
- this.$element[dimension](this.$element[0][scroll])
70
+ $.support.transition && this.$element[dimension](this.$element[0][scroll])
71
71
  }
72
72
 
73
73
  , hide: function () {
@@ -144,12 +144,13 @@
144
144
  * ==================== */
145
145
 
146
146
  $(function () {
147
- $('body').on('click.collapse.data-api', '[data-toggle=collapse]', function ( e ) {
147
+ $('body').on('click.collapse.data-api', '[data-toggle=collapse]', function (e) {
148
148
  var $this = $(this), href
149
149
  , target = $this.attr('data-target')
150
150
  || e.preventDefault()
151
151
  || (href = $this.attr('href')) && href.replace(/.*(?=#[^\s]+$)/, '') //strip for ie7
152
152
  , option = $(target).data('collapse') ? 'toggle' : $this.data()
153
+ $this[$(target).hasClass('in') ? 'addClass' : 'removeClass']('collapsed')
153
154
  $(target).collapse(option)
154
155
  })
155
156
  })
@@ -1,5 +1,5 @@
1
1
  /* ============================================================
2
- * bootstrap-dropdown.js v2.0.4
2
+ * bootstrap-dropdown.js v2.1.0
3
3
  * http://twitter.github.com/bootstrap/javascript.html#dropdowns
4
4
  * ============================================================
5
5
  * Copyright 2012 Twitter, Inc.
@@ -26,7 +26,7 @@
26
26
  /* DROPDOWN CLASS DEFINITION
27
27
  * ========================= */
28
28
 
29
- var toggle = '[data-toggle="dropdown"]'
29
+ var toggle = '[data-toggle=dropdown]'
30
30
  , Dropdown = function (element) {
31
31
  var $el = $(element).on('click.dropdown.data-api', this.toggle)
32
32
  $('html').on('click.dropdown.data-api', function () {
@@ -41,34 +41,82 @@
41
41
  , toggle: function (e) {
42
42
  var $this = $(this)
43
43
  , $parent
44
- , selector
45
44
  , isActive
46
45
 
47
46
  if ($this.is('.disabled, :disabled')) return
48
47
 
49
- selector = $this.attr('data-target')
48
+ $parent = getParent($this)
50
49
 
51
- if (!selector) {
52
- selector = $this.attr('href')
53
- selector = selector && selector.replace(/.*(?=#[^\s]*$)/, '') //strip for ie7
50
+ isActive = $parent.hasClass('open')
51
+
52
+ clearMenus()
53
+
54
+ if (!isActive) {
55
+ $parent.toggleClass('open')
56
+ $this.focus()
54
57
  }
55
58
 
56
- $parent = $(selector)
57
- $parent.length || ($parent = $this.parent())
59
+ return false
60
+ }
61
+
62
+ , keydown: function (e) {
63
+ var $this
64
+ , $items
65
+ , $active
66
+ , $parent
67
+ , isActive
68
+ , index
69
+
70
+ if (!/(38|40|27)/.test(e.keyCode)) return
71
+
72
+ $this = $(this)
73
+
74
+ e.preventDefault()
75
+ e.stopPropagation()
76
+
77
+ if ($this.is('.disabled, :disabled')) return
78
+
79
+ $parent = getParent($this)
58
80
 
59
81
  isActive = $parent.hasClass('open')
60
82
 
61
- clearMenus()
83
+ if (!isActive || (isActive && e.keyCode == 27)) return $this.click()
62
84
 
63
- if (!isActive) $parent.toggleClass('open')
85
+ $items = $('[role=menu] li:not(.divider) a', $parent)
64
86
 
65
- return false
87
+ if (!$items.length) return
88
+
89
+ index = $items.index($items.filter(':focus'))
90
+
91
+ if (e.keyCode == 38 && index > 0) index-- // up
92
+ if (e.keyCode == 40 && index < $items.length - 1) index++ // down
93
+ if (!~index) index = 0
94
+
95
+ $items
96
+ .eq(index)
97
+ .focus()
66
98
  }
67
99
 
68
100
  }
69
101
 
70
102
  function clearMenus() {
71
- $(toggle).parent().removeClass('open')
103
+ getParent($(toggle))
104
+ .removeClass('open')
105
+ }
106
+
107
+ function getParent($this) {
108
+ var selector = $this.attr('data-target')
109
+ , $parent
110
+
111
+ if (!selector) {
112
+ selector = $this.attr('href')
113
+ selector = selector && selector.replace(/.*(?=#[^\s]*$)/, '') //strip for ie7
114
+ }
115
+
116
+ $parent = $(selector)
117
+ $parent.length || ($parent = $this.parent())
118
+
119
+ return $parent
72
120
  }
73
121
 
74
122
 
@@ -91,10 +139,12 @@
91
139
  * =================================== */
92
140
 
93
141
  $(function () {
94
- $('html').on('click.dropdown.data-api', clearMenus)
142
+ $('html')
143
+ .on('click.dropdown.data-api touchstart.dropdown.data-api', clearMenus)
95
144
  $('body')
96
- .on('click.dropdown', '.dropdown form', function (e) { e.stopPropagation() })
97
- .on('click.dropdown.data-api', toggle, Dropdown.prototype.toggle)
145
+ .on('click.dropdown touchstart.dropdown.data-api', '.dropdown', function (e) { e.stopPropagation() })
146
+ .on('click.dropdown.data-api touchstart.dropdown.data-api' , toggle, Dropdown.prototype.toggle)
147
+ .on('keydown.dropdown.data-api touchstart.dropdown.data-api', toggle + ', [role=menu]' , Dropdown.prototype.keydown)
98
148
  })
99
149
 
100
150
  }(window.jQuery);