diff --git a/js/collapse.js b/js/collapse.js
index abbf25f2a6a7e66798acbd7c29fd5d6d10cf4b75..5d0f932ffbbdc9033a217b174ff0a5b51fb6ae3a 100644
--- a/js/collapse.js
+++ b/js/collapse.js
@@ -16,9 +16,15 @@
   var Collapse = function (element, options) {
     this.$element      = $(element)
     this.options       = $.extend({}, Collapse.DEFAULTS, options)
+    this.$trigger      = $(this.options.trigger).filter('[href="#' + element.id + '"], [data-target="#' + element.id + '"]')
     this.transitioning = null
 
-    if (this.options.parent) this.$parent = $(this.options.parent)
+    if (this.options.parent) {
+      this.$parent = this.getParent()
+    } else {
+      this.addAriaAndCollapsedClass(this.$element, this.$trigger)
+    }
+
     if (this.options.toggle) this.toggle()
   }
 
@@ -27,7 +33,8 @@
   Collapse.TRANSITION_DURATION = 350
 
   Collapse.DEFAULTS = {
-    toggle: true
+    toggle: true,
+    trigger: '[data-toggle="collapse"]'
   }
 
   Collapse.prototype.dimension = function () {
@@ -62,6 +69,10 @@
       .addClass('collapsing')[dimension](0)
       .attr('aria-expanded', true)
 
+    this.$trigger
+      .removeClass('collapsed')
+      .attr('aria-expanded', true)
+
     this.transitioning = 1
 
     var complete = function () {
@@ -98,6 +109,10 @@
       .removeClass('collapse in')
       .attr('aria-expanded', false)
 
+    this.$trigger
+      .addClass('collapsed')
+      .attr('aria-expanded', false)
+
     this.transitioning = 1
 
     var complete = function () {
@@ -120,6 +135,33 @@
     this[this.$element.hasClass('in') ? 'hide' : 'show']()
   }
 
+  Collapse.prototype.getParent = function () {
+    return $(this.options.parent)
+      .find('[data-toggle="collapse"][data-parent="' + this.options.parent + '"]')
+      .each($.proxy(function (i, element) {
+        var $element = $(element)
+        this.addAriaAndCollapsedClass(getTargetFromTrigger($element), $element)
+      }, this))
+      .end()
+  }
+
+  Collapse.prototype.addAriaAndCollapsedClass = function ($element, $trigger) {
+    var isOpen = $element.hasClass('in')
+
+    $element.attr('aria-expanded', isOpen)
+    $trigger
+      .toggleClass('collapsed', !isOpen)
+      .attr('aria-expanded', isOpen)
+  }
+
+  function getTargetFromTrigger($trigger) {
+    var href
+    var target = $trigger.attr('data-target')
+      || (href = $trigger.attr('href')) && href.replace(/.*(?=#[^\s]+$)/, '') // strip for ie7
+
+    return $(target)
+  }
+
 
   // COLLAPSE PLUGIN DEFINITION
   // ==========================
@@ -155,22 +197,13 @@
   // =================
 
   $(document).on('click.bs.collapse.data-api', '[data-toggle="collapse"]', function (e) {
-    var href
     var $this   = $(this)
-    var target  = $this.attr('data-target')
-        || e.preventDefault()
-        || (href = $this.attr('href')) && href.replace(/.*(?=#[^\s]+$)/, '') // strip for ie7
-    var $target = $(target)
+
+    if (!$this.attr('data-target')) e.preventDefault()
+
+    var $target = getTargetFromTrigger($this)
     var data    = $target.data('bs.collapse')
-    var option  = data ? 'toggle' : $this.data()
-    var parent  = $this.attr('data-parent')
-    var $parent = parent && $(parent)
-
-    if (!data || !data.transitioning) {
-      if ($parent) $parent.find('[data-toggle="collapse"][data-parent="' + parent + '"]').not($this).addClass('collapsed').attr('aria-expanded', false)
-      var isCollapsed = $target.hasClass('in')
-      $this.toggleClass('collapsed', isCollapsed).attr('aria-expanded', !isCollapsed)
-    }
+    var option  = data ? 'toggle' : $.extend({}, $this.data(), { trigger: this })
 
     Plugin.call($target, option)
   })
diff --git a/js/tests/unit/collapse.js b/js/tests/unit/collapse.js
index c1d78575c6ba525b6eb6530627c2847dd7f8f1b8..30d00e413561f33feeb715da8fb92bf070ee1f6c 100644
--- a/js/tests/unit/collapse.js
+++ b/js/tests/unit/collapse.js
@@ -79,7 +79,7 @@ $(function () {
 
     $('<div id="test1"/>')
       .appendTo('#qunit-fixture')
-      .on('show.bs.collapse', function () {
+      .on('shown.bs.collapse', function () {
         ok(!$target.hasClass('collapsed'))
         start()
       })
@@ -94,7 +94,7 @@ $(function () {
 
     $('<div id="test1" class="in"/>')
       .appendTo('#qunit-fixture')
-      .on('hide.bs.collapse', function () {
+      .on('hidden.bs.collapse', function () {
         ok($target.hasClass('collapsed'))
         start()
       })
@@ -137,12 +137,12 @@ $(function () {
   test('should remove "collapsed" class from active accordion target', function () {
     stop()
 
-    var accordionHTML = '<div id="accordion">'
-        + '<div class="accordion-group"/>'
-        + '<div class="accordion-group"/>'
-        + '<div class="accordion-group"/>'
+    var accordionHTML = '<div class="panel-group" id="accordion">'
+        + '<div class="panel"/>'
+        + '<div class="panel"/>'
+        + '<div class="panel"/>'
         + '</div>'
-    var $groups = $(accordionHTML).appendTo('#qunit-fixture').find('.accordion-group')
+    var $groups = $(accordionHTML).appendTo('#qunit-fixture').find('.panel')
 
     var $target1 = $('<a data-toggle="collapse" href="#body1" data-parent="#accordion"/>').appendTo($groups.eq(0))
 
@@ -156,7 +156,7 @@ $(function () {
 
     $('<div id="body3"/>')
       .appendTo($groups.eq(2))
-      .on('show.bs.collapse', function () {
+      .on('shown.bs.collapse', function () {
         ok($target1.hasClass('collapsed'), 'inactive target 1 does have class "collapsed"')
         ok($target2.hasClass('collapsed'), 'inactive target 2 does have class "collapsed"')
         ok(!$target3.hasClass('collapsed'), 'active target 3 does not have class "collapsed"')
@@ -170,12 +170,12 @@ $(function () {
   test('should allow dots in data-parent', function () {
     stop()
 
-    var accordionHTML = '<div class="accordion">'
-        + '<div class="accordion-group"/>'
-        + '<div class="accordion-group"/>'
-        + '<div class="accordion-group"/>'
+    var accordionHTML = '<div class="panel-group accordion">'
+        + '<div class="panel"/>'
+        + '<div class="panel"/>'
+        + '<div class="panel"/>'
         + '</div>'
-    var $groups = $(accordionHTML).appendTo('#qunit-fixture').find('.accordion-group')
+    var $groups = $(accordionHTML).appendTo('#qunit-fixture').find('.panel')
 
     var $target1 = $('<a data-toggle="collapse" href="#body1" data-parent=".accordion"/>').appendTo($groups.eq(0))
 
@@ -189,7 +189,7 @@ $(function () {
 
     $('<div id="body3"/>')
       .appendTo($groups.eq(2))
-      .on('show.bs.collapse', function () {
+      .on('shown.bs.collapse', function () {
         ok($target1.hasClass('collapsed'), 'inactive target 1 does have class "collapsed"')
         ok($target2.hasClass('collapsed'), 'inactive target 2 does have class "collapsed"')
         ok(!$target3.hasClass('collapsed'), 'active target 3 does not have class "collapsed"')
@@ -207,7 +207,7 @@ $(function () {
 
     $('<div id="test1"/>')
       .appendTo('#qunit-fixture')
-      .on('show.bs.collapse', function () {
+      .on('shown.bs.collapse', function () {
         equal($target.attr('aria-expanded'), 'true', 'aria-expanded on target is "true"')
         start()
       })
@@ -222,7 +222,7 @@ $(function () {
 
     $('<div id="test1" class="in"/>')
       .appendTo('#qunit-fixture')
-      .on('hide.bs.collapse', function () {
+      .on('hidden.bs.collapse', function () {
         equal($target.attr('aria-expanded'), 'false', 'aria-expanded on target is "false"')
         start()
       })
@@ -233,12 +233,12 @@ $(function () {
   test('should change aria-expanded from active accordion target to "false" and set the newly active one to "true"', function () {
     stop()
 
-    var accordionHTML = '<div id="accordion">'
-        + '<div class="accordion-group"/>'
-        + '<div class="accordion-group"/>'
-        + '<div class="accordion-group"/>'
+    var accordionHTML = '<div class="panel-group" id="accordion">'
+        + '<div class="panel"/>'
+        + '<div class="panel"/>'
+        + '<div class="panel"/>'
         + '</div>'
-    var $groups = $(accordionHTML).appendTo('#qunit-fixture').find('.accordion-group')
+    var $groups = $(accordionHTML).appendTo('#qunit-fixture').find('.panel')
 
     var $target1 = $('<a data-toggle="collapse" href="#body1" data-parent="#accordion"/>').appendTo($groups.eq(0))
 
@@ -252,7 +252,7 @@ $(function () {
 
     $('<div id="body3" aria-expanded="false"/>')
       .appendTo($groups.eq(2))
-      .on('show.bs.collapse', function () {
+      .on('shown.bs.collapse', function () {
         equal($target1.attr('aria-expanded'), 'false', 'inactive target 1 has aria-expanded="false"')
         equal($target2.attr('aria-expanded'), 'false', 'inactive target 2 has aria-expanded="false"')
         equal($target3.attr('aria-expanded'), 'true', 'active target 3 has aria-expanded="false"')
@@ -298,4 +298,32 @@ $(function () {
     }, 1)
   })
 
+  test('should add "collapsed" class to target when collapse is hidden via manual invocation', function () {
+    stop()
+
+    var $target = $('<a data-toggle="collapse" href="#test1"/>').appendTo('#qunit-fixture')
+
+    $('<div id="test1" class="in"/>')
+      .appendTo('#qunit-fixture')
+      .on('hidden.bs.collapse', function () {
+        ok($target.hasClass('collapsed'))
+        start()
+      })
+      .bootstrapCollapse('hide')
+  })
+
+  test('should remove "collapsed" class from target when collapse is shown via manual invocation', function () {
+    stop()
+
+    var $target = $('<a data-toggle="collapse" class="collapsed" href="#test1"/>').appendTo('#qunit-fixture')
+
+    $('<div id="test1"/>')
+      .appendTo('#qunit-fixture')
+      .on('shown.bs.collapse', function () {
+        ok(!$target.hasClass('collapsed'))
+        start()
+      })
+      .bootstrapCollapse('show')
+  })
+
 })