Simple expandable menu with jQuery

I recently needed a nested and expandable navigation system (accordion style) for a project I was working on.  I took a look around at the existing jquery plugins and was surprised by the complexity of them. To me, there’s no reason for a simple menu to require 200 lines of JavaScript.  Thankfully jQuery makes it possible to pack a lot of punch into just a few lines of code.  While I recognize the other plugins offer more functionality, I wanted to show that these days it sometimes makes more sense to just roll your own solution. Not only does this solution cut down on the number of bytes that the user has to download, but you’ll also have code that is more concise and easier to maintain.

Click here to check out the demo and download the code

Here’s the jQuery magic that I came up with:

$(document).ready(function() {
    $(".menu").click(function(e) {
        // unhighlight the previous menu selection
        $(".menu .selected").removeClass("selected");
        // highlight the selected item & its parents
        $(e.target).closest("li").addClass("selected").parent().parent().addClass("selected");
    });
});

The HTML is a standard nested list and looks something like this:

<div class='menu'>
    <ul>
        <li><a href='http://www.onlineaspect.com'>My blog</a></li>
        <li><a href='#'>My profiles</a>
            <ul>
                <li><a href='http://www.facebook.com/joshfraser'>Facebook</a></li>
                <li><a href='http://www.linkedin.com/in/joshuafraser'>LinkedIn</a></li>
                <li><a href='http://www.twitter.com/joshfraser'>Twitter</a></li>
            </ul>
        </li>
    </ul>
</div>

And the CSS is easy to customize to match your own look and feel:

.menu {
    width:200px;
}
.menu a {
    color:#666;
    text-decoration:none;
}
.menu ul {
    padding:0;
    border-top:1px solid #CCC;
}
.menu ul li {
    list-style:none;
    border-bottom:1px solid #CCC;
}
.menu ul li a {
    text-indent:6px;
    display:block;
    padding:6px;
}
.menu ul li a:hover, .menu ul li.selected a  {
    color:#FFF;
    background-color:#006363;
}
/* nested items */
.menu ul li ul {
    display:none;
}
.menu ul li.selected ul {
    display:block;
}
.menu ul li.selected ul a {
    color:#666;
    background-color:white;
    border-left:6px solid white;
}
.menu ul li ul li {
    border-bottom:1px solid white;
}
.menu ul li ul li:first-child {
    border-top:1px solid white;
}
.menu ul li.selected ul li.selected a, .menu ul li.selected ul li a:hover {
    color:#FFF;
    background-color:#7EB0B0;
    border-left:6px solid #006363;
}

That’s it. Remember – guard your bytes!