A Simple jQuery Accordeon Menu
Some days ago I wanted to reinvent the wheel and create a accordeon menu with jQuery. Here I explain how I did.
First we prepare our page like the following:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" dir="ltr" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; utf-8" />
<script type="text/javascript" src="jquery-1.3.2.min.js"></script>
</head>
<body>
<div id="menu" align="center">
<div id="header_1">First heading</div>
<div id="content_1">First content</div>
<div id="header_2">Second heading</div>
<div id="content_2">Second content</div>
</div>
</body>
</html>
And then set the css for the menu:
body { font: 10pt Sans; }
#menu { width: 800px; margin-left: 200px;}
#menu div { padding-top: 10px; }
div[id^="header"] { background: #659EC7; color: #000; font-size: 12pt; height: 20px; padding-bottom: 10px;}
div[id^="content"] { background: #98AFC7; color: #fff; padding-bottom: 10px; text-align: left; overflow: auto;}
.hidden { display: none; }
The part I want to have your attention on is the css selector I have used. The meaning of "div[id^="header"] is all the divs of which ids are starting with "header". In the following line we set the rules for the divs of which ids are starting with content.
The next step is taking care of the jQuery part. Here is the list of what must be done: - hide all divs those are starting with content and children of the div with the id "menu" and add them to childIds array. - adding a click method to those divs. - in the click method, if the divs content div is open it should be closed, if it's not open, close all the other open divs and open this one.
This is all we must do. Now write the code.
$(document).ready(function () {
// the array that will have the divs of which ids are starting with content.
childIds = new Array();
// for each children of the div with the id menu..
$("#menu").children().each(function(i) {
// split the div id with "_"
dName = this.id.split("_");
// if first index is content add this div to childIds and hide it.
if (dName[0] == 'content') { childIds[i] = this.id; $("#"+this.id).addClass('hidden'); }
// if first index is not content -in this case, title-
else {
// add click method for this div
$("#"+this.id).click(function() {
// split the div id and get the content_id
content_id = "content_"+this.id.split("_")[1];
// if this div is visible, then hide it
if ($("#"+content_id).css('display') == 'block') { $("#"+content_id).slideToggle('slow'); }
// if this div isn't visible
else {
// for each div in childIds array
jQuery.each(childIds, function(j, id) {
// if this child is not equal to content_id then hide it.
if (id != content_id) { $("#"+id).css('display', 'none') }
// if this child is equal to content_id then display it.
else { $("#"+content_id).slideToggle("slow"); }
});
}
});
}
});
});
After collecting them together, here is what we have:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" dir="ltr" lang="EN">
<head>
<meta http-equiv="Content-Type" content="text/html; utf-8" />
<script type="text/javascript" src="jquery-1.3.2.min.js"></script>
<body>
<style type="text/css">
body { font: 10pt Sans; }
#menu { width: 800px; margin-left: 200px;}
#menu div { padding-top: 10px; }
div[id^="header"] { background: #659EC7; color: #000; font-size: 12pt; height: 20px; padding-bottom: 10px;}
div[id^="content"] { background: #98AFC7; color: #fff; padding-bottom: 10px; text-align: left; overflow: auto;}
.hidden { display: none; }
</style>
<script type="text/javascript">
$(document).ready(function () {
// the array that will have the divs of which ids are starting with content.
childIds = new Array();
// for each children of the div with the id menu..
$("#menu").children().each(function(i) {
// split the div id with "_"
dName = this.id.split("_");
// if first index is content add this div to childIds and hide it.
if (dName[0] == 'content') { childIds[i] = this.id; $("#"+this.id).addClass('hidden'); }
// if first index is not content -in this case, title-
else {
// add click method for this div
$("#"+this.id).click(function() {
// split the div id and get the content_id
content_id = "content_"+this.id.split("_")[1];
// if this div is visible, then hide it
if ($("#"+content_id).css('display') == 'block') { $("#"+content_id).slideToggle('slow'); }
// if this div isn't visible
else {
// for each div in childIds array
jQuery.each(childIds, function(j, id) {
// if this child is not equal to content_id then hide it.
if (id != content_id) { $("#"+id).css('display', 'none') }
// if this child is equal to content_id then display it.
else { $("#"+content_id).slideToggle("slow"); }
});
}
});
}
});
});
</script>
<div id="menu" align="center">
<div id="header_1">First heading</div>
<div id="content_1">First content</div>
<div id="header_2">Second heading</div>
<div id="content_2">Second content</div>
</div>
</body>
</html>
Enjoy your accordeon menu! :)

Comments
Leave a Response