bootstrap accordion menu - javascript

My problem is that i used the bootstrap accordion menu for my wordpress site.
Every menu item has sub menus as links so whenever I clicked on any link it toke me to another page meaning the page reloaded, but the accordion menu gets closed and I want it to remain open with the selected link.
My whole site is on bootstrap. I am new to wordpress so don't even know that which jquery function is working on this accordion menu.
Here is my code for accordion menu:
<div id="accordion2" class="accordion">
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle" href="#collapseOne" data-toggle="collapse" data-parent="#accordion2">B.A Honours Programmes</a>
</div>
<div id="collapseOne" class="accordion-body collapse">
<div class="accordion-inner">
Fashion Design
</div>
<div class="accordion-inner">
Fashion Styling & Image Design
</div>
<div class="accordion-inner">
Textile Design for Fashion And Interiors
</div>
<div class="accordion-inner">
Communication Design
</div>
<div class="accordion-inner">
Interior Architecture and Design
</div>
<div class="accordion-inner">
Interior Product Design
</div>
<div class="accordion-inner">
Jewellery Design
</div>
<div class="accordion-inner">
Fashion Media Communication
</div>
<div class="accordion-inner">
Fashion Business Management
</div>
<div class="accordion-inner">
Fashion Marketing and Retailing Management
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle" href="#collapseTwo" data-toggle="collapse" data-parent="#accordion2">Postgraduate Diploma Programmes</a>
</div>
<div id="collapseTwo" class="accordion-body collapse">
<div class="accordion-inner">
Fashion Design
</div>
<div class="accordion-inner">
Textile Design
</div>
<div class="accordion-inner">
Fashion Retail
</div>
<div class="accordion-inner">
Fashion Marketing
</div>
<div class="accordion-inner">
Garment Manufacturing
</div>
<div class="accordion-inner">
Fashion Merchandising
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle" href="#collapseThree" data-toggle="collapse" data-parent="#accordion2">Masters Programmes</a>
</div>
<div id="collapseThree" class="accordion-body collapse">
<div class="accordion-inner">
MA Design(Fashion and Textile)
</div>
<div class="accordion-inner">
MA Fashion Marketing
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle" href="#collapseFour" data-toggle="collapse" data-parent="#accordion2">Professional Programmes</a>
</div>
<div id="collapseFour" class="accordion-body collapse">
<div class="accordion-inner">
Luxury Brands
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle" href="#collapseFive" data-toggle="collapse" data-parent="#accordion2">Diploma Programmes</a>
</div>
<div id="collapseFive" class="accordion-body collapse">
<div class="accordion-inner">
Visual Merchandising & Store Design
</div>
<div class="accordion-inner">
Professional Photography with BTK Germany
</div>
<div class="accordion-inner">
Digital Film Making
</div>
<div class="accordion-inner">
Creative Graphic Design
</div>
<div class="accordion-inner">
Styling for Interiors
</div>
<div class="accordion-inner">
Fashion & Lifestyle Ecommerce
</div>
<div class="accordion-inner">
Fashion Media Makeup
</div>
<div class="accordion-inner">
New Media Design
</div>
<div class="accordion-inner">
Retail Operations
</div>
<div class="accordion-inner">
Entrepreneurship and Business Management for Creative Industries
</div>
<div class="accordion-inner">
Apparel Manufacturing
</div>
<div class="accordion-inner">
Interior Styling
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle" href="#collapseSix" data-toggle="collapse" data-parent="#accordion2">Certificate Programmes</a>
</div>
<div id="collapseSix" class="accordion-body collapse">
<div class="accordion-inner">
Creative Fashion & Technology in Women's Wear
</div>
<div class="accordion-inner">
Apparel Marketing & Merchandising
</div>
<div class="accordion-inner">
Personal Styling & Grooming
</div>
</div>
</div>
</div>
Here is the CSS for accordion menu resides in bootstrap.css:
.accordion {
margin-bottom: 20px;
}
.accordion-group {
margin-bottom: 2px;
/*border: 1px solid #e5e5e5;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;
border-radius: 4px;*/
}
.accordion-heading {
border-bottom: 0;
background-color:#cccccc;
}
.accordion-heading .accordion-toggle {
display: block;
padding: 2px 4px;
text-decoration:none;
/*background-color:#e52b27;*/
}
.accordion-toggle {
cursor: pointer;
color:#5e5e5e;
text-decoration:none;
}
.accordion-inner {
padding: 2px 4px;
border-top: 1px solid #e5e5e5;
text-decoration:none;
}
and I think this is the JS working on it (not sure):
/* COLLAPSE PUBLIC CLASS DEFINITION
* ================================ */
var Collapse = function (element, options) {
this.$element = $(element)
this.options = $.extend({}, $.fn.collapse.defaults, options)
if (this.options.parent) {
this.$parent = $(this.options.parent)
}
this.options.toggle && this.toggle()
}
Collapse.prototype = {
constructor: Collapse
, dimension: function () {
var hasWidth = this.$element.hasClass('width')
return hasWidth ? 'width' : 'height'
}
, show: function () {
var dimension
, scroll
, actives
, hasData
if (this.transitioning) return
dimension = this.dimension()
scroll = $.camelCase(['scroll', dimension].join('-'))
actives = this.$parent && this.$parent.find('> .accordion-group > .in')
if (actives && actives.length) {
hasData = actives.data('collapse')
if (hasData && hasData.transitioning) return
actives.collapse('hide')
hasData || actives.data('collapse', null)
}
this.$element[dimension](0)
this.transition('addClass', $.Event('show'), 'shown')
$.support.transition && this.$element[dimension](this.$element[0][scroll])
}
, hide: function () {
var dimension
if (this.transitioning) return
dimension = this.dimension()
this.reset(this.$element[dimension]())
this.transition('removeClass', $.Event('hide'), 'hidden')
this.$element[dimension](0)
}
, reset: function (size) {
var dimension = this.dimension()
this.$element
.removeClass('collapse')
[dimension](size || 'auto')
[0].offsetWidth
this.$element[size !== null ? 'addClass' : 'removeClass']('collapse')
return this
}
, transition: function (method, startEvent, completeEvent) {
var that = this
, complete = function () {
if (startEvent.type == 'show') that.reset()
that.transitioning = 0
that.$element.trigger(completeEvent)
}
this.$element.trigger(startEvent)
if (startEvent.isDefaultPrevented()) return
this.transitioning = 1
this.$element[method]('in')
$.support.transition && this.$element.hasClass('collapse') ?
this.$element.one($.support.transition.end, complete) :
complete()
}
, toggle: function () {
this[this.$element.hasClass('in') ? 'hide' : 'show']()
}
}

Here's what you should do. Throw away the code you've written, because you're misusing accordions. To make a navigation with dropdowns, here's an example.
<div class="navbar">
<div class="navbar-inner">
<div class="container">
<a class="btn btn-navbar" data-toggle="collapse" data-target=".subnav-collapse"> <span class="icon-bar"></span> <span class="icon-bar"></span> <span class="icon-bar"></span> </a>
<a class="brand" href="#">Title</a>
<div class="nav-collapse subnav-collapse">
<ul class="nav">
<li class="active">
Home
</li>
<li>
Link
</li>
<li>
Link
</li>
<li class="dropdown">
Dropdown <b class="caret"></b>
<ul class="dropdown-menu">
<li>
Action
</li>
<li>
Another action
</li>
<li>
Something else here
</li>
<li class="divider"></li>
<li class="nav-header">
Nav header
</li>
<li>
Separated link
</li>
<li>
One more separated link
</li>
</ul>
</li>
</ul>
</div><!-- /.nav-collapse -->
</div>
</div><!-- /navbar-inner -->
</div>
EDIT:
To open an accordion on page load, this should work:
Assign the accordion you want to be opened class="open-accordion" and add to your javascript file or within <script></script> the following snippet:
$('.open-accordion').on('hidden', function () {
$('.open-accordion').collapse('show')
})
I haven't tested it, but should work according to bootstrap documentation.

<ul class="accordion">
<li id="one" class="files">
Admin Video
<ul class="sub-menu">
<li><em>01</em>Add video</li>
<li><em>02</em>List Video</li>
<li><em>03</em>Video Categories</li>
</ul>
</li>
<li id="two" class="mail">
Users
<ul class="sub-menu">
<li><em>01</em>Subscribers List</li>
<li><em>02</em>User Video Suggestion</li>
</ul>
</li>
<li id="three" class="cloud">
<a class="active" href="#three">Background Image options</a>
<ul class="sub-menu">
<li><em>01</em>Add</li>
<li><em>02</em>List</li>
</ul>
</li>
</ul>
$(document).ready(function() {
var accordion_head = $('.accordion > li > a'),
accordion_body = $('.accordion li > .sub-menu');
$.each($(".accordion > li > a"), function(){
if($(this).attr('class') == 'active')
{
$(this).next().slideDown('normal');
}
});
// Open the first tab on load
//accordion_head.first().addClass('active').next().slideDown('normal');
// Click function
accordion_head.on('click', function(event) {
// Disable header links
event.preventDefault();
// Show and hide the tabs on click
if ($(this).attr('class') != 'active'){
accordion_body.slideUp('normal');
$(this).next().stop(true,true).slideToggle('normal');
accordion_head.removeClass('active');
$(this).addClass('active');
}
});
});

Related

How to write a "this" - Function

I would like to reduce my Javascript code, maybe with variables or with "this"? It's to much code for a little bit of intention.
$("#Linkitem1").click(function() {
$("#item1").fadeIn(2500);
$("#item2").hide();
$("#item3").hide();
$("#Linkitem3").removeClass("active btn-warning");
$("#Linkitem2").removeClass("active btn-warning");
$("#Linkitem1").addClass("active btn-warning");
});
$("#Linkitem2").click(function() {
$("#item2").fadeIn(2500);
$("#item1").hide();
$("#item3").hide();
$("#Linkitem1").removeClass("active btn-warning");
$("#Linkitem3").removeClass("active btn-warning");
$("#Linkitem2").addClass("active btn-warning");
});
$("#Linkitem3").click(function() {
$("#item3").fadeIn(2500);
$("#item2").hide();
$("#item1").hide();
$("#Linkitem1").removeClass("active btn-warning");
$("#Linkitem2").removeClass("active btn-warning");
$("#Linkitem3").addClass("active btn-warning");
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<main role="main">
<div id="card-content" class="container">
<div class="card border-warning text-center">
<div class="card-header">
<ul class="nav nav-pills card-header-pills">
<li class="nav-item">
<a id="Linkitem1" data-toggle="collapse" href="#item1" role="button" aria-expanded="true" aria-controls="collapseOne" title="" class="nav-link text-white btn-warning active">item1</a>
</li>
<li class="nav-item">
<a id="Linkitem2" data-toggle="collapse" href="#item2" role="button" aria-expanded="true" title="" class="nav-link collapsed text-white">item2</a>
</li>
<li class="nav-item">
<a id="Linkitem3" data-toggle="collapse" href="#item3" role="button" aria-expanded="true" title="" class="nav-link collapsed text-white">item3</a>
</li>
</ul>
</div>
<!--Content item1-->
<div id="item1" class="animated fadeIn collapse show card-body" data-parent="#card-content">
<h5 class="card-title">title for item 1</h5>
<p class="card-text">content item 1.</p>
</div>
<!--content item 2-->
<div id="item2" class="animated fadeIn collapse card-body" data-parent="#card-content">
<h5 class="card-title">title item 2</h5>
<p class="card-text">content item 2</p>
<!--content 3-->
<div id="item 3" class="collapse card-body" data-parent="#card-content">
<h5 class="card-title">title item 3</h5>
<p class="card-text">content item 3</p>
</div>
</div>
</main>
This code is working. I am clicking in the navigation of linkitem1 and in the card-body is just content of item 1. if am clicking on linkitem2, I can see the content of item2.
You can use that way if it is possible. add class "Linkitem" with nav-item anchor tag and add class "item" with content item
$(".Linkitem").click(function(){
let dataId = $(".Linkitem").index(this);
$('.item:eq('+dataId+')').fadeIn(500);
$('.item:not(:eq('+dataId+'))').fadeOut(500);
$('.Linkitem:eq('+dataId+')').addClass("active btn-warning");
$('.Linkitem:not(:eq('+dataId+'))').removeClass("active btn-warning");
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.0/jquery.min.js"></script>
<main role="main">
<div id="card-content" class="container">
<div class="card border-warning text-center">
<div class="card-header">
<ul class="nav nav-pills card-header-pills">
<li class="nav-item">
<a id="Linkitem1" class="Linkitem" data-toggle="collapse" href="#item1" role="button" aria-expanded="true" aria-controls="collapseOne" title="" class="nav-link text-white btn-warning active">item1</a>
</li>
<li class="nav-item">
<a id="Linkitem2" class="Linkitem" data-toggle="collapse" href="#item2" role="button" aria-expanded="true" title="" class="nav-link collapsed text-white">item2</a>
</li>
<li class="nav-item">
<a id="Linkitem3" class="Linkitem" data-toggle="collapse" href="#item3" role="button" aria-expanded="true" title="" class="nav-link collapsed text-white">item3</a>
</li>
</ul>
</div>
<!--Content item1-->
<div id="item1" class="item animated fadeIn collapse show card-body" data-parent="#card-content">
<h5 class="card-title">title for item 1</h5>
<p class="card-text">content item 1.</p>
</div>
<!--content item 2-->
<div id="item2" class="item animated fadeIn collapse card-body" data-parent="#card-content">
<h5 class="card-title">title item 2</h5>
<p class="card-text">content item 2</p>
</div>
<!--content 3-->
<div id="item3" class="item collapse card-body" data-parent="#card-content">
<h5 class="card-title">title item 3</h5>
<p class="card-text">content item 3</p>
</div>
</div>
</main>
You can apply for loop, but you need to change attribute id on class. Otherwise, you should use additional attributes like a data-.
$(()=>{
$(".item").each(function(){
$(this).hide();
});
for (let i = 0; i < 3; i++){
$(".Linkitem").eq(i).click(function(){
$(".item").each(function(){
$(this).hide();
});
$(".item").eq(i).fadeIn(2500);
$(".Linkitem").each(function(){
$(this).removeClass("active btn-warning");
});
$(this).addClass("active btn-warning");
});
}
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<a class='Linkitem otherclass'>Linkitem11111111</a> <br>
<a class='Linkitem otherclass'>Linkitem22222222</a> <br>
<a class='Linkitem otherclass'>Linkitem33333333</a> <br>
<br><br><br>
<div class='item other'>1 1 1 1 1 1 1</div>
<div class='item other'>2 2 2 2 2 2 2</div>
<div class='item other'>3 3 3 3 3 3 3</div>
Here's a solution that uses event.target instead of this (or $(this)).
JQuery is still used for .fadeIn and .hide, although this could be accomplished without JQuery, too.
A click listener distinguishes between clicks on "link" buttons and all other clicks, and loops through the item divs, hiding them and showing only the "active" one.
// Calls `changeActiveItem` when something is clicked
document.addEventListener("click", changeActiveItem);
// Defines a listener (with automatic access to the triggering event)
function changeActiveItem(event){
const clickedElement = event.target; // `target` property holds the clicked element
// Makes sure the clicked element is a link before proceeding
if(!clickedElement.classList.contains("link")){
return; // Function will stop here if a non-link element was clicked
}
// Gets the item id stored in the link's "data-linked-item-id" attribute
const linkedItemId = clickedElement.dataset["linkedItemId"]; // Magic name conversion
// Deactivates and hides all items
const items = document.getElementsByClassName("item");
for(let item of items){
item.classList.remove("active");
item.classList.remove("btn-warning"); // This class currently has no effect
$(item).hide(); // Hides item
// Activates and animates the selected item
if(item.id === linkedItemId){
$(item).fadeIn(2500);
item.classList.add("active");
item.classList.add("btn-warning");
}
}
}
div{ margin-bottom: 15px; }
.item{ display: none; font-size: 3em; }
.active{ display: block; color: darkred; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<button id="item1Link" class="link" data-linked-item-id="item1">activate item 1</button>
<div>
<div id="item1" class="item active">Item 1</div>
</div>
<button id="item2Link" class="link" data-linked-item-id="item2">activate item 2</button>
<div>
<div id="item2" class="item">Item 2</div>
</div>
<button id="item3Link" class="link" data-linked-item-id="item3">activate item 3</button>
<div>
<div id="item3" class="item">Item 3</div>
</div>

Expanding and collapsing in UL tag

I have the follwing HTML, where there is a collapse (collapsebutton1) and expand button (expandbutton1) which will collapse and expand the div networkDevicesCollapsePanel, this is working as expected.
Now i need to bring the collapse and expand in each < UL >. There are three UL here, but there may be more later. How to achieve this?
<div class="col-xs-4">
<div class="panel" id="networkDevicesLinks">
<div style="float:right;">
<div ng-show="ciAttributesCount>0" id="collapsebutton1" class="nodisp expandcollapse expand-collapse-new-link-button no-print"><i class="glyphicon glyphicon-minus"></i>Collapse All</div>
<div ng-show="ciAttributesCount>0" id="expandbutton1" class="disp expandcollapse expand-collapse-new-link-button no-print"><i class="glyphicon glyphicon-plus"></i>Expand All</div>
</div>
<div class="panel-collapse collapse in" id="networkDevicesCollapsePanel">
<ul ng-repeat="nav in ciRelationshipHierarchyBySection" style="background:none; padding:0 10px;margin:5px;" class="nav nav-list">
<li>
<a style="cursor:pointer; padding: 2px 12px;" ng-click="showNetworkDevices(nav.IdentificationSourceId)">{{nav.IdentifySourceName}}</a> <span style="padding: 2px 12px;">Source Id: {{nav.IdentificationSourceId}}</span><br />
</li>
</ul>
</div>
</div>
</div>
Button Click code below
$("#expandbutton1").hide();
$("#expandbutton1").click(function () {
$('#networkDevicesLinks div.panel-collapse').addClass('in').css("height", "");
$("#expandbutton1").hide();
$("#collapsebutton1").show();
$('a[data-toggle="collapse"]').each(function (index) {
$(this).find("i").removeClass("fa-plus-square-o").addClass("fa-minus-square-o");
});
});
$("#collapsebutton1").click(function () {
$('#networkDevicesLinks div.panel-collapse').removeClass('in');
$("#expandbutton1").show();
$("#collapsebutton1").hide();
$('a[data-toggle="collapse"]').each(function (index) {
$(this).find("i").removeClass("fa-minus-square-o").addClass("fa-plus-square-o");
});
});
});
It may provide an idea,Try to use angular $index to toggle arrow and toggle client div.
And in angular we can assign each UL with dynamic classes which is hosted from expand and collapse button
<div class="col-xs-4">
<div class="panel" id="networkDevicesLinks">
<div style="float:right;" ng-repeat="nav in ciRelationshipHierarchyBySection track by $index">
<div ng-show="ciAttributesCount" id="collapsebutton_{{$index}}" data-toggle="collapse" data-target="#networkDevicesCollapsePanel_{{$index}}" class="nodisp expandcollapse expand-collapse-new-link-button no-print"><i class="glyphicon glyphicon-minus"></i>Collapse All</div>
<div ng-show="ciAttributesCount" id="expandbutton1_{{$index}}" class="disp expandcollapse expand-collapse-new-link-button no-print"><i class="glyphicon glyphicon-plus"></i>Expand All</div>
</div>
<div class="" >
<ul ng-repeat="nav in ciRelationshipHierarchyBySection track by $index" style="background:none; padding:0 10px;margin:5px;" class="nav nav-list panel-collapse collapse in" id="networkDevicesCollapsePanel_{{$index}}">
<li>
<a style="cursor:pointer; padding: 2px 12px;" ng-click="showNetworkDevices(nav.IdentificationSourceId)">{{nav.IdentifySourceName}}</a> <span style="padding: 2px 12px;">Source Id: {{nav.IdentificationSourceId}}</span><br />
</li>
</ul>
</div>
</div>
</div>
Revised Code below:
I am able to put collapse button in each repeat, but when i click, it opening a popup , instead of collapsing and expanding. Please see where it is wrong
<div class="">
<ul ng-repeat="nav in ciRelationshipHierarchyBySection track by $index" style="background:none; padding:0 10px;margin:5px;" class="nav nav-list panel-collapse collapse in" id="networkDevicesCollapsePanel_{{$index}}">
<li>
<div ng-show="ciAttributesCount" id="collapsebutton_{{$index}}" data-toggle="collapse" data-target="#networkDevicesCollapsePanel_{{$index}}" class="nodisp expandcollapse no-print"><i class="glyphicon glyphicon-minus"></i>Collapse All</div>
<a style="cursor:pointer; padding: 2px 12px;" ng-click="showNetworkDevices(nav.IdentificationSourceId)">{{nav.IdentifySourceName}}</a>
<span style="padding: 2px 12px;">Source Id: {{nav.IdentificationSourceId}}</span>
<br />
<span style="padding: 2px 12px;">Data Source: {{nav.DataSource}}</span>
<br />
<span style="padding: 2px 12px;">Create New: {{nav.IsCreateNew}}</span>
<br />
</li>
</ul>
</div>

Toggle addclass with jquery parent selector

I have some items products in a grid.
I want that when i click on each icon from item, it will toggle a class '.active' and also remove class if others from others items are visible.
This is my script so far, can add the class remove from others items but when i click on the same icon it doesn't toggle it (remove the class).
$('.items #show-actions').on('click', function(event) {
event.preventDefault();
var $this = $(this).parent().parent('.items');
var $that = $(this).closest('.items');
$('.items').find('.actions').not($this).removeClass('active');
$that.find('.actions').toggleClass('active');
});
<ul class="products-grid row">
<li class="items">
<img src="/images/myimage.png" "/>
<div class="product-info">
<span id="show-actions" class="glyphicon glyphicon-option-horizontal visible-sm visible-xs ic"></span>
<h2 class="product-brand">Test</h2>
<div class="actions text-center hidden">
<button class="btn-block">Ok</button>
</div>
</div>
</li>
<li class="items">
<img src="/images/myimage.png" "/>
<div class="product-info">
<span id="show-actions" class="glyphicon glyphicon-option-horizontal visible-sm visible-xs ic"></span>
<h2 class="product-brand">Test</h2>
<div class="actions text-center hidden">
<button class="btn-block">Ok</button>
</div>
</div>
</li>
</ul>
You need to remove this row:
$('.items').find('.actions').not($this).removeClass('active');
Because in your function you first remove the class, and then toggle it. In this case, if the element already has active class, it will be removed first, and then toggle will add it again (it looks like the element still has an active class, because operations are very fast). I have removed the row as described above and added some styles to see the difference, so here is the working snippet (click on "Show Actions" to see the difference):
$('.items #show-actions').on('click', function(event) {
event.preventDefault();
var $this = $(this).parent().parent('.items');
var $that = $(this).closest('.items');
$that.find('.actions').toggleClass('active');
});
.items #show-actions {
width: 100vw;
background-color: royalblue;
color: white;
}
.active {
background-color: red;
}
img {
width: 50px;
height: auto;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<ul class="products-grid row">
<li class="items">
<img src="https://pp.userapi.com/c629327/v629327473/db66/r051joYFRX0.jpg" />
<div class="product-info">
<span id="show-actions" class="glyphicon glyphicon-option-horizontal visible-sm visible-xs ic">Show Actions</span>
<h2 class="product-brand">Test</h2>
<div class="actions text-center hidden">
<button class="btn-block">Ok</button>
</div>
</div>
</li>
<li class="items">
<img src="https://pp.userapi.com/c629327/v629327473/db66/r051joYFRX0.jpg" />
<div class="product-info">
<span id="show-actions" class="glyphicon glyphicon-option-horizontal visible-sm visible-xs ic">Show Actions</span>
<h2 class="product-brand">Test</h2>
<div class="actions text-center hidden">
<button class="btn-block">Ok</button>
</div>
</div>
</li>
</ul>
First, you can't have duplicate ID's on any HTML page. I suggest you change #show-actions to a class for the rather than an ID.
Second, you also have some extra quote marks in your img element.
Once you do that it's pretty simple.
$('.show-actions').on('click', function() {
var items = $('.items');
items.removeClass('active');
$(this).parent().parent('.items').addClass('active');
});
.active {
background-color:red;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<ul class="products-grid row">
<li class="items">
<a class="product-image"><img src="/images/myimage.png"/></a>
<div class="product-info">
<span class="show-actions glyphicon glyphicon-option-horizontal visible-sm visible-xs ic">TOGGLE ME</span>
<h2 class="product-brand">Test</h2>
<div class="actions text-center hidden">
<button class="btn-block">Ok</button>
</div>
</div>
</li>
<li class="items">
<a class="product-image"><img src="/images/myimage.png"/></a>
<div class="product-info">
<span class="show-actions glyphicon glyphicon-option-horizontal visible-sm visible-xs ic">TOGGLE ME</span>
<h2 class="product-brand">Test</h2>
<div class="actions text-center hidden">
<button class="btn-block">Ok</button>
</div>
</div>
</li>
</ul>

Bootstrap 3 : Accordion Chevron Icon pointing up or down

sorry for my english.
First, what is wrong in the script? The chevron doesn't change.
I'm not a web master. I'm a beginner. Thanks a lot.
This is my template :
<div class="panel-heading">
<div class="panel-title">Tableau de bord
<a data-toggle="collapse" data-parent="#accordion" href="#collapseOne"><span class="pull-right clickable"><i class="glyphicon glyphicon-chevron-up"></i></span></a>
</div>
</div>
<div id="collapseOne" class="panel-collapse collapse in">
<ul class="list-group">
<li class="list-group-item"><i class="fa fa-user"></i>Information</li>
<li class="list-group-item"><i class="fa fa-power-off"></i>Log out</li>
</ul><!--/.list-group-->
</div><!--/collapseOne-->
<div class="panel-footer">
<div class="panel-title">Archives
<a data-toggle="collapse" data-parent="#accordion" href="#collapseTwo"><span class="pull-right clickable"><i class="glyphicon glyphicon-chevron-up"></i></span></a>
</div>
</div>
<div id="collapseTwo" class="panel-collapse collapse in">
<ul class="list-group" style="margin-bottom:0">
<li class="list-group-item"><i class="fa fa-arrow-right"></i>2015</li>
<li class="list-group-item"><i class="fa fa-arrow-right"></i>2014</li>
</ul><!--/.list-group-->
</div><!--/collapseTwo-->
</div><!--/.panel-blue-->
</div><!--/.panel-group accordion-->
and this is the script :
<script>
$('.clickable').on('click', function (e) {
var $this = $(this);
if (!$this.hasClass('panel-collapsed')) {
$this.parents('.panel').find('.panel-title').slideUp();
$this.addClass('panel-collapse');
$this.find('i').removeClass('glyphicon-chevron-up').addClass('glyphicon-chevron-down');
} else {
$this.parents('.panel').find('.panel').slideDown();
$this.removeClass('.panel-title');
$this.find('i').removeClass('glyphicon-chevron-down').addClass('glyphicon-chevron-up');
}
})
</script>
I replaced the two lines addClass/removeClass by a toggleClass which do the same, and it seems to work : http://jsfiddle.net/FLZpk/1/
$('.clickable').on('click', function (e) {
var $this = $(this);
if (!$this.hasClass('panel-collapsed')) {
$this.parents('.panel').find('.panel-title').slideUp();
$this.addClass('panel-collapse');
} else {
$this.parents('.panel').find('.panel').slideDown();
$this.removeClass('.panel-title');
}
$this.find('i').toggleClass('glyphicon-chevron-up glyphicon-chevron-down');
})
jQuery toggleClass doc : https://api.jquery.com/toggleClass/

Collapse nested accordion groups based on custom class

I'm using Twitter Bootstrap 2.3.2 with Asp.net MVC.
I have a set of nested accordions on a tab pane and other accordions on other tab panes.
The External accordions are in an accordion-group and the Internal accordions are in another group, nested inside each External accordion.
The colours are applied using CSS rules on custom classes.
.accordion-toggle.outcome {
background-color:#d9edf7;
}
.accordion-toggle.outcome.collapsed {
background-color:White;
}
.accordion-toggle.achievement {
background-color:#dff0d8;
}
.accordion-toggle.achievement.collapsed {
background-color:White;
}
I need to force the full collapse of the open accordions depending on which new accordion is selected. If an internal accordion is selected then I only want the other internal accordions to close. If an external accordion is selected I want the internal and external accordions to close.
Closing means assigning the 'collapsed' class to the accordion-toggle, which determines the highlight colour of the accordion-heading.
I have the following javascript which needs amending to select the different levels of accordion. The class of 'outcome' for External and 'achievement' for internal are currently the only difference between the two.
I've tried a variety of if/else combinations but none of them seem to work. I've included the javascript I use when changing tabs as this might change how I need to approach this.
<script type="text/javascript">
//need to collapse all when tab changes
$('a[data-toggle="tab"]').on('shown', function (e) {
$('.accordion').find('.accordion-toggle').addClass('collapsed');
$('.accordion').find('.accordion-body').removeClass('in');
$('.accordion').find('.accordion-body').height('0px');
}
);
//collapse accordion depending on class
// from https://github.com/twbs/bootstrap/issues/7213#issuecomment-18547519
$('.collapse').on('hide', function () {
//do something to select internal or external accordion here...
$('[href="#' + $(this).attr('id') + '"]').addClass('collapsed');
});
</script>
The HTML for the above accordion set is as follows:
<div class="accordion" id="interventions">
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle outcome collapsed" data-toggle="collapse" data-parent="#interventions" href="#collapse12">
<label for="">Test Finance</label>
</a>
</div>
<div id="collapse12" class="accordion-body collapse">
<div class="accordion" id="intervention0">
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle achievement" data-toggle="collapse" data-parent="#intervention0" href="#collapse012">
<label for="">Achievement Finance 3</label>
</a>
</div>
<div id="collapse012" class="accordion-body collapse">
<div class="accordion-inner">
<div class="accordion-group">Test group</div>
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle achievement" data-toggle="collapse" data-parent="#intervention0" href="#collapse111">
<label for="">Achievement Finance 2</label>
</a>
</div>
<div id="collapse111" class="accordion-body collapse">
<div class="accordion-inner">
<div class="accordion-group">Test group</div>
</div>
</div>
</div>
</div>
</div>
</div>
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle outcome collapsed" data-toggle="collapse" data-parent="#interventions" href="#collapse10">
<label for="">Huge Money</label>
</a>
</div>
<div id="collapse10" class="accordion-body collapse">
<div class="accordion" id="intervention1">
<div class="accordion-group">
<div class="accordion-heading">
<a class="accordion-toggle achievement" data-toggle="collapse" data-parent="#intervention1" href="#collapse010">
<label for="">Achievement Finance 1</label>
</a>
</div>
<div id="collapse010" class="accordion-body collapse">
<div class="accordion-inner">
<div class="accordion-group">Test group</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
I managed to sort this out using the following javascript. The custom classes are only used by the CSS to apply the correct colour to an accordion-toggle when it is open or collapsed.
The css is amended to:
.accordion-toggle.outcome {
background-color:#d9edf7;
}
.accordion-toggle.achievement {
background-color:#dff0d8;
}
.accordion-toggle.collapsed {
background-color:transparent;
}
Thanks to Ammu for helping with this related question.
Javascript
//function to collapse all accordions when changing tabs
function tabCollapse() {
$('.accordion').find('.accordion-toggle').addClass('collapsed');
$('.accordion').find('.accordion-body').removeClass('in');
$('.accordion').find('.accordion-body').height('0px');
}
//function to fully collapse accordion on same page
function pageCollapse(inner) {
$('#' + inner).find('.accordion-toggle').addClass('collapsed');
$('#' + inner).find('.accordion-body').removeClass('in');
$('#' + inner).find('.accordion-body').height('0px');
}
//collapse all when tab changes
$('a[data-toggle="tab"]').on('shown', function () {
tabCollapse();
});
//collapse inner accordion on same page
$('.accordion').on('hidden', function (e) {
var inner = e.target.id;
pageCollapse(inner);
});
//on hide remove colour
$('.accordion').on('hide', function (e) {
var selected = e.target.id;
$('#' + selected).siblings().find('.accordion-toggle').addClass('collapsed');
});

Categories