In this tutorial I will show you how make a jQuery accordion menu navigation in Wordpress. This tutorial will not show you how to code an accordion menu from scratch, but instead walk you through the process of downloading one of our free designs, and then integrating it with the Wordpress menu system.

Note:
Check out our Wordpress Plugin for an easier way to create accordion menus.

Requirements

  • Ability to upload files to your Wordpress theme directory.
  • Ability to edit your theme's functions.php file.

Demo

Click on a menu item to expand its sub menus. Check out our other accordion menus menu designs that will also work with this tutorial.

Source Code

Use the link below to download the source code for the accordion menu.

Download Source

Create a Menu in Wordpress

Chances are you already have a menu built in Wordpress. Wordpress has an easy to use, drag-n-drop interface for you to create a menu structure. If you haven't already, go to Appearance > Menus to build and save a custom menu. Make sure to give your menu a name and remember that name for later.

Upload Menu Files

Unzip the source code files and you should see a directory structure that looks like this:

Upload the whole folder called cssmenu to your Wordpress theme's directory.

Functions.php

The next step is to add a little code to our functions.php file. Almost every Wordpress theme has a functions.php file, but if you don't see one in your theme just go ahead and create it.

What we want to do is let Wordpress know about the new CSS and javascript files we just uploaded. The following function does just that. Place the below snippet of code at the bottom of your functions.php file.


add_action('wp_enqueue_scripts', 'cssmenumaker_scripts_styles' );
function cssmenumaker_scripts_styles() {
wp_enqueue_style( 'cssmenu-styles', get_template_directory_uri() . '/cssmenu/styles.css');
wp_enqueue_script('cssmenu-scripts', get_template_directory_uri() . '/cssmenu/script.js');
}

The next bit of code we need to add to the functions.php file is our custom Wordpress Walker Class. Our custom walker class will alter the HTML output of a Wordpress menu so that it will be compatible with the CSS styles we just uploaded.


class CSS_Menu_Maker_Walker extends Walker {

var $db_fields = array( 'parent' => 'menu_item_parent', 'id' => 'db_id' );

function start_lvl( &$output, $depth = 0, $args = array() ) {
$indent = str_repeat("\t", $depth);
$output .= "\n$indent

    \n";
    }

    function end_lvl( &$output, $depth = 0, $args = array() ) {
    $indent = str_repeat("\t", $depth);
    $output .= "$indent

\n";
}

function start_el( &$output, $item, $depth = 0, $args = array(), $id = 0 ) {

global $wp_query;
$indent = ( $depth ) ? str_repeat( "\t", $depth ) : '';
$class_names = $value = '';
$classes = empty( $item->classes ) ? array() : (array) $item->classes;

/* Add active class */
if(in_array('current-menu-item', $classes)) {
$classes[] = 'active';
unset($classes['current-menu-item']);
}

/* Check for children */
$children = get_posts(array('post_type' => 'nav_menu_item', 'nopaging' => true, 'numberposts' => 1, 'meta_key' => '_menu_item_menu_item_parent', 'meta_value' => $item->ID));
if (!empty($children)) {
$classes[] = 'has-sub';
}

$class_names = join( ' ', apply_filters( 'nav_menu_css_class', array_filter( $classes ), $item, $args ) );
$class_names = $class_names ? ' class="' . esc_attr( $class_names ) . '"' : '';

$id = apply_filters( 'nav_menu_item_id', 'menu-item-'. $item->ID, $item, $args );
$id = $id ? ' id="' . esc_attr( $id ) . '"' : '';

$output .= $indent . '
';

$attributes = ! empty( $item->attr_title ) ? ' title="' . esc_attr( $item->attr_title ) .'"' : '';
$attributes .= ! empty( $item->target ) ? ' target="' . esc_attr( $item->target ) .'"' : '';
$attributes .= ! empty( $item->xfn ) ? ' rel="' . esc_attr( $item->xfn ) .'"' : '';
$attributes .= ! empty( $item->url ) ? ' href="' . esc_attr( $item->url ) .'"' : '';

$item_output = $args->before;
$item_output .= '';
$item_output .= $args->link_before . apply_filters( 'the_title', $item->title, $item->ID ) . $args->link_after;
$item_output .= '
';
$item_output .= $args->after;

$output .= apply_filters( 'walker_nav_menu_start_el', $item_output, $item, $depth, $args );
}

function end_el( &$output, $item, $depth = 0, $args = array() ) {
$output .= "

\n";
}
}

Print Menu in Theme File

Now that we have our functions.php all setup, we need to print our accordion menu in one of the theme template files. To do this we use the wp_nav_menu() function and pass it the variables for our menu. Where ever you place this code is where your menu will be printed out.


wp_nav_menu(array(
'menu' => 'Main Navigation', // This will be different for you.
'container_id' => 'cssmenu',
'walker' => new CSS_Menu_Maker_Walker()
));
?>

  1. menu => Name of the Wordpress menu you created.
  2. container_id => The ID that will be applied to the containing DIV around the menu. cssmenu the default we use for all our menus. You can change this if you want but you will also have to update the CSS file.
  3. walker => This tells the menu to use our custom Walker class to print out the HTML.

Conclusion

That's it! If you did everything correctly you should have a shiny new Wordpress accordion menu. If you have any questions make sure to leave a comment and we will try to get back to you.

Meet the Author

Russell Martin is a computer engineer and internet aficionado. He has been working in the web design/development industry for over 10 years now and enjoys the freedom of a job away from the office. Currently living in Thailand, he is focusing on sharing his web design knowledge by writing blog posts and tutorials.